Line data Source code
1 : // Copyright (c) 2017 The Bitcoin Core developers
2 : // Distributed under the MIT software license, see the accompanying
3 : // file COPYING or https://www.opensource.org/licenses/mit-license.php.
4 :
5 : #include "key.h"
6 : #include "keystore.h"
7 : #include "script/ismine.h"
8 : #include "script/script.h"
9 : #include "script/standard.h"
10 : #include "test/test_pivx.h"
11 :
12 : #include <boost/test/unit_test.hpp>
13 :
14 :
15 : BOOST_FIXTURE_TEST_SUITE(script_standard_tests, BasicTestingSetup)
16 :
17 2 : BOOST_AUTO_TEST_CASE(script_standard_Solver_success)
18 : {
19 8 : CKey keys[3];
20 4 : CPubKey pubkeys[3];
21 4 : for (int i = 0; i < 3; i++) {
22 3 : keys[i].MakeNewKey(true);
23 3 : pubkeys[i] = keys[i].GetPubKey();
24 : }
25 :
26 2 : CScript s;
27 1 : txnouttype whichType;
28 2 : std::vector<std::vector<unsigned char> > solutions;
29 :
30 : // TX_PUBKEY
31 1 : s.clear();
32 1 : s << ToByteVector(pubkeys[0]) << OP_CHECKSIG;
33 2 : BOOST_CHECK(Solver(s, whichType, solutions));
34 1 : BOOST_CHECK_EQUAL(whichType, TX_PUBKEY);
35 1 : BOOST_CHECK_EQUAL(solutions.size(), 1);
36 3 : BOOST_CHECK(solutions[0] == ToByteVector(pubkeys[0]));
37 :
38 : // TX_PUBKEYHASH
39 1 : s.clear();
40 1 : s << OP_DUP << OP_HASH160 << ToByteVector(pubkeys[0].GetID()) << OP_EQUALVERIFY << OP_CHECKSIG;
41 2 : BOOST_CHECK(Solver(s, whichType, solutions));
42 1 : BOOST_CHECK_EQUAL(whichType, TX_PUBKEYHASH);
43 1 : BOOST_CHECK_EQUAL(solutions.size(), 1);
44 3 : BOOST_CHECK(solutions[0] == ToByteVector(pubkeys[0].GetID()));
45 :
46 : // TX_EXCHANGEADDR
47 1 : s.clear();
48 1 : s << OP_EXCHANGEADDR << OP_DUP << OP_HASH160 << ToByteVector(pubkeys[0].GetID()) << OP_EQUALVERIFY << OP_CHECKSIG;
49 2 : BOOST_CHECK(Solver(s, whichType, solutions));
50 1 : BOOST_CHECK_EQUAL(whichType, TX_EXCHANGEADDR);
51 1 : BOOST_CHECK_EQUAL(solutions.size(), 1);
52 3 : BOOST_CHECK(solutions[0] == ToByteVector(pubkeys[0].GetID()));
53 :
54 : // TX_SCRIPTHASH
55 2 : CScript redeemScript(s); // initialize with leftover P2PKH script
56 1 : s.clear();
57 1 : s << OP_HASH160 << ToByteVector(CScriptID(redeemScript)) << OP_EQUAL;
58 2 : BOOST_CHECK(Solver(s, whichType, solutions));
59 1 : BOOST_CHECK_EQUAL(whichType, TX_SCRIPTHASH);
60 1 : BOOST_CHECK_EQUAL(solutions.size(), 1);
61 3 : BOOST_CHECK(solutions[0] == ToByteVector(CScriptID(redeemScript)));
62 :
63 : // TX_MULTISIG
64 1 : s.clear();
65 1 : s << OP_1 <<
66 1 : ToByteVector(pubkeys[0]) <<
67 2 : ToByteVector(pubkeys[1]) <<
68 1 : OP_2 << OP_CHECKMULTISIG;
69 2 : BOOST_CHECK(Solver(s, whichType, solutions));
70 1 : BOOST_CHECK_EQUAL(whichType, TX_MULTISIG);
71 1 : BOOST_CHECK_EQUAL(solutions.size(), 4);
72 3 : BOOST_CHECK(solutions[0] == std::vector<unsigned char>({1}));
73 3 : BOOST_CHECK(solutions[1] == ToByteVector(pubkeys[0]));
74 3 : BOOST_CHECK(solutions[2] == ToByteVector(pubkeys[1]));
75 3 : BOOST_CHECK(solutions[3] == std::vector<unsigned char>({2}));
76 :
77 1 : s.clear();
78 1 : s << OP_2 <<
79 1 : ToByteVector(pubkeys[0]) <<
80 2 : ToByteVector(pubkeys[1]) <<
81 2 : ToByteVector(pubkeys[2]) <<
82 1 : OP_3 << OP_CHECKMULTISIG;
83 2 : BOOST_CHECK(Solver(s, whichType, solutions));
84 1 : BOOST_CHECK_EQUAL(whichType, TX_MULTISIG);
85 1 : BOOST_CHECK_EQUAL(solutions.size(), 5);
86 3 : BOOST_CHECK(solutions[0] == std::vector<unsigned char>({2}));
87 3 : BOOST_CHECK(solutions[1] == ToByteVector(pubkeys[0]));
88 3 : BOOST_CHECK(solutions[2] == ToByteVector(pubkeys[1]));
89 3 : BOOST_CHECK(solutions[3] == ToByteVector(pubkeys[2]));
90 3 : BOOST_CHECK(solutions[4] == std::vector<unsigned char>({3}));
91 :
92 : // TX_NULL_DATA
93 1 : s.clear();
94 1 : s << OP_RETURN <<
95 1 : std::vector<unsigned char>({0}) <<
96 2 : std::vector<unsigned char>({75}) <<
97 2 : std::vector<unsigned char>({255});
98 2 : BOOST_CHECK(Solver(s, whichType, solutions));
99 1 : BOOST_CHECK_EQUAL(whichType, TX_NULL_DATA);
100 1 : BOOST_CHECK_EQUAL(solutions.size(), 0);
101 :
102 : // TX_NONSTANDARD
103 1 : s.clear();
104 1 : s << OP_9 << OP_ADD << OP_11 << OP_EQUAL;
105 2 : BOOST_CHECK(!Solver(s, whichType, solutions));
106 1 : BOOST_CHECK_EQUAL(whichType, TX_NONSTANDARD);
107 1 : }
108 :
109 2 : BOOST_AUTO_TEST_CASE(script_standard_Solver_failure)
110 : {
111 1 : CKey key;
112 1 : CPubKey pubkey;
113 1 : key.MakeNewKey(true);
114 1 : pubkey = key.GetPubKey();
115 :
116 2 : CScript s;
117 1 : txnouttype whichType;
118 2 : std::vector<std::vector<unsigned char> > solutions;
119 :
120 : // TX_PUBKEY with incorrectly sized pubkey
121 1 : s.clear();
122 1 : s << std::vector<unsigned char>(30, 0x01) << OP_CHECKSIG;
123 2 : BOOST_CHECK(!Solver(s, whichType, solutions));
124 :
125 : // TX_PUBKEYHASH with incorrectly sized key hash
126 1 : s.clear();
127 1 : s << OP_DUP << OP_HASH160 << ToByteVector(pubkey) << OP_EQUALVERIFY << OP_CHECKSIG;
128 2 : BOOST_CHECK(!Solver(s, whichType, solutions));
129 :
130 : // TX_EXCHANGEADDR with incorrectly sized key hash
131 1 : s.clear();
132 1 : s << OP_EXCHANGEADDR << OP_DUP << OP_HASH160 << ToByteVector(pubkey) << OP_EQUALVERIFY << OP_CHECKSIG;
133 2 : BOOST_CHECK(!Solver(s, whichType, solutions));
134 :
135 : // TX_SCRIPTHASH with incorrectly sized script hash
136 1 : s.clear();
137 1 : s << OP_HASH160 << std::vector<unsigned char>(21, 0x01) << OP_EQUAL;
138 2 : BOOST_CHECK(!Solver(s, whichType, solutions));
139 :
140 : // TX_MULTISIG 0/2
141 1 : s.clear();
142 1 : s << OP_0 << ToByteVector(pubkey) << OP_1 << OP_CHECKMULTISIG;
143 2 : BOOST_CHECK(!Solver(s, whichType, solutions));
144 :
145 : // TX_MULTISIG 2/1
146 1 : s.clear();
147 1 : s << OP_2 << ToByteVector(pubkey) << OP_1 << OP_CHECKMULTISIG;
148 2 : BOOST_CHECK(!Solver(s, whichType, solutions));
149 :
150 : // TX_MULTISIG n = 2 with 1 pubkey
151 1 : s.clear();
152 1 : s << OP_1 << ToByteVector(pubkey) << OP_2 << OP_CHECKMULTISIG;
153 2 : BOOST_CHECK(!Solver(s, whichType, solutions));
154 :
155 : // TX_MULTISIG n = 1 with 0 pubkeys
156 1 : s.clear();
157 1 : s << OP_1 << OP_1 << OP_CHECKMULTISIG;
158 2 : BOOST_CHECK(!Solver(s, whichType, solutions));
159 :
160 : // TX_NULL_DATA with other opcodes
161 1 : s.clear();
162 1 : s << OP_RETURN << std::vector<unsigned char>({75}) << OP_ADD;
163 2 : BOOST_CHECK(!Solver(s, whichType, solutions));
164 :
165 : // TX_WITNESS with incorrect program size
166 1 : s.clear();
167 1 : s << OP_0 << std::vector<unsigned char>(19, 0x01);
168 2 : BOOST_CHECK(!Solver(s, whichType, solutions));
169 1 : }
170 :
171 2 : BOOST_AUTO_TEST_CASE(script_standard_ExtractDestination)
172 : {
173 1 : CKey key;
174 1 : CPubKey pubkey;
175 1 : key.MakeNewKey(true);
176 1 : pubkey = key.GetPubKey();
177 :
178 2 : CScript s;
179 2 : CTxDestination address;
180 :
181 : // TX_PUBKEY
182 1 : s.clear();
183 1 : s << ToByteVector(pubkey) << OP_CHECKSIG;
184 2 : BOOST_CHECK(ExtractDestination(s, address));
185 3 : BOOST_CHECK(boost::get<CKeyID>(&address) &&
186 : *boost::get<CKeyID>(&address) == pubkey.GetID());
187 :
188 : // TX_PUBKEYHASH
189 1 : s.clear();
190 1 : s << OP_DUP << OP_HASH160 << ToByteVector(pubkey.GetID()) << OP_EQUALVERIFY << OP_CHECKSIG;
191 2 : BOOST_CHECK(ExtractDestination(s, address));
192 3 : BOOST_CHECK(boost::get<CKeyID>(&address) &&
193 : *boost::get<CKeyID>(&address) == pubkey.GetID());
194 :
195 : // TX_EXCHANGEADDR
196 1 : s.clear();
197 1 : s << OP_EXCHANGEADDR << OP_DUP << OP_HASH160 << ToByteVector(pubkey.GetID()) << OP_EQUALVERIFY << OP_CHECKSIG;
198 2 : BOOST_CHECK(ExtractDestination(s, address));
199 3 : BOOST_CHECK(boost::get<CExchangeKeyID>(&address) &&
200 : *boost::get<CExchangeKeyID>(&address) == pubkey.GetID());
201 :
202 : // TX_SCRIPTHASH
203 2 : CScript redeemScript(s); // initialize with leftover P2PKH script
204 1 : s.clear();
205 1 : s << OP_HASH160 << ToByteVector(CScriptID(redeemScript)) << OP_EQUAL;
206 2 : BOOST_CHECK(ExtractDestination(s, address));
207 3 : BOOST_CHECK(boost::get<CScriptID>(&address) &&
208 : *boost::get<CScriptID>(&address) == CScriptID(redeemScript));
209 :
210 : // TX_MULTISIG
211 1 : s.clear();
212 1 : s << OP_1 << ToByteVector(pubkey) << OP_1 << OP_CHECKMULTISIG;
213 2 : BOOST_CHECK(!ExtractDestination(s, address));
214 :
215 : // TX_NULL_DATA
216 1 : s.clear();
217 1 : s << OP_RETURN << std::vector<unsigned char>({75});
218 2 : BOOST_CHECK(!ExtractDestination(s, address));
219 1 : }
220 :
221 2 : BOOST_AUTO_TEST_CASE(script_standard_ExtractDestinations)
222 : {
223 8 : CKey keys[3];
224 4 : CPubKey pubkeys[3];
225 4 : for (int i = 0; i < 3; i++) {
226 3 : keys[i].MakeNewKey(true);
227 3 : pubkeys[i] = keys[i].GetPubKey();
228 : }
229 :
230 2 : CScript s;
231 1 : txnouttype whichType;
232 2 : std::vector<CTxDestination> addresses;
233 1 : int nRequired;
234 :
235 : // TX_PUBKEY
236 1 : s.clear();
237 1 : s << ToByteVector(pubkeys[0]) << OP_CHECKSIG;
238 2 : BOOST_CHECK(ExtractDestinations(s, whichType, addresses, nRequired));
239 1 : BOOST_CHECK_EQUAL(whichType, TX_PUBKEY);
240 1 : BOOST_CHECK_EQUAL(addresses.size(), 1);
241 1 : BOOST_CHECK_EQUAL(nRequired, 1);
242 4 : BOOST_CHECK(boost::get<CKeyID>(&addresses[0]) &&
243 : *boost::get<CKeyID>(&addresses[0]) == pubkeys[0].GetID());
244 :
245 : // TX_PUBKEYHASH
246 1 : s.clear();
247 1 : s << OP_DUP << OP_HASH160 << ToByteVector(pubkeys[0].GetID()) << OP_EQUALVERIFY << OP_CHECKSIG;
248 2 : BOOST_CHECK(ExtractDestinations(s, whichType, addresses, nRequired));
249 1 : BOOST_CHECK_EQUAL(whichType, TX_PUBKEYHASH);
250 1 : BOOST_CHECK_EQUAL(addresses.size(), 1);
251 1 : BOOST_CHECK_EQUAL(nRequired, 1);
252 4 : BOOST_CHECK(boost::get<CKeyID>(&addresses[0]) &&
253 : *boost::get<CKeyID>(&addresses[0]) == pubkeys[0].GetID());
254 :
255 : // TX_EXCHANGEADDR
256 1 : s.clear();
257 1 : s << OP_EXCHANGEADDR << OP_DUP << OP_HASH160 << ToByteVector(pubkeys[0].GetID()) << OP_EQUALVERIFY << OP_CHECKSIG;
258 2 : BOOST_CHECK(ExtractDestinations(s, whichType, addresses, nRequired));
259 1 : BOOST_CHECK_EQUAL(whichType, TX_EXCHANGEADDR);
260 1 : BOOST_CHECK_EQUAL(addresses.size(), 1);
261 1 : BOOST_CHECK_EQUAL(nRequired, 1);
262 4 : BOOST_CHECK(boost::get<CExchangeKeyID>(&addresses[0]) &&
263 : *boost::get<CExchangeKeyID>(&addresses[0]) == pubkeys[0].GetID());
264 :
265 : // TX_SCRIPTHASH
266 2 : CScript redeemScript(s); // initialize with leftover P2PKH script
267 1 : s.clear();
268 1 : s << OP_HASH160 << ToByteVector(CScriptID(redeemScript)) << OP_EQUAL;
269 2 : BOOST_CHECK(ExtractDestinations(s, whichType, addresses, nRequired));
270 1 : BOOST_CHECK_EQUAL(whichType, TX_SCRIPTHASH);
271 1 : BOOST_CHECK_EQUAL(addresses.size(), 1);
272 1 : BOOST_CHECK_EQUAL(nRequired, 1);
273 4 : BOOST_CHECK(boost::get<CScriptID>(&addresses[0]) &&
274 : *boost::get<CScriptID>(&addresses[0]) == CScriptID(redeemScript));
275 :
276 : // TX_MULTISIG
277 1 : s.clear();
278 1 : s << OP_2 <<
279 1 : ToByteVector(pubkeys[0]) <<
280 2 : ToByteVector(pubkeys[1]) <<
281 1 : OP_2 << OP_CHECKMULTISIG;
282 2 : BOOST_CHECK(ExtractDestinations(s, whichType, addresses, nRequired));
283 1 : BOOST_CHECK_EQUAL(whichType, TX_MULTISIG);
284 1 : BOOST_CHECK_EQUAL(addresses.size(), 2);
285 1 : BOOST_CHECK_EQUAL(nRequired, 2);
286 4 : BOOST_CHECK(boost::get<CKeyID>(&addresses[0]) &&
287 : *boost::get<CKeyID>(&addresses[0]) == pubkeys[0].GetID());
288 4 : BOOST_CHECK(boost::get<CKeyID>(&addresses[1]) &&
289 : *boost::get<CKeyID>(&addresses[1]) == pubkeys[1].GetID());
290 :
291 : // TX_NULL_DATA
292 1 : s.clear();
293 1 : s << OP_RETURN << std::vector<unsigned char>({75});
294 2 : BOOST_CHECK(!ExtractDestinations(s, whichType, addresses, nRequired));
295 1 : }
296 :
297 2 : BOOST_AUTO_TEST_CASE(script_standard_GetScriptFor_)
298 : {
299 8 : CKey keys[3];
300 4 : CPubKey pubkeys[3];
301 4 : for (int i = 0; i < 3; i++) {
302 3 : keys[i].MakeNewKey(true);
303 3 : pubkeys[i] = keys[i].GetPubKey();
304 : }
305 :
306 3 : CScript expected, result;
307 :
308 : // CKeyID
309 1 : expected.clear();
310 1 : expected << OP_DUP << OP_HASH160 << ToByteVector(pubkeys[0].GetID()) << OP_EQUALVERIFY << OP_CHECKSIG;
311 1 : result = GetScriptForDestination(pubkeys[0].GetID());
312 2 : BOOST_CHECK(result == expected);
313 :
314 : // CScriptID
315 2 : CScript redeemScript(result);
316 1 : expected.clear();
317 1 : expected << OP_HASH160 << ToByteVector(CScriptID(redeemScript)) << OP_EQUAL;
318 1 : result = GetScriptForDestination(CScriptID(redeemScript));
319 2 : BOOST_CHECK(result == expected);
320 :
321 : // CNoDestination
322 1 : expected.clear();
323 1 : result = GetScriptForDestination(CNoDestination());
324 2 : BOOST_CHECK(result == expected);
325 :
326 : // GetScriptForRawPubKey
327 1 : expected.clear();
328 1 : expected << ToByteVector(pubkeys[0]) << OP_CHECKSIG;
329 1 : result = GetScriptForRawPubKey(pubkeys[0]);
330 2 : BOOST_CHECK(result == expected);
331 :
332 : // GetScriptForMultisig
333 1 : expected.clear();
334 1 : expected << OP_2 <<
335 1 : ToByteVector(pubkeys[0]) <<
336 2 : ToByteVector(pubkeys[1]) <<
337 2 : ToByteVector(pubkeys[2]) <<
338 1 : OP_3 << OP_CHECKMULTISIG;
339 2 : result = GetScriptForMultisig(2, std::vector<CPubKey>(pubkeys, pubkeys + 3));
340 2 : BOOST_CHECK(result == expected);
341 1 : }
342 :
343 2 : BOOST_AUTO_TEST_CASE(script_standard_IsMine)
344 : {
345 6 : CKey keys[2];
346 3 : CPubKey pubkeys[2];
347 3 : for (int i = 0; i < 2; i++) {
348 2 : keys[i].MakeNewKey(true);
349 2 : pubkeys[i] = keys[i].GetPubKey();
350 : }
351 :
352 2 : CKey uncompressedKey;
353 1 : uncompressedKey.MakeNewKey(false);
354 1 : CPubKey uncompressedPubkey = uncompressedKey.GetPubKey();
355 :
356 2 : CScript scriptPubKey;
357 1 : isminetype result;
358 :
359 : // P2PK compressed
360 1 : {
361 2 : CBasicKeyStore keystore;
362 1 : scriptPubKey.clear();
363 1 : scriptPubKey << ToByteVector(pubkeys[0]) << OP_CHECKSIG;
364 :
365 : // Keystore does not have key
366 1 : result = IsMine(keystore, scriptPubKey);
367 1 : BOOST_CHECK_EQUAL(result, ISMINE_NO);
368 :
369 : // Keystore has key
370 1 : keystore.AddKey(keys[0]);
371 1 : result = IsMine(keystore, scriptPubKey);
372 1 : BOOST_CHECK_EQUAL(result, ISMINE_SPENDABLE);
373 : }
374 :
375 : // P2PK uncompressed
376 1 : {
377 2 : CBasicKeyStore keystore;
378 1 : scriptPubKey.clear();
379 1 : scriptPubKey << ToByteVector(uncompressedPubkey) << OP_CHECKSIG;
380 :
381 : // Keystore does not have key
382 1 : result = IsMine(keystore, scriptPubKey);
383 1 : BOOST_CHECK_EQUAL(result, ISMINE_NO);
384 :
385 : // Keystore has key
386 1 : keystore.AddKey(uncompressedKey);
387 1 : result = IsMine(keystore, scriptPubKey);
388 1 : BOOST_CHECK_EQUAL(result, ISMINE_SPENDABLE);
389 : }
390 :
391 : // P2PKH compressed
392 1 : {
393 2 : CBasicKeyStore keystore;
394 1 : scriptPubKey.clear();
395 1 : scriptPubKey << OP_DUP << OP_HASH160 << ToByteVector(pubkeys[0].GetID()) << OP_EQUALVERIFY << OP_CHECKSIG;
396 :
397 : // Keystore does not have key
398 1 : result = IsMine(keystore, scriptPubKey);
399 1 : BOOST_CHECK_EQUAL(result, ISMINE_NO);
400 :
401 : // Keystore has key
402 1 : keystore.AddKey(keys[0]);
403 1 : result = IsMine(keystore, scriptPubKey);
404 1 : BOOST_CHECK_EQUAL(result, ISMINE_SPENDABLE);
405 : }
406 :
407 : // P2PKH uncompressed
408 1 : {
409 2 : CBasicKeyStore keystore;
410 1 : scriptPubKey.clear();
411 1 : scriptPubKey << OP_DUP << OP_HASH160 << ToByteVector(uncompressedPubkey.GetID()) << OP_EQUALVERIFY << OP_CHECKSIG;
412 :
413 : // Keystore does not have key
414 1 : result = IsMine(keystore, scriptPubKey);
415 1 : BOOST_CHECK_EQUAL(result, ISMINE_NO);
416 :
417 : // Keystore has key
418 1 : keystore.AddKey(uncompressedKey);
419 1 : result = IsMine(keystore, scriptPubKey);
420 1 : BOOST_CHECK_EQUAL(result, ISMINE_SPENDABLE);
421 : }
422 :
423 : // P2SH
424 1 : {
425 1 : CBasicKeyStore keystore;
426 :
427 2 : CScript redeemScript;
428 1 : redeemScript << OP_DUP << OP_HASH160 << ToByteVector(pubkeys[0].GetID()) << OP_EQUALVERIFY << OP_CHECKSIG;
429 :
430 1 : scriptPubKey.clear();
431 1 : scriptPubKey << OP_HASH160 << ToByteVector(CScriptID(redeemScript)) << OP_EQUAL;
432 :
433 : // Keystore does not have redeemScript or key
434 1 : result = IsMine(keystore, scriptPubKey);
435 1 : BOOST_CHECK_EQUAL(result, ISMINE_NO);
436 :
437 : // Keystore has redeemScript but no key
438 1 : keystore.AddCScript(redeemScript);
439 1 : result = IsMine(keystore, scriptPubKey);
440 1 : BOOST_CHECK_EQUAL(result, ISMINE_NO);
441 :
442 : // Keystore has redeemScript and key
443 1 : keystore.AddKey(keys[0]);
444 1 : result = IsMine(keystore, scriptPubKey);
445 1 : BOOST_CHECK_EQUAL(result, ISMINE_SPENDABLE);
446 : }
447 :
448 : // scriptPubKey multisig
449 1 : {
450 2 : CBasicKeyStore keystore;
451 :
452 1 : scriptPubKey.clear();
453 1 : scriptPubKey << OP_2 <<
454 1 : ToByteVector(uncompressedPubkey) <<
455 2 : ToByteVector(pubkeys[1]) <<
456 1 : OP_2 << OP_CHECKMULTISIG;
457 :
458 : // Keystore does not have any keys
459 1 : result = IsMine(keystore, scriptPubKey);
460 1 : BOOST_CHECK_EQUAL(result, ISMINE_NO);
461 :
462 : // Keystore has 1/2 keys
463 1 : keystore.AddKey(uncompressedKey);
464 :
465 1 : result = IsMine(keystore, scriptPubKey);
466 1 : BOOST_CHECK_EQUAL(result, ISMINE_NO);
467 :
468 : // Keystore has 2/2 keys
469 1 : keystore.AddKey(keys[1]);
470 :
471 1 : result = IsMine(keystore, scriptPubKey);
472 1 : BOOST_CHECK_EQUAL(result, ISMINE_SPENDABLE);
473 : }
474 :
475 : // P2SH multisig
476 1 : {
477 1 : CBasicKeyStore keystore;
478 1 : keystore.AddKey(uncompressedKey);
479 1 : keystore.AddKey(keys[1]);
480 :
481 2 : CScript redeemScript;
482 1 : redeemScript << OP_2 <<
483 1 : ToByteVector(uncompressedPubkey) <<
484 2 : ToByteVector(pubkeys[1]) <<
485 1 : OP_2 << OP_CHECKMULTISIG;
486 :
487 1 : scriptPubKey.clear();
488 1 : scriptPubKey << OP_HASH160 << ToByteVector(CScriptID(redeemScript)) << OP_EQUAL;
489 :
490 : // Keystore has no redeemScript
491 1 : result = IsMine(keystore, scriptPubKey);
492 1 : BOOST_CHECK_EQUAL(result, ISMINE_NO);
493 :
494 : // Keystore has redeemScript
495 1 : keystore.AddCScript(redeemScript);
496 1 : result = IsMine(keystore, scriptPubKey);
497 1 : BOOST_CHECK_EQUAL(result, ISMINE_SPENDABLE);
498 : }
499 :
500 : // OP_RETURN
501 1 : {
502 2 : CBasicKeyStore keystore;
503 1 : keystore.AddKey(keys[0]);
504 :
505 1 : scriptPubKey.clear();
506 1 : scriptPubKey << OP_RETURN << ToByteVector(pubkeys[0]);
507 :
508 1 : result = IsMine(keystore, scriptPubKey);
509 1 : BOOST_CHECK_EQUAL(result, ISMINE_NO);
510 : }
511 :
512 : // Nonstandard
513 1 : {
514 2 : CBasicKeyStore keystore;
515 1 : keystore.AddKey(keys[0]);
516 :
517 1 : scriptPubKey.clear();
518 1 : scriptPubKey << OP_9 << OP_ADD << OP_11 << OP_EQUAL;
519 :
520 1 : result = IsMine(keystore, scriptPubKey);
521 1 : BOOST_CHECK_EQUAL(result, ISMINE_NO);
522 : }
523 1 : }
524 :
525 : BOOST_AUTO_TEST_SUITE_END()
|