github.com/turingchain2020/turingchain@v1.1.21/wallet/bipwallet/bipwallet.go (about) 1 // Copyright Turing Corp. 2018 All Rights Reserved. 2 // Use of this source code is governed by a BSD-style 3 // license that can be found in the LICENSE file. 4 5 // Package bipwallet 比特币改进协议钱包相关定义 6 package bipwallet 7 8 import ( 9 "errors" 10 "strings" 11 12 "github.com/turingchain2020/turingchain/common/address" 13 "github.com/turingchain2020/turingchain/common/crypto" 14 log "github.com/turingchain2020/turingchain/common/log/log15" 15 "github.com/turingchain2020/turingchain/types" 16 bip32 "github.com/turingchain2020/turingchain/wallet/bipwallet/go-bip32" 17 bip39 "github.com/turingchain2020/turingchain/wallet/bipwallet/go-bip39" 18 bip44 "github.com/turingchain2020/turingchain/wallet/bipwallet/go-bip44" 19 "github.com/turingchain2020/turingchain/wallet/bipwallet/transformer" 20 _ "github.com/turingchain2020/turingchain/wallet/bipwallet/transformer/btcbase" //register 21 ) 22 23 // https://github.com/satoshilabs/slips/blob/master/slip-0044.md 24 const ( 25 TypeBitcoin uint32 = 0x80000000 26 TypeLitecoin uint32 = 0x80000002 27 TypeEther uint32 = 0x8000003c 28 TypeEtherClassic uint32 = 0x8000003d 29 TypeFactomFactoids uint32 = 0x80000083 30 TypeFactomEntryCredits uint32 = 0x80000084 31 TypeZcash uint32 = 0x80000085 32 TypeTrc uint32 = 0x80003333 33 TypeYcc uint32 = 0x80003334 34 ) 35 36 // CoinName 币种名称 37 var CoinName = map[uint32]string{ 38 TypeEther: "ETH", 39 TypeEtherClassic: "ETC", 40 TypeBitcoin: "BTC", 41 TypeLitecoin: "LTC", 42 TypeZcash: "ZEC", 43 TypeTrc: "TRC", 44 TypeYcc: "YCC", 45 } 46 47 // coinNameType 映射关系 48 var coinNameType = map[string]uint32{ 49 "ETH": TypeEther, 50 "ETC": TypeEtherClassic, 51 "BTC": TypeBitcoin, 52 "LTC": TypeLitecoin, 53 "ZEC": TypeZcash, 54 "TRC": TypeTrc, 55 "YCC": TypeYcc, 56 } 57 58 //GetSLIP0044CoinType 获取货币的 CoinType 值 59 func GetSLIP0044CoinType(name string) uint32 { 60 name = strings.ToUpper(name) 61 if ty, ok := coinNameType[name]; ok { 62 return ty 63 } 64 log.Error("GetSLIP0044CoinType: " + name + " not exist.") 65 return TypeTrc 66 } 67 68 // HDWallet 支持BIP-44标准的HD钱包 69 type HDWallet struct { 70 CoinType uint32 71 RootSeed []byte 72 MasterKey *bip32.Key 73 KeyType uint32 74 } 75 76 // NewKeyPair 通过索引生成新的秘钥对 77 func (w *HDWallet) NewKeyPair(index uint32) (priv, pub []byte, err error) { 78 //bip44 标准 32字节私钥 79 key, err := bip44.NewKeyFromMasterKey(w.MasterKey, w.CoinType, bip32.FirstHardenedChild, 0, index) 80 if err != nil { 81 return nil, nil, err 82 } 83 if w.KeyType == types.SECP256K1 { 84 return key.Key, key.PublicKey().Key, err 85 } 86 87 edcrypto, err := crypto.New(crypto.GetName(int(w.KeyType))) 88 if err != nil { 89 return nil, nil, err 90 } 91 edkey, err := edcrypto.PrivKeyFromBytes(key.Key[:]) 92 if err != nil { 93 return nil, nil, err 94 } 95 96 priv = edkey.Bytes() 97 pub = edkey.PubKey().Bytes() 98 99 return 100 } 101 102 // NewAddress 新建地址 103 func (w *HDWallet) NewAddress(index uint32) (string, error) { 104 if cointype, ok := CoinName[w.CoinType]; ok { 105 _, pub, err := w.NewKeyPair(index) 106 if err != nil { 107 return "", err 108 } 109 110 trans, err := transformer.New(cointype) 111 if err != nil { 112 return "", err 113 } 114 addr, err := trans.PubKeyToAddress(pub) 115 if err != nil { 116 return "", err 117 } 118 return addr, nil 119 } 120 121 return "", errors.New("cointype no support to create address") 122 123 } 124 125 // PrivkeyToPub 私钥转换成公钥 126 func PrivkeyToPub(coinType, keyTy uint32, priv []byte) ([]byte, error) { 127 if cointype, ok := CoinName[coinType]; ok { 128 trans, err := transformer.New(cointype) 129 if err != nil { 130 return nil, err 131 } 132 pub, err := trans.PrivKeyToPub(keyTy, priv) 133 if err != nil { 134 return nil, err 135 } 136 137 return pub, nil 138 139 } 140 return nil, errors.New("cointype no support to create address") 141 } 142 143 // PubToAddress 将公钥转换成地址 144 func PubToAddress(pub []byte) (string, error) { 145 return address.PubKeyToAddr(pub), nil 146 } 147 148 //NewMnemonicString 创建助记词 lang=0 英文助记词,lang=1 中文助记词bitsize=[128,256]并且bitsize%32=0 149 func NewMnemonicString(lang, bitsize int) (string, error) { 150 entropy, err := bip39.NewEntropy(bitsize) 151 if err != nil { 152 return "", err 153 } 154 155 mnemonic, err := bip39.NewMnemonic(entropy, int32(lang)) 156 if err != nil { 157 return "", err 158 } 159 return mnemonic, nil 160 } 161 162 // NewWalletFromMnemonic 通过助记词生成钱包对象 163 func NewWalletFromMnemonic(coinType, keyType uint32, mnemonic string) (wallet *HDWallet, err error) { 164 seed, err := bip39.NewSeedWithErrorChecking(mnemonic, "") 165 if err != nil { 166 return nil, err 167 } 168 169 return NewWalletFromSeed(coinType, keyType, seed) 170 } 171 172 // NewWalletFromSeed 通过种子生成钱包对象 173 func NewWalletFromSeed(coinType, keyType uint32, seed []byte) (wallet *HDWallet, err error) { 174 masterKey, err := bip32.NewMasterKey(seed) 175 if err != nil { 176 return nil, err 177 } 178 return &HDWallet{ 179 CoinType: coinType, 180 KeyType: keyType, 181 RootSeed: seed, 182 MasterKey: masterKey}, nil 183 }