你如何在MySQL中安全地存储用户的密码和盐?

时间:2011-09-01 12:48:51

标签: mysql passwords sha1

所以,我发现你应该将密码与“盐”一起散列。 (可以找到文章herehere。)

以下是代码:

$password = 'fish';

/* should be "unique" for every user? */
$salt= 'ABC09';

$site_key = 'static_site_key';

hash_hmac('sha1', $password . $salt, $site_key);

现在我需要在MySQL中保存$password$salt,如下所示:

+---------+--------+----------+-------+
| user_id |  name  | password |  salt |
+---------+--------+----------+-------+
|    1    | krysis |  fish**  | ABC09 |
+---------+--------+----------+-------+

** fish当然会被散列,而不是以纯文本形式存储。

我只是想知道这样做是否真的有意义,因为这样一个黑客或谁也知道盐?所以,如果他们破解密码并看到密码fishABC09,他们会自动知道密码是fish?或者他可能“永远”无法破解密码,因为他不知道secret_key,因为它没有存储在数据库中?

如果我没有任何意义,我很抱歉。我只是总是使用sha1来获取密码,今天我发现这些文章谈到了添加salt

8 个答案:

答案 0 :(得分:8)

有关于正确存储密码的好文章。其中一个例如:Storing Passwords - done right!

您应该为每个用户使用不同的盐,但不需要单独存储盐。请参阅another thread

中的类似讨论

顺便说一句,你可能不应该使用sha1,例如sha256或sha512更强的东西(至少避免不良宣传)。对此有一个很好的答案:How insecure is a salted SHA1 compared to a salted SHA512

答案 1 :(得分:6)

$username = mysql_real_escape_string($username);
$password = mysql_real_escape_string($password);
$time = time();
$query = "
INSERT INTO user (name, unixcreationtime, passhash) 
VALUES ('$username', '$time', SHA2(CONCAT('$time','$password'),512) ";

不要使用SHA1,它不再安全 我建议在MySQL中进行所有哈希,这样你就可以确定哈希的结果没有区别。

使用以下选择用户:

$query = "SELECT id FROM user 
          WHERE name = '$username' 
            AND passhash = SHA2(CONCAT(creationdate,'$password'),512) ";

答案 2 :(得分:6)

答案 3 :(得分:4)

不,因为当密码被哈希时它看起来不像fishABC09,它看起来像:5f4dcc3b5aa765d61d8327deb882cf99这是一个md5哈希。

要获得对系统的访问权限,即使他们知道哈希值,也无法撤消。我们使用salt来增加哈希的复杂性,并防止彩虹表中的哈希查找。

例如:对“密码”的md5哈希执行Google search5f4dcc3b5aa765d61d8327deb882cf99

很多结果对吗?

现在我要再次创建一个哈希,我仍然会使用“密码”,但我会添加一个SALT,即“AHG(* @”。我猜这个帖子的唯一响应是一些读过这篇文章的机器人刮刀:)

cbe57e92ffbb0086320891b9f979156d

应该只是few results,或者是这篇文章的帖子。

请记住

请记住这个......哈希单向,所以即使你获得哈希,你也不知道用它来创建哈希

答案 4 :(得分:1)

我知道这已经过时了,但对于那些设法偶然发现这个帖子的人来说......

你真正想做什么HMAC。试图自己创造问题。例如,您可以部分计算哈希值,从而减少猜测密码所需的工作量。 HMAC解决了这些问题。

更好的是scrypt或bcrypt。 HMAC仍然经常使用设计为快速且易于计算的哈希算法;甚至有许多哈希算法的硬件实现。 bcrypt计算量很大,scrypt是内存密集型的。两者都使攻击者更难,但特别是scrypt使得构建硬件设备以破解密码变得非常困难。

我非常喜欢这里的图表:https://github.com/pbhogan/scrypt#why-you-should-use-scrypt

答案 5 :(得分:1)

这是一个古老的话题,但其他人也会来到这里,所以我会试着很容易地描述它:

如果你做哈希(密码),你会得到每个密码相同的哈希值[哈希(密码)=哈希(密码)]。如果两个用户拥有相同的密码,您将看到它,因为哈希值是相同的。一些密码,如"密码"或" 12345678"经常这样:数据库中的哈希值相同 - >也许密码"密码"或" 12345678" (彩虹式攻击)。

如果你哈希(盐+密码)你没有获得相同密码的相同哈希,因为哈希(salt1 +密码)不是哈希(salt2 +密码)。

hash(x)只是一个像f(x)= y的数学函数。如果你把相同的x,你会得到相同的y。这个功能必须是特殊的"为了安全起见。只是不要使用sha1因为它不再安全:D

答案 6 :(得分:0)

盐是固定长度的随机数。对于每个存储的条目,此盐必须不同。它必须以散列密码旁边的明文形式存储。

https://www.owasp.org/index.php/Hashing_Java#Why_add_salt_.3F

答案 7 :(得分:0)

如果黑客可以访问您的PHP文件,他只需添加邮件功能,无论谁登录,帐户详细信息都会通过电子邮件发送给黑客。

如果黑客只能访问数据库,他不应该在那里明确地写入密码,因此在保存之前将其加密。将其保存在无法反转的md5哈希中。

我通常使用基于username或userID的salt,PHP程序知道如何为每个用户生成static_site_key。