From 927a0e9c37d1c71c9d8b072d83dae67d908cb99f Mon Sep 17 00:00:00 2001 From: Dave Collins Date: Sat, 2 May 2015 14:56:55 -0500 Subject: [PATCH] txscript: Test consistency and cleanup. - Move reference tests to test package since they are intended to exercise the engine as callers would - Improve the short form script parsing to allow additional opcodes: DATA_#, OP_#, FALSE, TRUE - Make use of a function to decode hex strings rather than manually defining byte slices - Update the tests to make use of the short form script parsing logic rather than manually defining byte slices - Consistently replace all []byte{} and [][]byte{} with nil - Define tests only used in a specific function inside that func - Move invalid flag combination test to engine_test since that is what it is testing - Remove all redundant script tests in favor of the JSON-based tests in the data directory. - Move several functions from internal_test.go to the test files associated with what the tests are checking --- txscript/engine_test.go | 285 +- txscript/internal_test.go | 7651 +++++++++++++++----------------- txscript/reference_test.go | 60 +- txscript/script_test.go | 2161 ++------- txscript/scriptbuilder_test.go | 8 +- txscript/sign_test.go | 48 +- txscript/stack_test.go | 110 +- txscript/standard.go | 2 +- txscript/standard_test.go | 801 ++-- 9 files changed, 4626 insertions(+), 6500 deletions(-) diff --git a/txscript/engine_test.go b/txscript/engine_test.go index 37d67f1c..5d47fc6e 100644 --- a/txscript/engine_test.go +++ b/txscript/engine_test.go @@ -54,7 +54,7 @@ func TestBadPC(t *testing.T) { TxOut: []*wire.TxOut{ { Value: 1000000000, - PkScript: []byte{}, + PkScript: nil, }, }, LockTime: 0, @@ -114,7 +114,7 @@ func TestCheckErrorCondition(t *testing.T) { TxOut: []*wire.TxOut{ { Value: 1000000000, - PkScript: []byte{}, + PkScript: nil, }, }, LockTime: 0, @@ -171,3 +171,284 @@ func TestCheckErrorCondition(t *testing.T) { t.Errorf("unexpected error %v on final check", err) } } + +// TestInvalidFlagCombinations ensures the script engine returns the expected +// error when disallowed flag combinations are specified. +func TestInvalidFlagCombinations(t *testing.T) { + t.Parallel() + + tests := []txscript.ScriptFlags{ + txscript.ScriptVerifyCleanStack, + } + + // tx with almost empty scripts. + tx := &wire.MsgTx{ + Version: 1, + TxIn: []*wire.TxIn{ + { + PreviousOutPoint: wire.OutPoint{ + Hash: wire.ShaHash([32]byte{ + 0xc9, 0x97, 0xa5, 0xe5, + 0x6e, 0x10, 0x41, 0x02, + 0xfa, 0x20, 0x9c, 0x6a, + 0x85, 0x2d, 0xd9, 0x06, + 0x60, 0xa2, 0x0b, 0x2d, + 0x9c, 0x35, 0x24, 0x23, + 0xed, 0xce, 0x25, 0x85, + 0x7f, 0xcd, 0x37, 0x04, + }), + Index: 0, + }, + SignatureScript: []uint8{txscript.OP_NOP}, + Sequence: 4294967295, + }, + }, + TxOut: []*wire.TxOut{ + { + Value: 1000000000, + PkScript: nil, + }, + }, + LockTime: 0, + } + pkScript := []byte{txscript.OP_NOP} + + for i, test := range tests { + _, err := txscript.NewEngine(pkScript, tx, 0, test) + if err != txscript.ErrInvalidFlags { + t.Fatalf("TestInvalidFlagCombinations #%d unexpected "+ + "error: %v", i, err) + } + } +} + +// TestCheckPubKeyEncoding ensures the internal checkPubKeyEncoding function +// works as expected. +func TestCheckPubKeyEncoding(t *testing.T) { + t.Parallel() + + tests := []struct { + name string + key []byte + isValid bool + }{ + { + name: "uncompressed ok", + key: decodeHex("0411db93e1dcdb8a016b49840f8c53bc1eb68" + + "a382e97b1482ecad7b148a6909a5cb2e0eaddfb84ccf" + + "9744464f82e160bfa9b8b64f9d4c03f999b8643f656b" + + "412a3"), + isValid: true, + }, + { + name: "compressed ok", + key: decodeHex("02ce0b14fb842b1ba549fdd675c98075f12e9" + + "c510f8ef52bd021a9a1f4809d3b4d"), + isValid: true, + }, + { + name: "compressed ok", + key: decodeHex("032689c7c2dab13309fb143e0e8fe39634252" + + "1887e976690b6b47f5b2a4b7d448e"), + isValid: true, + }, + { + name: "hybrid", + key: decodeHex("0679be667ef9dcbbac55a06295ce870b07029" + + "bfcdb2dce28d959f2815b16f81798483ada7726a3c46" + + "55da4fbfc0e1108a8fd17b448a68554199c47d08ffb1" + + "0d4b8"), + isValid: false, + }, + { + name: "empty", + key: nil, + isValid: false, + }, + } + + flags := txscript.ScriptVerifyStrictEncoding + for _, test := range tests { + err := txscript.TstCheckPubKeyEncoding(test.key, flags) + if err != nil && test.isValid { + t.Errorf("checkSignatureEncoding test '%s' failed "+ + "when it should have succeeded: %v", test.name, + err) + } else if err == nil && !test.isValid { + t.Errorf("checkSignatureEncooding test '%s' succeeded "+ + "when it should have failed", test.name) + } + } + +} + +// TestCheckSignatureEncoding ensures the internal checkSignatureEncoding +// function works as expected. +func TestCheckSignatureEncoding(t *testing.T) { + t.Parallel() + + tests := []struct { + name string + sig []byte + isValid bool + }{ + { + name: "valid signature", + sig: decodeHex("304402204e45e16932b8af514961a1d3a1a25" + + "fdf3f4f7732e9d624c6c61548ab5fb8cd41022018152" + + "2ec8eca07de4860a4acdd12909d831cc56cbbac46220" + + "82221a8768d1d09"), + isValid: true, + }, + { + name: "empty.", + sig: nil, + isValid: false, + }, + { + name: "bad magic", + sig: decodeHex("314402204e45e16932b8af514961a1d3a1a25" + + "fdf3f4f7732e9d624c6c61548ab5fb8cd41022018152" + + "2ec8eca07de4860a4acdd12909d831cc56cbbac46220" + + "82221a8768d1d09"), + isValid: false, + }, + { + name: "bad 1st int marker magic", + sig: decodeHex("304403204e45e16932b8af514961a1d3a1a25" + + "fdf3f4f7732e9d624c6c61548ab5fb8cd41022018152" + + "2ec8eca07de4860a4acdd12909d831cc56cbbac46220" + + "82221a8768d1d09"), + isValid: false, + }, + { + name: "bad 2nd int marker", + sig: decodeHex("304402204e45e16932b8af514961a1d3a1a25" + + "fdf3f4f7732e9d624c6c61548ab5fb8cd41032018152" + + "2ec8eca07de4860a4acdd12909d831cc56cbbac46220" + + "82221a8768d1d09"), + isValid: false, + }, + { + name: "short len", + sig: decodeHex("304302204e45e16932b8af514961a1d3a1a25" + + "fdf3f4f7732e9d624c6c61548ab5fb8cd41022018152" + + "2ec8eca07de4860a4acdd12909d831cc56cbbac46220" + + "82221a8768d1d09"), + isValid: false, + }, + { + name: "long len", + sig: decodeHex("304502204e45e16932b8af514961a1d3a1a25" + + "fdf3f4f7732e9d624c6c61548ab5fb8cd41022018152" + + "2ec8eca07de4860a4acdd12909d831cc56cbbac46220" + + "82221a8768d1d09"), + isValid: false, + }, + { + name: "long X", + sig: decodeHex("304402424e45e16932b8af514961a1d3a1a25" + + "fdf3f4f7732e9d624c6c61548ab5fb8cd41022018152" + + "2ec8eca07de4860a4acdd12909d831cc56cbbac46220" + + "82221a8768d1d09"), + isValid: false, + }, + { + name: "long Y", + sig: decodeHex("304402204e45e16932b8af514961a1d3a1a25" + + "fdf3f4f7732e9d624c6c61548ab5fb8cd41022118152" + + "2ec8eca07de4860a4acdd12909d831cc56cbbac46220" + + "82221a8768d1d09"), + isValid: false, + }, + { + name: "short Y", + sig: decodeHex("304402204e45e16932b8af514961a1d3a1a25" + + "fdf3f4f7732e9d624c6c61548ab5fb8cd41021918152" + + "2ec8eca07de4860a4acdd12909d831cc56cbbac46220" + + "82221a8768d1d09"), + isValid: false, + }, + { + name: "trailing crap", + sig: decodeHex("304402204e45e16932b8af514961a1d3a1a25" + + "fdf3f4f7732e9d624c6c61548ab5fb8cd41022018152" + + "2ec8eca07de4860a4acdd12909d831cc56cbbac46220" + + "82221a8768d1d0901"), + isValid: false, + }, + { + name: "X == N ", + sig: decodeHex("30440220fffffffffffffffffffffffffffff" + + "ffebaaedce6af48a03bbfd25e8cd0364141022018152" + + "2ec8eca07de4860a4acdd12909d831cc56cbbac46220" + + "82221a8768d1d09"), + isValid: false, + }, + { + name: "X == N ", + sig: decodeHex("30440220fffffffffffffffffffffffffffff" + + "ffebaaedce6af48a03bbfd25e8cd0364142022018152" + + "2ec8eca07de4860a4acdd12909d831cc56cbbac46220" + + "82221a8768d1d09"), + isValid: false, + }, + { + name: "Y == N", + sig: decodeHex("304402204e45e16932b8af514961a1d3a1a25" + + "fdf3f4f7732e9d624c6c61548ab5fb8cd410220fffff" + + "ffffffffffffffffffffffffffebaaedce6af48a03bb" + + "fd25e8cd0364141"), + isValid: false, + }, + { + name: "Y > N", + sig: decodeHex("304402204e45e16932b8af514961a1d3a1a25" + + "fdf3f4f7732e9d624c6c61548ab5fb8cd410220fffff" + + "ffffffffffffffffffffffffffebaaedce6af48a03bb" + + "fd25e8cd0364142"), + isValid: false, + }, + { + name: "0 len X", + sig: decodeHex("302402000220181522ec8eca07de4860a4acd" + + "d12909d831cc56cbbac4622082221a8768d1d09"), + isValid: false, + }, + { + name: "0 len Y", + sig: decodeHex("302402204e45e16932b8af514961a1d3a1a25" + + "fdf3f4f7732e9d624c6c61548ab5fb8cd410200"), + isValid: false, + }, + { + name: "extra R padding", + sig: decodeHex("30450221004e45e16932b8af514961a1d3a1a" + + "25fdf3f4f7732e9d624c6c61548ab5fb8cd410220181" + + "522ec8eca07de4860a4acdd12909d831cc56cbbac462" + + "2082221a8768d1d09"), + isValid: false, + }, + { + name: "extra S padding", + sig: decodeHex("304502204e45e16932b8af514961a1d3a1a25" + + "fdf3f4f7732e9d624c6c61548ab5fb8cd41022100181" + + "522ec8eca07de4860a4acdd12909d831cc56cbbac462" + + "2082221a8768d1d09"), + isValid: false, + }, + } + + flags := txscript.ScriptVerifyStrictEncoding + for _, test := range tests { + err := txscript.TstCheckSignatureEncoding(test.sig, flags) + if err != nil && test.isValid { + t.Errorf("checkSignatureEncoding test '%s' failed "+ + "when it should have succeeded: %v", test.name, + err) + } else if err == nil && !test.isValid { + t.Errorf("checkSignatureEncooding test '%s' succeeded "+ + "when it should have failed", test.name) + } + } +} diff --git a/txscript/internal_test.go b/txscript/internal_test.go index bdc8eb6c..8fc1c00d 100644 --- a/txscript/internal_test.go +++ b/txscript/internal_test.go @@ -2,6 +2,13 @@ // Use of this source code is governed by an ISC // license that can be found in the LICENSE file. +/* +This test file is part of the txscript package rather than than the +txscript_test package so it can bridge access to the internals to properly test +cases which are either not possible or can't reliably be tested via the public +interface. The functions are only exported while the tests are being run. +*/ + package txscript import "testing" @@ -18,339 +25,37 @@ var TstHasCanonicalPushes = canonicalPush // test package. var TstParseScript = parseScript -// this file is present to export some internal interfaces so that we can -// test them reliably. - -func TestCheckPubKeyEncoding(t *testing.T) { - t.Parallel() - - tests := []struct { - name string - key []byte - isValid bool - }{ - { - name: "uncompressed ok", - key: []byte{0x04, 0x11, 0xdb, 0x93, 0xe1, 0xdc, 0xdb, 0x8a, - 0x01, 0x6b, 0x49, 0x84, 0x0f, 0x8c, 0x53, 0xbc, 0x1e, - 0xb6, 0x8a, 0x38, 0x2e, 0x97, 0xb1, 0x48, 0x2e, 0xca, - 0xd7, 0xb1, 0x48, 0xa6, 0x90, 0x9a, 0x5c, 0xb2, 0xe0, - 0xea, 0xdd, 0xfb, 0x84, 0xcc, 0xf9, 0x74, 0x44, 0x64, - 0xf8, 0x2e, 0x16, 0x0b, 0xfa, 0x9b, 0x8b, 0x64, 0xf9, - 0xd4, 0xc0, 0x3f, 0x99, 0x9b, 0x86, 0x43, 0xf6, 0x56, - 0xb4, 0x12, 0xa3, - }, - isValid: true, - }, - { - name: "compressed ok", - key: []byte{0x02, 0xce, 0x0b, 0x14, 0xfb, 0x84, 0x2b, 0x1b, - 0xa5, 0x49, 0xfd, 0xd6, 0x75, 0xc9, 0x80, 0x75, 0xf1, - 0x2e, 0x9c, 0x51, 0x0f, 0x8e, 0xf5, 0x2b, 0xd0, 0x21, - 0xa9, 0xa1, 0xf4, 0x80, 0x9d, 0x3b, 0x4d, - }, - isValid: true, - }, - { - name: "compressed ok", - key: []byte{0x03, 0x26, 0x89, 0xc7, 0xc2, 0xda, 0xb1, 0x33, - 0x09, 0xfb, 0x14, 0x3e, 0x0e, 0x8f, 0xe3, 0x96, 0x34, - 0x25, 0x21, 0x88, 0x7e, 0x97, 0x66, 0x90, 0xb6, 0xb4, - 0x7f, 0x5b, 0x2a, 0x4b, 0x7d, 0x44, 0x8e, - }, - isValid: true, - }, - { - name: "hybrid", - key: []byte{0x06, 0x79, 0xbe, 0x66, 0x7e, 0xf9, 0xdc, 0xbb, - 0xac, 0x55, 0xa0, 0x62, 0x95, 0xce, 0x87, 0x0b, 0x07, - 0x02, 0x9b, 0xfc, 0xdb, 0x2d, 0xce, 0x28, 0xd9, 0x59, - 0xf2, 0x81, 0x5b, 0x16, 0xf8, 0x17, 0x98, 0x48, 0x3a, - 0xda, 0x77, 0x26, 0xa3, 0xc4, 0x65, 0x5d, 0xa4, 0xfb, - 0xfc, 0x0e, 0x11, 0x08, 0xa8, 0xfd, 0x17, 0xb4, 0x48, - 0xa6, 0x85, 0x54, 0x19, 0x9c, 0x47, 0xd0, 0x8f, 0xfb, - 0x10, 0xd4, 0xb8, - }, - isValid: false, - }, - { - name: "empty.", - key: []byte{}, - isValid: false, - }, - } - vm := Engine{flags: ScriptVerifyStrictEncoding} - for _, test := range tests { - err := vm.checkPubKeyEncoding(test.key) - if err != nil && test.isValid { - t.Errorf("checkSignatureEncoding test '%s' failed "+ - "when it should have succeeded: %v", test.name, - err) - } else if err == nil && !test.isValid { - t.Errorf("checkSignatureEncooding test '%s' succeeded "+ - "when it should have failed", test.name) - } +// TstConcatRawScript makes the ability to add the pass script directly to +// an existing script to the test package. This differs from AddData since it +// doesn't add a push data opcode. +func (b *ScriptBuilder) TstConcatRawScript(data []byte) *ScriptBuilder { + if b.err != nil { + return b } + b.script = append(b.script, data...) + return b } -func TestCheckSignatureEncoding(t *testing.T) { - t.Parallel() - - tests := []struct { - name string - sig []byte - isValid bool - }{ - { - name: "valid signature.", - sig: []byte{0x30, 0x44, 0x02, 0x20, 0x4e, 0x45, 0xe1, 0x69, - 0x32, 0xb8, 0xaf, 0x51, 0x49, 0x61, 0xa1, 0xd3, 0xa1, - 0xa2, 0x5f, 0xdf, 0x3f, 0x4f, 0x77, 0x32, 0xe9, 0xd6, - 0x24, 0xc6, 0xc6, 0x15, 0x48, 0xab, 0x5f, 0xb8, 0xcd, - 0x41, 0x02, 0x20, 0x18, 0x15, 0x22, 0xec, 0x8e, 0xca, - 0x07, 0xde, 0x48, 0x60, 0xa4, 0xac, 0xdd, 0x12, 0x90, - 0x9d, 0x83, 0x1c, 0xc5, 0x6c, 0xbb, 0xac, 0x46, 0x22, - 0x08, 0x22, 0x21, 0xa8, 0x76, 0x8d, 0x1d, 0x09, - }, - isValid: true, - }, - { - name: "empty.", - sig: []byte{}, - isValid: false, - }, - { - name: "bad magic.", - sig: []byte{0x31, 0x44, 0x02, 0x20, 0x4e, 0x45, 0xe1, 0x69, - 0x32, 0xb8, 0xaf, 0x51, 0x49, 0x61, 0xa1, 0xd3, 0xa1, - 0xa2, 0x5f, 0xdf, 0x3f, 0x4f, 0x77, 0x32, 0xe9, 0xd6, - 0x24, 0xc6, 0xc6, 0x15, 0x48, 0xab, 0x5f, 0xb8, 0xcd, - 0x41, 0x02, 0x20, 0x18, 0x15, 0x22, 0xec, 0x8e, 0xca, - 0x07, 0xde, 0x48, 0x60, 0xa4, 0xac, 0xdd, 0x12, 0x90, - 0x9d, 0x83, 0x1c, 0xc5, 0x6c, 0xbb, 0xac, 0x46, 0x22, - 0x08, 0x22, 0x21, 0xa8, 0x76, 0x8d, 0x1d, 0x09, - }, - isValid: false, - }, - { - name: "bad 1st int marker magic.", - sig: []byte{0x30, 0x44, 0x03, 0x20, 0x4e, 0x45, 0xe1, 0x69, - 0x32, 0xb8, 0xaf, 0x51, 0x49, 0x61, 0xa1, 0xd3, 0xa1, - 0xa2, 0x5f, 0xdf, 0x3f, 0x4f, 0x77, 0x32, 0xe9, 0xd6, - 0x24, 0xc6, 0xc6, 0x15, 0x48, 0xab, 0x5f, 0xb8, 0xcd, - 0x41, 0x02, 0x20, 0x18, 0x15, 0x22, 0xec, 0x8e, 0xca, - 0x07, 0xde, 0x48, 0x60, 0xa4, 0xac, 0xdd, 0x12, 0x90, - 0x9d, 0x83, 0x1c, 0xc5, 0x6c, 0xbb, 0xac, 0x46, 0x22, - 0x08, 0x22, 0x21, 0xa8, 0x76, 0x8d, 0x1d, 0x09, - }, - isValid: false, - }, - { - name: "bad 2nd int marker.", - sig: []byte{0x30, 0x44, 0x02, 0x20, 0x4e, 0x45, 0xe1, 0x69, - 0x32, 0xb8, 0xaf, 0x51, 0x49, 0x61, 0xa1, 0xd3, 0xa1, - 0xa2, 0x5f, 0xdf, 0x3f, 0x4f, 0x77, 0x32, 0xe9, 0xd6, - 0x24, 0xc6, 0xc6, 0x15, 0x48, 0xab, 0x5f, 0xb8, 0xcd, - 0x41, 0x03, 0x20, 0x18, 0x15, 0x22, 0xec, 0x8e, 0xca, - 0x07, 0xde, 0x48, 0x60, 0xa4, 0xac, 0xdd, 0x12, 0x90, - 0x9d, 0x83, 0x1c, 0xc5, 0x6c, 0xbb, 0xac, 0x46, 0x22, - 0x08, 0x22, 0x21, 0xa8, 0x76, 0x8d, 0x1d, 0x09, - }, - isValid: false, - }, - { - name: "short len", - sig: []byte{0x30, 0x43, 0x02, 0x20, 0x4e, 0x45, 0xe1, 0x69, - 0x32, 0xb8, 0xaf, 0x51, 0x49, 0x61, 0xa1, 0xd3, 0xa1, - 0xa2, 0x5f, 0xdf, 0x3f, 0x4f, 0x77, 0x32, 0xe9, 0xd6, - 0x24, 0xc6, 0xc6, 0x15, 0x48, 0xab, 0x5f, 0xb8, 0xcd, - 0x41, 0x02, 0x20, 0x18, 0x15, 0x22, 0xec, 0x8e, 0xca, - 0x07, 0xde, 0x48, 0x60, 0xa4, 0xac, 0xdd, 0x12, 0x90, - 0x9d, 0x83, 0x1c, 0xc5, 0x6c, 0xbb, 0xac, 0x46, 0x22, - 0x08, 0x22, 0x21, 0xa8, 0x76, 0x8d, 0x1d, 0x09, - }, - isValid: false, - }, - { - name: "long len", - sig: []byte{0x30, 0x45, 0x02, 0x20, 0x4e, 0x45, 0xe1, 0x69, - 0x32, 0xb8, 0xaf, 0x51, 0x49, 0x61, 0xa1, 0xd3, 0xa1, - 0xa2, 0x5f, 0xdf, 0x3f, 0x4f, 0x77, 0x32, 0xe9, 0xd6, - 0x24, 0xc6, 0xc6, 0x15, 0x48, 0xab, 0x5f, 0xb8, 0xcd, - 0x41, 0x02, 0x20, 0x18, 0x15, 0x22, 0xec, 0x8e, 0xca, - 0x07, 0xde, 0x48, 0x60, 0xa4, 0xac, 0xdd, 0x12, 0x90, - 0x9d, 0x83, 0x1c, 0xc5, 0x6c, 0xbb, 0xac, 0x46, 0x22, - 0x08, 0x22, 0x21, 0xa8, 0x76, 0x8d, 0x1d, 0x09, - }, - isValid: false, - }, - { - name: "long X", - sig: []byte{0x30, 0x44, 0x02, 0x42, 0x4e, 0x45, 0xe1, 0x69, - 0x32, 0xb8, 0xaf, 0x51, 0x49, 0x61, 0xa1, 0xd3, 0xa1, - 0xa2, 0x5f, 0xdf, 0x3f, 0x4f, 0x77, 0x32, 0xe9, 0xd6, - 0x24, 0xc6, 0xc6, 0x15, 0x48, 0xab, 0x5f, 0xb8, 0xcd, - 0x41, 0x02, 0x20, 0x18, 0x15, 0x22, 0xec, 0x8e, 0xca, - 0x07, 0xde, 0x48, 0x60, 0xa4, 0xac, 0xdd, 0x12, 0x90, - 0x9d, 0x83, 0x1c, 0xc5, 0x6c, 0xbb, 0xac, 0x46, 0x22, - 0x08, 0x22, 0x21, 0xa8, 0x76, 0x8d, 0x1d, 0x09, - }, - isValid: false, - }, - { - name: "long Y", - sig: []byte{0x30, 0x44, 0x02, 0x20, 0x4e, 0x45, 0xe1, 0x69, - 0x32, 0xb8, 0xaf, 0x51, 0x49, 0x61, 0xa1, 0xd3, 0xa1, - 0xa2, 0x5f, 0xdf, 0x3f, 0x4f, 0x77, 0x32, 0xe9, 0xd6, - 0x24, 0xc6, 0xc6, 0x15, 0x48, 0xab, 0x5f, 0xb8, 0xcd, - 0x41, 0x02, 0x21, 0x18, 0x15, 0x22, 0xec, 0x8e, 0xca, - 0x07, 0xde, 0x48, 0x60, 0xa4, 0xac, 0xdd, 0x12, 0x90, - 0x9d, 0x83, 0x1c, 0xc5, 0x6c, 0xbb, 0xac, 0x46, 0x22, - 0x08, 0x22, 0x21, 0xa8, 0x76, 0x8d, 0x1d, 0x09, - }, - isValid: false, - }, - { - name: "short Y", - sig: []byte{0x30, 0x44, 0x02, 0x20, 0x4e, 0x45, 0xe1, 0x69, - 0x32, 0xb8, 0xaf, 0x51, 0x49, 0x61, 0xa1, 0xd3, 0xa1, - 0xa2, 0x5f, 0xdf, 0x3f, 0x4f, 0x77, 0x32, 0xe9, 0xd6, - 0x24, 0xc6, 0xc6, 0x15, 0x48, 0xab, 0x5f, 0xb8, 0xcd, - 0x41, 0x02, 0x19, 0x18, 0x15, 0x22, 0xec, 0x8e, 0xca, - 0x07, 0xde, 0x48, 0x60, 0xa4, 0xac, 0xdd, 0x12, 0x90, - 0x9d, 0x83, 0x1c, 0xc5, 0x6c, 0xbb, 0xac, 0x46, 0x22, - 0x08, 0x22, 0x21, 0xa8, 0x76, 0x8d, 0x1d, 0x09, - }, - isValid: false, - }, - { - name: "trailing crap.", - sig: []byte{0x30, 0x44, 0x02, 0x20, 0x4e, 0x45, 0xe1, 0x69, - 0x32, 0xb8, 0xaf, 0x51, 0x49, 0x61, 0xa1, 0xd3, 0xa1, - 0xa2, 0x5f, 0xdf, 0x3f, 0x4f, 0x77, 0x32, 0xe9, 0xd6, - 0x24, 0xc6, 0xc6, 0x15, 0x48, 0xab, 0x5f, 0xb8, 0xcd, - 0x41, 0x02, 0x20, 0x18, 0x15, 0x22, 0xec, 0x8e, 0xca, - 0x07, 0xde, 0x48, 0x60, 0xa4, 0xac, 0xdd, 0x12, 0x90, - 0x9d, 0x83, 0x1c, 0xc5, 0x6c, 0xbb, 0xac, 0x46, 0x22, - 0x08, 0x22, 0x21, 0xa8, 0x76, 0x8d, 0x1d, 0x09, 0x01, - }, - isValid: false, - }, - { - name: "X == N ", - sig: []byte{0x30, 0x44, 0x02, 0x20, 0xFF, 0xFF, 0xFF, 0xFF, - 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, - 0xFF, 0xFF, 0xFE, 0xBA, 0xAE, 0xDC, 0xE6, 0xAF, 0x48, - 0xA0, 0x3B, 0xBF, 0xD2, 0x5E, 0x8C, 0xD0, 0x36, 0x41, - 0x41, 0x02, 0x20, 0x18, 0x15, 0x22, 0xec, 0x8e, 0xca, - 0x07, 0xde, 0x48, 0x60, 0xa4, 0xac, 0xdd, 0x12, 0x90, - 0x9d, 0x83, 0x1c, 0xc5, 0x6c, 0xbb, 0xac, 0x46, 0x22, - 0x08, 0x22, 0x21, 0xa8, 0x76, 0x8d, 0x1d, 0x09, - }, - isValid: false, - }, - { - name: "X == N ", - sig: []byte{0x30, 0x44, 0x02, 0x20, 0xFF, 0xFF, 0xFF, 0xFF, - 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, - 0xFF, 0xFF, 0xFE, 0xBA, 0xAE, 0xDC, 0xE6, 0xAF, 0x48, - 0xA0, 0x3B, 0xBF, 0xD2, 0x5E, 0x8C, 0xD0, 0x36, 0x41, - 0x42, 0x02, 0x20, 0x18, 0x15, 0x22, 0xec, 0x8e, 0xca, - 0x07, 0xde, 0x48, 0x60, 0xa4, 0xac, 0xdd, 0x12, 0x90, - 0x9d, 0x83, 0x1c, 0xc5, 0x6c, 0xbb, 0xac, 0x46, 0x22, - 0x08, 0x22, 0x21, 0xa8, 0x76, 0x8d, 0x1d, 0x09, - }, - isValid: false, - }, - { - name: "Y == N", - sig: []byte{0x30, 0x44, 0x02, 0x20, 0x4e, 0x45, 0xe1, 0x69, - 0x32, 0xb8, 0xaf, 0x51, 0x49, 0x61, 0xa1, 0xd3, 0xa1, - 0xa2, 0x5f, 0xdf, 0x3f, 0x4f, 0x77, 0x32, 0xe9, 0xd6, - 0x24, 0xc6, 0xc6, 0x15, 0x48, 0xab, 0x5f, 0xb8, 0xcd, - 0x41, 0x02, 0x20, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, - 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, - 0xFE, 0xBA, 0xAE, 0xDC, 0xE6, 0xAF, 0x48, 0xA0, 0x3B, - 0xBF, 0xD2, 0x5E, 0x8C, 0xD0, 0x36, 0x41, 0x41, - }, - isValid: false, - }, - { - name: "Y > N", - sig: []byte{0x30, 0x44, 0x02, 0x20, 0x4e, 0x45, 0xe1, 0x69, - 0x32, 0xb8, 0xaf, 0x51, 0x49, 0x61, 0xa1, 0xd3, 0xa1, - 0xa2, 0x5f, 0xdf, 0x3f, 0x4f, 0x77, 0x32, 0xe9, 0xd6, - 0x24, 0xc6, 0xc6, 0x15, 0x48, 0xab, 0x5f, 0xb8, 0xcd, - 0x41, 0x02, 0x20, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, - 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, - 0xFE, 0xBA, 0xAE, 0xDC, 0xE6, 0xAF, 0x48, 0xA0, 0x3B, - 0xBF, 0xD2, 0x5E, 0x8C, 0xD0, 0x36, 0x41, 0x42, - }, - isValid: false, - }, - { - name: "0 len X.", - sig: []byte{0x30, 0x24, 0x02, 0x00, 0x02, 0x20, 0x18, 0x15, - 0x22, 0xec, 0x8e, 0xca, 0x07, 0xde, 0x48, 0x60, 0xa4, - 0xac, 0xdd, 0x12, 0x90, 0x9d, 0x83, 0x1c, 0xc5, 0x6c, - 0xbb, 0xac, 0x46, 0x22, 0x08, 0x22, 0x21, 0xa8, 0x76, - 0x8d, 0x1d, 0x09, - }, - isValid: false, - }, - { - name: "0 len Y.", - sig: []byte{0x30, 0x24, 0x02, 0x20, 0x4e, 0x45, 0xe1, 0x69, - 0x32, 0xb8, 0xaf, 0x51, 0x49, 0x61, 0xa1, 0xd3, 0xa1, - 0xa2, 0x5f, 0xdf, 0x3f, 0x4f, 0x77, 0x32, 0xe9, 0xd6, - 0x24, 0xc6, 0xc6, 0x15, 0x48, 0xab, 0x5f, 0xb8, 0xcd, - 0x41, 0x02, 0x00, - }, - isValid: false, - }, - { - name: "extra R padding.", - sig: []byte{0x30, 0x45, 0x02, 0x21, 0x00, 0x4e, 0x45, 0xe1, 0x69, - 0x32, 0xb8, 0xaf, 0x51, 0x49, 0x61, 0xa1, 0xd3, 0xa1, - 0xa2, 0x5f, 0xdf, 0x3f, 0x4f, 0x77, 0x32, 0xe9, 0xd6, - 0x24, 0xc6, 0xc6, 0x15, 0x48, 0xab, 0x5f, 0xb8, 0xcd, - 0x41, 0x02, 0x20, 0x18, 0x15, 0x22, 0xec, 0x8e, 0xca, - 0x07, 0xde, 0x48, 0x60, 0xa4, 0xac, 0xdd, 0x12, 0x90, - 0x9d, 0x83, 0x1c, 0xc5, 0x6c, 0xbb, 0xac, 0x46, 0x22, - 0x08, 0x22, 0x21, 0xa8, 0x76, 0x8d, 0x1d, 0x09, - }, - isValid: false, - }, - { - name: "extra S padding.", - sig: []byte{0x30, 0x45, 0x02, 0x20, 0x4e, 0x45, 0xe1, 0x69, - 0x32, 0xb8, 0xaf, 0x51, 0x49, 0x61, 0xa1, 0xd3, 0xa1, - 0xa2, 0x5f, 0xdf, 0x3f, 0x4f, 0x77, 0x32, 0xe9, 0xd6, - 0x24, 0xc6, 0xc6, 0x15, 0x48, 0xab, 0x5f, 0xb8, 0xcd, - 0x41, 0x02, 0x21, 0x00, 0x18, 0x15, 0x22, 0xec, 0x8e, 0xca, - 0x07, 0xde, 0x48, 0x60, 0xa4, 0xac, 0xdd, 0x12, 0x90, - 0x9d, 0x83, 0x1c, 0xc5, 0x6c, 0xbb, 0xac, 0x46, 0x22, - 0x08, 0x22, 0x21, 0xa8, 0x76, 0x8d, 0x1d, 0x09, - }, - isValid: false, - }, - } - - vm := Engine{flags: ScriptVerifyStrictEncoding} - for _, test := range tests { - err := vm.checkSignatureEncoding(test.sig) - if err != nil && test.isValid { - t.Errorf("checkSignatureEncoding test '%s' failed "+ - "when it should have succeeded: %v", test.name, - err) - } else if err == nil && !test.isValid { - t.Errorf("checkSignatureEncooding test '%s' succeeded "+ - "when it should have failed", test.name) - } - } +// TstCheckPubKeyEncoding makes the internal checkPubKeyEncoding function +// available to the test package. Since it only really needs from the engine +// for the flags, just accept the flags and create a new engine skeleton. +func TstCheckPubKeyEncoding(pubKey []byte, flags ScriptFlags) error { + vm := Engine{flags: flags} + return vm.checkPubKeyEncoding(pubKey) } +// TstCheckSignatureEncoding makes the internal checkSignatureEncoding function +// available to the test package. Since it only really needs from the engine +// for the flags, just accept the flags and create a new engine skeleton with +// them. +func TstCheckSignatureEncoding(sig []byte, flags ScriptFlags) error { + vm := Engine{flags: flags} + return vm.checkSignatureEncoding(sig) +} + +// TstRemoveOpcode makes the internal removeOpcode function available to the +// test package. func TstRemoveOpcode(pkscript []byte, opcode byte) ([]byte, error) { pops, err := parseScript(pkscript) if err != nil { @@ -360,6 +65,8 @@ func TstRemoveOpcode(pkscript []byte, opcode byte) ([]byte, error) { return unparseScript(pops) } +// TstRemoveOpcodeByData makes the internal removeOpcodeByData function +// available to the test package. func TstRemoveOpcodeByData(pkscript []byte, data []byte) ([]byte, error) { pops, err := parseScript(pkscript) if err != nil { @@ -376,15 +83,15 @@ func (vm *Engine) TstSetPC(script, off int) { vm.scriptOff = off } -// Internal tests for opcodde parsing with bad data templates. +// Internal tests for opcode parsing with bad data templates. func TestParseOpcode(t *testing.T) { - // Deep copy the array. + // Deep copy the array and make one of the opcodes invalid by setting it + // to the wrong length. fakeArray := opcodeArray - // wrong length -8. fakeArray[OP_PUSHDATA4] = opcode{value: OP_PUSHDATA4, name: "OP_PUSHDATA4", length: -8, opfunc: opcodePushData} - // this script would be fine if -8 was a valid length. + // This script would be fine if -8 was a valid length. _, err := parseScriptTemplate([]byte{OP_PUSHDATA4, 0x1, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00}, &fakeArray) if err == nil { @@ -392,3649 +99,3647 @@ func TestParseOpcode(t *testing.T) { } } -type popTest struct { - name string - pop *parsedOpcode - expectedErr error -} - -var popTests = []popTest{ - { - name: "OP_FALSE", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_FALSE], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_FALSE long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_FALSE], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_1 short", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_1], - data: nil, - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_1", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_1], - data: make([]byte, 1), - }, - expectedErr: nil, - }, - { - name: "OP_DATA_1 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_1], - data: make([]byte, 2), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_2 short", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_2], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_2", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_2], - data: make([]byte, 2), - }, - expectedErr: nil, - }, - { - name: "OP_DATA_2 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_2], - data: make([]byte, 3), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_3 short", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_3], - data: make([]byte, 2), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_3", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_3], - data: make([]byte, 3), - }, - expectedErr: nil, - }, - { - name: "OP_DATA_3 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_3], - data: make([]byte, 4), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_4 short", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_4], - data: make([]byte, 3), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_4", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_4], - data: make([]byte, 4), - }, - expectedErr: nil, - }, - { - name: "OP_DATA_4 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_4], - data: make([]byte, 5), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_5 short", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_5], - data: make([]byte, 4), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_5", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_5], - data: make([]byte, 5), - }, - expectedErr: nil, - }, - { - name: "OP_DATA_5 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_5], - data: make([]byte, 6), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_6 short", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_6], - data: make([]byte, 5), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_6", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_6], - data: make([]byte, 6), - }, - expectedErr: nil, - }, - { - name: "OP_DATA_6 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_6], - data: make([]byte, 7), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_7 short", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_7], - data: make([]byte, 6), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_7", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_7], - data: make([]byte, 7), - }, - expectedErr: nil, - }, - { - name: "OP_DATA_7 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_7], - data: make([]byte, 8), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_8 short", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_8], - data: make([]byte, 7), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_8", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_8], - data: make([]byte, 8), - }, - expectedErr: nil, - }, - { - name: "OP_DATA_8 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_8], - data: make([]byte, 9), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_9 short", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_9], - data: make([]byte, 8), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_9", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_9], - data: make([]byte, 9), - }, - expectedErr: nil, - }, - { - name: "OP_DATA_9 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_9], - data: make([]byte, 10), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_10 short", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_10], - data: make([]byte, 9), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_10", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_10], - data: make([]byte, 10), - }, - expectedErr: nil, - }, - { - name: "OP_DATA_10 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_10], - data: make([]byte, 11), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_11 short", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_11], - data: make([]byte, 10), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_11", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_11], - data: make([]byte, 11), - }, - expectedErr: nil, - }, - { - name: "OP_DATA_11 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_11], - data: make([]byte, 12), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_12 short", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_12], - data: make([]byte, 11), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_12", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_12], - data: make([]byte, 12), - }, - expectedErr: nil, - }, - { - name: "OP_DATA_12 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_12], - data: make([]byte, 13), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_13 short", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_13], - data: make([]byte, 12), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_13", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_13], - data: make([]byte, 13), - }, - expectedErr: nil, - }, - { - name: "OP_DATA_13 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_13], - data: make([]byte, 14), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_14 short", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_14], - data: make([]byte, 13), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_14", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_14], - data: make([]byte, 14), - }, - expectedErr: nil, - }, - { - name: "OP_DATA_14 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_14], - data: make([]byte, 15), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_15 short", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_15], - data: make([]byte, 14), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_15", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_15], - data: make([]byte, 15), - }, - expectedErr: nil, - }, - { - name: "OP_DATA_15 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_15], - data: make([]byte, 16), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_16 short", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_16], - data: make([]byte, 15), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_16", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_16], - data: make([]byte, 16), - }, - expectedErr: nil, - }, - { - name: "OP_DATA_16 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_16], - data: make([]byte, 17), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_17 short", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_17], - data: make([]byte, 16), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_17", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_17], - data: make([]byte, 17), - }, - expectedErr: nil, - }, - { - name: "OP_DATA_17 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_17], - data: make([]byte, 18), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_18 short", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_18], - data: make([]byte, 17), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_18", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_18], - data: make([]byte, 18), - }, - expectedErr: nil, - }, - { - name: "OP_DATA_18 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_18], - data: make([]byte, 19), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_19 short", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_19], - data: make([]byte, 18), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_19", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_19], - data: make([]byte, 19), - }, - expectedErr: nil, - }, - { - name: "OP_DATA_19 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_19], - data: make([]byte, 20), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_20 short", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_20], - data: make([]byte, 19), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_20", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_20], - data: make([]byte, 20), - }, - expectedErr: nil, - }, - { - name: "OP_DATA_20 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_20], - data: make([]byte, 21), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_21 short", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_21], - data: make([]byte, 20), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_21", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_21], - data: make([]byte, 21), - }, - expectedErr: nil, - }, - { - name: "OP_DATA_21 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_21], - data: make([]byte, 22), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_22 short", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_22], - data: make([]byte, 21), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_22", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_22], - data: make([]byte, 22), - }, - expectedErr: nil, - }, - { - name: "OP_DATA_22 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_22], - data: make([]byte, 23), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_23 short", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_23], - data: make([]byte, 22), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_23", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_23], - data: make([]byte, 23), - }, - expectedErr: nil, - }, - { - name: "OP_DATA_23 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_23], - data: make([]byte, 24), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_24 short", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_24], - data: make([]byte, 23), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_24", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_24], - data: make([]byte, 24), - }, - expectedErr: nil, - }, - { - name: "OP_DATA_24 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_24], - data: make([]byte, 25), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_25 short", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_25], - data: make([]byte, 24), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_25", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_25], - data: make([]byte, 25), - }, - expectedErr: nil, - }, - { - name: "OP_DATA_25 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_25], - data: make([]byte, 26), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_26 short", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_26], - data: make([]byte, 25), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_26", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_26], - data: make([]byte, 26), - }, - expectedErr: nil, - }, - { - name: "OP_DATA_26 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_26], - data: make([]byte, 27), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_27 short", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_27], - data: make([]byte, 26), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_27", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_27], - data: make([]byte, 27), - }, - expectedErr: nil, - }, - { - name: "OP_DATA_27 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_27], - data: make([]byte, 28), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_28 short", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_28], - data: make([]byte, 27), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_28", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_28], - data: make([]byte, 28), - }, - expectedErr: nil, - }, - { - name: "OP_DATA_28 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_28], - data: make([]byte, 29), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_29 short", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_29], - data: make([]byte, 28), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_29", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_29], - data: make([]byte, 29), - }, - expectedErr: nil, - }, - { - name: "OP_DATA_29 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_29], - data: make([]byte, 30), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_30 short", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_30], - data: make([]byte, 29), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_30", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_30], - data: make([]byte, 30), - }, - expectedErr: nil, - }, - { - name: "OP_DATA_30 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_30], - data: make([]byte, 31), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_31 short", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_31], - data: make([]byte, 30), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_31", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_31], - data: make([]byte, 31), - }, - expectedErr: nil, - }, - { - name: "OP_DATA_31 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_31], - data: make([]byte, 32), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_32 short", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_32], - data: make([]byte, 31), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_32", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_32], - data: make([]byte, 32), - }, - expectedErr: nil, - }, - { - name: "OP_DATA_32 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_32], - data: make([]byte, 33), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_33 short", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_33], - data: make([]byte, 32), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_33", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_33], - data: make([]byte, 33), - }, - expectedErr: nil, - }, - { - name: "OP_DATA_33 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_33], - data: make([]byte, 34), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_34 short", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_34], - data: make([]byte, 33), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_34", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_34], - data: make([]byte, 34), - }, - expectedErr: nil, - }, - { - name: "OP_DATA_34 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_34], - data: make([]byte, 35), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_35 short", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_35], - data: make([]byte, 34), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_35", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_35], - data: make([]byte, 35), - }, - expectedErr: nil, - }, - { - name: "OP_DATA_35 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_35], - data: make([]byte, 36), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_36 short", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_36], - data: make([]byte, 35), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_36", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_36], - data: make([]byte, 36), - }, - expectedErr: nil, - }, - { - name: "OP_DATA_36 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_36], - data: make([]byte, 37), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_37 short", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_37], - data: make([]byte, 36), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_37", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_37], - data: make([]byte, 37), - }, - expectedErr: nil, - }, - { - name: "OP_DATA_37 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_37], - data: make([]byte, 38), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_38 short", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_38], - data: make([]byte, 37), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_38", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_38], - data: make([]byte, 38), - }, - expectedErr: nil, - }, - { - name: "OP_DATA_38 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_38], - data: make([]byte, 39), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_39 short", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_39], - data: make([]byte, 38), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_39", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_39], - data: make([]byte, 39), - }, - expectedErr: nil, - }, - { - name: "OP_DATA_39 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_39], - data: make([]byte, 40), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_40 short", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_40], - data: make([]byte, 39), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_40", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_40], - data: make([]byte, 40), - }, - expectedErr: nil, - }, - { - name: "OP_DATA_40 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_40], - data: make([]byte, 41), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_41 short", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_41], - data: make([]byte, 40), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_41", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_41], - data: make([]byte, 41), - }, - expectedErr: nil, - }, - { - name: "OP_DATA_41 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_41], - data: make([]byte, 42), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_42 short", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_42], - data: make([]byte, 41), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_42", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_42], - data: make([]byte, 42), - }, - expectedErr: nil, - }, - { - name: "OP_DATA_42 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_42], - data: make([]byte, 43), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_43 short", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_43], - data: make([]byte, 42), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_43", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_43], - data: make([]byte, 43), - }, - expectedErr: nil, - }, - { - name: "OP_DATA_43 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_43], - data: make([]byte, 44), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_44 short", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_44], - data: make([]byte, 43), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_44", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_44], - data: make([]byte, 44), - }, - expectedErr: nil, - }, - { - name: "OP_DATA_44 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_44], - data: make([]byte, 45), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_45 short", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_45], - data: make([]byte, 44), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_45", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_45], - data: make([]byte, 45), - }, - expectedErr: nil, - }, - { - name: "OP_DATA_45 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_45], - data: make([]byte, 46), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_46 short", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_46], - data: make([]byte, 45), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_46", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_46], - data: make([]byte, 46), - }, - expectedErr: nil, - }, - { - name: "OP_DATA_46 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_46], - data: make([]byte, 47), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_47 short", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_47], - data: make([]byte, 46), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_47", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_47], - data: make([]byte, 47), - }, - expectedErr: nil, - }, - { - name: "OP_DATA_47 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_47], - data: make([]byte, 48), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_48 short", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_48], - data: make([]byte, 47), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_48", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_48], - data: make([]byte, 48), - }, - expectedErr: nil, - }, - { - name: "OP_DATA_48 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_48], - data: make([]byte, 49), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_49 short", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_49], - data: make([]byte, 48), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_49", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_49], - data: make([]byte, 49), - }, - expectedErr: nil, - }, - { - name: "OP_DATA_49 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_49], - data: make([]byte, 50), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_50 short", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_50], - data: make([]byte, 49), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_50", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_50], - data: make([]byte, 50), - }, - expectedErr: nil, - }, - { - name: "OP_DATA_50 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_50], - data: make([]byte, 51), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_51 short", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_51], - data: make([]byte, 50), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_51", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_51], - data: make([]byte, 51), - }, - expectedErr: nil, - }, - { - name: "OP_DATA_51 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_51], - data: make([]byte, 52), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_52 short", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_52], - data: make([]byte, 51), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_52", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_52], - data: make([]byte, 52), - }, - expectedErr: nil, - }, - { - name: "OP_DATA_52 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_52], - data: make([]byte, 53), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_53 short", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_53], - data: make([]byte, 52), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_53", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_53], - data: make([]byte, 53), - }, - expectedErr: nil, - }, - { - name: "OP_DATA_53 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_53], - data: make([]byte, 54), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_54 short", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_54], - data: make([]byte, 53), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_54", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_54], - data: make([]byte, 54), - }, - expectedErr: nil, - }, - { - name: "OP_DATA_54 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_54], - data: make([]byte, 55), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_55 short", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_55], - data: make([]byte, 54), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_55", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_55], - data: make([]byte, 55), - }, - expectedErr: nil, - }, - { - name: "OP_DATA_55 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_55], - data: make([]byte, 56), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_56 short", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_56], - data: make([]byte, 55), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_56", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_56], - data: make([]byte, 56), - }, - expectedErr: nil, - }, - { - name: "OP_DATA_56 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_56], - data: make([]byte, 57), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_57 short", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_57], - data: make([]byte, 56), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_57", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_57], - data: make([]byte, 57), - }, - expectedErr: nil, - }, - { - name: "OP_DATA_57 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_57], - data: make([]byte, 58), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_58 short", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_58], - data: make([]byte, 57), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_58", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_58], - data: make([]byte, 58), - }, - expectedErr: nil, - }, - { - name: "OP_DATA_58 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_58], - data: make([]byte, 59), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_59 short", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_59], - data: make([]byte, 58), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_59", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_59], - data: make([]byte, 59), - }, - expectedErr: nil, - }, - { - name: "OP_DATA_59 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_59], - data: make([]byte, 60), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_60 short", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_60], - data: make([]byte, 59), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_60", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_60], - data: make([]byte, 60), - }, - expectedErr: nil, - }, - { - name: "OP_DATA_60 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_60], - data: make([]byte, 61), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_61 short", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_61], - data: make([]byte, 60), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_61", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_61], - data: make([]byte, 61), - }, - expectedErr: nil, - }, - { - name: "OP_DATA_61 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_61], - data: make([]byte, 62), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_62 short", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_62], - data: make([]byte, 61), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_62", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_62], - data: make([]byte, 62), - }, - expectedErr: nil, - }, - { - name: "OP_DATA_62 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_62], - data: make([]byte, 63), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_63 short", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_63], - data: make([]byte, 62), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_63", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_63], - data: make([]byte, 63), - }, - expectedErr: nil, - }, - { - name: "OP_DATA_63 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_63], - data: make([]byte, 64), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_64 short", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_64], - data: make([]byte, 63), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_64", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_64], - data: make([]byte, 64), - }, - expectedErr: nil, - }, - { - name: "OP_DATA_64 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_64], - data: make([]byte, 65), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_65 short", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_65], - data: make([]byte, 64), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_65", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_65], - data: make([]byte, 65), - }, - expectedErr: nil, - }, - { - name: "OP_DATA_65 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_65], - data: make([]byte, 66), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_66 short", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_66], - data: make([]byte, 65), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_66", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_66], - data: make([]byte, 66), - }, - expectedErr: nil, - }, - { - name: "OP_DATA_66 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_66], - data: make([]byte, 67), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_67 short", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_67], - data: make([]byte, 66), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_67", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_67], - data: make([]byte, 67), - }, - expectedErr: nil, - }, - { - name: "OP_DATA_67 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_67], - data: make([]byte, 68), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_68 short", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_68], - data: make([]byte, 67), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_68", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_68], - data: make([]byte, 68), - }, - expectedErr: nil, - }, - { - name: "OP_DATA_68 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_68], - data: make([]byte, 69), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_69 short", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_69], - data: make([]byte, 68), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_69", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_69], - data: make([]byte, 69), - }, - expectedErr: nil, - }, - { - name: "OP_DATA_69 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_69], - data: make([]byte, 70), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_70 short", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_70], - data: make([]byte, 69), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_70", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_70], - data: make([]byte, 70), - }, - expectedErr: nil, - }, - { - name: "OP_DATA_70 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_70], - data: make([]byte, 71), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_71 short", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_71], - data: make([]byte, 70), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_71", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_71], - data: make([]byte, 71), - }, - expectedErr: nil, - }, - { - name: "OP_DATA_71 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_71], - data: make([]byte, 72), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_72 short", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_72], - data: make([]byte, 71), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_72", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_72], - data: make([]byte, 72), - }, - expectedErr: nil, - }, - { - name: "OP_DATA_72 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_72], - data: make([]byte, 73), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_73 short", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_73], - data: make([]byte, 72), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_73", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_73], - data: make([]byte, 73), - }, - expectedErr: nil, - }, - { - name: "OP_DATA_73 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_73], - data: make([]byte, 74), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_74 short", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_74], - data: make([]byte, 73), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_74", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_74], - data: make([]byte, 74), - }, - expectedErr: nil, - }, - { - name: "OP_DATA_74 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_74], - data: make([]byte, 75), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_75 short", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_75], - data: make([]byte, 74), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DATA_75", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_75], - data: make([]byte, 75), - }, - expectedErr: nil, - }, - { - name: "OP_DATA_75 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DATA_75], - data: make([]byte, 76), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_PUSHDATA1", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_PUSHDATA1], - data: []byte{0, 1, 2, 3, 4}, - }, - expectedErr: nil, - }, - { - name: "OP_PUSHDATA2", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_PUSHDATA2], - data: []byte{0, 1, 2, 3, 4}, - }, - expectedErr: nil, - }, - { - name: "OP_PUSHDATA4", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_PUSHDATA1], - data: []byte{0, 1, 2, 3, 4}, - }, - expectedErr: nil, - }, - { - name: "OP_1NEGATE", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_1NEGATE], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_1NEGATE long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_1NEGATE], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_RESERVED", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_RESERVED], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_RESERVED long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_RESERVED], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_TRUE", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_TRUE], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_TRUE long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_TRUE], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_2", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_2], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_2 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_2], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_2", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_2], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_2 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_2], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_3", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_3], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_3 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_3], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_4", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_4], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_4 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_4], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_5", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_5], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_5 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_5], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_6", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_6], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_6 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_6], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_7", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_7], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_7 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_7], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_8", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_8], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_8 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_8], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_9", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_9], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_9 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_9], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_10", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_10], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_10 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_10], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_11", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_11], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_11 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_11], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_12", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_12], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_12 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_12], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_13", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_13], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_13 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_13], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_14", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_14], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_14 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_14], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_15", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_15], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_15 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_15], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_16", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_16], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_16 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_16], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_NOP", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_NOP], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_NOP long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_NOP], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_VER", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_VER], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_VER long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_VER], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_IF", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_IF], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_IF long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_IF], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_NOTIF", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_NOTIF], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_NOTIF long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_NOTIF], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_VERIF", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_VERIF], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_VERIF long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_VERIF], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_VERNOTIF", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_VERNOTIF], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_VERNOTIF long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_VERNOTIF], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_ELSE", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_ELSE], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_ELSE long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_ELSE], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_ENDIF", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_ENDIF], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_ENDIF long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_ENDIF], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_VERIFY", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_VERIFY], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_VERIFY long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_VERIFY], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_RETURN", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_RETURN], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_RETURN long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_RETURN], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_TOALTSTACK", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_TOALTSTACK], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_TOALTSTACK long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_TOALTSTACK], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_FROMALTSTACK", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_FROMALTSTACK], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_FROMALTSTACK long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_FROMALTSTACK], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_2DROP", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_2DROP], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_2DROP long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_2DROP], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_2DUP", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_2DUP], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_2DUP long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_2DUP], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_3DUP", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_3DUP], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_3DUP long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_3DUP], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_2OVER", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_2OVER], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_2OVER long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_2OVER], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_2ROT", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_2ROT], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_2ROT long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_2ROT], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_2SWAP", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_2SWAP], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_2SWAP long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_2SWAP], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_IFDUP", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_IFDUP], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_IFDUP long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_IFDUP], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DEPTH", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DEPTH], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_DEPTH long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DEPTH], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DROP", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DROP], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_DROP long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DROP], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DUP", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DUP], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_DUP long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DUP], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_NIP", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_NIP], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_NIP long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_NIP], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_OVER", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_OVER], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_OVER long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_OVER], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_PICK", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_PICK], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_PICK long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_PICK], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_ROLL", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_ROLL], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_ROLL long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_ROLL], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_ROT", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_ROT], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_ROT long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_ROT], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_SWAP", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_SWAP], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_SWAP long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_SWAP], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_TUCK", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_TUCK], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_TUCK long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_TUCK], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_CAT", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_CAT], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_CAT long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_CAT], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_SUBSTR", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_SUBSTR], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_SUBSTR long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_SUBSTR], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_LEFT", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_LEFT], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_LEFT long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_LEFT], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_LEFT", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_LEFT], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_LEFT long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_LEFT], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_RIGHT", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_RIGHT], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_RIGHT long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_RIGHT], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_SIZE", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_SIZE], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_SIZE long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_SIZE], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_INVERT", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_INVERT], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_INVERT long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_INVERT], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_AND", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_AND], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_AND long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_AND], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_OR", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_OR], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_OR long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_OR], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_XOR", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_XOR], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_XOR long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_XOR], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_EQUAL", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_EQUAL], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_EQUAL long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_EQUAL], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_EQUALVERIFY", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_EQUALVERIFY], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_EQUALVERIFY long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_EQUALVERIFY], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_RESERVED1", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_RESERVED1], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_RESERVED1 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_RESERVED1], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_RESERVED2", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_RESERVED2], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_RESERVED2 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_RESERVED2], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_1ADD", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_1ADD], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_1ADD long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_1ADD], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_1SUB", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_1SUB], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_1SUB long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_1SUB], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_2MUL", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_2MUL], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_2MUL long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_2MUL], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_2DIV", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_2DIV], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_2DIV long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_2DIV], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_NEGATE", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_NEGATE], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_NEGATE long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_NEGATE], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_ABS", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_ABS], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_ABS long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_ABS], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_NOT", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_NOT], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_NOT long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_NOT], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_0NOTEQUAL", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_0NOTEQUAL], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_0NOTEQUAL long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_0NOTEQUAL], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_ADD", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_ADD], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_ADD long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_ADD], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_SUB", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_SUB], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_SUB long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_SUB], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_MUL", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_MUL], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_MUL long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_MUL], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_DIV", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DIV], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_DIV long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_DIV], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_MOD", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_MOD], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_MOD long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_MOD], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_LSHIFT", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_LSHIFT], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_LSHIFT long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_LSHIFT], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_RSHIFT", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_RSHIFT], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_RSHIFT long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_RSHIFT], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_BOOLAND", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_BOOLAND], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_BOOLAND long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_BOOLAND], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_BOOLOR", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_BOOLOR], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_BOOLOR long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_BOOLOR], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_NUMEQUAL", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_NUMEQUAL], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_NUMEQUAL long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_NUMEQUAL], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_NUMEQUALVERIFY", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_NUMEQUALVERIFY], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_NUMEQUALVERIFY long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_NUMEQUALVERIFY], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_NUMNOTEQUAL", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_NUMNOTEQUAL], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_NUMNOTEQUAL long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_NUMNOTEQUAL], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_LESSTHAN", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_LESSTHAN], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_LESSTHAN long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_LESSTHAN], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_GREATERTHAN", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_GREATERTHAN], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_GREATERTHAN long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_GREATERTHAN], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_LESSTHANOREQUAL", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_LESSTHANOREQUAL], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_LESSTHANOREQUAL long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_LESSTHANOREQUAL], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_GREATERTHANOREQUAL", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_GREATERTHANOREQUAL], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_GREATERTHANOREQUAL long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_GREATERTHANOREQUAL], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_MIN", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_MIN], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_MIN long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_MIN], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_MAX", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_MAX], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_MAX long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_MAX], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_WITHIN", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_WITHIN], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_WITHIN long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_WITHIN], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_RIPEMD160", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_RIPEMD160], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_RIPEMD160 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_RIPEMD160], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_SHA1", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_SHA1], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_SHA1 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_SHA1], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_SHA256", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_SHA256], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_SHA256 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_SHA256], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_HASH160", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_HASH160], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_HASH160 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_HASH160], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_HASH256", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_HASH256], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_HASH256 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_HASH256], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_CODESAPERATOR", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_CODESEPARATOR], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_CODESEPARATOR long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_CODESEPARATOR], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_CHECKSIG", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_CHECKSIG], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_CHECKSIG long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_CHECKSIG], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_CHECKSIGVERIFY", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_CHECKSIGVERIFY], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_CHECKSIGVERIFY long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_CHECKSIGVERIFY], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_CHECKMULTISIG", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_CHECKMULTISIG], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_CHECKMULTISIG long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_CHECKMULTISIG], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_CHECKMULTISIGVERIFY", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_CHECKMULTISIGVERIFY], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_CHECKMULTISIGVERIFY long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_CHECKMULTISIGVERIFY], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_NOP1", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_NOP1], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_NOP1 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_NOP1], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_NOP2", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_NOP2], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_NOP2 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_NOP2], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_NOP3", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_NOP3], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_NOP3 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_NOP3], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_NOP4", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_NOP4], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_NOP4 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_NOP4], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_NOP5", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_NOP5], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_NOP5 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_NOP5], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_NOP6", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_NOP6], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_NOP6 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_NOP6], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_NOP7", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_NOP7], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_NOP7 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_NOP7], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_NOP8", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_NOP8], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_NOP8 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_NOP8], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_NOP9", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_NOP9], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_NOP9 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_NOP9], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_NOP10", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_NOP10], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_NOP10 long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_NOP10], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_PUBKEYHASH", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_PUBKEYHASH], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_PUBKEYHASH long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_PUBKEYHASH], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_PUBKEY", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_PUBKEY], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_PUBKEY long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_PUBKEY], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, - { - name: "OP_INVALIDOPCODE", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_INVALIDOPCODE], - data: nil, - }, - expectedErr: nil, - }, - { - name: "OP_INVALIDOPCODE long", - pop: &parsedOpcode{ - opcode: &opcodeArray[OP_INVALIDOPCODE], - data: make([]byte, 1), - }, - expectedErr: ErrStackInvalidOpcode, - }, -} - func TestUnparsingInvalidOpcodes(t *testing.T) { - for _, test := range popTests { + tests := []struct { + name string + pop *parsedOpcode + expectedErr error + }{ + { + name: "OP_FALSE", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_FALSE], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_FALSE long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_FALSE], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_1 short", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_1], + data: nil, + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_1", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_1], + data: make([]byte, 1), + }, + expectedErr: nil, + }, + { + name: "OP_DATA_1 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_1], + data: make([]byte, 2), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_2 short", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_2], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_2", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_2], + data: make([]byte, 2), + }, + expectedErr: nil, + }, + { + name: "OP_DATA_2 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_2], + data: make([]byte, 3), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_3 short", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_3], + data: make([]byte, 2), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_3", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_3], + data: make([]byte, 3), + }, + expectedErr: nil, + }, + { + name: "OP_DATA_3 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_3], + data: make([]byte, 4), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_4 short", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_4], + data: make([]byte, 3), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_4", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_4], + data: make([]byte, 4), + }, + expectedErr: nil, + }, + { + name: "OP_DATA_4 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_4], + data: make([]byte, 5), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_5 short", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_5], + data: make([]byte, 4), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_5", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_5], + data: make([]byte, 5), + }, + expectedErr: nil, + }, + { + name: "OP_DATA_5 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_5], + data: make([]byte, 6), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_6 short", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_6], + data: make([]byte, 5), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_6", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_6], + data: make([]byte, 6), + }, + expectedErr: nil, + }, + { + name: "OP_DATA_6 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_6], + data: make([]byte, 7), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_7 short", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_7], + data: make([]byte, 6), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_7", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_7], + data: make([]byte, 7), + }, + expectedErr: nil, + }, + { + name: "OP_DATA_7 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_7], + data: make([]byte, 8), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_8 short", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_8], + data: make([]byte, 7), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_8", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_8], + data: make([]byte, 8), + }, + expectedErr: nil, + }, + { + name: "OP_DATA_8 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_8], + data: make([]byte, 9), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_9 short", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_9], + data: make([]byte, 8), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_9", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_9], + data: make([]byte, 9), + }, + expectedErr: nil, + }, + { + name: "OP_DATA_9 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_9], + data: make([]byte, 10), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_10 short", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_10], + data: make([]byte, 9), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_10", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_10], + data: make([]byte, 10), + }, + expectedErr: nil, + }, + { + name: "OP_DATA_10 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_10], + data: make([]byte, 11), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_11 short", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_11], + data: make([]byte, 10), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_11", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_11], + data: make([]byte, 11), + }, + expectedErr: nil, + }, + { + name: "OP_DATA_11 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_11], + data: make([]byte, 12), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_12 short", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_12], + data: make([]byte, 11), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_12", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_12], + data: make([]byte, 12), + }, + expectedErr: nil, + }, + { + name: "OP_DATA_12 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_12], + data: make([]byte, 13), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_13 short", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_13], + data: make([]byte, 12), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_13", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_13], + data: make([]byte, 13), + }, + expectedErr: nil, + }, + { + name: "OP_DATA_13 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_13], + data: make([]byte, 14), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_14 short", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_14], + data: make([]byte, 13), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_14", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_14], + data: make([]byte, 14), + }, + expectedErr: nil, + }, + { + name: "OP_DATA_14 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_14], + data: make([]byte, 15), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_15 short", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_15], + data: make([]byte, 14), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_15", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_15], + data: make([]byte, 15), + }, + expectedErr: nil, + }, + { + name: "OP_DATA_15 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_15], + data: make([]byte, 16), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_16 short", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_16], + data: make([]byte, 15), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_16", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_16], + data: make([]byte, 16), + }, + expectedErr: nil, + }, + { + name: "OP_DATA_16 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_16], + data: make([]byte, 17), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_17 short", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_17], + data: make([]byte, 16), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_17", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_17], + data: make([]byte, 17), + }, + expectedErr: nil, + }, + { + name: "OP_DATA_17 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_17], + data: make([]byte, 18), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_18 short", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_18], + data: make([]byte, 17), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_18", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_18], + data: make([]byte, 18), + }, + expectedErr: nil, + }, + { + name: "OP_DATA_18 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_18], + data: make([]byte, 19), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_19 short", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_19], + data: make([]byte, 18), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_19", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_19], + data: make([]byte, 19), + }, + expectedErr: nil, + }, + { + name: "OP_DATA_19 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_19], + data: make([]byte, 20), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_20 short", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_20], + data: make([]byte, 19), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_20", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_20], + data: make([]byte, 20), + }, + expectedErr: nil, + }, + { + name: "OP_DATA_20 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_20], + data: make([]byte, 21), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_21 short", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_21], + data: make([]byte, 20), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_21", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_21], + data: make([]byte, 21), + }, + expectedErr: nil, + }, + { + name: "OP_DATA_21 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_21], + data: make([]byte, 22), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_22 short", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_22], + data: make([]byte, 21), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_22", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_22], + data: make([]byte, 22), + }, + expectedErr: nil, + }, + { + name: "OP_DATA_22 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_22], + data: make([]byte, 23), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_23 short", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_23], + data: make([]byte, 22), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_23", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_23], + data: make([]byte, 23), + }, + expectedErr: nil, + }, + { + name: "OP_DATA_23 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_23], + data: make([]byte, 24), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_24 short", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_24], + data: make([]byte, 23), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_24", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_24], + data: make([]byte, 24), + }, + expectedErr: nil, + }, + { + name: "OP_DATA_24 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_24], + data: make([]byte, 25), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_25 short", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_25], + data: make([]byte, 24), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_25", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_25], + data: make([]byte, 25), + }, + expectedErr: nil, + }, + { + name: "OP_DATA_25 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_25], + data: make([]byte, 26), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_26 short", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_26], + data: make([]byte, 25), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_26", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_26], + data: make([]byte, 26), + }, + expectedErr: nil, + }, + { + name: "OP_DATA_26 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_26], + data: make([]byte, 27), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_27 short", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_27], + data: make([]byte, 26), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_27", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_27], + data: make([]byte, 27), + }, + expectedErr: nil, + }, + { + name: "OP_DATA_27 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_27], + data: make([]byte, 28), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_28 short", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_28], + data: make([]byte, 27), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_28", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_28], + data: make([]byte, 28), + }, + expectedErr: nil, + }, + { + name: "OP_DATA_28 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_28], + data: make([]byte, 29), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_29 short", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_29], + data: make([]byte, 28), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_29", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_29], + data: make([]byte, 29), + }, + expectedErr: nil, + }, + { + name: "OP_DATA_29 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_29], + data: make([]byte, 30), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_30 short", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_30], + data: make([]byte, 29), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_30", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_30], + data: make([]byte, 30), + }, + expectedErr: nil, + }, + { + name: "OP_DATA_30 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_30], + data: make([]byte, 31), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_31 short", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_31], + data: make([]byte, 30), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_31", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_31], + data: make([]byte, 31), + }, + expectedErr: nil, + }, + { + name: "OP_DATA_31 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_31], + data: make([]byte, 32), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_32 short", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_32], + data: make([]byte, 31), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_32", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_32], + data: make([]byte, 32), + }, + expectedErr: nil, + }, + { + name: "OP_DATA_32 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_32], + data: make([]byte, 33), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_33 short", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_33], + data: make([]byte, 32), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_33", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_33], + data: make([]byte, 33), + }, + expectedErr: nil, + }, + { + name: "OP_DATA_33 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_33], + data: make([]byte, 34), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_34 short", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_34], + data: make([]byte, 33), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_34", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_34], + data: make([]byte, 34), + }, + expectedErr: nil, + }, + { + name: "OP_DATA_34 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_34], + data: make([]byte, 35), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_35 short", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_35], + data: make([]byte, 34), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_35", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_35], + data: make([]byte, 35), + }, + expectedErr: nil, + }, + { + name: "OP_DATA_35 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_35], + data: make([]byte, 36), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_36 short", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_36], + data: make([]byte, 35), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_36", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_36], + data: make([]byte, 36), + }, + expectedErr: nil, + }, + { + name: "OP_DATA_36 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_36], + data: make([]byte, 37), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_37 short", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_37], + data: make([]byte, 36), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_37", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_37], + data: make([]byte, 37), + }, + expectedErr: nil, + }, + { + name: "OP_DATA_37 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_37], + data: make([]byte, 38), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_38 short", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_38], + data: make([]byte, 37), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_38", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_38], + data: make([]byte, 38), + }, + expectedErr: nil, + }, + { + name: "OP_DATA_38 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_38], + data: make([]byte, 39), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_39 short", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_39], + data: make([]byte, 38), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_39", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_39], + data: make([]byte, 39), + }, + expectedErr: nil, + }, + { + name: "OP_DATA_39 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_39], + data: make([]byte, 40), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_40 short", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_40], + data: make([]byte, 39), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_40", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_40], + data: make([]byte, 40), + }, + expectedErr: nil, + }, + { + name: "OP_DATA_40 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_40], + data: make([]byte, 41), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_41 short", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_41], + data: make([]byte, 40), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_41", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_41], + data: make([]byte, 41), + }, + expectedErr: nil, + }, + { + name: "OP_DATA_41 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_41], + data: make([]byte, 42), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_42 short", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_42], + data: make([]byte, 41), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_42", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_42], + data: make([]byte, 42), + }, + expectedErr: nil, + }, + { + name: "OP_DATA_42 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_42], + data: make([]byte, 43), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_43 short", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_43], + data: make([]byte, 42), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_43", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_43], + data: make([]byte, 43), + }, + expectedErr: nil, + }, + { + name: "OP_DATA_43 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_43], + data: make([]byte, 44), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_44 short", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_44], + data: make([]byte, 43), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_44", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_44], + data: make([]byte, 44), + }, + expectedErr: nil, + }, + { + name: "OP_DATA_44 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_44], + data: make([]byte, 45), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_45 short", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_45], + data: make([]byte, 44), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_45", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_45], + data: make([]byte, 45), + }, + expectedErr: nil, + }, + { + name: "OP_DATA_45 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_45], + data: make([]byte, 46), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_46 short", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_46], + data: make([]byte, 45), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_46", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_46], + data: make([]byte, 46), + }, + expectedErr: nil, + }, + { + name: "OP_DATA_46 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_46], + data: make([]byte, 47), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_47 short", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_47], + data: make([]byte, 46), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_47", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_47], + data: make([]byte, 47), + }, + expectedErr: nil, + }, + { + name: "OP_DATA_47 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_47], + data: make([]byte, 48), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_48 short", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_48], + data: make([]byte, 47), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_48", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_48], + data: make([]byte, 48), + }, + expectedErr: nil, + }, + { + name: "OP_DATA_48 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_48], + data: make([]byte, 49), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_49 short", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_49], + data: make([]byte, 48), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_49", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_49], + data: make([]byte, 49), + }, + expectedErr: nil, + }, + { + name: "OP_DATA_49 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_49], + data: make([]byte, 50), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_50 short", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_50], + data: make([]byte, 49), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_50", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_50], + data: make([]byte, 50), + }, + expectedErr: nil, + }, + { + name: "OP_DATA_50 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_50], + data: make([]byte, 51), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_51 short", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_51], + data: make([]byte, 50), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_51", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_51], + data: make([]byte, 51), + }, + expectedErr: nil, + }, + { + name: "OP_DATA_51 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_51], + data: make([]byte, 52), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_52 short", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_52], + data: make([]byte, 51), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_52", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_52], + data: make([]byte, 52), + }, + expectedErr: nil, + }, + { + name: "OP_DATA_52 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_52], + data: make([]byte, 53), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_53 short", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_53], + data: make([]byte, 52), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_53", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_53], + data: make([]byte, 53), + }, + expectedErr: nil, + }, + { + name: "OP_DATA_53 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_53], + data: make([]byte, 54), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_54 short", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_54], + data: make([]byte, 53), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_54", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_54], + data: make([]byte, 54), + }, + expectedErr: nil, + }, + { + name: "OP_DATA_54 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_54], + data: make([]byte, 55), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_55 short", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_55], + data: make([]byte, 54), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_55", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_55], + data: make([]byte, 55), + }, + expectedErr: nil, + }, + { + name: "OP_DATA_55 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_55], + data: make([]byte, 56), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_56 short", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_56], + data: make([]byte, 55), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_56", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_56], + data: make([]byte, 56), + }, + expectedErr: nil, + }, + { + name: "OP_DATA_56 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_56], + data: make([]byte, 57), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_57 short", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_57], + data: make([]byte, 56), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_57", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_57], + data: make([]byte, 57), + }, + expectedErr: nil, + }, + { + name: "OP_DATA_57 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_57], + data: make([]byte, 58), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_58 short", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_58], + data: make([]byte, 57), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_58", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_58], + data: make([]byte, 58), + }, + expectedErr: nil, + }, + { + name: "OP_DATA_58 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_58], + data: make([]byte, 59), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_59 short", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_59], + data: make([]byte, 58), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_59", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_59], + data: make([]byte, 59), + }, + expectedErr: nil, + }, + { + name: "OP_DATA_59 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_59], + data: make([]byte, 60), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_60 short", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_60], + data: make([]byte, 59), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_60", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_60], + data: make([]byte, 60), + }, + expectedErr: nil, + }, + { + name: "OP_DATA_60 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_60], + data: make([]byte, 61), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_61 short", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_61], + data: make([]byte, 60), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_61", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_61], + data: make([]byte, 61), + }, + expectedErr: nil, + }, + { + name: "OP_DATA_61 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_61], + data: make([]byte, 62), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_62 short", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_62], + data: make([]byte, 61), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_62", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_62], + data: make([]byte, 62), + }, + expectedErr: nil, + }, + { + name: "OP_DATA_62 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_62], + data: make([]byte, 63), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_63 short", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_63], + data: make([]byte, 62), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_63", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_63], + data: make([]byte, 63), + }, + expectedErr: nil, + }, + { + name: "OP_DATA_63 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_63], + data: make([]byte, 64), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_64 short", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_64], + data: make([]byte, 63), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_64", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_64], + data: make([]byte, 64), + }, + expectedErr: nil, + }, + { + name: "OP_DATA_64 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_64], + data: make([]byte, 65), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_65 short", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_65], + data: make([]byte, 64), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_65", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_65], + data: make([]byte, 65), + }, + expectedErr: nil, + }, + { + name: "OP_DATA_65 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_65], + data: make([]byte, 66), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_66 short", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_66], + data: make([]byte, 65), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_66", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_66], + data: make([]byte, 66), + }, + expectedErr: nil, + }, + { + name: "OP_DATA_66 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_66], + data: make([]byte, 67), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_67 short", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_67], + data: make([]byte, 66), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_67", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_67], + data: make([]byte, 67), + }, + expectedErr: nil, + }, + { + name: "OP_DATA_67 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_67], + data: make([]byte, 68), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_68 short", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_68], + data: make([]byte, 67), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_68", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_68], + data: make([]byte, 68), + }, + expectedErr: nil, + }, + { + name: "OP_DATA_68 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_68], + data: make([]byte, 69), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_69 short", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_69], + data: make([]byte, 68), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_69", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_69], + data: make([]byte, 69), + }, + expectedErr: nil, + }, + { + name: "OP_DATA_69 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_69], + data: make([]byte, 70), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_70 short", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_70], + data: make([]byte, 69), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_70", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_70], + data: make([]byte, 70), + }, + expectedErr: nil, + }, + { + name: "OP_DATA_70 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_70], + data: make([]byte, 71), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_71 short", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_71], + data: make([]byte, 70), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_71", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_71], + data: make([]byte, 71), + }, + expectedErr: nil, + }, + { + name: "OP_DATA_71 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_71], + data: make([]byte, 72), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_72 short", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_72], + data: make([]byte, 71), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_72", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_72], + data: make([]byte, 72), + }, + expectedErr: nil, + }, + { + name: "OP_DATA_72 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_72], + data: make([]byte, 73), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_73 short", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_73], + data: make([]byte, 72), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_73", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_73], + data: make([]byte, 73), + }, + expectedErr: nil, + }, + { + name: "OP_DATA_73 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_73], + data: make([]byte, 74), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_74 short", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_74], + data: make([]byte, 73), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_74", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_74], + data: make([]byte, 74), + }, + expectedErr: nil, + }, + { + name: "OP_DATA_74 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_74], + data: make([]byte, 75), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_75 short", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_75], + data: make([]byte, 74), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DATA_75", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_75], + data: make([]byte, 75), + }, + expectedErr: nil, + }, + { + name: "OP_DATA_75 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DATA_75], + data: make([]byte, 76), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_PUSHDATA1", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_PUSHDATA1], + data: []byte{0, 1, 2, 3, 4}, + }, + expectedErr: nil, + }, + { + name: "OP_PUSHDATA2", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_PUSHDATA2], + data: []byte{0, 1, 2, 3, 4}, + }, + expectedErr: nil, + }, + { + name: "OP_PUSHDATA4", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_PUSHDATA1], + data: []byte{0, 1, 2, 3, 4}, + }, + expectedErr: nil, + }, + { + name: "OP_1NEGATE", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_1NEGATE], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_1NEGATE long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_1NEGATE], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_RESERVED", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_RESERVED], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_RESERVED long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_RESERVED], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_TRUE", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_TRUE], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_TRUE long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_TRUE], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_2", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_2], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_2 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_2], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_2", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_2], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_2 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_2], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_3", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_3], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_3 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_3], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_4", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_4], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_4 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_4], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_5", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_5], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_5 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_5], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_6", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_6], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_6 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_6], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_7", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_7], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_7 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_7], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_8", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_8], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_8 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_8], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_9", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_9], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_9 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_9], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_10", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_10], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_10 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_10], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_11", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_11], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_11 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_11], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_12", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_12], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_12 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_12], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_13", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_13], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_13 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_13], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_14", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_14], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_14 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_14], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_15", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_15], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_15 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_15], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_16", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_16], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_16 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_16], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_NOP", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_NOP], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_NOP long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_NOP], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_VER", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_VER], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_VER long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_VER], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_IF", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_IF], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_IF long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_IF], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_NOTIF", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_NOTIF], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_NOTIF long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_NOTIF], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_VERIF", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_VERIF], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_VERIF long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_VERIF], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_VERNOTIF", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_VERNOTIF], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_VERNOTIF long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_VERNOTIF], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_ELSE", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_ELSE], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_ELSE long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_ELSE], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_ENDIF", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_ENDIF], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_ENDIF long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_ENDIF], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_VERIFY", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_VERIFY], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_VERIFY long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_VERIFY], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_RETURN", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_RETURN], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_RETURN long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_RETURN], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_TOALTSTACK", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_TOALTSTACK], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_TOALTSTACK long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_TOALTSTACK], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_FROMALTSTACK", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_FROMALTSTACK], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_FROMALTSTACK long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_FROMALTSTACK], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_2DROP", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_2DROP], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_2DROP long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_2DROP], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_2DUP", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_2DUP], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_2DUP long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_2DUP], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_3DUP", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_3DUP], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_3DUP long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_3DUP], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_2OVER", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_2OVER], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_2OVER long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_2OVER], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_2ROT", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_2ROT], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_2ROT long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_2ROT], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_2SWAP", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_2SWAP], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_2SWAP long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_2SWAP], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_IFDUP", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_IFDUP], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_IFDUP long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_IFDUP], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DEPTH", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DEPTH], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_DEPTH long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DEPTH], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DROP", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DROP], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_DROP long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DROP], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DUP", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DUP], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_DUP long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DUP], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_NIP", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_NIP], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_NIP long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_NIP], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_OVER", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_OVER], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_OVER long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_OVER], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_PICK", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_PICK], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_PICK long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_PICK], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_ROLL", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_ROLL], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_ROLL long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_ROLL], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_ROT", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_ROT], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_ROT long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_ROT], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_SWAP", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_SWAP], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_SWAP long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_SWAP], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_TUCK", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_TUCK], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_TUCK long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_TUCK], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_CAT", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_CAT], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_CAT long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_CAT], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_SUBSTR", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_SUBSTR], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_SUBSTR long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_SUBSTR], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_LEFT", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_LEFT], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_LEFT long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_LEFT], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_LEFT", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_LEFT], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_LEFT long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_LEFT], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_RIGHT", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_RIGHT], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_RIGHT long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_RIGHT], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_SIZE", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_SIZE], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_SIZE long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_SIZE], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_INVERT", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_INVERT], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_INVERT long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_INVERT], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_AND", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_AND], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_AND long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_AND], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_OR", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_OR], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_OR long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_OR], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_XOR", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_XOR], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_XOR long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_XOR], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_EQUAL", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_EQUAL], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_EQUAL long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_EQUAL], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_EQUALVERIFY", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_EQUALVERIFY], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_EQUALVERIFY long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_EQUALVERIFY], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_RESERVED1", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_RESERVED1], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_RESERVED1 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_RESERVED1], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_RESERVED2", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_RESERVED2], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_RESERVED2 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_RESERVED2], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_1ADD", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_1ADD], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_1ADD long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_1ADD], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_1SUB", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_1SUB], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_1SUB long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_1SUB], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_2MUL", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_2MUL], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_2MUL long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_2MUL], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_2DIV", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_2DIV], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_2DIV long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_2DIV], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_NEGATE", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_NEGATE], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_NEGATE long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_NEGATE], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_ABS", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_ABS], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_ABS long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_ABS], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_NOT", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_NOT], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_NOT long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_NOT], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_0NOTEQUAL", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_0NOTEQUAL], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_0NOTEQUAL long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_0NOTEQUAL], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_ADD", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_ADD], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_ADD long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_ADD], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_SUB", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_SUB], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_SUB long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_SUB], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_MUL", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_MUL], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_MUL long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_MUL], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_DIV", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DIV], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_DIV long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_DIV], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_MOD", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_MOD], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_MOD long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_MOD], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_LSHIFT", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_LSHIFT], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_LSHIFT long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_LSHIFT], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_RSHIFT", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_RSHIFT], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_RSHIFT long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_RSHIFT], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_BOOLAND", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_BOOLAND], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_BOOLAND long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_BOOLAND], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_BOOLOR", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_BOOLOR], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_BOOLOR long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_BOOLOR], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_NUMEQUAL", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_NUMEQUAL], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_NUMEQUAL long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_NUMEQUAL], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_NUMEQUALVERIFY", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_NUMEQUALVERIFY], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_NUMEQUALVERIFY long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_NUMEQUALVERIFY], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_NUMNOTEQUAL", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_NUMNOTEQUAL], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_NUMNOTEQUAL long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_NUMNOTEQUAL], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_LESSTHAN", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_LESSTHAN], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_LESSTHAN long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_LESSTHAN], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_GREATERTHAN", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_GREATERTHAN], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_GREATERTHAN long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_GREATERTHAN], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_LESSTHANOREQUAL", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_LESSTHANOREQUAL], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_LESSTHANOREQUAL long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_LESSTHANOREQUAL], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_GREATERTHANOREQUAL", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_GREATERTHANOREQUAL], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_GREATERTHANOREQUAL long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_GREATERTHANOREQUAL], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_MIN", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_MIN], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_MIN long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_MIN], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_MAX", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_MAX], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_MAX long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_MAX], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_WITHIN", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_WITHIN], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_WITHIN long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_WITHIN], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_RIPEMD160", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_RIPEMD160], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_RIPEMD160 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_RIPEMD160], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_SHA1", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_SHA1], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_SHA1 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_SHA1], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_SHA256", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_SHA256], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_SHA256 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_SHA256], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_HASH160", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_HASH160], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_HASH160 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_HASH160], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_HASH256", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_HASH256], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_HASH256 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_HASH256], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_CODESAPERATOR", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_CODESEPARATOR], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_CODESEPARATOR long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_CODESEPARATOR], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_CHECKSIG", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_CHECKSIG], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_CHECKSIG long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_CHECKSIG], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_CHECKSIGVERIFY", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_CHECKSIGVERIFY], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_CHECKSIGVERIFY long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_CHECKSIGVERIFY], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_CHECKMULTISIG", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_CHECKMULTISIG], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_CHECKMULTISIG long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_CHECKMULTISIG], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_CHECKMULTISIGVERIFY", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_CHECKMULTISIGVERIFY], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_CHECKMULTISIGVERIFY long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_CHECKMULTISIGVERIFY], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_NOP1", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_NOP1], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_NOP1 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_NOP1], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_NOP2", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_NOP2], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_NOP2 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_NOP2], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_NOP3", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_NOP3], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_NOP3 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_NOP3], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_NOP4", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_NOP4], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_NOP4 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_NOP4], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_NOP5", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_NOP5], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_NOP5 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_NOP5], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_NOP6", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_NOP6], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_NOP6 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_NOP6], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_NOP7", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_NOP7], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_NOP7 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_NOP7], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_NOP8", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_NOP8], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_NOP8 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_NOP8], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_NOP9", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_NOP9], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_NOP9 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_NOP9], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_NOP10", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_NOP10], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_NOP10 long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_NOP10], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_PUBKEYHASH", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_PUBKEYHASH], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_PUBKEYHASH long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_PUBKEYHASH], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_PUBKEY", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_PUBKEY], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_PUBKEY long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_PUBKEY], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + { + name: "OP_INVALIDOPCODE", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_INVALIDOPCODE], + data: nil, + }, + expectedErr: nil, + }, + { + name: "OP_INVALIDOPCODE long", + pop: &parsedOpcode{ + opcode: &opcodeArray[OP_INVALIDOPCODE], + data: make([]byte, 1), + }, + expectedErr: ErrStackInvalidOpcode, + }, + } + + for _, test := range tests { _, err := test.pop.bytes() if err != test.expectedErr { t.Errorf("Parsed Opcode test '%s' failed", test.name) diff --git a/txscript/reference_test.go b/txscript/reference_test.go index eeb73bbe..50d5531a 100644 --- a/txscript/reference_test.go +++ b/txscript/reference_test.go @@ -2,7 +2,7 @@ // Use of this source code is governed by an ISC // license that can be found in the LICENSE file. -package txscript +package txscript_test import ( "encoding/hex" @@ -14,6 +14,7 @@ import ( "strings" "testing" + . "github.com/btcsuite/btcd/txscript" "github.com/btcsuite/btcd/wire" "github.com/btcsuite/btcutil" ) @@ -43,30 +44,46 @@ func parseHex(tok string) ([]byte, error) { return hex.DecodeString(tok[2:]) } +// shortFormOps holds a map of opcode names to values for use in short form +// parsing. It is declared here so it only needs to be created once. +var shortFormOps map[string]byte + // parseShortForm parses a string as as used in the Bitcoin Core reference tests // into the script it came from. +// +// The format used for these tests is pretty simple if ad-hoc: +// - Opcodes other than the push opcodes and unknown are present as +// either OP_NAME or just NAME +// - Plain numbers are made into push operations +// - Numbers beginning with 0x are inserted into the []byte as-is (so +// 0x14 is OP_DATA_20) +// - Single quoted strings are pushed as data +// - Anything else is an error func parseShortForm(script string) ([]byte, error) { - ops := make(map[string]byte) + // Only create the short form opcode map once. + if shortFormOps == nil { + ops := make(map[string]byte) + for opcodeName, opcodeValue := range OpcodeByName { + if strings.Contains(opcodeName, "OP_UNKNOWN") { + continue + } + ops[opcodeName] = opcodeValue - // the format used for these tests is pretty simple if ad-hoc: - // - opcodes other than the push opcodes and unknown are present as - // either OP_NAME or just NAME - // - plain numbers are made into push operations - // - numbers beginning with 0x are inserted into the []byte as-is (so - // 0x14 is OP_DATA_20) - // - single quoted strings are pushed as data. - // - anything else is an error. - for opcodeName, opcodeValue := range OpcodeByName { - if opcodeValue < OP_NOP && opcodeValue != OP_RESERVED { - continue + // The opcodes named OP_# can't have the OP_ prefix + // stripped or they would conflict with the plain + // numbers. Also, since OP_FALSE and OP_TRUE are + // aliases for the OP_0, and OP_1, respectively, they + // have the same value, so detect those by name and + // allow them. + if (opcodeName == "OP_FALSE" || opcodeName == "OP_TRUE") || + (opcodeValue != OP_0 && (opcodeValue < OP_1 || + opcodeValue > OP_16)) { + + ops[strings.TrimPrefix(opcodeName, "OP_")] = opcodeValue + } } - if strings.Contains(opcodeName, "OP_UNKNOWN") { - continue - } - ops[opcodeName] = opcodeValue - ops[strings.TrimPrefix(opcodeName, "OP_")] = opcodeValue + shortFormOps = ops } - // do once, build map. // Split only does one separator so convert all \n and tab into space. script = strings.Replace(script, "\n", " ", -1) @@ -83,12 +100,11 @@ func parseShortForm(script string) ([]byte, error) { builder.AddInt64(num) continue } else if bts, err := parseHex(tok); err == nil { - // naughty... - builder.script = append(builder.script, bts...) + builder.TstConcatRawScript(bts) } else if len(tok) >= 2 && tok[0] == '\'' && tok[len(tok)-1] == '\'' { builder.AddFullData([]byte(tok[1 : len(tok)-1])) - } else if opcode, ok := ops[tok]; ok { + } else if opcode, ok := shortFormOps[tok]; ok { builder.AddOp(opcode) } else { return nil, fmt.Errorf("bad token \"%s\"", tok) diff --git a/txscript/script_test.go b/txscript/script_test.go index b90a49de..21b88af7 100644 --- a/txscript/script_test.go +++ b/txscript/script_test.go @@ -6,39 +6,29 @@ package txscript_test import ( "bytes" + "reflect" "testing" "github.com/btcsuite/btcd/txscript" - "github.com/btcsuite/btcd/wire" ) -// builderScript is a convenience function which is used in the tests. It -// allows access to the script from a known good script built with the builder. -// Any errors are converted to a panic since it is only, and must only, be used -// with hard coded, and therefore, known good, scripts. -func builderScript(builder *txscript.ScriptBuilder) []byte { - script, err := builder.Script() - if err != nil { - panic(err) - } - return script -} - +// TestPushedData ensured the PushedData function extracts the expected data out +// of various scripts. func TestPushedData(t *testing.T) { t.Parallel() var tests = []struct { - in []byte - out [][]byte - valid bool + script string + out [][]byte + valid bool }{ { - []byte{txscript.OP_0, txscript.OP_IF, txscript.OP_0, txscript.OP_ELSE, txscript.OP_2, txscript.OP_ENDIF}, - [][]byte{{}, {}}, + "0 IF 0 ELSE 2 ENDIF", + [][]byte{nil, nil}, true, }, { - builderScript(txscript.NewScriptBuilder().AddInt64(16777216).AddInt64(10000000)), + "16777216 10000000", [][]byte{ {0x00, 0x00, 0x00, 0x01}, // 16777216 {0x80, 0x96, 0x98, 0x00}, // 10000000 @@ -46,9 +36,7 @@ func TestPushedData(t *testing.T) { true, }, { - builderScript(txscript.NewScriptBuilder().AddOp(txscript.OP_DUP).AddOp(txscript.OP_HASH160). - AddData([]byte("17VZNX1SN5NtKa8UQFxwQbFeFc3iqRYhem")).AddOp(txscript.OP_EQUALVERIFY). - AddOp(txscript.OP_CHECKSIG)), + "DUP HASH160 '17VZNX1SN5NtKa8UQFxwQbFeFc3iqRYhem' EQUALVERIFY CHECKSIG", [][]byte{ // 17VZNX1SN5NtKa8UQFxwQbFeFc3iqRYhem { @@ -61,32 +49,32 @@ func TestPushedData(t *testing.T) { true, }, { - builderScript(txscript.NewScriptBuilder().AddOp(txscript.OP_PUSHDATA4).AddInt64(1000). - AddOp(txscript.OP_EQUAL)), - [][]byte{}, + "PUSHDATA4 1000 EQUAL", + nil, false, }, } - for x, test := range tests { - pushedData, err := txscript.PushedData(test.in) + for i, test := range tests { + script := mustParseShortForm(test.script) + data, err := txscript.PushedData(script) if test.valid && err != nil { - t.Errorf("TestPushedData failed test #%d: %v\n", x, err) + t.Errorf("TestPushedData failed test #%d: %v\n", i, err) continue } else if !test.valid && err == nil { - t.Errorf("TestPushedData failed test #%d: test should be invalid\n", x) + t.Errorf("TestPushedData failed test #%d: test should "+ + "be invalid\n", i) continue } - for x, data := range pushedData { - if !bytes.Equal(data, test.out[x]) { - t.Errorf("TestPushedData failed test #%d: want: %x got: %x\n", - x, test.out[x], data) - } + if !reflect.DeepEqual(data, test.out) { + t.Errorf("TestPushedData failed test #%d: want: %x "+ + "got: %x\n", i, test.out, data) } } } -func TestStandardPushes(t *testing.T) { +// TestHasCanonicalPush ensures the canonicalPush function works as expected. +func TestHasCanonicalPush(t *testing.T) { t.Parallel() for i := 0; i < 65535; i++ { @@ -94,21 +82,24 @@ func TestStandardPushes(t *testing.T) { builder.AddInt64(int64(i)) script, err := builder.Script() if err != nil { - t.Errorf("StandardPushesTests test #%d unexpected error: %v\n", i, err) + t.Errorf("Script: test #%d unexpected error: %v\n", i, + err) continue } if result := txscript.IsPushOnlyScript(script); !result { - t.Errorf("StandardPushesTests IsPushOnlyScript test #%d failed: %x\n", i, script) + t.Errorf("IsPushOnlyScript: test #%d failed: %x\n", i, + script) continue } pops, err := txscript.TstParseScript(script) if err != nil { - t.Errorf("StandardPushesTests #%d failed to TstParseScript: %v", i, err) + t.Errorf("TstParseScript: #%d failed: %v", i, err) continue } for _, pop := range pops { if result := txscript.TstHasCanonicalPushes(pop); !result { - t.Errorf("StandardPushesTests TstHasCanonicalPushes test #%d failed: %x\n", i, script) + t.Errorf("TstHasCanonicalPushes: test #%d "+ + "failed: %x\n", i, script) break } } @@ -139,1564 +130,17 @@ func TestStandardPushes(t *testing.T) { } } -type txTest struct { - name string - tx *wire.MsgTx - pkScript []byte // output script of previous tx - idx int // tx idx to be run. - bip16 bool // is bip16 active? - strictSigs bool // should signatures be validated as strict? - parseErr error // failure of NewScript - err error // Failure of Executre - shouldFail bool // Execute should fail with nonspecified error. - nSigOps int // result of GetPreciseSigOpsCount - scriptInfo txscript.ScriptInfo // result of ScriptInfo - scriptInfoErr error // error return of ScriptInfo -} - -var txTests = []txTest{ - // tx 0437cd7f8525ceed2324359c2d0ba26006d92d85. the first tx in the - // blockchain that verifies signatures. - { - name: "CheckSig", - tx: &wire.MsgTx{ - Version: 1, - TxIn: []*wire.TxIn{ - { - PreviousOutPoint: wire.OutPoint{ - Hash: wire.ShaHash([32]byte{ - 0xc9, 0x97, 0xa5, 0xe5, - 0x6e, 0x10, 0x41, 0x02, - 0xfa, 0x20, 0x9c, 0x6a, - 0x85, 0x2d, 0xd9, 0x06, - 0x60, 0xa2, 0x0b, 0x2d, - 0x9c, 0x35, 0x24, 0x23, - 0xed, 0xce, 0x25, 0x85, - 0x7f, 0xcd, 0x37, 0x04, - }), - Index: 0, - }, - SignatureScript: []uint8{ - txscript.OP_DATA_71, - 0x30, 0x44, 0x02, 0x20, 0x4e, - 0x45, 0xe1, 0x69, 0x32, 0xb8, - 0xaf, 0x51, 0x49, 0x61, 0xa1, - 0xd3, 0xa1, 0xa2, 0x5f, 0xdf, - 0x3f, 0x4f, 0x77, 0x32, 0xe9, - 0xd6, 0x24, 0xc6, 0xc6, 0x15, - 0x48, 0xab, 0x5f, 0xb8, 0xcd, - 0x41, 0x02, 0x20, 0x18, 0x15, - 0x22, 0xec, 0x8e, 0xca, 0x07, - 0xde, 0x48, 0x60, 0xa4, 0xac, - 0xdd, 0x12, 0x90, 0x9d, 0x83, - 0x1c, 0xc5, 0x6c, 0xbb, 0xac, - 0x46, 0x22, 0x08, 0x22, 0x21, - 0xa8, 0x76, 0x8d, 0x1d, 0x09, - 0x01, - }, - - Sequence: 4294967295, - }, - }, - TxOut: []*wire.TxOut{ - { - Value: 1000000000, - PkScript: []byte{ - txscript.OP_DATA_65, - 0x04, 0xae, 0x1a, 0x62, 0xfe, - 0x09, 0xc5, 0xf5, 0x1b, 0x13, - 0x90, 0x5f, 0x07, 0xf0, 0x6b, - 0x99, 0xa2, 0xf7, 0x15, 0x9b, - 0x22, 0x25, 0xf3, 0x74, 0xcd, - 0x37, 0x8d, 0x71, 0x30, 0x2f, - 0xa2, 0x84, 0x14, 0xe7, 0xaa, - 0xb3, 0x73, 0x97, 0xf5, 0x54, - 0xa7, 0xdf, 0x5f, 0x14, 0x2c, - 0x21, 0xc1, 0xb7, 0x30, 0x3b, - 0x8a, 0x06, 0x26, 0xf1, 0xba, - 0xde, 0xd5, 0xc7, 0x2a, 0x70, - 0x4f, 0x7e, 0x6c, 0xd8, 0x4c, - txscript.OP_CHECKSIG, - }, - }, - { - Value: 4000000000, - PkScript: []byte{ - txscript.OP_DATA_65, - 0x04, 0x11, 0xdb, 0x93, 0xe1, - 0xdc, 0xdb, 0x8a, 0x01, 0x6b, - 0x49, 0x84, 0x0f, 0x8c, 0x53, - 0xbc, 0x1e, 0xb6, 0x8a, 0x38, - 0x2e, 0x97, 0xb1, 0x48, 0x2e, - 0xca, 0xd7, 0xb1, 0x48, 0xa6, - 0x90, 0x9a, 0x5c, 0xb2, 0xe0, - 0xea, 0xdd, 0xfb, 0x84, 0xcc, - 0xf9, 0x74, 0x44, 0x64, 0xf8, - 0x2e, 0x16, 0x0b, 0xfa, 0x9b, - 0x8b, 0x64, 0xf9, 0xd4, 0xc0, - 0x3f, 0x99, 0x9b, 0x86, 0x43, - 0xf6, 0x56, 0xb4, 0x12, 0xa3, - txscript.OP_CHECKSIG, - }, - }, - }, - LockTime: 0, - }, - pkScript: []byte{ - txscript.OP_DATA_65, - 0x04, 0x11, 0xdb, 0x93, 0xe1, 0xdc, 0xdb, 0x8a, 0x01, - 0x6b, 0x49, 0x84, 0x0f, 0x8c, 0x53, 0xbc, 0x1e, 0xb6, - 0x8a, 0x38, 0x2e, 0x97, 0xb1, 0x48, 0x2e, 0xca, 0xd7, - 0xb1, 0x48, 0xa6, 0x90, 0x9a, 0x5c, 0xb2, 0xe0, 0xea, - 0xdd, 0xfb, 0x84, 0xcc, 0xf9, 0x74, 0x44, 0x64, 0xf8, - 0x2e, 0x16, 0x0b, 0xfa, 0x9b, 0x8b, 0x64, 0xf9, 0xd4, - 0xc0, 0x3f, 0x99, 0x9b, 0x86, 0x43, 0xf6, 0x56, 0xb4, - 0x12, 0xa3, txscript.OP_CHECKSIG, - }, - idx: 0, - nSigOps: 1, - scriptInfo: txscript.ScriptInfo{ - PkScriptClass: txscript.PubKeyTy, - NumInputs: 1, - ExpectedInputs: 1, - SigOps: 1, - }, - }, - // Previous test with the value of one output changed. - { - name: "CheckSig Failure", - tx: &wire.MsgTx{ - Version: 1, - TxIn: []*wire.TxIn{ - { - PreviousOutPoint: wire.OutPoint{ - Hash: wire.ShaHash([32]byte{ - 0xc9, 0x97, 0xa5, 0xe5, - 0x6e, 0x10, 0x41, 0x02, - 0xfa, 0x20, 0x9c, 0x6a, - 0x85, 0x2d, 0xd9, 0x06, - 0x60, 0xa2, 0x0b, 0x2d, - 0x9c, 0x35, 0x24, 0x23, - 0xed, 0xce, 0x25, 0x85, - 0x7f, 0xcd, 0x37, 0x04, - }), - Index: 0, - }, - SignatureScript: []uint8{ - txscript.OP_DATA_71, - 0x30, 0x44, 0x02, 0x20, 0x4e, - 0x45, 0xe1, 0x69, 0x32, 0xb8, - 0xaf, 0x51, 0x49, 0x61, 0xa1, - 0xd3, 0xa1, 0xa2, 0x5f, 0xdf, - 0x3f, 0x4f, 0x77, 0x32, 0xe9, - 0xd6, 0x24, 0xc6, 0xc6, 0x15, - 0x48, 0xab, 0x5f, 0xb8, 0xcd, - 0x41, 0x02, 0x20, 0x18, 0x15, - 0x22, 0xec, 0x8e, 0xca, 0x07, - 0xde, 0x48, 0x60, 0xa4, 0xac, - 0xdd, 0x12, 0x90, 0x9d, 0x83, - 0x1c, 0xc5, 0x6c, 0xbb, 0xac, - 0x46, 0x22, 0x08, 0x22, 0x21, - 0xa8, 0x76, 0x8d, 0x1d, 0x09, - 0x01, - }, - - Sequence: 4294967295, - }, - }, - TxOut: []*wire.TxOut{ - { - Value: 1000000000, - PkScript: []byte{ - txscript.OP_DATA_65, - 0x04, 0xae, 0x1a, 0x62, 0xfe, - 0x09, 0xc5, 0xf5, 0x1b, 0x13, - 0x90, 0x5f, 0x07, 0xf0, 0x6b, - 0x99, 0xa2, 0xf7, 0x15, 0x9b, - 0x22, 0x25, 0xf3, 0x74, 0xcd, - 0x37, 0x8d, 0x71, 0x30, 0x2f, - 0xa2, 0x84, 0x14, 0xe7, 0xaa, - 0xb3, 0x73, 0x97, 0xf5, 0x54, - 0xa7, 0xdf, 0x5f, 0x14, 0x2c, - 0x21, 0xc1, 0xb7, 0x30, 0x3b, - 0x8a, 0x06, 0x26, 0xf1, 0xba, - 0xde, 0xd5, 0xc7, 0x2a, 0x70, - 0x4f, 0x7e, 0x6c, 0xd8, 0x4c, - txscript.OP_CHECKSIG, - }, - }, - { - Value: 5000000000, - PkScript: []byte{ - txscript.OP_DATA_65, - 0x04, 0x11, 0xdb, 0x93, 0xe1, - 0xdc, 0xdb, 0x8a, 0x01, 0x6b, - 0x49, 0x84, 0x0f, 0x8c, 0x53, - 0xbc, 0x1e, 0xb6, 0x8a, 0x38, - 0x2e, 0x97, 0xb1, 0x48, 0x2e, - 0xca, 0xd7, 0xb1, 0x48, 0xa6, - 0x90, 0x9a, 0x5c, 0xb2, 0xe0, - 0xea, 0xdd, 0xfb, 0x84, 0xcc, - 0xf9, 0x74, 0x44, 0x64, 0xf8, - 0x2e, 0x16, 0x0b, 0xfa, 0x9b, - 0x8b, 0x64, 0xf9, 0xd4, 0xc0, - 0x3f, 0x99, 0x9b, 0x86, 0x43, - 0xf6, 0x56, 0xb4, 0x12, 0xa3, - txscript.OP_CHECKSIG, - }, - }, - }, - LockTime: 0, - }, - pkScript: []byte{ - txscript.OP_DATA_65, - 0x04, 0x11, 0xdb, 0x93, 0xe1, 0xdc, 0xdb, 0x8a, 0x01, - 0x6b, 0x49, 0x84, 0x0f, 0x8c, 0x53, 0xbc, 0x1e, 0xb6, - 0x8a, 0x38, 0x2e, 0x97, 0xb1, 0x48, 0x2e, 0xca, 0xd7, - 0xb1, 0x48, 0xa6, 0x90, 0x9a, 0x5c, 0xb2, 0xe0, 0xea, - 0xdd, 0xfb, 0x84, 0xcc, 0xf9, 0x74, 0x44, 0x64, 0xf8, - 0x2e, 0x16, 0x0b, 0xfa, 0x9b, 0x8b, 0x64, 0xf9, 0xd4, - 0xc0, 0x3f, 0x99, 0x9b, 0x86, 0x43, 0xf6, 0x56, 0xb4, - 0x12, 0xa3, txscript.OP_CHECKSIG, - }, - idx: 0, - err: txscript.ErrStackScriptFailed, - nSigOps: 1, - scriptInfo: txscript.ScriptInfo{ - PkScriptClass: txscript.PubKeyTy, - NumInputs: 1, - ExpectedInputs: 1, - SigOps: 1, - }, - }, - { - name: "CheckSig invalid signature", - tx: &wire.MsgTx{ - Version: 1, - TxIn: []*wire.TxIn{ - { - PreviousOutPoint: wire.OutPoint{ - Hash: wire.ShaHash([32]byte{ - 0xc9, 0x97, 0xa5, 0xe5, - 0x6e, 0x10, 0x41, 0x02, - 0xfa, 0x20, 0x9c, 0x6a, - 0x85, 0x2d, 0xd9, 0x06, - 0x60, 0xa2, 0x0b, 0x2d, - 0x9c, 0x35, 0x24, 0x23, - 0xed, 0xce, 0x25, 0x85, - 0x7f, 0xcd, 0x37, 0x04, - }), - Index: 0, - }, - // Signature has length fiddled to - // fail parsing. - SignatureScript: []uint8{ - txscript.OP_DATA_71, - 0x30, 0x45, 0x02, 0x20, 0x4e, - 0x45, 0xe1, 0x69, 0x32, 0xb8, - 0xaf, 0x51, 0x49, 0x61, 0xa1, - 0xd3, 0xa1, 0xa2, 0x5f, 0xdf, - 0x3f, 0x4f, 0x77, 0x32, 0xe9, - 0xd6, 0x24, 0xc6, 0xc6, 0x15, - 0x48, 0xab, 0x5f, 0xb8, 0xcd, - 0x41, 0x02, 0x20, 0x18, 0x15, - 0x22, 0xec, 0x8e, 0xca, 0x07, - 0xde, 0x48, 0x60, 0xa4, 0xac, - 0xdd, 0x12, 0x90, 0x9d, 0x83, - 0x1c, 0xc5, 0x6c, 0xbb, 0xac, - 0x46, 0x22, 0x08, 0x22, 0x21, - 0xa8, 0x76, 0x8d, 0x1d, 0x09, - 0x01, - }, - - Sequence: 4294967295, - }, - }, - TxOut: []*wire.TxOut{ - { - Value: 1000000000, - PkScript: []byte{ - txscript.OP_DATA_65, - 0x04, 0xae, 0x1a, 0x62, 0xfe, - 0x09, 0xc5, 0xf5, 0x1b, 0x13, - 0x90, 0x5f, 0x07, 0xf0, 0x6b, - 0x99, 0xa2, 0xf7, 0x15, 0x9b, - 0x22, 0x25, 0xf3, 0x74, 0xcd, - 0x37, 0x8d, 0x71, 0x30, 0x2f, - 0xa2, 0x84, 0x14, 0xe7, 0xaa, - 0xb3, 0x73, 0x97, 0xf5, 0x54, - 0xa7, 0xdf, 0x5f, 0x14, 0x2c, - 0x21, 0xc1, 0xb7, 0x30, 0x3b, - 0x8a, 0x06, 0x26, 0xf1, 0xba, - 0xde, 0xd5, 0xc7, 0x2a, 0x70, - 0x4f, 0x7e, 0x6c, 0xd8, 0x4c, - txscript.OP_CHECKSIG, - }, - }, - { - Value: 4000000000, - PkScript: []byte{ - txscript.OP_DATA_65, - 0x04, 0x11, 0xdb, 0x93, 0xe1, - 0xdc, 0xdb, 0x8a, 0x01, 0x6b, - 0x49, 0x84, 0x0f, 0x8c, 0x53, - 0xbc, 0x1e, 0xb6, 0x8a, 0x38, - 0x2e, 0x97, 0xb1, 0x48, 0x2e, - 0xca, 0xd7, 0xb1, 0x48, 0xa6, - 0x90, 0x9a, 0x5c, 0xb2, 0xe0, - 0xea, 0xdd, 0xfb, 0x84, 0xcc, - 0xf9, 0x74, 0x44, 0x64, 0xf8, - 0x2e, 0x16, 0x0b, 0xfa, 0x9b, - 0x8b, 0x64, 0xf9, 0xd4, 0xc0, - 0x3f, 0x99, 0x9b, 0x86, 0x43, - 0xf6, 0x56, 0xb4, 0x12, 0xa3, - txscript.OP_CHECKSIG, - }, - }, - }, - LockTime: 0, - }, - pkScript: []byte{ - txscript.OP_DATA_65, - 0x04, 0x11, 0xdb, 0x93, 0xe1, 0xdc, 0xdb, 0x8a, 0x01, - 0x6b, 0x49, 0x84, 0x0f, 0x8c, 0x53, 0xbc, 0x1e, 0xb6, - 0x8a, 0x38, 0x2e, 0x97, 0xb1, 0x48, 0x2e, 0xca, 0xd7, - 0xb1, 0x48, 0xa6, 0x90, 0x9a, 0x5c, 0xb2, 0xe0, 0xea, - 0xdd, 0xfb, 0x84, 0xcc, 0xf9, 0x74, 0x44, 0x64, 0xf8, - 0x2e, 0x16, 0x0b, 0xfa, 0x9b, 0x8b, 0x64, 0xf9, 0xd4, - 0xc0, 0x3f, 0x99, 0x9b, 0x86, 0x43, 0xf6, 0x56, 0xb4, - 0x12, 0xa3, txscript.OP_CHECKSIG, - }, - idx: 0, - shouldFail: true, - nSigOps: 1, - scriptInfo: txscript.ScriptInfo{ - PkScriptClass: txscript.PubKeyTy, - NumInputs: 1, - ExpectedInputs: 1, - SigOps: 1, - }, - }, - { - name: "CheckSig invalid pubkey", - tx: &wire.MsgTx{ - Version: 1, - TxIn: []*wire.TxIn{ - { - PreviousOutPoint: wire.OutPoint{ - Hash: wire.ShaHash([32]byte{ - 0xc9, 0x97, 0xa5, 0xe5, - 0x6e, 0x10, 0x41, 0x02, - 0xfa, 0x20, 0x9c, 0x6a, - 0x85, 0x2d, 0xd9, 0x06, - 0x60, 0xa2, 0x0b, 0x2d, - 0x9c, 0x35, 0x24, 0x23, - 0xed, 0xce, 0x25, 0x85, - 0x7f, 0xcd, 0x37, 0x04, - }), - Index: 0, - }, - SignatureScript: []uint8{ - txscript.OP_DATA_71, - 0x30, 0x44, 0x02, 0x20, 0x4e, - 0x45, 0xe1, 0x69, 0x32, 0xb8, - 0xaf, 0x51, 0x49, 0x61, 0xa1, - 0xd3, 0xa1, 0xa2, 0x5f, 0xdf, - 0x3f, 0x4f, 0x77, 0x32, 0xe9, - 0xd6, 0x24, 0xc6, 0xc6, 0x15, - 0x48, 0xab, 0x5f, 0xb8, 0xcd, - 0x41, 0x02, 0x20, 0x18, 0x15, - 0x22, 0xec, 0x8e, 0xca, 0x07, - 0xde, 0x48, 0x60, 0xa4, 0xac, - 0xdd, 0x12, 0x90, 0x9d, 0x83, - 0x1c, 0xc5, 0x6c, 0xbb, 0xac, - 0x46, 0x22, 0x08, 0x22, 0x21, - 0xa8, 0x76, 0x8d, 0x1d, 0x09, - 0x01, - }, - - Sequence: 4294967295, - }, - }, - TxOut: []*wire.TxOut{ - { - Value: 1000000000, - PkScript: []byte{ - txscript.OP_DATA_65, - 0x04, 0xae, 0x1a, 0x62, 0xfe, - 0x09, 0xc5, 0xf5, 0x1b, 0x13, - 0x90, 0x5f, 0x07, 0xf0, 0x6b, - 0x99, 0xa2, 0xf7, 0x15, 0x9b, - 0x22, 0x25, 0xf3, 0x74, 0xcd, - 0x37, 0x8d, 0x71, 0x30, 0x2f, - 0xa2, 0x84, 0x14, 0xe7, 0xaa, - 0xb3, 0x73, 0x97, 0xf5, 0x54, - 0xa7, 0xdf, 0x5f, 0x14, 0x2c, - 0x21, 0xc1, 0xb7, 0x30, 0x3b, - 0x8a, 0x06, 0x26, 0xf1, 0xba, - 0xde, 0xd5, 0xc7, 0x2a, 0x70, - 0x4f, 0x7e, 0x6c, 0xd8, 0x4c, - txscript.OP_CHECKSIG, - }, - }, - { - Value: 4000000000, - PkScript: []byte{ - txscript.OP_DATA_65, - 0x04, 0x11, 0xdb, 0x93, 0xe1, - 0xdc, 0xdb, 0x8a, 0x01, 0x6b, - 0x49, 0x84, 0x0f, 0x8c, 0x53, - 0xbc, 0x1e, 0xb6, 0x8a, 0x38, - 0x2e, 0x97, 0xb1, 0x48, 0x2e, - 0xca, 0xd7, 0xb1, 0x48, 0xa6, - 0x90, 0x9a, 0x5c, 0xb2, 0xe0, - 0xea, 0xdd, 0xfb, 0x84, 0xcc, - 0xf9, 0x74, 0x44, 0x64, 0xf8, - 0x2e, 0x16, 0x0b, 0xfa, 0x9b, - 0x8b, 0x64, 0xf9, 0xd4, 0xc0, - 0x3f, 0x99, 0x9b, 0x86, 0x43, - 0xf6, 0x56, 0xb4, 0x12, 0xa3, - txscript.OP_CHECKSIG, - }, - }, - }, - LockTime: 0, - }, - // pubkey header magic byte has been changed to parse wrong. - pkScript: []byte{ - txscript.OP_DATA_65, - 0x02, 0x11, 0xdb, 0x93, 0xe1, 0xdc, 0xdb, 0x8a, 0x01, - 0x6b, 0x49, 0x84, 0x0f, 0x8c, 0x53, 0xbc, 0x1e, 0xb6, - 0x8a, 0x38, 0x2e, 0x97, 0xb1, 0x48, 0x2e, 0xca, 0xd7, - 0xb1, 0x48, 0xa6, 0x90, 0x9a, 0x5c, 0xb2, 0xe0, 0xea, - 0xdd, 0xfb, 0x84, 0xcc, 0xf9, 0x74, 0x44, 0x64, 0xf8, - 0x2e, 0x16, 0x0b, 0xfa, 0x9b, 0x8b, 0x64, 0xf9, 0xd4, - 0xc0, 0x3f, 0x99, 0x9b, 0x86, 0x43, 0xf6, 0x56, 0xb4, - 0x12, 0xa3, txscript.OP_CHECKSIG, - }, - idx: 0, - shouldFail: true, - nSigOps: 1, - scriptInfo: txscript.ScriptInfo{ - PkScriptClass: txscript.PubKeyTy, - NumInputs: 1, - ExpectedInputs: 1, - SigOps: 1, - }, - }, - // tx 599e47a8114fe098103663029548811d2651991b62397e057f0c863c2bc9f9ea - // uses checksig with SigHashNone. - { - name: "CheckSigHashNone", - tx: &wire.MsgTx{ - Version: 1, - TxIn: []*wire.TxIn{ - { - PreviousOutPoint: wire.OutPoint{ - Hash: wire.ShaHash([32]byte{ - 0x5f, 0x38, 0x6c, 0x8a, - 0x38, 0x42, 0xc9, 0xa9, - 0xdc, 0xfa, 0x9b, 0x78, - 0xbe, 0x78, 0x5a, 0x40, - 0xa7, 0xbd, 0xa0, 0x8b, - 0x64, 0x64, 0x6b, 0xe3, - 0x65, 0x43, 0x01, 0xea, - 0xcc, 0xfc, 0x8d, 0x5e, - }), - Index: 1, - }, - SignatureScript: []byte{ - txscript.OP_DATA_71, - 0x30, 0x44, 0x02, 0x20, 0xbb, - 0x4f, 0xbc, 0x49, 0x5a, 0xa2, - 0x3b, 0xab, 0xb2, 0xc2, 0xbe, - 0x4e, 0x3f, 0xb4, 0xa5, 0xdf, - 0xfe, 0xfe, 0x20, 0xc8, 0xef, - 0xf5, 0x94, 0x0f, 0x13, 0x56, - 0x49, 0xc3, 0xea, 0x96, 0x44, - 0x4a, 0x02, 0x20, 0x04, 0xaf, - 0xcd, 0xa9, 0x66, 0xc8, 0x07, - 0xbb, 0x97, 0x62, 0x2d, 0x3e, - 0xef, 0xea, 0x82, 0x8f, 0x62, - 0x3a, 0xf3, 0x06, 0xef, 0x2b, - 0x75, 0x67, 0x82, 0xee, 0x6f, - 0x8a, 0x22, 0xa9, 0x59, 0xa2, - 0x02, - txscript.OP_DATA_65, - 0x04, 0xf1, 0x93, 0x9a, 0xe6, - 0xb0, 0x1e, 0x84, 0x9b, 0xf0, - 0x5d, 0x0e, 0xd5, 0x1f, 0xd5, - 0xb9, 0x2b, 0x79, 0xa0, 0xe3, - 0x13, 0xe3, 0xf3, 0x89, 0xc7, - 0x26, 0xf1, 0x1f, 0xa3, 0xe1, - 0x44, 0xd9, 0x22, 0x7b, 0x07, - 0xe8, 0xa8, 0x7c, 0x0e, 0xe3, - 0x63, 0x72, 0xe9, 0x67, 0xe0, - 0x90, 0xd1, 0x1b, 0x77, 0x77, - 0x07, 0xaa, 0x73, 0xef, 0xac, - 0xab, 0xff, 0xff, 0xa2, 0x85, - 0xc0, 0x0b, 0x36, 0x22, 0xd6, - }, - Sequence: 4294967295, - }, - }, - TxOut: []*wire.TxOut{ - { - Value: 1000000, - PkScript: []byte{ - txscript.OP_DUP, - txscript.OP_HASH160, - txscript.OP_DATA_20, - 0x66, 0x0d, 0x4e, 0xf3, 0xa7, - 0x43, 0xe3, 0xe6, 0x96, 0xad, - 0x99, 0x03, 0x64, 0xe5, 0x55, - 0xc2, 0x71, 0xad, 0x50, 0x4b, - txscript.OP_EQUALVERIFY, - txscript.OP_CHECKSIG, - }, - }, - { - Value: 29913632, - PkScript: []byte{ - txscript.OP_DUP, - txscript.OP_HASH160, - txscript.OP_DATA_20, - 0x21, 0xc4, 0x3c, 0xe4, 0x00, - 0x90, 0x13, 0x12, 0xa6, 0x03, - 0xe4, 0x20, 0x7a, 0xad, 0xfd, - 0x74, 0x2b, 0xe8, 0xe7, 0xda, - txscript.OP_EQUALVERIFY, - txscript.OP_CHECKSIG, - }, - }, - }, - LockTime: 0, - }, - pkScript: []byte{ - txscript.OP_DUP, - txscript.OP_HASH160, - txscript.OP_DATA_20, - 0x21, 0xc4, 0x3c, 0xe4, 0x00, 0x90, 0x13, 0x12, 0xa6, - 0x03, 0xe4, 0x20, 0x7a, 0xad, 0xfd, 0x74, 0x2b, 0xe8, - 0xe7, 0xda, - txscript.OP_EQUALVERIFY, - txscript.OP_CHECKSIG, - }, - idx: 0, - bip16: true, // after threshold - nSigOps: 1, - scriptInfo: txscript.ScriptInfo{ - PkScriptClass: txscript.PubKeyHashTy, - NumInputs: 2, - ExpectedInputs: 2, - SigOps: 1, - }, - }, - { - name: "Non-canonical signature: R value negative", - tx: &wire.MsgTx{ - Version: 1, - TxIn: []*wire.TxIn{ - { - PreviousOutPoint: wire.OutPoint{ - Hash: wire.ShaHash([32]byte{ - 0xfe, 0x15, 0x62, 0xc4, - 0x8b, 0x3a, 0xa6, 0x37, - 0x3f, 0x42, 0xe9, 0x61, - 0x51, 0x89, 0xcf, 0x73, - 0x32, 0xd7, 0x33, 0x5c, - 0xbe, 0xa7, 0x80, 0xbe, - 0x69, 0x6a, 0xc6, 0xc6, - 0x50, 0xfd, 0xda, 0x4a, - }), - Index: 1, - }, - SignatureScript: []byte{ - txscript.OP_DATA_71, - 0x30, 0x44, 0x02, 0x20, 0xa0, - 0x42, 0xde, 0xe5, 0x52, 0x6b, - 0xf2, 0x29, 0x4d, 0x3f, 0x3e, - 0xb9, 0x5a, 0xa7, 0x73, 0x19, - 0xd3, 0xff, 0x56, 0x7b, 0xcf, - 0x36, 0x46, 0x07, 0x0c, 0x81, - 0x12, 0x33, 0x01, 0xca, 0xce, - 0xa9, 0x02, 0x20, 0xea, 0x48, - 0xae, 0x58, 0xf5, 0x54, 0x10, - 0x96, 0x3f, 0xa7, 0x03, 0xdb, - 0x56, 0xf0, 0xba, 0xb2, 0x70, - 0xb1, 0x08, 0x22, 0xc5, 0x1c, - 0x68, 0x02, 0x6a, 0x97, 0x5c, - 0x7d, 0xae, 0x11, 0x2e, 0x4f, - 0x01, - txscript.OP_DATA_65, - 0x04, 0x49, 0x45, 0x33, 0x18, - 0xbd, 0x5e, 0xcf, 0xea, 0x5f, - 0x86, 0x32, 0x8c, 0x6d, 0x8e, - 0xd4, 0x12, 0xb4, 0xde, 0x2c, - 0xab, 0xd7, 0xb8, 0x56, 0x51, - 0x2f, 0x8c, 0xb7, 0xfd, 0x25, - 0xf6, 0x03, 0xb0, 0x55, 0xc5, - 0xdf, 0xe6, 0x22, 0x4b, 0xc4, - 0xfd, 0xbb, 0x6a, 0x7a, 0xa0, - 0x58, 0xd7, 0x5d, 0xad, 0x92, - 0x99, 0x45, 0x4f, 0x62, 0x1a, - 0x95, 0xb4, 0xb0, 0x21, 0x0e, - 0xc4, 0x09, 0x2b, 0xe5, 0x27, - }, - Sequence: 4294967295, - }, - { - PreviousOutPoint: wire.OutPoint{ - Hash: wire.ShaHash([32]byte{ - 0x2a, 0xc7, 0xee, 0xf8, - 0xa9, 0x62, 0x2d, 0xda, - 0xec, 0x18, 0x3b, 0xba, - 0xa9, 0x92, 0xb0, 0x7a, - 0x70, 0x3b, 0x48, 0x86, - 0x27, 0x9c, 0x46, 0xac, - 0x25, 0xeb, 0x91, 0xec, - 0x4c, 0x86, 0xd2, 0x9c, - }), - Index: 1, - }, - SignatureScript: []byte{ - txscript.OP_DATA_71, - 0x30, 0x44, 0x02, 0x20, 0xc3, - 0x02, 0x3b, 0xed, 0x85, 0x0d, - 0x94, 0x27, 0x8e, 0x06, 0xd2, - 0x37, 0x92, 0x21, 0x55, 0x28, - 0xdd, 0xdb, 0x63, 0xa4, 0xb6, - 0x88, 0x33, 0x92, 0x06, 0xdd, - 0xf9, 0xee, 0x72, 0x97, 0xa3, - 0x08, 0x02, 0x20, 0x25, 0x00, - 0x42, 0x8b, 0x26, 0x36, 0x45, - 0x54, 0xcb, 0x11, 0xd3, 0x3e, - 0x85, 0x35, 0x23, 0x49, 0x65, - 0x82, 0x8e, 0x33, 0x6e, 0x1a, - 0x4a, 0x72, 0x73, 0xeb, 0x5b, - 0x8d, 0x1d, 0xd7, 0x02, 0xcc, - 0x01, - txscript.OP_DATA_65, - 0x04, 0x49, 0x5c, 0x8f, 0x66, - 0x90, 0x0d, 0xb7, 0x62, 0x69, - 0x0b, 0x54, 0x49, 0xa1, 0xf4, - 0xe7, 0xc2, 0xed, 0x1f, 0x4b, - 0x34, 0x70, 0xfd, 0x42, 0x79, - 0x68, 0xa1, 0x31, 0x76, 0x0c, - 0x25, 0xf9, 0x12, 0x63, 0xad, - 0x51, 0x73, 0x8e, 0x19, 0xb6, - 0x07, 0xf5, 0xcf, 0x5f, 0x94, - 0x27, 0x4a, 0x8b, 0xbc, 0x74, - 0xba, 0x4b, 0x56, 0x0c, 0xe0, - 0xb3, 0x08, 0x8f, 0x7f, 0x5c, - 0x5f, 0xcf, 0xd6, 0xa0, 0x4b, - }, - Sequence: 4294967295, - }, - }, - TxOut: []*wire.TxOut{ - { - Value: 630320000, - PkScript: []byte{ - txscript.OP_DUP, - txscript.OP_HASH160, - txscript.OP_DATA_20, - 0x43, 0xdc, 0x32, 0x1b, 0x66, - 0x00, 0x51, 0x1f, 0xe0, 0xa9, - 0x6a, 0x97, 0xc2, 0x59, 0x3a, - 0x90, 0x54, 0x29, 0x74, 0xd6, - txscript.OP_EQUALVERIFY, - txscript.OP_CHECKSIG, - }, - }, - { - Value: 100000181, - PkScript: []byte{ - txscript.OP_DUP, - txscript.OP_HASH160, - txscript.OP_DATA_20, - 0xa4, 0x05, 0xea, 0x18, 0x09, - 0x14, 0xa9, 0x11, 0xd0, 0xb8, - 0x07, 0x99, 0x19, 0x2b, 0x0b, - 0x84, 0xae, 0x80, 0x1e, 0xbd, - txscript.OP_EQUALVERIFY, - txscript.OP_CHECKSIG, - }, - }, - { - Value: 596516343, - PkScript: []byte{ - txscript.OP_DUP, - txscript.OP_HASH160, - txscript.OP_DATA_20, - 0x24, 0x56, 0x76, 0x45, 0x4f, - 0x6f, 0xff, 0x28, 0x88, 0x39, - 0x47, 0xea, 0x70, 0x23, 0x86, - 0x9b, 0x8a, 0x71, 0xa3, 0x05, - txscript.OP_EQUALVERIFY, - txscript.OP_CHECKSIG, - }, - }, - }, - LockTime: 0, - }, - // Test input 0 - pkScript: []byte{ - txscript.OP_DUP, - txscript.OP_HASH160, - txscript.OP_DATA_20, - 0xfd, 0xf6, 0xea, 0xe7, 0x10, - 0xa0, 0xc4, 0x49, 0x7a, 0x8d, - 0x0f, 0xd2, 0x9a, 0xf6, 0x6b, - 0xac, 0x94, 0xaf, 0x6c, 0x98, - txscript.OP_EQUALVERIFY, - txscript.OP_CHECKSIG, - }, - idx: 0, - strictSigs: true, - shouldFail: true, - nSigOps: 1, - scriptInfo: txscript.ScriptInfo{ - PkScriptClass: txscript.PubKeyHashTy, - NumInputs: 2, - ExpectedInputs: 2, - SigOps: 1, - }, - }, - - // tx 51bf528ecf3c161e7c021224197dbe84f9a8564212f6207baa014c01a1668e1e - // first instance of an AnyoneCanPay signature in the blockchain - { - name: "CheckSigHashAnyoneCanPay", - tx: &wire.MsgTx{ - Version: 1, - TxIn: []*wire.TxIn{ - { - PreviousOutPoint: wire.OutPoint{ - Hash: wire.ShaHash([32]byte{ - 0xf6, 0x04, 0x4c, 0x0a, - 0xd4, 0x85, 0xf6, 0x33, - 0xb4, 0x1f, 0x97, 0xd0, - 0xd7, 0x93, 0xeb, 0x28, - 0x37, 0xae, 0x40, 0xf7, - 0x38, 0xff, 0x6d, 0x5f, - 0x50, 0xfd, 0xfd, 0x10, - 0x52, 0x8c, 0x1d, 0x76, - }), - Index: 1, - }, - SignatureScript: []byte{ - txscript.OP_DATA_72, - 0x30, 0x45, 0x02, 0x20, 0x58, - 0x53, 0xc7, 0xf1, 0x39, 0x57, - 0x85, 0xbf, 0xab, 0xb0, 0x3c, - 0x57, 0xe9, 0x62, 0xeb, 0x07, - 0x6f, 0xf2, 0x4d, 0x8e, 0x4e, - 0x57, 0x3b, 0x04, 0xdb, 0x13, - 0xb4, 0x5e, 0xd3, 0xed, 0x6e, - 0xe2, 0x02, 0x21, 0x00, 0x9d, - 0xc8, 0x2a, 0xe4, 0x3b, 0xe9, - 0xd4, 0xb1, 0xfe, 0x28, 0x47, - 0x75, 0x4e, 0x1d, 0x36, 0xda, - 0xd4, 0x8b, 0xa8, 0x01, 0x81, - 0x7d, 0x48, 0x5d, 0xc5, 0x29, - 0xaf, 0xc5, 0x16, 0xc2, 0xdd, - 0xb4, 0x81, - txscript.OP_DATA_33, - 0x03, 0x05, 0x58, 0x49, 0x80, - 0x36, 0x7b, 0x32, 0x1f, 0xad, - 0x7f, 0x1c, 0x1f, 0x4d, 0x5d, - 0x72, 0x3d, 0x0a, 0xc8, 0x0c, - 0x1d, 0x80, 0xc8, 0xba, 0x12, - 0x34, 0x39, 0x65, 0xb4, 0x83, - 0x64, 0x53, 0x7a, - }, - Sequence: 4294967295, - }, - { - PreviousOutPoint: wire.OutPoint{ - Hash: wire.ShaHash([32]byte{ - 0x9c, 0x6a, 0xf0, 0xdf, - 0x66, 0x69, 0xbc, 0xde, - 0xd1, 0x9e, 0x31, 0x7e, - 0x25, 0xbe, 0xbc, 0x8c, - 0x78, 0xe4, 0x8d, 0xf8, - 0xae, 0x1f, 0xe0, 0x2a, - 0x7f, 0x03, 0x08, 0x18, - 0xe7, 0x1e, 0xcd, 0x40, - }), - Index: 1, - }, - SignatureScript: []byte{ - txscript.OP_DATA_73, - 0x30, 0x46, 0x02, 0x21, 0x00, - 0x82, 0x69, 0xc9, 0xd7, 0xba, - 0x0a, 0x7e, 0x73, 0x0d, 0xd1, - 0x6f, 0x40, 0x82, 0xd2, 0x9e, - 0x36, 0x84, 0xfb, 0x74, 0x63, - 0xba, 0x06, 0x4f, 0xd0, 0x93, - 0xaf, 0xc1, 0x70, 0xad, 0x6e, - 0x03, 0x88, 0x02, 0x21, 0x00, - 0xbc, 0x6d, 0x76, 0x37, 0x39, - 0x16, 0xa3, 0xff, 0x6e, 0xe4, - 0x1b, 0x2c, 0x75, 0x20, 0x01, - 0xfd, 0xa3, 0xc9, 0xe0, 0x48, - 0xbc, 0xff, 0x0d, 0x81, 0xd0, - 0x5b, 0x39, 0xff, 0x0f, 0x42, - 0x17, 0xb2, 0x81, - txscript.OP_DATA_33, - 0x03, 0xaa, 0xe3, 0x03, 0xd8, - 0x25, 0x42, 0x15, 0x45, 0xc5, - 0xbc, 0x7c, 0xcd, 0x5a, 0xc8, - 0x7d, 0xd5, 0xad, 0xd3, 0xbc, - 0xc3, 0xa4, 0x32, 0xba, 0x7a, - 0xa2, 0xf2, 0x66, 0x16, 0x99, - 0xf9, 0xf6, 0x59, - }, - Sequence: 4294967295, - }, - }, - TxOut: []*wire.TxOut{ - { - Value: 300000, - PkScript: []byte{ - txscript.OP_DUP, - txscript.OP_HASH160, - txscript.OP_DATA_20, - 0x5c, 0x11, 0xf9, 0x17, 0x88, - 0x3b, 0x92, 0x7e, 0xef, 0x77, - 0xdc, 0x57, 0x70, 0x7a, 0xeb, - 0x85, 0x3f, 0x6d, 0x38, 0x94, - txscript.OP_EQUALVERIFY, - txscript.OP_CHECKSIG, - }, - }, - }, - LockTime: 0, - }, - pkScript: []byte{ - txscript.OP_DUP, - txscript.OP_HASH160, - txscript.OP_DATA_20, - 0x85, 0x51, 0xe4, 0x8a, 0x53, 0xde, 0xcd, 0x1c, 0xfc, - 0x63, 0x07, 0x9a, 0x45, 0x81, 0xbc, 0xcc, 0xfa, 0xd1, - 0xa9, 0x3c, - txscript.OP_EQUALVERIFY, - txscript.OP_CHECKSIG, - }, - idx: 0, - bip16: true, // after threshold - nSigOps: 1, - scriptInfo: txscript.ScriptInfo{ - PkScriptClass: txscript.PubKeyHashTy, - NumInputs: 2, - ExpectedInputs: 2, - SigOps: 1, - }, - }, - // tx 6d36bc17e947ce00bb6f12f8e7a56a1585c5a36188ffa2b05e10b4743273a74b - // Uses OP_CODESEPARATOR and OP_CHECKMULTISIG - { - name: "CheckMultiSig", - tx: &wire.MsgTx{ - Version: 1, - TxIn: []*wire.TxIn{ - { - PreviousOutPoint: wire.OutPoint{ - Hash: wire.ShaHash([32]byte{ - 0x37, 0xb1, 0x7d, 0x76, - 0x38, 0x51, 0xcd, 0x1a, - 0xb0, 0x4a, 0x42, 0x44, - 0x63, 0xd4, 0x13, 0xc4, - 0xee, 0x5c, 0xf6, 0x13, - 0x04, 0xc7, 0xfd, 0x76, - 0x97, 0x7b, 0xea, 0x7f, - 0xce, 0x07, 0x57, 0x05, - }), - Index: 0, - }, - SignatureScript: []byte{ - txscript.OP_DATA_71, - 0x30, 0x44, 0x02, 0x20, 0x02, - 0xdb, 0xe4, 0xb5, 0xa2, 0xfb, - 0xb5, 0x21, 0xe4, 0xdc, 0x5f, - 0xbe, 0xc7, 0x5f, 0xd9, 0x60, - 0x65, 0x1a, 0x27, 0x54, 0xb0, - 0x3d, 0x08, 0x71, 0xb8, 0xc9, - 0x65, 0x46, 0x9b, 0xe5, 0x0f, - 0xa7, 0x02, 0x20, 0x6d, 0x97, - 0x42, 0x1f, 0xb7, 0xea, 0x93, - 0x59, 0xb6, 0x3e, 0x48, 0xc2, - 0x10, 0x82, 0x23, 0x28, 0x4b, - 0x9a, 0x71, 0x56, 0x0b, 0xd8, - 0x18, 0x24, 0x69, 0xb9, 0x03, - 0x92, 0x28, 0xd7, 0xb3, 0xd7, - 0x01, 0x21, 0x02, 0x95, 0xbf, - 0x72, 0x71, 0x11, 0xac, 0xde, - 0xab, 0x87, 0x78, 0x28, 0x4f, - 0x02, 0xb7, 0x68, 0xd1, 0xe2, - 0x1a, 0xcb, 0xcb, 0xae, 0x42, - }, - Sequence: 4294967295, - }, - { - PreviousOutPoint: wire.OutPoint{ - Hash: wire.ShaHash([32]byte{ - 0x37, 0xb1, 0x7d, 0x76, - 0x38, 0x51, 0xcd, 0x1a, - 0xb0, 0x4a, 0x42, 0x44, - 0x63, 0xd4, 0x13, 0xc4, - 0xee, 0x5c, 0xf6, 0x13, - 0x04, 0xc7, 0xfd, 0x76, - 0x97, 0x7b, 0xea, 0x7f, - 0xce, 0x07, 0x57, 0x05, - }), - Index: 1, - }, - SignatureScript: []uint8{ - txscript.OP_FALSE, - txscript.OP_DATA_72, - 0x30, 0x45, 0x02, 0x20, 0x10, - 0x6a, 0x3e, 0x4e, 0xf0, 0xb5, - 0x1b, 0x76, 0x4a, 0x28, 0x87, - 0x22, 0x62, 0xff, 0xef, 0x55, - 0x84, 0x65, 0x14, 0xda, 0xcb, - 0xdc, 0xbb, 0xdd, 0x65, 0x2c, - 0x84, 0x9d, 0x39, 0x5b, 0x43, - 0x84, 0x02, 0x21, 0x00, 0xe0, - 0x3a, 0xe5, 0x54, 0xc3, 0xcb, - 0xb4, 0x06, 0x00, 0xd3, 0x1d, - 0xd4, 0x6f, 0xc3, 0x3f, 0x25, - 0xe4, 0x7b, 0xf8, 0x52, 0x5b, - 0x1f, 0xe0, 0x72, 0x82, 0xe3, - 0xb6, 0xec, 0xb5, 0xf3, 0xbb, - 0x28, 0x01, - txscript.OP_CODESEPARATOR, - txscript.OP_TRUE, - txscript.OP_DATA_33, - 0x02, 0x32, 0xab, 0xdc, 0x89, - 0x3e, 0x7f, 0x06, 0x31, 0x36, - 0x4d, 0x7f, 0xd0, 0x1c, 0xb3, - 0x3d, 0x24, 0xda, 0x45, 0x32, - 0x9a, 0x00, 0x35, 0x7b, 0x3a, - 0x78, 0x86, 0x21, 0x1a, 0xb4, - 0x14, 0xd5, 0x5a, - txscript.OP_TRUE, - txscript.OP_CHECKMULTISIG, - }, - Sequence: 4294967295, - }, - }, - TxOut: []*wire.TxOut{ - { - Value: 4800000, - PkScript: []byte{ - txscript.OP_DUP, - txscript.OP_HASH160, - txscript.OP_DATA_20, - 0x0d, 0x77, 0x13, 0x64, 0x9f, - 0x9a, 0x06, 0x78, 0xf4, 0xe8, - 0x80, 0xb4, 0x0f, 0x86, 0xb9, - 0x32, 0x89, 0xd1, 0xbb, 0x27, - txscript.OP_EQUALVERIFY, - txscript.OP_CHECKSIG, - }, - }, - }, - LockTime: 0, - }, - // This is a very weird script... - pkScript: []byte{ - txscript.OP_DATA_20, - 0x2a, 0x9b, 0xc5, 0x44, 0x7d, 0x66, 0x4c, 0x1d, 0x01, - 0x41, 0x39, 0x2a, 0x84, 0x2d, 0x23, 0xdb, 0xa4, 0x5c, - 0x4f, 0x13, - txscript.OP_NOP2, txscript.OP_DROP, - }, - idx: 1, - bip16: false, - nSigOps: 0, // multisig is in the pkScript! - scriptInfoErr: txscript.ErrStackNonPushOnly, - }, - // same as previous but with one byte changed to make signature fail - { - name: "CheckMultiSig fail", - tx: &wire.MsgTx{ - Version: 1, - TxIn: []*wire.TxIn{ - { - PreviousOutPoint: wire.OutPoint{ - Hash: wire.ShaHash([32]byte{ - 0x37, 0xb1, 0x7d, 0x76, - 0x38, 0x51, 0xcd, 0x1a, - 0xb0, 0x4a, 0x42, 0x44, - 0x63, 0xd4, 0x13, 0xc4, - 0xee, 0x5c, 0xf6, 0x13, - 0x04, 0xc7, 0xfd, 0x76, - 0x97, 0x7b, 0xea, 0x7f, - 0xce, 0x07, 0x57, 0x05, - }), - Index: 0, - }, - SignatureScript: []byte{ - txscript.OP_DATA_71, - 0x30, 0x44, 0x02, 0x20, 0x02, - 0xdb, 0xe4, 0xb5, 0xa2, 0xfb, - 0xb5, 0x21, 0xe4, 0xdc, 0x5f, - 0xbe, 0xc7, 0x5f, 0xd9, 0x60, - 0x65, 0x1a, 0x27, 0x54, 0xb0, - 0x3d, 0x08, 0x71, 0xb8, 0xc9, - 0x65, 0x46, 0x9b, 0xe5, 0x0f, - 0xa7, 0x02, 0x20, 0x6d, 0x97, - 0x42, 0x1f, 0xb7, 0xea, 0x93, - 0x59, 0xb6, 0x3e, 0x48, 0xc2, - 0x10, 0x82, 0x23, 0x28, 0x4b, - 0x9a, 0x71, 0x56, 0x0b, 0xd8, - 0x18, 0x24, 0x69, 0xb9, 0x03, - 0x92, 0x28, 0xd7, 0xb3, 0xd7, - 0x01, 0x21, 0x02, 0x95, 0xbf, - 0x72, 0x71, 0x11, 0xac, 0xde, - 0xab, 0x87, 0x78, 0x28, 0x4f, - 0x02, 0xb7, 0x68, 0xd1, 0xe2, - 0x1a, 0xcb, 0xcb, 0xae, 0x42, - }, - Sequence: 4294967295, - }, - { - PreviousOutPoint: wire.OutPoint{ - Hash: wire.ShaHash([32]byte{ - 0x37, 0xb1, 0x7d, 0x76, - 0x38, 0x51, 0xcd, 0x1a, - 0xb0, 0x4a, 0x42, 0x44, - 0x63, 0xd4, 0x13, 0xc4, - 0xee, 0x5c, 0xf6, 0x13, - 0x04, 0xc7, 0xfd, 0x76, - 0x97, 0x7b, 0xea, 0x7f, - 0xce, 0x07, 0x57, 0x05, - }), - Index: 1, - }, - SignatureScript: []uint8{ - txscript.OP_FALSE, - txscript.OP_DATA_72, - 0x30, 0x45, 0x02, 0x20, 0x10, - 0x6a, 0x3e, 0x4e, 0xf0, 0xb5, - 0x1b, 0x76, 0x4a, 0x28, 0x87, - 0x22, 0x62, 0xff, 0xef, 0x55, - 0x84, 0x65, 0x14, 0xda, 0xcb, - 0xdc, 0xbb, 0xdd, 0x65, 0x2c, - 0x84, 0x9d, 0x39, 0x5b, 0x43, - 0x84, 0x02, 0x21, 0x00, 0xe0, - 0x3a, 0xe5, 0x54, 0xc3, 0xcb, - 0xb4, 0x06, 0x00, 0xd3, 0x1d, - 0xd4, 0x6f, 0xc3, 0x3f, 0x25, - 0xe4, 0x7b, 0xf8, 0x52, 0x5b, - 0x1f, 0xe0, 0x72, 0x82, 0xe3, - 0xb6, 0xec, 0xb5, 0xf3, 0xbb, - 0x28, 0x01, - txscript.OP_CODESEPARATOR, - txscript.OP_TRUE, - txscript.OP_DATA_33, - 0x02, 0x32, 0xab, 0xdc, 0x89, - 0x3e, 0x7f, 0x06, 0x31, 0x36, - 0x4d, 0x7f, 0xd0, 0x1c, 0xb3, - 0x3d, 0x24, 0xda, 0x45, 0x32, - 0x9a, 0x00, 0x35, 0x7b, 0x3a, - 0x78, 0x86, 0x21, 0x1a, 0xb4, - 0x14, 0xd5, 0x5a, - txscript.OP_TRUE, - txscript.OP_CHECKMULTISIG, - }, - Sequence: 4294967295, - }, - }, - TxOut: []*wire.TxOut{ - { - Value: 5800000, - PkScript: []byte{ - txscript.OP_DUP, - txscript.OP_HASH160, - txscript.OP_DATA_20, - 0x0d, 0x77, 0x13, 0x64, 0x9f, - 0x9a, 0x06, 0x78, 0xf4, 0xe8, - 0x80, 0xb4, 0x0f, 0x86, 0xb9, - 0x32, 0x89, 0xd1, 0xbb, 0x27, - txscript.OP_EQUALVERIFY, - txscript.OP_CHECKSIG, - }, - }, - }, - LockTime: 0, - }, - // This is a very weird script... - pkScript: []byte{ - txscript.OP_DATA_20, - 0x2a, 0x9b, 0xc5, 0x44, 0x7d, 0x66, 0x4c, 0x1d, 0x01, - 0x41, 0x39, 0x2a, 0x84, 0x2d, 0x23, 0xdb, 0xa4, 0x5c, - 0x4f, 0x13, - txscript.OP_NOP2, txscript.OP_DROP, - }, - idx: 1, - bip16: false, - err: txscript.ErrStackScriptFailed, - nSigOps: 0, // multisig is in the pkScript! - scriptInfoErr: txscript.ErrStackNonPushOnly, - }, - // taken from tx b2d93dfd0b2c1a380e55e76a8d9cb3075dec9f4474e9485be008c337fd62c1f7 - // on testnet - // multisig with zero required signatures - { - name: "CheckMultiSig zero required signatures", - tx: &wire.MsgTx{ - Version: 1, - TxIn: []*wire.TxIn{ - { - PreviousOutPoint: wire.OutPoint{ - Hash: wire.ShaHash([32]byte{ - 0x37, 0xb1, 0x7d, 0x76, - 0x38, 0x51, 0xcd, 0x1a, - 0xb0, 0x4a, 0x42, 0x44, - 0x63, 0xd4, 0x13, 0xc4, - 0xee, 0x5c, 0xf6, 0x13, - 0x04, 0xc7, 0xfd, 0x76, - 0x97, 0x7b, 0xea, 0x7f, - 0xce, 0x07, 0x57, 0x05, - }), - Index: 0, - }, - SignatureScript: []byte{ - txscript.OP_0, - txscript.OP_DATA_37, - txscript.OP_0, - txscript.OP_DATA_33, - 0x02, 0x4a, 0xb3, 0x3c, 0x3a, - 0x54, 0x7a, 0x37, 0x29, 0x3e, - 0xb8, 0x75, 0xb4, 0xbb, 0xdb, - 0xd4, 0x73, 0xe9, 0xd4, 0xba, - 0xfd, 0xf3, 0x56, 0x87, 0xe7, - 0x97, 0x44, 0xdc, 0xd7, 0x0f, - 0x6e, 0x4d, 0xe2, - txscript.OP_1, - txscript.OP_CHECKMULTISIG, - }, - Sequence: 4294967295, - }, - }, - TxOut: []*wire.TxOut{}, - LockTime: 0, - }, - pkScript: []byte{ - txscript.OP_HASH160, - txscript.OP_DATA_20, - 0x2c, 0x6b, 0x10, 0x7f, 0xdf, 0x10, 0x6f, 0x22, 0x6f, - 0x3f, 0xa3, 0x27, 0xba, 0x36, 0xd6, 0xe3, 0xca, 0xc7, - 0x3d, 0xf0, - txscript.OP_EQUAL, - }, - idx: 0, - bip16: true, - nSigOps: 1, - scriptInfo: txscript.ScriptInfo{ - PkScriptClass: txscript.ScriptHashTy, - NumInputs: 2, - ExpectedInputs: 2, - SigOps: 1, - }, - }, - // tx e5779b9e78f9650debc2893fd9636d827b26b4ddfa6a8172fe8708c924f5c39d - // First P2SH transaction in the blockchain - { - name: "P2SH", - tx: &wire.MsgTx{ - Version: 1, - TxIn: []*wire.TxIn{ - { - PreviousOutPoint: wire.OutPoint{ - Hash: wire.ShaHash([32]byte{ - 0x6d, 0x58, 0xf8, 0xa3, - 0xaa, 0x43, 0x0b, 0x84, - 0x78, 0x52, 0x3a, 0x65, - 0xc2, 0x03, 0xa2, 0x7b, - 0xb8, 0x81, 0x17, 0x8c, - 0xb1, 0x23, 0x13, 0xaf, - 0xde, 0x29, 0xf9, 0x2e, - 0xd7, 0x56, 0xaa, 0x7e, - }), - Index: 0, - }, - SignatureScript: []byte{ - txscript.OP_DATA_2, - // OP_3 OP_7 - 0x53, 0x57, - }, - Sequence: 4294967295, - }, - }, - TxOut: []*wire.TxOut{ - { - Value: 1000000, - PkScript: []byte{ - txscript.OP_DUP, - txscript.OP_HASH160, - txscript.OP_DATA_20, - 0x5b, 0x69, 0xd8, 0xb9, 0xdf, - 0xa6, 0xe4, 0x12, 0x26, 0x47, - 0xe1, 0x79, 0x4e, 0xaa, 0x3b, - 0xfc, 0x11, 0x1f, 0x70, 0xef, - txscript.OP_EQUALVERIFY, - txscript.OP_CHECKSIG, - }, - }, - }, - LockTime: 0, - }, - pkScript: []byte{ - txscript.OP_HASH160, - txscript.OP_DATA_20, - 0x43, 0x3e, 0xc2, 0xac, 0x1f, 0xfa, 0x1b, 0x7b, 0x7d, - 0x02, 0x7f, 0x56, 0x45, 0x29, 0xc5, 0x71, 0x97, 0xf9, - 0xae, 0x88, - txscript.OP_EQUAL, - }, - idx: 0, - bip16: true, - nSigOps: 0, // no signature ops in the pushed script. - scriptInfo: txscript.ScriptInfo{ - PkScriptClass: txscript.ScriptHashTy, - NumInputs: 1, - ExpectedInputs: -1, // p2sh script is non standard - SigOps: 0, - }, - }, - // next few tests are modified versions of previous to hit p2sh error - // cases. - { - // sigscript changed so that pkscript hash will not match. - name: "P2SH - bad hash", - tx: &wire.MsgTx{ - Version: 1, - TxIn: []*wire.TxIn{ - { - PreviousOutPoint: wire.OutPoint{ - Hash: wire.ShaHash([32]byte{ - 0x6d, 0x58, 0xf8, 0xa3, - 0xaa, 0x43, 0x0b, 0x84, - 0x78, 0x52, 0x3a, 0x65, - 0xc2, 0x03, 0xa2, 0x7b, - 0xb8, 0x81, 0x17, 0x8c, - 0xb1, 0x23, 0x13, 0xaf, - 0xde, 0x29, 0xf9, 0x2e, - 0xd7, 0x56, 0xaa, 0x7e, - }), - Index: 0, - }, - SignatureScript: []byte{ - txscript.OP_DATA_2, - // OP_3 OP_8 - 0x53, 0x58, - }, - Sequence: 4294967295, - }, - }, - TxOut: []*wire.TxOut{ - { - Value: 1000000, - PkScript: []byte{ - txscript.OP_DUP, - txscript.OP_HASH160, - txscript.OP_DATA_20, - 0x5b, 0x69, 0xd8, 0xb9, 0xdf, - 0xa6, 0xe4, 0x12, 0x26, 0x47, - 0xe1, 0x79, 0x4e, 0xaa, 0x3b, - 0xfc, 0x11, 0x1f, 0x70, 0xef, - txscript.OP_EQUALVERIFY, - txscript.OP_CHECKSIG, - }, - }, - }, - LockTime: 0, - }, - pkScript: []byte{ - txscript.OP_HASH160, - txscript.OP_DATA_20, - 0x43, 0x3e, 0xc2, 0xac, 0x1f, 0xfa, 0x1b, 0x7b, 0x7d, - 0x02, 0x7f, 0x56, 0x45, 0x29, 0xc5, 0x71, 0x97, 0xf9, - 0xae, 0x88, - txscript.OP_EQUAL, - }, - idx: 0, - err: txscript.ErrStackScriptFailed, - bip16: true, - nSigOps: 0, // no signature ops in the pushed script. - scriptInfo: txscript.ScriptInfo{ - PkScriptClass: txscript.ScriptHashTy, - NumInputs: 1, - ExpectedInputs: -1, // p2sh script is non standard - SigOps: 0, - }, - }, - { - // sigscript changed so that pkscript hash will not match. - name: "P2SH - doesn't parse", - tx: &wire.MsgTx{ - Version: 1, - TxIn: []*wire.TxIn{ - { - PreviousOutPoint: wire.OutPoint{ - Hash: wire.ShaHash([32]byte{ - 0x6d, 0x58, 0xf8, 0xa3, - 0xaa, 0x43, 0x0b, 0x84, - 0x78, 0x52, 0x3a, 0x65, - 0xc2, 0x03, 0xa2, 0x7b, - 0xb8, 0x81, 0x17, 0x8c, - 0xb1, 0x23, 0x13, 0xaf, - 0xde, 0x29, 0xf9, 0x2e, - 0xd7, 0x56, 0xaa, 0x7e, - }), - Index: 0, - }, - SignatureScript: []byte{ - txscript.OP_DATA_2, - // pushed script. - txscript.OP_DATA_2, 0x1, - }, - Sequence: 4294967295, - }, - }, - TxOut: []*wire.TxOut{ - { - Value: 1000000, - PkScript: []byte{ - txscript.OP_DUP, - txscript.OP_HASH160, - txscript.OP_DATA_20, - 0x5b, 0x69, 0xd8, 0xb9, 0xdf, - 0xa6, 0xe4, 0x12, 0x26, 0x47, - 0xe1, 0x79, 0x4e, 0xaa, 0x3b, - 0xfc, 0x11, 0x1f, 0x70, 0xef, - txscript.OP_EQUALVERIFY, - txscript.OP_CHECKSIG, - }, - }, - }, - LockTime: 0, - }, - pkScript: []byte{ - txscript.OP_HASH160, - txscript.OP_DATA_20, - 0xd4, 0x8c, 0xe8, 0x6c, 0x69, 0x8f, 0x24, 0x68, 0x29, - 0x92, 0x1b, 0xa9, 0xfb, 0x2a, 0x84, 0x4a, 0xe2, 0xad, - 0xba, 0x67, - txscript.OP_EQUAL, - }, - idx: 0, - err: txscript.ErrStackShortScript, - bip16: true, - scriptInfoErr: txscript.ErrStackShortScript, - }, - { - // sigscript changed so to be non pushonly. - name: "P2SH - non pushonly", - tx: &wire.MsgTx{ - Version: 1, - TxIn: []*wire.TxIn{ - { - PreviousOutPoint: wire.OutPoint{ - Hash: wire.ShaHash([32]byte{ - 0x6d, 0x58, 0xf8, 0xa3, - 0xaa, 0x43, 0x0b, 0x84, - 0x78, 0x52, 0x3a, 0x65, - 0xc2, 0x03, 0xa2, 0x7b, - 0xb8, 0x81, 0x17, 0x8c, - 0xb1, 0x23, 0x13, 0xaf, - 0xde, 0x29, 0xf9, 0x2e, - 0xd7, 0x56, 0xaa, 0x7e, - }), - Index: 0, - }, - // doesn't have to match signature. - // will never run. - SignatureScript: []byte{ - - txscript.OP_DATA_2, - // pushed script. - txscript.OP_DATA_1, 0x1, - txscript.OP_DUP, - }, - Sequence: 4294967295, - }, - }, - TxOut: []*wire.TxOut{ - { - Value: 1000000, - PkScript: []byte{ - txscript.OP_DUP, - txscript.OP_HASH160, - txscript.OP_DATA_20, - 0x5b, 0x69, 0xd8, 0xb9, 0xdf, - 0xa6, 0xe4, 0x12, 0x26, 0x47, - 0xe1, 0x79, 0x4e, 0xaa, 0x3b, - 0xfc, 0x11, 0x1f, 0x70, 0xef, - txscript.OP_EQUALVERIFY, - txscript.OP_CHECKSIG, - }, - }, - }, - LockTime: 0, - }, - pkScript: []byte{ - txscript.OP_HASH160, - txscript.OP_DATA_20, - 0x43, 0x3e, 0xc2, 0xac, 0x1f, 0xfa, 0x1b, 0x7b, 0x7d, - 0x02, 0x7f, 0x56, 0x45, 0x29, 0xc5, 0x71, 0x97, 0xf9, - 0xae, 0x88, - txscript.OP_EQUAL, - }, - idx: 0, - parseErr: txscript.ErrStackP2SHNonPushOnly, - bip16: true, - nSigOps: 0, // no signature ops in the pushed script. - scriptInfoErr: txscript.ErrStackNonPushOnly, - }, - { - // sigscript changed so to be non pushonly. - name: "empty pkScript", - tx: &wire.MsgTx{ - Version: 1, - TxIn: []*wire.TxIn{ - { - PreviousOutPoint: wire.OutPoint{ - Hash: wire.ShaHash([32]byte{ - 0x6d, 0x58, 0xf8, 0xa3, - 0xaa, 0x43, 0x0b, 0x84, - 0x78, 0x52, 0x3a, 0x65, - 0xc2, 0x03, 0xa2, 0x7b, - 0xb8, 0x81, 0x17, 0x8c, - 0xb1, 0x23, 0x13, 0xaf, - 0xde, 0x29, 0xf9, 0x2e, - 0xd7, 0x56, 0xaa, 0x7e, - }), - Index: 0, - }, - // doesn't have to match signature. - // will never run. - SignatureScript: []byte{ - txscript.OP_TRUE, - }, - Sequence: 4294967295, - }, - }, - TxOut: []*wire.TxOut{ - { - Value: 1000000, - PkScript: []byte{ - txscript.OP_DUP, - txscript.OP_HASH160, - txscript.OP_DATA_20, - 0x5b, 0x69, 0xd8, 0xb9, 0xdf, - 0xa6, 0xe4, 0x12, 0x26, 0x47, - 0xe1, 0x79, 0x4e, 0xaa, 0x3b, - 0xfc, 0x11, 0x1f, 0x70, 0xef, - txscript.OP_EQUALVERIFY, - txscript.OP_CHECKSIG, - }, - }, - }, - LockTime: 0, - }, - pkScript: []byte{}, - idx: 0, - bip16: true, - nSigOps: 0, // no signature ops in the pushed script. - scriptInfo: txscript.ScriptInfo{ - PkScriptClass: txscript.NonStandardTy, - NumInputs: 1, - ExpectedInputs: -1, - SigOps: 0, - }, - }, -} - -// Test a number of tx from the blockchain to test otherwise difficult to test -// opcodes (i.e. those that involve signatures). Being from the blockchain, -// these transactions are known good. -// TODO(oga) For signatures we currently do not test SigHashSingle because -// nothing in the blockchain that we have yet seen uses them, making it hard -// to confirm we implemented the spec correctly. -func testTx(t *testing.T, test txTest) { - var flags txscript.ScriptFlags - if test.bip16 { - flags |= txscript.ScriptBip16 - } - if test.strictSigs { - flags |= txscript.ScriptVerifyDERSignatures - } - vm, err := txscript.NewEngine(test.pkScript, test.tx, test.idx, - flags) - if err != nil { - if err != test.parseErr { - t.Errorf("Failed to parse %s: got \"%v\" expected "+ - "\"%v\"", test.name, err, test.parseErr) - } - return - } - if test.parseErr != nil { - t.Errorf("%s: parse succeeded when expecting \"%v\"", test.name, - test.parseErr) - } - - err = vm.Execute() - if err != nil { - // failed means no specified error - if test.shouldFail == true { - return - } - if err != test.err { - t.Errorf("Failed to validate %s tx: %v expected %v", - test.name, err, test.err) - } - return - } - if test.err != nil || test.shouldFail == true { - t.Errorf("%s: expected failure: %v, succeeded", test.name, - test.err) - } -} - -func TestTX(t *testing.T) { +// TestGetPreciseSigOps ensures the more precise signature operation counting +// mechanism which includes signatures in P2SH scripts works as expected. +func TestGetPreciseSigOps(t *testing.T) { t.Parallel() - for i := range txTests { - testTx(t, txTests[i]) - } -} - -func TestGetPreciseSignOps(t *testing.T) { - t.Parallel() - - // First we go over the range of tests in testTx and count the sigops in - // them. - for _, test := range txTests { - count := txscript.GetPreciseSigOpCount( - test.tx.TxIn[test.idx].SignatureScript, test.pkScript, - test.bip16) - if count != test.nSigOps { - t.Errorf("%s: expected count of %d, got %d", test.name, - test.nSigOps, count) - - } - } - - // Now we go over a number of tests to hit the more awkward error - // conditions in the P2SH cases.. - - type psocTest struct { + tests := []struct { name string scriptSig []byte nSigOps int err error - } - psocTests := []psocTest{ + }{ { name: "scriptSig doesn't parse", scriptSig: []byte{txscript.OP_PUSHDATA1, 2}, @@ -1709,7 +153,7 @@ func TestGetPreciseSignOps(t *testing.T) { }, { name: "scriptSig length 0", - scriptSig: []byte{}, + scriptSig: nil, nSigOps: 0, }, { @@ -1718,7 +162,6 @@ func TestGetPreciseSignOps(t *testing.T) { scriptSig: []byte{txscript.OP_1, txscript.OP_1}, nSigOps: 0, }, - // pushed script doesn't parse. { name: "pushed script doesn't parse", scriptSig: []byte{txscript.OP_DATA_2, @@ -1726,20 +169,15 @@ func TestGetPreciseSignOps(t *testing.T) { err: txscript.ErrStackShortScript, }, } + // The signature in the p2sh script is nonsensical for the tests since - // this script will never be executed. What matters is that it matches + // this script will never be executed. What matters is that it matches // the right pattern. - pkScript := []byte{ - txscript.OP_HASH160, - txscript.OP_DATA_20, - 0x43, 0x3e, 0xc2, 0xac, 0x1f, 0xfa, 0x1b, 0x7b, 0x7d, - 0x02, 0x7f, 0x56, 0x45, 0x29, 0xc5, 0x71, 0x97, 0xf9, - 0xae, 0x88, - txscript.OP_EQUAL, - } - for _, test := range psocTests { - count := txscript.GetPreciseSigOpCount( - test.scriptSig, pkScript, true) + pkScript := mustParseShortForm("HASH160 DATA_20 0x433ec2ac1ffa1b7b7d0" + + "27f564529c57197f9ae88 EQUAL") + for _, test := range tests { + count := txscript.GetPreciseSigOpCount(test.scriptSig, pkScript, + true) if count != test.nSigOps { t.Errorf("%s: expected count of %d, got %d", test.name, test.nSigOps, count) @@ -1748,236 +186,235 @@ func TestGetPreciseSignOps(t *testing.T) { } } -type removeOpcodeTest struct { - name string - before []byte - remove byte - err error - after []byte -} - -var removeOpcodeTests = []removeOpcodeTest{ - // Nothing to remove. - { - name: "nothing to remove", - before: []byte{txscript.OP_NOP}, - remove: txscript.OP_CODESEPARATOR, - after: []byte{txscript.OP_NOP}, - }, - // Test basic opcode removal - { - name: "codeseparator 1", - before: []byte{txscript.OP_NOP, txscript.OP_CODESEPARATOR, - txscript.OP_TRUE}, - remove: txscript.OP_CODESEPARATOR, - after: []byte{txscript.OP_NOP, txscript.OP_TRUE}, - }, - // The opcode in question is actually part of the data in a previous - // opcode - { - name: "codeseparator by coincidence", - before: []byte{txscript.OP_NOP, txscript.OP_DATA_1, txscript.OP_CODESEPARATOR, - txscript.OP_TRUE}, - remove: txscript.OP_CODESEPARATOR, - after: []byte{txscript.OP_NOP, txscript.OP_DATA_1, txscript.OP_CODESEPARATOR, - txscript.OP_TRUE}, - }, - { - name: "invalid opcode", - before: []byte{txscript.OP_UNKNOWN186}, - remove: txscript.OP_CODESEPARATOR, - after: []byte{txscript.OP_UNKNOWN186}, - }, - { - name: "invalid length (insruction)", - before: []byte{txscript.OP_PUSHDATA1}, - remove: txscript.OP_CODESEPARATOR, - err: txscript.ErrStackShortScript, - }, - { - name: "invalid length (data)", - before: []byte{txscript.OP_PUSHDATA1, 255, 254}, - remove: txscript.OP_CODESEPARATOR, - err: txscript.ErrStackShortScript, - }, -} - -func testRemoveOpcode(t *testing.T, test *removeOpcodeTest) { - result, err := txscript.TstRemoveOpcode(test.before, test.remove) - if test.err != nil { - if err != test.err { - t.Errorf("%s: got unexpected error. exp: \"%v\" "+ - "got: \"%v\"", test.name, test.err, err) - } - return - } - if err != nil { - t.Errorf("%s: unexpected failure: \"%v\"", test.name, err) - return - } - if !bytes.Equal(test.after, result) { - t.Errorf("%s: value does not equal expected: exp: \"%v\""+ - " got: \"%v\"", test.name, test.after, result) - } -} - +// TestRemoveOpcodes ensures that removing opcodes from scripts behaves as +// expected. func TestRemoveOpcodes(t *testing.T) { t.Parallel() - for i := range removeOpcodeTests { - testRemoveOpcode(t, &removeOpcodeTests[i]) + tests := []struct { + name string + before string + remove byte + err error + after string + }{ + { + // Nothing to remove. + name: "nothing to remove", + before: "NOP", + remove: txscript.OP_CODESEPARATOR, + after: "NOP", + }, + { + // Test basic opcode removal. + name: "codeseparator 1", + before: "NOP CODESEPARATOR TRUE", + remove: txscript.OP_CODESEPARATOR, + after: "NOP TRUE", + }, + { + // The opcode in question is actually part of the data + // in a previous opcode. + name: "codeseparator by coincidence", + before: "NOP DATA_1 CODESEPARATOR TRUE", + remove: txscript.OP_CODESEPARATOR, + after: "NOP DATA_1 CODESEPARATOR TRUE", + }, + { + name: "invalid opcode", + before: "CAT", + remove: txscript.OP_CODESEPARATOR, + after: "CAT", + }, + { + name: "invalid length (insruction)", + before: "PUSHDATA1", + remove: txscript.OP_CODESEPARATOR, + err: txscript.ErrStackShortScript, + }, + { + name: "invalid length (data)", + before: "PUSHDATA1 0xff 0xfe", + remove: txscript.OP_CODESEPARATOR, + err: txscript.ErrStackShortScript, + }, } -} -type removeOpcodeByDataTest struct { - name string - before []byte - remove []byte - err error - after []byte -} - -var removeOpcodeByDataTests = []removeOpcodeByDataTest{ - { - name: "nothing to do", - before: []byte{txscript.OP_NOP}, - remove: []byte{1, 2, 3, 4}, - after: []byte{txscript.OP_NOP}, - }, - { - name: "simple case", - before: []byte{txscript.OP_DATA_4, 1, 2, 3, 4}, - remove: []byte{1, 2, 3, 4}, - after: []byte{}, - }, - { - name: "simple case (miss)", - before: []byte{txscript.OP_DATA_4, 1, 2, 3, 4}, - remove: []byte{1, 2, 3, 5}, - after: []byte{txscript.OP_DATA_4, 1, 2, 3, 4}, - }, - { - // padded to keep it canonical. - name: "simple case (pushdata1)", - before: append(append([]byte{txscript.OP_PUSHDATA1, 76}, - bytes.Repeat([]byte{0}, 72)...), []byte{1, 2, 3, 4}...), - remove: []byte{1, 2, 3, 4}, - after: []byte{}, - }, - { - name: "simple case (pushdata1 miss)", - before: append(append([]byte{txscript.OP_PUSHDATA1, 76}, - bytes.Repeat([]byte{0}, 72)...), []byte{1, 2, 3, 4}...), - remove: []byte{1, 2, 3, 5}, - after: append(append([]byte{txscript.OP_PUSHDATA1, 76}, - bytes.Repeat([]byte{0}, 72)...), []byte{1, 2, 3, 4}...), - }, - { - name: "simple case (pushdata1 miss noncanonical)", - before: []byte{txscript.OP_PUSHDATA1, 4, 1, 2, 3, 4}, - remove: []byte{1, 2, 3, 4}, - after: []byte{txscript.OP_PUSHDATA1, 4, 1, 2, 3, 4}, - }, - { - name: "simple case (pushdata2)", - before: append(append([]byte{txscript.OP_PUSHDATA2, 0, 1}, - bytes.Repeat([]byte{0}, 252)...), []byte{1, 2, 3, 4}...), - remove: []byte{1, 2, 3, 4}, - after: []byte{}, - }, - { - name: "simple case (pushdata2 miss)", - before: append(append([]byte{txscript.OP_PUSHDATA2, 0, 1}, - bytes.Repeat([]byte{0}, 252)...), []byte{1, 2, 3, 4}...), - remove: []byte{1, 2, 3, 4, 5}, - after: append(append([]byte{txscript.OP_PUSHDATA2, 0, 1}, - bytes.Repeat([]byte{0}, 252)...), []byte{1, 2, 3, 4}...), - }, - { - name: "simple case (pushdata2 miss noncanonical)", - before: []byte{txscript.OP_PUSHDATA2, 4, 0, 1, 2, 3, 4}, - remove: []byte{1, 2, 3, 4}, - after: []byte{txscript.OP_PUSHDATA2, 4, 0, 1, 2, 3, 4}, - }, - { - // This is padded to make the push canonical. - name: "simple case (pushdata4)", - before: append(append([]byte{txscript.OP_PUSHDATA4, 0, 0, 1, 0}, - bytes.Repeat([]byte{0}, 65532)...), []byte{1, 2, 3, 4}...), - remove: []byte{1, 2, 3, 4}, - after: []byte{}, - }, - { - name: "simple case (pushdata4 miss noncanonical)", - before: []byte{txscript.OP_PUSHDATA4, 4, 0, 0, 0, 1, 2, 3, 4}, - remove: []byte{1, 2, 3, 4}, - after: []byte{txscript.OP_PUSHDATA4, 4, 0, 0, 0, 1, 2, 3, 4}, - }, - { - // This is padded to make the push canonical. - name: "simple case (pushdata4 miss)", - before: append(append([]byte{txscript.OP_PUSHDATA4, 0, 0, 1, 0}, - bytes.Repeat([]byte{0}, 65532)...), []byte{1, 2, 3, 4}...), - remove: []byte{1, 2, 3, 4, 5}, - after: append(append([]byte{txscript.OP_PUSHDATA4, 0, 0, 1, 0}, - bytes.Repeat([]byte{0}, 65532)...), []byte{1, 2, 3, 4}...), - }, - { - name: "invalid opcode ", - before: []byte{txscript.OP_UNKNOWN187}, - remove: []byte{1, 2, 3, 4}, - after: []byte{txscript.OP_UNKNOWN187}, - }, - { - name: "invalid length (instruction)", - before: []byte{txscript.OP_PUSHDATA1}, - remove: []byte{1, 2, 3, 4}, - err: txscript.ErrStackShortScript, - }, - { - name: "invalid length (data)", - before: []byte{txscript.OP_PUSHDATA1, 255, 254}, - remove: []byte{1, 2, 3, 4}, - err: txscript.ErrStackShortScript, - }, -} - -func testRemoveOpcodeByData(t *testing.T, test *removeOpcodeByDataTest) { - result, err := txscript.TstRemoveOpcodeByData(test.before, - test.remove) - if test.err != nil { - if err != test.err { - t.Errorf("%s: got unexpected error. exp: \"%v\" "+ - "got: \"%v\"", test.name, test.err, err) + for _, test := range tests { + before := mustParseShortForm(test.before) + after := mustParseShortForm(test.after) + result, err := txscript.TstRemoveOpcode(before, test.remove) + if test.err != nil { + if err != test.err { + t.Errorf("%s: got unexpected error. exp: \"%v\" "+ + "got: \"%v\"", test.name, test.err, err) + } + return + } + if err != nil { + t.Errorf("%s: unexpected failure: \"%v\"", test.name, err) + return + } + if !bytes.Equal(after, result) { + t.Errorf("%s: value does not equal expected: exp: \"%v\""+ + " got: \"%v\"", test.name, after, result) } - return - } - if err != nil { - t.Errorf("%s: unexpected failure: \"%v\"", test.name, err) - return - } - if !bytes.Equal(test.after, result) { - t.Errorf("%s: value does not equal expected: exp: \"%v\""+ - " got: \"%v\"", test.name, test.after, result) } } -func TestRemoveOpcodeByDatas(t *testing.T) { +// TestRemoveOpcodeByData ensures that removing data carrying opcodes based on +// the data they contain works as expected. +func TestRemoveOpcodeByData(t *testing.T) { t.Parallel() - for i := range removeOpcodeByDataTests { - testRemoveOpcodeByData(t, &removeOpcodeByDataTests[i]) + tests := []struct { + name string + before []byte + remove []byte + err error + after []byte + }{ + { + name: "nothing to do", + before: []byte{txscript.OP_NOP}, + remove: []byte{1, 2, 3, 4}, + after: []byte{txscript.OP_NOP}, + }, + { + name: "simple case", + before: []byte{txscript.OP_DATA_4, 1, 2, 3, 4}, + remove: []byte{1, 2, 3, 4}, + after: nil, + }, + { + name: "simple case (miss)", + before: []byte{txscript.OP_DATA_4, 1, 2, 3, 4}, + remove: []byte{1, 2, 3, 5}, + after: []byte{txscript.OP_DATA_4, 1, 2, 3, 4}, + }, + { + // padded to keep it canonical. + name: "simple case (pushdata1)", + before: append(append([]byte{txscript.OP_PUSHDATA1, 76}, + bytes.Repeat([]byte{0}, 72)...), + []byte{1, 2, 3, 4}...), + remove: []byte{1, 2, 3, 4}, + after: nil, + }, + { + name: "simple case (pushdata1 miss)", + before: append(append([]byte{txscript.OP_PUSHDATA1, 76}, + bytes.Repeat([]byte{0}, 72)...), + []byte{1, 2, 3, 4}...), + remove: []byte{1, 2, 3, 5}, + after: append(append([]byte{txscript.OP_PUSHDATA1, 76}, + bytes.Repeat([]byte{0}, 72)...), + []byte{1, 2, 3, 4}...), + }, + { + name: "simple case (pushdata1 miss noncanonical)", + before: []byte{txscript.OP_PUSHDATA1, 4, 1, 2, 3, 4}, + remove: []byte{1, 2, 3, 4}, + after: []byte{txscript.OP_PUSHDATA1, 4, 1, 2, 3, 4}, + }, + { + name: "simple case (pushdata2)", + before: append(append([]byte{txscript.OP_PUSHDATA2, 0, 1}, + bytes.Repeat([]byte{0}, 252)...), + []byte{1, 2, 3, 4}...), + remove: []byte{1, 2, 3, 4}, + after: nil, + }, + { + name: "simple case (pushdata2 miss)", + before: append(append([]byte{txscript.OP_PUSHDATA2, 0, 1}, + bytes.Repeat([]byte{0}, 252)...), + []byte{1, 2, 3, 4}...), + remove: []byte{1, 2, 3, 4, 5}, + after: append(append([]byte{txscript.OP_PUSHDATA2, 0, 1}, + bytes.Repeat([]byte{0}, 252)...), + []byte{1, 2, 3, 4}...), + }, + { + name: "simple case (pushdata2 miss noncanonical)", + before: []byte{txscript.OP_PUSHDATA2, 4, 0, 1, 2, 3, 4}, + remove: []byte{1, 2, 3, 4}, + after: []byte{txscript.OP_PUSHDATA2, 4, 0, 1, 2, 3, 4}, + }, + { + // This is padded to make the push canonical. + name: "simple case (pushdata4)", + before: append(append([]byte{txscript.OP_PUSHDATA4, 0, 0, 1, 0}, + bytes.Repeat([]byte{0}, 65532)...), + []byte{1, 2, 3, 4}...), + remove: []byte{1, 2, 3, 4}, + after: nil, + }, + { + name: "simple case (pushdata4 miss noncanonical)", + before: []byte{txscript.OP_PUSHDATA4, 4, 0, 0, 0, 1, 2, 3, 4}, + remove: []byte{1, 2, 3, 4}, + after: []byte{txscript.OP_PUSHDATA4, 4, 0, 0, 0, 1, 2, 3, 4}, + }, + { + // This is padded to make the push canonical. + name: "simple case (pushdata4 miss)", + before: append(append([]byte{txscript.OP_PUSHDATA4, 0, 0, 1, 0}, + bytes.Repeat([]byte{0}, 65532)...), []byte{1, 2, 3, 4}...), + remove: []byte{1, 2, 3, 4, 5}, + after: append(append([]byte{txscript.OP_PUSHDATA4, 0, 0, 1, 0}, + bytes.Repeat([]byte{0}, 65532)...), []byte{1, 2, 3, 4}...), + }, + { + name: "invalid opcode ", + before: []byte{txscript.OP_UNKNOWN187}, + remove: []byte{1, 2, 3, 4}, + after: []byte{txscript.OP_UNKNOWN187}, + }, + { + name: "invalid length (instruction)", + before: []byte{txscript.OP_PUSHDATA1}, + remove: []byte{1, 2, 3, 4}, + err: txscript.ErrStackShortScript, + }, + { + name: "invalid length (data)", + before: []byte{txscript.OP_PUSHDATA1, 255, 254}, + remove: []byte{1, 2, 3, 4}, + err: txscript.ErrStackShortScript, + }, + } + + for _, test := range tests { + result, err := txscript.TstRemoveOpcodeByData(test.before, + test.remove) + if test.err != nil { + if err != test.err { + t.Errorf("%s: got unexpected error. exp: \"%v\" "+ + "got: \"%v\"", test.name, test.err, err) + } + return + } + if err != nil { + t.Errorf("%s: unexpected failure: \"%v\"", test.name, err) + return + } + if !bytes.Equal(test.after, result) { + t.Errorf("%s: value does not equal expected: exp: \"%v\""+ + " got: \"%v\"", test.name, test.after, result) + } } } -// Tests for the script type logic - +// TestIsPayToScriptHash ensures the IsPayToScriptHash function returns the +// expected results for all the scripts in scriptClassTests. func TestIsPayToScriptHash(t *testing.T) { t.Parallel() - for _, test := range scriptTypeTests { - shouldBe := (test.scripttype == txscript.ScriptHashTy) - p2sh := txscript.IsPayToScriptHash(test.script) + for _, test := range scriptClassTests { + script := mustParseShortForm(test.script) + shouldBe := (test.class == txscript.ScriptHashTy) + p2sh := txscript.IsPayToScriptHash(script) if p2sh != shouldBe { t.Errorf("%s: epxected p2sh %v, got %v", test.name, shouldBe, p2sh) @@ -1985,50 +422,51 @@ func TestIsPayToScriptHash(t *testing.T) { } } +// TestHasCanonicalPushes ensures the canonicalPush function properly determines +// what is considered a canonical push for the purposes of removeOpcodeByData. func TestHasCanonicalPushes(t *testing.T) { t.Parallel() tests := []struct { name string - script []byte + script string expected bool }{ { name: "does not parse", - script: []byte{ - 0x04, 0x67, 0x08, 0xaf, 0xdb, 0x0f, 0xe5, 0x54, - 0x82, 0x71, 0x96, 0x7f, 0x1a, 0x67, 0x13, 0x0b, - 0x71, 0x05, 0xcd, 0x6a, 0x82, 0x8e, 0x03, 0x90, - 0x9a, 0x67, 0x96, 0x2e, 0x0e, 0xa1, 0xf6, 0x1d, - }, + script: "0x046708afdb0fe5548271967f1a67130b7105cd6a82" + + "8e03909a67962e0ea1f61d", expected: false, }, { name: "non-canonical push", - script: []byte{txscript.OP_PUSHDATA1, 4, 1, 2, 3, 4}, + script: "PUSHDATA1 0x04 0x01020304", expected: false, }, } for i, test := range tests { - pops, err := txscript.TstParseScript(test.script) + script := mustParseShortForm(test.script) + pops, err := txscript.TstParseScript(script) if err != nil { if test.expected { - t.Errorf("StandardPushesTests #%d failed to TstParseScript: %v", i, err) + t.Errorf("TstParseScript #%d failed: %v", i, err) } continue } for _, pop := range pops { if txscript.TstHasCanonicalPushes(pop) != test.expected { - t.Errorf("TstHasCanonicalPushes #%d (%s) wrong result\n"+ - "got: %v\nwant: %v", i, test.name, true, - test.expected) + t.Errorf("TstHasCanonicalPushes: #%d (%s) "+ + "wrong result\ngot: %v\nwant: %v", i, + test.name, true, test.expected) break } } } } +// TestIsPushOnlyScript ensures the IsPushOnlyScript function returns the +// expected results. func TestIsPushOnlyScript(t *testing.T) { t.Parallel() @@ -2038,66 +476,13 @@ func TestIsPushOnlyScript(t *testing.T) { expected bool }{ name: "does not parse", - script: []byte{ - 0x04, 0x67, 0x08, 0xaf, 0xdb, 0x0f, 0xe5, 0x54, - 0x82, 0x71, 0x96, 0x7f, 0x1a, 0x67, 0x13, 0x0b, - 0x71, 0x05, 0xcd, 0x6a, 0x82, 0x8e, 0x03, 0x90, - 0x9a, 0x67, 0x96, 0x2e, 0x0e, 0xa1, 0xf6, 0x1d, - }, + script: mustParseShortForm("0x046708afdb0fe5548271967f1a67130" + + "b7105cd6a828e03909a67962e0ea1f61d"), expected: false, } if txscript.IsPushOnlyScript(test.script) != test.expected { - t.Errorf("IsPushOnlyScript (%s) wrong result\n"+ - "got: %v\nwant: %v", test.name, true, - test.expected) - } -} - -func TestInvalidFlagCombinations(t *testing.T) { - t.Parallel() - - tests := []txscript.ScriptFlags{ - txscript.ScriptVerifyCleanStack, - } - - // tx with almost empty scripts. - tx := &wire.MsgTx{ - Version: 1, - TxIn: []*wire.TxIn{ - { - PreviousOutPoint: wire.OutPoint{ - Hash: wire.ShaHash([32]byte{ - 0xc9, 0x97, 0xa5, 0xe5, - 0x6e, 0x10, 0x41, 0x02, - 0xfa, 0x20, 0x9c, 0x6a, - 0x85, 0x2d, 0xd9, 0x06, - 0x60, 0xa2, 0x0b, 0x2d, - 0x9c, 0x35, 0x24, 0x23, - 0xed, 0xce, 0x25, 0x85, - 0x7f, 0xcd, 0x37, 0x04, - }), - Index: 0, - }, - SignatureScript: []uint8{txscript.OP_NOP}, - Sequence: 4294967295, - }, - }, - TxOut: []*wire.TxOut{ - { - Value: 1000000000, - PkScript: []byte{}, - }, - }, - LockTime: 0, - } - pkScript := []byte{txscript.OP_NOP} - - for i, test := range tests { - _, err := txscript.NewEngine(pkScript, tx, 0, test) - if err != txscript.ErrInvalidFlags { - t.Fatalf("TestInvalidFlagCombinations #%d unexpected "+ - "error: %v", i, err) - } + t.Errorf("IsPushOnlyScript (%s) wrong result\ngot: %v\nwant: "+ + "%v", test.name, true, test.expected) } } diff --git a/txscript/scriptbuilder_test.go b/txscript/scriptbuilder_test.go index b3f1cd75..677c0cf0 100644 --- a/txscript/scriptbuilder_test.go +++ b/txscript/scriptbuilder_test.go @@ -141,7 +141,7 @@ func TestScriptBuilderAddData(t *testing.T) { useFull bool // use AddFullData instead of AddData. }{ // BIP0062: Pushing an empty byte sequence must use OP_0. - {name: "push empty byte sequence", data: []byte{}, expected: []byte{txscript.OP_0}}, + {name: "push empty byte sequence", data: nil, expected: []byte{txscript.OP_0}}, {name: "push 1 byte 0x00", data: []byte{0x00}, expected: []byte{txscript.OP_0}}, // BIP0062: Pushing a 1-byte sequence of byte 0x01 through 0x10 must use OP_n. @@ -213,17 +213,17 @@ func TestScriptBuilderAddData(t *testing.T) { { name: "push data len 521", data: bytes.Repeat([]byte{0x49}, 521), - expected: []byte{}, + expected: nil, }, { name: "push data len 32767 (canonical)", data: bytes.Repeat([]byte{0x49}, 32767), - expected: []byte{}, + expected: nil, }, { name: "push data len 65536 (canonical)", data: bytes.Repeat([]byte{0x49}, 65536), - expected: []byte{}, + expected: nil, }, // Additional tests for the PushFullData function that diff --git a/txscript/sign_test.go b/txscript/sign_test.go index ccd044db..1da4cba5 100644 --- a/txscript/sign_test.go +++ b/txscript/sign_test.go @@ -78,7 +78,7 @@ func signAndCheck(msg string, tx *wire.MsgTx, idx int, pkScript []byte, previousScript []byte) error { sigScript, err := txscript.SignTxOutput(&chaincfg.TestNet3Params, tx, - idx, pkScript, hashType, kdb, sdb, []byte{}) + idx, pkScript, hashType, kdb, sdb, nil) if err != nil { return fmt.Errorf("failed to sign output %s: %v", msg, err) } @@ -170,7 +170,7 @@ func TestSignTxOutput(t *testing.T) { if err := signAndCheck(msg, tx, i, pkScript, hashType, mkGetKey(map[string]addressToKey{ address.EncodeAddress(): {key, false}, - }), mkGetScript(nil), []byte{}); err != nil { + }), mkGetScript(nil), nil); err != nil { t.Error(err) break } @@ -208,7 +208,7 @@ func TestSignTxOutput(t *testing.T) { &chaincfg.TestNet3Params, tx, i, pkScript, hashType, mkGetKey(map[string]addressToKey{ address.EncodeAddress(): {key, false}, - }), mkGetScript(nil), []byte{}) + }), mkGetScript(nil), nil) if err != nil { t.Errorf("failed to sign output %s: %v", msg, err) @@ -268,7 +268,7 @@ func TestSignTxOutput(t *testing.T) { if err := signAndCheck(msg, tx, i, pkScript, hashType, mkGetKey(map[string]addressToKey{ address.EncodeAddress(): {key, true}, - }), mkGetScript(nil), []byte{}); err != nil { + }), mkGetScript(nil), nil); err != nil { t.Error(err) break } @@ -307,7 +307,7 @@ func TestSignTxOutput(t *testing.T) { &chaincfg.TestNet3Params, tx, i, pkScript, hashType, mkGetKey(map[string]addressToKey{ address.EncodeAddress(): {key, true}, - }), mkGetScript(nil), []byte{}) + }), mkGetScript(nil), nil) if err != nil { t.Errorf("failed to sign output %s: %v", msg, err) @@ -367,7 +367,7 @@ func TestSignTxOutput(t *testing.T) { if err := signAndCheck(msg, tx, i, pkScript, hashType, mkGetKey(map[string]addressToKey{ address.EncodeAddress(): {key, false}, - }), mkGetScript(nil), []byte{}); err != nil { + }), mkGetScript(nil), nil); err != nil { t.Error(err) break } @@ -406,7 +406,7 @@ func TestSignTxOutput(t *testing.T) { &chaincfg.TestNet3Params, tx, i, pkScript, hashType, mkGetKey(map[string]addressToKey{ address.EncodeAddress(): {key, false}, - }), mkGetScript(nil), []byte{}) + }), mkGetScript(nil), nil) if err != nil { t.Errorf("failed to sign output %s: %v", msg, err) @@ -466,7 +466,7 @@ func TestSignTxOutput(t *testing.T) { if err := signAndCheck(msg, tx, i, pkScript, hashType, mkGetKey(map[string]addressToKey{ address.EncodeAddress(): {key, true}, - }), mkGetScript(nil), []byte{}); err != nil { + }), mkGetScript(nil), nil); err != nil { t.Error(err) break } @@ -505,7 +505,7 @@ func TestSignTxOutput(t *testing.T) { &chaincfg.TestNet3Params, tx, i, pkScript, hashType, mkGetKey(map[string]addressToKey{ address.EncodeAddress(): {key, true}, - }), mkGetScript(nil), []byte{}) + }), mkGetScript(nil), nil) if err != nil { t.Errorf("failed to sign output %s: %v", msg, err) @@ -585,7 +585,7 @@ func TestSignTxOutput(t *testing.T) { address.EncodeAddress(): {key, false}, }), mkGetScript(map[string][]byte{ scriptAddr.EncodeAddress(): pkScript, - }), []byte{}); err != nil { + }), nil); err != nil { t.Error(err) break } @@ -642,7 +642,7 @@ func TestSignTxOutput(t *testing.T) { address.EncodeAddress(): {key, false}, }), mkGetScript(map[string][]byte{ scriptAddr.EncodeAddress(): pkScript, - }), []byte{}) + }), nil) if err != nil { t.Errorf("failed to sign output %s: %v", msg, err) @@ -657,7 +657,7 @@ func TestSignTxOutput(t *testing.T) { address.EncodeAddress(): {key, false}, }), mkGetScript(map[string][]byte{ scriptAddr.EncodeAddress(): pkScript, - }), []byte{}) + }), nil) if err != nil { t.Errorf("failed to sign output %s a "+ "second time: %v", msg, err) @@ -723,7 +723,7 @@ func TestSignTxOutput(t *testing.T) { address.EncodeAddress(): {key, true}, }), mkGetScript(map[string][]byte{ scriptAddr.EncodeAddress(): pkScript, - }), []byte{}); err != nil { + }), nil); err != nil { t.Error(err) break } @@ -780,7 +780,7 @@ func TestSignTxOutput(t *testing.T) { address.EncodeAddress(): {key, true}, }), mkGetScript(map[string][]byte{ scriptAddr.EncodeAddress(): pkScript, - }), []byte{}) + }), nil) if err != nil { t.Errorf("failed to sign output %s: %v", msg, err) @@ -795,7 +795,7 @@ func TestSignTxOutput(t *testing.T) { address.EncodeAddress(): {key, true}, }), mkGetScript(map[string][]byte{ scriptAddr.EncodeAddress(): pkScript, - }), []byte{}) + }), nil) if err != nil { t.Errorf("failed to sign output %s a "+ "second time: %v", msg, err) @@ -861,7 +861,7 @@ func TestSignTxOutput(t *testing.T) { address.EncodeAddress(): {key, false}, }), mkGetScript(map[string][]byte{ scriptAddr.EncodeAddress(): pkScript, - }), []byte{}); err != nil { + }), nil); err != nil { t.Error(err) break } @@ -918,7 +918,7 @@ func TestSignTxOutput(t *testing.T) { address.EncodeAddress(): {key, false}, }), mkGetScript(map[string][]byte{ scriptAddr.EncodeAddress(): pkScript, - }), []byte{}) + }), nil) if err != nil { t.Errorf("failed to sign output %s: %v", msg, err) @@ -933,7 +933,7 @@ func TestSignTxOutput(t *testing.T) { address.EncodeAddress(): {key, false}, }), mkGetScript(map[string][]byte{ scriptAddr.EncodeAddress(): pkScript, - }), []byte{}) + }), nil) if err != nil { t.Errorf("failed to sign output %s a "+ "second time: %v", msg, err) @@ -999,7 +999,7 @@ func TestSignTxOutput(t *testing.T) { address.EncodeAddress(): {key, true}, }), mkGetScript(map[string][]byte{ scriptAddr.EncodeAddress(): pkScript, - }), []byte{}); err != nil { + }), nil); err != nil { t.Error(err) break } @@ -1056,7 +1056,7 @@ func TestSignTxOutput(t *testing.T) { address.EncodeAddress(): {key, true}, }), mkGetScript(map[string][]byte{ scriptAddr.EncodeAddress(): pkScript, - }), []byte{}) + }), nil) if err != nil { t.Errorf("failed to sign output %s: %v", msg, err) @@ -1071,7 +1071,7 @@ func TestSignTxOutput(t *testing.T) { address.EncodeAddress(): {key, true}, }), mkGetScript(map[string][]byte{ scriptAddr.EncodeAddress(): pkScript, - }), []byte{}) + }), nil) if err != nil { t.Errorf("failed to sign output %s a "+ "second time: %v", msg, err) @@ -1157,7 +1157,7 @@ func TestSignTxOutput(t *testing.T) { address2.EncodeAddress(): {key2, true}, }), mkGetScript(map[string][]byte{ scriptAddr.EncodeAddress(): pkScript, - }), []byte{}); err != nil { + }), nil); err != nil { t.Error(err) break } @@ -1233,7 +1233,7 @@ func TestSignTxOutput(t *testing.T) { address1.EncodeAddress(): {key1, true}, }), mkGetScript(map[string][]byte{ scriptAddr.EncodeAddress(): pkScript, - }), []byte{}) + }), nil) if err != nil { t.Errorf("failed to sign output %s: %v", msg, err) @@ -1340,7 +1340,7 @@ func TestSignTxOutput(t *testing.T) { address1.EncodeAddress(): {key1, true}, }), mkGetScript(map[string][]byte{ scriptAddr.EncodeAddress(): pkScript, - }), []byte{}) + }), nil) if err != nil { t.Errorf("failed to sign output %s: %v", msg, err) diff --git a/txscript/stack_test.go b/txscript/stack_test.go index 72e31b11..7b9902e3 100644 --- a/txscript/stack_test.go +++ b/txscript/stack_test.go @@ -39,7 +39,7 @@ func TestStack(t *testing.T) { return err }, ErrStackUnderflow, - [][]byte{}, + nil, }, { "peek underflow (int)", @@ -49,7 +49,7 @@ func TestStack(t *testing.T) { return err }, ErrStackUnderflow, - [][]byte{}, + nil, }, { "peek underflow (bool)", @@ -59,7 +59,7 @@ func TestStack(t *testing.T) { return err }, ErrStackUnderflow, - [][]byte{}, + nil, }, { "pop", @@ -106,7 +106,7 @@ func TestStack(t *testing.T) { return nil }, nil, - [][]byte{}, + nil, }, { "pop underflow", @@ -121,7 +121,7 @@ func TestStack(t *testing.T) { return nil }, ErrStackUnderflow, - [][]byte{}, + nil, }, { "pop bool", @@ -138,7 +138,7 @@ func TestStack(t *testing.T) { return nil }, nil, - [][]byte{}, + nil, }, { "pop bool", @@ -155,11 +155,11 @@ func TestStack(t *testing.T) { return nil }, nil, - [][]byte{}, + nil, }, { "pop bool", - [][]byte{}, + nil, func(s *stack) error { _, err := s.PopBool() if err != nil { @@ -169,7 +169,7 @@ func TestStack(t *testing.T) { return nil }, ErrStackUnderflow, - [][]byte{}, + nil, }, { "popInt 0", @@ -185,7 +185,7 @@ func TestStack(t *testing.T) { return nil }, nil, - [][]byte{}, + nil, }, { "popInt -0", @@ -201,7 +201,7 @@ func TestStack(t *testing.T) { return nil }, nil, - [][]byte{}, + nil, }, { "popInt 1", @@ -217,7 +217,7 @@ func TestStack(t *testing.T) { return nil }, nil, - [][]byte{}, + nil, }, { "popInt 1 leading 0", @@ -234,7 +234,7 @@ func TestStack(t *testing.T) { return nil }, nil, - [][]byte{}, + nil, }, { "popInt -1", @@ -250,7 +250,7 @@ func TestStack(t *testing.T) { return nil }, nil, - [][]byte{}, + nil, }, { "popInt -1 leading 0", @@ -267,7 +267,7 @@ func TestStack(t *testing.T) { return nil }, nil, - [][]byte{}, + nil, }, // Triggers the multibyte case in asInt { @@ -285,7 +285,7 @@ func TestStack(t *testing.T) { return nil }, nil, - [][]byte{}, + nil, }, // Confirm that the asInt code doesn't modify the base data. { @@ -307,7 +307,7 @@ func TestStack(t *testing.T) { }, { "PushInt 0", - [][]byte{}, + nil, func(s *stack) error { s.PushInt(scriptNum(0)) return nil @@ -317,7 +317,7 @@ func TestStack(t *testing.T) { }, { "PushInt 1", - [][]byte{}, + nil, func(s *stack) error { s.PushInt(scriptNum(1)) return nil @@ -327,7 +327,7 @@ func TestStack(t *testing.T) { }, { "PushInt -1", - [][]byte{}, + nil, func(s *stack) error { s.PushInt(scriptNum(-1)) return nil @@ -337,7 +337,7 @@ func TestStack(t *testing.T) { }, { "PushInt two bytes", - [][]byte{}, + nil, func(s *stack) error { s.PushInt(scriptNum(256)) return nil @@ -348,7 +348,7 @@ func TestStack(t *testing.T) { }, { "PushInt leading zeros", - [][]byte{}, + nil, func(s *stack) error { // this will have the highbit set s.PushInt(scriptNum(128)) @@ -411,7 +411,7 @@ func TestStack(t *testing.T) { return nil }, ErrStackInvalidArgs, - [][]byte{}, + nil, }, { "dup-1", @@ -425,7 +425,7 @@ func TestStack(t *testing.T) { return nil }, ErrStackInvalidArgs, - [][]byte{}, + nil, }, { "dup too much", @@ -439,7 +439,7 @@ func TestStack(t *testing.T) { return nil }, ErrStackUnderflow, - [][]byte{}, + nil, }, { "dup-1", @@ -453,11 +453,11 @@ func TestStack(t *testing.T) { return nil }, ErrStackInvalidArgs, - [][]byte{}, + nil, }, { "PushBool true", - [][]byte{}, + nil, func(s *stack) error { s.PushBool(true) @@ -468,7 +468,7 @@ func TestStack(t *testing.T) { }, { "PushBool false", - [][]byte{}, + nil, func(s *stack) error { s.PushBool(false) @@ -479,7 +479,7 @@ func TestStack(t *testing.T) { }, { "PushBool PopBool", - [][]byte{}, + nil, func(s *stack) error { s.PushBool(true) val, err := s.PopBool() @@ -493,11 +493,11 @@ func TestStack(t *testing.T) { return nil }, nil, - [][]byte{}, + nil, }, { "PushBool PopBool 2", - [][]byte{}, + nil, func(s *stack) error { s.PushBool(false) val, err := s.PopBool() @@ -511,11 +511,11 @@ func TestStack(t *testing.T) { return nil }, nil, - [][]byte{}, + nil, }, { "PushInt PopBool", - [][]byte{}, + nil, func(s *stack) error { s.PushInt(scriptNum(1)) val, err := s.PopBool() @@ -529,11 +529,11 @@ func TestStack(t *testing.T) { return nil }, nil, - [][]byte{}, + nil, }, { "PushInt PopBool 2", - [][]byte{}, + nil, func(s *stack) error { s.PushInt(scriptNum(0)) val, err := s.PopBool() @@ -547,11 +547,11 @@ func TestStack(t *testing.T) { return nil }, nil, - [][]byte{}, + nil, }, { "PushInt PopBool 2", - [][]byte{}, + nil, func(s *stack) error { s.PushInt(scriptNum(0)) val, err := s.PopBool() @@ -565,7 +565,7 @@ func TestStack(t *testing.T) { return nil }, nil, - [][]byte{}, + nil, }, { "Nip top", @@ -620,16 +620,16 @@ func TestStack(t *testing.T) { return s.Tuck() }, ErrStackUnderflow, - [][]byte{}, + nil, }, { "all tucked up", - [][]byte{}, // too few arguments for tuck + nil, // too few arguments for tuck func(s *stack) error { return s.Tuck() }, ErrStackUnderflow, - [][]byte{}, + nil, }, { "drop 1", @@ -665,7 +665,7 @@ func TestStack(t *testing.T) { return s.DropN(4) }, nil, - [][]byte{}, + nil, }, { "drop 4/5", @@ -674,7 +674,7 @@ func TestStack(t *testing.T) { return s.DropN(5) }, ErrStackUnderflow, - [][]byte{}, + nil, }, { "drop invalid", @@ -683,7 +683,7 @@ func TestStack(t *testing.T) { return s.DropN(0) }, ErrStackInvalidArgs, - [][]byte{}, + nil, }, { "Rot1", @@ -710,7 +710,7 @@ func TestStack(t *testing.T) { return s.RotN(1) }, ErrStackUnderflow, - [][]byte{}, + nil, }, { "Rot0", @@ -719,7 +719,7 @@ func TestStack(t *testing.T) { return s.RotN(0) }, ErrStackInvalidArgs, - [][]byte{}, + nil, }, { "Swap1", @@ -746,7 +746,7 @@ func TestStack(t *testing.T) { return s.SwapN(1) }, ErrStackUnderflow, - [][]byte{}, + nil, }, { "Swap0", @@ -755,7 +755,7 @@ func TestStack(t *testing.T) { return s.SwapN(0) }, ErrStackInvalidArgs, - [][]byte{}, + nil, }, { "Over1", @@ -782,7 +782,7 @@ func TestStack(t *testing.T) { return s.OverN(1) }, ErrStackUnderflow, - [][]byte{}, + nil, }, { "Over0", @@ -791,7 +791,7 @@ func TestStack(t *testing.T) { return s.OverN(0) }, ErrStackInvalidArgs, - [][]byte{}, + nil, }, { "Pick1", @@ -818,7 +818,7 @@ func TestStack(t *testing.T) { return s.PickN(1) }, ErrStackUnderflow, - [][]byte{}, + nil, }, { "Roll1", @@ -845,7 +845,7 @@ func TestStack(t *testing.T) { return s.RollN(1) }, ErrStackUnderflow, - [][]byte{}, + nil, }, { "Peek bool", @@ -921,7 +921,7 @@ func TestStack(t *testing.T) { }, { "pop int", - [][]byte{}, + nil, func(s *stack) error { s.PushInt(scriptNum(1)) // Peek int is otherwise pretty well tested, @@ -936,11 +936,11 @@ func TestStack(t *testing.T) { return nil }, nil, - [][]byte{}, + nil, }, { "pop empty", - [][]byte{}, + nil, func(s *stack) error { // Peek int is otherwise pretty well tested, // just check it works. @@ -948,7 +948,7 @@ func TestStack(t *testing.T) { return err }, ErrStackUnderflow, - [][]byte{}, + nil, }, } diff --git a/txscript/standard.go b/txscript/standard.go index 7bf7d2d4..71349248 100644 --- a/txscript/standard.go +++ b/txscript/standard.go @@ -372,7 +372,7 @@ func PushedData(script []byte) ([][]byte, error) { if pop.data != nil { data = append(data, pop.data) } else if pop.opcode.value == OP_0 { - data = append(data, []byte{}) + data = append(data, nil) } } return data, nil diff --git a/txscript/standard_test.go b/txscript/standard_test.go index 57fde9b5..dafd3560 100644 --- a/txscript/standard_test.go +++ b/txscript/standard_test.go @@ -1,6 +1,7 @@ // Copyright (c) 2013-2015 The btcsuite developers // Use of this source code is governed by an ISC // license that can be found in the LICENSE file. + package txscript_test import ( @@ -27,6 +28,20 @@ func decodeHex(hexStr string) []byte { return b } +// mustParseShortForm parses the passed short form script and returns the +// resulting bytes. It panics if an error occurs. This is only used in the +// tests as a helper since the only way it can fail is if there is an error in +// the test source code. +func mustParseShortForm(script string) []byte { + s, err := parseShortForm(script) + if err != nil { + panic("invalid short form script in test source: err " + + err.Error() + ", script: " + script) + } + + return s +} + // newAddressPubKey returns a new btcutil.AddressPubKey from the provided // serialized public key. It panics if an error occurs. This is only used in // the tests as a helper since the only way it can fail is if there is an error @@ -71,6 +86,8 @@ func newAddressScriptHash(scriptHash []byte) btcutil.Address { // TestExtractPkScriptAddrs ensures that extracting the type, addresses, and // number of required signatures from PkScripts works as intended. func TestExtractPkScriptAddrs(t *testing.T) { + t.Parallel() + tests := []struct { name string script []byte @@ -368,103 +385,48 @@ func TestExtractPkScriptAddrs(t *testing.T) { } } -type scriptInfoTest struct { - name string - sigScript []byte - pkScript []byte - bip16 bool - scriptInfo txscript.ScriptInfo - scriptInfoErr error -} - -func TestScriptInfo(t *testing.T) { +// TestCalcScriptInfo ensures the CalcScriptInfo provides the expected results +// for various valid and invalid script pairs. +func TestCalcScriptInfo(t *testing.T) { t.Parallel() - for _, test := range txTests { - si, err := txscript.CalcScriptInfo( - test.tx.TxIn[test.idx].SignatureScript, - test.pkScript, test.bip16) - if err != nil { - if err != test.scriptInfoErr { - t.Errorf("scriptinfo test \"%s\": got \"%v\""+ - "expected \"%v\"", test.name, err, - test.scriptInfoErr) - } - continue - } - if test.scriptInfoErr != nil { - t.Errorf("%s: succeeded when expecting \"%v\"", - test.name, test.scriptInfoErr) - continue - } - if *si != test.scriptInfo { - t.Errorf("%s: scriptinfo doesn't match expected. "+ - "got: \"%v\" expected \"%v\"", test.name, - *si, test.scriptInfo) - continue - } - } - - extraTests := []scriptInfoTest{ + tests := []struct { + name string + sigScript string + pkScript string + bip16 bool + scriptInfo txscript.ScriptInfo + scriptInfoErr error + }{ { // Invented scripts, the hashes do not match + // Truncated version of test below: name: "pkscript doesn't parse", - sigScript: []byte{txscript.OP_TRUE, - txscript.OP_DATA_1, 81, - txscript.OP_DATA_8, - txscript.OP_2DUP, txscript.OP_EQUAL, - txscript.OP_NOT, txscript.OP_VERIFY, - txscript.OP_ABS, txscript.OP_SWAP, - txscript.OP_ABS, txscript.OP_EQUAL, - }, - // truncated version of test below: - pkScript: []byte{txscript.OP_HASH160, - txscript.OP_DATA_20, - 0xfe, 0x44, 0x10, 0x65, 0xb6, 0x53, 0x22, 0x31, - 0xde, 0x2f, 0xac, 0x56, 0x31, 0x52, 0x20, 0x5e, - 0xc4, 0xf5, 0x9c, - }, + sigScript: "1 81 DATA_8 2DUP EQUAL NOT VERIFY ABS " + + "SWAP ABS EQUAL", + pkScript: "HASH160 DATA_20 0xfe441065b6532231de2fac56" + + "3152205ec4f59c", bip16: true, scriptInfoErr: txscript.ErrStackShortScript, }, { name: "sigScript doesn't parse", // Truncated version of p2sh script below. - sigScript: []byte{txscript.OP_TRUE, - txscript.OP_DATA_1, 81, - txscript.OP_DATA_8, - txscript.OP_2DUP, txscript.OP_EQUAL, - txscript.OP_NOT, txscript.OP_VERIFY, - txscript.OP_ABS, txscript.OP_SWAP, - txscript.OP_ABS, - }, - pkScript: []byte{txscript.OP_HASH160, - txscript.OP_DATA_20, - 0xfe, 0x44, 0x10, 0x65, 0xb6, 0x53, 0x22, 0x31, - 0xde, 0x2f, 0xac, 0x56, 0x31, 0x52, 0x20, 0x5e, - 0xc4, 0xf5, 0x9c, 0x74, txscript.OP_EQUAL, - }, + sigScript: "1 81 DATA_8 2DUP EQUAL NOT VERIFY ABS " + + "SWAP ABS", + pkScript: "HASH160 DATA_20 0xfe441065b6532231de2fac56" + + "3152205ec4f59c74 EQUAL", bip16: true, scriptInfoErr: txscript.ErrStackShortScript, }, { // Invented scripts, the hashes do not match name: "p2sh standard script", - sigScript: []byte{txscript.OP_TRUE, - txscript.OP_DATA_1, 81, - txscript.OP_DATA_25, - txscript.OP_DUP, txscript.OP_HASH160, - txscript.OP_DATA_20, 0x1, 0x2, 0x3, 0x4, 0x5, - 0x6, 0x7, 0x8, 0x9, 0xa, 0xb, 0xc, 0xd, 0xe, - 0xf, 0x10, 0x11, 0x12, 0x13, 0x14, - txscript.OP_EQUALVERIFY, txscript.OP_CHECKSIG, - }, - pkScript: []byte{txscript.OP_HASH160, - txscript.OP_DATA_20, - 0xfe, 0x44, 0x10, 0x65, 0xb6, 0x53, 0x22, 0x31, - 0xde, 0x2f, 0xac, 0x56, 0x31, 0x52, 0x20, 0x5e, - 0xc4, 0xf5, 0x9c, 0x74, txscript.OP_EQUAL, - }, + sigScript: "1 81 DATA_25 DUP HASH160 DATA_20 0x010203" + + "0405060708090a0b0c0d0e0f1011121314 EQUALVERIFY " + + "CHECKSIG", + pkScript: "HASH160 DATA_20 0xfe441065b6532231de2fac56" + + "3152205ec4f59c74 EQUAL", bip16: true, scriptInfo: txscript.ScriptInfo{ PkScriptClass: txscript.ScriptHashTy, @@ -477,20 +439,10 @@ func TestScriptInfo(t *testing.T) { // from 567a53d1ce19ce3d07711885168484439965501536d0d0294c5d46d46c10e53b // from the blockchain. name: "p2sh nonstandard script", - sigScript: []byte{txscript.OP_TRUE, - txscript.OP_DATA_1, 81, - txscript.OP_DATA_8, - txscript.OP_2DUP, txscript.OP_EQUAL, - txscript.OP_NOT, txscript.OP_VERIFY, - txscript.OP_ABS, txscript.OP_SWAP, - txscript.OP_ABS, txscript.OP_EQUAL, - }, - pkScript: []byte{txscript.OP_HASH160, - txscript.OP_DATA_20, - 0xfe, 0x44, 0x10, 0x65, 0xb6, 0x53, 0x22, 0x31, - 0xde, 0x2f, 0xac, 0x56, 0x31, 0x52, 0x20, 0x5e, - 0xc4, 0xf5, 0x9c, 0x74, txscript.OP_EQUAL, - }, + sigScript: "1 81 DATA_8 2DUP EQUAL NOT VERIFY ABS " + + "SWAP ABS EQUAL", + pkScript: "HASH160 DATA_20 0xfe441065b6532231de2fac56" + + "3152205ec4f59c74 EQUAL", bip16: true, scriptInfo: txscript.ScriptInfo{ PkScriptClass: txscript.ScriptHashTy, @@ -502,28 +454,15 @@ func TestScriptInfo(t *testing.T) { { // Script is invented, numbers all fake. name: "multisig script", - sigScript: []byte{txscript.OP_TRUE, - txscript.OP_TRUE, txscript.OP_TRUE, - txscript.OP_0, // Extra arg for OP_CHECKMULTISIG bug - }, - pkScript: []byte{ - txscript.OP_3, txscript.OP_DATA_33, - 0x1, 0x2, 0x3, 0x4, 0x5, 0x6, 0x7, 0x8, 0x9, - 0xa, 0xb, 0xc, 0xd, 0xe, 0xf, 0x10, 0x11, 0x12, - 0x13, 0x14, 0x15, 0x16, 0x17, 0x18, 0x19, 0x1a, - 0x1b, 0x1c, 0x1d, 0x1e, 0x1f, 0x20, 0x21, - txscript.OP_DATA_33, - 0x1, 0x2, 0x3, 0x4, 0x5, 0x6, 0x7, 0x8, 0x9, - 0xa, 0xb, 0xc, 0xd, 0xe, 0xf, 0x10, 0x11, 0x12, - 0x13, 0x14, 0x15, 0x16, 0x17, 0x18, 0x19, 0x1a, - 0x1b, 0x1c, 0x1d, 0x1e, 0x1f, 0x20, 0x21, - txscript.OP_DATA_33, - 0x1, 0x2, 0x3, 0x4, 0x5, 0x6, 0x7, 0x8, 0x9, - 0xa, 0xb, 0xc, 0xd, 0xe, 0xf, 0x10, 0x11, 0x12, - 0x13, 0x14, 0x15, 0x16, 0x17, 0x18, 0x19, 0x1a, - 0x1b, 0x1c, 0x1d, 0x1e, 0x1f, 0x20, 0x21, - txscript.OP_3, txscript.OP_CHECKMULTISIG, - }, + // Extra 0 arg on the end for OP_CHECKMULTISIG bug. + sigScript: "1 1 1 0", + pkScript: "3 " + + "DATA_33 0x0102030405060708090a0b0c0d0e0f1011" + + "12131415161718191a1b1c1d1e1f2021 DATA_33 " + + "0x0102030405060708090a0b0c0d0e0f101112131415" + + "161718191a1b1c1d1e1f2021 DATA_33 0x010203040" + + "5060708090a0b0c0d0e0f101112131415161718191a1" + + "b1c1d1e1f2021 3 CHECKMULTISIG", bip16: true, scriptInfo: txscript.ScriptInfo{ PkScriptClass: txscript.MultiSigTy, @@ -534,9 +473,11 @@ func TestScriptInfo(t *testing.T) { }, } - for _, test := range extraTests { - si, err := txscript.CalcScriptInfo(test.sigScript, - test.pkScript, test.bip16) + for _, test := range tests { + sigScript := mustParseShortForm(test.sigScript) + pkScript := mustParseShortForm(test.pkScript) + si, err := txscript.CalcScriptInfo(sigScript, pkScript, + test.bip16) if err != nil { if err != test.scriptInfoErr { t.Errorf("scriptinfo test \"%s\": got \"%v\""+ @@ -557,7 +498,6 @@ func TestScriptInfo(t *testing.T) { continue } } - } // bogusAddress implements the btcutil.Address interface so the tests can ensure @@ -573,7 +513,7 @@ func (b *bogusAddress) EncodeAddress() string { // ScriptAddress simply returns an empty byte slice. It exists to satsify the // btcutil.Address interface. func (b *bogusAddress) ScriptAddress() []byte { - return []byte{} + return nil } // IsForNet lies blatantly to satisfy the btcutil.Address interface. @@ -587,14 +527,14 @@ func (b *bogusAddress) String() string { return "" } +// TestPayToAddrScript ensures the PayToAddrScript function generates the +// correct scripts for the various types of addresses. func TestPayToAddrScript(t *testing.T) { t.Parallel() // 1MirQ9bwyQcGVJPwKUgapu5ouK2E2Ey4gX - p2pkhMain, err := btcutil.NewAddressPubKeyHash([]byte{ - 0xe3, 0x4c, 0xce, 0x70, 0xc8, 0x63, 0x73, 0x27, 0x3e, 0xfc, - 0xc5, 0x4c, 0xe7, 0xd2, 0xa4, 0x91, 0xbb, 0x4a, 0x0e, 0x84, - }, &chaincfg.MainNetParams) + p2pkhMain, err := btcutil.NewAddressPubKeyHash(decodeHex("e34cce70c863"+ + "73273efcc54ce7d2a491bb4a0e84"), &chaincfg.MainNetParams) if err != nil { t.Errorf("Unable to create public key hash address: %v", err) return @@ -602,45 +542,35 @@ func TestPayToAddrScript(t *testing.T) { // Taken from transaction: // b0539a45de13b3e0403909b8bd1a555b8cbe45fd4e3f3fda76f3a5f52835c29d - p2shMain, _ := btcutil.NewAddressScriptHashFromHash([]byte{ - 0xe8, 0xc3, 0x00, 0xc8, 0x79, 0x86, 0xef, 0xa8, 0x4c, 0x37, - 0xc0, 0x51, 0x99, 0x29, 0x01, 0x9e, 0xf8, 0x6e, 0xb5, 0xb4, - }, &chaincfg.MainNetParams) + p2shMain, _ := btcutil.NewAddressScriptHashFromHash(decodeHex("e8c300"+ + "c87986efa84c37c0519929019ef86eb5b4"), &chaincfg.MainNetParams) if err != nil { t.Errorf("Unable to create script hash address: %v", err) return } // mainnet p2pk 13CG6SJ3yHUXo4Cr2RY4THLLJrNFuG3gUg - p2pkCompressedMain, err := btcutil.NewAddressPubKey([]byte{ - 0x02, 0x19, 0x2d, 0x74, 0xd0, 0xcb, 0x94, 0x34, 0x4c, 0x95, - 0x69, 0xc2, 0xe7, 0x79, 0x01, 0x57, 0x3d, 0x8d, 0x79, 0x03, - 0xc3, 0xeb, 0xec, 0x3a, 0x95, 0x77, 0x24, 0x89, 0x5d, 0xca, - 0x52, 0xc6, 0xb4}, &chaincfg.MainNetParams) + p2pkCompressedMain, err := btcutil.NewAddressPubKey(decodeHex("02192d74"+ + "d0cb94344c9569c2e77901573d8d7903c3ebec3a957724895dca52c6b4"), + &chaincfg.MainNetParams) if err != nil { t.Errorf("Unable to create pubkey address (compressed): %v", err) return } - p2pkCompressed2Main, err := btcutil.NewAddressPubKey([]byte{ - 0x03, 0xb0, 0xbd, 0x63, 0x42, 0x34, 0xab, 0xbb, 0x1b, 0xa1, - 0xe9, 0x86, 0xe8, 0x84, 0x18, 0x5c, 0x61, 0xcf, 0x43, 0xe0, - 0x01, 0xf9, 0x13, 0x7f, 0x23, 0xc2, 0xc4, 0x09, 0x27, 0x3e, - 0xb1, 0x6e, 0x65}, &chaincfg.MainNetParams) + p2pkCompressed2Main, err := btcutil.NewAddressPubKey(decodeHex("03b0bd"+ + "634234abbb1ba1e986e884185c61cf43e001f9137f23c2c409273eb16e65"), + &chaincfg.MainNetParams) if err != nil { t.Errorf("Unable to create pubkey address (compressed 2): %v", err) return } - p2pkUncompressedMain, err := btcutil.NewAddressPubKey([]byte{ - 0x04, 0x11, 0xdb, 0x93, 0xe1, 0xdc, 0xdb, 0x8a, 0x01, 0x6b, - 0x49, 0x84, 0x0f, 0x8c, 0x53, 0xbc, 0x1e, 0xb6, 0x8a, 0x38, - 0x2e, 0x97, 0xb1, 0x48, 0x2e, 0xca, 0xd7, 0xb1, 0x48, 0xa6, - 0x90, 0x9a, 0x5c, 0xb2, 0xe0, 0xea, 0xdd, 0xfb, 0x84, 0xcc, - 0xf9, 0x74, 0x44, 0x64, 0xf8, 0x2e, 0x16, 0x0b, 0xfa, 0x9b, - 0x8b, 0x64, 0xf9, 0xd4, 0xc0, 0x3f, 0x99, 0x9b, 0x86, 0x43, - 0xf6, 0x56, 0xb4, 0x12, 0xa3}, &chaincfg.MainNetParams) + p2pkUncompressedMain, err := btcutil.NewAddressPubKey(decodeHex("0411db"+ + "93e1dcdb8a016b49840f8c53bc1eb68a382e97b1482ecad7b148a6909a5cb2"+ + "e0eaddfb84ccf9744464f82e160bfa9b8b64f9d4c03f999b8643f656b412a3"), + &chaincfg.MainNetParams) if err != nil { t.Errorf("Unable to create pubkey address (uncompressed): %v", err) @@ -649,81 +579,54 @@ func TestPayToAddrScript(t *testing.T) { tests := []struct { in btcutil.Address - expected []byte + expected string err error }{ // pay-to-pubkey-hash address on mainnet { p2pkhMain, - []byte{ - 0x76, 0xa9, 0x14, 0xe3, 0x4c, 0xce, 0x70, 0xc8, - 0x63, 0x73, 0x27, 0x3e, 0xfc, 0xc5, 0x4c, 0xe7, - 0xd2, 0xa4, 0x91, 0xbb, 0x4a, 0x0e, 0x84, 0x88, - 0xac, - }, + "DUP HASH160 DATA_20 0xe34cce70c86373273efcc54ce7d2a4" + + "91bb4a0e8488 CHECKSIG", nil, }, // pay-to-script-hash address on mainnet { p2shMain, - []byte{ - 0xa9, 0x14, 0xe8, 0xc3, 0x00, 0xc8, 0x79, 0x86, - 0xef, 0xa8, 0x4c, 0x37, 0xc0, 0x51, 0x99, 0x29, - 0x01, 0x9e, 0xf8, 0x6e, 0xb5, 0xb4, 0x87, - }, + "HASH160 DATA_20 0xe8c300c87986efa84c37c0519929019ef8" + + "6eb5b4 EQUAL", nil, }, // pay-to-pubkey address on mainnet. compressed key. { p2pkCompressedMain, - []byte{ - txscript.OP_DATA_33, - 0x02, 0x19, 0x2d, 0x74, 0xd0, 0xcb, 0x94, 0x34, - 0x4c, 0x95, 0x69, 0xc2, 0xe7, 0x79, 0x01, 0x57, - 0x3d, 0x8d, 0x79, 0x03, 0xc3, 0xeb, 0xec, 0x3a, - 0x95, 0x77, 0x24, 0x89, 0x5d, 0xca, 0x52, 0xc6, - 0xb4, txscript.OP_CHECKSIG, - }, + "DATA_33 0x02192d74d0cb94344c9569c2e77901573d8d7903c3" + + "ebec3a957724895dca52c6b4 CHECKSIG", nil, }, // pay-to-pubkey address on mainnet. compressed key (other way). { p2pkCompressed2Main, - []byte{ - txscript.OP_DATA_33, - 0x03, 0xb0, 0xbd, 0x63, 0x42, 0x34, 0xab, 0xbb, - 0x1b, 0xa1, 0xe9, 0x86, 0xe8, 0x84, 0x18, 0x5c, - 0x61, 0xcf, 0x43, 0xe0, 0x01, 0xf9, 0x13, 0x7f, - 0x23, 0xc2, 0xc4, 0x09, 0x27, 0x3e, 0xb1, 0x6e, - 0x65, txscript.OP_CHECKSIG, - }, + "DATA_33 0x03b0bd634234abbb1ba1e986e884185c61cf43e001" + + "f9137f23c2c409273eb16e65 CHECKSIG", nil, }, // pay-to-pubkey address on mainnet. uncompressed key. { p2pkUncompressedMain, - []byte{ - txscript.OP_DATA_65, - 0x04, 0x11, 0xdb, 0x93, 0xe1, 0xdc, 0xdb, 0x8a, - 0x01, 0x6b, 0x49, 0x84, 0x0f, 0x8c, 0x53, 0xbc, - 0x1e, 0xb6, 0x8a, 0x38, 0x2e, 0x97, 0xb1, 0x48, - 0x2e, 0xca, 0xd7, 0xb1, 0x48, 0xa6, 0x90, 0x9a, - 0x5c, 0xb2, 0xe0, 0xea, 0xdd, 0xfb, 0x84, 0xcc, - 0xf9, 0x74, 0x44, 0x64, 0xf8, 0x2e, 0x16, 0x0b, - 0xfa, 0x9b, 0x8b, 0x64, 0xf9, 0xd4, 0xc0, 0x3f, - 0x99, 0x9b, 0x86, 0x43, 0xf6, 0x56, 0xb4, 0x12, - 0xa3, txscript.OP_CHECKSIG, - }, + "DATA_65 0x0411db93e1dcdb8a016b49840f8c53bc1eb68a382e" + + "97b1482ecad7b148a6909a5cb2e0eaddfb84ccf97444" + + "64f82e160bfa9b8b64f9d4c03f999b8643f656b412a3 " + + "CHECKSIG", nil, }, // Supported address types with nil pointers. - {(*btcutil.AddressPubKeyHash)(nil), []byte{}, txscript.ErrUnsupportedAddress}, - {(*btcutil.AddressScriptHash)(nil), []byte{}, txscript.ErrUnsupportedAddress}, - {(*btcutil.AddressPubKey)(nil), []byte{}, txscript.ErrUnsupportedAddress}, + {(*btcutil.AddressPubKeyHash)(nil), "", txscript.ErrUnsupportedAddress}, + {(*btcutil.AddressScriptHash)(nil), "", txscript.ErrUnsupportedAddress}, + {(*btcutil.AddressPubKey)(nil), "", txscript.ErrUnsupportedAddress}, // Unsupported address type. - {&bogusAddress{}, []byte{}, txscript.ErrUnsupportedAddress}, + {&bogusAddress{}, "", txscript.ErrUnsupportedAddress}, } t.Logf("Running %d tests", len(tests)) @@ -735,47 +638,42 @@ func TestPayToAddrScript(t *testing.T) { continue } - if !bytes.Equal(pkScript, test.expected) { + expected := mustParseShortForm(test.expected) + if !bytes.Equal(pkScript, expected) { t.Errorf("PayToAddrScript #%d got: %x\nwant: %x", - i, pkScript, test.expected) + i, pkScript, expected) continue } } } +// TestMultiSigScript ensures the MultiSigScript function returns the expected +// scripts and errors. func TestMultiSigScript(t *testing.T) { t.Parallel() // mainnet p2pk 13CG6SJ3yHUXo4Cr2RY4THLLJrNFuG3gUg - p2pkCompressedMain, err := btcutil.NewAddressPubKey([]byte{ - 0x02, 0x19, 0x2d, 0x74, 0xd0, 0xcb, 0x94, 0x34, 0x4c, 0x95, - 0x69, 0xc2, 0xe7, 0x79, 0x01, 0x57, 0x3d, 0x8d, 0x79, 0x03, - 0xc3, 0xeb, 0xec, 0x3a, 0x95, 0x77, 0x24, 0x89, 0x5d, 0xca, - 0x52, 0xc6, 0xb4}, &chaincfg.MainNetParams) + p2pkCompressedMain, err := btcutil.NewAddressPubKey(decodeHex("02192d7"+ + "4d0cb94344c9569c2e77901573d8d7903c3ebec3a957724895dca52c6b4"), + &chaincfg.MainNetParams) if err != nil { t.Errorf("Unable to create pubkey address (compressed): %v", err) return } - p2pkCompressed2Main, err := btcutil.NewAddressPubKey([]byte{ - 0x03, 0xb0, 0xbd, 0x63, 0x42, 0x34, 0xab, 0xbb, 0x1b, 0xa1, - 0xe9, 0x86, 0xe8, 0x84, 0x18, 0x5c, 0x61, 0xcf, 0x43, 0xe0, - 0x01, 0xf9, 0x13, 0x7f, 0x23, 0xc2, 0xc4, 0x09, 0x27, 0x3e, - 0xb1, 0x6e, 0x65}, &chaincfg.MainNetParams) + p2pkCompressed2Main, err := btcutil.NewAddressPubKey(decodeHex("03b0bd"+ + "634234abbb1ba1e986e884185c61cf43e001f9137f23c2c409273eb16e65"), + &chaincfg.MainNetParams) if err != nil { t.Errorf("Unable to create pubkey address (compressed 2): %v", err) return } - p2pkUncompressedMain, err := btcutil.NewAddressPubKey([]byte{ - 0x04, 0x11, 0xdb, 0x93, 0xe1, 0xdc, 0xdb, 0x8a, 0x01, 0x6b, - 0x49, 0x84, 0x0f, 0x8c, 0x53, 0xbc, 0x1e, 0xb6, 0x8a, 0x38, - 0x2e, 0x97, 0xb1, 0x48, 0x2e, 0xca, 0xd7, 0xb1, 0x48, 0xa6, - 0x90, 0x9a, 0x5c, 0xb2, 0xe0, 0xea, 0xdd, 0xfb, 0x84, 0xcc, - 0xf9, 0x74, 0x44, 0x64, 0xf8, 0x2e, 0x16, 0x0b, 0xfa, 0x9b, - 0x8b, 0x64, 0xf9, 0xd4, 0xc0, 0x3f, 0x99, 0x9b, 0x86, 0x43, - 0xf6, 0x56, 0xb4, 0x12, 0xa3}, &chaincfg.MainNetParams) + p2pkUncompressedMain, err := btcutil.NewAddressPubKey(decodeHex("0411d"+ + "b93e1dcdb8a016b49840f8c53bc1eb68a382e97b1482ecad7b148a6909a5c"+ + "b2e0eaddfb84ccf9744464f82e160bfa9b8b64f9d4c03f999b8643f656b41"+ + "2a3"), &chaincfg.MainNetParams) if err != nil { t.Errorf("Unable to create pubkey address (uncompressed): %v", err) @@ -785,7 +683,7 @@ func TestMultiSigScript(t *testing.T) { tests := []struct { keys []*btcutil.AddressPubKey nrequired int - expected []byte + expected string err error }{ { @@ -794,22 +692,10 @@ func TestMultiSigScript(t *testing.T) { p2pkCompressed2Main, }, 1, - []byte{ - txscript.OP_1, - txscript.OP_DATA_33, - 0x02, 0x19, 0x2d, 0x74, 0xd0, 0xcb, 0x94, 0x34, - 0x4c, 0x95, 0x69, 0xc2, 0xe7, 0x79, 0x01, 0x57, - 0x3d, 0x8d, 0x79, 0x03, 0xc3, 0xeb, 0xec, 0x3a, - 0x95, 0x77, 0x24, 0x89, 0x5d, 0xca, 0x52, 0xc6, - 0xb4, - txscript.OP_DATA_33, - 0x03, 0xb0, 0xbd, 0x63, 0x42, 0x34, 0xab, 0xbb, - 0x1b, 0xa1, 0xe9, 0x86, 0xe8, 0x84, 0x18, 0x5c, - 0x61, 0xcf, 0x43, 0xe0, 0x01, 0xf9, 0x13, 0x7f, - 0x23, 0xc2, 0xc4, 0x09, 0x27, 0x3e, 0xb1, 0x6e, - 0x65, - txscript.OP_2, txscript.OP_CHECKMULTISIG, - }, + "1 DATA_33 0x02192d74d0cb94344c9569c2e77901573d8d7903c" + + "3ebec3a957724895dca52c6b4 DATA_33 0x03b0bd634" + + "234abbb1ba1e986e884185c61cf43e001f9137f23c2c4" + + "09273eb16e65 2 CHECKMULTISIG", nil, }, { @@ -818,22 +704,10 @@ func TestMultiSigScript(t *testing.T) { p2pkCompressed2Main, }, 2, - []byte{ - txscript.OP_2, - txscript.OP_DATA_33, - 0x02, 0x19, 0x2d, 0x74, 0xd0, 0xcb, 0x94, 0x34, - 0x4c, 0x95, 0x69, 0xc2, 0xe7, 0x79, 0x01, 0x57, - 0x3d, 0x8d, 0x79, 0x03, 0xc3, 0xeb, 0xec, 0x3a, - 0x95, 0x77, 0x24, 0x89, 0x5d, 0xca, 0x52, 0xc6, - 0xb4, - txscript.OP_DATA_33, - 0x03, 0xb0, 0xbd, 0x63, 0x42, 0x34, 0xab, 0xbb, - 0x1b, 0xa1, 0xe9, 0x86, 0xe8, 0x84, 0x18, 0x5c, - 0x61, 0xcf, 0x43, 0xe0, 0x01, 0xf9, 0x13, 0x7f, - 0x23, 0xc2, 0xc4, 0x09, 0x27, 0x3e, 0xb1, 0x6e, - 0x65, - txscript.OP_2, txscript.OP_CHECKMULTISIG, - }, + "2 DATA_33 0x02192d74d0cb94344c9569c2e77901573d8d7903c" + + "3ebec3a957724895dca52c6b4 DATA_33 0x03b0bd634" + + "234abbb1ba1e986e884185c61cf43e001f9137f23c2c4" + + "09273eb16e65 2 CHECKMULTISIG", nil, }, { @@ -842,7 +716,7 @@ func TestMultiSigScript(t *testing.T) { p2pkCompressed2Main, }, 3, - []byte{}, + "", txscript.ErrBadNumRequired, }, { @@ -850,19 +724,10 @@ func TestMultiSigScript(t *testing.T) { p2pkUncompressedMain, }, 1, - []byte{ - txscript.OP_1, txscript.OP_DATA_65, - 0x04, 0x11, 0xdb, 0x93, 0xe1, 0xdc, 0xdb, 0x8a, - 0x01, 0x6b, 0x49, 0x84, 0x0f, 0x8c, 0x53, 0xbc, - 0x1e, 0xb6, 0x8a, 0x38, 0x2e, 0x97, 0xb1, 0x48, - 0x2e, 0xca, 0xd7, 0xb1, 0x48, 0xa6, 0x90, 0x9a, - 0x5c, 0xb2, 0xe0, 0xea, 0xdd, 0xfb, 0x84, 0xcc, - 0xf9, 0x74, 0x44, 0x64, 0xf8, 0x2e, 0x16, 0x0b, - 0xfa, 0x9b, 0x8b, 0x64, 0xf9, 0xd4, 0xc0, 0x3f, - 0x99, 0x9b, 0x86, 0x43, 0xf6, 0x56, 0xb4, 0x12, - 0xa3, - txscript.OP_1, txscript.OP_CHECKMULTISIG, - }, + "1 DATA_65 0x0411db93e1dcdb8a016b49840f8c53bc1eb68a382" + + "e97b1482ecad7b148a6909a5cb2e0eaddfb84ccf97444" + + "64f82e160bfa9b8b64f9d4c03f999b8643f656b412a3 " + + "1 CHECKMULTISIG", nil, }, { @@ -870,7 +735,7 @@ func TestMultiSigScript(t *testing.T) { p2pkUncompressedMain, }, 2, - []byte{}, + "", txscript.ErrBadNumRequired, }, } @@ -885,379 +750,253 @@ func TestMultiSigScript(t *testing.T) { continue } - if !bytes.Equal(script, test.expected) { + expected := mustParseShortForm(test.expected) + if !bytes.Equal(script, expected) { t.Errorf("MultiSigScript #%d got: %x\nwant: %x", - i, script, test.expected) + i, script, expected) continue } } } +// TestCalcMultiSigStats ensures the CalcMutliSigStats function returns the +// expected errors. func TestCalcMultiSigStats(t *testing.T) { t.Parallel() tests := []struct { - name string - script []byte - expected error + name string + script string + err error }{ { name: "short script", - script: []byte{ - 0x04, 0x67, 0x08, 0xaf, 0xdb, 0x0f, 0xe5, 0x54, - 0x82, 0x71, 0x96, 0x7f, 0x1a, 0x67, 0x13, 0x0b, - 0x71, 0x05, 0xcd, 0x6a, 0x82, 0x8e, 0x03, 0x90, - 0x9a, 0x67, 0x96, 0x2e, 0x0e, 0xa1, 0xf6, 0x1d, - }, - expected: txscript.ErrStackShortScript, + script: "0x046708afdb0fe5548271967f1a67130b7105cd6a828" + + "e03909a67962e0ea1f61d", + err: txscript.ErrStackShortScript, }, { name: "stack underflow", - script: []byte{ - txscript.OP_RETURN, - txscript.OP_PUSHDATA1, - 0x29, - 0x04, 0x67, 0x08, 0xaf, 0xdb, 0x0f, 0xe5, 0x54, - 0x82, 0x71, 0x96, 0x7f, 0x1a, 0x67, 0x13, 0x0b, - 0x71, 0x05, 0xcd, 0x6a, 0x82, 0x8e, 0x03, 0x90, - 0x9a, 0x67, 0x96, 0x2e, 0x0e, 0xa1, 0xf6, 0x1d, - 0xeb, 0x64, 0x9f, 0x6b, 0xc3, 0xf4, 0xce, 0xf3, - 0x08, - }, - expected: txscript.ErrStackUnderflow, + script: "RETURN DATA_41 0x046708afdb0fe5548271967f1a" + + "67130b7105cd6a828e03909a67962e0ea1f61deb649f6" + + "bc3f4cef308", + err: txscript.ErrStackUnderflow, }, { name: "multisig script", - script: []uint8{ - txscript.OP_FALSE, - txscript.OP_DATA_72, - 0x30, 0x45, 0x02, 0x20, 0x10, - 0x6a, 0x3e, 0x4e, 0xf0, 0xb5, - 0x1b, 0x76, 0x4a, 0x28, 0x87, - 0x22, 0x62, 0xff, 0xef, 0x55, - 0x84, 0x65, 0x14, 0xda, 0xcb, - 0xdc, 0xbb, 0xdd, 0x65, 0x2c, - 0x84, 0x9d, 0x39, 0x5b, 0x43, - 0x84, 0x02, 0x21, 0x00, 0xe0, - 0x3a, 0xe5, 0x54, 0xc3, 0xcb, - 0xb4, 0x06, 0x00, 0xd3, 0x1d, - 0xd4, 0x6f, 0xc3, 0x3f, 0x25, - 0xe4, 0x7b, 0xf8, 0x52, 0x5b, - 0x1f, 0xe0, 0x72, 0x82, 0xe3, - 0xb6, 0xec, 0xb5, 0xf3, 0xbb, - 0x28, 0x01, - txscript.OP_CODESEPARATOR, - txscript.OP_TRUE, - txscript.OP_DATA_33, - 0x02, 0x32, 0xab, 0xdc, 0x89, - 0x3e, 0x7f, 0x06, 0x31, 0x36, - 0x4d, 0x7f, 0xd0, 0x1c, 0xb3, - 0x3d, 0x24, 0xda, 0x45, 0x32, - 0x9a, 0x00, 0x35, 0x7b, 0x3a, - 0x78, 0x86, 0x21, 0x1a, 0xb4, - 0x14, 0xd5, 0x5a, - txscript.OP_TRUE, - txscript.OP_CHECKMULTISIG, - }, - expected: nil, + script: "0 DATA_72 0x30450220106a3e4ef0b51b764a2887226" + + "2ffef55846514dacbdcbbdd652c849d395b4384022100" + + "e03ae554c3cbb40600d31dd46fc33f25e47bf8525b1fe" + + "07282e3b6ecb5f3bb2801 CODESEPARATOR 1 DATA_33 " + + "0x0232abdc893e7f0631364d7fd01cb33d24da45329a0" + + "0357b3a7886211ab414d55a 1 CHECKMULTISIG", + err: nil, }, } for i, test := range tests { - if _, _, err := txscript.CalcMultiSigStats(test.script); err != test.expected { - t.Errorf("CalcMultiSigStats #%d (%s) wrong result\n"+ - "got: %v\nwant: %v", i, test.name, err, - test.expected) + script := mustParseShortForm(test.script) + if _, _, err := txscript.CalcMultiSigStats(script); err != test.err { + t.Errorf("CalcMultiSigStats #%d (%s) unexpected "+ + "error\ngot: %v\nwant: %v", i, test.name, err, + test.err) } } } -type scriptTypeTest struct { - name string - script []byte - scripttype txscript.ScriptClass +// scriptClassTest houses a test used to ensure various scripts have the +// expected class. +type scriptClassTest struct { + name string + script string + class txscript.ScriptClass } -var scriptTypeTests = []scriptTypeTest{ - // tx 0437cd7f8525ceed2324359c2d0ba26006d92d85. +// scriptClassTests houses several test scripts used to ensure various class +// determination is working as expected. It's defined as a test global versus +// inside a function scope since this spans both the standard tests and the +// consensus tests (pay-to-script-hash is part of consensus). +var scriptClassTests = []scriptClassTest{ { name: "Pay Pubkey", - script: []byte{ - txscript.OP_DATA_65, - 0x04, 0x11, 0xdb, 0x93, 0xe1, 0xdc, 0xdb, 0x8a, 0x01, - 0x6b, 0x49, 0x84, 0x0f, 0x8c, 0x53, 0xbc, 0x1e, 0xb6, - 0x8a, 0x38, 0x2e, 0x97, 0xb1, 0x48, 0x2e, 0xca, 0xd7, - 0xb1, 0x48, 0xa6, 0x90, 0x9a, 0x5c, 0xb2, 0xe0, 0xea, - 0xdd, 0xfb, 0x84, 0xcc, 0xf9, 0x74, 0x44, 0x64, 0xf8, - 0x2e, 0x16, 0x0b, 0xfa, 0x9b, 0x8b, 0x64, 0xf9, 0xd4, - 0xc0, 0x3f, 0x99, 0x9b, 0x86, 0x43, 0xf6, 0x56, 0xb4, - 0x12, 0xa3, - txscript.OP_CHECKSIG, - }, - scripttype: txscript.PubKeyTy, + script: "DATA_65 0x0411db93e1dcdb8a016b49840f8c53bc1eb68a382e" + + "97b1482ecad7b148a6909a5cb2e0eaddfb84ccf9744464f82e16" + + "0bfa9b8b64f9d4c03f999b8643f656b412a3 CHECKSIG", + class: txscript.PubKeyTy, }, // tx 599e47a8114fe098103663029548811d2651991b62397e057f0c863c2bc9f9ea { name: "Pay PubkeyHash", - script: []byte{ - txscript.OP_DUP, - txscript.OP_HASH160, - txscript.OP_DATA_20, - 0x66, 0x0d, 0x4e, 0xf3, 0xa7, 0x43, 0xe3, 0xe6, 0x96, - 0xad, 0x99, 0x03, 0x64, 0xe5, 0x55, 0xc2, 0x71, 0xad, - 0x50, 0x4b, - txscript.OP_EQUALVERIFY, - txscript.OP_CHECKSIG, - }, - scripttype: txscript.PubKeyHashTy, + script: "DUP HASH160 DATA_20 0x660d4ef3a743e3e696ad990364e555" + + "c271ad504b EQUALVERIFY CHECKSIG", + class: txscript.PubKeyHashTy, }, // part of tx 6d36bc17e947ce00bb6f12f8e7a56a1585c5a36188ffa2b05e10b4743273a74b - // codeseparator parts have been elided. (bitcoind's checks for multisig - // type doesn't have codesep etc either. + // codeseparator parts have been elided. (bitcoin core's checks for + // multisig type doesn't have codesep either). { name: "multisig", - script: []byte{ - txscript.OP_TRUE, - txscript.OP_DATA_33, - 0x02, 0x32, 0xab, 0xdc, 0x89, 0x3e, 0x7f, 0x06, 0x31, - 0x36, 0x4d, 0x7f, 0xd0, 0x1c, 0xb3, 0x3d, 0x24, 0xda, - 0x45, 0x32, 0x9a, 0x00, 0x35, 0x7b, 0x3a, 0x78, 0x86, - 0x21, 0x1a, 0xb4, 0x14, 0xd5, 0x5a, - txscript.OP_TRUE, - txscript.OP_CHECKMULTISIG, - }, - scripttype: txscript.MultiSigTy, + script: "1 DATA_33 0x0232abdc893e7f0631364d7fd01cb33d24da4" + + "5329a00357b3a7886211ab414d55a 1 CHECKMULTISIG", + class: txscript.MultiSigTy, }, // tx e5779b9e78f9650debc2893fd9636d827b26b4ddfa6a8172fe8708c924f5c39d - // P2SH { name: "P2SH", - script: []byte{ - txscript.OP_HASH160, - txscript.OP_DATA_20, - 0x43, 0x3e, 0xc2, 0xac, 0x1f, 0xfa, 0x1b, 0x7b, 0x7d, - 0x02, 0x7f, 0x56, 0x45, 0x29, 0xc5, 0x71, 0x97, 0xf9, - 0xae, 0x88, - txscript.OP_EQUAL, - }, - scripttype: txscript.ScriptHashTy, + script: "HASH160 DATA_20 0x433ec2ac1ffa1b7b7d027f564529c57197f" + + "9ae88 EQUAL", + class: txscript.ScriptHashTy, }, - // Nulldata with no data at all. { - name: "nulldata", - script: []byte{ - txscript.OP_RETURN, - }, - scripttype: txscript.NullDataTy, + // Nulldata with no data at all. + name: "nulldata", + script: "RETURN", + class: txscript.NullDataTy, }, - // Nulldata with small data. { - name: "nulldata2", - script: []byte{ - txscript.OP_RETURN, - txscript.OP_DATA_8, - 0x04, 0x67, 0x08, 0xaf, 0xdb, 0x0f, 0xe5, 0x54, - }, - scripttype: txscript.NullDataTy, + // Nulldata with small data. + name: "nulldata2", + script: "RETURN DATA_8 0x046708afdb0fe554", + class: txscript.NullDataTy, }, - // Nulldata with max allowed data. { + // Nulldata with max allowed data. name: "nulldata3", - script: []byte{ - txscript.OP_RETURN, - txscript.OP_PUSHDATA1, - 0x50, // 80 - 0x04, 0x67, 0x08, 0xaf, 0xdb, 0x0f, 0xe5, 0x54, - 0x82, 0x71, 0x96, 0x7f, 0x1a, 0x67, 0x13, 0x0b, - 0x71, 0x05, 0xcd, 0x6a, 0x82, 0x8e, 0x03, 0x90, - 0x9a, 0x67, 0x96, 0x2e, 0x0e, 0xa1, 0xf6, 0x1d, - 0xeb, 0x64, 0x9f, 0x6b, 0xc3, 0xf4, 0xce, 0xf3, - 0x04, 0x67, 0x08, 0xaf, 0xdb, 0x0f, 0xe5, 0x54, - 0x82, 0x71, 0x96, 0x7f, 0x1a, 0x67, 0x13, 0x0b, - 0x71, 0x05, 0xcd, 0x6a, 0x82, 0x8e, 0x03, 0x90, - 0x9a, 0x67, 0x96, 0x2e, 0x0e, 0xa1, 0xf6, 0x1d, - 0xeb, 0x64, 0x9f, 0x6b, 0xc3, 0xf4, 0xce, 0xf3, - }, - scripttype: txscript.NullDataTy, + script: "RETURN PUSHDATA1 0x50 0x046708afdb0fe5548271967f1a67" + + "130b7105cd6a828e03909a67962e0ea1f61deb649f6bc3f4cef3" + + "046708afdb0fe5548271967f1a67130b7105cd6a828e03909a67" + + "962e0ea1f61deb649f6bc3f4cef3", + class: txscript.NullDataTy, }, - // Nulldata with more than max allowed data (so therefore nonstandard) { + // Nulldata with more than max allowed data (so therefore + // nonstandard) name: "nulldata4", - script: []byte{ - txscript.OP_RETURN, - txscript.OP_PUSHDATA1, - 0x51, // 81 - 0x04, 0x67, 0x08, 0xaf, 0xdb, 0x0f, 0xe5, 0x54, - 0x82, 0x71, 0x96, 0x7f, 0x1a, 0x67, 0x13, 0x0b, - 0x71, 0x05, 0xcd, 0x6a, 0x82, 0x8e, 0x03, 0x90, - 0x9a, 0x67, 0x96, 0x2e, 0x0e, 0xa1, 0xf6, 0x1d, - 0xeb, 0x64, 0x9f, 0x6b, 0xc3, 0xf4, 0xce, 0xf3, - 0x04, 0x67, 0x08, 0xaf, 0xdb, 0x0f, 0xe5, 0x54, - 0x82, 0x71, 0x96, 0x7f, 0x1a, 0x67, 0x13, 0x0b, - 0x71, 0x05, 0xcd, 0x6a, 0x82, 0x8e, 0x03, 0x90, - 0x9a, 0x67, 0x96, 0x2e, 0x0e, 0xa1, 0xf6, 0x1d, - 0xeb, 0x64, 0x9f, 0x6b, 0xc3, 0xf4, 0xce, 0xf3, - 0x08, - }, - scripttype: txscript.NonStandardTy, + script: "RETURN PUSHDATA1 0x51 0x046708afdb0fe5548271967f1a67" + + "130b7105cd6a828e03909a67962e0ea1f61deb649f6bc3f4cef3" + + "046708afdb0fe5548271967f1a67130b7105cd6a828e03909a67" + + "962e0ea1f61deb649f6bc3f4cef308", + class: txscript.NonStandardTy, }, - // Almost nulldata, but add an additional opcode after the data to make - // it nonstandard. { - name: "nulldata5", - script: []byte{ - txscript.OP_RETURN, - txscript.OP_DATA_1, - 0x04, - txscript.OP_TRUE, - }, - scripttype: txscript.NonStandardTy, - }, // The next few are almost multisig (it is the more complex script type) + // Almost nulldata, but add an additional opcode after the data + // to make it nonstandard. + name: "nulldata5", + script: "RETURN 4 TRUE", + class: txscript.NonStandardTy, + }, + + // The next few are almost multisig (it is the more complex script type) // but with various changes to make it fail. { - // multisig but funny nsigs.. + // Multisig but invalid nsigs. name: "strange 1", - script: []byte{ - txscript.OP_DUP, - txscript.OP_DATA_33, - 0x02, 0x32, 0xab, 0xdc, 0x89, 0x3e, 0x7f, 0x06, 0x31, - 0x36, 0x4d, 0x7f, 0xd0, 0x1c, 0xb3, 0x3d, 0x24, 0xda, - 0x45, 0x32, 0x9a, 0x00, 0x35, 0x7b, 0x3a, 0x78, 0x86, - 0x21, 0x1a, 0xb4, 0x14, 0xd5, 0x5a, - txscript.OP_TRUE, - txscript.OP_CHECKMULTISIG, - }, - scripttype: txscript.NonStandardTy, + script: "DUP DATA_33 0x0232abdc893e7f0631364d7fd01cb33d24da45" + + "329a00357b3a7886211ab414d55a 1 CHECKMULTISIG", + class: txscript.NonStandardTy, }, { - name: "strange 2", - // multisig but funny pubkey. - script: []byte{ - txscript.OP_TRUE, - txscript.OP_TRUE, - txscript.OP_TRUE, - txscript.OP_CHECKMULTISIG, - }, - scripttype: txscript.NonStandardTy, + // Multisig but invalid pubkey. + name: "strange 2", + script: "1 1 1 CHECKMULTISIG", + class: txscript.NonStandardTy, }, { + // Multisig but no matching npubkeys opcode. name: "strange 3", - // multisig but no matching npubkeys opcode. - script: []byte{ - txscript.OP_TRUE, - txscript.OP_DATA_33, - 0x02, 0x32, 0xab, 0xdc, 0x89, 0x3e, 0x7f, 0x06, 0x31, - 0x36, 0x4d, 0x7f, 0xd0, 0x1c, 0xb3, 0x3d, 0x24, 0xda, - 0x45, 0x32, 0x9a, 0x00, 0x35, 0x7b, 0x3a, 0x78, 0x86, - 0x21, 0x1a, 0xb4, 0x14, 0xd5, 0x5a, - txscript.OP_DATA_33, - 0x02, 0x32, 0xab, 0xdc, 0x89, 0x3e, 0x7f, 0x06, 0x31, - 0x36, 0x4d, 0x7f, 0xd0, 0x1c, 0xb3, 0x3d, 0x24, 0xda, - 0x45, 0x32, 0x9a, 0x00, 0x35, 0x7b, 0x3a, 0x78, 0x86, - 0x21, 0x1a, 0xb4, 0x14, 0xd5, 0x5a, - // No number. - txscript.OP_CHECKMULTISIG, - }, - scripttype: txscript.NonStandardTy, + script: "1 DATA_33 0x0232abdc893e7f0631364d7fd01cb33d24da4532" + + "9a00357b3a7886211ab414d55a DATA_33 0x0232abdc893e7f0" + + "631364d7fd01cb33d24da45329a00357b3a7886211ab414d55a " + + "CHECKMULTISIG", + class: txscript.NonStandardTy, }, { + // Multisig but with multisigverify. name: "strange 4", - // multisig but with multisigverify - script: []byte{ - txscript.OP_TRUE, - txscript.OP_DATA_33, - 0x02, 0x32, 0xab, 0xdc, 0x89, 0x3e, 0x7f, 0x06, 0x31, - 0x36, 0x4d, 0x7f, 0xd0, 0x1c, 0xb3, 0x3d, 0x24, 0xda, - 0x45, 0x32, 0x9a, 0x00, 0x35, 0x7b, 0x3a, 0x78, 0x86, - 0x21, 0x1a, 0xb4, 0x14, 0xd5, 0x5a, - txscript.OP_TRUE, - txscript.OP_CHECKMULTISIGVERIFY, - }, - scripttype: txscript.NonStandardTy, + script: "1 DATA_33 0x0232abdc893e7f0631364d7fd01cb33d24da4532" + + "9a00357b3a7886211ab414d55a 1 CHECKMULTISIGVERIFY", + class: txscript.NonStandardTy, }, { - name: "strange 5", - // multisig but wrong length. - script: []byte{ - txscript.OP_TRUE, - txscript.OP_CHECKMULTISIG, - }, - scripttype: txscript.NonStandardTy, + // Multisig but wrong length. + name: "strange 5", + script: "1 CHECKMULTISIG", + class: txscript.NonStandardTy, }, { - name: "doesn't parse", - script: []byte{ - txscript.OP_DATA_5, 0x1, 0x2, 0x3, 0x4, - }, - scripttype: txscript.NonStandardTy, + name: "doesn't parse", + script: "DATA_5 0x01020304", + class: txscript.NonStandardTy, }, } -func testScriptType(t *testing.T, test *scriptTypeTest) { - scripttype := txscript.GetScriptClass(test.script) - if scripttype != test.scripttype { - t.Errorf("%s: expected %s got %s", test.name, test.scripttype, - scripttype) - } -} - -func TestScriptTypes(t *testing.T) { +// TestScriptClass ensures all the scripts in scriptClassTests have the expected +// class. +func TestScriptClass(t *testing.T) { t.Parallel() - for i := range scriptTypeTests { - testScriptType(t, &scriptTypeTests[i]) + for _, test := range scriptClassTests { + script := mustParseShortForm(test.script) + class := txscript.GetScriptClass(script) + if class != test.class { + t.Errorf("%s: expected %s got %s", test.name, + test.class, class) + return + } } } +// TestStringifyClass ensures the script class string returns the expected +// string for each script class. func TestStringifyClass(t *testing.T) { t.Parallel() tests := []struct { - name string - scriptclass txscript.ScriptClass - stringed string + name string + class txscript.ScriptClass + stringed string }{ { - name: "nonstandardty", - scriptclass: txscript.NonStandardTy, - stringed: "nonstandard", + name: "nonstandardty", + class: txscript.NonStandardTy, + stringed: "nonstandard", }, { - name: "pubkey", - scriptclass: txscript.PubKeyTy, - stringed: "pubkey", + name: "pubkey", + class: txscript.PubKeyTy, + stringed: "pubkey", }, { - name: "pubkeyhash", - scriptclass: txscript.PubKeyHashTy, - stringed: "pubkeyhash", + name: "pubkeyhash", + class: txscript.PubKeyHashTy, + stringed: "pubkeyhash", }, { - name: "scripthash", - scriptclass: txscript.ScriptHashTy, - stringed: "scripthash", + name: "scripthash", + class: txscript.ScriptHashTy, + stringed: "scripthash", }, { - name: "multisigty", - scriptclass: txscript.MultiSigTy, - stringed: "multisig", + name: "multisigty", + class: txscript.MultiSigTy, + stringed: "multisig", }, { - name: "nulldataty", - scriptclass: txscript.NullDataTy, - stringed: "nulldata", + name: "nulldataty", + class: txscript.NullDataTy, + stringed: "nulldata", }, { - name: "broken", - scriptclass: txscript.ScriptClass(255), - stringed: "Invalid", + name: "broken", + class: txscript.ScriptClass(255), + stringed: "Invalid", }, } for _, test := range tests { - typeString := test.scriptclass.String() + typeString := test.class.String() if typeString != test.stringed { - t.Errorf("%s: got \"%s\" expected \"%s\"", test.name, + t.Errorf("%s: got %#q, want %#q", test.name, typeString, test.stringed) } }