PHP password_hash函数盐长21或22?

时间:2014-10-10 08:41:23

标签: php salt bcrypt password-hash php-password-hash

代码:

echo password_hash("stackoverflow", PASSWORD_DEFAULT, ['salt' => 'twenty-one-characters'] );

结果:

Warning: password_hash(): Provided salt is too short: 21 expecting 22 

代码:

echo password_hash("stackoverflow", PASSWORD_DEFAULT, ['salt' => 'twenty-one-charactersA'] );

结果:

$2y$10$dHdlbnR5LW9uZS1jaGFyYOVyX13hK9eb4/KXMAkHsAJX..YR7t/32

代码:

echo password_hash("stackoverflow", PASSWORD_DEFAULT, ['salt' => 'twenty-one-charactersB'] );

$2y$10$dHdlbnR5LW9uZS1jaGFyYOVyX13hK9eb4/KXMAkHsAJX..YR7t/32

问题:

如您所见,通过将A和B附加到21个字符串,我们创建了两个不同的22个字符的盐,但是,HASHES是相同的!那是第22个字符被忽略了吗?如果被忽略那么为什么要求22个字符盐?

2 个答案:

答案 0 :(得分:2)

BCrypt期望给定字母的盐:./0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz。你可以看到' - '不在其中,这就是你的盐无效的原因。一个有效的盐,你可以在哈希值中看到明文。

在大多数情况下,最好省略salt参数。如果没有此参数,该函数将从操作系统的随机源生成加密安全的盐。

password_hash("stackoverflow", PASSWORD_DEFAULT);

尽管如此,当你说BCrypt没有使用完整的22个字符时你是对的。似乎BCrypt只使用126位盐,而不是使用22位base64编码字符获得的128位。有关详细信息,请查看此讨论Why does crypt/blowfish generate the same hash...

答案 1 :(得分:0)

首先,不提供自己的盐。你不会比图书馆做得更好。使用静态盐(就像您在示例中所做的那样)危害安全性。只是让它产生自己的盐(顺便说一句,我认为让盐进入是我在该API中犯的最大错误)。

对于21个字符和22个字符,请给this answer一个读数。

基本上,salt是base64编码的。这意味着盐的每6位被编码为8位。所以编码盐的每个字节都是6位。

21个字符是126位。这意味着只使用了第22个字符的一部分(前2个解码位)。您与AB获得相同哈希的原因是两个字符的前2位相同。

实际上,第22个字节只有4个唯一的哈希值。