PHP尾随美元符号-仅从散列中提取盐部分-填充盐


php trailing dollar sign - extract only the salt part from hash - padding the salt

我正在阅读PHP的crypt()函数。我有几个问题-

  1. 我在大多数例子中看到的salt字符串末尾的'$'符号的意义是什么?手册中没有特别提到如何用它来结束盐串。

  2. 无论如何,我只能从哈希中提取盐部分吗?我知道我可能不需要这样做,因为crypt()函数在进行比较时将在内部执行此操作。但只是为了好玩。只是为了让我看看盐。对于蛋,考虑以下代码-

    $pass = 'secret'; $salt = '$2y$07$usesomesillystringforsalt$'; echo crypt($pass, $salt);

    它的输出是$2y$07$usesomesillystringforex.u2VJUMLRWaJNuw0Hu2FvCEimdeYVO,我不确定盐和哈希之间的边界。'e'在'forex'子字符串的盐或哈希的一部分?如果我能把它的盐部分提取出来,那就容易多了。

  3. crypt()手册也说

    …河豚哈希与盐如下:"$2a$","$2x$"或"$2y$",一个两位数的成本参数,"$"和22个字符的字母表"。/0-9A-Za-z"....

    根据这个,我期望在cost参数后面的$符号后面有22个字符。但是考虑这段代码-

    $pass = 'secret'; $salt = '$2y$07$somesillystring$'; echo crypt($pass, $salt);

    它的输出是$2y$07$somesillystring$$$$$$.O6JLPmGlDvy4BicGmkuBD.DN8OYiIoG。我的问题是,为什么在cost参数后面的$符号后面最多只能填充21个字符。我原以为最多可以加到22个字符。

  1. 一些crypt()算法用美元符号将盐与crypt分开。河豚没有。

  2. PHP没有提供直接提取盐的工具。你需要一个算法和盐的位置/长度的关联数组。

  3. 我不知道为什么21 vs 22字符的差异。这是PHP手册中的错误吗?

  4. 尝试运行"man crypt"或访问http://linux.die.net/man/3/crypt。

我依稀记得在某个地方读到过,只使用了第22个字符的剩余4位/一小块。但是在运行了下面的代码片段之后,我看不到哈希前后第22个字符的二进制表示之间的关系。但是第22个字符确实对结果有影响。

$pass = 'secret';
$salt = '$2y$07$usesomesillystringforsalt$';
$hash = crypt($pass, $salt);
var_dump(
    $hash,
    str_split($hash) // the 22th salt character 'e' is on index 28
);
function meow($char) {
    $hash = crypt('secret', '$2y$04$usesomesillystringfor' . $char);
    $substr = substr($hash, 28, 1);
    var_dump(
        $hash,
        $char,
        decbin(ord($char)),
        $substr,
        decbin(ord($substr)),
        '------------------------------'
    );
}
$alphabet = str_split('abcdefghijklmnopqrstuvwxyz');
foreach($alphabet as $char) {
    meow($char);
}

参见:http://3v4l.org/qQmho