【问题标题】:Issue with PHP/MYSQLi Password validation using salt使用盐的 PHP/MYSQLi 密码验证问题
【发布时间】:2014-11-24 04:53:47
【问题描述】:

我在获取存储在 mysql 中的密码以匹配使用 salt 的登录密码时遇到问题。

这是我创建密码的代码:

        $hash = hash('sha256', $password);

        function createSalt()
        {
        $text = md5(uniqid(rand(), true));
            return substr($text, 0, 3);
        }

        $salt = createSalt();
        $password = hash('sha256', $salt . $hash);

这是我登录页面中的代码:

        $userData = $result->fetch_array(MYSQL_ASSOC);

        $hash = hash('sha256', $password);

        $password = hash('sha256', $userData['salt'] . $hash);

        //$hash = hash('sha256', $userData['salt'] . hash('sha256', $password) ); 

        if($password != $userData['Password']) // Incorrect password. So, redirect to login_form again.

在 mysql 中创建密码没有错误(该字段填充了即 0d02a88c1e1057a64df6b3fed4c6ad64e228313b803e9f9b36...

虽然登录创建类似:51839f9a15dac1f26825f4cd5d2ecf7ae83ea88d440415b04fb6ae41c3a0566f

只是不确定问题出在哪里。在此先感谢,我对 PHP 很陌生。

【问题讨论】:

  • 你不能对此草率。发布您的代码生成的“类似”的内容没有帮助。您的第一步应该是肉眼验证数据库中的散列密码是否与您的预期结果相匹配。然后验证流程中的每个步骤是否符合您的期望。
  • 您不是总是使用不同的盐来创建密码吗?这是一个问题。另一个你可能不会把salt信息放到$userData
  • @mike W 什么是邋遢?显然,我给出的示例是我的 mysql 数据库中的 EXACT 以及登录页面正在创建的示例。但是,如果我说这些是我的结果,您可能会说“嗯,每个用户都不能得到相同的结果”之类的屈尊俯就的话,而且我已经根据我对 PHP 的理解尽可能多地追踪了它。感谢您非常无用的 cmets。
  • @Gabor Bakos - 我认为 $text = md5(uniqid(rand(), true));返回 substr($text, 0, 3);正在为每个人创建一个唯一的盐,并且 $userData['Password'] 正在使用在创建页面中创建的盐来进行匹配?
  • @86Tango 请再次阅读您自己的 cmets:虽然登录创建 类似的内容:您的另一个示例以省略号为后缀。由于您现在说这些是确切,因此省略号可能存在​​于您自己的代码中。我认为'slapdash'很好地涵盖了它。

标签: php hash mysqli salt


【解决方案1】:

首先,您在这里有一些令人困惑的变量命名 - 您使用 $password 来表示明文密码和盐和哈希表示。这使您的代码更难阅读。

其次,让我们将您的代码视为一系列状态,以找出它们可能出错的地方:

  1. 密码输入。在这两种情况下是否传递了相同的字符串?你有注意空格和大写吗?使用调试器进行验证。如果明文密码不是逐字节相同,则初始 sha256 哈希此时应显示差异。
  2. 盐生成/检索。您是否逐字节保存/检索完全相同的盐?同样,请注意空格/大写,并检查您的数据库是否没有静默截断或更改字符串的编码。
  3. 在字符串连接之后但在第二个 sha256 哈希操作之前比较字符串。根据定义,由于最终输出不同,因此您的明文密码或盐不是逐字节相同的。这将帮助您判断一个或两个是罪魁祸首。

【讨论】:

  • 谢谢。我现在会看这些东西并做出回应。谢谢
【解决方案2】:

使用password_hash()功能让您的生活更轻松,密码存储更安全。

SHA-* 算法不适合散列密码,因为它们的速度太快了。函数 password_hash() 不仅会计算出更适合的 BCrypt 哈希值,它还会负责生成安全盐,并且您不必在单独的数据库字段中存储/检索盐(它将成为一部分产生的哈希值)。

// Hash a new password for storing in the database.
// The function automatically generates a cryptographically safe salt.
$hashToStoreInDb = password_hash($password, PASSWORD_BCRYPT);

// Check if the hash of the entered login password, matches the stored hash.
// The salt and the cost factor will be extracted from $existingHashFromDb.
$isPasswordCorrect = password_verify($password, $existingHashFromDb);

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2017-06-22
    • 1970-01-01
    • 2020-12-26
    • 1970-01-01
    • 2011-05-08
    • 1970-01-01
    • 2021-07-30
    相关资源
    最近更新 更多