-
Notifications
You must be signed in to change notification settings - Fork 9
/
wif.rb
99 lines (72 loc) · 2.31 KB
/
wif.rb
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
require 'digest'
_pri_key = "ccea9c5a20e2b78c2e0fbdd8ae2d2b67e6b1894ccb7a55fc1de08bd53994ea64"
_wif_mainnet = '80'
_wif_testnet = 'ef'
def _hash160(pub_key)
bytes = [pub_key].pack("H*")
Digest::RMD160.hexdigest(Digest::SHA256.digest(bytes) )
end
def _checksum(val)
hex_str = [val].pack("H*")
Digest::SHA256.hexdigest(Digest::SHA256.digest(hex_str) )[0...8]
end
def _encode_base58(int_val, leading_zero_bytes=0)
alpha = "123456789ABCDEFGHJKLMNPQRSTUVWXYZabcdefghijkmnopqrstuvwxyz"
base58_val, base = '', alpha.size
while int_val > 0
int_val, remainder = int_val.divmod(base)
base58_val = alpha[remainder] + base58_val
end
base58_val
end
def _base58_to_int(base58_val)
alphabet = "123456789ABCDEFGHJKLMNPQRSTUVWXYZabcdefghijkmnopqrstuvwxyz"
size = alphabet.size
int_val = 0
base58_val.reverse.split(//).each_with_index do |char,index|
char_index = alphabet.index(char)
int_val += (char_index)*(size**(index))
end
int_val
end
def _int_to_hex int
hex = int.to_s(16)
(hex.length % 2 == 0) ? hex : ('0'+hex)
end
def _decode_base58(base58_val)
alphabet = "123456789ABCDEFGHJKLMNPQRSTUVWXYZabcdefghijkmnopqrstuvwxyz"
nzeroes = base58_val.chars.find_index{|c| c != alphabet[0]} || base58_val.length-1
prefix = nzeroes < 0 ? '' : '00' * nzeroes
nzeroes = base58_val.chars.find_index{|c| c != alphabet} || base58_val.length-1
prefix = nzeroes < 0 ? '' : '00' * nzeroes
prefix + _int_to_hex(_base58_to_int(base58_val))
end
def pri_key_to_wif(prefix, pri, compress=true)
flag = compress ? "01" : ""
rk = prefix + pri + flag
hash160 = _hash160(rk)
checksum = _checksum(rk)
val = rk + checksum
_encode_base58(val.to_i(16))
end
def wif_to_pri_key(_wif)
pri_key = ""
_val = _decode_base58(_wif)
if _wif.size == 52
pri_key = _val[2..-11]
end
if _wif.size == 51
pri_key = _val[2..-9]
end
pri_key
end
puts "WIF: Wallet Import Format"
puts "非压缩私钥的WIF格式是51位长度, 已5开头"
puts "压缩私钥的WIF格式是52位长度, 已K或L开头"
puts
res = pri_key_to_wif(_wif_mainnet, _pri_key)
puts "wif: " + res
puts "私钥: " + wif_to_pri_key(res)
puts "私钥: " + wif_to_pri_key(pri_key_to_wif(_wif_mainnet, _pri_key, false))
# http://learnmeabitcoin.com/glossary/wif
# https://github.com/dougal/base58/blob/master/lib/base58.rb