如何实施安全的密码历史记录


23

出于明显的安全原因,不应以纯文本形式存储密码:您必须存储散列,并且还应谨慎生成散列,以避免彩虹表攻击。

但是,通常您需要存储最后的n个密码,并在不同密码之间进行最小的复杂度和最小的更改(以防止用户使用诸​​如Password_1,Password_2,...,Password_ n之类的序列)。使用纯文本密码将是微不足道的,但是如何仅存储散列呢?

换句话说:如何实现安全的密码历史记录机制?


2
相关信息:security.stackexchange.com/questions/4704/…(顺便说一句,该站点可能是此问题的更好位置)。至于“最小变化”,我想不出任何替代方法来生成所有可以视为“最小变化”的选项(根据您的定义,这可能很多)并比较散列。'minimum change'的解释是什么?
凯文·维米尔

7
存储最新的n个密码仅意味着用户将选择一个从1到n + 1的序列。
约阿希姆·绍尔

11
我非常怀疑这样的密码策略是否可以提高安全性。恕我直言,这增加了人们诉诸于将密码保存在便笺上的机会。凯文的链接是一个很好的讨论。@KevinVermeer-您实际上可以将变化量度量为Levenshtein距离(en.wikipedia.org/wiki/Levenshtein_distance),也称为“编辑距离”。
内森·朗

5
如果您的安全性如此严格,那么您最好为用户生成一个随机密码,强迫他们使用它,并定期更改它。这样,您就可以完全控制他们的密码。
Reactgular 2012年

2
@nathan:在便签上存储密码实际上是安全的。除非您可以物理访问便笺,否则无法攻击密码-消除了大约99%的威胁。将该便条放在钱包或钱包中,您基本上需要抢劫该人才能得到它-这意味着可以识别安全隐患并加以缓解。
mattnz

Answers:


22

存储散列并针对存储的散列验证输入的密码,这与登录时验证密码的方式相同。您将必须根据数字模式从给定的密码中生成“替代”密码,以检测“最小”变化。

登录时,您已经针对哈希验证了输入的密码,无需以明文形式存储密码。更改密码时,可以使用相同的技巧,只需对照历史哈希值检查输入的“最小更改”生成的密码即可。如果新密码令人满意,则将当前密码哈希移至历史记录集,并用新密码的新哈希替换。


因此,如果用户输入Password6,我应该检测数字部分,并尝试例如Password4Password5Password7等等。那是对的吗?
Wizard79 2012年

4
@洛伦佐:是的。生成替代方案可以像您想要的那样复杂,只需确保在复杂性和风险之间找到适当的权衡(不要让您的用户等待5分钟,同时检查所有可能消失的风险)。
Martijn Pieters 2012年

我不确定到底增加这个数字对用户是个好建议-这只是可以预料的一点。并且呈指数级增长,因此,如果您告诉用户这样做的话。
Wyatt Barnett 2012年

2
@WyattBarnett:没有人告诉用户这样做。关键是要检测用户这样做,并防止使用“递增”密码。
马丁·彼得

啊,完全误读了这里的内容。抱歉。
Wyatt Barnett 2012年

28

用户更改密码时,要求他们输入以前的密码。现在您可以访问两个纯文本密码,即使您没有在数据库中存储纯文本密码也是如此。

对这两个密码执行所需的任何验证。这不会阻止用户在两个密码之间进行替换(带有后缀-您可以根据其他答案中的建议防止直接更改密码),但是可以避免更为公然的情况。


好吧,如果您不需要针对n个以前的密码进行测试,那么这无疑是一个聪明的解决方法,但是建议您及时生成替代方案更好。但是生成两个密码的替代品更好!
Wizard79 2012年

2
@Lorenzo:想法是您对前n个密码进行直接测试,对最后一个密码进行更严格的测试。这是一个妥协。
Brian

是。如果他们的当前密码是potatoSalad1,并且想要更新为potatoSalad2,则您会说更改太小,因为此时您同时拥有两个纯文本密码。但是比这更远,您只有哈希,并且哈希的性质是您无法确定两个哈希是否具有相似或完全不同的纯文本作为输入。
内森·朗

7

要添加到@martijnPieter的答案中,可以通过基于新密码和旧密码(您都可以使用)进行短暂的暴力破解来实现最小的更改

例如,您可以遍历所有密码与新密码之间的汉明距离为1或2的所有密码,并查看其是否与旧密码匹配

但您可能要注意,这会降低用户对密码进行哈希处理的信心(因为您实际上是在说可以找回以前的密码来拒绝新密码)


但是有许多汉明距离较大的序列,例如February2012-> March2012或Fri-09-28-12-> Tue-11-27-12(日期),Password_Alpha-> ​​Password_Beta,Pass_1111-> Pass_2222,Pass_qwer,Pass_tyui,通过,_op []或11->十二(备用计数系统),或FrankSmith-> FredJones-> FriarTuck或愤怒->动物->苹果(公司目录中的名称或词典中的单词),表示攻击者具有先前的密码很容易猜到,但是您的算法将很难生成。
凯文·维米尔

@KevinVermeer然后说明您的变量生成器中的变量,并接受您将永远无法获得所有内容
棘手的怪胎2012年

+1以降低信心。当我看到某件事告诉我我的密码太像我三个月前使用的密码时,我立即想知道它们是否可逆地存储它们……还是他们有一个很棒的程序员。怀疑主义通常会胜出。
Tim Post

5

这实际上是@Brian聪明答案的补充。还可以@Martijn Pieters添加有关如何基于当前密码强行破解旧密码的详细信息,以及@ratchet怪胎的“汉明距离”。我不会删除我的答案,因为我认为它提供了支持他们的有趣背景。

最先进的密码存储需要为每个用户使用多轮强大的单向加密哈希(SHA-512 +),并带有唯一的盐(128位+)。但是不要试图存储有关每个密码的其他信息。您将存储的有关每个密码的信息越多,破坏哈希算法的安全性就越多。

考虑一下知道暴力破解密码变得多么容易:

  • 7个字符长
  • 字符3-5为大写(4为小写)
  • 1和7是数字
  • 6是符号

美国键盘具有95个可打印字符,因此知道密码的长度为7个字符可产生95 ^ 7 = 69,833,729,610,000 = 7x10 ^ 13排列。如果确实是随机的,则可能需要一年时间才能在单个3Ghz处理器上破解它。但:

  • 只有26个大写字母和26个小写字母
  • 只有10位数字可以产生这两个数字的100个可能性
  • 只有32个符号

因此(由于@Hellion而已更正):

         26^4 (charcters 2-5 are known upper or lower-case)
        x 100 (characters 1 & 7 are digits)
        x  32 (character 6 is a symbol)
         ====
1,462,323,200 possible passwords.

那更容易破解50,000次!在这种情况下,存储良好的信息以防止使用相似的密码,使您可以花7年的时间来破解7个字符的密码,从一年下来到几个小时。现在,在功能强大,具有良好视频卡和耐心的多处理器桌面上对所有密码进行解码非常可行。我希望这个简单的示例能够说明,您越能有意义地比较相似的密码,则哈希处理的安全性就越差。

强哈希的重要性

带有密码的数据库会定期被盗,每个月的新闻中都会有大量闯入事件。哎呀,就在上个月,SC州失去了每个人的社会保险号码 -哎呀!这些违规行为又掩盖了多少?

结束语

对我来说,最可怕的事情是,当人们为多个站点选择相同或相似的密码时,如果将其分成一个站点,攻击者便可以访问所有站点。我希望看到一种行之有效的防止这种情况的方法,尽管我认为防止最常见的错误密码将比阻止单个用户在同一站点内重用其错误密码有所帮助。我最好建议的是公司范围内的政策,即使用安全的密码管理器,该管理器为每个用户生成高度随机的密码并安全地存储它们。


1
次要级别:密码的可能性仍然是可乘的,因此(26 ^ 4)* 100 * 32 = 1,462,323,200。如果我们假设破解(95 ^ 7)的可能性需要一年,那么破解这个较小数目的可能性将花费大约11分钟。
Hellion

@Hellion-糟糕!感谢您指出了这一点。我已经改正了。
GlenPeterson,2012年

1

首先,您可以存储最后一个“ n”个先前密码的哈希,因此您可以检查其新密码是否与先前密码重复。您还拥有他们当前密码的纯文本(因为他们已经登录或提供给您以验证他们的密码更改请求)和他们的新密码,因此您可以检查这两个密码之间的最小更改。

如果(对您而言)将这两个密码与之前的“ n”个密码直接进行比较非常重要,那么您必须存储(加密)这些密码以便以后可以检索它们。

虽然这样做可能被视为安全缺陷,但可以实施加密方法以提供足够的安全性。

  1. 存储每个密码(已加密),以获取最后的“ n”个密码。
  2. 存储创建最新密码的日期和时间。
  3. 存储最新密码的哈希。
  4. 使用当前密码的哈希值(加盐)和密码创建时间戳记(例如,帐号或电子邮件地址)对所有密码进行加密。
  5. 每次创建新密码时,对所有密码进行解密和重新加密。

然后,无论何时更改密码,您都可以取消对所有旧密码的加密,并进行所有最小更改测试。

现在,如果某人拥有此人的密码,并且知道所有其他必要的详细信息,则可以为该人取消对该信息的加密。但是,如果他们已经有了该人的密码,他们就可以以该人的身份登录并访问该人的帐户。

同样,对于旧密码,可能不必严格以纯文本形式存储它们。它们可以以某种混淆的方式存储。或存储为密码中字母的字母顺序列表。

我并不是说在一般情况下建议这样做,但是假设您所描述的任务在您的情况下是必需的,那么这是通过一些安全措施来完成此任务的一种方法。


这个答案在安全性方面提出了几个可怕的建议。我们不应该能够轻易地解密密码,也不能以“某种混淆的方式”存储它们,而不是对它们进行高度加密。
user45623
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.