From 6421cf3ff6662b74f76f019532721b619d4b70de Mon Sep 17 00:00:00 2001 From: ar-qun <17101722+ar-qun@users.noreply.github.com> Date: Tue, 26 Mar 2019 13:06:29 +0100 Subject: [PATCH] BIP-44 is default for Ledger wallets. The legacy BIP-32 is made optional and can be activated using option LedgerLegacyHDDerivationPath in commandline. --- accounts/hd.go | 8 ++++---- cmd/clef/main.go | 3 ++- cmd/geth/main.go | 5 +++-- cmd/geth/usage.go | 1 + cmd/utils/flags.go | 7 +++++++ node/config.go | 4 ++++ signer/core/api.go | 10 +++++----- signer/core/api_test.go | 2 +- 8 files changed, 27 insertions(+), 13 deletions(-) diff --git a/accounts/hd.go b/accounts/hd.go index 6ed6318078..6f8b7432c8 100644 --- a/accounts/hd.go +++ b/accounts/hd.go @@ -34,10 +34,10 @@ var DefaultRootDerivationPath = DerivationPath{0x80000000 + 44, 0x80000000 + 60, // at m/44'/60'/0'/0/1, etc. var DefaultBaseDerivationPath = DerivationPath{0x80000000 + 44, 0x80000000 + 60, 0x80000000 + 0, 0, 0} -// DefaultLedgerBaseDerivationPath is the base path from which custom derivation endpoints -// are incremented. As such, the first account will be at m/44'/60'/0'/0, the second -// at m/44'/60'/0'/1, etc. -var DefaultLedgerBaseDerivationPath = DerivationPath{0x80000000 + 44, 0x80000000 + 60, 0x80000000 + 0, 0} +// DefaultLegacyLedgerBaseDerivationPath is the base path from which custom derivation +// endpoints were incremented before the switch to BIP-44. As such, the first account +// will be at m/44'/60'/0'/0, the second at m/44'/60'/0'/1, etc. +var DefaultLegacyLedgerBaseDerivationPath = DerivationPath{0x80000000 + 44, 0x80000000 + 60, 0x80000000 + 0, 0} // DerivationPath represents the computer friendly version of a hierarchical // deterministic wallet account derivaion path. diff --git a/cmd/clef/main.go b/cmd/clef/main.go index a900312459..0a33eb0e2f 100644 --- a/cmd/clef/main.go +++ b/cmd/clef/main.go @@ -421,11 +421,12 @@ func signer(c *cli.Context) error { lightKdf = c.GlobalBool(utils.LightKDFFlag.Name) advanced = c.GlobalBool(advancedMode.Name) nousb = c.GlobalBool(utils.NoUSBFlag.Name) + ldgrLeg = c.GlobalBool(utils.LedgerLegacyHDDerivationPath.Name) ) log.Info("Starting signer", "chainid", chainId, "keystore", ksLoc, "light-kdf", lightKdf, "advanced", advanced) am := core.StartClefAccountManager(ksLoc, nousb, lightKdf) - apiImpl := core.NewSignerAPI(am, chainId, nousb, ui, db, advanced, pwStorage) + apiImpl := core.NewSignerAPI(am, chainId, nousb, ldgrLeg, ui, db, advanced, pwStorage) // Establish the bidirectional communication, by creating a new UI backend and registering // it with the UI. diff --git a/cmd/geth/main.go b/cmd/geth/main.go index 83847fc533..ca25fd89e3 100644 --- a/cmd/geth/main.go +++ b/cmd/geth/main.go @@ -64,6 +64,7 @@ var ( utils.KeyStoreDirFlag, utils.ExternalSignerFlag, utils.NoUSBFlag, + utils.LedgerLegacyHDDerivationPath, utils.DashboardEnabledFlag, utils.DashboardAddrFlag, utils.DashboardPortFlag, @@ -337,8 +338,8 @@ func startNode(ctx *cli.Context, stack *node.Node) { log.Info("New wallet appeared", "url", event.Wallet.URL(), "status", status) derivationPath := accounts.DefaultBaseDerivationPath - if event.Wallet.URL().Scheme == "ledger" { - derivationPath = accounts.DefaultLedgerBaseDerivationPath + if event.Wallet.URL().Scheme == "ledger" && ctx.GlobalIsSet(utils.LedgerLegacyHDDerivationPath.Name) { + derivationPath = accounts.DefaultLegacyLedgerBaseDerivationPath } event.Wallet.SelfDerive(derivationPath, stateReader) diff --git a/cmd/geth/usage.go b/cmd/geth/usage.go index 8658a3fdcf..f21a4177e2 100644 --- a/cmd/geth/usage.go +++ b/cmd/geth/usage.go @@ -71,6 +71,7 @@ var AppHelpFlagGroups = []flagGroup{ utils.DataDirFlag, utils.KeyStoreDirFlag, utils.NoUSBFlag, + utils.LedgerLegacyHDDerivationPath, utils.NetworkIdFlag, utils.TestnetFlag, utils.RinkebyFlag, diff --git a/cmd/utils/flags.go b/cmd/utils/flags.go index bf433242ec..e23046abb4 100644 --- a/cmd/utils/flags.go +++ b/cmd/utils/flags.go @@ -127,6 +127,10 @@ var ( Name: "nousb", Usage: "Disables monitoring for and managing USB hardware wallets", } + LedgerLegacyHDDerivationPath = cli.BoolFlag{ + Name: "ledgerlegacyhdderivationpath", + Usage: "For Ledger Hardware Wallet Use BIP32 to access old derivation path (not supported by Ledger Live anymore) ", + } NetworkIdFlag = cli.Uint64Flag{ Name: "networkid", Usage: "Network identifier (integer, 1=Frontier, 2=Morden (disused), 3=Ropsten, 4=Rinkeby)", @@ -1126,6 +1130,9 @@ func SetNodeConfig(ctx *cli.Context, cfg *node.Config) { if ctx.GlobalIsSet(NoUSBFlag.Name) { cfg.NoUSB = ctx.GlobalBool(NoUSBFlag.Name) } + if ctx.GlobalIsSet(LedgerLegacyHDDerivationPath.Name) { + cfg.LedgerLegacyHDDerivationPath = ctx.GlobalBool(LedgerLegacyHDDerivationPath.Name) + } } func setDataDir(ctx *cli.Context, cfg *node.Config) { diff --git a/node/config.go b/node/config.go index 2f871e478b..4350cac6e0 100644 --- a/node/config.go +++ b/node/config.go @@ -91,6 +91,10 @@ type Config struct { // NoUSB disables hardware wallet monitoring and connectivity. NoUSB bool `toml:",omitempty"` + // LedgerLegacyHDDerivationPath uses older BIP-32 HD derivation path that has + // dropped from Ledger Live in favor of BIP-44. + LedgerLegacyHDDerivationPath bool `toml:",omitempty"` + // IPCPath is the requested location to place the IPC endpoint. If the path is // a simple file name, it is placed inside the data directory (or on the root // pipe path on Windows), whereas if it's a resolvable path name (absolute or diff --git a/signer/core/api.go b/signer/core/api.go index 184b903103..e0a72ef322 100644 --- a/signer/core/api.go +++ b/signer/core/api.go @@ -234,13 +234,13 @@ var ErrRequestDenied = errors.New("Request denied") // key that is generated when a new Account is created. // noUSB disables USB support that is required to support hardware devices such as // ledger and trezor. -func NewSignerAPI(am *accounts.Manager, chainID int64, noUSB bool, ui UIClientAPI, abidb *AbiDb, advancedMode bool, credentials storage.Storage) *SignerAPI { +func NewSignerAPI(am *accounts.Manager, chainID int64, noUSB bool, ldgrLeg bool, ui UIClientAPI, abidb *AbiDb, advancedMode bool, credentials storage.Storage) *SignerAPI { if advancedMode { log.Info("Clef is in advanced mode: will warn instead of reject") } signer := &SignerAPI{big.NewInt(chainID), am, ui, NewValidator(abidb), !advancedMode, credentials} if !noUSB { - signer.startUSBListener() + signer.startUSBListener(ldgrLeg) } return signer } @@ -276,7 +276,7 @@ func (api *SignerAPI) openTrezor(url accounts.URL) { } // startUSBListener starts a listener for USB events, for hardware wallet interaction -func (api *SignerAPI) startUSBListener() { +func (api *SignerAPI) startUSBListener(ldgrLeg bool) { events := make(chan accounts.WalletEvent, 16) am := api.am am.Subscribe(events) @@ -306,8 +306,8 @@ func (api *SignerAPI) startUSBListener() { log.Info("New wallet appeared", "url", event.Wallet.URL(), "status", status) derivationPath := accounts.DefaultBaseDerivationPath - if event.Wallet.URL().Scheme == "ledger" { - derivationPath = accounts.DefaultLedgerBaseDerivationPath + if event.Wallet.URL().Scheme == "ledger" && ldgrLeg { + derivationPath = accounts.DefaultLegacyLedgerBaseDerivationPath } var nextPath = derivationPath // Derive first N accounts, hardcoded for now diff --git a/signer/core/api_test.go b/signer/core/api_test.go index 3225c10ea6..44c2339935 100644 --- a/signer/core/api_test.go +++ b/signer/core/api_test.go @@ -124,7 +124,7 @@ func setup(t *testing.T) (*SignerAPI, *headlessUi) { } ui := &headlessUi{make(chan string, 20), make(chan string, 20)} am := StartClefAccountManager(tmpDirName(t), true, true) - api := NewSignerAPI(am, 1337, true, ui, db, true, &storage.NoStorage{}) + api := NewSignerAPI(am, 1337, true, true, ui, db, true, &storage.NoStorage{}) return api, ui }