Recover Bitbox password PBKDF2_ROUNDS_MCU = 2048,PBKDF2_ROUNDS_APP = 20480
#1
I am trying to recover a Bitbox wallet password based on a password hash and some knowledge of the password.
I found this old post where Undeath gave some advise on how a Bitbox plain text hash should be hex decoded and base64 encoded and formated for Haschat.
I created as test wallet and attempted to crack it with the know password using the attack mode specified by Undeath and failed.

Undeath gave the following advice based on the original question
"pbkdf2-hmac-sha512 (mode 12100) with 20480 iterations and a fixed salt "Digital Bitbox".

so your hash would look like
sha512:20480:RGlnaXRhbCBCaXRib3g=:[base64-encoded hash]"
https://hashcat.net/forum/thread-9813-post-51446.html

The test wallet was created using this online Bitbox backup code.
https://github.com/digitalbitbox/html_ba...ckup_in.js
https://github.com/digitalbitbox/html_ba.../backup.js

The information on the hashing I found in the code is:

var Crypto = require('crypto');


var PBKDF2_SALT = 'Digital Bitbox',
PBKDF2_HMACLEN = 64,
PBKDF2_ROUNDS_MCU = 2048,
PBKDF2_ROUNDS_APP = 20480;


later in the code the backup seed is hashed which is the format present in the wallet backup:

var hash = Crypto.createHash('sha256')

.update(new Buffer(ui.backupUserEntropy.value, 'ascii'))
.digest()
.toString('hex');
ui.backupEntropy.value = hash;

################################

My questions
1) Does anyone know what the following stands for? I think it is two rounds of hashing, but I am not sure how that would have been done.
"PBKDF2_ROUNDS_MCU = 2048,
PBKDF2_ROUNDS_APP = 20480;"
Update: MCU refers to the micro controller of the hardware wallet, APP is probably the wallet APP. So most likely hashing occurs two times.


2) Based on the code, is this indeed pbkdf2-hmac-sha512 (mode 12100) with 20480 rounds as Undeath indicated in his original post?
I am quite certain my decoding hex and base64 encoding is correct and that as such my test hash should have been cracked if the has mode was indeed 12100.

Just to be certain I will share my Python code for the conversion of the hash of the test wallet (that is allowed right?).

import codecs

## SEED/ENTROPY for test wallet with pwd 'test123', seed is always 64 bytes long
seed = '4fcc72e591076ec13ec1adad6daf769fce8217c1307908183f9ebea1b58e9cb2' # Hex format

## Decode Hex, encode base 64 for hashcat
b64 = codecs.encode(codecs.decode(seed, 'hex'), 'base64').decode()
## b64 = T8xy5ZEHbsE+wa2tba92n86CF8EweQgYP56+obWOnLI=

The results test hash is:
sha512:20480:RGlnaXRhbCBCaXRib3g=:T8xy5ZEHbsE+wa2tba92n86CF8EweQgYP56+obWOnLI=
Reply
#2
RESOLVED
After analyzing the html and javascript code I realized that the Bitbox 1 backups only contains the plain sha256 of the mnemonic input (also other input is allowed). Bitbox does not use the mnemonic index or a checksum like the normal seed generation process of a BIP39 mnemonic.

This means that the backup seed (stored in the pdf file that you put on the SD of the Bitbox) is not yet hashed with the password. So similar to normal BIP39 it is not something Hascat can attack.
The only way to recover coins from a Bitbox is to repeat the derivation procedure with many possible passwords and see if the resulting Bitcoin addresses are one of the addresses you used. This is much slower than using Hashcat to brute-force a hash. I am working on some Python scripts to do the derivation and check in a list of addresses (any Bitcoin address in existence).
In case you read this post and you are in a similar situation, you can contact me. Note that because the attack is very slow this only makes sense if you have some solid knowledge of the password. So if you planned to brute force someone else's Bitbox, forget about, it is not gonna work, BitBox security is solid.
Reply