Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[feat] Expose HD public key derivation #155

Open
chromatic opened this issue Aug 13, 2023 · 4 comments
Open

[feat] Expose HD public key derivation #155

chromatic opened this issue Aug 13, 2023 · 4 comments

Comments

@chromatic
Copy link
Contributor

Feature Request

Describe the Feature Request

BIP-44 private key derivation exists and works according to the tests. However, it'd be safer to expose extended public key derivation, such that users do not have to expose their public keys.

This code may work as it exists, so I might be asking for more complete documentation and testing.

Describe Preferred Solution

Just as src/address.c exposes getHDAddress by path and path components, expose similar functions which accept an extpub key instead.

Related Code

I expect the code to work something like this:

  • deserialize a provided key to a HD node, regardless of whether it's extpriv or extpub
  • generate a HD key from the node (respecting chain params and public/private input)
  • derive a new key from the HD key and the path

Again, my simple reading of src/address.c makes me think that it works, but I'm not sure if I have the correct results to write tests.

@xanimo
Copy link
Member

xanimo commented Aug 15, 2023

so i just tested deriving ext pubkey from ext pubkey in the address tests and this worked fine for me:

    /* bip44 hd pubkey to derived hd extended child pubkey */
    char* pubkey_ext = "dgub8wfrZMXz8ojFcPziSubEoQ65sB4PYPyYTMo3PqFwf2Vx5zZ6ia17Nk2Py25c3dvq1e7ZnfBrurCS5wuagzRoBCXhJ2NeGU54NBytvuUuRyA";
    res = getDerivedHDAddressByPath(pubkey_ext, "m/0/0/0/0/0", extout, false);
    u_assert_int_eq(res, true);
    u_assert_str_eq(extout, "dgub8waBQm8Ym74KcWfeNwgxUcon6q3AiBdEYhsFxn6WYjmWXF9Gr1HiVhpb8RDCivjaDVhzuNSWjCYPonrvUduAhxrStr2yXAU7ePQc6R8q3dd");

the problem is we can't derive ext child pub keys from ext pubkeys because of hardening derivation standard stated in bip44, thus this one which more or less aligns with bip32 without hardening flags ' or h.

@xanimo
Copy link
Member

xanimo commented Aug 15, 2023

extra info re bip32:

Public parent key → public child key

The function CKDpub((Kpar, cpar), i) → (Ki, ci) computes a child extended public key from the parent extended public key. It is only defined for non-hardened child keys.

    Check whether i ≥ 231 (whether the child is a hardened key).
        If so (hardened child): return failure
        If not (normal child): let I = HMAC-SHA512(Key = cpar, Data = serP(Kpar) || ser32(i)).
    Split I into two 32-byte sequences, IL and IR.
    The returned child key Ki is point(parse256(IL)) + Kpar.
    The returned chain code ci is IR.
    In case parse256(IL) ≥ n or Ki is the point at infinity, the resulting key is invalid, and one should proceed with the next value for i.

@xanimo xanimo closed this as completed Feb 7, 2024
@xanimo xanimo reopened this Feb 7, 2024
@xanimo
Copy link
Member

xanimo commented Feb 7, 2024

@chromatic is this issue resolved?

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants