6
6
import base58
7
7
import ctssl
8
8
9
- def wif (priv , testnet = False ):
9
+ def wif (priv , compressed , testnet = False ):
10
10
'''
11
11
Convert raw private key to base58-encoded wallet import format.
12
12
13
- >>> wif (binascii.unhexlify (b'338b7f9c13b44747fdef077898f688411693df40d5f6943ebba30917125934c9'))
14
- b'5JCzE8aEchKzGQThaYqKn5bcHvisWThwC2tU3eUB6VVAx1WV5fQ'
13
+ >>> wif (binascii.unhexlify (b'1111111111111111111111111111111111111111111111111111111111111111'), False)
14
+ b'5HwoXVkHoRM8sL2KmNRS217n1g8mPPBomrY7yehCuXC1115WWsh'
15
+ >>> wif (binascii.unhexlify (b'1111111111111111111111111111111111111111111111111111111111111111'), True)
16
+ b'KwntMbt59tTsj8xqpqYqRRWufyjGunvhSyeMo3NTYpFYzZbXJ5Hp'
17
+ >>> wif (binascii.unhexlify (b'dddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddd'), False)
18
+ b'5KVzsHJiUxgvBBgtVS7qBTbbYZpwWM4WQNCCyNSiuFCJzYMxg8H'
19
+ >>> wif (binascii.unhexlify (b'dddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddddd'), True)
20
+ b'L4ezQvyC6QoBhxB4GVs9fAPhUKtbaXYUn8YTqoeXwbevQq4U92vN'
21
+ >>> wif (binascii.unhexlify (b'47f7616ea6f9b923076625b4488115de1ef1187f760e65f89eb6f4f7ff04b012'), False)
22
+ b'5JMys7YfK72cRVTrbwkq5paxU7vgkMypB55KyXEtN5uSnjV7K8Y'
23
+ >>> wif (binascii.unhexlify (b'47f7616ea6f9b923076625b4488115de1ef1187f760e65f89eb6f4f7ff04b012'), True)
24
+ b'KydbzBtk6uc7M6dXwEgTEH2sphZxSPbmDSz6kUUHi4eUpSQuhEbq'
15
25
'''
16
26
result = (b'\x80 ' if not testnet else b'\xef ' ) + (b'\x00 ' * (32 - len (priv )) + priv )
17
27
assert len (result ) == 33
28
+ if compressed :
29
+ result += b'\x01 '
18
30
h1 = hashlib .sha256 (result )
19
31
h2 = hashlib .sha256 (h1 .digest ())
20
32
result += h2 .digest ()[:4 ]
@@ -24,11 +36,25 @@ def addr (pub, testnet=False):
24
36
'''
25
37
Convert raw public key to base58check-encoded address.
26
38
27
- >>> addr (binascii.unhexlify (b'04bbed292cf660fcd6fd29590ea53bbad38603a8b55d93806d12af56c994bae8d1df64d4b52607543c44031b26c401648928f748dd447c736b3c47f61f38477c28'))
28
- b'1Br8AVNn7XtvEBHc5hyaXsnPZFVAbLpNiL'
39
+ >>> addr (binascii.unhexlify (b'044f355bdcb7cc0af728ef3cceb9615d90684bb5b2ca5f859ab0f0b704075871aa385b6b1b8ead809ca67454d9683fcf2ba03456d6fe2c4abe2b07f0fbdbb2f1c1'))
40
+ b'1MsHWS1BnwMc3tLE8G35UXsS58fKipzB7a'
41
+ >>> addr (binascii.unhexlify (b'034f355bdcb7cc0af728ef3cceb9615d90684bb5b2ca5f859ab0f0b704075871aa'))
42
+ b'1Q1pE5vPGEEMqRcVRMbtBK842Y6Pzo6nK9'
43
+ >>> addr (binascii.unhexlify (b'04ed83704c95d829046f1ac27806211132102c34e9ac7ffa1b71110658e5b9d1bdedc416f5cefc1db0625cd0c75de8192d2b592d7e3b00bcfb4a0e860d880fd1fc'))
44
+ b'1JyMKvPHkrCQd8jQrqTR1rBsAd1VpRhTiE'
45
+ >>> addr (binascii.unhexlify (b'02ed83704c95d829046f1ac27806211132102c34e9ac7ffa1b71110658e5b9d1bd'))
46
+ b'1NKRhS7iYUGTaAfaR5z8BueAJesqaTyc4a'
47
+ >>> addr (binascii.unhexlify (b'042596957532fc37e40486b910802ff45eeaa924548c0e1c080ef804e523ec3ed3ed0a9004acf927666eee18b7f5e8ad72ff100a3bb710a577256fd7ec81eb1cb3'))
48
+ b'1PM35qz2uwCDzcUJtiqDSudAaaLrWRw41L'
49
+ >>> addr (binascii.unhexlify (b'032596957532fc37e40486b910802ff45eeaa924548c0e1c080ef804e523ec3ed3'))
50
+ b'19ck9VKC6KjGxR9LJg4DNMRc45qFrJguvV'
29
51
'''
30
- assert len (pub ) == 65 # pad?
31
- assert pub [0 ] == 4
52
+ if pub [0 ] == 4 :
53
+ assert len (pub ) == 65
54
+ elif pub [0 ] == 2 or pub [0 ] == 3 :
55
+ assert len (pub ) == 33
56
+ else :
57
+ assert False , 'Unknown public key format: {}' .format (pub [0 ])
32
58
h3 = hashlib .sha256 (pub )
33
59
h4 = hashlib .new ('ripemd160' , h3 .digest ())
34
60
result = (b'\x00 ' if not testnet else b'\x6f ' ) + h4 .digest ()
@@ -38,23 +64,24 @@ def addr (pub, testnet=False):
38
64
return base58 .encode (result )
39
65
40
66
def generate (a ):
41
- with ctssl .EC_KEY () as key :
67
+ with ctssl .EC_KEY (compressed = not a . uncompressed ) as key :
42
68
priv = key .priv ()
43
69
pub = key .pub ()
44
70
with print_lock :
45
- print (wif (priv , testnet = a .testnet ).decode ('ascii' ), addr (pub , testnet = a .testnet ).decode ('ascii' ))
71
+ print (wif (priv , key . compressed , testnet = a .testnet ).decode ('ascii' ), addr (pub , testnet = a .testnet ).decode ('ascii' ))
46
72
if a .raw :
47
73
print ('' , binascii .hexlify (priv ).decode ('ascii' ), binascii .hexlify (pub ).decode ('ascii' ))
48
74
49
75
def main ():
50
76
parser = argparse .ArgumentParser (description = 'Generate Bitcoin addresses.' )
51
- parser .add_argument ('--count' , '-c' , help = 'Number of addresses to generate' , action = 'store' , default = 1 )
77
+ parser .add_argument ('--number' , '-n' , help = 'Number of addresses to generate' , action = 'store' , default = 1 )
78
+ parser .add_argument ('--uncompressed' , '-u' , help = 'Use uncompressed format' , action = 'store_true' )
52
79
parser .add_argument ('--raw' , '-r' , help = 'Display raw private/public key' , action = 'store_true' )
53
80
parser .add_argument ('--testnet' , '-t' , help = 'Generate testnet address' , action = 'store_true' )
54
81
a = parser .parse_args ()
55
82
56
83
p = multiprocessing .Pool (processes = multiprocessing .cpu_count ())
57
- p .map (generate , [a ] * int (a .count ))
84
+ p .map (generate , [a ] * int (a .number ))
58
85
59
86
if __name__ == '__main__' :
60
87
print_lock = multiprocessing .Lock ()
0 commit comments