在 C # 中使用 BCrypt 是一个好的哈希算法吗? 我在哪里可以找到它?

我读到过,当散列一个密码时,许多程序员建议使用 BCrypt 算法。

我用 C # 编程,想知道是否有人知道一个很好的 BCrypt 实现?我找到了 这一页,但我真的不知道它是不是假的。

在选择密码哈希方案时,我应该注意什么? BCrypt 是一个“好”的实现吗?

61555 次浏览

首先,一些重要的术语:

散列 -获取一个字符串并生成一个不能恢复到原始字符串的字符序列的操作。

对称加密 -(通常只称为“加密”)-获取一个字符串并生成一系列字符的行为,通过使用加密该字符串的同一个加密密钥将 可以解密为原始字符串。

Rainbow Table -一个查找表,包含特定散列算法中散列的所有字符变体。

Salt -在散列之前附加到原始字符串的已知随机字符串。

为了。NET 框架,Bcrypt 还没有 已确认引用实现。这一点很重要,因为没有办法知道现有实现中是否存在严重的缺陷。您可以得到 这里是.NET 的 BCrypt的实现。我对密码学的了解还不足以说明它是一个好的还是坏的实现。密码学是一个非常深奥的领域。不要尝试构建自己的加密算法.说真的。

如果你要实现自己的密码安全(叹气) ,那么你需要做几件事:

  1. 使用 相对 SHA家族
  2. 在对每个密码进行散列之前对其进行盐化。
  3. 使用 每个密码都有唯一的长盐,并将盐与密码一起存储。
  4. 需要强密码

不幸的是,即使你做了所有这些,一个有决心的黑客仍然可能找出密码,只是需要很长的时间。那是你的主要敌人: 时间

Bcrypt 算法之所以有效,是因为它比 MD5花费更长的数量级来散列密码; (仍然比 AES 或 SHA-512长得多)。它迫使黑客花费更多的时间来创建一个彩虹表来查找您的密码,使您的密码被黑客攻击的可能性大大降低。

如果你正在盐和哈希你的密码,每个盐是不同的,那么一个潜在的黑客就必须为每种盐创建一个彩虹表,只是有一个彩虹表的一个盐 + 哈希密码。这意味着如果你有100万用户,黑客必须生成100万个彩虹表。如果你对每个用户使用相同的盐,那么黑客只需要生成1个彩虹表就可以成功地黑进你的系统。

如果你没有在你的密码中添加盐,那么攻击者所要做的就是为每个实现(AES,SHA-512,MD5)提取一个现有的 Rainbow 表,然后看看是否有一个符合散列表。这是 已经完成了攻击者 不需要自己计算这些彩虹表

即使这样,你必须使用良好的安全措施。如果他们能够成功地在您的站点上使用另一种攻击载体(XSS、 SQL 注入、 CSRF、 等等。) ,良好的密码安全性并不重要。这听起来像是一个有争议的声明,但是想想看: 如果我可以通过 SQL 注入攻击获得你所有的用户信息,或者我可以让你的用户通过 XSS,那么你的密码安全性有多好就不重要了给我他们的 cookie。

其他资源:

  1. Jeff Atwood: .NET 加密简化(非常适合于散列概述)
  2. 杰夫 · 阿特伍德: 我刚刚用你的名字登录了
  3. 杰夫 · 阿特伍德: 您可能存储的密码不正确
  4. 杰夫 · 阿特伍德: 速度哈希

注: 请推荐其他好的资源。我一定读过几十个作者的十几篇文章,但很少有人像杰夫那样直白地写这个主题。请在文章中编辑,因为你发现他们。

你进入 不得使用地穴。NET.你 必须使用 PBKDF2是与内置的。NET 框架实现。中唯一可免费获得的加密验证实现。NET 以及 NIST 推荐的算法

StackId 之前使用的是 BCrypt,因为这个原因移到了 PBKDF2:

对于那些好奇,我们正在哈希与 PBKDF2密码。相关代码 在这里 Http://code.google.com/p/stackid/source/browse/openidprovider/current.cs#1135 ) ,通过几个间接层 正在使用 BCrypt; 但是由于它内置在.NET 中,所以移到了 PBKDF2 框架,而 BCrypt 需要我们验证一个实现 (不小的事业)。

Kevin Montrose,May 272011凯文 · 蒙特罗斯,2011年5月27日

(GitHub 更新链接)

编辑: 已确认在加密术语中的含义似乎不容易理解,一个经过验证的实现意味着它已经被加密证明实现没有错误。这项工程的成本很容易达到20,000美元或更高。我记得当我在研究 OpenSSL 的时候,读到他们说他们还没有完成整个验证过程,但是如果你需要完全验证,他们可以为你指出正确的方向,并提到相关的成本。某些政府要求包括授权验证加密算法。

中的 bcrypt 实现。NET 尚未被验证。使用未经验证的加密实现,您无法完全确定其中是否存在故意的恶意错误,比如允许后门进入加密的内容或导致加密不安全数据的无意实现错误。

2014年编辑: 对于那些质疑使用经过验证的加密算法的必要性的人来说,看看 OpenSSL 中使用的 心血来潮的黑客造成的破坏吧。这就是使用未经验证的实现的成本。很安全。直到发现任何人都可以读取服务器的整个内存内容。

引入 Heart〉的更改的作者 Robin Seggelmann 说,他“错过了验证包含长度的变量”,并否认有任何提交有缺陷的实现的意图。随着心脏出血的披露,Seggelmann 建议关注第二个方面,他说 OpenSSL 没有得到足够多的人的评审。

这是一个未经验证的实现的定义。即使是最小的缺陷也会导致整个安全系统的瘫痪。

2015编辑: 删除基于推荐的语言,代之以绝对。为子孙后代嵌入原始凯文 · 蒙特罗斯评论。