php - 在 PHP 中根据 SSHA256 哈希验证密码

标签 php validation passwords salt

为了使用 Dovecot 进行身份验证,我使用 SSHA256 哈希值,但我不知道如何根据现有哈希值验证给定密码。以下 PHP 函数(在网络中找到)用于创建 SSHA256 哈希:

function ssha256($pw) {
        $salt = make_salt();
        return "{SSHA256}" . base64_encode( hash('sha256', $pw . $salt, true ) . $salt );
}

function make_salt() {
        $len   = 4;
        $bytes = array();
        for ($i = 0; $i < $len; $i++ ) {
                $bytes[] = rand(1,255);
        }
        $salt_str = '';
        foreach ($bytes as $b) {
                $salt_str .= pack('C', $b);
        }
        return $salt_str;
}

示例输出:{SSHA256}lGq49JTKmBC49AUrk7wLyQVmeZ7cGl/V13A9QbY4RVKchckL

我必须提取盐吗,但是如何提取呢? 我完全迷失了解决问题的方法,有人对此有提示吗?

感谢大家的帮助!

哦,抱歉,我必须使用 SSHA256,因为 Dovecot 1.2.15 仅支持这些方案: CRYPT MD5 MD5-CRYPT SHA SHA1 SHA256 SMD5 SSHA SSHA256 纯明文 CRAM-MD5 HMAC-MD5 DIGEST-MD5 PLAIN-MD4 PLAIN-MD5 LDAP-MD5 LANMAN NTLM OTP SKEY RPA

最佳答案

您不应使用 SHA 系列进行密码哈希处理。它们速度快,专为快速散列文件而设计。您需要密码哈希昂贵。使用 bcrypt、PHPass 或直接使用这个类,这是我自己推出的(但直到你学会找出其中的漏洞):

class PassHash {
    public static function rand_str($length) {
        $total = $length % 2;
        $output = "";
        if ($total !== 0) {
            $count = floor($length / 2);
            $output .= ".";
        } else $count = $length / 2;

        $bytes = openssl_random_pseudo_bytes($count);
        $output .= bin2hex($bytes);

        // warning: prepending with a dot if the length is odd.
        // this can be very dangerous. no clue why you'd want your
        // bcrypt salt to do this, but /shrug

        return $output;
    }
    // 2y is an exploit fix, and an improvement over 2a. Only available in 5.4.0+
    public static function hash($input) {
        return crypt($input, "$2y$13$" . self::rand_str(22));

    }

    // legacy support, add exception handling and fall back to <= 5.3.0
    public static function hash_weak($input) {
        return crypt($input, "$2a$13$" . self::rand_str(22));
    }

    public static function compare($input, $hash) {
        return (crypt($input, $hash) === $hash);
    }
}

您必须对给定的明文进行哈希处理,并将该哈希值与您存储的哈希值进行比较。盐存储在哈希中,并且应该是随机的。如果你喜欢,可以加点胡椒粉。您还应该设置工作率变量,以便您可以在需要时随时更改工作率,并且系统仍然可以工作。


如果,就像你说的,你无法实现这一点,你可以按如下方式解压哈希:

function unpack_hash($hash) {
        $hash = base64_decode($hash);
        $split = str_split($hash, 64);
        return array("salt" => $split[1], "hash" => $split[0]);

这是因为 SHA256 是 256 位,即 64 个十六进制字符。您可以始终假设前 64 个字符是哈希

关于php - 在 PHP 中根据 SSHA256 哈希验证密码,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/14922302/

相关文章:

php - 如何使用 Build Ubuntu 运行 HipHop/HHVM

.net - Silverlight - INotifyDataErrorInfo 和复杂的属性绑定(bind)

javascript - 如何在文本框中的客户端验证 youtube url

PHP 检查是否有任何数组值不是字符串或数字?

php - 防止脚本在开源PHP项目中窃取密码?

php - 通过数据库修改用户密码

javascript - 在另一个页面上显示搜索数据 <div>

php - PHP中有没有办法让函数出错

php - MySQL 哈希函数实现

php - 使用 php javascript 时出现错误未终止的字符串文字?