diff --git a/packages/jellyfish-transaction/__tests__/script/index.test.ts b/packages/jellyfish-transaction/__tests__/script/index.test.ts index 02abf45abe..6dbe81a8a8 100644 --- a/packages/jellyfish-transaction/__tests__/script/index.test.ts +++ b/packages/jellyfish-transaction/__tests__/script/index.test.ts @@ -1026,6 +1026,492 @@ describe('[OP_RESERVED2]', () => { }) }) +describe('[OP_1ADD]', () => { + const hex = '018b' + + it('should map fromBuffer', () => { + const codes = OP_CODES.fromBuffer(SmartBuffer.fromBuffer( + Buffer.from(hex, 'hex') + )) + expect(codes[0].type).toStrictEqual('OP_1ADD') + expect(codes.length).toStrictEqual(1) + }) + + it('should map toBuffer', () => { + const smartBuffer = new SmartBuffer() + OP_CODES.toBuffer([OP_CODES.OP_1ADD], smartBuffer) + expect(smartBuffer.toBuffer().toString('hex')).toStrictEqual(hex) + }) +}) + +describe('[OP_1SUB]', () => { + const hex = '018c' + + it('should map fromBuffer', () => { + const codes = OP_CODES.fromBuffer(SmartBuffer.fromBuffer( + Buffer.from(hex, 'hex') + )) + expect(codes[0].type).toStrictEqual('OP_1SUB') + expect(codes.length).toStrictEqual(1) + }) + + it('should map toBuffer', () => { + const smartBuffer = new SmartBuffer() + OP_CODES.toBuffer([OP_CODES.OP_1SUB], smartBuffer) + expect(smartBuffer.toBuffer().toString('hex')).toStrictEqual(hex) + }) +}) + +describe('[OP_2MUL]', () => { + const hex = '018d' + + it('should map fromBuffer', () => { + const codes = OP_CODES.fromBuffer(SmartBuffer.fromBuffer( + Buffer.from(hex, 'hex') + )) + expect(codes[0].type).toStrictEqual('OP_2MUL') + expect(codes.length).toStrictEqual(1) + }) + + it('should map toBuffer', () => { + const smartBuffer = new SmartBuffer() + OP_CODES.toBuffer([OP_CODES.OP_2MUL], smartBuffer) + expect(smartBuffer.toBuffer().toString('hex')).toStrictEqual(hex) + }) +}) + +describe('[OP_2DIV]', () => { + const hex = '018e' + + it('should map fromBuffer', () => { + const codes = OP_CODES.fromBuffer(SmartBuffer.fromBuffer( + Buffer.from(hex, 'hex') + )) + expect(codes[0].type).toStrictEqual('OP_2DIV') + expect(codes.length).toStrictEqual(1) + }) + + it('should map toBuffer', () => { + const smartBuffer = new SmartBuffer() + OP_CODES.toBuffer([OP_CODES.OP_2DIV], smartBuffer) + expect(smartBuffer.toBuffer().toString('hex')).toStrictEqual(hex) + }) +}) + +describe('[OP_NEGATE]', () => { + const hex = '018f' + + it('should map fromBuffer', () => { + const codes = OP_CODES.fromBuffer(SmartBuffer.fromBuffer( + Buffer.from(hex, 'hex') + )) + expect(codes[0].type).toStrictEqual('OP_NEGATE') + expect(codes.length).toStrictEqual(1) + }) + + it('should map toBuffer', () => { + const smartBuffer = new SmartBuffer() + OP_CODES.toBuffer([OP_CODES.OP_NEGATE], smartBuffer) + expect(smartBuffer.toBuffer().toString('hex')).toStrictEqual(hex) + }) +}) + +describe('[OP_ABS]', () => { + const hex = '0190' + + it('should map fromBuffer', () => { + const codes = OP_CODES.fromBuffer(SmartBuffer.fromBuffer( + Buffer.from(hex, 'hex') + )) + expect(codes[0].type).toStrictEqual('OP_ABS') + expect(codes.length).toStrictEqual(1) + }) + + it('should map toBuffer', () => { + const smartBuffer = new SmartBuffer() + OP_CODES.toBuffer([OP_CODES.OP_ABS], smartBuffer) + expect(smartBuffer.toBuffer().toString('hex')).toStrictEqual(hex) + }) +}) + +describe('[OP_NOT]', () => { + const hex = '0191' + + it('should map fromBuffer', () => { + const codes = OP_CODES.fromBuffer(SmartBuffer.fromBuffer( + Buffer.from(hex, 'hex') + )) + expect(codes[0].type).toStrictEqual('OP_NOT') + expect(codes.length).toStrictEqual(1) + }) + + it('should map toBuffer', () => { + const smartBuffer = new SmartBuffer() + OP_CODES.toBuffer([OP_CODES.OP_NOT], smartBuffer) + expect(smartBuffer.toBuffer().toString('hex')).toStrictEqual(hex) + }) +}) + +describe('[OP_0NOTEQUAL]', () => { + const hex = '0192' + + it('should map fromBuffer', () => { + const codes = OP_CODES.fromBuffer(SmartBuffer.fromBuffer( + Buffer.from(hex, 'hex') + )) + expect(codes[0].type).toStrictEqual('OP_0NOTEQUAL') + expect(codes.length).toStrictEqual(1) + }) + + it('should map toBuffer', () => { + const smartBuffer = new SmartBuffer() + OP_CODES.toBuffer([OP_CODES.OP_0NOTEQUAL], smartBuffer) + expect(smartBuffer.toBuffer().toString('hex')).toStrictEqual(hex) + }) +}) + +describe('[OP_ADD]', () => { + const hex = '0193' + + it('should map fromBuffer', () => { + const codes = OP_CODES.fromBuffer(SmartBuffer.fromBuffer( + Buffer.from(hex, 'hex') + )) + expect(codes[0].type).toStrictEqual('OP_ADD') + expect(codes.length).toStrictEqual(1) + }) + + it('should map toBuffer', () => { + const smartBuffer = new SmartBuffer() + OP_CODES.toBuffer([OP_CODES.OP_ADD], smartBuffer) + expect(smartBuffer.toBuffer().toString('hex')).toStrictEqual(hex) + }) +}) + +describe('[OP_SUB]', () => { + const hex = '0194' + + it('should map fromBuffer', () => { + const codes = OP_CODES.fromBuffer(SmartBuffer.fromBuffer( + Buffer.from(hex, 'hex') + )) + expect(codes[0].type).toStrictEqual('OP_SUB') + expect(codes.length).toStrictEqual(1) + }) + + it('should map toBuffer', () => { + const smartBuffer = new SmartBuffer() + OP_CODES.toBuffer([OP_CODES.OP_SUB], smartBuffer) + expect(smartBuffer.toBuffer().toString('hex')).toStrictEqual(hex) + }) +}) + +describe('[OP_MUL]', () => { + const hex = '0195' + + it('should map fromBuffer', () => { + const codes = OP_CODES.fromBuffer(SmartBuffer.fromBuffer( + Buffer.from(hex, 'hex') + )) + expect(codes[0].type).toStrictEqual('OP_MUL') + expect(codes.length).toStrictEqual(1) + }) + + it('should map toBuffer', () => { + const smartBuffer = new SmartBuffer() + OP_CODES.toBuffer([OP_CODES.OP_MUL], smartBuffer) + expect(smartBuffer.toBuffer().toString('hex')).toStrictEqual(hex) + }) +}) + +describe('[OP_DIV]', () => { + const hex = '0196' + + it('should map fromBuffer', () => { + const codes = OP_CODES.fromBuffer(SmartBuffer.fromBuffer( + Buffer.from(hex, 'hex') + )) + expect(codes[0].type).toStrictEqual('OP_DIV') + expect(codes.length).toStrictEqual(1) + }) + + it('should map toBuffer', () => { + const smartBuffer = new SmartBuffer() + OP_CODES.toBuffer([OP_CODES.OP_DIV], smartBuffer) + expect(smartBuffer.toBuffer().toString('hex')).toStrictEqual(hex) + }) +}) + +describe('[OP_MOD]', () => { + const hex = '0197' + + it('should map fromBuffer', () => { + const codes = OP_CODES.fromBuffer(SmartBuffer.fromBuffer( + Buffer.from(hex, 'hex') + )) + expect(codes[0].type).toStrictEqual('OP_MOD') + expect(codes.length).toStrictEqual(1) + }) + + it('should map toBuffer', () => { + const smartBuffer = new SmartBuffer() + OP_CODES.toBuffer([OP_CODES.OP_MOD], smartBuffer) + expect(smartBuffer.toBuffer().toString('hex')).toStrictEqual(hex) + }) +}) + +describe('[OP_LSHIFT]', () => { + const hex = '0198' + + it('should map fromBuffer', () => { + const codes = OP_CODES.fromBuffer(SmartBuffer.fromBuffer( + Buffer.from(hex, 'hex') + )) + expect(codes[0].type).toStrictEqual('OP_LSHIFT') + expect(codes.length).toStrictEqual(1) + }) + + it('should map toBuffer', () => { + const smartBuffer = new SmartBuffer() + OP_CODES.toBuffer([OP_CODES.OP_LSHIFT], smartBuffer) + expect(smartBuffer.toBuffer().toString('hex')).toStrictEqual(hex) + }) +}) + +describe('[OP_RSHIFT]', () => { + const hex = '0199' + + it('should map fromBuffer', () => { + const codes = OP_CODES.fromBuffer(SmartBuffer.fromBuffer( + Buffer.from(hex, 'hex') + )) + expect(codes[0].type).toStrictEqual('OP_RSHIFT') + expect(codes.length).toStrictEqual(1) + }) + + it('should map toBuffer', () => { + const smartBuffer = new SmartBuffer() + OP_CODES.toBuffer([OP_CODES.OP_RSHIFT], smartBuffer) + expect(smartBuffer.toBuffer().toString('hex')).toStrictEqual(hex) + }) +}) + +describe('[OP_BOOLAND]', () => { + const hex = '019a' + + it('should map fromBuffer', () => { + const codes = OP_CODES.fromBuffer(SmartBuffer.fromBuffer( + Buffer.from(hex, 'hex') + )) + expect(codes[0].type).toStrictEqual('OP_BOOLAND') + expect(codes.length).toStrictEqual(1) + }) + + it('should map toBuffer', () => { + const smartBuffer = new SmartBuffer() + OP_CODES.toBuffer([OP_CODES.OP_BOOLAND], smartBuffer) + expect(smartBuffer.toBuffer().toString('hex')).toStrictEqual(hex) + }) +}) + +describe('[OP_BOOLOR]', () => { + const hex = '019b' + + it('should map fromBuffer', () => { + const codes = OP_CODES.fromBuffer(SmartBuffer.fromBuffer( + Buffer.from(hex, 'hex') + )) + expect(codes[0].type).toStrictEqual('OP_BOOLOR') + expect(codes.length).toStrictEqual(1) + }) + + it('should map toBuffer', () => { + const smartBuffer = new SmartBuffer() + OP_CODES.toBuffer([OP_CODES.OP_BOOLOR], smartBuffer) + expect(smartBuffer.toBuffer().toString('hex')).toStrictEqual(hex) + }) +}) + +describe('[OP_NUMEQUAL]', () => { + const hex = '019c' + + it('should map fromBuffer', () => { + const codes = OP_CODES.fromBuffer(SmartBuffer.fromBuffer( + Buffer.from(hex, 'hex') + )) + expect(codes[0].type).toStrictEqual('OP_NUMEQUAL') + expect(codes.length).toStrictEqual(1) + }) + + it('should map toBuffer', () => { + const smartBuffer = new SmartBuffer() + OP_CODES.toBuffer([OP_CODES.OP_NUMEQUAL], smartBuffer) + expect(smartBuffer.toBuffer().toString('hex')).toStrictEqual(hex) + }) +}) + +describe('[OP_NUMEQUALVERIFY]', () => { + const hex = '019d' + + it('should map fromBuffer', () => { + const codes = OP_CODES.fromBuffer(SmartBuffer.fromBuffer( + Buffer.from(hex, 'hex') + )) + expect(codes[0].type).toStrictEqual('OP_NUMEQUALVERIFY') + expect(codes.length).toStrictEqual(1) + }) + + it('should map toBuffer', () => { + const smartBuffer = new SmartBuffer() + OP_CODES.toBuffer([OP_CODES.OP_NUMEQUALVERIFY], smartBuffer) + expect(smartBuffer.toBuffer().toString('hex')).toStrictEqual(hex) + }) +}) + +describe('[OP_NUMNOTEQUAL]', () => { + const hex = '019e' + + it('should map fromBuffer', () => { + const codes = OP_CODES.fromBuffer(SmartBuffer.fromBuffer( + Buffer.from(hex, 'hex') + )) + expect(codes[0].type).toStrictEqual('OP_NUMNOTEQUAL') + expect(codes.length).toStrictEqual(1) + }) + + it('should map toBuffer', () => { + const smartBuffer = new SmartBuffer() + OP_CODES.toBuffer([OP_CODES.OP_NUMNOTEQUAL], smartBuffer) + expect(smartBuffer.toBuffer().toString('hex')).toStrictEqual(hex) + }) +}) + +describe('[OP_LESSTHAN]', () => { + const hex = '019f' + + it('should map fromBuffer', () => { + const codes = OP_CODES.fromBuffer(SmartBuffer.fromBuffer( + Buffer.from(hex, 'hex') + )) + expect(codes[0].type).toStrictEqual('OP_LESSTHAN') + expect(codes.length).toStrictEqual(1) + }) + + it('should map toBuffer', () => { + const smartBuffer = new SmartBuffer() + OP_CODES.toBuffer([OP_CODES.OP_LESSTHAN], smartBuffer) + expect(smartBuffer.toBuffer().toString('hex')).toStrictEqual(hex) + }) +}) + +describe('[OP_GREATERTHAN]', () => { + const hex = '01a0' + + it('should map fromBuffer', () => { + const codes = OP_CODES.fromBuffer(SmartBuffer.fromBuffer( + Buffer.from(hex, 'hex') + )) + expect(codes[0].type).toStrictEqual('OP_GREATERTHAN') + expect(codes.length).toStrictEqual(1) + }) + + it('should map toBuffer', () => { + const smartBuffer = new SmartBuffer() + OP_CODES.toBuffer([OP_CODES.OP_GREATERTHAN], smartBuffer) + expect(smartBuffer.toBuffer().toString('hex')).toStrictEqual(hex) + }) +}) + +describe('[OP_LESSTHANOREQUAL]', () => { + const hex = '01a1' + + it('should map fromBuffer', () => { + const codes = OP_CODES.fromBuffer(SmartBuffer.fromBuffer( + Buffer.from(hex, 'hex') + )) + expect(codes[0].type).toStrictEqual('OP_LESSTHANOREQUAL') + expect(codes.length).toStrictEqual(1) + }) + + it('should map toBuffer', () => { + const smartBuffer = new SmartBuffer() + OP_CODES.toBuffer([OP_CODES.OP_LESSTHANOREQUAL], smartBuffer) + expect(smartBuffer.toBuffer().toString('hex')).toStrictEqual(hex) + }) +}) + +describe('[OP_GREATERTHANOREQUAL]', () => { + const hex = '01a2' + + it('should map fromBuffer', () => { + const codes = OP_CODES.fromBuffer(SmartBuffer.fromBuffer( + Buffer.from(hex, 'hex') + )) + expect(codes[0].type).toStrictEqual('OP_GREATERTHANOREQUAL') + expect(codes.length).toStrictEqual(1) + }) + + it('should map toBuffer', () => { + const smartBuffer = new SmartBuffer() + OP_CODES.toBuffer([OP_CODES.OP_GREATERTHANOREQUAL], smartBuffer) + expect(smartBuffer.toBuffer().toString('hex')).toStrictEqual(hex) + }) +}) + +describe('[OP_MIN]', () => { + const hex = '01a3' + + it('should map fromBuffer', () => { + const codes = OP_CODES.fromBuffer(SmartBuffer.fromBuffer( + Buffer.from(hex, 'hex') + )) + expect(codes[0].type).toStrictEqual('OP_MIN') + expect(codes.length).toStrictEqual(1) + }) + + it('should map toBuffer', () => { + const smartBuffer = new SmartBuffer() + OP_CODES.toBuffer([OP_CODES.OP_MIN], smartBuffer) + expect(smartBuffer.toBuffer().toString('hex')).toStrictEqual(hex) + }) +}) + +describe('[OP_MAX]', () => { + const hex = '01a4' + + it('should map fromBuffer', () => { + const codes = OP_CODES.fromBuffer(SmartBuffer.fromBuffer( + Buffer.from(hex, 'hex') + )) + expect(codes[0].type).toStrictEqual('OP_MAX') + expect(codes.length).toStrictEqual(1) + }) + + it('should map toBuffer', () => { + const smartBuffer = new SmartBuffer() + OP_CODES.toBuffer([OP_CODES.OP_MAX], smartBuffer) + expect(smartBuffer.toBuffer().toString('hex')).toStrictEqual(hex) + }) +}) + +describe('[OP_WITHIN]', () => { + const hex = '01a5' + + it('should map fromBuffer', () => { + const codes = OP_CODES.fromBuffer(SmartBuffer.fromBuffer( + Buffer.from(hex, 'hex') + )) + expect(codes[0].type).toStrictEqual('OP_WITHIN') + expect(codes.length).toStrictEqual(1) + }) + + it('should map toBuffer', () => { + const smartBuffer = new SmartBuffer() + OP_CODES.toBuffer([OP_CODES.OP_WITHIN], smartBuffer) + expect(smartBuffer.toBuffer().toString('hex')).toStrictEqual(hex) + }) +}) + describe('[OP_RIPEMD160]', () => { const hex = '01a6' diff --git a/packages/jellyfish-transaction/__tests__/script/mapping.test.ts b/packages/jellyfish-transaction/__tests__/script/mapping.test.ts index 6deb3ceabf..e4ad6dcdc3 100644 --- a/packages/jellyfish-transaction/__tests__/script/mapping.test.ts +++ b/packages/jellyfish-transaction/__tests__/script/mapping.test.ts @@ -226,6 +226,114 @@ describe('All mapped OP_CODES are setup properly: (static, hex, num, asm)', () = expectOPCode(script.OP_CODES.OP_RESERVED2, script.OP_RESERVED2, 'OP_RESERVED2', 0x8a, '8a') }) + it('OP_1ADD', () => { + expectOPCode(script.OP_CODES.OP_1ADD, script.OP_1ADD, 'OP_1ADD', 0x8b, '8b') + }) + + it('OP_1SUB', () => { + expectOPCode(script.OP_CODES.OP_1SUB, script.OP_1SUB, 'OP_1SUB', 0x8c, '8c') + }) + + it('OP_2MUL', () => { + expectOPCode(script.OP_CODES.OP_2MUL, script.OP_2MUL, 'OP_2MUL', 0x8d, '8d') + }) + + it('OP_2DIV', () => { + expectOPCode(script.OP_CODES.OP_2DIV, script.OP_2DIV, 'OP_2DIV', 0x8e, '8e') + }) + + it('OP_NEGATE', () => { + expectOPCode(script.OP_CODES.OP_NEGATE, script.OP_NEGATE, 'OP_NEGATE', 0x8f, '8f') + }) + + it('OP_ABS', () => { + expectOPCode(script.OP_CODES.OP_ABS, script.OP_ABS, 'OP_ABS', 0x90, '90') + }) + + it('OP_NOT', () => { + expectOPCode(script.OP_CODES.OP_NOT, script.OP_NOT, 'OP_NOT', 0x91, '91') + }) + + it('OP_0NOTEQUAL', () => { + expectOPCode(script.OP_CODES.OP_0NOTEQUAL, script.OP_0NOTEQUAL, 'OP_0NOTEQUAL', 0x92, '92') + }) + + it('OP_ADD', () => { + expectOPCode(script.OP_CODES.OP_ADD, script.OP_ADD, 'OP_ADD', 0x93, '93') + }) + + it('OP_SUB', () => { + expectOPCode(script.OP_CODES.OP_SUB, script.OP_SUB, 'OP_SUB', 0x94, '94') + }) + + it('OP_MUL', () => { + expectOPCode(script.OP_CODES.OP_MUL, script.OP_MUL, 'OP_MUL', 0x95, '95') + }) + + it('OP_DIV', () => { + expectOPCode(script.OP_CODES.OP_DIV, script.OP_DIV, 'OP_DIV', 0x96, '96') + }) + + it('OP_MOD', () => { + expectOPCode(script.OP_CODES.OP_MOD, script.OP_MOD, 'OP_MOD', 0x97, '97') + }) + + it('OP_LSHIFT', () => { + expectOPCode(script.OP_CODES.OP_LSHIFT, script.OP_LSHIFT, 'OP_LSHIFT', 0x98, '98') + }) + + it('OP_RSHIFT', () => { + expectOPCode(script.OP_CODES.OP_RSHIFT, script.OP_RSHIFT, 'OP_RSHIFT', 0x99, '99') + }) + + it('OP_BOOLAND', () => { + expectOPCode(script.OP_CODES.OP_BOOLAND, script.OP_BOOLAND, 'OP_BOOLAND', 0x9a, '9a') + }) + + it('OP_BOOLOR', () => { + expectOPCode(script.OP_CODES.OP_BOOLOR, script.OP_BOOLOR, 'OP_BOOLOR', 0x9b, '9b') + }) + + it('OP_NUMEQUAL', () => { + expectOPCode(script.OP_CODES.OP_NUMEQUAL, script.OP_NUMEQUAL, 'OP_NUMEQUAL', 0x9c, '9c') + }) + + it('OP_NUMEQUALVERIFY', () => { + expectOPCode(script.OP_CODES.OP_NUMEQUALVERIFY, script.OP_NUMEQUALVERIFY, 'OP_NUMEQUALVERIFY', 0x9d, '9d') + }) + + it('OP_NUMNOTEQUAL', () => { + expectOPCode(script.OP_CODES.OP_NUMNOTEQUAL, script.OP_NUMNOTEQUAL, 'OP_NUMNOTEQUAL', 0x9e, '9e') + }) + + it('OP_LESSTHAN', () => { + expectOPCode(script.OP_CODES.OP_LESSTHAN, script.OP_LESSTHAN, 'OP_LESSTHAN', 0x9f, '9f') + }) + + it('OP_GREATERTHAN', () => { + expectOPCode(script.OP_CODES.OP_GREATERTHAN, script.OP_GREATERTHAN, 'OP_GREATERTHAN', 0xa0, 'a0') + }) + + it('OP_LESSTHANOREQUAL', () => { + expectOPCode(script.OP_CODES.OP_LESSTHANOREQUAL, script.OP_LESSTHANOREQUAL, 'OP_LESSTHANOREQUAL', 0xa1, 'a1') + }) + + it('OP_GREATERTHANOREQUAL', () => { + expectOPCode(script.OP_CODES.OP_GREATERTHANOREQUAL, script.OP_GREATERTHANOREQUAL, 'OP_GREATERTHANOREQUAL', 0xa2, 'a2') + }) + + it('OP_MIN', () => { + expectOPCode(script.OP_CODES.OP_MIN, script.OP_MIN, 'OP_MIN', 0xa3, 'a3') + }) + + it('OP_MAX', () => { + expectOPCode(script.OP_CODES.OP_MAX, script.OP_MAX, 'OP_MAX', 0xa4, 'a4') + }) + + it('OP_WITHIN', () => { + expectOPCode(script.OP_CODES.OP_WITHIN, script.OP_WITHIN, 'OP_WITHIN', 0xa5, 'a5') + }) + it('OP_RIPEMD160', () => { expectOPCode(script.OP_CODES.OP_RIPEMD160, script.OP_RIPEMD160, 'OP_RIPEMD160', 0xa6, 'a6') }) diff --git a/packages/jellyfish-transaction/src/script/arithmetic.ts b/packages/jellyfish-transaction/src/script/arithmetic.ts new file mode 100644 index 0000000000..be3d2fac83 --- /dev/null +++ b/packages/jellyfish-transaction/src/script/arithmetic.ts @@ -0,0 +1,244 @@ +import { StaticCode } from './opcode' + +/** + * 1 is added to the input. + */ +export class OP_1ADD extends StaticCode { + constructor () { + super(0x8b, 'OP_1ADD') + } +} + +/** + * 1 is subtracted from the input. + */ +export class OP_1SUB extends StaticCode { + constructor () { + super(0x8c, 'OP_1SUB') + } +} + +/** + * The input is multiplied by 2. disabled. + */ +export class OP_2MUL extends StaticCode { + constructor () { + super(0x8d, 'OP_2MUL') + } +} + +/** + * The input is divided by 2. disabled. + */ +export class OP_2DIV extends StaticCode { + constructor () { + super(0x8e, 'OP_2DIV') + } +} + +/** + * The sign of the input is flipped. + */ +export class OP_NEGATE extends StaticCode { + constructor () { + super(0x8f, 'OP_NEGATE') + } +} + +/** + * The input is made positive. + */ +export class OP_ABS extends StaticCode { + constructor () { + super(0x90, 'OP_ABS') + } +} + +/** + * If the input is 0 or 1, it is flipped. Otherwise the output will be 0. + */ +export class OP_NOT extends StaticCode { + constructor () { + super(0x91, 'OP_NOT') + } +} + +/** + * Returns 0 if the input is 0. 1 otherwise. + */ +export class OP_0NOTEQUAL extends StaticCode { + constructor () { + super(0x92, 'OP_0NOTEQUAL') + } +} + +/** + * a is added to b. + */ +export class OP_ADD extends StaticCode { + constructor () { + super(0x93, 'OP_ADD') + } +} + +/** + * b is subtracted from a. + */ +export class OP_SUB extends StaticCode { + constructor () { + super(0x94, 'OP_SUB') + } +} + +/** + * a is multiplied by b. disabled. + */ +export class OP_MUL extends StaticCode { + constructor () { + super(0x95, 'OP_MUL') + } +} + +/** + * a is divided by b. disabled. + */ +export class OP_DIV extends StaticCode { + constructor () { + super(0x96, 'OP_DIV') + } +} + +/** + * Returns the remainder after dividing a by b. disabled. + */ +export class OP_MOD extends StaticCode { + constructor () { + super(0x97, 'OP_MOD') + } +} + +/** + * Shifts a left b bits, preserving sign. disabled. + */ +export class OP_LSHIFT extends StaticCode { + constructor () { + super(0x98, 'OP_LSHIFT') + } +} + +/** + * Shifts a right b bits, preserving sign. disabled. + */ +export class OP_RSHIFT extends StaticCode { + constructor () { + super(0x99, 'OP_RSHIFT') + } +} + +/** + * If both a and b are not 0, the output is 1. Otherwise 0. + */ +export class OP_BOOLAND extends StaticCode { + constructor () { + super(0x9a, 'OP_BOOLAND') + } +} + +/** + * If a or b is not 0, the output is 1. Otherwise 0. + */ +export class OP_BOOLOR extends StaticCode { + constructor () { + super(0x9b, 'OP_BOOLOR') + } +} + +/** + * Returns 1 if the numbers are equal, 0 otherwise. + */ +export class OP_NUMEQUAL extends StaticCode { + constructor () { + super(0x9c, 'OP_NUMEQUAL') + } +} + +/** + * Same as OP_NUMEQUAL, but runs OP_VERIFY afterward. + */ +export class OP_NUMEQUALVERIFY extends StaticCode { + constructor () { + super(0x9d, 'OP_NUMEQUALVERIFY') + } +} + +/** + * Returns 1 if the numbers are not equal, 0 otherwise. + */ +export class OP_NUMNOTEQUAL extends StaticCode { + constructor () { + super(0x9e, 'OP_NUMNOTEQUAL') + } +} + +/** + * Returns 1 if a is less than b, 0 otherwise. + */ +export class OP_LESSTHAN extends StaticCode { + constructor () { + super(0x9f, 'OP_LESSTHAN') + } +} + +/** + * Returns 1 if a is greater than b, 0 otherwise. + */ +export class OP_GREATERTHAN extends StaticCode { + constructor () { + super(0xa0, 'OP_GREATERTHAN') + } +} + +/** + * Returns 1 if a is less than or equal to b, 0 otherwise. + */ +export class OP_LESSTHANOREQUAL extends StaticCode { + constructor () { + super(0xa1, 'OP_LESSTHANOREQUAL') + } +} + +/** + * Returns 1 if a is greater than or equal to b, 0 otherwise. + */ +export class OP_GREATERTHANOREQUAL extends StaticCode { + constructor () { + super(0xa2, 'OP_GREATERTHANOREQUAL') + } +} + +/** + * Returns the smaller of a and b. + */ +export class OP_MIN extends StaticCode { + constructor () { + super(0xa3, 'OP_MIN') + } +} + +/** + * Returns the larger of a and b. + */ +export class OP_MAX extends StaticCode { + constructor () { + super(0xa4, 'OP_MAX') + } +} + +/** + * Returns 1 if x is within the specified range (left-inclusive), 0 otherwise. + */ +export class OP_WITHIN extends StaticCode { + constructor () { + super(0xa5, 'OP_WITHIN') + } +} diff --git a/packages/jellyfish-transaction/src/script/index.ts b/packages/jellyfish-transaction/src/script/index.ts index d51ea3bcb8..8aa643a998 100644 --- a/packages/jellyfish-transaction/src/script/index.ts +++ b/packages/jellyfish-transaction/src/script/index.ts @@ -1,11 +1,12 @@ -export * from './bitwise' +export * from './data' export * from './constants' export * from './control' +export * from './stack' +export * from './bitwise' +export * from './arithmetic' export * from './crypto' -export * from './data' +export * from './expansion' +export * from './invalid' export * from './mapping' export * from './opcode' -export * from './stack' export * from './dftx' -export * from './expansion' -export * from './invalid' diff --git a/packages/jellyfish-transaction/src/script/mapping.ts b/packages/jellyfish-transaction/src/script/mapping.ts index e30b233a07..7f9803115c 100644 --- a/packages/jellyfish-transaction/src/script/mapping.ts +++ b/packages/jellyfish-transaction/src/script/mapping.ts @@ -6,10 +6,11 @@ import { OP_PUSHDATA } from './data' import { OP_DEFI_TX } from './dftx' import { CDfTx, DfTx } from './dftx/dftx' import * as constants from './constants' -import * as crypto from './crypto' import * as control from './control' import * as stack from './stack' import * as bitwise from './bitwise' +import * as arithmetic from './arithmetic' +import * as crypto from './crypto' import * as expansion from './expansion' import * as invalid from './invalid' import { @@ -405,33 +406,33 @@ export const OP_CODES = { OP_RESERVED2: new bitwise.OP_RESERVED2(), // numeric - // OP_1ADD = 0x8b, - // OP_1SUB = 0x8c, - // OP_2MUL = 0x8d, - // OP_2DIV = 0x8e, - // OP_NEGATE = 0x8f, - // OP_ABS = 0x90, - // OP_NOT = 0x91, - // OP_0NOTEQUAL = 0x92, - // OP_ADD = 0x93, - // OP_SUB = 0x94, - // OP_MUL = 0x95, - // OP_DIV = 0x96, - // OP_MOD = 0x97, - // OP_LSHIFT = 0x98, - // OP_RSHIFT = 0x99, - // OP_BOOLAND = 0x9a, - // OP_BOOLOR = 0x9b, - // OP_NUMEQUAL = 0x9c, - // OP_NUMEQUALVERIFY = 0x9d, - // OP_NUMNOTEQUAL = 0x9e, - // OP_LESSTHAN = 0x9f, - // OP_GREATERTHAN = 0xa0, - // OP_LESSTHANOREQUAL = 0xa1, - // OP_GREATERTHANOREQUAL = 0xa2, - // OP_MIN = 0xa3, - // OP_MAX = 0xa4, - // OP_WITHIN = 0xa5, + OP_1ADD: new arithmetic.OP_1ADD(), + OP_1SUB: new arithmetic.OP_1SUB(), + OP_2MUL: new arithmetic.OP_2MUL(), + OP_2DIV: new arithmetic.OP_2DIV(), + OP_NEGATE: new arithmetic.OP_NEGATE(), + OP_ABS: new arithmetic.OP_ABS(), + OP_NOT: new arithmetic.OP_NOT(), + OP_0NOTEQUAL: new arithmetic.OP_0NOTEQUAL(), + OP_ADD: new arithmetic.OP_ADD(), + OP_SUB: new arithmetic.OP_SUB(), + OP_MUL: new arithmetic.OP_MUL(), + OP_DIV: new arithmetic.OP_DIV(), + OP_MOD: new arithmetic.OP_MOD(), + OP_LSHIFT: new arithmetic.OP_LSHIFT(), + OP_RSHIFT: new arithmetic.OP_RSHIFT(), + OP_BOOLAND: new arithmetic.OP_BOOLAND(), + OP_BOOLOR: new arithmetic.OP_BOOLOR(), + OP_NUMEQUAL: new arithmetic.OP_NUMEQUAL(), + OP_NUMEQUALVERIFY: new arithmetic.OP_NUMEQUALVERIFY(), + OP_NUMNOTEQUAL: new arithmetic.OP_NUMNOTEQUAL(), + OP_LESSTHAN: new arithmetic.OP_LESSTHAN(), + OP_GREATERTHAN: new arithmetic.OP_GREATERTHAN(), + OP_LESSTHANOREQUAL: new arithmetic.OP_LESSTHANOREQUAL(), + OP_GREATERTHANOREQUAL: new arithmetic.OP_GREATERTHANOREQUAL(), + OP_MIN: new arithmetic.OP_MIN(), + OP_MAX: new arithmetic.OP_MAX(), + OP_WITHIN: new arithmetic.OP_WITHIN(), // crypto OP_RIPEMD160: new crypto.OP_RIPEMD160(), @@ -528,6 +529,34 @@ const HEX_MAPPING: { 0x88: OP_CODES.OP_EQUALVERIFY, 0x89: OP_CODES.OP_RESERVED1, 0x8a: OP_CODES.OP_RESERVED2, + // numeric + 0x8b: OP_CODES.OP_1ADD, + 0x8c: OP_CODES.OP_1SUB, + 0x8d: OP_CODES.OP_2MUL, + 0x8e: OP_CODES.OP_2DIV, + 0x8f: OP_CODES.OP_NEGATE, + 0x90: OP_CODES.OP_ABS, + 0x91: OP_CODES.OP_NOT, + 0x92: OP_CODES.OP_0NOTEQUAL, + 0x93: OP_CODES.OP_ADD, + 0x94: OP_CODES.OP_SUB, + 0x95: OP_CODES.OP_MUL, + 0x96: OP_CODES.OP_DIV, + 0x97: OP_CODES.OP_MOD, + 0x98: OP_CODES.OP_LSHIFT, + 0x99: OP_CODES.OP_RSHIFT, + 0x9a: OP_CODES.OP_BOOLAND, + 0x9b: OP_CODES.OP_BOOLOR, + 0x9c: OP_CODES.OP_NUMEQUAL, + 0x9d: OP_CODES.OP_NUMEQUALVERIFY, + 0x9e: OP_CODES.OP_NUMNOTEQUAL, + 0x9f: OP_CODES.OP_LESSTHAN, + 0xa0: OP_CODES.OP_GREATERTHAN, + 0xa1: OP_CODES.OP_LESSTHANOREQUAL, + 0xa2: OP_CODES.OP_GREATERTHANOREQUAL, + 0xa3: OP_CODES.OP_MIN, + 0xa4: OP_CODES.OP_MAX, + 0xa5: OP_CODES.OP_WITHIN, // crypto 0xa6: OP_CODES.OP_RIPEMD160, 0xa7: OP_CODES.OP_SHA1,