Stop requiring imported pubkey to sign non-PKH schemes

This commit is contained in:
Pieter Wuille 2018-10-06 03:33:24 -07:00
parent f504a1402a
commit 2f6b466aeb

View file

@ -73,15 +73,18 @@ static bool GetPubKey(const SigningProvider& provider, SignatureData& sigdata, c
return false; return false;
} }
static bool CreateSig(const BaseSignatureCreator& creator, SignatureData& sigdata, const SigningProvider& provider, std::vector<unsigned char>& sig_out, const CKeyID& keyid, const CScript& scriptcode, SigVersion sigversion) static bool CreateSig(const BaseSignatureCreator& creator, SignatureData& sigdata, const SigningProvider& provider, std::vector<unsigned char>& sig_out, const CPubKey& pubkey, const CScript& scriptcode, SigVersion sigversion)
{ {
CKeyID keyid = pubkey.GetID();
const auto it = sigdata.signatures.find(keyid); const auto it = sigdata.signatures.find(keyid);
if (it != sigdata.signatures.end()) { if (it != sigdata.signatures.end()) {
sig_out = it->second.second; sig_out = it->second.second;
return true; return true;
} }
CPubKey pubkey; KeyOriginInfo info;
GetPubKey(provider, sigdata, keyid, pubkey); if (provider.GetKeyOrigin(keyid, info)) {
sigdata.misc_pubkeys.emplace(keyid, std::make_pair(pubkey, std::move(info)));
}
if (creator.CreateSig(provider, sig_out, keyid, scriptcode, sigversion)) { if (creator.CreateSig(provider, sig_out, keyid, scriptcode, sigversion)) {
auto i = sigdata.signatures.emplace(keyid, SigPair(pubkey, sig_out)); auto i = sigdata.signatures.emplace(keyid, SigPair(pubkey, sig_out));
assert(i.second); assert(i.second);
@ -114,15 +117,15 @@ static bool SignStep(const SigningProvider& provider, const BaseSignatureCreator
case TX_WITNESS_UNKNOWN: case TX_WITNESS_UNKNOWN:
return false; return false;
case TX_PUBKEY: case TX_PUBKEY:
if (!CreateSig(creator, sigdata, provider, sig, CPubKey(vSolutions[0]).GetID(), scriptPubKey, sigversion)) return false; if (!CreateSig(creator, sigdata, provider, sig, CPubKey(vSolutions[0]), scriptPubKey, sigversion)) return false;
ret.push_back(std::move(sig)); ret.push_back(std::move(sig));
return true; return true;
case TX_PUBKEYHASH: { case TX_PUBKEYHASH: {
CKeyID keyID = CKeyID(uint160(vSolutions[0])); CKeyID keyID = CKeyID(uint160(vSolutions[0]));
if (!CreateSig(creator, sigdata, provider, sig, keyID, scriptPubKey, sigversion)) return false;
ret.push_back(std::move(sig));
CPubKey pubkey; CPubKey pubkey;
GetPubKey(provider, sigdata, keyID, pubkey); GetPubKey(provider, sigdata, keyID, pubkey);
if (!CreateSig(creator, sigdata, provider, sig, pubkey, scriptPubKey, sigversion)) return false;
ret.push_back(std::move(sig));
ret.push_back(ToByteVector(pubkey)); ret.push_back(ToByteVector(pubkey));
return true; return true;
} }
@ -138,7 +141,7 @@ static bool SignStep(const SigningProvider& provider, const BaseSignatureCreator
ret.push_back(valtype()); // workaround CHECKMULTISIG bug ret.push_back(valtype()); // workaround CHECKMULTISIG bug
for (size_t i = 1; i < vSolutions.size() - 1; ++i) { for (size_t i = 1; i < vSolutions.size() - 1; ++i) {
CPubKey pubkey = CPubKey(vSolutions[i]); CPubKey pubkey = CPubKey(vSolutions[i]);
if (ret.size() < required + 1 && CreateSig(creator, sigdata, provider, sig, pubkey.GetID(), scriptPubKey, sigversion)) { if (ret.size() < required + 1 && CreateSig(creator, sigdata, provider, sig, pubkey, scriptPubKey, sigversion)) {
ret.push_back(std::move(sig)); ret.push_back(std::move(sig));
} }
} }