Merge pull request #298 from jdlcdl/bip85_via_embit070

bip85 child seeds via embit.bip85.derive_mnemonic()
This commit is contained in:
Nick Klockenga
2023-01-20 21:42:17 -05:00
committed by GitHub
2 changed files with 7 additions and 30 deletions
+1 -1
View File
@@ -1,4 +1,4 @@
embit==0.6.1
embit==0.7.0
numpy==1.21.1
picamera==1.13
Pillow==8.2.0
+6 -29
View File
@@ -1,16 +1,13 @@
import unicodedata
from binascii import hexlify
from embit import bip39, bip32
from embit import bip39, bip32, bip85
from embit.networks import NETWORKS
from typing import List
from seedsigner.models.settings import SettingsConstants
from seedsigner.helpers import embit_utils
import hashlib
import hmac
class InvalidSeedException(Exception):
pass
@@ -37,7 +34,7 @@ class Seed:
@staticmethod
def get_wordlist(wordlist_language_code: str = SettingsConstants.WORDLIST_LANGUAGE__ENGLISH) -> List[str]:
# TODO: Support other bip-39 wordlist languages!
# TODO: Support other BIP-39 wordlist languages!
if wordlist_language_code == SettingsConstants.WORDLIST_LANGUAGE__ENGLISH:
return bip39.WORDLIST
else:
@@ -101,7 +98,7 @@ class Seed:
def set_wordlist_language_code(self, language_code: str):
# TODO: Support other bip-39 wordlist languages!
# TODO: Support other BIP-39 wordlist languages!
raise Exception("Not yet implemented!")
@@ -114,32 +111,12 @@ class Seed:
return embit_utils.get_xpub(seed_bytes=self.seed_bytes, derivation_path=wallet_path, embit_network=SettingsConstants.map_network_to_embit(network))
# Derives a BIP85 mnemonic (seed word) from the master seed words using embit functions
def get_bip85_child_mnemonic(self, bip85_index: int, bip85_num_words: int, network: str = SettingsConstants.MAINNET):
# Calculate the master bip32 root key from the parents bip39 seed_bytes (the mnemonic entropy)
"""Derives the seed's nth BIP-85 child mnemonic"""
root = bip32.HDKey.from_seed(self.seed_bytes, version=NETWORKS[SettingsConstants.map_network_to_embit(network)]["xprv"])
# TODO: Support other bip-39 wordlist languages!
# As per the BIP85 spec, 39 is the application number used for bip39 mnemonic,
# we use the selected word count and the index to form the full path.
path = "m/83696968'/39'/0'/{bip85_num_words}'/{bip85_index}'".format(
bip85_num_words=bip85_num_words,
bip85_index=bip85_index)
# Derive the child xprv (HDKey) using the path format defined above
xprv = root.derive(path)
# The xprv.secret plus the BIP85 key is hashed together using hmac sha512.
entropy = hmac.new(key=b'bip-entropy-from-k', msg=xprv.secret, digestmod=hashlib.sha512).digest()
# Calculate number of bytes to retain for the entropy
# 24 words the width is 32bytes (256bits)
# 12 words the width is 16bytes (128bits)
width = round(bip85_num_words / 12 * 16)
# Return the derived BIP85 child mnemonic using the truncated derived entropy
return bip39.mnemonic_from_bytes(entropy[:width])
# TODO: Support other BIP-39 wordlist languages!
return bip85.derive_mnemonic(root, bip85_num_words, bip85_index)
### override operators