用户密码盐的最佳长度是多少? [关闭]

Posted

技术标签:

【中文标题】用户密码盐的最佳长度是多少? [关闭]【英文标题】:What is the optimal length for user password salt? [closed] 【发布时间】:2010-09-16 02:16:19 【问题描述】:

任何salt 在对用户密码进行加盐和散列处理时显然都会有所帮助。盐应该放多长时间有什么最佳做法吗?我会将盐存储在我的用户表中,因此我希望在存储大小和安全性之间进行最佳权衡。随机的 10 个字符的盐是否足够?还是我需要更长的时间?

【问题讨论】:

我没有关于盐长度的建议,但是这里显示的答案有很多不好的信息。你的盐绝对应该: - 是随机的 - 是每个秘密(不是存储在程序映像或配置文件中的单个值)。盐不是密码秘密,因此将其存储在您的表中是没有问题的。 salt 的唯一目的是确保当对同一项目的不同实例进行散列(或加密)时,您会得到不同的结果。 对于那些不知道什么是盐的人:***上的en.wikipedia.org/wiki/Salt_(cryptography)">Salt(密码学) 或者是否存在盐长度与哈希输出长度的最佳比率? 8 字节盐对于 HMAC-SHA-256 可能就足够了,但对于 HMAC-SHA-512 可能不够。 加密随机盐与散列函数的输出大小相同意味着“尝试所有可能的盐”(加上密码字典)攻击需要与“尝试所有可能的散列结果”一样多的努力攻击 - 这是标准的蛮力。较短的盐意味着您可以将盐字典和密码字典作为暴力攻击。 -1 诚然没有(甚至试图)回答这个问题。 【参考方案1】:

目前accepted standards 用于散列密码为每个密码创建一个新的 16 字符长的盐,并将盐与密码散列一起存储。

当然应该采取适当的加密措施来创建真正随机的盐。

【讨论】:

Character 的定义有点不明确。你应该说 byte. @CodesInChaos 我相信你的意思是octet ;-) 嗨!似乎***的文章发生了变化-也许您应该参考en.wikipedia.org/wiki/PBKDF2或其他什么? 或者更好owasp.org/index.php/Password_Storage_Cheat_Sheet【参考方案2】:

编辑:我下面的答案回答了所问的问题,但“真正的”答案是:只需使用 bcrypt、scrypt 或 Argon2。如果您提出这样的问题,几乎可以肯定您使用的工具级别太低了。

老实说,没有正当理由不让盐的长度与散列密码的长度完全相同。如果您使用的是 SHA-256,那么您有一个 256 位哈希。没有理由不使用 256 位盐。

从数学上讲,超过 256 位不会为您带来任何安全性改进。但是使用较短的盐可能最终会出现彩虹表赶上您的盐长度的情况——尤其是使用较短的盐。

【讨论】:

这不是什么大事;用户几乎不会注意到毫秒散列和半秒散列之间的区别,加上密码散列实际上应该需要更长的时间来减缓暴力攻击——尽管典型的三击锁定 15 分钟更好.您是否“浪费”了 CPU 周期来执行此操作?好吧,无所谓了。无论如何,在大多数网站上,CPU 的空闲时间都比没有空闲的时间多,那有什么关系呢?如果您遇到性能问题,请横向扩展。 盐可以抵御彩虹桌。带有 256 位哈希的 512 位盐仍然只会在最终密码中产生 256 位熵。 Slow hashing 是一个功能,而不是一个错误。 如果你有一个 3 位散列,你的 9999 位盐仍然只会散列到 3 个可能的熵位。彩虹表只需要为每个密码找到三个盐,这会导致不同的输出,这是一个常数乘法因子,因此会从大 O 中丢弃。 ................................................. ................................... 特定系统。 The purpose of salts is to stop precomputation attacks so that hashes cannot be searched for and immediately reversed into plaintext 。使用 9999 位的 salt,您的密码仍然是一个秘密,而使用 3 位的 salt,您的密码现在为全世界所知(他们可以使用它来登录您的其他帐户,因为许多人经常重复使用密码)。我觉得有趣的是,这里有 5 个人实际上赞成你的评论,因为里面有“熵”这个词。【参考方案3】:

这些答案中的大多数都有些误导,并表明盐和加密密钥之间存在混淆。包含盐的目的是修改用于散列每个用户密码的函数,以便必须单独攻击每个存储的密码散列。唯一的安全要求是它们对每个用户都是唯一的,它们不可预测或难以猜测没有任何好处。

盐只需要足够长,以便每个用户的盐都是唯一的。即使有 10 亿注册用户,随机 64 位盐也不太可能重复,所以这应该没问题。单独重复的盐是一个相对较小的安全问题,它允许攻击者一次搜索两个帐户,但总的来说不会加快整个数据库的搜索速度。即使是 32 位的 salt 对于大多数用途来说也是可以接受的,在最坏的情况下,它会使攻击者的搜索速度提高约 58%。将盐增加到 64 位以上的成本并不高,但没有安全理由这样做。

在每个用户的 salt 之上使用站点范围的 salt 也有一些好处,这将防止与存储在其他站点的密码哈希可能发生冲突,并防止使用通用彩虹表,尽管即使32 位盐就足以让彩虹表成为不切实际的攻击。

即使更简单(开发人员总是忽略这一点),如果您有唯一的用户 ID 或登录名,它们也可以作为盐使用。如果你这样做,你应该添加一个站点范围的盐,以确保你不会与另一个系统的用户重叠,他们有同样的好主意。

【讨论】:

盐的不可预测性有一个好处。可预测的盐可以被预测并用于哈希表攻击。例如,如果您的 salt 只是用户 ID,那么足够长的纯 alpha 哈希表将不仅包括所有密码,还包括所有用户名 + 密码组合。 请注意关于你的最后一段,如果你使用站点范围的盐,那应该就是:站点范围。不是应用程序范围的,即您为应用程序安装的每个新实例都应该生成一个新的站点范围的盐。例如,如果 Windows 在每个 Windows 身份验证数据库上使用相同的 salt,那么为该 salt 创建一个彩虹表是值得的,但如果每次安装 Windows 都生成一个新的 salt,那么它就不会。 问题不在于盐需要难以猜测。攻击者不需要猜测盐:任何有权访问散列的人都已经拥有盐。问题是,如果您的盐非常常见(如用户名),它们可能与其他站点的盐相同,此时攻击者需要一组更小的彩虹表才能使攻击可行。这就是为什么提到 per-site salt 的想法,以避免与其他站点发生这种冲突。 快速说明:如果使用用户名作为盐,如果用户名发生变化,这可能会成为问题。实际上,(尽管客户的设计文档中说了些什么)我发现用户经常想要更改用户名。 @NateC-K,您所说的按站点加盐的想法称为胡椒。【参考方案4】:

Wikipedia:

SHA2-crypt 和 bcrypt 方法——用于 Linux、BSD Unix 和 Solaris — 有 128 位的盐。这些较大的盐值使 几乎任何长度的密码都不可行的预计算攻击 在可预见的未来对抗这些系统。

128 位(16 字节)盐就足够了。您可以将其表示为128 / 4 = 32 十六进制数字的序列。

【讨论】:

在我看来,其他安全系统使用的示例是最佳实践的一个很好的示例。 @mklement0 谢谢,我已经更新了答案。【参考方案5】:

一个答案可能是使用您将要使用的哈希值在安全性方面提供的值作为盐的大小。

例如如果您要使用 SHA-512,请使用 256 位 salt,因为 SHA-512 提供的安全性是 256 位。

【讨论】:

以上是关于用户密码盐的最佳长度是多少? [关闭]的主要内容,如果未能解决你的问题,请参考以下文章

如何在 Python 中使用 scrypt 生成密码和盐的哈希值

创建链接以重置密码的最佳做法是啥? [关闭]

C# 保持哈希盐的安全,即使是来自开发人员

airos默认密码

为哈希隐藏盐的必要性

关于如何使用正确的密码加密方式