终极密码盐

时间:2013-01-25 06:01:10

标签: php passwords salt

最近,我一直在研究如何保护密码。我相信我理解它的基础知识。因此我试图编写自己的函数来保护php中的密码。

但是,当涉及到密码时,我有点困惑。我们创建一个随机的唯一salt并将其附加到密码然后散列它,最后将未散列的salt和散列密码/ salt组合存储在数据库中。如果他获得对数据库和我们的哈希密码的访问权限,这会增加黑客的搜索空间。

所以这看起来像是完全过度的安全性,但无论如何,无论如何,我总是将盐附加到密码的正面或背面。那么看一下SINGLE用户的密码这个独特的盐不会影响搜索空间吗?虽然每个用户都有一个独特的盐,但每个用户的整体搜索空间都会大大增加。

创建一个将盐插入密码中可预测的半随机位置(例如用户名/ 2的长度)的算法会不会更安全?例如,这是我提出的保护功能的步骤:

Create a random salt
take username length %(mod) password length
insert the salt at the spot determined
hash

示例运行:

random salt = 12345
len("imauserwithalongname") % len("mypass") = 2
valueToHash = my12345pass

现在我们的破解者不知道在没有看到我们的php / source的情况下把盐放在哪里,如果我错了就更正(如果我错了,请纠正我)比数据库更难获得访问权。

我也知道安全性应该取决于密钥的安全性而不是算法的保密性,但是我认为基于它添加层是没有错的,只要整个系统不依赖于算法的保密性。

编辑:这样做会大大增加黑客的搜索空间吗?

如果我们将盐放在一个依赖于密码长度的地方,那会不会破坏使用字典攻击的目的,即使是基于每个用户呢?

4 个答案:

答案 0 :(得分:3)

将盐插入不同的位置不会增加搜索空间。如果您为每个用户使用随机盐,则黑客无论如何都不知道每个用户的每种盐。关于它在未散列的弦中的位置的知识并不重要。

使用bcryptPBKDF2。两种算法都强制执行salt和循环次数。如果您足够耐心,PHP 5.5将允许您password_hash($password)

答案 1 :(得分:0)

个人认为你过度了。对哈希进行加盐的最有效方法是在系统上的只读文件中存储一个动态的,特定于记录的AND和一个静态的方法。这是一种非常有效但安全的盐渍化方式。

答案 2 :(得分:0)

我认为你误解了盐的目的。盐不会增加攻击者的搜索空间,毕竟它是使用哈希值存储的明文。盐的目的是,攻击者无法构建一个单一的rainbowtable,然后检索所有存储的密码。

如果你要为每个密码添加相同的盐,那么攻击者不能简单地使用互联网上现有的预先计算的彩虹表,他必须为这个盐建立一个新的彩虹表(现有的彩虹表将包含密码如“马”,但不是密码,如horse8ze * w398dhek3 + qmxno0)。不幸的是,这个单一的彩虹表可用于获取所有密码。

因此我们为每个密码使用一个唯一的盐。攻击者现在必须为每个密码构建一个单独的彩虹表,但为什么他应该继续构建表,当他已经找到匹配项(?)时,他不能在以后重用该表用于其他密码。换句话说,蛮力比建造彩虹表更快,所以我们使彩虹表无用。

因此,对于每个密码,salt应该唯一,如果可能,它应该不可预测。使用确定性计算机难以实现这些标准,您可以做的最好的事情是使用操作系统的随机源来构建盐。像BCrypt和PBKDF2这样的密码的良好哈希算法重复散列变慢,并在每次迭代中组合密码和原始盐。它不仅仅是密码+盐的串联。

关于将盐放在某处秘密的想法确实增加了一个秘密(盐在哪里?),只要攻击者不知道你的代码就行。获取数据库(SQL注入)确实比访问代码更容易,但使用 pepper 可以更轻松地实现相同的目标。

我试图在tutorial中总结一下,也许你想看看它。

答案 3 :(得分:0)

  

因此我试图编写自己的函数来保护密码   在php。

哇哇哇,把它抱在那里。

有一种说法从密码学家传给了我们凡人,多年来一直如此。俗话说得好:

  

不要发明自己的加密。

大声说出来然后再说一遍。

我知道你只是想保护你的密码,但我必须把它弄清楚。有许多经过试验和测试的方法可以实现您想要实现的目标。

我感谢你做了一些研究,但互联网上充满了可怕的糟糕信息,所以我要指出一些有用的文章。

一个不错的短名单。

以下是一些可以帮助您的关键字。

  • Bcrypt
  • Scrypt (当PHP支持时,有人请取消此功能)

再一次非常简短的清单。

解决您的具体问题。盐不需要保密,因为你说它们旨在阻止攻击者预先计算有效密码/哈希组合的表。但是,如果使用弱散列算法,它们会很快失去它们的值。

通过默默无闻的安全并不像看起来那么大。如果黑客获得对您的数据库的访问权限,那么他们也可以访问您的文件系统的可能性非常高。如果他们获得了对您的源的访问权限,那么存储密码的自定义方法就没有用了。

总之,自定义算法+弱哈希=不安全。

相反,您希望使用久经考验的密钥派生函数/密钥强化算法。

这些旨在使计算机很难生成哈希值,并且使攻击者很难暴力破解密码。

Bcrypt将盐存储在密码旁边,并且被证明非常安全。事实上,安全性足以确保它是安全专家对密码进行哈希处理的推荐方法。

在PHP 5.5中,基于Bcrypt引入了一个简单的密码哈希API,对于5.5以下的版本,有一个密码哈希兼容库可以完全相同。

这对你来说应该足够了。