散列密钥:比密钥本身的熵少

信息安全 哈希 蛮力
2021-09-10 14:39:21

Web API 需要存储用于身份验证的“密钥”,其方式与密码大致相同,但长度为 128 个字符。我担心的是密钥的加盐 SHA1 哈希比密钥本身的熵少(40 个字符对 128 个字符)。

我知道哈希是必要的,以防数据库遭到破坏,但在这种情况下,从外部来看,假设没有数据库泄露,这个设置是否比我存储和匹配未散列的密钥更容易受到暴力破解?

注意:这个可怕的设置并不能取代真正的密码设置。“做主”的人想要第二个密码来访问某个功能,并且他希望它很长并且被称为“密钥”。编码后,我将有机会证明这是多么愚蠢。我在这里的问题仅涉及 128 个字符的字符串被暴力破解与 40 个字符的加盐哈希被暴力破解的敏感性。

4个回答

是一个数学概念的大词(在密码学的上下文中),因此它的命名是出于与物理学中使用的“熵”的近似类比。这里,“ n位熵”或多或少意味着密钥2 n 个可能的值。

为了安全起见,熵超过 100 位没有实际差异。我们希望我们的密钥不会被彻底搜索,而这是在尝试所有可能的密钥时实现的,或者至少是密钥空间的很大一部分,这对于现有技术来说是非常不可行的密码学家长期以来一直使用“80 位”作为阈值。100 位应该考虑到技术的改进和舒适的余量(在这些尺寸下,能量占主导地位,而不是摩尔定律)。超出这个规模,穷举搜索就彻底失败了,没有比这更大的失败了。

因此,虽然您的“128 字符密钥”可能具有 512 位熵(假设“字符”是十六进制数字)并且 SHA-1 哈希“只有”160 位(SHA-1 的输出大小),但两者都是离“做不到”的境界还很远,从安全的角度来看,说一个比另一个“更安全”是没有意义的。两者都免于穷举搜索。

相应地,这里不需要盐。是关于防止并行性和预计算:他们假设攻击者可以对一个键进行详尽的搜索,并希望对多个键运行相同的攻击。盐确保十个密钥的攻击成本将是一个密钥成本的十倍。使用 100 位以上的密钥,一次攻击的成本远远超出了可以做到的程度,因此阻止并行性几乎没有意义。换句话说,如果盐改变了安全局势,那么攻击者就是神,你应该牺牲牛来安抚他,而不是试图用你微不足道的哈希函数来对抗他。

SHA1 产生 160 位输出。它通常以 base16 表示,这将产生一个 40 个字符的字符串。不管它的基本表示是什么,它仍然是一个 160 位的散列。SHA1 不是理想的哈希函数,因为它存在已知的弱点,SHA-256 是更好的选择,SHA3 很快就会普及。

彩虹表是查找表,允许攻击者快速确定特定散列函数的纯文本输入。一个示例生成将是 6-9 个字符长之间的所有字母数字混合大小写字符串。为纯十六进制输入制作表格,af,0-9 意味着输入空间要小得多,因此更容易生成。128 个字符的 8 字节 ASCII 是 128*8 或 1024 位的信息,而 128 个字符的十六进制编码是 128*4 即 512 位的信息。即使是 512 位也是足够大的空间来防止暴力破解。攻击散列函数的大输入大小没有“捷径”,但没有什么能阻止您使用 SHA-512。

对于具有任意密码系统的安全系统,可能还有其他更严重的威胁。 我们散列密码的原因是为了防止数据库泄露这是因为攻击者被迫破解密码哈希以使其有用。如果你不打算失败,那你就做错了。

如果您有 40 个字符的输入和 40 个字符的散列,我们会假设密码与散列的比率约为 1 比 1。这意味着每个密码都会有一个散列,但不能保证一个密码将只有一个哈希值,它只是近似值。

考虑到有 128 个字符并产生一个 40 个字符的散列,如果考虑 128 个字符的所有可能组合,每个散列将有大约 3.2 个密码。

128 个字符的密码可能与 1 个字符的密码具有相同的哈希值!这不太可能,但绝对有可能,并且是一个潜在的弱点

总之,当您的输入多于输出时,您将不得不重用一些输出来满足所有输入。

请记住,从安全的角度来看,像 SHA-X、MD5 和其他“快速”哈希这样的哈希函数很容易出现彩虹表 [1]。尽管很难计算 160 位的熵,但如果哈希函数可以在非常大的输入域中并行运行,那么黑客可以存储此预计算并轻松地反转任何弱密码。

加盐可以极大地帮助这一点,特别是如果每​​个密码都使用不同的盐,但是由于 GPU 上的并行性,使用诸如 bcrypt 或 scrypt 之类的慢速、内存效率低的散列函数要高效得多。有关密码大小和破解不同长度密码的成本的说明,请参见 [2]。

[1] - http://en.wikipedia.org/wiki/Rainbow_table

[2] - https://raw.githubusercontent.com/tarcieri/scrypt/modern-readme/kdf-comparison.png