From f0c649b7acd1d8072142a0c1979b4ddd3ce25e31 Mon Sep 17 00:00:00 2001 From: Josh Rickmar Date: Wed, 15 Jan 2014 17:29:01 -0500 Subject: [PATCH] Make maximum keypool size a config option. --- account.go | 2 +- accountstore.go | 2 +- config.go | 13 ++++++++----- createtx.go | 2 +- sample-btcwallet.conf | 3 +++ wallet/wallet.go | 17 +++++++++-------- 6 files changed, 23 insertions(+), 16 deletions(-) diff --git a/account.go b/account.go index 6d6b971..f056ec9 100644 --- a/account.go +++ b/account.go @@ -548,7 +548,7 @@ func (a *Account) NewAddress() (btcutil.Address, error) { } // Get next address from wallet. - addr, err := a.NextChainedAddress(&bs) + addr, err := a.NextChainedAddress(&bs, cfg.KeypoolSize) if err != nil { a.mtx.Unlock() return nil, err diff --git a/accountstore.go b/accountstore.go index e034b63..bd488e5 100644 --- a/accountstore.go +++ b/accountstore.go @@ -189,7 +189,7 @@ func (store *AccountStore) CreateEncryptedWallet(name, desc string, passphrase [ } // Create new wallet in memory. - wlt, err := wallet.NewWallet(name, desc, passphrase, cfg.Net(), &bs) + wlt, err := wallet.NewWallet(name, desc, passphrase, cfg.Net(), &bs, cfg.KeypoolSize) if err != nil { return err } diff --git a/config.go b/config.go index 9fb4b8d..2ddb994 100644 --- a/config.go +++ b/config.go @@ -32,6 +32,7 @@ const ( defaultConfigFilename = "btcwallet.conf" defaultBtcNet = btcwire.TestNet3 defaultLogLevel = "info" + defaultKeypoolSize = 100 ) var ( @@ -58,6 +59,7 @@ type config struct { RPCCert string `long:"rpccert" description:"File containing the certificate file"` RPCKey string `long:"rpckey" description:"File containing the certificate key"` MainNet bool `long:"mainnet" description:"Use the main Bitcoin network (default testnet3)"` + KeypoolSize uint `short:"k" long:"keypoolsize" description:"Maximum number of addresses in keypool"` Proxy string `long:"proxy" description:"Connect via SOCKS5 proxy (eg. 127.0.0.1:9050)"` ProxyUser string `long:"proxyuser" description:"Username for proxy server"` ProxyPass string `long:"proxypass" default-mask:"-" description:"Password for proxy server"` @@ -137,11 +139,12 @@ func normalizeAddress(addr, defaultPort string) string { func loadConfig() (*config, []string, error) { // Default config. cfg := config{ - DebugLevel: defaultLogLevel, - ConfigFile: defaultConfigFile, - DataDir: defaultDataDir, - RPCKey: defaultRPCKeyFile, - RPCCert: defaultRPCCertFile, + DebugLevel: defaultLogLevel, + ConfigFile: defaultConfigFile, + DataDir: defaultDataDir, + RPCKey: defaultRPCKeyFile, + RPCCert: defaultRPCCertFile, + KeypoolSize: defaultKeypoolSize, } // A config file in the current directory takes precedence. diff --git a/createtx.go b/createtx.go index 2ed6168..c013a9b 100644 --- a/createtx.go +++ b/createtx.go @@ -245,7 +245,7 @@ func (a *Account) txToPairs(pairs map[string]int64, minconf int) (*CreatedTx, er // Get a new change address if one has not already been found. if changeAddr == nil { - changeAddr, err = a.NextChainedAddress(&bs) + changeAddr, err = a.NextChainedAddress(&bs, cfg.KeypoolSize) if err != nil { return nil, fmt.Errorf("failed to get next address: %s", err) } diff --git a/sample-btcwallet.conf b/sample-btcwallet.conf index fe72ad7..ea935b9 100644 --- a/sample-btcwallet.conf +++ b/sample-btcwallet.conf @@ -12,6 +12,9 @@ ; directory for mainnet and testnet wallets, respectively. ; datadir=~/.btcwallet +; Maximum number of addresses to generate for the keypool +; keypoolsize=100 + ; ------------------------------------------------------------------------------ diff --git a/wallet/wallet.go b/wallet/wallet.go index 179d514..620e2c1 100644 --- a/wallet/wallet.go +++ b/wallet/wallet.go @@ -46,9 +46,6 @@ const ( // Maximum length in bytes of a comment that can have a size represented // as a uint16. maxCommentLen = (1 << 16) - 1 - - // Number of addresses to extend keypool by. - nKeypoolIncrement = 100 ) const ( @@ -455,7 +452,7 @@ type Wallet struct { addrCommentMap map[btcutil.AddressPubKeyHash]comment txCommentMap map[transactionHashKey]comment - // These are not serialized. + // The rest of the fields in this struct are not serialized. secret struct { sync.Mutex key []byte @@ -469,7 +466,9 @@ type Wallet struct { // desc's binary representation must not exceed 32 and 256 bytes, // respectively. All address private keys are encrypted with passphrase. // The wallet is returned unlocked. -func NewWallet(name, desc string, passphrase []byte, net btcwire.BitcoinNet, createdAt *BlockStamp) (*Wallet, error) { +func NewWallet(name, desc string, passphrase []byte, net btcwire.BitcoinNet, + createdAt *BlockStamp, keypoolSize uint) (*Wallet, error) { + // Check sizes of inputs. if len([]byte(name)) > 32 { return nil, errors.New("name exceeds 32 byte maximum size") @@ -546,7 +545,7 @@ func NewWallet(name, desc string, passphrase []byte, net btcwire.BitcoinNet, cre w.chainIdxMap[rootKeyChainIdx] = w.keyGenerator.address(net) // Fill keypool. - if err := w.extendKeypool(nKeypoolIncrement, aeskey, createdAt); err != nil { + if err := w.extendKeypool(keypoolSize, aeskey, createdAt); err != nil { return nil, err } @@ -796,7 +795,9 @@ func (w *Wallet) Version() (string, int) { // NextChainedAddress attempts to get the next chained address, // refilling the keypool if necessary. -func (w *Wallet) NextChainedAddress(bs *BlockStamp) (*btcutil.AddressPubKeyHash, error) { +func (w *Wallet) NextChainedAddress(bs *BlockStamp, + keypoolSize uint) (*btcutil.AddressPubKeyHash, error) { + // Attempt to get address hash of next chained address. next160, ok := w.chainIdxMap[w.highestUsed+1] if !ok { @@ -810,7 +811,7 @@ func (w *Wallet) NextChainedAddress(bs *BlockStamp) (*btcutil.AddressPubKeyHash, copy(aeskey, w.secret.key) w.secret.Unlock() - err := w.extendKeypool(nKeypoolIncrement, aeskey, bs) + err := w.extendKeypool(keypoolSize, aeskey, bs) if err != nil { return nil, err }