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

Ethereum Pre-Sale: PBKDF2-SHA256 #1279

Closed
Chick3nman opened this Issue Jun 18, 2017 · 17 comments

Comments

Projects
None yet
9 participants
@Chick3nman
Contributor

Chick3nman commented Jun 18, 2017

New algorithm: Ethereum Pre-Sale PBKDF2-SHA256

Use: Currently in use by Ethereum wallets that were made during the "PreSale".

Algorithm as detailed in simple terms here:

genwallet says:

genwallet(opts['seed'],pw,email)

You say "here's my email and pw"

seed says "give me super random number":

seed = random_key().decode('hex') # uses pybitcointools' 3-source random generator

so now you need to get your encseed:

encseed = aes.encryptData(pbkdf2(pw),seed)

so we head over to mr. aes and say whats up:

def encryptData(key, data, mode=AESModeOfOperation.modeOfOperation["CBC"], iv=None):
........
........

and now you have your encseed.

then you get the `ethpriv:

ethpriv = sha3(seed)

and your address:

ethaddr = sha3(privtopub(ethpriv)[1:])[12:].encode('hex')

and finally your bkp:

bkp = sha3(seed + '\x02').encode('hex')

So your bkp is the sha3 of your seed plus essentially the number "2" (number "1" was used for your btcpriv to differentiate it from your ethpriv) encoded in hex.

Algorithm used in "genwallet" function of pyethtool.py is being used as the master for comparison, however the pbkdf2 settings may differ from what is used in that function.

The correct PBKDF2 used is set like this:
pbkdf2(password, password, 2000)[:16]

The password is used as the salt and 2000 rounds are used.

Hash format as set by https://github.com/magnumripper/JohnTheRipper/blob/bleeding-jumbo/run/ethereum2john.py

$ethereum$w*encseed*ethaddr*bkp[:32]

Real world Pre-Sale wallet to be used for testing(thanks to @FredericHeem for posting this on the JTR OpenCL thread):

{"encseed": "0b2fa2c63a8b5603e1104fbada15a609aa9736ed41db1678d91a9b1a1f7c1628e711dbc250c4c289b06b0faa56cd499dc4af9daf878202db22cc61df1a91c918314c77ce92e5c8b1265580edd79a852acf40fe2138653ac16524c08247381d9802cf5ef3f8c4baf69fb869f2b7fb796bae853cfbdc3c5b788a14e75f39e0cf7df2e90779181a5dd45cce8e8df938af3c6b6c8a92ce123338e6ed87eb16ff11a02cd4a2a07aff8a3a57097fcf137501e07a941a7ce9bc19498252d98769125fbd2c9a14f1c56212a6bf2a7e374474c60e7a3a1cf443ce8194c4c960474472d6ca761ada075169fa8c7017bf1274b99df898deb65f51ed8eb29fbc0997d69c9800ad9b8351155bec5d8e7f73e7e2882a6e1b62883d0158c44fed8e4412fb18e75757e1355aaadd8a2dab50ae40c800d032dc77d3e84904085d628b5a13b60317d6f12ede26b7b38e7c6805bea1d2e11e3a7d7153b76ebfd99ae2536dfdd071ff8111a86fbd63e7b17155162263ef45471ac5b4c517520572cd19410cc4cbde77914fad12326fe5a4cbd5fc4a297740d6b5e64001196b0531e2464b7e4cee77136a38844b94dc59a9a72eec3ff49bca3d5bf0c29652ee6ff028e22f8936aac58fa3cf05ce4c8de8883204e43b57e4ebed922ad7b3a8953042033d34d7e94bc8ff393d1df4c8b062f5228b4f9dbc5d157af96772af1ef2c84f6562049b1c44f0359c07f193623a8b0f1b7e34b31481ddf54a24128e5a21b929f57fd07f8911ad8eb8d8bfe928ae9dfa2d35663764161094552a43b43a0a43dca687d4d04b79c8dbb2d4f87b7d8e0805a77adddfd5149741faa594009639fb730dccfbee1f99286aaf94052c06a1c68efc29dcd57a8b1a421e", "ethaddr": "f9438b7121a15fd127ec0d8a72ee2b3e8da04a5a", "bkp": "74fdb879ece341dd590a769f2cd39d6717aac4bd87b0e5c82084dd65a40750b4", "email": "pippo@gmail.com", "btcaddr": "1DcQxkURtPhtX1wH3DVkdz75UD4RdoefqG"}

Which produces the following hash, to which the correct password is "password":

./ethereum2john.py ethwallet.json 
ethwallet.json:$ethereum$w*0b2fa2c63a8b5603e1104fbada15a609aa9736ed41db1678d91a9b1a1f7c1628e711dbc250c4c289b06b0faa56cd499dc4af9daf878202db22cc61df1a91c918314c77ce92e5c8b1265580edd79a852acf40fe2138653ac16524c08247381d9802cf5ef3f8c4baf69fb869f2b7fb796bae853cfbdc3c5b788a14e75f39e0cf7df2e90779181a5dd45cce8e8df938af3c6b6c8a92ce123338e6ed87eb16ff11a02cd4a2a07aff8a3a57097fcf137501e07a941a7ce9bc19498252d98769125fbd2c9a14f1c56212a6bf2a7e374474c60e7a3a1cf443ce8194c4c960474472d6ca761ada075169fa8c7017bf1274b99df898deb65f51ed8eb29fbc0997d69c9800ad9b8351155bec5d8e7f73e7e2882a6e1b62883d0158c44fed8e4412fb18e75757e1355aaadd8a2dab50ae40c800d032dc77d3e84904085d628b5a13b60317d6f12ede26b7b38e7c6805bea1d2e11e3a7d7153b76ebfd99ae2536dfdd071ff8111a86fbd63e7b17155162263ef45471ac5b4c517520572cd19410cc4cbde77914fad12326fe5a4cbd5fc4a297740d6b5e64001196b0531e2464b7e4cee77136a38844b94dc59a9a72eec3ff49bca3d5bf0c29652ee6ff028e22f8936aac58fa3cf05ce4c8de8883204e43b57e4ebed922ad7b3a8953042033d34d7e94bc8ff393d1df4c8b062f5228b4f9dbc5d157af96772af1ef2c84f6562049b1c44f0359c07f193623a8b0f1b7e34b31481ddf54a24128e5a21b929f57fd07f8911ad8eb8d8bfe928ae9dfa2d35663764161094552a43b43a0a43dca687d4d04b79c8dbb2d4f87b7d8e0805a77adddfd5149741faa594009639fb730dccfbee1f99286aaf94052c06a1c68efc29dcd57a8b1a421e*f9438b7121a15fd127ec0d8a72ee2b3e8da04a5a*74fdb879ece341dd590a769f2cd39d67

@Chick3nman Chick3nman changed the title from Ethereum Pre-Sale: PBKDF2-HMAC-SHA256 to Ethereum Pre-Sale: PBKDF2-SHA256 Jun 18, 2017

@kost123

This comment has been minimized.

Show comment
Hide comment
@kost123

kost123 Aug 3, 2017

Also have a strong interest in this.

kost123 commented Aug 3, 2017

Also have a strong interest in this.

@Giampa79

This comment has been minimized.

Show comment
Hide comment
@Giampa79

Giampa79 Aug 9, 2017

I'm really interested in this !! Hashcat works perfectly with wallet but for pre-sale wallet at the time there's no distributable solution across GPU, so if you have 24/25 char password using CPU can be tricky :-)

Giampa79 commented Aug 9, 2017

I'm really interested in this !! Hashcat works perfectly with wallet but for pre-sale wallet at the time there's no distributable solution across GPU, so if you have 24/25 char password using CPU can be tricky :-)

@ChristianPapathanasiou

This comment has been minimized.

Show comment
Hide comment
@ChristianPapathanasiou

ChristianPapathanasiou Nov 5, 2017

This is sorely required...

ChristianPapathanasiou commented Nov 5, 2017

This is sorely required...

@anormore

This comment has been minimized.

Show comment
Hide comment
@anormore

anormore Dec 10, 2017

Still waiting..

anormore commented Dec 10, 2017

Still waiting..

@nicola

This comment has been minimized.

Show comment
Hide comment
@nicola

nicola Dec 13, 2017

please@!

nicola commented Dec 13, 2017

please@!

@ChristianPapathanasiou

This comment has been minimized.

Show comment
Hide comment
@ChristianPapathanasiou

ChristianPapathanasiou Dec 13, 2017

@philsmd

This comment has been minimized.

Show comment
Hide comment
@philsmd

philsmd Dec 14, 2017

Member

I must admit that I was quite unmotivated when I saw this issue for the first time because I saw that the algorithm description by the OP uses genwallet (), privtopub () and therefore I thought about Elliptic-curves cryptography and whatnot.

Now I just gave it another glance and it seems that all of this is not needed at all. The algorithm is very easy.
sha3 (aes_256_cbc_decrypt (pbkdf2 ($pass, $pass, 2000), $iv, $encseed) . "\x02")

So basically we just extract the first 16 bytes (0-15) from the "encseed" field which we use as the initialization vector (iv) for the AES-256-CBC decryption, the remaining bytes (starting from byte 16) we use as the encrypted seed.
The key for the AES-256-CBC decrytion is generated by using the user password as salt AND pass and use 2000 iterations of pbkdf2-hmac-sha256.

The final hash is just a sha3/keccak hash of the seed (the decrypted encseed from the AES decrytion mentioned above).

Therefore the code is basically just this:

#!/usr/bin/env perl

# Author: philsmd (for hashcat)
# Date: dec 2017
# License: CC0 (public domain)

use strict;
use warnings;

use Crypt::PBKDF2;
use Crypt::CBC;
use Digest::Keccak qw (keccak_256);

#
# Algorithm can be found in: https://github.com/tagawa/website/blob/f784ca60be00ddd6fab9418307cb74289822f1eb/pyethtool/pyethtool.py#L53 (attention: the pbkdf2 settings are different, also the salt for pbkdf is different)
#
# An example can be found here: https://github.com/hashcat/hashcat/issues/1279
#


# Example 1: (password is "password", without quotes):
# $ethereum$w*0b2fa2c63a8b5603e1104fbada15a609aa9736ed41db1678d91a9b1a1f7c1628e711dbc250c4c289b06b0faa56cd499dc4af9daf878202db22cc61df1a91c918314c77ce92e5c8b1265580edd79a852acf40fe2138653ac16524c08247381d9802cf5ef3f8c4baf69fb869f2b7fb796bae853cfbdc3c5b788a14e75f39e0cf7df2e90779181a5dd45cce8e8df938af3c6b6c8a92ce123338e6ed87eb16ff11a02cd4a2a07aff8a3a57097fcf137501e07a941a7ce9bc19498252d98769125fbd2c9a14f1c56212a6bf2a7e374474c60e7a3a1cf443ce8194c4c960474472d6ca761ada075169fa8c7017bf1274b99df898deb65f51ed8eb29fbc0997d69c9800ad9b8351155bec5d8e7f73e7e2882a6e1b62883d0158c44fed8e4412fb18e75757e1355aaadd8a2dab50ae40c800d032dc77d3e84904085d628b5a13b60317d6f12ede26b7b38e7c6805bea1d2e11e3a7d7153b76ebfd99ae2536dfdd071ff8111a86fbd63e7b17155162263ef45471ac5b4c517520572cd19410cc4cbde77914fad12326fe5a4cbd5fc4a297740d6b5e64001196b0531e2464b7e4cee77136a38844b94dc59a9a72eec3ff49bca3d5bf0c29652ee6ff028e22f8936aac58fa3cf05ce4c8de8883204e43b57e4ebed922ad7b3a8953042033d34d7e94bc8ff393d1df4c8b062f5228b4f9dbc5d157af96772af1ef2c84f6562049b1c44f0359c07f193623a8b0f1b7e34b31481ddf54a24128e5a21b929f57fd07f8911ad8eb8d8bfe928ae9dfa2d35663764161094552a43b43a0a43dca687d4d04b79c8dbb2d4f87b7d8e0805a77adddfd5149741faa594009639fb730dccfbee1f99286aaf94052c06a1c68efc29dcd57a8b1a421e*f9438b7121a15fd127ec0d8a72ee2b3e8da04a5a*74fdb879ece341dd590a769f2cd39d67
#

my $iv_and_encseed = pack ("H*", "0b2fa2c63a8b5603e1104fbada15a609aa9736ed41db1678d91a9b1a1f7c1628e711dbc250c4c289b06b0faa56cd499dc4af9daf878202db22cc61df1a91c918314c77ce92e5c8b1265580edd79a852acf40fe2138653ac16524c08247381d9802cf5ef3f8c4baf69fb869f2b7fb796bae853cfbdc3c5b788a14e75f39e0cf7df2e90779181a5dd45cce8e8df938af3c6b6c8a92ce123338e6ed87eb16ff11a02cd4a2a07aff8a3a57097fcf137501e07a941a7ce9bc19498252d98769125fbd2c9a14f1c56212a6bf2a7e374474c60e7a3a1cf443ce8194c4c960474472d6ca761ada075169fa8c7017bf1274b99df898deb65f51ed8eb29fbc0997d69c9800ad9b8351155bec5d8e7f73e7e2882a6e1b62883d0158c44fed8e4412fb18e75757e1355aaadd8a2dab50ae40c800d032dc77d3e84904085d628b5a13b60317d6f12ede26b7b38e7c6805bea1d2e11e3a7d7153b76ebfd99ae2536dfdd071ff8111a86fbd63e7b17155162263ef45471ac5b4c517520572cd19410cc4cbde77914fad12326fe5a4cbd5fc4a297740d6b5e64001196b0531e2464b7e4cee77136a38844b94dc59a9a72eec3ff49bca3d5bf0c29652ee6ff028e22f8936aac58fa3cf05ce4c8de8883204e43b57e4ebed922ad7b3a8953042033d34d7e94bc8ff393d1df4c8b062f5228b4f9dbc5d157af96772af1ef2c84f6562049b1c44f0359c07f193623a8b0f1b7e34b31481ddf54a24128e5a21b929f57fd07f8911ad8eb8d8bfe928ae9dfa2d35663764161094552a43b43a0a43dca687d4d04b79c8dbb2d4f87b7d8e0805a77adddfd5149741faa594009639fb730dccfbee1f99286aaf94052c06a1c68efc29dcd57a8b1a421e");

my $bkp = pack ("H*", "74fdb879ece341dd590a769f2cd39d67");

#
# Start:
#

# get the initialization vector for AES-256-CBC from the "encseed" field:

my $iv = substr ($iv_and_encseed, 0, 16);

# get the raw encrypted seed (encseed):

my $encseed = substr ($iv_and_encseed, 16);


# setup pbkdf2 params:

my $pbkdf2 = Crypt::PBKDF2->new
(
  hasher     => Crypt::PBKDF2->hasher_from_algorithm ('HMACSHA2', 256),
  iterations => 2000,
  output_len => 16
);


# main loop:

while (my $pass = <>)
{
  chomp ($pass);

  my $key = $pbkdf2->PBKDF2 ($pass, $pass);

  my $aes_cbc = Crypt::CBC->new ({
    key         => $key,
    cipher      => "Crypt::Rijndael",
    iv          => $iv,
    literal_key => 1,
    header      => "none",
    keysize     => 16
  });

  my $seed = $aes_cbc->decrypt ($encseed);

  my $hash = keccak_256 ($seed. "\x02");

  if (substr ($hash, 0, 16) eq $bkp)
  {
    print "Password found: '$pass'\n";

    exit (0);
  }
}

exit (1);

As you can see the algorithm is basically the same as -m 15600 = Ethereum Wallet, PBKDF2-HMAC-SHA256 (I say the same as -m 15600 because also 15600 uses a large number of iteration of pbkdf2 and a final keccak hashing step)... except that we need to AES decrypt the encseed field (with AES-256-CBC) to get the raw seed.

I was suprised that this algorithm is actually so easy, because from the description above it seemed to me that much more was involved here... but as said it is basically just the same as -m 15600 (with an additional AES decrypt step and slightly different settings for pbkdf2).

I think that this is really easy to add, not sure why nobody added it yet (maybe others were also confused about all this genwallet and pubtopriv stuff which is not used at all ... or it is just not that common to have these presale hashes anymore because they were just used for a very short time)

Member

philsmd commented Dec 14, 2017

I must admit that I was quite unmotivated when I saw this issue for the first time because I saw that the algorithm description by the OP uses genwallet (), privtopub () and therefore I thought about Elliptic-curves cryptography and whatnot.

Now I just gave it another glance and it seems that all of this is not needed at all. The algorithm is very easy.
sha3 (aes_256_cbc_decrypt (pbkdf2 ($pass, $pass, 2000), $iv, $encseed) . "\x02")

So basically we just extract the first 16 bytes (0-15) from the "encseed" field which we use as the initialization vector (iv) for the AES-256-CBC decryption, the remaining bytes (starting from byte 16) we use as the encrypted seed.
The key for the AES-256-CBC decrytion is generated by using the user password as salt AND pass and use 2000 iterations of pbkdf2-hmac-sha256.

The final hash is just a sha3/keccak hash of the seed (the decrypted encseed from the AES decrytion mentioned above).

Therefore the code is basically just this:

#!/usr/bin/env perl

# Author: philsmd (for hashcat)
# Date: dec 2017
# License: CC0 (public domain)

use strict;
use warnings;

use Crypt::PBKDF2;
use Crypt::CBC;
use Digest::Keccak qw (keccak_256);

#
# Algorithm can be found in: https://github.com/tagawa/website/blob/f784ca60be00ddd6fab9418307cb74289822f1eb/pyethtool/pyethtool.py#L53 (attention: the pbkdf2 settings are different, also the salt for pbkdf is different)
#
# An example can be found here: https://github.com/hashcat/hashcat/issues/1279
#


# Example 1: (password is "password", without quotes):
# $ethereum$w*0b2fa2c63a8b5603e1104fbada15a609aa9736ed41db1678d91a9b1a1f7c1628e711dbc250c4c289b06b0faa56cd499dc4af9daf878202db22cc61df1a91c918314c77ce92e5c8b1265580edd79a852acf40fe2138653ac16524c08247381d9802cf5ef3f8c4baf69fb869f2b7fb796bae853cfbdc3c5b788a14e75f39e0cf7df2e90779181a5dd45cce8e8df938af3c6b6c8a92ce123338e6ed87eb16ff11a02cd4a2a07aff8a3a57097fcf137501e07a941a7ce9bc19498252d98769125fbd2c9a14f1c56212a6bf2a7e374474c60e7a3a1cf443ce8194c4c960474472d6ca761ada075169fa8c7017bf1274b99df898deb65f51ed8eb29fbc0997d69c9800ad9b8351155bec5d8e7f73e7e2882a6e1b62883d0158c44fed8e4412fb18e75757e1355aaadd8a2dab50ae40c800d032dc77d3e84904085d628b5a13b60317d6f12ede26b7b38e7c6805bea1d2e11e3a7d7153b76ebfd99ae2536dfdd071ff8111a86fbd63e7b17155162263ef45471ac5b4c517520572cd19410cc4cbde77914fad12326fe5a4cbd5fc4a297740d6b5e64001196b0531e2464b7e4cee77136a38844b94dc59a9a72eec3ff49bca3d5bf0c29652ee6ff028e22f8936aac58fa3cf05ce4c8de8883204e43b57e4ebed922ad7b3a8953042033d34d7e94bc8ff393d1df4c8b062f5228b4f9dbc5d157af96772af1ef2c84f6562049b1c44f0359c07f193623a8b0f1b7e34b31481ddf54a24128e5a21b929f57fd07f8911ad8eb8d8bfe928ae9dfa2d35663764161094552a43b43a0a43dca687d4d04b79c8dbb2d4f87b7d8e0805a77adddfd5149741faa594009639fb730dccfbee1f99286aaf94052c06a1c68efc29dcd57a8b1a421e*f9438b7121a15fd127ec0d8a72ee2b3e8da04a5a*74fdb879ece341dd590a769f2cd39d67
#

my $iv_and_encseed = pack ("H*", "0b2fa2c63a8b5603e1104fbada15a609aa9736ed41db1678d91a9b1a1f7c1628e711dbc250c4c289b06b0faa56cd499dc4af9daf878202db22cc61df1a91c918314c77ce92e5c8b1265580edd79a852acf40fe2138653ac16524c08247381d9802cf5ef3f8c4baf69fb869f2b7fb796bae853cfbdc3c5b788a14e75f39e0cf7df2e90779181a5dd45cce8e8df938af3c6b6c8a92ce123338e6ed87eb16ff11a02cd4a2a07aff8a3a57097fcf137501e07a941a7ce9bc19498252d98769125fbd2c9a14f1c56212a6bf2a7e374474c60e7a3a1cf443ce8194c4c960474472d6ca761ada075169fa8c7017bf1274b99df898deb65f51ed8eb29fbc0997d69c9800ad9b8351155bec5d8e7f73e7e2882a6e1b62883d0158c44fed8e4412fb18e75757e1355aaadd8a2dab50ae40c800d032dc77d3e84904085d628b5a13b60317d6f12ede26b7b38e7c6805bea1d2e11e3a7d7153b76ebfd99ae2536dfdd071ff8111a86fbd63e7b17155162263ef45471ac5b4c517520572cd19410cc4cbde77914fad12326fe5a4cbd5fc4a297740d6b5e64001196b0531e2464b7e4cee77136a38844b94dc59a9a72eec3ff49bca3d5bf0c29652ee6ff028e22f8936aac58fa3cf05ce4c8de8883204e43b57e4ebed922ad7b3a8953042033d34d7e94bc8ff393d1df4c8b062f5228b4f9dbc5d157af96772af1ef2c84f6562049b1c44f0359c07f193623a8b0f1b7e34b31481ddf54a24128e5a21b929f57fd07f8911ad8eb8d8bfe928ae9dfa2d35663764161094552a43b43a0a43dca687d4d04b79c8dbb2d4f87b7d8e0805a77adddfd5149741faa594009639fb730dccfbee1f99286aaf94052c06a1c68efc29dcd57a8b1a421e");

my $bkp = pack ("H*", "74fdb879ece341dd590a769f2cd39d67");

#
# Start:
#

# get the initialization vector for AES-256-CBC from the "encseed" field:

my $iv = substr ($iv_and_encseed, 0, 16);

# get the raw encrypted seed (encseed):

my $encseed = substr ($iv_and_encseed, 16);


# setup pbkdf2 params:

my $pbkdf2 = Crypt::PBKDF2->new
(
  hasher     => Crypt::PBKDF2->hasher_from_algorithm ('HMACSHA2', 256),
  iterations => 2000,
  output_len => 16
);


# main loop:

while (my $pass = <>)
{
  chomp ($pass);

  my $key = $pbkdf2->PBKDF2 ($pass, $pass);

  my $aes_cbc = Crypt::CBC->new ({
    key         => $key,
    cipher      => "Crypt::Rijndael",
    iv          => $iv,
    literal_key => 1,
    header      => "none",
    keysize     => 16
  });

  my $seed = $aes_cbc->decrypt ($encseed);

  my $hash = keccak_256 ($seed. "\x02");

  if (substr ($hash, 0, 16) eq $bkp)
  {
    print "Password found: '$pass'\n";

    exit (0);
  }
}

exit (1);

As you can see the algorithm is basically the same as -m 15600 = Ethereum Wallet, PBKDF2-HMAC-SHA256 (I say the same as -m 15600 because also 15600 uses a large number of iteration of pbkdf2 and a final keccak hashing step)... except that we need to AES decrypt the encseed field (with AES-256-CBC) to get the raw seed.

I was suprised that this algorithm is actually so easy, because from the description above it seemed to me that much more was involved here... but as said it is basically just the same as -m 15600 (with an additional AES decrypt step and slightly different settings for pbkdf2).

I think that this is really easy to add, not sure why nobody added it yet (maybe others were also confused about all this genwallet and pubtopriv stuff which is not used at all ... or it is just not that common to have these presale hashes anymore because they were just used for a very short time)

@ChristianPapathanasiou

This comment has been minimized.

Show comment
Hide comment
@ChristianPapathanasiou

ChristianPapathanasiou Dec 14, 2017

@philsmd

This comment has been minimized.

Show comment
Hide comment
@philsmd

philsmd Dec 18, 2017

Member

Can anybody find out what the length of the seed normally is?
I see that john the ripper has example hashes with 64-16 bytes seed and 624-16 bytes of seed (the 16 bytes are used for the initialization vector):

https://github.com/magnumripper/JohnTheRipper/blob/4f7824e3e05120c9eb6735844f36867431997f6f/src/ethereum_common_plug.c#L25-L28

Other source code files mention that it is a sha256 () hash over some entropy data:

https://github.com/ethereum/pyethsaletool/blob/6fe7254d7109e7677c5fcafb7873cacff9d0e2a5/pyethsaletool.py#L213

https://github.com/vbuterin/pybitcointools/blob/aeb0a2bbb8bbfe421432d776c649650eaeb882a5/bitcoin/main.py#L416

I'm not sure which software generates the longer seed.
What software do/did you use and what is/was the length of the seed? Is it of fixed length? Is it 608 bytes (624-16) long or just 48 bytes (64-16) long?
It's okay if you do not know the raw seed, it's enough if we know the normal length of the encseed (encrypted seed).

Member

philsmd commented Dec 18, 2017

Can anybody find out what the length of the seed normally is?
I see that john the ripper has example hashes with 64-16 bytes seed and 624-16 bytes of seed (the 16 bytes are used for the initialization vector):

https://github.com/magnumripper/JohnTheRipper/blob/4f7824e3e05120c9eb6735844f36867431997f6f/src/ethereum_common_plug.c#L25-L28

Other source code files mention that it is a sha256 () hash over some entropy data:

https://github.com/ethereum/pyethsaletool/blob/6fe7254d7109e7677c5fcafb7873cacff9d0e2a5/pyethsaletool.py#L213

https://github.com/vbuterin/pybitcointools/blob/aeb0a2bbb8bbfe421432d776c649650eaeb882a5/bitcoin/main.py#L416

I'm not sure which software generates the longer seed.
What software do/did you use and what is/was the length of the seed? Is it of fixed length? Is it 608 bytes (624-16) long or just 48 bytes (64-16) long?
It's okay if you do not know the raw seed, it's enough if we know the normal length of the encseed (encrypted seed).

@jsteube jsteube closed this in bf65677 Dec 20, 2017

jsteube added a commit that referenced this issue Dec 20, 2017

Merge pull request #1476 from philsmd/master
fixes #1279: added -m 16300 = Ethereum Pre-Sale Wallet, PBKDF2-HMAC-SHA256
@branmcf

This comment has been minimized.

Show comment
Hide comment
@branmcf

branmcf Dec 25, 2017

@philsmd First of all, thank you for the PR! I've seen this question asked numerous times on multiple sites with very few answers, so hopefully this helps out. I know for a fact that Ethereum wallet backup json files with the format below exist, but I cannot speak as to whether this format is standardized.

{ "bkp": 64 chars, "btcaddr": 34 chars, "email": example@github.com, "encseed": 1248 chars, "ethaddr": 40 chars }

branmcf commented Dec 25, 2017

@philsmd First of all, thank you for the PR! I've seen this question asked numerous times on multiple sites with very few answers, so hopefully this helps out. I know for a fact that Ethereum wallet backup json files with the format below exist, but I cannot speak as to whether this format is standardized.

{ "bkp": 64 chars, "btcaddr": 34 chars, "email": example@github.com, "encseed": 1248 chars, "ethaddr": 40 chars }

@philsmd

This comment has been minimized.

Show comment
Hide comment
@philsmd

philsmd Jan 3, 2018

Member

@branmcf yeah, thanks for the confirmation. That's also what I saw what most modern software for ethereum generates.... it seems that some time ago the encseed was much shorter, e.g. 128 hex chars (64 bytes)
It shouldn't matter too much because hashcat now supports all these lengths for the encseed decryption.
Again, you could just extract the "hash" from the json file with ethereum2john.py (and remove the file names and colons if any are present) and run it with -m 16300 with hashcat (betas are already up on https://hashcat.net/beta)

Member

philsmd commented Jan 3, 2018

@branmcf yeah, thanks for the confirmation. That's also what I saw what most modern software for ethereum generates.... it seems that some time ago the encseed was much shorter, e.g. 128 hex chars (64 bytes)
It shouldn't matter too much because hashcat now supports all these lengths for the encseed decryption.
Again, you could just extract the "hash" from the json file with ethereum2john.py (and remove the file names and colons if any are present) and run it with -m 16300 with hashcat (betas are already up on https://hashcat.net/beta)

@anormore

This comment has been minimized.

Show comment
Hide comment
@anormore

anormore Jan 8, 2018

@philsmd Is there some sort of easy to understand guide I can follow? Trying to get this running... Noobish level cracker here...

anormore commented Jan 8, 2018

@philsmd Is there some sort of easy to understand guide I can follow? Trying to get this running... Noobish level cracker here...

@philsmd

This comment has been minimized.

Show comment
Hide comment
@philsmd

philsmd Jan 8, 2018

Member

@anormore
Hey,
I don't think this is the right place to discuss how to get hashcat working.
I would suggest that you go to https://hashcat.net/forum and https://hashcat.net/faq and https://hashcat.net/wiki/ to try to understand how you setup hashcat correctly.

It's not a good idea to start a discussion here on how to get hashcat working with hash mode -m 16300 to crack the presale ethereum wallets. This is a github issue (feature request) with the goal to implement this new algorithm in hashcat.

Anyways, to get you started:

  1. for now you need to use the beta from (https://hashcat.net/beta)
  2. you need to install your OpenCL drivers correctly (for OpenCL CPU or OpenCL GPUs)
  3. you need to extract the beta version with 7-Zip
  4. you need to download ethereum2john.py from https://raw.githubusercontent.com/magnumripper/JohnTheRipper/bleeding-jumbo/run/ethereum2john.py .
  5. you need to install python2.7 (and setup the PATH environment variable under windows to get python working within cmd)
  6. run this command: python ethereum2john.py my_wallet.json
  7. you need to copy the output of ethereum2john.py to a file (e.g. hash.txt), make sure there are no file names within the hash. The hash should look similar to the one that you can find here: https://hashcat.net/wiki/example_hashes (search for 16300)
  8. you need to run hashcat something like this: hashcat -m 16300 -a 0 -w 3 hash.txt dict.txt
Member

philsmd commented Jan 8, 2018

@anormore
Hey,
I don't think this is the right place to discuss how to get hashcat working.
I would suggest that you go to https://hashcat.net/forum and https://hashcat.net/faq and https://hashcat.net/wiki/ to try to understand how you setup hashcat correctly.

It's not a good idea to start a discussion here on how to get hashcat working with hash mode -m 16300 to crack the presale ethereum wallets. This is a github issue (feature request) with the goal to implement this new algorithm in hashcat.

Anyways, to get you started:

  1. for now you need to use the beta from (https://hashcat.net/beta)
  2. you need to install your OpenCL drivers correctly (for OpenCL CPU or OpenCL GPUs)
  3. you need to extract the beta version with 7-Zip
  4. you need to download ethereum2john.py from https://raw.githubusercontent.com/magnumripper/JohnTheRipper/bleeding-jumbo/run/ethereum2john.py .
  5. you need to install python2.7 (and setup the PATH environment variable under windows to get python working within cmd)
  6. run this command: python ethereum2john.py my_wallet.json
  7. you need to copy the output of ethereum2john.py to a file (e.g. hash.txt), make sure there are no file names within the hash. The hash should look similar to the one that you can find here: https://hashcat.net/wiki/example_hashes (search for 16300)
  8. you need to run hashcat something like this: hashcat -m 16300 -a 0 -w 3 hash.txt dict.txt
@anormore

This comment has been minimized.

Show comment
Hide comment
@anormore

anormore Jan 8, 2018

Perfect, thanks for the guide. I have it running now (no luck yet initially). You've provided a great resource for lost souls like myself.

HOWEVER! I'd like to know if the PreSale wallet website screwed up the input. Let's say I entered Password123!

A) My wallet is wrong because the Ethereum bug has incorrectly applied the input, making the entire .json wallet screwed anyway. The scenario being the input password script from their website was bugged entirely.

B) The wallet data is fine, it's just the Mist / Geth client that is bugged and not importing. This would mean that other tools (Kraken import tool,etc) work just fine. It would mean that Hashcat will find the password. The fact Hashcat hasn't found my password means I really screwed it up.

So I can accept B as fate -- but without knowing the CAUSE of this Ethereum bug, we can't rule out option A, which means 'corrupt' wallet.json

Thoughts?

anormore commented Jan 8, 2018

Perfect, thanks for the guide. I have it running now (no luck yet initially). You've provided a great resource for lost souls like myself.

HOWEVER! I'd like to know if the PreSale wallet website screwed up the input. Let's say I entered Password123!

A) My wallet is wrong because the Ethereum bug has incorrectly applied the input, making the entire .json wallet screwed anyway. The scenario being the input password script from their website was bugged entirely.

B) The wallet data is fine, it's just the Mist / Geth client that is bugged and not importing. This would mean that other tools (Kraken import tool,etc) work just fine. It would mean that Hashcat will find the password. The fact Hashcat hasn't found my password means I really screwed it up.

So I can accept B as fate -- but without knowing the CAUSE of this Ethereum bug, we can't rule out option A, which means 'corrupt' wallet.json

Thoughts?

@branmcf

This comment has been minimized.

Show comment
Hide comment
@branmcf

branmcf Jan 8, 2018

@anormore I'm in a similar boat and I definitely feel your pain. I have a document that's verifiably unchanged since the year of my ETH presale purchase (I, too, used the website) but Kraken nor MIst/geth has been able to decrypt my backup file and I haven't had any luck recovering the password with pyethrecover or hashcat.

I've seen rumblings about special characters (e.g. !) causing issues but I've also seen updates to posts, months later, where people who were certain of their password actually had it wrong so it's still unclear to me whether or not this is user or programmer error.

Anyways, I'm working on getting hashcat installed on an EC2 instance that could be used to scale my password cracking efforts, feel free to reach out if you want to use it!

branmcf commented Jan 8, 2018

@anormore I'm in a similar boat and I definitely feel your pain. I have a document that's verifiably unchanged since the year of my ETH presale purchase (I, too, used the website) but Kraken nor MIst/geth has been able to decrypt my backup file and I haven't had any luck recovering the password with pyethrecover or hashcat.

I've seen rumblings about special characters (e.g. !) causing issues but I've also seen updates to posts, months later, where people who were certain of their password actually had it wrong so it's still unclear to me whether or not this is user or programmer error.

Anyways, I'm working on getting hashcat installed on an EC2 instance that could be used to scale my password cracking efforts, feel free to reach out if you want to use it!

@anormore

This comment has been minimized.

Show comment
Hide comment
@anormore

anormore Jan 29, 2018

Howdy yall, I have un-covered the bug with Ethereum wallets and return characters here: ethereum/mist#3513

@Chick3nman Hey buddy, can you have a look at this? It seems absurd but it's repeatable 100%. Come on over and join the conversation if interested..

anormore commented Jan 29, 2018

Howdy yall, I have un-covered the bug with Ethereum wallets and return characters here: ethereum/mist#3513

@Chick3nman Hey buddy, can you have a look at this? It seems absurd but it's repeatable 100%. Come on over and join the conversation if interested..

@Chick3nman

This comment has been minimized.

Show comment
Hide comment
@Chick3nman

Chick3nman Jan 30, 2018

Contributor

Can you give me a quick summary of the issue? I'm trying to read through that thread but it's quite long. It sounds like return characters were incorrectly considered during the KDF portion instead of being stripped, which caused wallets that implement the KDF correctly to fail to decrypt due to the lack of the return characters? If so, it should be trivial to apply those characters using a rule or a hex wordlist with those characters applied to the ends of the plaintexts.

Contributor

Chick3nman commented Jan 30, 2018

Can you give me a quick summary of the issue? I'm trying to read through that thread but it's quite long. It sounds like return characters were incorrectly considered during the KDF portion instead of being stripped, which caused wallets that implement the KDF correctly to fail to decrypt due to the lack of the return characters? If so, it should be trivial to apply those characters using a rule or a hex wordlist with those characters applied to the ends of the plaintexts.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment