4

假设我们不使用password_hash并使用crypt()withsha512来散列密码。我们需要在密码中添加盐,所以攻击者无法使用彩虹表攻击。为什么盐必须是好的并且非常随机,如许多 SO 答案中所述?即使盐的差异很小或不是很随机,它仍然会给出与其他完全不同的哈希值。因此,攻击者不知道谁使用了相同的密码,他仍然无法只创建一个彩虹表。

4

2 回答 2

2

盐应该是唯一的,必须足够长,并且应该是不可预测的。随机性不是必需的,但它是计算机满足这些要求的最简单方法。保密并不是盐的目的,盐即使在已知的情况下也能实现其目的。

唯一性意味着它不仅在您的数据库中应该是唯一的(否则您可以使用用户 ID),它应该在全球范围内是唯一的。有人可以为盐创建彩虹表,例如 1-1000,并且能够检索具有这些用户 ID 的所有帐户的密码(通常管理员帐户的用户 ID 较低)。

足够长:如果盐太短(可能的组合太少),构建彩虹表再次变得有利可图。然后盐和密码一起可以被视为一个更长的密码,如果你可以为这个更长的密码构建一个彩虹表,你也会得到更短的原始密码。对于非常强且长的密码,实际上根本不需要加盐,但是大多数人为生成的密码都可以被暴力破解,因为它们很短(人们必须记住它们)。

使用从其他参数派生的盐也可以属于这一类。只是因为您从用户 ID 计算哈希,这不会增加可能的组合。

不可预测性稍微不那么重要,但再次想象一下,如果您将用户 ID 用作盐,攻击者可以找出接下来的几个用户 ID 将是什么,因此可以预先计算出少量的彩虹表。根据使用的哈希算法,这可能适用或不适用。然后他有时间优势,可以马上找回密码。如果管理员帐户使用可预测的盐,那么问题就更大了。

因此,使用从操作系统随机源(dev/urandom)生成的真正随机数是您能做的最好的事情。即使您忽略了上述所有原因,当有更好的方法时,为什么要使用衍生盐,为什么不使用您知道的最佳方法?

于 2013-10-02T12:59:50.593 回答
2

计算和存储强盐只需要很少的努力,但减少了彩虹表被预先计算的盐分天文数字很小的机会。

如果盐是一个 3 位数字,攻击者可以为所有可能的盐组合预先计算彩虹表是可行的。如果盐是一个随机的 24 个字符的字母数字字符串,那么攻击者可以为所有可能的盐预先计算的机会几乎为零。

于 2013-10-02T12:54:10.207 回答