1 // Copyright (c) 2009-2010 Satoshi Nakamoto
2 // Copyright (c) 2009-2014 The Bitcoin Core developers
3 // Distributed under the MIT software license, see the accompanying
4 // file COPYING or http://www.opensource.org/licenses/mit-license.php.
8 #include "tinyformat.h"
9 #include "utilstrencodings.h"
10 #include "script/cc.h"
12 #include "cryptoconditions/include/cryptoconditions.h"
14 #include "pbaas/reserves.h"
19 inline std::string ValueString(const std::vector<unsigned char>& vch)
22 return strprintf("%d", CScriptNum(vch, false).getint());
28 const char* GetOpName(opcodetype opcode)
33 case OP_0 : return "0";
34 case OP_PUSHDATA1 : return "OP_PUSHDATA1";
35 case OP_PUSHDATA2 : return "OP_PUSHDATA2";
36 case OP_PUSHDATA4 : return "OP_PUSHDATA4";
37 case OP_1NEGATE : return "-1";
38 case OP_RESERVED : return "OP_RESERVED";
39 case OP_1 : return "1";
40 case OP_2 : return "2";
41 case OP_3 : return "3";
42 case OP_4 : return "4";
43 case OP_5 : return "5";
44 case OP_6 : return "6";
45 case OP_7 : return "7";
46 case OP_8 : return "8";
47 case OP_9 : return "9";
48 case OP_10 : return "10";
49 case OP_11 : return "11";
50 case OP_12 : return "12";
51 case OP_13 : return "13";
52 case OP_14 : return "14";
53 case OP_15 : return "15";
54 case OP_16 : return "16";
57 case OP_NOP : return "OP_NOP";
58 case OP_VER : return "OP_VER";
59 case OP_IF : return "OP_IF";
60 case OP_NOTIF : return "OP_NOTIF";
61 case OP_VERIF : return "OP_VERIF";
62 case OP_VERNOTIF : return "OP_VERNOTIF";
63 case OP_ELSE : return "OP_ELSE";
64 case OP_ENDIF : return "OP_ENDIF";
65 case OP_VERIFY : return "OP_VERIFY";
66 case OP_RETURN : return "OP_RETURN";
69 case OP_TOALTSTACK : return "OP_TOALTSTACK";
70 case OP_FROMALTSTACK : return "OP_FROMALTSTACK";
71 case OP_2DROP : return "OP_2DROP";
72 case OP_2DUP : return "OP_2DUP";
73 case OP_3DUP : return "OP_3DUP";
74 case OP_2OVER : return "OP_2OVER";
75 case OP_2ROT : return "OP_2ROT";
76 case OP_2SWAP : return "OP_2SWAP";
77 case OP_IFDUP : return "OP_IFDUP";
78 case OP_DEPTH : return "OP_DEPTH";
79 case OP_DROP : return "OP_DROP";
80 case OP_DUP : return "OP_DUP";
81 case OP_NIP : return "OP_NIP";
82 case OP_OVER : return "OP_OVER";
83 case OP_PICK : return "OP_PICK";
84 case OP_ROLL : return "OP_ROLL";
85 case OP_ROT : return "OP_ROT";
86 case OP_SWAP : return "OP_SWAP";
87 case OP_TUCK : return "OP_TUCK";
90 case OP_CAT : return "OP_CAT";
91 case OP_SUBSTR : return "OP_SUBSTR";
92 case OP_LEFT : return "OP_LEFT";
93 case OP_RIGHT : return "OP_RIGHT";
94 case OP_SIZE : return "OP_SIZE";
97 case OP_INVERT : return "OP_INVERT";
98 case OP_AND : return "OP_AND";
99 case OP_OR : return "OP_OR";
100 case OP_XOR : return "OP_XOR";
101 case OP_EQUAL : return "OP_EQUAL";
102 case OP_EQUALVERIFY : return "OP_EQUALVERIFY";
103 case OP_RESERVED1 : return "OP_RESERVED1";
104 case OP_RESERVED2 : return "OP_RESERVED2";
107 case OP_1ADD : return "OP_1ADD";
108 case OP_1SUB : return "OP_1SUB";
109 case OP_2MUL : return "OP_2MUL";
110 case OP_2DIV : return "OP_2DIV";
111 case OP_NEGATE : return "OP_NEGATE";
112 case OP_ABS : return "OP_ABS";
113 case OP_NOT : return "OP_NOT";
114 case OP_0NOTEQUAL : return "OP_0NOTEQUAL";
115 case OP_ADD : return "OP_ADD";
116 case OP_SUB : return "OP_SUB";
117 case OP_MUL : return "OP_MUL";
118 case OP_DIV : return "OP_DIV";
119 case OP_MOD : return "OP_MOD";
120 case OP_LSHIFT : return "OP_LSHIFT";
121 case OP_RSHIFT : return "OP_RSHIFT";
122 case OP_BOOLAND : return "OP_BOOLAND";
123 case OP_BOOLOR : return "OP_BOOLOR";
124 case OP_NUMEQUAL : return "OP_NUMEQUAL";
125 case OP_NUMEQUALVERIFY : return "OP_NUMEQUALVERIFY";
126 case OP_NUMNOTEQUAL : return "OP_NUMNOTEQUAL";
127 case OP_LESSTHAN : return "OP_LESSTHAN";
128 case OP_GREATERTHAN : return "OP_GREATERTHAN";
129 case OP_LESSTHANOREQUAL : return "OP_LESSTHANOREQUAL";
130 case OP_GREATERTHANOREQUAL : return "OP_GREATERTHANOREQUAL";
131 case OP_MIN : return "OP_MIN";
132 case OP_MAX : return "OP_MAX";
133 case OP_WITHIN : return "OP_WITHIN";
136 case OP_RIPEMD160 : return "OP_RIPEMD160";
137 case OP_SHA1 : return "OP_SHA1";
138 case OP_SHA256 : return "OP_SHA256";
139 case OP_HASH160 : return "OP_HASH160";
140 case OP_HASH256 : return "OP_HASH256";
141 case OP_CODESEPARATOR : return "OP_CODESEPARATOR";
142 case OP_CHECKSIG : return "OP_CHECKSIG";
143 case OP_CHECKSIGVERIFY : return "OP_CHECKSIGVERIFY";
144 case OP_CHECKMULTISIG : return "OP_CHECKMULTISIG";
145 case OP_CHECKMULTISIGVERIFY : return "OP_CHECKMULTISIGVERIFY";
146 case OP_CHECKCRYPTOCONDITION : return "OP_CHECKCRYPTOCONDITION";
147 case OP_CHECKCRYPTOCONDITIONVERIFY
148 : return "OP_CHECKCRYPTOCONDITIONVERIFY";
151 case OP_NOP1 : return "OP_NOP1";
152 case OP_NOP2 : return "OP_NOP2";
153 case OP_NOP3 : return "OP_NOP3";
154 case OP_NOP4 : return "OP_NOP4";
155 case OP_NOP5 : return "OP_NOP5";
156 case OP_NOP6 : return "OP_NOP6";
157 case OP_NOP7 : return "OP_NOP7";
158 case OP_NOP8 : return "OP_NOP8";
159 case OP_NOP9 : return "OP_NOP9";
160 case OP_NOP10 : return "OP_NOP10";
162 case OP_INVALIDOPCODE : return "OP_INVALIDOPCODE";
165 // The template matching params OP_SMALLDATA/etc are defined in opcodetype enum
166 // as kind of implementation hack, they are *NOT* real opcodes. If found in real
167 // Script, just let the default: case deal with them.
174 unsigned int CScript::GetSigOpCount(bool fAccurate) const
177 const_iterator pc = begin();
178 opcodetype lastOpcode = OP_INVALIDOPCODE;
182 if (!GetOp(pc, opcode))
184 if (opcode == OP_CHECKSIG || opcode == OP_CHECKSIGVERIFY)
186 else if (opcode == OP_CHECKMULTISIG || opcode == OP_CHECKMULTISIGVERIFY)
188 if (fAccurate && lastOpcode >= OP_1 && lastOpcode <= OP_16)
189 n += DecodeOP_N(lastOpcode);
198 unsigned int CScript::GetSigOpCount(const CScript& scriptSig) const
200 if (!IsPayToScriptHash())
201 return GetSigOpCount(true);
203 // This is a pay-to-script-hash scriptPubKey;
204 // get the last item that the scriptSig
205 // pushes onto the stack:
206 const_iterator pc = scriptSig.begin();
207 vector<unsigned char> data;
208 while (pc < scriptSig.end())
211 if (!scriptSig.GetOp(pc, opcode, data))
217 /// ... and return its opcount:
218 CScript subscript(data.begin(), data.end());
219 return subscript.GetSigOpCount(true);
222 bool CScript::IsPayToPublicKeyHash() const
224 // Extra-fast test for pay-to-pubkey-hash CScripts:
225 return (this->size() == 25 &&
226 (*this)[0] == OP_DUP &&
227 (*this)[1] == OP_HASH160 &&
228 (*this)[2] == 0x14 &&
229 (*this)[23] == OP_EQUALVERIFY &&
230 (*this)[24] == OP_CHECKSIG);
233 bool CScript::IsPayToPublicKey() const
235 // Extra-fast test for pay-to-pubkey CScripts:
236 return (this->size() == 35 &&
238 (*this)[34] == OP_CHECKSIG);
241 bool CScript::IsPayToScriptHash() const
243 // Extra-fast test for pay-to-script-hash CScripts:
244 return (this->size() == 23 &&
245 (*this)[0] == OP_HASH160 &&
246 (*this)[1] == 0x14 &&
247 (*this)[22] == OP_EQUAL);
250 // this returns true if either there is nothing left and pc points at the end, or
251 // all instructions from the pc to the end of the script are balanced pushes and pops
252 // if there is data, it also returns all the values as byte vectors in a list of vectors
253 bool CScript::GetBalancedData(const_iterator& pc, std::vector<std::vector<unsigned char>>& vSolutions) const
260 vector<unsigned char> data;
262 if (this->GetOp(pc, opcode, data))
264 if (opcode == OP_DROP)
266 // this should never pop what it hasn't pushed (like a success code)
278 vSolutions.push_back(data);
280 else if (opcode >= OP_1 && opcode <= OP_16)
283 data[0] = (opcode - OP_1) + 1;
284 vSolutions.push_back(data);
286 else if (opcode > 0 && opcode <= OP_PUSHDATA4 && data.size() > 0)
288 vSolutions.push_back(data);
297 return netPushes == 0;
300 // this returns true if either there is nothing left and pc points at the end
301 // if there is data, it also returns all the values as byte vectors in a list of vectors
302 bool CScript::GetPushedData(CScript::const_iterator pc, std::vector<std::vector<unsigned char>>& vData) const
304 vector<unsigned char> data;
306 std::vector<unsigned char> vch1 = std::vector<unsigned char>(1);
312 if (GetOp(pc, opcode, data))
317 vData.push_back(vch1);
319 else if (opcode >= OP_1 && opcode <= OP_16)
321 vch1[0] = (opcode - OP_1) + 1;
322 vData.push_back(vch1);
324 else if (opcode > 0 && opcode <= OP_PUSHDATA4 && data.size() > 0)
326 vData.push_back(data);
332 return vData.size() != 0;
335 // this returns true if either there is nothing left and pc points at the end
336 // if there is data, it also returns all the values as byte vectors in a list of vectors
337 bool CScript::GetOpretData(std::vector<std::vector<unsigned char>>& vData) const
339 vector<unsigned char> data;
341 CScript::const_iterator pc = this->begin();
343 if (GetOp(pc, opcode, data) && opcode == OP_RETURN)
345 return GetPushedData(pc, vData);
350 bool CScript::IsPayToCryptoCondition(CScript *pCCSubScript, std::vector<std::vector<unsigned char>>& vParams) const
352 const_iterator pc = begin();
353 vector<unsigned char> data;
355 if (this->GetOp(pc, opcode, data))
356 // Sha256 conditions are <76 bytes
357 if (opcode > OP_0 && opcode < OP_PUSHDATA1)
358 if (this->GetOp(pc, opcode, data))
359 if (opcode == OP_CHECKCRYPTOCONDITION)
361 const_iterator pcCCEnd = pc;
362 if (GetBalancedData(pc, vParams))
365 *pCCSubScript = CScript(begin(),pcCCEnd);
372 bool CScript::IsPayToCryptoCondition(CScript *pCCSubScript) const
374 std::vector<std::vector<unsigned char>> vParams;
375 return IsPayToCryptoCondition(pCCSubScript, vParams);
378 bool CScript::IsPayToCryptoCondition() const
380 return IsPayToCryptoCondition((CScript *)NULL);
383 bool CScript::IsInstantSpend() const
386 if (!IsPayToCryptoCondition(&ecode))
390 // only instant spend for now
391 return ecode == EVAL_EARNEDNOTARIZATION;
394 bool CScript::IsPayToCryptoCondition(COptCCParams &ccParams) const
397 std::vector<std::vector<unsigned char>> vParams;
399 if (IsPayToCryptoCondition(&subScript, vParams))
401 if (!vParams.empty())
403 ccParams = COptCCParams(vParams[0]);
410 bool CScript::IsPayToCryptoCondition(CScript *ccSubScript, std::vector<std::vector<unsigned char>> &vParams, COptCCParams &optParams) const
412 if (IsPayToCryptoCondition(ccSubScript, vParams))
414 if (vParams.size() > 0)
416 optParams = COptCCParams(vParams[0]);
417 return optParams.IsValid();
423 bool CScript::IsPayToCryptoCondition(uint32_t *ecode) const
426 std::vector<std::vector<unsigned char>> vParams;
428 if (IsPayToCryptoCondition(&sub, vParams, p))
436 CScript CScript::ReplaceCCParams(const COptCCParams ¶ms)
439 std::vector<std::vector<unsigned char>> vParams;
441 if (!this->IsPayToCryptoCondition(&subScript, vParams, p) || p.evalCode != params.evalCode)
446 // add the object to the end of the script
447 subScript << params.AsVector() << OP_DROP;
452 int64_t CScript::ReserveOutValue() const
457 // already validated above
458 if (::IsPayToCryptoCondition(*this, p) && p.IsValid())
462 case EVAL_RESERVE_OUTPUT:
464 CReserveOutput ro(p.vData[0]);
468 case EVAL_CURRENCYSTATE:
470 CCoinbaseCurrencyState cbcs(p.vData[0]);
471 return cbcs.ReserveOut.nValue;
474 case EVAL_RESERVE_TRANSFER:
476 CReserveTransfer rt(p.vData[0]);
480 case EVAL_RESERVE_EXCHANGE:
482 CReserveExchange re(p.vData[0]);
483 // reserve out amount when converting to reserve is 0, since the amount cannot be calculated in isolation as an input
484 // if reserve in, we can consider the output the same reserve value as the input
485 return (re.flags & re.TO_RESERVE) ? 0 : re.nValue;
493 int64_t CScript::ReserveOutValue(const CCurrencyState ¤cyState) const
498 // already validated above
499 if (::IsPayToCryptoCondition(*this, p) && p.IsValid())
503 case EVAL_RESERVE_OUTPUT:
505 CReserveOutput ro(p.vData[0]);
509 case EVAL_RESERVE_TRANSFER:
511 CReserveTransfer rt(p.vData[0]);
515 case EVAL_RESERVE_EXCHANGE:
517 CReserveExchange re(p.vData[0]);
518 // reserve out amount when converting to reserve is 0, since the amount cannot be calculated in isolation as an input
519 // if reserve in, we can consider the output the same reserve value as the input
520 return (re.flags & re.TO_RESERVE) ? currencyState.NativeToReserve(re.nValue) : re.nValue;
528 bool CScript::SetReserveOutValue(int64_t newValue)
533 // already validated above
534 if (::IsPayToCryptoCondition(*this, p) && p.IsValid())
538 case EVAL_RESERVE_OUTPUT:
540 CReserveOutput ro(p.vData[0]);
541 p.vData[0] = ro.AsVector();
544 case EVAL_RESERVE_TRANSFER:
546 CReserveTransfer rt(p.vData[0]);
547 rt.nValue = newValue;
548 p.vData[0] = rt.AsVector();
551 case EVAL_RESERVE_EXCHANGE:
553 CReserveExchange re(p.vData[0]);
554 re.nValue = newValue;
555 p.vData[0] = re.AsVector();
561 *this = ReplaceCCParams(p);
567 bool CScript::MayAcceptCryptoCondition() const
569 // Get the type mask of the condition
570 const_iterator pc = this->begin();
571 vector<unsigned char> data;
573 if (!this->GetOp(pc, opcode, data)) return false;
574 if (!(opcode > OP_0 && opcode < OP_PUSHDATA1)) return false;
575 CC *cond = cc_readConditionBinary(data.data(), data.size());
576 if (!cond) return false;
578 bool out = IsSupportedCryptoCondition(cond);
584 bool CScript::IsCoinImport() const
586 const_iterator pc = this->begin();
587 vector<unsigned char> data;
589 if (this->GetOp(pc, opcode, data))
590 if (opcode > OP_0 && opcode <= OP_PUSHDATA4)
591 return data.begin()[0] == EVAL_IMPORTCOIN;
595 bool CScript::IsPushOnly() const
597 const_iterator pc = begin();
601 if (!GetOp(pc, opcode))
603 // Note that IsPushOnly() *does* consider OP_RESERVED to be a
604 // push-type opcode, however execution of OP_RESERVED fails, so
605 // it's not relevant to P2SH/BIP62 as the scriptSig would fail prior to
606 // the P2SH special validation code being executed.
613 // if the front of the script has check lock time verify. this is a fairly simple check.
614 // accepts NULL as parameter if unlockTime is not needed.
615 bool CScript::IsCheckLockTimeVerify(int64_t *unlockTime) const
618 std::vector<unsigned char> unlockTimeParam = std::vector<unsigned char>();
619 CScript::const_iterator it = this->begin();
621 if (this->GetOp2(it, op, &unlockTimeParam))
623 if (unlockTimeParam.size() >= 0 && unlockTimeParam.size() < 6 &&
624 (*this)[unlockTimeParam.size() + 1] == OP_CHECKLOCKTIMEVERIFY)
626 int i = unlockTimeParam.size() - 1;
627 for (*unlockTime = 0; i >= 0; i--)
630 *unlockTime |= *((unsigned char *)unlockTimeParam.data() + i);
638 bool CScript::IsCheckLockTimeVerify() const
641 return this->IsCheckLockTimeVerify(&ult);
644 std::string CScript::ToString() const
648 std::vector<unsigned char> vch;
649 const_iterator pc = begin();
654 if (!GetOp(pc, opcode, vch))
659 if (0 <= opcode && opcode <= OP_PUSHDATA4)
660 str += ValueString(vch);
662 str += GetOpName(opcode);