From BIP32:
We symbolize an prolonged personal key as (ok, c), with ok the conventional
personal key, and c the chain code. An prolonged public secret is
represented as (Okay, c), with Okay = level(ok) and c the chain code.
level(p): returns the coordinate pair ensuing from EC level
multiplication (repeated software of the EC group operation) of the
secp256k1 base level with the integer p.
ser256(p): serializes the integer p as a 32-byte sequence,
most important byte first.
serP(P): serializes the coordinate pair P = (x,y) as a byte
sequence utilizing SEC1’s compressed type: (0x02 or 0x03) ||
ser256(x), the place the header byte depends upon the parity of
the omitted y coordinate.
Prolonged private and non-private keys are serialized as follows:
- 4 byte: model bytes (mainnet: 0x0488B21E public, 0x0488ADE4 personal; testnet: 0x043587CF public, 0x04358394 personal)
- 1 byte: depth: 0x00 for grasp nodes, 0x01 for level-1 derived keys, ….
- 4 bytes: the fingerprint of the guardian’s key (0x00000000 if grasp key)
- 4 bytes: little one quantity. That is ser32(i) for i in xi = xpar/i, with xi the important thing being serialized. (0x00000000 if grasp key)
- 32 bytes: the chain code
- 33 bytes: the general public key or personal key information (serP(Okay) for public keys, 0x00 || ser256(ok) for personal keys)
This 78 byte construction will be encoded like different Bitcoin information in
Base58, by first including 32 checksum bits (derived from the double
SHA-256 checksum), after which changing to the Base58 illustration.
This ends in a Base58-encoded string of as much as 112 characters.
Thus the prolonged public key (xpub) will be derived from the prolonged personal key (xprv) as follows:
- Convert the xprv from Base58 to bytes and extract the personal key from the final 33 bytes (ignoring the checksum).
- Calculate the general public key from the personal key as per level(p).
- Serialize the outcome:
- 4 bytes: 0x0488B21E (mainnet) or 0x043587CF (testnet)
- 41 bytes: depth, guardian fingerprint, little one quantity and chain code are the identical as within the xprv
- 33 bytes: public key serialized utilizing serP(Okay)
- Add the 4-byte checksum and convert to Base58.