Make and get the multisig redeemscript and destination in one function instead of two

Instead of creating a redeemScript with CreateMultisigRedeemscript and
then getting the destination with AddAndGetDestinationForScript, do
both in the same function.

CreateMultisigRedeemscript is changed to AddAndGetMultisigDestination.
It creates the redeemScript and returns it via an output parameter. Then
it calls AddAndGetDestinationForScript to add the destination to the
keystore and get the proper destination.

This allows us to inspect the public keys in the redeemScript before creating
the destination so that the correct destination is used when uncompressed
pubkeys are in the multisig.
This commit is contained in:
Andrew Chow
2019-05-15 00:21:11 -04:00
parent 65526fc866
commit a49503402b
5 changed files with 53 additions and 12 deletions

View File

@ -7,9 +7,13 @@
from test_framework.test_framework import BitcoinTestFramework
from test_framework.util import (
assert_raises_rpc_error,
assert_equal,
)
import decimal
from test_framework.key import ECPubKey
import binascii
import decimal
import itertools
class RpcCreateMultiSigTest(BitcoinTestFramework):
def set_test_params(self):
@ -44,6 +48,30 @@ class RpcCreateMultiSigTest(BitcoinTestFramework):
self.checkbalances()
# Test mixed compressed and uncompressed pubkeys
self.log.info('Mixed compressed and uncompressed multisigs are not allowed')
pk0 = node0.getaddressinfo(node0.getnewaddress())['pubkey']
pk1 = node1.getaddressinfo(node1.getnewaddress())['pubkey']
pk2 = node2.getaddressinfo(node2.getnewaddress())['pubkey']
# decompress pk2
pk_obj = ECPubKey()
pk_obj.set(binascii.unhexlify(pk2))
pk_obj.compressed = False
pk2 = binascii.hexlify(pk_obj.get_bytes()).decode()
# Check all permutations of keys because order matters apparently
for keys in itertools.permutations([pk0, pk1, pk2]):
# Results should be the same as this legacy one
legacy_addr = node0.createmultisig(2, keys, 'legacy')['address']
assert_equal(legacy_addr, node0.addmultisigaddress(2, keys, '', 'legacy')['address'])
# Generate addresses with the segwit types. These should all make legacy addresses
assert_equal(legacy_addr, node0.createmultisig(2, keys, 'bech32')['address'])
assert_equal(legacy_addr, node0.createmultisig(2, keys, 'p2sh-segwit')['address'])
assert_equal(legacy_addr, node0.addmultisigaddress(2, keys, '', 'bech32')['address'])
assert_equal(legacy_addr, node0.addmultisigaddress(2, keys, '', 'p2sh-segwit')['address'])
def check_addmultisigaddress_errors(self):
self.log.info('Check that addmultisigaddress fails when the private keys are missing')
addresses = [self.nodes[1].getnewaddress(address_type='legacy') for _ in range(2)]