bitcoinrb 0.0.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (86) hide show
  1. checksums.yaml +7 -0
  2. data/.gitignore +9 -0
  3. data/.rspec +2 -0
  4. data/.ruby-gemset +1 -0
  5. data/.ruby-version +1 -0
  6. data/.travis.yml +4 -0
  7. data/CODE_OF_CONDUCT.md +49 -0
  8. data/Gemfile +4 -0
  9. data/LICENSE.txt +21 -0
  10. data/README.md +41 -0
  11. data/Rakefile +6 -0
  12. data/bin/console +14 -0
  13. data/bin/setup +8 -0
  14. data/bitcoinrb.gemspec +32 -0
  15. data/exe/bitcoinrb-cli +5 -0
  16. data/exe/bitcoinrbd +49 -0
  17. data/lib/bitcoin.rb +121 -0
  18. data/lib/bitcoin/base58.rb +40 -0
  19. data/lib/bitcoin/block_header.rb +41 -0
  20. data/lib/bitcoin/chain_params.rb +57 -0
  21. data/lib/bitcoin/chainparams/mainnet.yml +25 -0
  22. data/lib/bitcoin/chainparams/regtest.yml +20 -0
  23. data/lib/bitcoin/chainparams/testnet.yml +24 -0
  24. data/lib/bitcoin/connection.rb +66 -0
  25. data/lib/bitcoin/ext_key.rb +205 -0
  26. data/lib/bitcoin/key.rb +131 -0
  27. data/lib/bitcoin/logger.rb +18 -0
  28. data/lib/bitcoin/merkle_tree.rb +120 -0
  29. data/lib/bitcoin/message.rb +42 -0
  30. data/lib/bitcoin/message/addr.rb +74 -0
  31. data/lib/bitcoin/message/base.rb +40 -0
  32. data/lib/bitcoin/message/block.rb +41 -0
  33. data/lib/bitcoin/message/error.rb +10 -0
  34. data/lib/bitcoin/message/fee_filter.rb +27 -0
  35. data/lib/bitcoin/message/filter_add.rb +28 -0
  36. data/lib/bitcoin/message/filter_clear.rb +17 -0
  37. data/lib/bitcoin/message/filter_load.rb +43 -0
  38. data/lib/bitcoin/message/get_addr.rb +17 -0
  39. data/lib/bitcoin/message/get_blocks.rb +29 -0
  40. data/lib/bitcoin/message/get_data.rb +21 -0
  41. data/lib/bitcoin/message/get_headers.rb +28 -0
  42. data/lib/bitcoin/message/handler.rb +170 -0
  43. data/lib/bitcoin/message/headers.rb +34 -0
  44. data/lib/bitcoin/message/headers_parser.rb +24 -0
  45. data/lib/bitcoin/message/inv.rb +21 -0
  46. data/lib/bitcoin/message/inventories_parser.rb +23 -0
  47. data/lib/bitcoin/message/inventory.rb +47 -0
  48. data/lib/bitcoin/message/mem_pool.rb +17 -0
  49. data/lib/bitcoin/message/merkle_block.rb +42 -0
  50. data/lib/bitcoin/message/not_found.rb +29 -0
  51. data/lib/bitcoin/message/ping.rb +30 -0
  52. data/lib/bitcoin/message/pong.rb +26 -0
  53. data/lib/bitcoin/message/reject.rb +46 -0
  54. data/lib/bitcoin/message/send_cmpct.rb +43 -0
  55. data/lib/bitcoin/message/send_headers.rb +16 -0
  56. data/lib/bitcoin/message/tx.rb +30 -0
  57. data/lib/bitcoin/message/ver_ack.rb +17 -0
  58. data/lib/bitcoin/message/version.rb +79 -0
  59. data/lib/bitcoin/mnemonic.rb +76 -0
  60. data/lib/bitcoin/mnemonic/wordlist/chinese_simplified.txt +2048 -0
  61. data/lib/bitcoin/mnemonic/wordlist/chinese_traditional.txt +2048 -0
  62. data/lib/bitcoin/mnemonic/wordlist/english.txt +2048 -0
  63. data/lib/bitcoin/mnemonic/wordlist/french.txt +2048 -0
  64. data/lib/bitcoin/mnemonic/wordlist/italian.txt +2048 -0
  65. data/lib/bitcoin/mnemonic/wordlist/japanese.txt +2048 -0
  66. data/lib/bitcoin/mnemonic/wordlist/spanish.txt +2048 -0
  67. data/lib/bitcoin/nodes.rb +5 -0
  68. data/lib/bitcoin/nodes/spv.rb +13 -0
  69. data/lib/bitcoin/nodes/spv/cli.rb +12 -0
  70. data/lib/bitcoin/nodes/spv/daemon.rb +21 -0
  71. data/lib/bitcoin/opcodes.rb +172 -0
  72. data/lib/bitcoin/out_point.rb +31 -0
  73. data/lib/bitcoin/script/script.rb +347 -0
  74. data/lib/bitcoin/script/script_error.rb +168 -0
  75. data/lib/bitcoin/script/script_interpreter.rb +694 -0
  76. data/lib/bitcoin/script/tx_checker.rb +44 -0
  77. data/lib/bitcoin/script_witness.rb +29 -0
  78. data/lib/bitcoin/secp256k1.rb +10 -0
  79. data/lib/bitcoin/secp256k1/native.rb +22 -0
  80. data/lib/bitcoin/secp256k1/ruby.rb +96 -0
  81. data/lib/bitcoin/tx.rb +191 -0
  82. data/lib/bitcoin/tx_in.rb +45 -0
  83. data/lib/bitcoin/tx_out.rb +32 -0
  84. data/lib/bitcoin/util.rb +105 -0
  85. data/lib/bitcoin/version.rb +3 -0
  86. metadata +256 -0
@@ -0,0 +1,168 @@
1
+ module Bitcoin
2
+
3
+ # bitcoin script error
4
+ class ScriptError < Exception
5
+
6
+ SCRIPT_ERR_OK = 0
7
+ SCRIPT_ERR_UNKNOWN_ERROR = 1
8
+ SCRIPT_ERR_EVAL_FALSE = 2
9
+ SCRIPT_ERR_OP_RETURN = 3
10
+
11
+ # Max sizes
12
+ SCRIPT_ERR_SCRIPT_SIZE = 10
13
+ SCRIPT_ERR_PUSH_SIZE = 11
14
+ SCRIPT_ERR_OP_COUNT = 12
15
+ SCRIPT_ERR_STACK_SIZE = 13
16
+ SCRIPT_ERR_SIG_COUNT = 14
17
+ SCRIPT_ERR_PUBKEY_COUNT = 15
18
+
19
+ # Failed verify operations
20
+ SCRIPT_ERR_VERIFY = 20
21
+ SCRIPT_ERR_EQUALVERIFY = 21
22
+ SCRIPT_ERR_CHECKMULTISIGVERIFY = 22
23
+ SCRIPT_ERR_CHECKSIGVERIFY = 23
24
+ SCRIPT_ERR_NUMEQUALVERIFY = 24
25
+
26
+ # Logical/Format/Canonical errors
27
+ SCRIPT_ERR_BAD_OPCODE = 30
28
+ SCRIPT_ERR_DISABLED_OPCODE = 31
29
+ SCRIPT_ERR_INVALID_STACK_OPERATION = 32
30
+ SCRIPT_ERR_INVALID_ALTSTACK_OPERATION = 33
31
+ SCRIPT_ERR_UNBALANCED_CONDITIONAL = 34
32
+
33
+ # CHECKLOCKTIMEVERIFY and CHECKSEQUENCEVERIFY
34
+ SCRIPT_ERR_NEGATIVE_LOCKTIME = 40
35
+ SCRIPT_ERR_UNSATISFIED_LOCKTIME = 41
36
+
37
+ # Malleability
38
+ SCRIPT_ERR_SIG_HASHTYPE = 50
39
+ SCRIPT_ERR_SIG_DER = 51
40
+ SCRIPT_ERR_MINIMALDATA = 52
41
+ SCRIPT_ERR_SIG_PUSHONLY = 53
42
+ SCRIPT_ERR_SIG_HIGH_S = 54
43
+ SCRIPT_ERR_SIG_NULLDUMMY = 55
44
+ SCRIPT_ERR_PUBKEYTYPE = 56
45
+ SCRIPT_ERR_CLEANSTACK = 56
46
+ SCRIPT_ERR_MINIMALIF = 57
47
+ SCRIPT_ERR_SIG_NULLFAIL = 58
48
+
49
+ # softfork safeness
50
+ SCRIPT_ERR_DISCOURAGE_UPGRADABLE_NOPS = 60
51
+ SCRIPT_ERR_DISCOURAGE_UPGRADABLE_WITNESS_PROGRAM = 61
52
+
53
+ # segregated witness
54
+ SCRIPT_ERR_WITNESS_PROGRAM_WRONG_LENGTH = 70
55
+ SCRIPT_ERR_WITNESS_PROGRAM_WITNESS_EMPTY = 71
56
+ SCRIPT_ERR_WITNESS_PROGRAM_MISMATCH = 72
57
+ SCRIPT_ERR_WITNESS_MALLEATED = 73
58
+ SCRIPT_ERR_WITNESS_MALLEATED_P2SH = 74
59
+ SCRIPT_ERR_WITNESS_UNEXPECTED = 75
60
+ SCRIPT_ERR_WITNESS_PUBKEYTYPE = 76
61
+
62
+ SCRIPT_ERR_ERROR_COUNT = 80
63
+
64
+ ERRCODES_MAP = Hash[*constants.grep(/^SCRIPT_ERR_/).map { |c| [const_get(c), c.to_s] }.flatten]
65
+ NAME_MAP = Hash[*constants.grep(/^SCRIPT_ERR_/).map { |c| [c.to_s, const_get(c)] }.flatten]
66
+
67
+ attr_accessor :code
68
+ attr_accessor :extra_msg
69
+
70
+ def initialize(code, extra_msg = '')
71
+ raise 'invalid error code.' unless ERRCODES_MAP[code]
72
+ @code = code
73
+ @extra_msg = extra_msg
74
+ end
75
+
76
+ def to_s
77
+ case code
78
+ when SCRIPT_ERR_OK
79
+ 'No error'
80
+ when SCRIPT_ERR_EVAL_FALSE
81
+ 'Script evaluated without error but finished with a false/empty top stack element'
82
+ when SCRIPT_ERR_VERIFY
83
+ 'Script failed an OP_VERIFY operation'
84
+ when SCRIPT_ERR_EQUALVERIFY
85
+ 'Script failed an OP_EQUALVERIFY operation'
86
+ when SCRIPT_ERR_CHECKMULTISIGVERIFY
87
+ 'Script failed an OP_CHECKMULTISIGVERIFY operation'
88
+ when SCRIPT_ERR_CHECKSIGVERIFY
89
+ 'Script failed an OP_CHECKSIGVERIFY operation'
90
+ when SCRIPT_ERR_NUMEQUALVERIFY
91
+ 'Script failed an OP_NUMEQUALVERIFY operation'
92
+ when SCRIPT_ERR_SCRIPT_SIZE
93
+ 'Script is too big'
94
+ when SCRIPT_ERR_PUSH_SIZE
95
+ 'Push value size limit exceeded'
96
+ when SCRIPT_ERR_OP_COUNT
97
+ 'Operation limit exceeded'
98
+ when SCRIPT_ERR_STACK_SIZE
99
+ 'Stack size limit exceeded'
100
+ when SCRIPT_ERR_SIG_COUNT
101
+ 'Signature count negative or greater than pubkey count'
102
+ when SCRIPT_ERR_PUBKEY_COUNT
103
+ 'Pubkey count negative or limit exceeded'
104
+ when SCRIPT_ERR_BAD_OPCODE
105
+ 'Opcode missing or not understood'
106
+ when SCRIPT_ERR_DISABLED_OPCODE
107
+ 'Attempted to use a disabled opcode'
108
+ when SCRIPT_ERR_INVALID_STACK_OPERATION
109
+ 'Operation not valid with the current stack size'
110
+ when SCRIPT_ERR_INVALID_ALTSTACK_OPERATION
111
+ 'Operation not valid with the current altstack size'
112
+ when SCRIPT_ERR_OP_RETURN
113
+ 'OP_was encountered'
114
+ when SCRIPT_ERR_UNBALANCED_CONDITIONAL
115
+ 'Invalid OP_IF construction'
116
+ when SCRIPT_ERR_NEGATIVE_LOCKTIME
117
+ 'Negative locktime'
118
+ when SCRIPT_ERR_UNSATISFIED_LOCKTIME
119
+ 'Locktime requirement not satisfied'
120
+ when SCRIPT_ERR_SIG_HASHTYPE
121
+ 'Signature hash type missing or not understood'
122
+ when SCRIPT_ERR_SIG_DER
123
+ 'Non-canonical DER signature'
124
+ when SCRIPT_ERR_MINIMALDATA
125
+ 'Data push larger than necessary'
126
+ when SCRIPT_ERR_SIG_PUSHONLY
127
+ 'Only non-push operators allowed in signatures'
128
+ when SCRIPT_ERR_SIG_HIGH_S
129
+ 'Non-canonical signature S value is unnecessarily high'
130
+ when SCRIPT_ERR_SIG_NULLDUMMY
131
+ 'Dummy CHECKMULTISIG argument must be zero'
132
+ when SCRIPT_ERR_MINIMALIF
133
+ 'OP_IF/NOTIF argument must be minimal'
134
+ when SCRIPT_ERR_SIG_NULLFAIL
135
+ 'Signature must be zero for failed CHECK(MULTI)SIG operation'
136
+ when SCRIPT_ERR_DISCOURAGE_UPGRADABLE_NOPS
137
+ 'NOPx reserved for soft-fork upgrades'
138
+ when SCRIPT_ERR_DISCOURAGE_UPGRADABLE_WITNESS_PROGRAM
139
+ 'Witness version reserved for soft-fork upgrades'
140
+ when SCRIPT_ERR_PUBKEYTYPE
141
+ 'Public key is neither compressed or uncompressed'
142
+ when SCRIPT_ERR_WITNESS_PROGRAM_WRONG_LENGTH
143
+ 'Witness program has incorrect length'
144
+ when SCRIPT_ERR_WITNESS_PROGRAM_WITNESS_EMPTY
145
+ 'Witness program was passed an empty witness'
146
+ when SCRIPT_ERR_WITNESS_PROGRAM_MISMATCH
147
+ 'Witness program hash mismatch'
148
+ when SCRIPT_ERR_WITNESS_MALLEATED
149
+ 'Witness requires empty scriptSig'
150
+ when SCRIPT_ERR_WITNESS_MALLEATED_P2SH
151
+ 'Witness requires only-redeemscript scriptSig'
152
+ when SCRIPT_ERR_WITNESS_UNEXPECTED
153
+ 'Witness provided for non-witness script'
154
+ when SCRIPT_ERR_WITNESS_PUBKEYTYPE
155
+ 'Using non-compressed keys in segwit'
156
+ when SCRIPT_ERR_UNKNOWN_ERROR, SCRIPT_ERR_ERROR_COUNT
157
+ 'unknown error'
158
+ else
159
+ extra_msg ? extra_msg : 'unknown error'
160
+ end
161
+ end
162
+
163
+ def self.name_to_code(name)
164
+ NAME_MAP[name]
165
+ end
166
+
167
+ end
168
+ end
@@ -0,0 +1,694 @@
1
+ module Bitcoin
2
+
3
+ SCRIPT_VERIFY_NONE = 0
4
+ SCRIPT_VERIFY_P2SH = (1 << 0)
5
+ SCRIPT_VERIFY_STRICTENC = (1 << 1)
6
+ SCRIPT_VERIFY_DERSIG = (1 << 2)
7
+ SCRIPT_VERIFY_LOW_S = (1 << 3)
8
+ SCRIPT_VERIFY_NULLDUMMY = (1 << 4)
9
+ SCRIPT_VERIFY_SIGPUSHONLY = (1 << 5)
10
+ SCRIPT_VERIFY_MINIMALDATA = (1 << 6)
11
+ SCRIPT_VERIFY_DISCOURAGE_UPGRADABLE_NOPS = (1 << 7)
12
+ SCRIPT_VERIFY_CLEANSTACK = (1 << 8)
13
+ SCRIPT_VERIFY_CHECKLOCKTIMEVERIFY = (1 << 9) # Verify CHECKLOCKTIMEVERIFY (BIP-65)
14
+ SCRIPT_VERIFY_CHECKSEQUENCEVERIFY = (1 << 10) # support CHECKSEQUENCEVERIFY opcode (BIP-112)
15
+ SCRIPT_VERIFY_WITNESS = (1 << 11) # Support segregated witness
16
+ SCRIPT_VERIFY_DISCOURAGE_UPGRADABLE_WITNESS_PROGRAM = (1 << 12) # Making v1-v16 witness program non-standard
17
+ SCRIPT_VERIFY_MINIMALIF = (1 << 13) # Segwit script only: Require the argument of OP_IF/NOTIF to be exactly 0x01 or empty vector
18
+ SCRIPT_VERIFY_NULLFAIL = (1 << 14) # Signature(s) must be empty vector if an CHECK(MULTI)SIG operation failed
19
+ SCRIPT_VERIFY_WITNESS_PUBKEYTYPE = (1 << 15) # Public keys in segregated witness scripts must be compressed
20
+
21
+ class ScriptInterpreter
22
+
23
+ include Bitcoin::Opcodes
24
+
25
+ SIG_VERSION = {base: 0, witness_v0: 1}
26
+
27
+ attr_reader :stack
28
+ attr_reader :debug
29
+ attr_reader :flags
30
+ attr_accessor :error
31
+ attr_reader :checker
32
+ attr_reader :require_minimal
33
+
34
+ DISABLE_OPCODES = [OP_CAT, OP_SUBSTR, OP_LEFT, OP_RIGHT, OP_INVERT, OP_AND, OP_OR, OP_XOR, OP_2MUL, OP_2DIV, OP_DIV, OP_MUL, OP_MOD, OP_LSHIFT, OP_RSHIFT]
35
+
36
+ # initialize runner
37
+ def initialize(flags: [], checker: TxChecker.new)
38
+ @stack, @debug = [], []
39
+ @flags = flags
40
+ @checker = checker
41
+ @require_minimal = flag?(SCRIPT_VERIFY_MINIMALDATA)
42
+ end
43
+
44
+ # eval script
45
+ # @param [Bitcoin::Script] script_sig a signature script (unlock script which data push only)
46
+ # @param [Bitcoin::Script] script_pubkey a script pubkey (locking script)
47
+ # @param [Bitcoin::ScriptWitness] witness a witness script
48
+ # @return [Boolean] result
49
+ def verify(script_sig, script_pubkey, witness = nil)
50
+
51
+ return set_error(ScriptError::SCRIPT_ERR_SIG_PUSHONLY) if flag?(SCRIPT_VERIFY_SIGPUSHONLY) && !script_sig.data_only?
52
+
53
+ stack_copy = nil
54
+ had_witness = false
55
+
56
+ return false unless eval_script(script_sig, SIG_VERSION[:base])
57
+
58
+ stack_copy = stack.dup if flag?(SCRIPT_VERIFY_P2SH)
59
+
60
+ return false unless eval_script(script_pubkey, SIG_VERSION[:base])
61
+
62
+ return set_error(ScriptError::SCRIPT_ERR_EVAL_FALSE) if stack.empty? || !cast_to_bool(stack.last)
63
+
64
+ # Bare witness programs
65
+ if flag?(SCRIPT_VERIFY_WITNESS) && script_pubkey.witness_program?
66
+ had_witness = true
67
+ return set_error(ScriptError::SCRIPT_ERR_WITNESS_MALLEATED) unless script_sig.size == 0
68
+ version, program = script_pubkey.witness_data
69
+ stack_copy = stack.dup
70
+ return false unless verify_witness_program(witness, version, program)
71
+ end
72
+
73
+ # Additional validation for spend-to-script-hash transactions
74
+ if flag?(SCRIPT_VERIFY_P2SH) && script_pubkey.p2sh?
75
+ return set_error(ScriptError::SCRIPT_ERR_SIG_PUSHONLY) unless script_sig.data_only?
76
+ tmp = stack
77
+ @stack = stack_copy
78
+ raise 'stack cannot be empty.' if stack.empty?
79
+ begin
80
+ redeem_script = Bitcoin::Script.parse_from_payload(stack.pop.htb)
81
+ rescue Exception => e
82
+ return set_error(ScriptError::SCRIPT_ERR_BAD_OPCODE, "Failed to parse serialized redeem script for P2SH. #{e.message}")
83
+ end
84
+ return false unless eval_script(redeem_script, SIG_VERSION[:base])
85
+ return set_error(ScriptError::SCRIPT_ERR_EVAL_FALSE) if stack.empty? || !cast_to_bool(stack.last)
86
+
87
+ # P2SH witness program
88
+ if flag?(SCRIPT_VERIFY_WITNESS) && redeem_script.witness_program?
89
+ had_witness = true
90
+ # The scriptSig must be _exactly_ a single push of the redeemScript. Otherwise we reintroduce malleability.
91
+ return set_error(ScriptError::SCRIPT_ERR_WITNESS_MALLEATED_P2SH) unless script_sig == (Bitcoin::Script.new << redeem_script.to_payload.bth)
92
+
93
+ version, program = redeem_script.witness_data
94
+ return false unless verify_witness_program(witness, version, program)
95
+ end
96
+ end
97
+
98
+ # The CLEANSTACK check is only performed after potential P2SH evaluation,
99
+ # as the non-P2SH evaluation of a P2SH script will obviously not result in a clean stack (the P2SH inputs remain).
100
+ # The same holds for witness evaluation.
101
+ if flag?(SCRIPT_VERIFY_CLEANSTACK)
102
+ # Disallow CLEANSTACK without P2SH, as otherwise a switch CLEANSTACK->P2SH+CLEANSTACK would be possible,
103
+ # which is not a softfork (and P2SH should be one).
104
+ raise 'assert' unless flag?(SCRIPT_VERIFY_P2SH)
105
+ return set_error(ScriptError::SCRIPT_ERR_CLEANSTACK) unless stack.size == 1
106
+ end
107
+
108
+ if flag?(SCRIPT_VERIFY_WITNESS)
109
+ raise 'assert' unless flag?(SCRIPT_VERIFY_P2SH)
110
+ return set_error(ScriptError::SCRIPT_ERR_WITNESS_UNEXPECTED) if !had_witness && !witness.empty?
111
+ end
112
+
113
+ true
114
+ end
115
+
116
+ def set_error(err_code, extra_message = nil)
117
+ @error = ScriptError.new(err_code, extra_message)
118
+ false
119
+ end
120
+
121
+ def verify_sig
122
+
123
+ end
124
+
125
+ def verify_witness_program(witness, version, program)
126
+ if version == 0
127
+ if program.bytesize == 32
128
+ return set_error(ScriptError::SCRIPT_ERR_WITNESS_PROGRAM_WITNESS_EMPTY) if witness.stack.size == 0
129
+ script_pubkey = Bitcoin::Script.parse_from_payload(witness.stack.last)
130
+ @stack = witness.stack[0..-2]
131
+ script_hash = Bitcoin.sha256(script_pubkey.to_payload)
132
+ return set_error(ScriptError::SCRIPT_ERR_WITNESS_PROGRAM_MISMATCH) unless script_hash == program
133
+ elsif program.bytesize == 20
134
+ return set_error(ScriptError::SCRIPT_ERR_WITNESS_PROGRAM_MISMATCH) unless witness.stack.size == 2
135
+ script_pubkey = Bitcoin::Script.to_p2pkh(program.bth)
136
+ @stack = witness.stack.map{|w|w.bth}
137
+ else
138
+ return set_error(ScriptError::SCRIPT_ERR_WITNESS_PROGRAM_WRONG_LENGTH)
139
+ end
140
+ elsif flag?(SCRIPT_VERIFY_DISCOURAGE_UPGRADABLE_WITNESS_PROGRAM)
141
+ return set_error(ScriptError::SCRIPT_ERR_WITNESS_PROGRAM_WRONG_LENGTH)
142
+ else
143
+ return true # Higher version witness scripts return true for future softfork compatibility
144
+ end
145
+
146
+ stack.each do |s| # Disallow stack item size > MAX_SCRIPT_ELEMENT_SIZE in witness stack
147
+ return set_error(ScriptError::SCRIPT_ERR_PUSH_SIZE) if s.bytesize > Script::MAX_SCRIPT_ELEMENT_SIZE
148
+ end
149
+
150
+ return false unless eval_script(script_pubkey, SIG_VERSION[:witness_v0])
151
+
152
+ return set_error(ScriptError::SCRIPT_ERR_EVAL_FALSE) unless stack.size == 1
153
+ return set_error(ScriptError::SCRIPT_ERR_EVAL_FALSE) unless cast_to_bool(stack.last)
154
+ true
155
+ end
156
+
157
+ def eval_script(script, sig_version)
158
+ return set_error(ScriptError::SCRIPT_ERR_SCRIPT_SIZE) if script.size > Script::MAX_SCRIPT_SIZE
159
+ begin
160
+ flow_stack = []
161
+ alt_stack = []
162
+ last_code_separator_index = 0
163
+ op_count = 0
164
+
165
+ script.chunks.each_with_index do |c, index|
166
+ need_exec = !flow_stack.include?(false)
167
+
168
+ return set_error(ScriptError::SCRIPT_ERR_PUSH_SIZE) if c.pushdata? && c.pushed_data.bytesize > Script::MAX_SCRIPT_ELEMENT_SIZE
169
+
170
+ opcode = c.opcode
171
+
172
+ if need_exec && c.pushdata?
173
+ if require_minimal && !minimal_push?(c.pushed_data, opcode)
174
+ return set_error(ScriptError::SCRIPT_ERR_MINIMALDATA)
175
+ end
176
+ return set_error(ScriptError::SCRIPT_ERR_BAD_OPCODE) unless verify_pushdata_length(c)
177
+ stack << c.pushed_data.bth
178
+ else
179
+ if opcode > OP_16 && (op_count += 1) > Script::MAX_OPS_PER_SCRIPT
180
+ return set_error(ScriptError::SCRIPT_ERR_OP_COUNT)
181
+ end
182
+ return set_error(ScriptError::SCRIPT_ERR_DISABLED_OPCODE) if DISABLE_OPCODES.include?(opcode)
183
+ next unless (need_exec || (OP_IF <= opcode && opcode <= OP_ENDIF))
184
+ small_int = Opcodes.opcode_to_small_int(opcode)
185
+ if small_int && opcode != OP_0
186
+ push_int(small_int)
187
+ else
188
+ case opcode
189
+ when OP_0
190
+ stack << ''
191
+ when OP_DEPTH
192
+ push_int(stack.size)
193
+ when OP_EQUAL, OP_EQUALVERIFY
194
+ return set_error(ScriptError::SCRIPT_ERR_INVALID_STACK_OPERATION) if stack.size < 2
195
+ a, b = pop_string(2)
196
+ result = a == b
197
+ push_int(result ? 1 : 0)
198
+ if opcode == OP_EQUALVERIFY
199
+ if result
200
+ stack.pop
201
+ else
202
+ return set_error(ScriptError::SCRIPT_ERR_EQUALVERIFY)
203
+ end
204
+ end
205
+ when OP_0NOTEQUAL
206
+ return set_error(ScriptError::SCRIPT_ERR_INVALID_STACK_OPERATION) if stack.size < 1
207
+ push_int(pop_int == 0 ? 0 : 1)
208
+ when OP_ADD
209
+ return set_error(ScriptError::SCRIPT_ERR_INVALID_STACK_OPERATION) if stack.size < 2
210
+ a, b = pop_int(2)
211
+ push_int(a + b)
212
+ when OP_1ADD
213
+ return set_error(ScriptError::SCRIPT_ERR_INVALID_STACK_OPERATION) if stack.size < 1
214
+ push_int(pop_int + 1)
215
+ when OP_SUB
216
+ return set_error(ScriptError::SCRIPT_ERR_INVALID_STACK_OPERATION) if stack.size < 2
217
+ a, b = pop_int(2)
218
+ push_int(a - b)
219
+ when OP_1SUB
220
+ return set_error(ScriptError::SCRIPT_ERR_INVALID_STACK_OPERATION) if stack.size < 1
221
+ push_int(pop_int - 1)
222
+ when OP_IF, OP_NOTIF
223
+ result = false
224
+ if need_exec
225
+ return set_error(ScriptError::SCRIPT_ERR_UNBALANCED_CONDITIONAL) if stack.size < 1
226
+ result = pop_bool
227
+ result = !result if opcode == OP_NOTIF
228
+ end
229
+ flow_stack << result
230
+ when OP_ELSE
231
+ return set_error(ScriptError::SCRIPT_ERR_UNBALANCED_CONDITIONAL) if flow_stack.size < 1
232
+ flow_stack << !flow_stack.pop
233
+ when OP_ENDIF
234
+ return set_error(ScriptError::SCRIPT_ERR_UNBALANCED_CONDITIONAL) if flow_stack.empty?
235
+ flow_stack.pop
236
+ when OP_NOP
237
+ when OP_NOP1, OP_NOP4..OP_NOP10
238
+ return set_error(ScriptError::SCRIPT_ERR_DISCOURAGE_UPGRADABLE_NOPS) if flag?(SCRIPT_VERIFY_DISCOURAGE_UPGRADABLE_NOPS)
239
+ when OP_CHECKLOCKTIMEVERIFY
240
+ unless flag?(SCRIPT_VERIFY_CHECKLOCKTIMEVERIFY)
241
+ return set_error(ScriptError::SCRIPT_ERR_DISCOURAGE_UPGRADABLE_NOPS) if flag?(SCRIPT_VERIFY_DISCOURAGE_UPGRADABLE_NOPS)
242
+ next
243
+ end
244
+ return set_error(ScriptError::SCRIPT_ERR_INVALID_STACK_OPERATION) if stack.size < 1
245
+ locktime = pop_int
246
+ return set_error(ScriptError::SCRIPT_ERR_NEGATIVE_LOCKTIME) if locktime < 0
247
+ return set_error(ScriptError::SCRIPT_ERR_UNSATISFIED_LOCKTIME) unless checker.check_locktime(locktime)
248
+ when OP_CHECKSEQUENCEVERIFY
249
+ unless flag?(SCRIPT_VERIFY_CHECKSEQUENCEVERIFY)
250
+ return set_error(ScriptError::SCRIPT_ERR_DISCOURAGE_UPGRADABLE_NOPS) if flag?(SCRIPT_VERIFY_DISCOURAGE_UPGRADABLE_NOPS)
251
+ next
252
+ end
253
+ return set_error(ScriptError::SCRIPT_ERR_INVALID_STACK_OPERATION) if stack.size < 1
254
+ # TODO implement
255
+ when OP_DUP
256
+ return set_error(ScriptError::SCRIPT_ERR_INVALID_STACK_OPERATION) if stack.size < 1
257
+ stack << stack.last
258
+ when OP_2DUP
259
+ return set_error(ScriptError::SCRIPT_ERR_INVALID_STACK_OPERATION) if stack.size < 2
260
+ 2.times { stack << stack[-2] }
261
+ when OP_3DUP
262
+ return set_error(ScriptError::SCRIPT_ERR_INVALID_STACK_OPERATION) if stack.size < 3
263
+ 3.times { stack << stack[-3] }
264
+ when OP_IFDUP
265
+ return set_error(ScriptError::SCRIPT_ERR_INVALID_STACK_OPERATION) if stack.size < 1
266
+ stack << stack.last if cast_to_bool(stack.last)
267
+ when OP_RIPEMD160
268
+ return set_error(ScriptError::SCRIPT_ERR_INVALID_STACK_OPERATION) if stack.size < 1
269
+ stack << Digest::RMD160.hexdigest(pop_string.htb)
270
+ when OP_SHA1
271
+ return set_error(ScriptError::SCRIPT_ERR_INVALID_STACK_OPERATION) if stack.size < 1
272
+ stack << Digest::SHA1.hexdigest(pop_string.htb)
273
+ when OP_SHA256
274
+ return set_error(ScriptError::SCRIPT_ERR_INVALID_STACK_OPERATION) if stack.size < 1
275
+ stack << Digest::SHA256.hexdigest(pop_string.htb)
276
+ when OP_HASH160
277
+ return set_error(ScriptError::SCRIPT_ERR_INVALID_STACK_OPERATION) if stack.size < 1
278
+ stack << Bitcoin.hash160(pop_string)
279
+ when OP_HASH256
280
+ return set_error(ScriptError::SCRIPT_ERR_INVALID_STACK_OPERATION) if stack.size < 1
281
+ stack << Bitcoin.double_sha256(pop_string.htb).bth
282
+ when OP_VERIFY
283
+ return set_error(ScriptError::SCRIPT_ERR_INVALID_STACK_OPERATION) if stack.size < 1
284
+ return set_error(ScriptError::SCRIPT_ERR_VERIFY) unless pop_bool
285
+ when OP_TOALTSTACK
286
+ return set_error(ScriptError::SCRIPT_ERR_INVALID_STACK_OPERATION) if stack.size < 1
287
+ alt_stack << stack.pop
288
+ when OP_FROMALTSTACK
289
+ return set_error(ScriptError::SCRIPT_ERR_INVALID_ALTSTACK_OPERATION) if alt_stack.size < 1
290
+ stack << alt_stack.pop
291
+ when OP_DROP
292
+ return set_error(ScriptError::SCRIPT_ERR_INVALID_STACK_OPERATION) if stack.size < 1
293
+ stack.pop
294
+ when OP_2DROP
295
+ return set_error(ScriptError::SCRIPT_ERR_INVALID_STACK_OPERATION) if stack.size < 2
296
+ 2.times { stack.pop }
297
+ when OP_NIP
298
+ return set_error(ScriptError::SCRIPT_ERR_INVALID_STACK_OPERATION) if stack.size < 2
299
+ stack.delete_at(-2)
300
+ when OP_OVER
301
+ return set_error(ScriptError::SCRIPT_ERR_INVALID_STACK_OPERATION) if stack.size < 2
302
+ stack << stack[-2]
303
+ when OP_2OVER
304
+ return set_error(ScriptError::SCRIPT_ERR_INVALID_STACK_OPERATION) if stack.size < 4
305
+ 2.times { stack << stack[-4]}
306
+ when OP_PICK, OP_ROLL
307
+ return set_error(ScriptError::SCRIPT_ERR_INVALID_STACK_OPERATION) if stack.size < 2
308
+ pos = pop_int
309
+ return set_error(ScriptError::SCRIPT_ERR_INVALID_STACK_OPERATION) if pos < 0 || pos >= stack.size
310
+ stack << stack[-pos - 1]
311
+ stack.delete_at(-pos - 2) if opcode == OP_ROLL
312
+ when OP_ROT
313
+ return set_error(ScriptError::SCRIPT_ERR_INVALID_STACK_OPERATION) if stack.size < 3
314
+ stack << stack[-3]
315
+ stack.delete_at(-4)
316
+ when OP_2ROT
317
+ return set_error(ScriptError::SCRIPT_ERR_INVALID_STACK_OPERATION) if stack.size < 6
318
+ 2.times { stack << stack[-6] }
319
+ 2.times { stack.delete_at(-7) }
320
+ when OP_SWAP
321
+ return set_error(ScriptError::SCRIPT_ERR_INVALID_STACK_OPERATION) if stack.size < 2
322
+ tmp = stack.last
323
+ stack[-1] = stack[-2]
324
+ stack[-2] = tmp
325
+ when OP_2SWAP
326
+ return set_error(ScriptError::SCRIPT_ERR_INVALID_STACK_OPERATION) if stack.size < 4
327
+ 2.times {stack << stack[-4]}
328
+ 2.times {stack.delete_at(-5)}
329
+ when OP_TUCK
330
+ return set_error(ScriptError::SCRIPT_ERR_INVALID_STACK_OPERATION) if stack.size < 2
331
+ stack.insert(-3, stack.last)
332
+ when OP_ABS
333
+ return set_error(ScriptError::SCRIPT_ERR_INVALID_STACK_OPERATION) if stack.size < 1
334
+ v = pop_int
335
+ push_int(v.abs)
336
+ when OP_BOOLAND
337
+ return set_error(ScriptError::SCRIPT_ERR_INVALID_STACK_OPERATION) if stack.size < 2
338
+ a, b = pop_int(2)
339
+ push_int((!a.zero? && !b.zero?) ? 1 : 0)
340
+ when OP_BOOLOR
341
+ return set_error(ScriptError::SCRIPT_ERR_INVALID_STACK_OPERATION) if stack.size < 2
342
+ a, b = pop_int(2)
343
+ push_int((!a.zero? || !b.zero?) ? 1 : 0)
344
+ when OP_NUMEQUAL, OP_NUMEQUALVERIFY
345
+ return set_error(ScriptError::SCRIPT_ERR_INVALID_STACK_OPERATION) if stack.size < 2
346
+ a, b = pop_int(2)
347
+ result = a == b
348
+ push_int(result ? 1 : 0)
349
+ if opcode == OP_NUMEQUALVERIFY
350
+ if result
351
+ stack.pop
352
+ else
353
+ return set_error(ScriptError::SCRIPT_ERR_NUMEQUALVERIFY)
354
+ end
355
+ end
356
+ when OP_LESSTHAN, OP_LESSTHANOREQUAL
357
+ return set_error(ScriptError::SCRIPT_ERR_INVALID_STACK_OPERATION) if stack.size < 2
358
+ a, b = pop_int(2)
359
+ push_int(a < b ? 1 : 0) if opcode == OP_LESSTHAN
360
+ push_int(a <= b ? 1 : 0) if opcode == OP_LESSTHANOREQUAL
361
+ when OP_GREATERTHAN, OP_GREATERTHANOREQUAL
362
+ return set_error(ScriptError::SCRIPT_ERR_INVALID_STACK_OPERATION) if stack.size < 2
363
+ a, b = pop_int(2)
364
+ push_int(a > b ? 1 : 0) if opcode == OP_GREATERTHAN
365
+ push_int(a >= b ? 1 : 0) if opcode == OP_GREATERTHANOREQUAL
366
+ when OP_MIN
367
+ return set_error(ScriptError::SCRIPT_ERR_INVALID_STACK_OPERATION) if stack.size < 2
368
+ push_int(pop_int(2).min)
369
+ when OP_MAX
370
+ return set_error(ScriptError::SCRIPT_ERR_INVALID_STACK_OPERATION) if stack.size < 2
371
+ push_int(pop_int(2).max)
372
+ when OP_WITHIN
373
+ return set_error(ScriptError::SCRIPT_ERR_INVALID_STACK_OPERATION) if stack.size < 3
374
+ x, a, b = pop_int(3)
375
+ push_int((a <= x && x < b) ? 1 : 0)
376
+ when OP_NOT
377
+ return set_error(ScriptError::SCRIPT_ERR_INVALID_STACK_OPERATION) if stack.size < 1
378
+ push_int(pop_int == 0 ? 1 : 0)
379
+ when OP_SIZE
380
+ return set_error(ScriptError::SCRIPT_ERR_INVALID_STACK_OPERATION) if stack.size < 1
381
+ item = stack.last
382
+ item = Bitcoin::Script.encode_number(item) if item.is_a?(Numeric)
383
+ size = item.htb.bytesize
384
+ push_int(size)
385
+ when OP_NEGATE
386
+ return set_error(ScriptError::SCRIPT_ERR_INVALID_STACK_OPERATION) if stack.size < 1
387
+ push_int(-pop_int)
388
+ when OP_NUMNOTEQUAL
389
+ return set_error(ScriptError::SCRIPT_ERR_INVALID_STACK_OPERATION) if stack.size < 2
390
+ a, b = pop_int(2)
391
+ push_int(a == b ? 0 : 1)
392
+ when OP_CODESEPARATOR
393
+ last_code_separator_index = index + 1
394
+ when OP_CHECKSIG, OP_CHECKSIGVERIFY
395
+ return set_error(ScriptError::SCRIPT_ERR_INVALID_STACK_OPERATION) if stack.size < 2
396
+ sig, pubkey = pop_string(2)
397
+
398
+ subscript = script.subscript(last_code_separator_index..-1)
399
+ if sig_version == SIG_VERSION[:base]
400
+ subscript = subscript.find_and_delete(Script.new << sig)
401
+ end
402
+
403
+ return false if !check_pubkey_encoding(pubkey, sig_version) || !check_signature_encoding(sig) # error already set.
404
+
405
+ success = checker.check_sig(sig, pubkey, subscript, sig_version)
406
+
407
+ # https://github.com/bitcoin/bips/blob/master/bip-0146.mediawiki#NULLFAIL
408
+ if !success && flag?(SCRIPT_VERIFY_NULLFAIL) && sig.bytesize > 0
409
+ return set_error(ScriptError::SCRIPT_ERR_SIG_NULLFAIL)
410
+ end
411
+
412
+ push_int(success ? 1 : 0)
413
+
414
+ if opcode == OP_CHECKSIGVERIFY
415
+ if success
416
+ stack.pop
417
+ else
418
+ return set_error(SCRIPT_ERR_CHECKSIGVERIFY)
419
+ end
420
+ end
421
+ when OP_CHECKMULTISIG, OP_CHECKMULTISIGVERIFY
422
+ return set_error(ScriptError::SCRIPT_ERR_INVALID_STACK_OPERATION) if stack.size < 1
423
+ pubkey_count = pop_int
424
+ unless (0..Script::MAX_PUBKEYS_PER_MULTISIG).include?(pubkey_count)
425
+ return set_error(ScriptError::SCRIPT_ERR_PUBKEY_COUNT)
426
+ end
427
+
428
+ op_count += pubkey_count
429
+ return set_error(ScriptError::SCRIPT_ERR_OP_COUNT) if op_count > Script::MAX_OPS_PER_SCRIPT
430
+
431
+ return set_error(ScriptError::SCRIPT_ERR_INVALID_STACK_OPERATION) if stack.size < pubkey_count
432
+
433
+ pubkeys = pop_string(pubkey_count)
434
+ pubkeys = [pubkeys] if pubkeys.is_a?(String)
435
+
436
+ return set_error(ScriptError::SCRIPT_ERR_INVALID_STACK_OPERATION) if stack.size < 1
437
+
438
+ sig_count = pop_int
439
+ return set_error(ScriptError::SCRIPT_ERR_SIG_COUNT) if sig_count < 0 || sig_count > pubkey_count
440
+ return set_error(ScriptError::SCRIPT_ERR_INVALID_STACK_OPERATION) if stack.size < (sig_count)
441
+
442
+ sigs = pop_string(sig_count)
443
+ sigs = [sigs] if sigs.is_a?(String)
444
+
445
+ subscript = script.subscript(last_code_separator_index..-1)
446
+
447
+ if sig_version == SIG_VERSION[:base]
448
+ sigs.each do |sig|
449
+ subscript = subscript.find_and_delete(Script.new << sig)
450
+ end
451
+ end
452
+
453
+ success = true
454
+ while success && sig_count > 0
455
+ sig = sigs.pop
456
+ pubkey = pubkeys.pop
457
+ return false if !check_pubkey_encoding(pubkey, sig_version) || !check_signature_encoding(sig) # error already set.
458
+ ok = checker.check_sig(sig, pubkey, subscript, sig_version)
459
+ if ok
460
+ sig_count -= 1
461
+ else
462
+ sigs << sig
463
+ end
464
+ pubkey_count -= 1
465
+ success = false if sig_count > pubkey_count
466
+ end
467
+
468
+ if !success && flag?(SCRIPT_VERIFY_NULLFAIL)
469
+ sigs.each do |sig|
470
+ # If the operation failed, we require that all signatures must be empty vector
471
+ return set_error(ScriptError::SCRIPT_ERR_SIG_NULLFAIL) if sig.bytesize > 0
472
+ end
473
+ end
474
+
475
+ # A bug causes CHECKMULTISIG to consume one extra argument whose contents were not checked in any way.
476
+ # Unfortunately this is a potential source of mutability,
477
+ # so optionally verify it is exactly equal to zero prior to removing it from the stack.
478
+ return set_error(ScriptError::SCRIPT_ERR_INVALID_STACK_OPERATION) if stack.size < 1
479
+ if flag?(SCRIPT_VERIFY_NULLDUMMY) && stack[-1].size > 0
480
+ return set_error(ScriptError::SCRIPT_ERR_SIG_NULLDUMMY)
481
+ end
482
+ stack.pop
483
+
484
+ push_int(success ? 1 : 0)
485
+ if opcode == OP_CHECKMULTISIGVERIFY
486
+ if success
487
+ stack.pop
488
+ else
489
+ return set_error(ScriptError::SCRIPT_ERR_CHECKMULTISIGVERIFY)
490
+ end
491
+ end
492
+ when OP_RETURN
493
+ return set_error(ScriptError::SCRIPT_ERR_OP_RETURN)
494
+ else
495
+ return set_error(ScriptError::SCRIPT_ERR_BAD_OPCODE)
496
+ end
497
+ end
498
+ end
499
+
500
+ # max stack size check
501
+ return set_error(ScriptError::SCRIPT_ERR_STACK_SIZE) if stack.size + alt_stack.size > Script::MAX_STACK_SIZE
502
+ end
503
+ rescue Exception => e
504
+ puts e
505
+ puts e.backtrace
506
+ return set_error(ScriptError::SCRIPT_ERR_UNKNOWN_ERROR, e.message)
507
+ end
508
+
509
+ return set_error(ScriptError::SCRIPT_ERR_UNBALANCED_CONDITIONAL) unless flow_stack.empty?
510
+
511
+ set_error(ScriptError::SCRIPT_ERR_OK)
512
+ true
513
+ end
514
+
515
+ private
516
+
517
+ def flag?(flag)
518
+ (all_flags & flag) != 0
519
+ end
520
+
521
+ def all_flags
522
+ result = SCRIPT_VERIFY_NONE
523
+ flags.each{ |f| result |= f }
524
+ result
525
+ end
526
+
527
+ # pop the item with the int value for the number specified by +count+ from the stack.
528
+ def pop_int(count = 1)
529
+ i = stack.pop(count).map do |s|
530
+ data = s.htb
531
+ raise '"script number overflow"' if data.bytesize > Script::DEFAULT_MAX_NUM_SIZE
532
+ if require_minimal && data.bytesize > 0
533
+ if data.bytes[-1] & 0x7f == 0 && (data.bytesize <= 1 || data.bytes[data.bytesize - 2] & 0x80 ==0)
534
+ raise 'non-minimally encoded script number'
535
+ end
536
+ end
537
+ Script.decode_number(s)
538
+ end
539
+ count == 1 ? i.first : i
540
+ end
541
+
542
+ # push +i+ into stack as encoded by Script#encode_number
543
+ def push_int(i)
544
+ stack << Script.encode_number(i)
545
+ end
546
+
547
+ # pop the item with the string(hex) value for the number specified by +count+ from the stack.
548
+ def pop_string(count = 1)
549
+ s = stack.pop(count).map do |s|
550
+ case s
551
+ when Numeric
552
+ Script.encode_number(s)
553
+ else
554
+ s
555
+ end
556
+ end
557
+ count == 1 ? s.first : s
558
+ end
559
+
560
+ # pop the item with the boolean value from the stack.
561
+ def pop_bool
562
+ cast_to_bool(pop_string.htb)
563
+ end
564
+
565
+ # see https://github.com/bitcoin/bitcoin/blob/master/src/script/interpreter.cpp#L36-L49
566
+ def cast_to_bool(v)
567
+ case v
568
+ when Numeric
569
+ return v != 0
570
+ when String
571
+ v.each_byte.with_index do |b, i|
572
+ return !(i == (v.bytesize - 1) && b == 0x80) unless b == 0
573
+ end
574
+ false
575
+ else
576
+ false
577
+ end
578
+ end
579
+
580
+ def check_signature_encoding(sig)
581
+ return true if sig.size.zero?
582
+ if (flag?(SCRIPT_VERIFY_DERSIG) || flag?(SCRIPT_VERIFY_LOW_S) || flag?(SCRIPT_VERIFY_STRICTENC)) && !valid_signature_encoding?(sig)
583
+ return set_error(ScriptError::SCRIPT_ERR_SIG_DER)
584
+ elsif flag?(SCRIPT_VERIFY_LOW_S) && !low_der_signature?(sig)
585
+ return false
586
+ elsif flag?(SCRIPT_VERIFY_STRICTENC) && !defined_hashtype_signature?(sig)
587
+ return set_error(ScriptError::SCRIPT_ERR_SIG_HASHTYPE)
588
+ end
589
+ true
590
+ end
591
+
592
+ # check +sig+ (hex) is correct der encoding.
593
+ # This function is consensus-critical since BIP66.
594
+ def valid_signature_encoding?(signature)
595
+ sig = signature.htb
596
+ return false if sig.bytesize < 9 || sig.bytesize > 73 # Minimum and maximum size check
597
+
598
+ s = sig.unpack('C*')
599
+
600
+ return false if s[0] != 0x30 || s[1] != s.size - 3 # A signature is of type 0x30 (compound). Make sure the length covers the entire signature.
601
+
602
+ len_r = s[3]
603
+ return false if 5 + len_r >= s.size # Make sure the length of the S element is still inside the signature.
604
+
605
+ len_s = s[5 + len_r]
606
+ return false unless len_r + len_s + 7 == s.size #Verify that the length of the signature matches the sum of the length of the elements.
607
+
608
+ return false unless s[2] == 0x02 # Check whether the R element is an integer.
609
+
610
+ return false if len_r == 0 # Zero-length integers are not allowed for R.
611
+
612
+ return false unless s[4] & 0x80 == 0 # Negative numbers are not allowed for R.
613
+
614
+ # Null bytes at the start of R are not allowed, unless R would otherwise be interpreted as a negative number.
615
+ return false if len_r > 1 && (s[4] == 0x00) && (s[5] & 0x80 == 0)
616
+
617
+ return false unless s[len_r + 4] == 0x02 # Check whether the S element is an integer.
618
+
619
+ return false if len_s == 0 # Zero-length integers are not allowed for S.
620
+ return false unless (s[len_r + 6] & 0x80) == 0 # Negative numbers are not allowed for S.
621
+
622
+ # Null bytes at the start of S are not allowed, unless S would otherwise be interpreted as a negative number.
623
+ return false if len_s > 1 && (s[len_r + 6] == 0x00) && (s[len_r + 7] & 0x80 == 0)
624
+
625
+ true
626
+ end
627
+
628
+ def low_der_signature?(sig)
629
+ return set_error(ScriptError::SCRIPT_ERR_SIG_DER) unless valid_signature_encoding?(sig)
630
+ return set_error(ScriptError::SCRIPT_ERR_SIG_HIGH_S) unless Key.low_signature?(sig)
631
+ true
632
+ end
633
+
634
+ def defined_hashtype_signature?(signature)
635
+ sig = signature.htb
636
+ return false if sig.empty?
637
+ s = sig.unpack('C*')
638
+ hash_type = s[-1] & (~(Script::SIGHASH_TYPE[:anyonecanpay]))
639
+ return false if hash_type < Script::SIGHASH_TYPE[:all] || hash_type > Script::SIGHASH_TYPE[:single]
640
+ true
641
+ end
642
+
643
+ def check_pubkey_encoding(pubkey, sig_version)
644
+ if flag?(SCRIPT_VERIFY_STRICTENC) && !Key.compress_or_uncompress_pubkey?(pubkey)
645
+ return set_error(ScriptError::SCRIPT_ERR_PUBKEYTYPE)
646
+ end
647
+ # Only compressed keys are accepted in segwit
648
+ if flag?(SCRIPT_VERIFY_WITNESS_PUBKEYTYPE) &&
649
+ sig_version == SIG_VERSION[:witness_v0] && !Key.compress_pubkey?(pubkey)
650
+ return set_error(ScriptError::SCRIPT_ERR_WITNESS_PUBKEYTYPE)
651
+ end
652
+ true
653
+ end
654
+
655
+ def minimal_push?(data, opcode)
656
+ if data.bytesize.zero?
657
+ return opcode == OP_0
658
+ elsif data.bytesize == 1 && data.bytes[0] >= 1 && data.bytes[0] <= 16
659
+ return opcode == OP_1 + (data.bytes[0] - 1)
660
+ elsif data.bytesize == 1 && data.bytes[0] == 0x81
661
+ return opcode == OP_1NEGATE
662
+ elsif data.bytesize <= 75
663
+ return opcode == data.bytesize
664
+ elsif data.bytesize <= 255
665
+ return opcode == OP_PUSHDATA1
666
+ elsif data.bytesize <= 65535
667
+ return opcode == OP_PUSHDATA2
668
+ end
669
+ true
670
+ end
671
+
672
+ def verify_pushdata_length(chunk)
673
+ buf = StringIO.new(chunk)
674
+ opcode = buf.read(1).ord
675
+ offset = 1
676
+ len = case opcode
677
+ when OP_PUSHDATA1
678
+ offset += 1
679
+ buf.read(1).unpack('C').first
680
+ when OP_PUSHDATA2
681
+ offset += 2
682
+ buf.read(2).unpack('v').first
683
+ when OP_PUSHDATA4
684
+ offset += 4
685
+ buf.read(4).unpack('V').first
686
+ else
687
+ opcode
688
+ end
689
+ chunk.bytesize == len + offset
690
+ end
691
+
692
+ end
693
+
694
+ end