// Copyright (c) 2009-2012 The Bitcoin developers
// Distributed under the MIT/X11 software license, see the accompanying
// file COPYING or http://www.opensource.org/licenses/mit-license.php.
-#include <boost/foreach.hpp>
-#include <boost/tuple/tuple.hpp>
-
-using namespace std;
-using namespace boost;
#include "script.h"
#include "keystore.h"
#include "sync.h"
#include "util.h"
-bool CheckSig(vector<unsigned char> vchSig, const vector<unsigned char> &vchPubKey, const CScript &scriptCode, const CTransaction& txTo, unsigned int nIn, int nHashType, int flags);
+bool CheckSig(std::vector<unsigned char> vchSig, const std::vector<unsigned char> &vchPubKey, const CScript &scriptCode, const CTransaction& txTo, unsigned int nIn, int nHashType, int flags);
static const valtype vchFalse(0);
static const valtype vchZero(0);
CBigNum CastToBigNum(const valtype& vch)
{
if (vch.size() > nMaxNumSize)
- throw runtime_error("CastToBigNum() : overflow");
+ throw std::runtime_error("CastToBigNum() : overflow");
// Get rid of extra leading zeros
return CBigNum(CBigNum(vch).getvch());
}
//
#define stacktop(i) (stack.at(stack.size()+(i)))
#define altstacktop(i) (altstack.at(altstack.size()+(i)))
-static inline void popstack(vector<valtype>& stack)
+static inline void popstack(std::vector<valtype>& stack)
{
if (stack.empty())
- throw runtime_error("popstack() : stack empty");
+ throw std::runtime_error("popstack() : stack empty");
stack.pop_back();
}
return true;
}
-bool EvalScript(vector<vector<unsigned char> >& stack, const CScript& script, const CTransaction& txTo, unsigned int nIn, unsigned int flags, int nHashType)
+bool EvalScript(std::vector<std::vector<unsigned char> >& stack, const CScript& script, const CTransaction& txTo, unsigned int nIn, unsigned int flags, int nHashType)
{
CAutoBN_CTX pctx;
CScript::const_iterator pc = script.begin();
CScript::const_iterator pbegincodehash = script.begin();
opcodetype opcode;
valtype vchPushValue;
- vector<bool> vfExec;
- vector<valtype> altstack;
+ std::vector<bool> vfExec;
+ std::vector<valtype> altstack;
if (script.size() > 10000)
return false;
int nOpCount = 0;
{
private:
// sigdata_type is (signature hash, signature, public key):
- typedef boost::tuple<uint256, std::vector<unsigned char>, CPubKey > sigdata_type;
+ typedef std::tuple<uint256, std::vector<unsigned char>, CPubKey > sigdata_type;
std::set< sigdata_type> setValid;
boost::shared_mutex cs_sigcache;
}
};
-bool CheckSig(vector<unsigned char> vchSig, const vector<unsigned char> &vchPubKey, const CScript &scriptCode,
+bool CheckSig(std::vector<unsigned char> vchSig, const std::vector<unsigned char> &vchPubKey, const CScript &scriptCode,
const CTransaction& txTo, unsigned int nIn, int nHashType, int flags)
{
static CSignatureCache signatureCache;
- CKey key;
- if (!key.SetPubKey(vchPubKey))
- return false;
- CPubKey pubkey = key.GetPubKey();
+ CPubKey pubkey(vchPubKey);
if (!pubkey.IsValid())
return false;
if (signatureCache.Get(sighash, vchSig, pubkey))
return true;
- if (!key.Verify(sighash, vchSig))
+ if (!pubkey.Verify(sighash, vchSig))
return false;
if (!(flags & SCRIPT_VERIFY_NOCACHE))
}
-
-
-
-
-
-
//
// Return public keys or hashes from scriptPubKey, for 'standard' transaction types.
//
-bool Solver(const CScript& scriptPubKey, txnouttype& typeRet, vector<vector<unsigned char> >& vSolutionsRet)
+bool Solver(const CScript& scriptPubKey, txnouttype& typeRet, std::vector<std::vector<unsigned char> >& vSolutionsRet)
{
// Templates
- static map<txnouttype, CScript> mTemplates;
+ static std::map<txnouttype, CScript> mTemplates;
if (mTemplates.empty())
{
// Standard tx, sender provides pubkey, receiver adds signature
mTemplates.insert(make_pair(TX_PUBKEY, CScript() << OP_PUBKEY << OP_CHECKSIG));
- if (fTestNet || GetTime() > SMALLDATA_SWITCH_TIME)
- {
- // Malleable pubkey tx hack, sender provides generated pubkey combined with R parameter. The R parameter is dropped before checking a signature.
- mTemplates.insert(make_pair(TX_PUBKEY_DROP, CScript() << OP_PUBKEY << OP_PUBKEY << OP_DROP << OP_CHECKSIG));
- }
+ // Malleable pubkey tx hack, sender provides generated pubkey combined with R parameter. The R parameter is dropped before checking a signature.
+ mTemplates.insert(make_pair(TX_PUBKEY_DROP, CScript() << OP_PUBKEY << OP_PUBKEY << OP_DROP << OP_CHECKSIG));
// Bitcoin address tx, sender provides hash of pubkey, receiver provides signature and pubkey
mTemplates.insert(make_pair(TX_PUBKEYHASH, CScript() << OP_DUP << OP_HASH160 << OP_PUBKEYHASH << OP_EQUALVERIFY << OP_CHECKSIG));
if (scriptPubKey.IsPayToScriptHash())
{
typeRet = TX_SCRIPTHASH;
- vector<unsigned char> hashBytes(scriptPubKey.begin()+2, scriptPubKey.begin()+22);
+ std::vector<unsigned char> hashBytes(scriptPubKey.begin()+2, scriptPubKey.begin()+22);
vSolutionsRet.push_back(hashBytes);
return true;
}
// Scan templates
const CScript& script1 = scriptPubKey;
- BOOST_FOREACH(const PAIRTYPE(txnouttype, CScript)& tplate, mTemplates)
+ for (const auto& tplate : mTemplates)
{
const CScript& script2 = tplate.second;
vSolutionsRet.clear();
opcodetype opcode1, opcode2;
- vector<unsigned char> vch1, vch2;
+ std::vector<unsigned char> vch1, vch2;
// Compare
CScript::const_iterator pc1 = script1.begin();
CScript::const_iterator pc2 = script2.begin();
- while (true)
+ for ( ; ; )
{
if (pc1 == script1.end() && pc2 == script2.end())
{
else if (opcode2 == OP_SMALLDATA)
{
// small pushdata, <= 1024 bytes
- if (vch1.size() > (GetTime() > SMALLDATA_SWITCH_TIME ? 1024 : 80))
+ if (vch1.size() > 1024)
break;
}
else if (opcode1 != opcode2 || vch1 != vch2)
if (!keystore.GetKey(address, key))
return false;
- vector<unsigned char> vchSig;
+ std::vector<unsigned char> vchSig;
if (!key.Sign(hash, vchSig))
return false;
vchSig.push_back((unsigned char)nHashType);
if (!keystore.CreatePrivKey(pubKey, R, key))
return false;
- vector<unsigned char> vchSig;
+ std::vector<unsigned char> vchSig;
if (!key.Sign(hash, vchSig))
return false;
vchSig.push_back((unsigned char)nHashType);
return true;
}
-bool SignN(const vector<valtype>& multisigdata, const CKeyStore& keystore, const uint256& hash, int nHashType, CScript& scriptSigRet)
+bool SignN(const std::vector<valtype>& multisigdata, const CKeyStore& keystore, const uint256& hash, int nHashType, CScript& scriptSigRet)
{
int nSigned = 0;
int nRequired = multisigdata.front()[0];
{
scriptSigRet.clear();
- vector<valtype> vSolutions;
+ std::vector<valtype> vSolutions;
if (!Solver(scriptPubKey, whichTypeRet, vSolutions))
return false;
bool IsStandard(const CScript& scriptPubKey, txnouttype& whichType)
{
- vector<valtype> vSolutions;
+ std::vector<valtype> vSolutions;
if (!Solver(scriptPubKey, whichType, vSolutions))
return false;
}
-unsigned int HaveKeys(const vector<valtype>& pubkeys, const CKeyStore& keystore)
+unsigned int HaveKeys(const std::vector<valtype>& pubkeys, const CKeyStore& keystore)
{
unsigned int nResult = 0;
- BOOST_FOREACH(const valtype& pubkey, pubkeys)
+ for (const valtype& pubkey : pubkeys)
{
CKeyID keyID = CPubKey(pubkey).GetID();
if (keystore.HaveKey(keyID))
isminetype IsMine(const CKeyStore &keystore, const CScript& scriptPubKey)
{
- vector<valtype> vSolutions;
+ std::vector<valtype> vSolutions;
txnouttype whichType;
if (!Solver(scriptPubKey, whichType, vSolutions)) {
if (keystore.HaveWatchOnly(scriptPubKey))
// partially owned (somebody else has a key that can spend
// them) enable spend-out-from-under-you attacks, especially
// in shared-wallet situations.
- vector<valtype> keys(vSolutions.begin()+1, vSolutions.begin()+vSolutions.size()-1);
+ std::vector<valtype> keys(vSolutions.begin()+1, vSolutions.begin()+vSolutions.size()-1);
if (HaveKeys(keys, keystore) == keys.size())
return MINE_SPENDABLE;
break;
bool ExtractDestination(const CScript& scriptPubKey, CTxDestination& addressRet)
{
- vector<valtype> vSolutions;
+ std::vector<valtype> vSolutions;
txnouttype whichType;
if (!Solver(scriptPubKey, whichType, vSolutions))
return false;
bool ExtractAddress(const CKeyStore &keystore, const CScript& scriptPubKey, CBitcoinAddress& addressRet)
{
- vector<valtype> vSolutions;
+ std::vector<valtype> vSolutions;
txnouttype whichType;
if (!Solver(scriptPubKey, whichType, vSolutions))
return false;
std::vector<CTxDestination> vDest;
int nRequired;
if (ExtractDestinations(script, type, vDest, nRequired)) {
- BOOST_FOREACH(const CTxDestination &dest, vDest)
+ for (const CTxDestination &dest : vDest)
boost::apply_visitor(*this, dest);
}
}
CAffectedKeysVisitor(keystore, vKeys).Process(scriptPubKey);
}
-bool ExtractDestinations(const CScript& scriptPubKey, txnouttype& typeRet, vector<CTxDestination>& addressRet, int& nRequiredRet)
+bool ExtractDestinations(const CScript& scriptPubKey, txnouttype& typeRet, std::vector<CTxDestination>& addressRet, int& nRequiredRet)
{
addressRet.clear();
typeRet = TX_NONSTANDARD;
- vector<valtype> vSolutions;
+ std::vector<valtype> vSolutions;
if (!Solver(scriptPubKey, typeRet, vSolutions))
return false;
if (typeRet == TX_NULL_DATA)
bool VerifyScript(const CScript& scriptSig, const CScript& scriptPubKey, const CTransaction& txTo, unsigned int nIn,
unsigned int flags, int nHashType)
{
- vector<vector<unsigned char> > stack, stackCopy;
+ std::vector<std::vector<unsigned char> > stack, stackCopy;
if (!EvalScript(stack, scriptSig, txTo, nIn, flags, nHashType))
return false;
if (flags & SCRIPT_VERIFY_P2SH)
return SignSignature(keystore, txout.scriptPubKey, txTo, nIn, nHashType);
}
-static CScript PushAll(const vector<valtype>& values)
+static CScript PushAll(const std::vector<valtype>& values)
{
CScript result;
- BOOST_FOREACH(const valtype& v, values)
+ for (const valtype& v : values)
result << v;
return result;
}
static CScript CombineMultisig(const CScript& scriptPubKey, const CTransaction& txTo, unsigned int nIn,
- const vector<valtype>& vSolutions,
- vector<valtype>& sigs1, vector<valtype>& sigs2)
+ const std::vector<valtype>& vSolutions,
+ std::vector<valtype>& sigs1, std::vector<valtype>& sigs2)
{
// Combine all the signatures we've got:
- set<valtype> allsigs;
- BOOST_FOREACH(const valtype& v, sigs1)
+ std::set<valtype> allsigs;
+ for (const valtype& v : sigs1)
{
if (!v.empty())
allsigs.insert(v);
}
- BOOST_FOREACH(const valtype& v, sigs2)
+ for (const valtype& v : sigs2)
{
if (!v.empty())
allsigs.insert(v);
assert(vSolutions.size() > 1);
unsigned int nSigsRequired = vSolutions.front()[0];
unsigned int nPubKeys = (unsigned int)(vSolutions.size()-2);
- map<valtype, valtype> sigs;
- BOOST_FOREACH(const valtype& sig, allsigs)
+ std::map<valtype, valtype> sigs;
+ for (const valtype& sig : allsigs)
{
for (unsigned int i = 0; i < nPubKeys; i++)
{
}
static CScript CombineSignatures(const CScript& scriptPubKey, const CTransaction& txTo, unsigned int nIn,
- const txnouttype txType, const vector<valtype>& vSolutions,
- vector<valtype>& sigs1, vector<valtype>& sigs2)
+ const txnouttype txType, const std::vector<valtype>& vSolutions,
+ std::vector<valtype>& sigs1, std::vector<valtype>& sigs2)
{
switch (txType)
{
CScript pubKey2(spk.begin(), spk.end());
txnouttype txType2;
- vector<vector<unsigned char> > vSolutions2;
+ std::vector<std::vector<unsigned char> > vSolutions2;
Solver(pubKey2, txType2, vSolutions2);
sigs1.pop_back();
sigs2.pop_back();
const CScript& scriptSig1, const CScript& scriptSig2)
{
txnouttype txType;
- vector<vector<unsigned char> > vSolutions;
+ std::vector<std::vector<unsigned char> > vSolutions;
Solver(scriptPubKey, txType, vSolutions);
- vector<valtype> stack1;
+ std::vector<valtype> stack1;
EvalScript(stack1, scriptSig1, CTransaction(), 0, SCRIPT_VERIFY_STRICTENC, 0);
- vector<valtype> stack2;
+ std::vector<valtype> stack2;
EvalScript(stack2, scriptSig2, CTransaction(), 0, SCRIPT_VERIFY_STRICTENC, 0);
return CombineSignatures(scriptPubKey, txTo, nIn, txType, vSolutions, stack1, stack2);
}
}
-void CScript::SetMultisig(int nRequired, const std::vector<CKey>& keys)
+void CScript::SetMultisig(int nRequired, const std::vector<CPubKey>& keys)
{
this->clear();
*this << EncodeOP_N(nRequired);
- BOOST_FOREACH(const CKey& key, keys)
- *this << key.GetPubKey();
+ for (const CPubKey& key : keys)
+ *this << key;
*this << EncodeOP_N((int)(keys.size())) << OP_CHECKMULTISIG;
}