Skip to content

Commit

Permalink
slip-0039: drop pbkdf2 for shares
Browse files Browse the repository at this point in the history
  • Loading branch information
prusnak committed Jul 25, 2018
1 parent 868cdd0 commit f8573bc
Showing 1 changed file with 8 additions and 8 deletions.
16 changes: 8 additions & 8 deletions slip-0039.md
Original file line number Diff line number Diff line change
Expand Up @@ -33,18 +33,20 @@ In case sufficient `M` values are provided the points exactly define the polynom

## Generating the mnemonic shares

The value to be encoded as the master secret must be a multiple of 8 bits. This is typically a wallet entropy, but may be another secret value which was uniformly chosen from its (key) space. The master secret is divided into `N` Shamir parts and `M` specifies how many of those parts do we need to reconstruct the master secret. We use `GF(256)` reduced by `x^8 + x^4 + x^3 + x + 1` (the Rijndael polynomial) as the underlying field.

We propose the following format of the shares:

| nonce (N) | index (I) | threshold (M) | share (SSS) | checksum (C) |
| nonce (N) | index (I) | threshold (M) | share (S) | checksum (C) |
|-----------|------------|---------------|------------------|--------------|
| 20 bits | 5 bits | 5 bits | 130/200/260 bits | 30 bits |

* `nonce` field is a random 20-bit identifier which is the same for all shares and it's used for detection whether the shares belong together, it's also later as salt in key derivation functions
* `index` field corresponds to the SSS part's `x` value (see the diagram above) and the SSS part is the corresponding `y` value
* `index` field corresponds to the SSS part's `x` value (see the diagram above)
* `threshold` field indicates how many shares are needed to reconstruct the secret
* `index` and `threshold` fields values are from range 1-31, value 0 is not considered valid
* `share` field is a randomly generated share
* `checksum` field is a Bech32 checksum (defined in BIP-0173) of the whole share (that is `N || I || M || SSS`), human-readable part (hrp) of Bech32 is "SLIP0039"
* `share` field is the corresponding SSS part's `y` value (see the diagram above) right-padded with zeroes to the nearest multiple of 10 bits
* `checksum` field is a Bech32 checksum (defined in BIP-0173) of the whole share (that is `N || I || M || S`), human-readable part (hrp) of Bech32 is "SLIP0039"

This structure is then converted into a mnemonic code by splitting it up by 10 bits which correspond as an index to the a word list containing exactly 1024 words (see below).

Expand All @@ -58,11 +60,9 @@ Construction has the nice property that nonce transforms into exactly the first

## Converting the mnemonic shares to master secret

Once enough `M` secrets are provided, we can produce the master secret from the shares. First, we check the checksum of each share and abort if they don't match. Implementations SHOULD NOT implement correction beyond potentially suggesting to the user where in the string an error might be found, without suggesting the correction to make.

Then we derive the shares using `PBKDF2(PRF = HMAC-SHA256, Password = SSS, Salt = (N || I || M || C), iterations = 1, dkLen = 256 bits)` where `SSS`, `N`, `I`, `M`, `C` values are encoded as 6 words from the wordlist separated by exactly one space.
First, we check the checksum of each share and abort if they don't match. Implementations SHOULD NOT implement correction beyond potentially suggesting to the user where in the string an error might be found, without suggesting the correction to make.

The resulting output from `PBKDF2` is a multiple of 8 bits. We can use Shamir Secret Sharing and reconstruct the master secret. We use `GF(256)` reduced by `x^8 + x^4 + x^3 + x + 1` (the Rijndael polynomial) as the underlying field.
If the checksum of each share is correct and enough `M` secrets are provided, we can produce the master secret from the shares.

## Passphrase

Expand Down

0 comments on commit f8573bc

Please sign in to comment.