gpt4 book ai didi

security - 每个密码需要一次 "random salt"还是每个数据库只需要一次?

转载 作者:行者123 更新时间:2023-12-02 15:27:07 26 4
gpt4 key购买 nike

进一步my previous question about salted passwords in PHP/MySQL ,我还有一个关于盐的问题。

当有人说“使用随机盐”来预先/附加到密码时,这是否意味着:

  • 创建一个静态的 1 次随机生成的字符串
  • 创建一个字符串,该字符串每次都会随机变化密码已创建

如果每个用户的盐都是随机的,并与散列密码一起存储,那么如何检索原始盐以进行验证?

最佳答案

至少应为每个用户以及每次更改密码时随机生成一个新的盐。例如,不要仅仅依赖于站点范围的盐,因为这首先就违背了使用盐的意义。

为每个用户使用唯一的盐,这样如果两个用户具有相同的密码,他们将不会获得相同的结果哈希。这也意味着需要单独针对每个用户进行暴力攻击,而不是能够预先计算 rainbow table对于该网站。

然后,您将盐和密码的哈希结果存储在数据库中 hash(salt + password) ,以及 salt对于每个用户。您可以将它们存储在单独的列中,或全部存储在一列中(由散列中未使用的某些字符分隔,例如;)。只要你能把两个都找回来就没事了。

但是,如果您的数据库由于某人获得本地访问权限或通过 SQL 注入(inject)攻击而受到损害,那么盐和最终哈希都将可用,这意味着对用户密码的暴力攻击将是微不足道的。为了解决这个问题,按照The Rook的建议您还可以使用存储在本地文件中的站点范围 key 作为哈希方法的另一个输入,以便攻击者也需要知道这一点才能发动有效的攻击。这意味着您的数据库必须受到损害,并且攻击者需要访问本地文件。所以使用hash(hash(salt + secret) + password)

虽然在大多数算法中,您的目标是尽可能快,但对于密码散列,您希望减慢速度,这称为 Key Strengthening (或者有时是键拉伸(stretch))。如果您的哈希函数需要 0.00001 秒才能返回,那么有人可以尝试每秒暴力破解 100,000 个密码,直到找到匹配项。如果你的哈希函数需要 1 秒才能输出结果,那么对于登录你的应用程序的人来说这没什么大不了的,但对于破解密码来说这是一个更大的问题,因为现在每次尝试都需要 1 秒才能获得结果结果,这意味着测试每个暴力破解密码所需的时间是使用原始哈希函数的 100,000 倍。

要使哈希函数变慢,您只需运行它多次即可。例如,您可以这样做 new_hash = salt + password + previous_hash 10万次。如果迭代速度太快,您可能需要将迭代次数调整为更高的值。如果您希望以后能够更改该值,请确保将迭代次数与用户记录一起存储,这样就不会影响之前存储的任何密码。

您的用户记录现在应该有一个格式类似于“$<algorithm>$<iterations>$<salt>$<hash> ”的字段(如果需要,也可以作为单独的字段)。

当用户输入密码时,您可以从数据库检索盐和迭代次数,并从本地文件检索站点范围的 secret ,并验证当您使用盐和密码运行相同次数的迭代时,结果哈希与您存储的内容匹配。

如果用户更改了密码,那么您应该生成一个新的盐。

您使用的哈希方法并不重要(但哈希算法很重要*)。上面我建议hash(hash(salt + secret) + password)但同样可以是 hash(hash(salt) + hash(secret) + hash(password)) 。您使用的方法不会改变密码存储的有效性,一种方法并不比另一种方法更安全。依靠如何将密码和盐一起散列来提供安全性的设计称为 security through obscurity应避免。

*您不应使用 MD5 或 SHA-1,因为它们被认为是不安全的。请改用 SHA-2 系列(SHA256、SHA512 等)。 (Ref)

关于security - 每个密码需要一次 "random salt"还是每个数据库只需要一次?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/2999197/

26 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com