def test_parse(self): pk = PrivateKey.parse('L5oLkpV3aqBJ4BgssVAsax1iRa77G5CVYnv9adQ6Z87te7TyUdSC') want = 2**256-2**199 self.assertEqual(pk.secret, want) pk = PrivateKey.parse('93XfLeifX7Jx7n7ELGMAf1SUR6f9kgQs8Xke8WStMwUtrDucMzn') want = 2**256-2**201 self.assertEqual(pk.secret, want) pk = PrivateKey.parse('5HvLFPDVgFZRK9cd4C5jcWki5Skz6fmKqi1GQJf5ZoMofid2Dty') want = 0x0dba685b4511dbd3d368e5c4358a1277de9486447af7b3604a69b8d9d8b7889d self.assertEqual(pk.secret, want) pk = PrivateKey.parse('cNYfWuhDpbNM1JWc3c6JTrtrFVxU4AGhUKgw5f93NP2QaBqmxKkg') want = 0x1cca23de92fd1862fb5b76e5f4f50eb082165e5191e116c18ed1a6b24be6a53f self.assertEqual(pk.secret, want)
def spend_tx(cls, wifs, utxos, destination_addr, fee=540): destination_address_data = cls.get_address_data(destination_addr) testnet = destination_address_data['testnet'] if testnet: prefix = bytes([cls.testnet_prefixes[0]]) else: prefix = bytes([cls.p2pkh_prefixes[0]]) tx_ins = [] sequence = 0xffffffff priv_lookup = {} total = 0 for wif in wifs: priv_key = PrivateKey.parse(wif) addr = priv_key.point.address(priv_key.compressed, prefix=prefix) # look up utxos for each address address_data = cls.get_address_data(addr) script_pubkey = address_data['script_pubkey'] spk = script_pubkey.serialize() priv_lookup[spk] = priv_key if not utxos: raise RuntimeError('fetch utxos first') for serialized_script_pubkey, prev_tx, prev_index, value in utxos: tx_ins.append( TxIn(prev_tx, prev_index, b'', sequence, value=value, script_pubkey=serialized_script_pubkey)) total += value num_tx_ins = len(tx_ins) if num_tx_ins == 0: raise RuntimeError('nothing to spend') script_pubkey = destination_address_data['script_pubkey'] tx_out = TxOut(total - fee, script_pubkey.serialize()) tx = cls(cls.default_version, tx_ins, [tx_out], 0, testnet=testnet) for index, tx_in in enumerate(tx_ins): priv_key = priv_lookup[tx_in.script_pubkey().serialize()] tx.sign_input( index, priv_key, cls.default_hash_type, compressed=priv_key.compressed, ) if not tx.verify(): raise RuntimeError('failed validation') return tx.serialize()
def test_b2x_sign(self): # Generated from ./bitcoin2x-qt -regtest wif = 'cVC6z7gnezHZut5yyuCX3x79tfcbauCWiFcBY92Vg4crfu4Maa5B' prev_tx = 'b6d073333c1a8e4360b1e2c7fa2ed6b67b74272ad7fabf52a4e4732df5f47dbd' prev_index = 0 prev_value = 5000000000 destination = 'mrVqpGm7F5MVCwsP4s3fQEN2GAaykJoTu4' amount = 4996000000 priv_key = PrivateKey.parse(wif) prev_script_pubkey = B2XTx.get_address_data( priv_key.point.address())['script_pubkey'].serialize() tx_in = TxIn(unhexlify(prev_tx), prev_index, b'', 0xffffffff, b'\x00', prev_value, prev_script_pubkey) script = B2XTx.get_address_data( destination)['script_pubkey'].serialize() tx_out = TxOut(amount, script) tx = B2XTx(2, [tx_in], [tx_out], 0, testnet=True) tx.sign(priv_key) want = "0200000001bd7df4f52d73e4a452bffad72a27747bb6d62efac7e2b160438e1a3c3373d0b6000000006a47304402201df7c8c97443bd46da751e0051a4395ba3613be3604be97d3c801c21e3d23c79022012ad30b7ffd42ad7bb96f9157519f7e3c35409ed54f783a3c854a596343a6c713121030f96812693c4a50162134cfa307afb63580171963d6c4198e8e5cfeee2c92b60ffffffff0100e9c829010000001976a91478738f2c5a75397eb2f851597261f766a67d9b6388ac00000000" self.assertTrue(tx.verify()) self.assertEqual(tx.serialize().hex(), want)
import pprint raw="""\ 0491bba2510912a5bd37da1fb5b1673010e43d2c6d812c514e91bfa9f2eb129e1c183329db55bd868e209aac2fbc02cb33d98fe74bf23f0c235d6126b1d8334f86/5JaTXbAUmfPYZFRwrYaALK48fN6sFJp4rHqq2QSXs8ucfpE4yQU 04865c40293a680cb9c020e7b1e106d8c1916d3cef99aa431a56d253e69256dac09ef122b1a986818a7cb624532f062c1d1f8722084861c5c3291ccffef4ec6874/5Jb7fCeh1Wtm4yBBg3q3XbT6B525i17kVhy3vMC9AqfR6FH2qGk 048d2455d2403e08708fc1f556002f1b6cd83f992d085097f9974ab08a28838f07896fbab08f39495e15fa6fad6edbfb1e754e35fa1c7844c41f322a1863d46213/5JFjmGo5Fww9p8gvx48qBYDJNAzR9pmH5S389axMtDyPT8ddqmw\ """ from ecc import PrivateKey, S256Point from helper import little_endian_to_int, big_endian_to_int from binascii import unhexlify, hexlify import script import helper from tx import TxIn, TxOut, Tx key_pairs = [x.split('/') for x in map(str.strip,raw.split('\n'))] key_pairs = [(S256Point.parse(unhexlify(sec)), PrivateKey.parse(wif, compressed=False)) for sec, wif in key_pairs] assert all(p == pk.point for p,pk in key_pairs) pubkeys = [p for p, _ in key_pairs] OP_n = lambda n: 0x51 + n - 1 n_required = 2 elements = [OP_n(n_required)] + [pk.sec(compressed=False) for pk in pubkeys] + [OP_n(len(pubkeys))] + [174] redeemScript = script.Script(elements) address=helper.h160_to_p2sh_address(helper.hash160(redeemScript.serialize()), testnet=False) redeemScript=hexlify(redeemScript.serialize()) assert address=="3QJmV3qfvL9SuYo34YihAf3sRCW3qSinyC" assert redeemScript=="52410491bba2510912a5bd37da1fb5b1673010e43d2c6d812c514e91bfa9f2eb129e1c183329db55bd868e209aac2fbc02cb33d98fe74bf23f0c235d6126b1d8334f864104865c40293a680cb9c020e7b1e106d8c1916d3cef99aa431a56d253e69256dac09ef122b1a986818a7cb624532f062c1d1f8722084861c5c3291ccffef4ec687441048d2455d2403e08708fc1f556002f1b6cd83f992d085097f9974ab08a28838f07896fbab08f39495e15fa6fad6edbfb1e754e35fa1c7844c41f322a1863d4621353ae".encode('ascii') print(hexlify(helper.hash160(unhexlify(redeemScript))))