Payload -> Blob, Dependent -> Pointer, Member -> Set
This commit is contained in:
@@ -1,5 +1,4 @@
|
||||
export * from './interfaces';
|
||||
export * from './data_type';
|
||||
export * from './dependent_data_type';
|
||||
export * from './member_data_type';
|
||||
export * from './payload_data_type';
|
||||
import * as AbstractDataTypes from './types';
|
||||
export { AbstractDataTypes };
|
||||
|
@@ -1,13 +1,13 @@
|
||||
import { DataItem } from 'ethereum-types';
|
||||
import * as _ from 'lodash';
|
||||
|
||||
import { CalldataBlock, PayloadCalldataBlock, RawCalldata } from '../calldata';
|
||||
import { DecodingRules } from '../utils/rules';
|
||||
import { CalldataBlock, CalldataBlocks, RawCalldata } from '../../calldata';
|
||||
import { DecodingRules } from '../../utils/rules';
|
||||
|
||||
import { DataType } from './data_type';
|
||||
import { DataTypeFactory } from './interfaces';
|
||||
import { DataType } from '../data_type';
|
||||
import { DataTypeFactory } from '../interfaces';
|
||||
|
||||
export abstract class PayloadDataType extends DataType {
|
||||
export abstract class Blob extends DataType {
|
||||
protected _hasConstantSize: boolean;
|
||||
|
||||
public constructor(dataItem: DataItem, factory: DataTypeFactory, hasConstantSize: boolean) {
|
||||
@@ -15,12 +15,12 @@ export abstract class PayloadDataType extends DataType {
|
||||
this._hasConstantSize = hasConstantSize;
|
||||
}
|
||||
|
||||
public generateCalldataBlock(value: any, parentBlock?: CalldataBlock): PayloadCalldataBlock {
|
||||
public generateCalldataBlock(value: any, parentBlock?: CalldataBlock): CalldataBlocks.Blob {
|
||||
const encodedValue = this.encodeValue(value);
|
||||
const name = this.getDataItem().name;
|
||||
const signature = this.getSignature();
|
||||
const parentName = parentBlock ? parentBlock.getName() : '';
|
||||
const block = new PayloadCalldataBlock(name, signature, parentName, encodedValue);
|
||||
const block = new CalldataBlocks.Blob(name, signature, parentName, encodedValue);
|
||||
return block;
|
||||
}
|
||||
|
@@ -0,0 +1,3 @@
|
||||
export * from './blob';
|
||||
export * from './pointer';
|
||||
export * from './set';
|
@@ -2,14 +2,14 @@ import { DataItem } from 'ethereum-types';
|
||||
import * as ethUtil from 'ethereumjs-util';
|
||||
import * as _ from 'lodash';
|
||||
|
||||
import { CalldataBlock, DependentCalldataBlock, RawCalldata } from '../calldata';
|
||||
import * as Constants from '../utils/constants';
|
||||
import { DecodingRules } from '../utils/rules';
|
||||
import { CalldataBlock, CalldataBlocks, RawCalldata } from '../../calldata';
|
||||
import * as Constants from '../../utils/constants';
|
||||
import { DecodingRules } from '../../utils/rules';
|
||||
|
||||
import { DataType } from './data_type';
|
||||
import { DataTypeFactory } from './interfaces';
|
||||
import { DataType } from '../data_type';
|
||||
import { DataTypeFactory } from '../interfaces';
|
||||
|
||||
export abstract class DependentDataType extends DataType {
|
||||
export abstract class Pointer extends DataType {
|
||||
protected _dependency: DataType;
|
||||
protected _parent: DataType;
|
||||
private readonly _isStatic: boolean;
|
||||
@@ -21,7 +21,7 @@ export abstract class DependentDataType extends DataType {
|
||||
this._isStatic = true;
|
||||
}
|
||||
|
||||
public generateCalldataBlock(value: any, parentBlock?: CalldataBlock): DependentCalldataBlock {
|
||||
public generateCalldataBlock(value: any, parentBlock?: CalldataBlock): CalldataBlocks.Pointer {
|
||||
if (parentBlock === undefined) {
|
||||
throw new Error(`DependentDataType requires a parent block to generate its block`);
|
||||
}
|
||||
@@ -29,7 +29,7 @@ export abstract class DependentDataType extends DataType {
|
||||
const name = this.getDataItem().name;
|
||||
const signature = this.getSignature();
|
||||
const parentName = parentBlock ? parentBlock.getName() : '';
|
||||
const block = new DependentCalldataBlock(name, signature, parentName, dependencyBlock, parentBlock);
|
||||
const block = new CalldataBlocks.Pointer(name, signature, parentName, dependencyBlock, parentBlock);
|
||||
return block;
|
||||
}
|
||||
|
@@ -2,16 +2,17 @@ import { DataItem } from 'ethereum-types';
|
||||
import * as ethUtil from 'ethereumjs-util';
|
||||
import * as _ from 'lodash';
|
||||
|
||||
import { BigNumber } from '../../configured_bignumber';
|
||||
import { CalldataBlock, MemberCalldataBlock, RawCalldata } from '../calldata';
|
||||
import * as Constants from '../utils/constants';
|
||||
import { DecodingRules } from '../utils/rules';
|
||||
import { BigNumber } from '../../../configured_bignumber';
|
||||
import { CalldataBlock, CalldataBlocks, RawCalldata } from '../../calldata';
|
||||
import * as Constants from '../../utils/constants';
|
||||
import { DecodingRules } from '../../utils/rules';
|
||||
|
||||
import { DataType } from './data_type';
|
||||
import { DependentDataType } from './dependent_data_type';
|
||||
import { DataTypeFactory, MemberIndexByName } from './interfaces';
|
||||
import { DataType } from '../data_type';
|
||||
import { DataTypeFactory, MemberIndexByName } from '../interfaces';
|
||||
|
||||
export abstract class MemberDataType extends DataType {
|
||||
import { Pointer } from './pointer';
|
||||
|
||||
export abstract class Set extends DataType {
|
||||
protected readonly _arrayLength: number | undefined;
|
||||
protected readonly _arrayElementType: string | undefined;
|
||||
private readonly _memberIndexByName: MemberIndexByName;
|
||||
@@ -38,7 +39,7 @@ export abstract class MemberDataType extends DataType {
|
||||
}
|
||||
}
|
||||
|
||||
public generateCalldataBlock(value: any[] | object, parentBlock?: CalldataBlock): MemberCalldataBlock {
|
||||
public generateCalldataBlock(value: any[] | object, parentBlock?: CalldataBlock): CalldataBlocks.Set {
|
||||
const block =
|
||||
value instanceof Array
|
||||
? this._generateCalldataBlockFromArray(value, parentBlock)
|
||||
@@ -94,13 +95,13 @@ export abstract class MemberDataType extends DataType {
|
||||
|
||||
// Search for dependent members
|
||||
const dependentMember = _.find(this._members, (member: DataType) => {
|
||||
return member instanceof DependentDataType;
|
||||
return member instanceof Pointer;
|
||||
});
|
||||
const isStatic = dependentMember === undefined; // static if we couldn't find a dependent member
|
||||
return isStatic;
|
||||
}
|
||||
|
||||
protected _generateCalldataBlockFromArray(value: any[], parentBlock?: CalldataBlock): MemberCalldataBlock {
|
||||
protected _generateCalldataBlockFromArray(value: any[], parentBlock?: CalldataBlock): CalldataBlocks.Set {
|
||||
// Sanity check length
|
||||
if (this._arrayLength !== undefined && value.length !== this._arrayLength) {
|
||||
throw new Error(
|
||||
@@ -111,7 +112,7 @@ export abstract class MemberDataType extends DataType {
|
||||
}
|
||||
|
||||
const parentName = parentBlock === undefined ? '' : parentBlock.getName();
|
||||
const methodBlock: MemberCalldataBlock = new MemberCalldataBlock(
|
||||
const methodBlock: CalldataBlocks.Set = new CalldataBlocks.Set(
|
||||
this.getDataItem().name,
|
||||
this.getSignature(),
|
||||
parentName,
|
||||
@@ -128,23 +129,23 @@ export abstract class MemberDataType extends DataType {
|
||||
methodBlock.setHeader(lenBuf);
|
||||
}
|
||||
|
||||
const memberBlocks: CalldataBlock[] = [];
|
||||
const memberCalldataBlocks: CalldataBlock[] = [];
|
||||
_.each(members, (member: DataType, idx: number) => {
|
||||
const block = member.generateCalldataBlock(value[idx], methodBlock);
|
||||
memberBlocks.push(block);
|
||||
memberCalldataBlocks.push(block);
|
||||
});
|
||||
methodBlock.setMembers(memberBlocks);
|
||||
methodBlock.setMembers(memberCalldataBlocks);
|
||||
return methodBlock;
|
||||
}
|
||||
|
||||
protected _generateCalldataBlockFromObject(obj: object, parentBlock?: CalldataBlock): MemberCalldataBlock {
|
||||
protected _generateCalldataBlockFromObject(obj: object, parentBlock?: CalldataBlock): CalldataBlocks.Set {
|
||||
const parentName = parentBlock === undefined ? '' : parentBlock.getName();
|
||||
const methodBlock: MemberCalldataBlock = new MemberCalldataBlock(
|
||||
const methodBlock: CalldataBlocks.Set = new CalldataBlocks.Set(
|
||||
this.getDataItem().name,
|
||||
this.getSignature(),
|
||||
parentName,
|
||||
);
|
||||
const memberBlocks: CalldataBlock[] = [];
|
||||
const memberCalldataBlocks: CalldataBlock[] = [];
|
||||
const childMap = _.cloneDeep(this._memberIndexByName);
|
||||
_.forOwn(obj, (value: any, key: string) => {
|
||||
if (!(key in childMap)) {
|
||||
@@ -153,7 +154,7 @@ export abstract class MemberDataType extends DataType {
|
||||
);
|
||||
}
|
||||
const block = this._members[this._memberIndexByName[key]].generateCalldataBlock(value, methodBlock);
|
||||
memberBlocks.push(block);
|
||||
memberCalldataBlocks.push(block);
|
||||
delete childMap[key];
|
||||
});
|
||||
|
||||
@@ -161,7 +162,7 @@ export abstract class MemberDataType extends DataType {
|
||||
throw new Error(`Could not assign tuple to object: missing keys ${Object.keys(childMap)}`);
|
||||
}
|
||||
|
||||
methodBlock.setMembers(memberBlocks);
|
||||
methodBlock.setMembers(memberCalldataBlocks);
|
||||
return methodBlock;
|
||||
}
|
||||
|
20
packages/utils/src/abi_encoder/calldata/blocks/blob.ts
Normal file
20
packages/utils/src/abi_encoder/calldata/blocks/blob.ts
Normal file
@@ -0,0 +1,20 @@
|
||||
import { CalldataBlock } from '../calldata_block';
|
||||
|
||||
export class Blob extends CalldataBlock {
|
||||
private readonly _blob: Buffer;
|
||||
|
||||
constructor(name: string, signature: string, parentName: string, blob: Buffer) {
|
||||
const headerSizeInBytes = 0;
|
||||
const bodySizeInBytes = blob.byteLength;
|
||||
super(name, signature, parentName, headerSizeInBytes, bodySizeInBytes);
|
||||
this._blob = blob;
|
||||
}
|
||||
|
||||
public toBuffer(): Buffer {
|
||||
return this._blob;
|
||||
}
|
||||
|
||||
public getRawData(): Buffer {
|
||||
return this._blob;
|
||||
}
|
||||
}
|
3
packages/utils/src/abi_encoder/calldata/blocks/index.ts
Normal file
3
packages/utils/src/abi_encoder/calldata/blocks/index.ts
Normal file
@@ -0,0 +1,3 @@
|
||||
export * from './blob';
|
||||
export * from './pointer';
|
||||
export * from './set';
|
@@ -1,10 +1,10 @@
|
||||
import * as ethUtil from 'ethereumjs-util';
|
||||
|
||||
import * as Constants from '../utils/constants';
|
||||
import * as Constants from '../../utils/constants';
|
||||
|
||||
import { CalldataBlock } from './calldata_block';
|
||||
import { CalldataBlock } from '../calldata_block';
|
||||
|
||||
export class DependentCalldataBlock extends CalldataBlock {
|
||||
export class Pointer extends CalldataBlock {
|
||||
public static readonly RAW_DATA_START = new Buffer('<');
|
||||
public static readonly RAW_DATA_END = new Buffer('>');
|
||||
private static readonly _DEPENDENT_PAYLOAD_SIZE_IN_BYTES = 32;
|
||||
@@ -14,8 +14,8 @@ export class DependentCalldataBlock extends CalldataBlock {
|
||||
private _aliasFor: CalldataBlock | undefined;
|
||||
|
||||
constructor(name: string, signature: string, parentName: string, dependency: CalldataBlock, parent: CalldataBlock) {
|
||||
const headerSizeInBytes = DependentCalldataBlock._EMPTY_HEADER_SIZE;
|
||||
const bodySizeInBytes = DependentCalldataBlock._DEPENDENT_PAYLOAD_SIZE_IN_BYTES;
|
||||
const headerSizeInBytes = Pointer._EMPTY_HEADER_SIZE;
|
||||
const bodySizeInBytes = Pointer._DEPENDENT_PAYLOAD_SIZE_IN_BYTES;
|
||||
super(name, signature, parentName, headerSizeInBytes, bodySizeInBytes);
|
||||
this._parent = parent;
|
||||
this._dependency = dependency;
|
||||
@@ -28,9 +28,9 @@ export class DependentCalldataBlock extends CalldataBlock {
|
||||
const parentOffset = this._parent.getOffsetInBytes();
|
||||
const parentHeaderSize = this._parent.getHeaderSizeInBytes();
|
||||
const pointer: number = destinationOffset - (parentOffset + parentHeaderSize);
|
||||
const pointerBuf = ethUtil.toBuffer(`0x${pointer.toString(Constants.HEX_BASE)}`);
|
||||
const evmWordWidthInBytes = 32;
|
||||
const pointerBufPadded = ethUtil.setLengthLeft(pointerBuf, evmWordWidthInBytes);
|
||||
const pointerHex = `0x${pointer.toString(Constants.HEX_BASE)}`;
|
||||
const pointerBuf = ethUtil.toBuffer(pointerHex);
|
||||
const pointerBufPadded = ethUtil.setLengthLeft(pointerBuf, Constants.EVM_WORD_WIDTH_IN_BYTES);
|
||||
return pointerBufPadded;
|
||||
}
|
||||
|
||||
@@ -50,9 +50,9 @@ export class DependentCalldataBlock extends CalldataBlock {
|
||||
public getRawData(): Buffer {
|
||||
const dependencyRawData = this._dependency.getRawData();
|
||||
const rawDataComponents: Buffer[] = [];
|
||||
rawDataComponents.push(DependentCalldataBlock.RAW_DATA_START);
|
||||
rawDataComponents.push(Pointer.RAW_DATA_START);
|
||||
rawDataComponents.push(dependencyRawData);
|
||||
rawDataComponents.push(DependentCalldataBlock.RAW_DATA_END);
|
||||
rawDataComponents.push(Pointer.RAW_DATA_END);
|
||||
const rawData = Buffer.concat(rawDataComponents);
|
||||
return rawData;
|
||||
}
|
@@ -1,8 +1,8 @@
|
||||
import * as _ from 'lodash';
|
||||
|
||||
import { CalldataBlock } from './calldata_block';
|
||||
import { CalldataBlock } from '../calldata_block';
|
||||
|
||||
export class MemberCalldataBlock extends CalldataBlock {
|
||||
export class Set extends CalldataBlock {
|
||||
private _header: Buffer | undefined;
|
||||
private _members: CalldataBlock[];
|
||||
|
||||
@@ -14,14 +14,13 @@ export class MemberCalldataBlock extends CalldataBlock {
|
||||
|
||||
public getRawData(): Buffer {
|
||||
const rawDataComponents: Buffer[] = [];
|
||||
if (this._header !== undefined) {
|
||||
if (this._header) {
|
||||
rawDataComponents.push(this._header);
|
||||
}
|
||||
_.each(this._members, (member: CalldataBlock) => {
|
||||
const memberBuffer = member.getRawData();
|
||||
rawDataComponents.push(memberBuffer);
|
||||
});
|
||||
|
||||
const rawData = Buffer.concat(rawDataComponents);
|
||||
return rawData;
|
||||
}
|
||||
@@ -36,7 +35,7 @@ export class MemberCalldataBlock extends CalldataBlock {
|
||||
}
|
||||
|
||||
public toBuffer(): Buffer {
|
||||
if (this._header !== undefined) {
|
||||
if (this._header) {
|
||||
return this._header;
|
||||
}
|
||||
return new Buffer('');
|
@@ -5,8 +5,8 @@ import * as Constants from '../utils/constants';
|
||||
import { Queue } from '../utils/queue';
|
||||
import { EncodingRules } from '../utils/rules';
|
||||
|
||||
import * as CalldataBlocks from './blocks';
|
||||
import { CalldataBlock } from './calldata_block';
|
||||
import * as CalldataBlocks from './calldata_blocks';
|
||||
|
||||
export class Calldata {
|
||||
private readonly _rules: EncodingRules;
|
||||
@@ -18,7 +18,7 @@ export class Calldata {
|
||||
const blockQueue = new Queue<CalldataBlock>();
|
||||
|
||||
// Base Case
|
||||
if (!(block instanceof CalldataBlocks.MemberCalldataBlock)) {
|
||||
if (!(block instanceof CalldataBlocks.Set)) {
|
||||
blockQueue.pushBack(block);
|
||||
return blockQueue;
|
||||
}
|
||||
@@ -26,7 +26,7 @@ export class Calldata {
|
||||
// This is a Member Block
|
||||
const memberBlock = block;
|
||||
_.eachRight(memberBlock.getMembers(), (member: CalldataBlock) => {
|
||||
if (member instanceof CalldataBlocks.MemberCalldataBlock) {
|
||||
if (member instanceof CalldataBlocks.Set) {
|
||||
blockQueue.mergeFront(Calldata._createQueue(member));
|
||||
} else {
|
||||
blockQueue.pushFront(member);
|
||||
@@ -35,9 +35,9 @@ export class Calldata {
|
||||
|
||||
// Children
|
||||
_.each(memberBlock.getMembers(), (member: CalldataBlock) => {
|
||||
if (member instanceof CalldataBlocks.DependentCalldataBlock && member.getAlias() === undefined) {
|
||||
if (member instanceof CalldataBlocks.Pointer && member.getAlias() === undefined) {
|
||||
const dependency = member.getDependency();
|
||||
if (dependency instanceof CalldataBlocks.MemberCalldataBlock) {
|
||||
if (dependency instanceof CalldataBlocks.Set) {
|
||||
blockQueue.mergeBack(Calldata._createQueue(dependency));
|
||||
} else {
|
||||
blockQueue.pushBack(dependency);
|
||||
@@ -68,7 +68,7 @@ export class Calldata {
|
||||
const subtreeQueue = Calldata._createQueue(this._root);
|
||||
let block: CalldataBlock | undefined;
|
||||
for (block = subtreeQueue.popBack(); block !== undefined; block = subtreeQueue.popBack()) {
|
||||
if (block instanceof CalldataBlocks.DependentCalldataBlock) {
|
||||
if (block instanceof CalldataBlocks.Pointer) {
|
||||
const dependencyBlockHashBuf = block.getDependency().computeHash();
|
||||
const dependencyBlockHash = ethUtil.bufferToHex(dependencyBlockHashBuf);
|
||||
if (dependencyBlockHash in blocksByHash) {
|
||||
@@ -175,7 +175,7 @@ export class Calldata {
|
||||
),
|
||||
)
|
||||
.padEnd(valuePadding);
|
||||
if (block instanceof CalldataBlocks.MemberCalldataBlock) {
|
||||
if (block instanceof CalldataBlocks.Set) {
|
||||
nameStr = `### ${prettyName.padEnd(namePadding)}`;
|
||||
line = `\n${offsetStr}${value}${nameStr}`;
|
||||
} else {
|
||||
|
@@ -1,3 +0,0 @@
|
||||
export * from './dependent_calldata_block';
|
||||
export * from './member_calldata_block';
|
||||
export * from './payload_calldata_block';
|
@@ -1,6 +1,5 @@
|
||||
export * from './calldata_block';
|
||||
export * from './dependent_calldata_block';
|
||||
export * from './payload_calldata_block';
|
||||
export * from './member_calldata_block';
|
||||
export * from './calldata';
|
||||
export * from './calldata_block';
|
||||
export * from './raw_calldata';
|
||||
import * as CalldataBlocks from './blocks';
|
||||
export { CalldataBlocks };
|
||||
|
@@ -1,20 +0,0 @@
|
||||
import { CalldataBlock } from './calldata_block';
|
||||
|
||||
export class PayloadCalldataBlock extends CalldataBlock {
|
||||
private readonly _payload: Buffer;
|
||||
|
||||
constructor(name: string, signature: string, parentName: string, payload: Buffer) {
|
||||
const headerSizeInBytes = 0;
|
||||
const bodySizeInBytes = payload.byteLength;
|
||||
super(name, signature, parentName, headerSizeInBytes, bodySizeInBytes);
|
||||
this._payload = payload;
|
||||
}
|
||||
|
||||
public toBuffer(): Buffer {
|
||||
return this._payload;
|
||||
}
|
||||
|
||||
public getRawData(): Buffer {
|
||||
return this._payload;
|
||||
}
|
||||
}
|
@@ -8,26 +8,25 @@ export class RawCalldata {
|
||||
private readonly _value: Buffer;
|
||||
private readonly _selector: string;
|
||||
private readonly _scopes: Queue<number>;
|
||||
private _offset: number; // tracks current offset into raw calldata; used for parsing
|
||||
private _offset: number;
|
||||
|
||||
constructor(value: string | Buffer, hasSelectorPrefix: boolean = true) {
|
||||
public constructor(value: string | Buffer, hasSelector: boolean = true) {
|
||||
// Sanity check
|
||||
if (typeof value === 'string' && !value.startsWith('0x')) {
|
||||
throw new Error(`Expected raw calldata to start with '0x'`);
|
||||
}
|
||||
const valueBuf = ethUtil.toBuffer(value);
|
||||
if (hasSelectorPrefix) {
|
||||
this._selector = ethUtil.bufferToHex(
|
||||
valueBuf.slice(Constants.HEX_SELECTOR_BYTE_OFFSET_IN_CALLDATA, Constants.HEX_SELECTOR_LENGTH_IN_BYTES),
|
||||
);
|
||||
this._value = valueBuf.slice(Constants.HEX_SELECTOR_LENGTH_IN_BYTES); // disregard selector
|
||||
} else {
|
||||
this._selector = '0x';
|
||||
this._value = valueBuf;
|
||||
}
|
||||
|
||||
// Construct initial values
|
||||
this._value = ethUtil.toBuffer(value);
|
||||
this._selector = '0x';
|
||||
this._scopes = new Queue<number>();
|
||||
this._scopes.pushBack(RawCalldata._INITIAL_OFFSET);
|
||||
this._offset = RawCalldata._INITIAL_OFFSET;
|
||||
// If there's a selector then slice it
|
||||
if (hasSelector) {
|
||||
const selectorBuf = this._value.slice(Constants.HEX_SELECTOR_LENGTH_IN_BYTES);
|
||||
this._value = this._value.slice(Constants.HEX_SELECTOR_LENGTH_IN_BYTES);
|
||||
this._selector = ethUtil.bufferToHex(selectorBuf);
|
||||
}
|
||||
}
|
||||
|
||||
public popBytes(lengthInBytes: number): Buffer {
|
||||
|
@@ -3,11 +3,11 @@ import { DataItem } from 'ethereum-types';
|
||||
import * as ethUtil from 'ethereumjs-util';
|
||||
import * as _ from 'lodash';
|
||||
|
||||
import { DataTypeFactory, PayloadDataType } from '../abstract_data_types';
|
||||
import { AbstractDataTypes, DataTypeFactory } from '../abstract_data_types';
|
||||
import { RawCalldata } from '../calldata';
|
||||
import * as Constants from '../utils/constants';
|
||||
|
||||
export class Address extends PayloadDataType {
|
||||
export class Address extends AbstractDataTypes.Blob {
|
||||
public static ERROR_MESSAGE_ADDRESS_MUST_START_WITH_0X = "Address must start with '0x'";
|
||||
public static ERROR_MESSAGE_ADDRESS_MUST_BE_20_BYTES = 'Address must be 20 bytes';
|
||||
private static readonly _SIZE_KNOWN_AT_COMPILE_TIME: boolean = true;
|
||||
|
@@ -1,9 +1,9 @@
|
||||
import { DataItem } from 'ethereum-types';
|
||||
|
||||
import { DataTypeFactory, MemberDataType } from '../abstract_data_types';
|
||||
import { AbstractDataTypes, DataTypeFactory } from '../abstract_data_types';
|
||||
import * as Constants from '../utils/constants';
|
||||
|
||||
export class Array extends MemberDataType {
|
||||
export class Array extends AbstractDataTypes.Set {
|
||||
private static readonly _MATCHER = RegExp('^(.+)\\[([0-9]*)\\]$');
|
||||
private readonly _arraySignature: string;
|
||||
private readonly _elementType: string;
|
||||
|
@@ -4,11 +4,11 @@ import * as ethUtil from 'ethereumjs-util';
|
||||
import * as _ from 'lodash';
|
||||
|
||||
import { BigNumber } from '../../configured_bignumber';
|
||||
import { DataTypeFactory, PayloadDataType } from '../abstract_data_types';
|
||||
import { AbstractDataTypes, DataTypeFactory } from '../abstract_data_types';
|
||||
import { RawCalldata } from '../calldata';
|
||||
import * as Constants from '../utils/constants';
|
||||
|
||||
export class Bool extends PayloadDataType {
|
||||
export class Bool extends AbstractDataTypes.Blob {
|
||||
private static readonly _SIZE_KNOWN_AT_COMPILE_TIME: boolean = true;
|
||||
|
||||
public static matchType(type: string): boolean {
|
||||
|
@@ -3,11 +3,11 @@ import { DataItem } from 'ethereum-types';
|
||||
import * as ethUtil from 'ethereumjs-util';
|
||||
import * as _ from 'lodash';
|
||||
|
||||
import { DataTypeFactory, PayloadDataType } from '../abstract_data_types';
|
||||
import { AbstractDataTypes, DataTypeFactory } from '../abstract_data_types';
|
||||
import { RawCalldata } from '../calldata';
|
||||
import * as Constants from '../utils/constants';
|
||||
|
||||
export class DynamicBytes extends PayloadDataType {
|
||||
export class DynamicBytes extends AbstractDataTypes.Blob {
|
||||
private static readonly _SIZE_KNOWN_AT_COMPILE_TIME: boolean = false;
|
||||
|
||||
public static matchType(type: string): boolean {
|
||||
|
@@ -2,21 +2,21 @@
|
||||
import { DataItem } from 'ethereum-types';
|
||||
|
||||
import { BigNumber } from '../../configured_bignumber';
|
||||
import { DataTypeFactory, PayloadDataType } from '../abstract_data_types';
|
||||
import { AbstractDataTypes, DataTypeFactory } from '../abstract_data_types';
|
||||
import { RawCalldata } from '../calldata';
|
||||
import * as Constants from '../utils/constants';
|
||||
import * as EncoderMath from '../utils/math';
|
||||
|
||||
export class Int extends PayloadDataType {
|
||||
export class Int extends AbstractDataTypes.Blob {
|
||||
private static readonly _MATCHER = RegExp(
|
||||
'^int(8|16|24|32|40|48|56|64|72|88|96|104|112|120|128|136|144|152|160|168|176|184|192|200|208|216|224|232|240|248|256){0,1}$',
|
||||
);
|
||||
private static readonly _SIZE_KNOWN_AT_COMPILE_TIME: boolean = true;
|
||||
private static readonly _MAX_WIDTH: number = 256;
|
||||
private static readonly _DEFAULT_WIDTH: number = Int._MAX_WIDTH;
|
||||
private _width: number;
|
||||
private _minValue: BigNumber;
|
||||
private _maxValue: BigNumber;
|
||||
private readonly _width: number;
|
||||
private readonly _minValue: BigNumber;
|
||||
private readonly _maxValue: BigNumber;
|
||||
|
||||
public static matchType(type: string): boolean {
|
||||
return Int._MATCHER.test(type);
|
||||
|
@@ -2,13 +2,13 @@ import { DataItem, MethodAbi } from 'ethereum-types';
|
||||
import * as ethUtil from 'ethereumjs-util';
|
||||
import * as _ from 'lodash';
|
||||
|
||||
import { DataType, DataTypeFactory, MemberDataType } from '../abstract_data_types';
|
||||
import { AbstractDataTypes, DataType, DataTypeFactory } from '../abstract_data_types';
|
||||
import * as Constants from '../utils/constants';
|
||||
import { DecodingRules, EncodingRules } from '../utils/rules';
|
||||
|
||||
import { Tuple } from './tuple';
|
||||
|
||||
export class Method extends MemberDataType {
|
||||
export class Method extends AbstractDataTypes.Set {
|
||||
private readonly _methodSignature: string;
|
||||
private readonly _methodSelector: string;
|
||||
private readonly _returnDataType: DataType;
|
||||
|
@@ -1,8 +1,8 @@
|
||||
import { DataItem } from 'ethereum-types';
|
||||
|
||||
import { DataType, DataTypeFactory, DependentDataType } from '../abstract_data_types';
|
||||
import { AbstractDataTypes, DataType, DataTypeFactory } from '../abstract_data_types';
|
||||
|
||||
export class Pointer extends DependentDataType {
|
||||
export class Pointer extends AbstractDataTypes.Pointer {
|
||||
constructor(destDataType: DataType, parentDataType: DataType, dataTypeFactory: DataTypeFactory) {
|
||||
const destDataItem = destDataType.getDataItem();
|
||||
const dataItem: DataItem = { name: `ptr<${destDataItem.name}>`, type: `ptr<${destDataItem.type}>` };
|
||||
|
@@ -2,11 +2,11 @@ import { DataItem } from 'ethereum-types';
|
||||
import * as ethUtil from 'ethereumjs-util';
|
||||
import * as _ from 'lodash';
|
||||
|
||||
import { DataTypeFactory, PayloadDataType } from '../abstract_data_types';
|
||||
import { AbstractDataTypes, DataTypeFactory } from '../abstract_data_types';
|
||||
import { RawCalldata } from '../calldata';
|
||||
import * as Constants from '../utils/constants';
|
||||
|
||||
export class StaticBytes extends PayloadDataType {
|
||||
export class StaticBytes extends AbstractDataTypes.Blob {
|
||||
private static readonly _SIZE_KNOWN_AT_COMPILE_TIME: boolean = true;
|
||||
private static readonly _MATCHER = RegExp(
|
||||
'^(byte|bytes(1|2|3|4|5|6|7|8|9|10|11|12|13|14|15|16|17|18|19|20|21|22|23|24|25|26|27|28|29|30|31|32))$',
|
||||
|
@@ -3,11 +3,11 @@ import { DataItem } from 'ethereum-types';
|
||||
import * as ethUtil from 'ethereumjs-util';
|
||||
import * as _ from 'lodash';
|
||||
|
||||
import { DataTypeFactory, PayloadDataType } from '../abstract_data_types';
|
||||
import { AbstractDataTypes, DataTypeFactory } from '../abstract_data_types';
|
||||
import { RawCalldata } from '../calldata';
|
||||
import * as Constants from '../utils/constants';
|
||||
|
||||
export class String extends PayloadDataType {
|
||||
export class String extends AbstractDataTypes.Blob {
|
||||
private static readonly _SIZE_KNOWN_AT_COMPILE_TIME: boolean = false;
|
||||
|
||||
public static matchType(type: string): boolean {
|
||||
|
@@ -1,8 +1,8 @@
|
||||
import { DataItem } from 'ethereum-types';
|
||||
|
||||
import { DataTypeFactory, MemberDataType } from '../abstract_data_types';
|
||||
import { AbstractDataTypes, DataTypeFactory } from '../abstract_data_types';
|
||||
|
||||
export class Tuple extends MemberDataType {
|
||||
export class Tuple extends AbstractDataTypes.Set {
|
||||
private readonly _signature: string;
|
||||
|
||||
public static matchType(type: string): boolean {
|
||||
|
@@ -2,21 +2,21 @@
|
||||
import { DataItem } from 'ethereum-types';
|
||||
|
||||
import { BigNumber } from '../../configured_bignumber';
|
||||
import { DataTypeFactory, PayloadDataType } from '../abstract_data_types';
|
||||
import { AbstractDataTypes, DataTypeFactory } from '../abstract_data_types';
|
||||
import { RawCalldata } from '../calldata';
|
||||
import * as Constants from '../utils/constants';
|
||||
import * as EncoderMath from '../utils/math';
|
||||
|
||||
export class UInt extends PayloadDataType {
|
||||
export class UInt extends AbstractDataTypes.Blob {
|
||||
private static readonly _MATCHER = RegExp(
|
||||
'^uint(8|16|24|32|40|48|56|64|72|88|96|104|112|120|128|136|144|152|160|168|176|184|192|200|208|216|224|232|240|248|256){0,1}$',
|
||||
);
|
||||
private static readonly _SIZE_KNOWN_AT_COMPILE_TIME: boolean = true;
|
||||
private static readonly _MAX_WIDTH: number = 256;
|
||||
private static readonly _DEFAULT_WIDTH: number = UInt._MAX_WIDTH;
|
||||
private _width: number;
|
||||
private _minValue: BigNumber;
|
||||
private _maxValue: BigNumber;
|
||||
private static readonly _MIN_VALUE = new BigNumber(0);
|
||||
private readonly _width: number;
|
||||
private readonly _maxValue: BigNumber;
|
||||
|
||||
public static matchType(type: string): boolean {
|
||||
return UInt._MATCHER.test(type);
|
||||
@@ -36,18 +36,17 @@ export class UInt extends PayloadDataType {
|
||||
throw new Error(`Tried to instantiate UInt with bad input: ${dataItem}`);
|
||||
}
|
||||
this._width = UInt._decodeWidthFromType(dataItem.type);
|
||||
this._minValue = new BigNumber(0);
|
||||
this._maxValue = new BigNumber(2).toPower(this._width).sub(1);
|
||||
}
|
||||
|
||||
public encodeValue(value: BigNumber | string | number): Buffer {
|
||||
const encodedValue = EncoderMath.safeEncodeNumericValue(value, this._minValue, this._maxValue);
|
||||
const encodedValue = EncoderMath.safeEncodeNumericValue(value, UInt._MIN_VALUE, this._maxValue);
|
||||
return encodedValue;
|
||||
}
|
||||
|
||||
public decodeValue(calldata: RawCalldata): BigNumber {
|
||||
const valueBuf = calldata.popWord();
|
||||
const value = EncoderMath.safeDecodeNumericValue(valueBuf, this._minValue, this._maxValue);
|
||||
const value = EncoderMath.safeDecodeNumericValue(valueBuf, UInt._MIN_VALUE, this._maxValue);
|
||||
return value;
|
||||
}
|
||||
|
||||
@@ -55,4 +54,3 @@ export class UInt extends PayloadDataType {
|
||||
return `uint${this._width}`;
|
||||
}
|
||||
}
|
||||
|
||||
|
Reference in New Issue
Block a user