Skip to content
This repository has been archived by the owner on Apr 15, 2019. It is now read-only.

Splitting by word is incorrect in passphrase validation #1050

Closed
webmaster128 opened this issue Apr 8, 2018 · 0 comments
Closed

Splitting by word is incorrect in passphrase validation #1050

webmaster128 opened this issue Apr 8, 2018 · 0 comments

Comments

@webmaster128
Copy link
Contributor

Expected behaviour

Code respects the fact that a word can occur more than one time in a BIP39 mnemonic.

Actual behaviour

Code assumes that a word occurs only once in a BIP39 mnemonic.

Steps to reproduce

Study BIP39 or run this code to convince yourself that there are valid mnemonics with a word occurring multiple times:

node double_word_finder.js

const bip39 = require('bip39');
const crypto = require('crypto');

function distinctWords(list) {
  return new Set(list).size;
}

const rounds = 100000;
let doubles = 0;

for (var i = 0; i < rounds; ++i) {
    let bytes = crypto.randomBytes(16);
    let mnemonic = bip39.entropyToMnemonic(bytes);
    let wordsCount = distinctWords(mnemonic.split(' '));
    if (wordsCount < 12) {
        console.log(mnemonic);
        doubles++;
    }
}

console.log("total rounds:", rounds, "with double words:", doubles);

This runs for ~10 seconds and outputs something like

[...]
setup pitch release blast skill stool column lottery forget permit exile pitch
misery destroy life trip grant achieve situate glide film clean misery confirm
pupil identify balcony glass bullet winner surround fiscal resource identify just before
mule prevent include dash aerobic clarify sweet limb prevent seven gift flip
three mail world desert circle tape layer spatial multiply size lobster lobster
total rounds: 100000 with double words: 3132

As you can see, we have a little over 3% mnemonics with at least one word occurring at lest 2 times.

Now we have this code:

https://github.com/LiskHQ/lisk-nano/blob/ab5aafe/src/components/passphrase/passphraseVerifier.js#L25

There the passphrase is split by a word. The rest of the code assumes this results in 2 parts:

https://github.com/LiskHQ/lisk-nano/blob/ab5aafe/src/components/passphrase/passphraseVerifier.js#L44

Now the problem is that the following nmemonic split by prevent

mule prevent include dash aerobic clarify sweet limb prevent seven gift flip

results in 3 parts.


Proposed solution: do not assume a word occurs only once and split by index (part 1: 0...index-1; part2: index+1…11).

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

No branches or pull requests

1 participant