PasswordHash.java没有生成匹配的PBKDF2-HMAC-SHA1哈希

时间:2014-08-07 23:02:55

标签: java python hash cryptography pbkdf2

我正在编写一个需要使用现有Java Play框架应用程序的Django应用程序。 Play应用使用PasswordHash.java来存储密码。它以冒号分隔格式存储密码。每个哈希都存储为iterationssaltpbkdf2_hash

例如,这是密码“test”的条目: 1000:f7fe4d511bcd33321747a778dd21097f4c0ff98f1e0eba39:b69139f51bc4098afc36b4ff804291b0bc697f87be9c1ced

在这里,我们可以将字符串拆分为:并找到:

迭代:1000

盐:f7fe4d511bcd33321747a778dd21097f4c0ff98f1e0eba39

PBKDF2哈希:b69139f51bc4098afc36b4ff804291b0bc697f87be9c1ced

我修改了Django的check_password机制以兼容此格式,但发现它认为密码不正确。我使用Django的crypto.py来使用Play使用的相同的盐重新生成“test”的哈希值,并提出了这个:

hash = crypto.pbkdf2('test', 'f7fe4d511bcd33321747a778dd21097f4c0ff98f1e0eba39', 1000, 24)
base64.b16encode(hash)
'9A8725BA1025803028ED5B92748DD61DFC2625CC39E45B91'

播放中的PBKDF2哈希与此哈希不匹配。 (对于那些想知道的人,我使用24作为第四个参数,因为这是在PasswordHash.java中使用的。)

在我无法使Django生成的哈希匹配Java之后,我在website that does it for you.上尝试了

我插入相同的盐,使用SHA-1进行1000次迭代和24位密钥大小,发现网站与Django创建的匹配!

我不确定PasswordHash.java会发生什么,但我迫切需要让Django和Play“玩得很开心”(不能自己哈哈)。有没有人知道这里发生了什么?

1 个答案:

答案 0 :(得分:3)

尝试salt = base64.b16decode(salt.upper())

我做了,我在你的初始例子中得到了哈希值,尽管是大写B69139F5...

说明:

哈希和salt都存储在初始示例中的Base16(hex)中。因此,您解码salt以使用它,然后对生成的哈希进行编码,以将其与存储的哈希值进行比较。

upper()是因为python的b16decode对大写Base16严格。如果你给它小写的话就会出错。