为了散列而隐藏盐的必要性

在工作中,我们有两个相互竞争的盐理论。 我所使用的产品使用类似于用户名或电话号码的forms来encryption散列。 本质上,每个用户都有所不同,但是我们随时可用。 另一个产品为每个用户随机生成一个盐,每当用户更改密码时都会更改。 盐在数据库中被encryption。

我的问题是如果第二种方法真的有必要? 我从纯粹的理论angular度可以理解,它比第一种方法更安全,但从实践的angular度来看呢。 现在要validation用户,salt必须是未encryption的并应用于login信息。

思考一下之后,我从这个方法看不到真正的安全收益。 即使攻击者知道如何快速确定每个帐户的内容,但是将帐户之间的差异更改为帐户,仍然使得有人尝试强制哈希algorithm变得极其困难。 这是假设密码足够强。 (很明显,find一组密码的正确哈希,它们都是两位数字比find8位密码的正确哈希要容易得多。 我在逻辑上是不正确的,还是有我失踪的东西?

编辑:好吧,这就是为什么我认为这是真的没有什么encryption盐。 (让我知道我是否在正确的轨道上)。

对于下面的解释,我们假定密码总是8个字符,salt是5,所有的密码都是由小写字母组成(这只是使math更容易)。

对于每一个入口,盐的含量不同意味着我不能使用同一个彩虹桌(实际上,如果我有足够的尺寸,我可以做到这一点,但是暂时忽略这一点)。 根据我的理解,这是真正的盐的关键,因为要破解每一个帐户,我必须重新发明轮子,为每一个说话。 现在,如果我知道如何将正确的salt应用于密码来生成散列,我会这样做,因为salt实际上只是扩展了散列短语的长度/复杂度。 所以我会减less我需要产生的可能组合的数量,以“知道”我有13 ^ 26到8 ^ 26的密码+盐,因为我知道盐是什么。 现在,这使得它更容易,但仍然很难。

所以encryption盐。 如果我知道盐是encryption的,我不会尝试解密(假设我知道它有足够的encryption级别)。 我会忽略它。 回到前面的例子,我只想生成一个包含13 ^ 26所有键的更大的彩虹表,而不是试图找出解密的方法。 不知道盐会一定减慢我的速度,但我不认为这会增加尝试破解盐encryption的巨大任务。 这就是为什么我不认为这是值得的。 思考?

这里是一个链接,描述了在一个暴力攻击下密码将持续多长时间: http : //www.lockdown.co.uk/? pg=combi

这里的答案是问问自己,你真的想保护什么? 如果有人可以访问你的数据库,那么他们可以访问encryption盐,他们也可能访问你的代码。 所有这些他们可以解密encryption盐? 如果是这样的话,encryption几乎是无用的。 盐真的在那里,所以它是不可能形成一个彩虹表,一旦破解你的整个密码数据库破解。 从这个angular度来看,只要每种盐都是独一无二的,那么对于每种口令,你的盐或encryption的盐都需要进行暴力攻击。

隐藏盐是不必要的。

每个哈希应该使用不同的盐。 在实践中,通过从密码质量随机数发生器中获得8个或更多的字节很容易实现。

从我以前的回答 :

盐有助于阻止预先计算的字典攻击。

假设攻击者有一个可能的密码列表。 他可以散列每一个,并将其与受害者密码的散列进行比较,看看是否匹配。 如果名单很大,这可能需要很长时间。 他不想在他的下一个目标上花费那么多的时间,所以他把结果logging在一个“字典”中,一个散列指向相应的input。 如果密码列表非常长,他可以使用彩虹表等技术来节省一些空间。

但是,假设他的下一个目标淹没了他们的密码。 即使攻击者知道盐是什么,他的预先计算的表也毫无价值 – 盐会改变每个密码产生的散列。 他必须将所有密码重新打散,将目标盐粘贴到input中。 每种不同的盐都需要不同的字典,如果使用了足够的盐,攻击者将无法为所有字典存储字典。 交易空间节省时间不再是一个select; 攻击者必须回退哈希每个列表中的每个密码,他想攻击的每个目标。

所以,没有必要保持盐的秘密。 确保攻击者没有与特定的盐对应的预先计算的字典就足够了。


再想一想,我已经意识到,自欺欺人地认为盐可以隐藏是危险的。 尽pipe如此,假设盐不能被隐藏,devise系统是安全的。 我在另一个答案中提供了更详细的解释。

我对“盐”的理解是,它使得破解更加困难,但它并不试图隐藏额外的数据。 如果你试图通过使盐成为“秘密”来获得更多的安全性,那么你真的只需要更多的encryption密钥。

第二种方法只是稍微安全一些。 盐可以保护用户免受字典攻击和彩虹表攻击。 他们使得一个雄心勃勃的攻击者难以妥协整个系统,但仍然容易受到针对您的系统的一个用户的攻击的攻击。 如果您使用公开可用的信息(如电话号码), 并且攻击者意识到这一点 ,那么您已经为他们拯救了一步。 当然,如果攻击者得到你的整个数据库,盐和所有的东西,这个问题是没有意义的。

编辑:重新阅读这个答案和一些评论后,我发现一些混淆,可能是由于我只比较问题中提出的两个非常具体的情况:随机盐vs.非随机盐。 使用电话号码作为盐的问题在攻击者得到你的整个数据库时是没有意义的, 而不是使用盐的问题。

下面是一个简单的例子,说明为什么每个散列都有相同的盐是不好的

考虑下表

UserId UserName, Password 1 Fred Hash1 = Sha(Salt1+Password1) 2 Ted Hash2 = Sha(Salt2+Password2) 

情况1当salt 1与salt2相同时如果Hash2被replace为Hash1,则用户2可以用用户1的密码login

情况2当盐1不相同salt2如果Hash2被replace为Hash1,那么user2不能用用户1的密码login。

…就像用户名或电话号码来哈希。 …

我的问题是如果第二种方法真的有必要? 我从纯粹的理论angular度可以理解,它比第一种方法更安全,但是从实践的angular度来看呢?

从实际的angular度来看,盐是一个实现细节。 如果您更改了用户信息的收集或维护方式 – 并且用户名和电话号码有时会发生变化,请使用您的确切示例 – 那么您可能已经损害了您的安全性。 你想要这样一个外向的变化,有更深的安全问题吗?

是否停止要求每个帐户都有一个电话号码需要涉及一个完整的安全审查,以确保您没有打开这些帐户的安全妥协?

隐藏的盐不再是盐。 这是胡椒。 它有它的用处。 它不同于盐。

胡椒是添加到密码+ salt的密钥,使得哈希变成HMAC(基于哈希的消息validation码)。 有权访问哈希输出和盐的黑客可以理论上蛮力猜测将生成散列(因此在密码文本框中通过validation)的input。 通过添加胡椒粉,可以以密码随机方式增加问题空间,使问题难以解决,而不会造成严重的硬件问题。

有关辣椒的更多信息,请点击这里 。

另见hmac 。

有两种技术,有不同的目标:

  • “盐”是用来使两个不同的密码encryption不同。 这样,入侵者无法有效地使用字典攻击对整个encryption密码列表。

  • (共享)“秘密”是在散列消息之前添加的,因此入侵者不能创build自己的消息并接受它们。

真的,这取决于你试图保护你的数据的攻击types。

每个密码的唯一salt的目的是防止对整个密码数据库的字典攻击。

对每个密码encryption独特的密码会使得破解个人密码变得更加困难,是的,但是你必须权衡是否真的有很多好处。 如果攻击者通过蛮力发现这个string:

 Marianne2ae85fb5d 

散列到存储在数据库中的散列,真的很难弄清哪个部分是合格的,哪个部分是盐?