Пример #1
0
    def test_testnet(self):
        # bitcoin core derivation style
        rootxprv = b'tprv8ZgxMBicQKsPe3g3HwF9xxTLiyc5tNyEtjhBBAk29YA3MTQUqULrmg7aj9qTKNfieuu2HryQ6tGVHse9x7ANFGs3f4HgypMc5nSSoxwf7TK'

        # m/0'/0'/51'
        addr1 = b'mfXYCCsvWPgeCv8ZYGqcubpNLYy5nYHbbj'
        indexes = [0x80000000, 0x80000000, 0x80000000 + 51]
        addr = bip32.p2pkh_address_from_xpub(
            bip32.xpub_from_xprv(bip32.derive(rootxprv, indexes)))
        self.assertEqual(addr, addr1)
        path = "m/0'/0'/51'"
        addr = bip32.p2pkh_address_from_xpub(
            bip32.xpub_from_xprv(bip32.derive(rootxprv, path)))
        self.assertEqual(addr, addr1)

        # m/0'/1'/150'
        addr2 = b'mfaUnRFxVvf55uD1P3zWXpprN1EJcKcGrb'
        indexes = [0x80000000, 0x80000000 + 1, 0x80000000 + 150]
        addr = bip32.p2pkh_address_from_xpub(
            bip32.xpub_from_xprv(bip32.derive(rootxprv, indexes)))
        self.assertEqual(addr, addr2)
        path = "m/0'/1'/150'"
        addr = bip32.p2pkh_address_from_xpub(
            bip32.xpub_from_xprv(bip32.derive(rootxprv, path)))
        self.assertEqual(addr, addr2)
Пример #2
0
def test_slip132_test_vector() -> None:
    """SLIP132 test vector

    https://github.com/satoshilabs/slips/blob/master/slip-0132.md
    """
    mnemonic = "abandon abandon abandon abandon abandon abandon abandon abandon abandon abandon abandon about"
    kpath = "./0/0"
    test_vectors: List[Tuple[bytes, str, str, str, str]] = [
        (
            NETWORKS["mainnet"]["bip32_prv"],
            "m / 44h / 0h / 0h",
            "xprv9xpXFhFpqdQK3TmytPBqXtGSwS3DLjojFhTGht8gwAAii8py5X6pxeBnQ6ehJiyJ6nDjWGJfZ95WxByFXVkDxHXrqu53WCRGypk2ttuqncb",
            "xpub6BosfCnifzxcFwrSzQiqu2DBVTshkCXacvNsWGYJVVhhawA7d4R5WSWGFNbi8Aw6ZRc1brxMyWMzG3DSSSSoekkudhUd9yLb6qx39T9nMdj",
            "1LqBGSKuX5yYUonjxT5qGfpUsXKYYWeabA",
        ),
        (
            NETWORKS["mainnet"]["slip132_p2wpkh_p2sh_prv"],
            "m / 49h / 0h / 0h",
            "yprvAHwhK6RbpuS3dgCYHM5jc2ZvEKd7Bi61u9FVhYMpgMSuZS613T1xxQeKTffhrHY79hZ5PsskBjcc6C2V7DrnsMsNaGDaWev3GLRQRgV7hxF",
            "ypub6Ww3ibxVfGzLrAH1PNcjyAWenMTbbAosGNB6VvmSEgytSER9azLDWCxoJwW7Ke7icmizBMXrzBx9979FfaHxHcrArf3zbeJJJUZPf663zsP",
            "37VucYSaXLCAsxYyAPfbSi9eh4iEcbShgf",
        ),
        (
            NETWORKS["mainnet"]["slip132_p2wpkh_prv"],
            "m / 84h / 0h / 0h",
            "zprvAdG4iTXWBoARxkkzNpNh8r6Qag3irQB8PzEMkAFeTRXxHpbF9z4QgEvBRmfvqWvGp42t42nvgGpNgYSJA9iefm1yYNZKEm7z6qUWCroSQnE",
            "zpub6rFR7y4Q2AijBEqTUquhVz398htDFrtymD9xYYfG1m4wAcvPhXNfE3EfH1r1ADqtfSdVCToUG868RvUUkgDKf31mGDtKsAYz2oz2AGutZYs",
            "bc1qcr8te4kr609gcawutmrza0j4xv80jy8z306fyu",
        ),
    ]
    for version, der_path, prv, pub, addr_str in test_vectors:
        addr = addr_str.encode()
        rxprv = bip32.mxprv_from_bip39_mnemonic(mnemonic, "")
        mxprv = bip32.derive(rxprv, der_path, version)
        assert prv.encode() == mxprv
        mxpub = bip32.xpub_from_xprv(mxprv)
        assert pub.encode() == mxpub
        xpub = bip32.derive(mxpub, kpath)
        address = slip132.address_from_xpub(xpub)
        assert addr == address
        address = slip132.address_from_xkey(xpub)
        assert addr == address
        xprv = bip32.derive(mxprv, kpath)
        address = slip132.address_from_xkey(xprv)
        assert addr == address
        if version == NETWORKS["mainnet"]["bip32_prv"]:
            address = base58address.p2pkh(xpub)
            assert addr == address
            address = base58address.p2pkh(xprv)
            assert addr == address
        elif version == NETWORKS["mainnet"]["slip132_p2wpkh_p2sh_prv"]:
            address = base58address.p2wpkh_p2sh(xpub)
            assert addr == address
            address = base58address.p2wpkh_p2sh(xprv)
            assert addr == address
        elif version == NETWORKS["mainnet"]["slip132_p2wpkh_prv"]:
            address = bech32address.p2wpkh(xpub)
            assert addr == address
            address = bech32address.p2wpkh(xprv)
            assert addr == address
Пример #3
0
    def test_crack(self):
        parent_xpub = b'xpub6BabMgRo8rKHfpAb8waRM5vj2AneD4kDMsJhm7jpBDHSJvrFAjHJHU5hM43YgsuJVUVHWacAcTsgnyRptfMdMP8b28LYfqGocGdKCFjhQMV'
        child_xprv = b'xprv9xkG88dGyiurKbVbPH1kjdYrA8poBBBXa53RKuRGJXyruuoJUDd8e4m6poiz7rV8Z4NoM5AJNcPHN6aj8wRFt5CWvF8VPfQCrDUcLU5tcTm'
        parent_xprv = crack_prvkey(parent_xpub, child_xprv)
        self.assertEqual(xpub_from_xprv(parent_xprv), parent_xpub)
        # same check with XKeyDict
        parent_xprv = crack_prvkey(deserialize(parent_xpub),
                                   deserialize(child_xprv))
        self.assertEqual(xpub_from_xprv(parent_xprv), parent_xpub)

        # extended parent key is not a public one
        self.assertRaises(ValueError, crack_prvkey, parent_xprv, child_xprv)
        #crack_prvkey(parent_xprv, child_xprv)

        # extended child key is not a private one
        self.assertRaises(ValueError, crack_prvkey, parent_xpub, parent_xpub)
        #crack_prvkey(parent_xpub, parent_xpub)

        # wrong child/parent depth relation
        child_xpub = xpub_from_xprv(child_xprv)
        self.assertRaises(ValueError, crack_prvkey, child_xpub, child_xprv)
        #crack_prvkey(child_xpub, child_xprv)

        # not a child for the provided parent
        child0_xprv = derive(parent_xprv, 0)
        grandchild_xprv = derive(child0_xprv, 0)
        self.assertRaises(ValueError, crack_prvkey, child_xpub,
                          grandchild_xprv)
        #crack_prvkey(child_xpub, grandchild_xprv)

        # hardened derivation
        hardened_child_xprv = derive(parent_xprv, 0x80000000)
        self.assertRaises(ValueError, crack_prvkey, parent_xpub,
                          hardened_child_xprv)
Пример #4
0
def test_crack():
    parent_xpub = "xpub6BabMgRo8rKHfpAb8waRM5vj2AneD4kDMsJhm7jpBDHSJvrFAjHJHU5hM43YgsuJVUVHWacAcTsgnyRptfMdMP8b28LYfqGocGdKCFjhQMV"
    child_xprv = "xprv9xkG88dGyiurKbVbPH1kjdYrA8poBBBXa53RKuRGJXyruuoJUDd8e4m6poiz7rV8Z4NoM5AJNcPHN6aj8wRFt5CWvF8VPfQCrDUcLU5tcTm"
    parent_xprv = crack_prvkey(parent_xpub, child_xprv)
    assert xpub_from_xprv(parent_xprv).decode() == parent_xpub
    # same check with XKeyDict
    parent_xprv = crack_prvkey(deserialize(parent_xpub), deserialize(child_xprv))
    assert xpub_from_xprv(parent_xprv).decode() == parent_xpub

    errmsg = "extended parent key is not a public key: "
    with pytest.raises(ValueError, match=errmsg):
        crack_prvkey(parent_xprv, child_xprv)

    errmsg = "extended child key is not a private key: "
    with pytest.raises(ValueError, match=errmsg):
        crack_prvkey(parent_xpub, parent_xpub)

    child_xpub = xpub_from_xprv(child_xprv)
    with pytest.raises(ValueError, match="not a parent's child: wrong depths"):
        crack_prvkey(child_xpub, child_xprv)

    child0_xprv = derive(parent_xprv, 0)
    grandchild_xprv = derive(child0_xprv, 0)
    errmsg = "not a parent's child: wrong parent fingerprint"
    with pytest.raises(ValueError, match=errmsg):
        crack_prvkey(child_xpub, grandchild_xprv)

    hardened_child_xprv = derive(parent_xprv, 0x80000000)
    with pytest.raises(ValueError, match="hardened child derivation"):
        crack_prvkey(parent_xpub, hardened_child_xprv)
Пример #5
0
    def test_slip32_test_vector(self):
        """SLIP32 test vector

        https://github.com/satoshilabs/slips/blob/master/slip-0132.md
        """
        mnemonic = "abandon abandon abandon abandon abandon abandon abandon abandon abandon abandon abandon about"
        kpath = "./0/0"
        test_vectors = [
            [
                MAIN_xprv, "m / 44h / 0h / 0h",
                b'xprv9xpXFhFpqdQK3TmytPBqXtGSwS3DLjojFhTGht8gwAAii8py5X6pxeBnQ6ehJiyJ6nDjWGJfZ95WxByFXVkDxHXrqu53WCRGypk2ttuqncb',
                b'xpub6BosfCnifzxcFwrSzQiqu2DBVTshkCXacvNsWGYJVVhhawA7d4R5WSWGFNbi8Aw6ZRc1brxMyWMzG3DSSSSoekkudhUd9yLb6qx39T9nMdj',
                b'1LqBGSKuX5yYUonjxT5qGfpUsXKYYWeabA'
            ],
            [
                MAIN_yprv, "m / 49h / 0h / 0h",
                b'yprvAHwhK6RbpuS3dgCYHM5jc2ZvEKd7Bi61u9FVhYMpgMSuZS613T1xxQeKTffhrHY79hZ5PsskBjcc6C2V7DrnsMsNaGDaWev3GLRQRgV7hxF',
                b'ypub6Ww3ibxVfGzLrAH1PNcjyAWenMTbbAosGNB6VvmSEgytSER9azLDWCxoJwW7Ke7icmizBMXrzBx9979FfaHxHcrArf3zbeJJJUZPf663zsP',
                b'37VucYSaXLCAsxYyAPfbSi9eh4iEcbShgf'
            ],
            [
                MAIN_zprv, "m / 84h / 0h / 0h",
                b'zprvAdG4iTXWBoARxkkzNpNh8r6Qag3irQB8PzEMkAFeTRXxHpbF9z4QgEvBRmfvqWvGp42t42nvgGpNgYSJA9iefm1yYNZKEm7z6qUWCroSQnE',
                b'zpub6rFR7y4Q2AijBEqTUquhVz398htDFrtymD9xYYfG1m4wAcvPhXNfE3EfH1r1ADqtfSdVCToUG868RvUUkgDKf31mGDtKsAYz2oz2AGutZYs',
                b'bc1qcr8te4kr609gcawutmrza0j4xv80jy8z306fyu'
            ],
        ]
        for v in test_vectors:
            rxprv = bip32.rootxprv_from_bip39mnemonic(mnemonic, '', v[0])
            mxprv = bip32.derive(rxprv, v[1])
            self.assertEqual(v[2], mxprv)
            mxpub = bip32.xpub_from_xprv(mxprv)
            self.assertEqual(v[3], mxpub)
            xpub = bip32.derive(mxpub, kpath)
            address = slip32.address_from_xpub(xpub)
            self.assertEqual(v[4], address)
            address = slip32.address_from_xkey(xpub)
            self.assertEqual(v[4], address)
            xprv = bip32.derive(mxprv, kpath)
            address = slip32.address_from_xkey(xprv)
            self.assertEqual(v[4], address)
            if v[0] == MAIN_xprv:
                address = base58address.p2pkh(xpub)
                self.assertEqual(v[4], address)
                address = base58address.p2pkh(xprv)
                self.assertEqual(v[4], address)
            elif v[0] == MAIN_yprv:
                address = base58address.p2wpkh_p2sh(xpub)
                self.assertEqual(v[4], address)
                address = base58address.p2wpkh_p2sh(xprv)
                self.assertEqual(v[4], address)
            elif v[0] == MAIN_zprv:
                address = bech32address.p2wpkh(xpub)
                self.assertEqual(v[4], address)
                address = bech32address.p2wpkh(xprv)
                self.assertEqual(v[4], address)
Пример #6
0
    def test_fingerprint(self):
        xprv = b"xprv9s21ZrQH143K3QTDL4LXw2F7HEK3wJUD2nW2nRk4stbPy6cq3jPPqjiChkVvvNKmPGJxWUtg6LnF5kejMRNNU3TGtRBeJgk33yuGBxrMPHi"
        f = fingerprint(xprv)
        child_key = derive(xprv, b'\x00\x00\x00\x00')
        pf = deserialize(child_key)['parent_fingerprint']
        self.assertEqual(f, pf)

        xpub = xpub_from_xprv(xprv)
        f = fingerprint(xpub)
        self.assertEqual(f, pf)

        child_key2 = derive(deserialize(xprv), 0)
        self.assertEqual(child_key2, child_key)
Пример #7
0
def test_fingerprint():

    xpub = "xpub661MyMwAqRbcFMYjmw8C6dJV97a4oLss6hb3v9wTQn2X48msQB61RCaLGtNhzgPCWPaJu7SvuB9EBSFCL43kTaFJC3owdaMka85uS154cEh"
    pf = fingerprint(xpub)
    child_key = bip32.derive(xpub, 0)
    pf2 = bip32.deserialize(child_key)["parent_fingerprint"]
    assert pf == pf2
Пример #8
0
    def test_crack(self):
        parent_xpub = b'xpub6BabMgRo8rKHfpAb8waRM5vj2AneD4kDMsJhm7jpBDHSJvrFAjHJHU5hM43YgsuJVUVHWacAcTsgnyRptfMdMP8b28LYfqGocGdKCFjhQMV'
        child_xprv = b'xprv9xkG88dGyiurKbVbPH1kjdYrA8poBBBXa53RKuRGJXyruuoJUDd8e4m6poiz7rV8Z4NoM5AJNcPHN6aj8wRFt5CWvF8VPfQCrDUcLU5tcTm'
        parent_xprv = bip32.crack(parent_xpub, child_xprv)
        self.assertEqual(bip32.xpub_from_xprv(parent_xprv), parent_xpub)
        index = bip32.child_index(child_xprv)
        self.assertEqual(bip32.ckd(parent_xprv, index), child_xprv)
        path = [index]
        self.assertEqual(bip32.derive(parent_xprv, path), child_xprv)

        # extended parent key is not a public one
        self.assertRaises(ValueError, bip32.crack, parent_xprv, child_xprv)
        #bip32.crack(parent_xprv, child_xprv)

        # extended child key is not a private one
        self.assertRaises(ValueError, bip32.crack, parent_xpub, parent_xpub)
        #bip32.crack(parent_xpub, parent_xpub)

        # wrong child/parent depth relation
        child_xpub = bip32.xpub_from_xprv(child_xprv)
        self.assertRaises(ValueError, bip32.crack, child_xpub, child_xprv)
        #bip32.crack(child_xpub, child_xprv)

        # not a child for the provided parent
        child0_xprv = bip32.ckd(parent_xprv, 0)
        grandchild_xprv = bip32.ckd(child0_xprv, 0)
        self.assertRaises(ValueError, bip32.crack, child_xpub, grandchild_xprv)
        #bip32.crack(child_xpub, grandchild_xprv)

        # hardened derivation
        hardened_child_xprv = bip32.ckd(parent_xprv, 0x80000000)
        self.assertRaises(ValueError, bip32.crack, parent_xpub, hardened_child_xprv)
Пример #9
0
def derive_child_sec_from_xpub(xpub, path):
    child_xpub = bip32.derive(xpub, path)
    child_xpub_bytes = base58.decode_check(child_xpub)
    # assertion about length?
    child_sec_bytes = child_xpub_bytes[-33:]
    child_sec_hex = child_sec_bytes.hex()
    return child_sec_hex
Пример #10
0
def test_vectors():
    fname = "electrum_test_vectors.json"
    filename = path.join(path.dirname(__file__), "test_data", fname)
    with open(filename, "r") as f:
        test_vectors = json.load(f)

    lang = "en"
    for test_vector in test_vectors:
        mnemonic = test_vector[0]
        passphrase = test_vector[1]
        mxprv = test_vector[2]
        mxpub = test_vector[3]
        address = test_vector[4]  # "./0/0"

        if mnemonic != "":
            mxprv2 = bip32.mxprv_from_electrum_mnemonic(mnemonic, passphrase)
            assert mxprv2 == mxprv.encode()

            eversion, mnemonic = electrum.version_from_mnemonic(mnemonic)
            entr = int(electrum.entropy_from_mnemonic(mnemonic, lang), 2)
            mnem = electrum.mnemonic_from_entropy(entr, eversion, lang)
            assert mnem == mnemonic

        if mxprv != "":
            mxpub2 = bip32.xpub_from_xprv(mxprv)
            assert mxpub2 == mxpub.encode()

        xpub = bip32.derive(mxpub, "./0/0")
        address2 = slip32.address_from_xpub(xpub).decode("ascii")
        assert address2 == address
Пример #11
0
def test_fingerprint() -> None:

    seed = "bfc4cbaad0ff131aa97fa30a48d09ae7df914bcc083af1e07793cd0a7c61a03f65d622848209ad3366a419f4718a80ec9037df107d8d12c19b83202de00a40ad"
    xprv = rootxprv_from_seed(seed)
    pf = fingerprint(xprv)  # xprv is automatically converted to xpub
    child_key = derive(xprv, 0x80000000)
    pf2 = BIP32KeyData.deserialize(child_key).parent_fingerprint
    assert pf == pf2
Пример #12
0
    def test_exceptions2(self):
        rootxprv = b'xprv9s21ZrQH143K2ZP8tyNiUtgoezZosUkw9hhir2JFzDhcUWKz8qFYk3cxdgSFoCMzt8E2Ubi1nXw71TLhwgCfzqFHfM5Snv4zboSebePRmLS'
        d = deserialize(rootxprv)
        self.assertEqual(serialize(d), rootxprv)

        # invalid 34-bytes key length
        d['key'] += b'\x00'
        self.assertRaises(ValueError, serialize, d)
        # serialize(d)

        # invalid 33-bytes chain_code length
        d = deserialize(rootxprv)
        d['chain_code'] += b'\x00'
        self.assertRaises(ValueError, serialize, d)
        # serialize(d)

        # invalid 5-bytes parent_fingerprint length
        d = deserialize(rootxprv)
        d['parent_fingerprint'] += b'\x00'
        self.assertRaises(ValueError, serialize, d)
        # serialize(d)

        # invalid 5-bytes index length
        d = deserialize(rootxprv)
        d['index'] += b'\x00'
        self.assertRaises(ValueError, serialize, d)
        # serialize(d)

        # invalid depth (256)
        d = deserialize(rootxprv)
        d['depth'] = 256
        self.assertRaises(ValueError, serialize, d)
        # serialize(d)

        # zero depth with non-zero index b'\x00\x00\x00\x01'
        d = deserialize(rootxprv)
        d['index'] = b'\x00\x00\x00\x01'
        self.assertRaises(ValueError, serialize, d)
        # serialize(d)

        # zero depth with non-zero parent_fingerprint b'\x00\x00\x00\x01'
        d = deserialize(rootxprv)
        d['parent_fingerprint'] = b'\x00\x00\x00\x01'
        self.assertRaises(ValueError, serialize, d)
        # serialize(d)

        # non-zero depth (1) with zero parent_fingerprint b'\x00\x00\x00\x00'
        xprv = deserialize(derive(rootxprv, 1))
        xprv['parent_fingerprint'] = b'\x00\x00\x00\x00'
        self.assertRaises(ValueError, serialize, xprv)
        # serialize(xprv)

        # int too big to convert
        self.assertRaises(OverflowError, derive, rootxprv, 256**4)

        # Index must be 4-bytes, not 5
        self.assertRaises(ValueError, derive, rootxprv, b'\x00' * 5)
Пример #13
0
 def test_fingerprint(self):
     xpub = "xpub661MyMwAqRbcFtXgS5sYJABqqG9YLmC4Q1Rdap9gSE8NqtwybGhePY2gZ29ESFjqJoCu1Rupje8YtGqsefD265TMg7usUDFdp6W1EGMcet8"
     pf = fingerprint(xpub)
     # bytes are used to increase code coverage
     # dict is used to increase code coverage
     xpubd = bip32.deserialize(xpub)
     child_key = bip32.derive(xpubd, b'\x00' * 4)
     pf2 = bip32.deserialize(child_key)['parent_fingerprint']
     self.assertEqual(pf, pf2)
Пример #14
0
def test_bips_pr905() -> None:
    "https://github.com/bitcoin/bips/pull/905"

    seed = "57fb1e450b8afb95c62afbcd49e4100d6790e0822b8905608679180ac34ca0bd45bf7ccc6c5f5218236d0eb93afc78bd117b9f02a6b7df258ea182dfaef5aad7"
    xroot = rootxprv_from_seed(seed)
    der_path = "m/44H/60H/0H"
    xprv = b"xprv9yqXG1Cns3YEQi6fsCJ7NGV5sHPiyZcbgLVst61dbLYyn7qy1G9aFtRmaYp481ounqnVf9Go2ymQ4gmxZLEwYSRhU868aDk4ZxzGvqHJVhe"
    assert derive(xroot, der_path) == xprv
    xpub = b"xpub6CpsfWjghR6XdCB8yDq7jQRpRKEDP2LT3ZRUgURF9g5xevB7YoTpogkFRqq5nQtVSN8YCMZo2CD8u4zCaxRv85ctCWmzEi9gQ5DBhBFaTNo"
    assert xpub_from_xprv(xprv) == xpub
Пример #15
0
    def test_testnet(self):
        # bitcoin core derivation style
        rootxprv = "tprv8ZgxMBicQKsPe3g3HwF9xxTLiyc5tNyEtjhBBAk29YA3MTQUqULrmg7aj9qTKNfieuu2HryQ6tGVHse9x7ANFGs3f4HgypMc5nSSoxwf7TK"

        # m / 0h / 0h / 51h
        addr1 = b"mfXYCCsvWPgeCv8ZYGqcubpNLYy5nYHbbj"
        indexes = [0x80000000, 0x80000000, 0x80000000 + 51]
        addr = p2pkh(xpub_from_xprv(derive(rootxprv, indexes)))
        self.assertEqual(addr, addr1)
        path = "m/0h/0h/51h"
        addr = p2pkh(xpub_from_xprv(derive(rootxprv, path)))
        self.assertEqual(addr, addr1)

        # m / 0h / 1h / 150h
        addr2 = b"mfaUnRFxVvf55uD1P3zWXpprN1EJcKcGrb"
        indexes = [0x80000000, 0x80000000 + 1, 0x80000000 + 150]
        addr = p2pkh(xpub_from_xprv(derive(rootxprv, indexes)))
        self.assertEqual(addr, addr2)
        path = "m/0h/1h/150h"
        addr = p2pkh(xpub_from_xprv(derive(rootxprv, path)))
        self.assertEqual(addr, addr2)
Пример #16
0
def test_derive_from_account() -> None:

    seed = "bfc4cbaad0ff131aa97fa30a48d09ae7df914bcc083af1e07793cd0a7c61a03f65d622848209ad3366a419f4718a80ec9037df107d8d12c19b83202de00a40ad"
    rmxprv = bip32.rootxprv_from_seed(seed)

    der_path = "m / 44 h / 0 h"
    mxpub = bip32.xpub_from_xprv(bip32.derive(rmxprv, der_path))

    test_vectors = [
        [0, 0],
        [0, 1],
        [0, 2],
        [1, 0],
        [1, 1],
        [1, 2],
    ]

    for branch, index in test_vectors:
        full_path = der_path + f"/{branch}/{index}"
        addr = p2pkh(bip32.derive(rmxprv, full_path)).decode()
        assert addr == p2pkh(bip32.derive_from_account(mxpub, branch,
                                                       index)).decode()

    errmsg = "invalid private derivation at branch level"
    with pytest.raises(ValueError, match=errmsg):
        bip32.derive_from_account(mxpub, 0x80000000, 0, True)

    errmsg = "invalid branch: "
    with pytest.raises(ValueError, match=errmsg):
        bip32.derive_from_account(mxpub, 2, 0)

    errmsg = "invalid private derivation at address index level"
    with pytest.raises(ValueError, match=errmsg):
        bip32.derive_from_account(mxpub, 0, 0x80000000)

    der_path = "m / 44 h / 0"
    mxpub = bip32.xpub_from_xprv(bip32.derive(rmxprv, der_path))
    errmsg = "public derivation at account level"
    with pytest.raises(UserWarning, match=errmsg):
        bip32.derive_from_account(mxpub, 0, 0)
Пример #17
0
def test_derive() -> None:

    test_vectors = {
        "xprv9s21ZrQH143K2ZP8tyNiUtgoezZosUkw9hhir2JFzDhcUWKz8qFYk3cxdgSFoCMzt8E2Ubi1nXw71TLhwgCfzqFHfM5Snv4zboSebePRmLS":
        [
            ["m / 0 h / 0 h / 463 h", "1DyfBWxhVLmrJ7keyiHeMbt7N3UdeGU4G5"],
            ["M / 0H / 0h // 267' / ", "11x2mn59Qy43DjisZWQGRResjyQmgthki"],
        ],
        "tprv8ZgxMBicQKsPe3g3HwF9xxTLiyc5tNyEtjhBBAk29YA3MTQUqULrmg7aj9qTKNfieuu2HryQ6tGVHse9x7ANFGs3f4HgypMc5nSSoxwf7TK":
        [
            ["m / 0 h / 0 h / 51 h", "mfXYCCsvWPgeCv8ZYGqcubpNLYy5nYHbbj"],
            ["m / 0 h / 1 h / 150 h", "mfaUnRFxVvf55uD1P3zWXpprN1EJcKcGrb"],
        ],
    }

    for rootxprv, value in test_vectors.items():
        for der_path, address in value:
            assert address == p2pkh(bip32.derive(rootxprv, der_path)).decode()

            b_indexes, _ = bip32._indexes_from_path(der_path)
            indexes = [int.from_bytes(b_index, "big") for b_index in b_indexes]
            assert address == p2pkh(bip32.derive(rootxprv, indexes)).decode()
Пример #18
0
    def test_utils(self):
        # root key, zero depth
        xprv = b"xprv9s21ZrQH143K3QTDL4LXw2F7HEK3wJUD2nW2nRk4stbPy6cq3jPPqjiChkVvvNKmPGJxWUtg6LnF5kejMRNNU3TGtRBeJgk33yuGBxrMPHi"
        xdict = deserialize(xprv)

        decoded_key = b58decode(xprv, 78)
        self.assertEqual(xdict["version"], decoded_key[:4])
        self.assertEqual(xdict["depth"], decoded_key[4])
        self.assertEqual(xdict["parent_fingerprint"], decoded_key[5:9])
        self.assertEqual(xdict["index"], decoded_key[9:13])
        self.assertEqual(xdict["chain_code"], decoded_key[13:45])
        self.assertEqual(xdict["key"], decoded_key[45:])

        # zero depth with non-zero parent_fingerprint
        f2 = b'\x01\x01\x01\x01'
        invalid_key = b58encode(xprv[:5] + f2 + xprv[9:])
        self.assertRaises(ValueError, deserialize, invalid_key)
        # deserialize(invalid_key)

        # zero depth with non-zero index
        i2 = b'\x01\x01\x01\x01'
        invalid_key = b58encode(xprv[:9] + i2 + xprv[13:])
        self.assertRaises(ValueError, deserialize, invalid_key)
        # deserialize(invalid_key)

        # non-zero depth (255) with zero parent_fingerprint
        d2 = b'ff'
        invalid_key = b58encode(xprv[:4] + d2 + xprv[5:])
        self.assertRaises(ValueError, deserialize, invalid_key)
        # deserialize(invalid_key)

        child_key = derive(xprv, 0)

        # Derivation path final depth 256>255
        self.assertRaises(ValueError, derive, child_key, "." + 255 * "/0")
        #derive(child_key, "."+255*"/0")

        # Empty derivation path
        self.assertRaises(ValueError, derive, child_key, "")
        #derive(child_key, "")

        # Invalid derivation path root: ";"
        self.assertRaises(ValueError, derive, child_key, ";/0")
        #derive(child_key, ";/0")

        # Derivation path depth 256>255
        self.assertRaises(ValueError, derive, child_key, "." + 256 * "/0")
        #derive(child_key, "." + 256*"/0")

        # xkey is not a public one
        self.assertRaises(ValueError, p2pkh_from_xpub, xprv)
Пример #19
0
    def test_vector3(self):
        """BIP32 test vector 3

        https://github.com/bitcoin/bips/blob/master/bip-0032.mediawiki
        """
        xkey_version = _PRV_VERSIONS[0]

        seed = "4b381541583be4423346c643850da4b320e46a87ae3d2a4e6da11eba819cd4acba45d239319ac14f863b8d5ab5a0d0c64d2e8a1e7d1457df2e5a3c51c73235be"
        rootxprv = rootxprv_from_seed(seed, xkey_version)
        self.assertEqual(
            rootxprv,
            b"xprv9s21ZrQH143K25QhxbucbDDuQ4naNntJRi4KUfWT7xo4EKsHt2QJDu7KXp1A3u7Bi1j8ph3EGsZ9Xvz9dGuVrtHHs7pXeTzjuxBrCmmhgC6"
        )
        rootxpub = xpub_from_xprv(rootxprv)  # neutering
        self.assertEqual(
            rootxpub,
            b"xpub661MyMwAqRbcEZVB4dScxMAdx6d4nFc9nvyvH3v4gJL378CSRZiYmhRoP7mBy6gSPSCYk6SzXPTf3ND1cZAceL7SfJ1Z3GC8vBgp2epUt13"
        )

        xprv = rootxprv
        xpub = rootxpub

        xprv = derive(xprv, ".")  # private relative
        self.assertEqual(
            xprv,
            b"xprv9s21ZrQH143K25QhxbucbDDuQ4naNntJRi4KUfWT7xo4EKsHt2QJDu7KXp1A3u7Bi1j8ph3EGsZ9Xvz9dGuVrtHHs7pXeTzjuxBrCmmhgC6"
        )
        xprv = derive(rootxprv, "m")  # private absolute
        self.assertEqual(
            xprv,
            b"xprv9s21ZrQH143K25QhxbucbDDuQ4naNntJRi4KUfWT7xo4EKsHt2QJDu7KXp1A3u7Bi1j8ph3EGsZ9Xvz9dGuVrtHHs7pXeTzjuxBrCmmhgC6"
        )
        xpub = derive(xpub, ".")  # public relative
        self.assertEqual(
            xpub,
            b"xpub661MyMwAqRbcEZVB4dScxMAdx6d4nFc9nvyvH3v4gJL378CSRZiYmhRoP7mBy6gSPSCYk6SzXPTf3ND1cZAceL7SfJ1Z3GC8vBgp2epUt13"
        )
        xpub = derive(rootxpub, "m")  # public absolute
        self.assertEqual(
            xpub,
            b"xpub661MyMwAqRbcEZVB4dScxMAdx6d4nFc9nvyvH3v4gJL378CSRZiYmhRoP7mBy6gSPSCYk6SzXPTf3ND1cZAceL7SfJ1Z3GC8vBgp2epUt13"
        )

        xprv = derive(xprv, "./0'")  # private relative
        self.assertEqual(
            xprv,
            b"xprv9uPDJpEQgRQfDcW7BkF7eTya6RPxXeJCqCJGHuCJ4GiRVLzkTXBAJMu2qaMWPrS7AANYqdq6vcBcBUdJCVVFceUvJFjaPdGZ2y9WACViL4L"
        )
        xprv = derive(rootxprv, "m/0'")  # private absolute
        self.assertEqual(
            xprv,
            b"xprv9uPDJpEQgRQfDcW7BkF7eTya6RPxXeJCqCJGHuCJ4GiRVLzkTXBAJMu2qaMWPrS7AANYqdq6vcBcBUdJCVVFceUvJFjaPdGZ2y9WACViL4L"
        )
        xpub = xpub_from_xprv(xprv)  # neutering
        self.assertEqual(
            xpub,
            b"xpub68NZiKmJWnxxS6aaHmn81bvJeTESw724CRDs6HbuccFQN9Ku14VQrADWgqbhhTHBaohPX4CjNLf9fq9MYo6oDaPPLPxSb7gwQN3ih19Zm4Y"
        )
Пример #20
0
def test_bip32_vectors():
    """BIP32 test vectors

    https://github.com/bitcoin/bips/blob/master/bip-0032.mediawiki
    """
    filename = path.join(data_folder, "bip32_test_vectors.json")
    with open(filename, "r") as f:
        test_vectors = json.load(f)

    for seed in test_vectors:
        mxprv = rootxprv_from_seed(seed)
        for der_path, xpub, xprv in test_vectors[seed]:
            assert xprv == derive(mxprv, der_path).decode()
            assert xpub == xpub_from_xprv(xprv).decode()
Пример #21
0
    def test_p2pkh_from_wif(self):
        seed = b"00" * 32  # better be random
        rxprv = bip32.rootxprv_from_seed(seed)
        path = "m/0h/0h/12"
        xprv = bip32.derive(rxprv, path)
        wif = wif_from_xprv(xprv)
        self.assertEqual(
            wif, b'KyLk7s6Z1FtgYEVp3bPckPVnXvLUWNCcVL6wNt3gaT96EmzTKZwP')
        address = p2pkh_from_wif(wif)
        xpub = bip32.xpub_from_xprv(xprv)
        address2 = slip32.address_from_xpub(xpub)
        self.assertEqual(address, address2)

        self.assertRaises(ValueError, wif_from_xprv, xpub)
Пример #22
0
    def test_bip32_vectors(self):
        """BIP32 test vector 3

        https://github.com/bitcoin/bips/blob/master/bip-0032.mediawiki
        """
        fname = "bip32_test_vectors.json"
        filename = path.join(path.dirname(__file__), "test_data", fname)
        with open(filename, "r") as f:
            test_vectors = json.load(f)

        for seed in test_vectors:
            mxprv = rootxprv_from_seed(seed)
            for der_path, xpub, xprv in test_vectors[seed]:
                self.assertEqual(xprv, derive(mxprv, der_path).decode())
                self.assertEqual(xpub, xpub_from_xprv(xprv).decode())
Пример #23
0
def test_p2pkh_from_wif() -> None:
    seed = b"\x00" * 32  # better be a documented test case
    rxprv = bip32.rootxprv_from_seed(seed)
    path = "m/0h/0h/12"
    xprv = bip32.derive(rxprv, path)
    wif = wif_from_prvkey(xprv)
    assert wif == b"L2L1dqRmkmVtwStNf5wg8nnGaRn3buoQr721XShM4VwDbTcn9bpm"
    pubkey, _ = pubkeyinfo_from_prvkey(wif)
    address = p2pkh(pubkey)
    xpub = bip32.xpub_from_xprv(xprv)
    address2 = slip132.address_from_xpub(xpub)
    assert address == address2

    err_msg = "not a private key: "
    with pytest.raises(ValueError, match=err_msg):
        wif_from_prvkey(xpub)
Пример #24
0
def derive(mpub: str, start: int, length: int):
    """
    Will generate list of derived addresses, starting at index <n> for <length>.
    :param mpub: master extended public key
    :param start: starting index to generate address list
    :param length: how many addresses to generate
    :return: a json list of derived addresses
    """

    address_list = {}
    for index in range(start, start + length):
        xpub = bip32.derive(xkey=mpub, path=f"./0/{index}")
        address = slip32.address_from_xpub(xpub).decode("ascii")
        address_list[f"0/{index}"] = address

    return json.dumps(address_list)
Пример #25
0
def test_p2pkh_from_wif() -> None:
    seed = b"00" * 32  # better be a documented test case
    rxprv = bip32.rootxprv_from_seed(seed)
    path = "m/0h/0h/12"
    xprv = bip32.derive(rxprv, path)
    wif = wif_from_prvkey(xprv)
    assert wif == b"KyLk7s6Z1FtgYEVp3bPckPVnXvLUWNCcVL6wNt3gaT96EmzTKZwP"
    pubkey, _ = pubkeyinfo_from_prvkey(wif)
    address = p2pkh(pubkey)
    xpub = bip32.xpub_from_xprv(xprv)
    address2 = slip132.address_from_xpub(xpub)
    assert address == address2

    err_msg = "not a private key: "
    with pytest.raises(ValueError, match=err_msg):
        wif_from_prvkey(xpub)
Пример #26
0
def test_serialize() -> None:
    rootxprv = "xprv9s21ZrQH143K2ZP8tyNiUtgoezZosUkw9hhir2JFzDhcUWKz8qFYk3cxdgSFoCMzt8E2Ubi1nXw71TLhwgCfzqFHfM5Snv4zboSebePRmLS"
    d = bip32.deserialize(rootxprv)
    assert bip32.serialize(d).decode() == rootxprv

    d["key"] += b"\x00"
    with pytest.raises(ValueError, match="invalid key length: "):
        bip32.serialize(d)

    d = bip32.deserialize(rootxprv)
    d["depth"] = 256
    with pytest.raises(ValueError, match="invalid depth "):
        bip32.serialize(d)

    d = bip32.deserialize(rootxprv)
    d["parent_fingerprint"] = b"\x00\x00\x00\x01"
    errmsg = "zero depth with non-zero parent fingerprint 0x"
    with pytest.raises(ValueError, match=errmsg):
        bip32.serialize(d)

    d = bip32.deserialize(rootxprv)
    d["index"] = b"\x00\x00\x00\x01"
    with pytest.raises(ValueError, match="zero depth with non-zero index 0x"):
        bip32.serialize(d)

    xprv = bip32.deserialize(bip32.derive(rootxprv, 0x80000000))
    xprv["parent_fingerprint"] = b"\x00\x00\x00\x00"
    errmsg = "zero parent fingerprint with non-zero depth "
    with pytest.raises(ValueError, match=errmsg):
        bip32.serialize(xprv)

    d = bip32.deserialize(rootxprv)
    d["parent_fingerprint"] += b"\x00"
    with pytest.raises(ValueError,
                       match="invalid parent fingerprint length: "):
        bip32.serialize(d)

    d = bip32.deserialize(rootxprv)
    d["index"] += b"\x00"
    with pytest.raises(ValueError, match="invalid index length: "):
        bip32.serialize(d)

    d = bip32.deserialize(rootxprv)
    d["chain_code"] += b"\x00"
    with pytest.raises(ValueError, match="invalid chain code length: "):
        bip32.serialize(d)
Пример #27
0
    def test_slip32(self):
        """SLIP32 test vector

        https://github.com/satoshilabs/slips/blob/master/slip-0132.md
        """

        mnemonic = "abandon abandon abandon abandon abandon abandon abandon abandon abandon abandon abandon about"
        passphrase = ""

        path = "m/44'/0'/0'"
        prv = b"xprv9xpXFhFpqdQK3TmytPBqXtGSwS3DLjojFhTGht8gwAAii8py5X6pxeBnQ6ehJiyJ6nDjWGJfZ95WxByFXVkDxHXrqu53WCRGypk2ttuqncb"
        pub = b"xpub6BosfCnifzxcFwrSzQiqu2DBVTshkCXacvNsWGYJVVhhawA7d4R5WSWGFNbi8Aw6ZRc1brxMyWMzG3DSSSSoekkudhUd9yLb6qx39T9nMdj"
        address = b"1LqBGSKuX5yYUonjxT5qGfpUsXKYYWeabA"
        rxprv = bip32.rootxprv_from_bip39mnemonic(mnemonic, passphrase,
                                                  MAIN_xprv)
        mprv = bip32.derive(rxprv, path)
        self.assertEqual(mprv, prv)
        mpub = bip32.xpub_from_xprv(mprv)
        self.assertEqual(mpub, pub)
        pub = bip32.derive(mpub, "./0/0")
        addr = slip32.address_from_xpub(pub)
        self.assertEqual(address, addr)

        path = "m/49'/0'/0'"
        prv = b"yprvAHwhK6RbpuS3dgCYHM5jc2ZvEKd7Bi61u9FVhYMpgMSuZS613T1xxQeKTffhrHY79hZ5PsskBjcc6C2V7DrnsMsNaGDaWev3GLRQRgV7hxF"
        pub = b"ypub6Ww3ibxVfGzLrAH1PNcjyAWenMTbbAosGNB6VvmSEgytSER9azLDWCxoJwW7Ke7icmizBMXrzBx9979FfaHxHcrArf3zbeJJJUZPf663zsP"
        address = b"37VucYSaXLCAsxYyAPfbSi9eh4iEcbShgf"
        rxprv = bip32.rootxprv_from_bip39mnemonic(mnemonic, passphrase,
                                                  MAIN_yprv)
        mprv = bip32.derive(rxprv, path)
        self.assertEqual(mprv, prv)
        mpub = bip32.xpub_from_xprv(mprv)
        self.assertEqual(mpub, pub)
        pub = bip32.derive(mpub, "./0/0")
        addr = slip32.address_from_xpub(pub)
        self.assertEqual(address, addr)
        addr = base58address.p2wpkh_p2sh_from_xpub(pub)
        self.assertEqual(address, addr)

        path = "m/84'/0'/0'"
        prv = b"zprvAdG4iTXWBoARxkkzNpNh8r6Qag3irQB8PzEMkAFeTRXxHpbF9z4QgEvBRmfvqWvGp42t42nvgGpNgYSJA9iefm1yYNZKEm7z6qUWCroSQnE"
        pub = b"zpub6rFR7y4Q2AijBEqTUquhVz398htDFrtymD9xYYfG1m4wAcvPhXNfE3EfH1r1ADqtfSdVCToUG868RvUUkgDKf31mGDtKsAYz2oz2AGutZYs"
        address = b"bc1qcr8te4kr609gcawutmrza0j4xv80jy8z306fyu"
        rxprv = bip32.rootxprv_from_bip39mnemonic(mnemonic, passphrase,
                                                  MAIN_zprv)
        mprv = bip32.derive(rxprv, path)
        self.assertEqual(mprv, prv)
        mpub = bip32.xpub_from_xprv(mprv)
        self.assertEqual(mpub, pub)
        pub = bip32.derive(mpub, "./0/0")
        addr = slip32.address_from_xpub(pub)
        self.assertEqual(address, addr)
Пример #28
0
    def test_vectors(self):
        filename = "electrum_test_vectors.json"
        path_to_filename = path.join(path.dirname(__file__), "./data/",
                                     filename)
        with open(path_to_filename, 'r') as f:
            test_vectors = json.load(f)
        f.closed

        lang = "en"
        for test_vector in test_vectors:
            mnemonic = test_vector[0]
            passphrase = test_vector[1]
            mxprv = test_vector[2]
            mxpub = test_vector[3]
            address = test_vector[4]  # "./0/0"

            if mnemonic != "":
                mxprv2 = electrum.masterxprv_from_mnemonic(
                    mnemonic, passphrase)
                self.assertEqual(mxprv2.decode(), mxprv)

                eversion = electrum.version_from_mnemonic(mnemonic)
                entr = int(electrum.entropy_from_mnemonic(mnemonic, lang), 2)
                mnem = electrum.mnemonic_from_entropy(eversion, entr, lang)
                self.assertEqual(mnem, mnemonic)

            if mxprv != "":
                mxpub2 = bip32.xpub_from_xprv(mxprv)
                self.assertEqual(mxpub2.decode(), mxpub)

            xpub = bip32.derive(mxpub, "./0/0")
            address2 = bip32.address_from_xpub(xpub).decode()
            self.assertEqual(address2, address)

        # version 2fa_segwit
        mnemonic = "slender flight session office noodle hand couple option office wait uniform morning"
        self.assertEqual("2fa_segwit",
                         electrum.version_from_mnemonic(mnemonic))

        # version 2fa
        mnemonic = "history recycle company awful donor fold beef nominee hard bleak bracket six"
        self.assertEqual("2fa", electrum.version_from_mnemonic(mnemonic))
Пример #29
0
    def test_vectors(self):
        fname = "electrum_test_vectors.json"
        filename = path.join(path.dirname(__file__), "test_data", fname)
        with open(filename, "r") as f:
            test_vectors = json.load(f)

        lang = "en"
        for test_vector in test_vectors:
            mnemonic = test_vector[0]
            passphrase = test_vector[1]
            mxprv = test_vector[2]
            mxpub = test_vector[3]
            address = test_vector[4]  # "./0/0"

            if mnemonic != "":
                mxprv2 = bip32.mxprv_from_electrum_mnemonic(
                    mnemonic, passphrase)
                self.assertEqual(mxprv2, mxprv.encode())

                eversion, mnemonic = electrum.version_from_mnemonic(mnemonic)
                entr = int(electrum.entropy_from_mnemonic(mnemonic, lang), 2)
                mnem = electrum.mnemonic_from_entropy(entr, eversion, lang)
                self.assertEqual(mnem, mnemonic)

            if mxprv != "":
                mxpub2 = bip32.xpub_from_xprv(mxprv)
                self.assertEqual(mxpub2, mxpub.encode())

            xpub = bip32.derive(mxpub, "./0/0")
            address2 = slip32.address_from_xpub(xpub).decode("ascii")
            self.assertEqual(address2, address)

        # version 2fa_segwit
        mnemonic = ("slender flight session office noodle  hand "
                    "couple  option office  wait   uniform morning")
        self.assertEqual("2fa_segwit",
                         electrum.version_from_mnemonic(mnemonic)[0])

        # version 2fa
        mnemonic = ("history recycle company awful donor   fold "
                    "beef    nominee hard    bleak bracket six")
        self.assertEqual("2fa", electrum.version_from_mnemonic(mnemonic)[0])
Пример #30
0
def test_vectors() -> None:
    fname = "electrum_test_vectors.json"
    filename = path.join(path.dirname(__file__), "test_data", fname)
    with open(filename, "r") as f:
        test_vectors = json.load(f)

    lang = "en"
    for mnemonic, passphrase, rmxprv, rmxpub, address in test_vectors:
        if mnemonic != "":
            mxprv2 = bip32.mxprv_from_electrum_mnemonic(mnemonic, passphrase)
            assert mxprv2 == rmxprv.encode()

            eversion, mnemonic = electrum.version_from_mnemonic(mnemonic)
            entr = int(electrum.entropy_from_mnemonic(mnemonic, lang), 2)
            mnem = electrum.mnemonic_from_entropy(entr, eversion, lang)
            assert mnem == mnemonic

        assert rmxpub.encode() == bip32.xpub_from_xprv(rmxprv)

        xprv = bip32.derive(rmxprv, "m/0h/0")
        address2 = slip132.address_from_xkey(xprv).decode("ascii")
        assert address2 == address