Merge #16026: Ensure that uncompressed public keys in a multisig always returns a legacy address

a49503402b6bc21e3878e151c07529941d36aed0 Make and get the multisig redeemscript and destination in one function instead of two (Andrew Chow)

Pull request description:

  `CreateMultisigRedeemscript()` is changed to `AddAndGetMultisigDestination()` so that the process of constructing the redeemScript and then getting the `CTxDestination` are done in the same function. This allows that function to see what the keys in the multisig are so that the correct address type is returned from `AddAndGetDestinationForScript()`.

  This only effects the `createmultisig` and `addmultisigaddress` RPCs and does not change signing logic as #16022 does.

  Alternative to #16022 and #16012

  Fixes #16011

ACKs for commit a49503:

Tree-SHA512: 5b0154a714deea3b2cc3a54beb420c95eeeacf4ca30c40ca80940d9d640f8b03611b0fc14c2f0710bfd8a79e8d27ad7d9ae380b4b83d52b40ab201624f2a63f0
This commit is contained in:
MeshCollider 2019-06-21 19:43:13 +12:00 committed by PastaPastaPasta
parent fb205ed59f
commit d5269332a4
4 changed files with 16 additions and 14 deletions

View File

@ -279,11 +279,11 @@ static UniValue createmultisig(const JSONRPCRequest& request)
} }
// Construct using pay-to-script-hash: // Construct using pay-to-script-hash:
CScript inner = CreateMultisigRedeemscript(required, pubkeys); CScript inner;
CScriptID innerID(inner); const CTxDestination dest = AddAndGetMultisigDestination(required, pubkeys, inner);
UniValue result(UniValue::VOBJ); UniValue result(UniValue::VOBJ);
result.pushKV("address", EncodeDestination(ScriptHash(innerID))); result.pushKV("address", EncodeDestination(dest));
result.pushKV("redeemScript", HexStr(inner)); result.pushKV("redeemScript", HexStr(inner));
return result; return result;

View File

@ -209,8 +209,8 @@ CPubKey AddrToPubKey(const FillableSigningProvider& keystore, const std::string&
return vchPubKey; return vchPubKey;
} }
// Creates a multisig redeemscript from a given list of public keys and number required. // Creates a multisig address from a given list of public keys, number of signatures required
CScript CreateMultisigRedeemscript(const int required, const std::vector<CPubKey>& pubkeys) CTxDestination AddAndGetMultisigDestination(const int required, const std::vector<CPubKey>& pubkeys, CScript& script_out)
{ {
// Gather public keys // Gather public keys
if (required < 1) { if (required < 1) {
@ -223,13 +223,14 @@ CScript CreateMultisigRedeemscript(const int required, const std::vector<CPubKey
throw JSONRPCError(RPC_INVALID_PARAMETER, "Number of keys involved in the multisignature address creation > 16\nReduce the number"); throw JSONRPCError(RPC_INVALID_PARAMETER, "Number of keys involved in the multisignature address creation > 16\nReduce the number");
} }
CScript result = GetScriptForMultisig(required, pubkeys); script_out = GetScriptForMultisig(required, pubkeys);
if (result.size() > MAX_SCRIPT_ELEMENT_SIZE) { if (script_out.size() > MAX_SCRIPT_ELEMENT_SIZE) {
throw JSONRPCError(RPC_INVALID_PARAMETER, (strprintf("redeemScript exceeds size limit: %d > %d", result.size(), MAX_SCRIPT_ELEMENT_SIZE))); throw JSONRPCError(RPC_INVALID_PARAMETER, (strprintf("redeemScript exceeds size limit: %d > %d", script_out.size(), MAX_SCRIPT_ELEMENT_SIZE)));
} }
return result; // Make the address (simplier implementation in compare to bitcoin)
return ScriptHash(script_out);
} }
class DescribeAddressVisitor class DescribeAddressVisitor

View File

@ -84,7 +84,7 @@ extern std::string HelpExampleRpc(const std::string& methodname, const std::stri
CPubKey HexToPubKey(const std::string& hex_in); CPubKey HexToPubKey(const std::string& hex_in);
CPubKey AddrToPubKey(const FillableSigningProvider& keystore, const std::string& addr_in); CPubKey AddrToPubKey(const FillableSigningProvider& keystore, const std::string& addr_in);
CScript CreateMultisigRedeemscript(const int required, const std::vector<CPubKey>& pubkeys); CTxDestination AddAndGetMultisigDestination(const int required, const std::vector<CPubKey>& pubkeys, CScript& script_out);
UniValue DescribeAddress(const CTxDestination& dest); UniValue DescribeAddress(const CTxDestination& dest);

View File

@ -1030,14 +1030,15 @@ UniValue addmultisigaddress(const JSONRPCRequest& request)
} }
// Construct using pay-to-script-hash: // Construct using pay-to-script-hash:
CScript inner = CreateMultisigRedeemscript(required, pubkeys); CScript inner;
ScriptHash innerHash(inner); CTxDestination dest = AddAndGetMultisigDestination(required, pubkeys, inner);
spk_man.AddCScript(inner); spk_man.AddCScript(inner);
pwallet->SetAddressBook(innerHash, label, "send"); pwallet->SetAddressBook(dest, label, "send");
UniValue result(UniValue::VOBJ); UniValue result(UniValue::VOBJ);
result.pushKV("address", EncodeDestination(innerHash)); result.pushKV("address", EncodeDestination(dest));
result.pushKV("redeemScript", HexStr(inner)); result.pushKV("redeemScript", HexStr(inner));
return result; return result;
} }