什么是最佳的scrypt工作因素?

我正在使用Java scrypt库来存储密码。 当我encryption文件时,它要求Nrp值,其文档称之为“CPU成本”,“存储器成本”和“并行成本”参数。 唯一的问题是,我实际上并不知道他们具体是什么意思,或者对他们有什么好的价值。 也许他们以某种方式对应于Colin Percival的原始应用程序上的-t,-m和-M开关?

有没有人有这个build议? 图书馆本身列出了N = 16384,R = 8和P = 1,但我不知道这是强还是弱。

作为开始:

从2009年的幻灯片中提到高潮

  • (N = 2 ^ 14,r = 8,p = 1)<100ms(交互使用)
  • (N = 2 ^ 20,r = 8,p = 1)<5s(敏感存储)。

即使在今天(2012-09),这些值恰好足够用于一般用途(某些WebApp的password-db)。 当然,细节取决于应用程序。

而且,这些值(主要)是指:

  • N :一般工作因子,迭代次数。
  • r :使用底层散列的块大小; 微调相对的内存成本。
  • p :并行化因素; 微调相对的CPU成本。

rp是为了适应潜在的问题,CPU速度和内存大小和带宽不会像预期的那样增加。 如果CPU的性能提升得更快,那么你应该增加p ,而不是内存技术的突破提供了一个数量级的提高,你就增加r 。 而N在那里能够跟上一些倍增的性能。

重要提示:所有值都会更改结果。 (更新:)这就是所有的scrypt参数存储在结果string中的原因。

scrypt操作所需的内存计算如下:

128字节× N_cost × r_blockSizeFactor

对于你引用的参数( N=16384r=8p=1

128×16384×8 = 16,777,216字节= 16MB

select参数时必须考虑到这一点。

Bcrypt比Scrypt “弱” (虽然比PBKDF2强三个数量级 ),因为它只需要4 KB的内存。 您希望使硬件中的破解难以并行化。 例如,如果video卡有1.5 GB的机载内存,并且您调整了scrypt以消耗1 GB内存:

128×16384×512 = 1,073,741,824字节= 1GB

那么攻击者就不能在他们的video卡上进行并行处理。 但是,每次计算密码时,您的应用程序/电话/服务器都需要使用1 GB的RAM。

它帮助我把scrypt参数看成一个矩形。 哪里:

  • 宽度是所需的内存量(128 * N * r)
  • 高度是执行的迭代次数
  • 所产生的面积就是整体硬度

在这里输入图像说明

  • costN )增加了内存使用迭代
  • blockSizeFactorr )会增加内存使用量

其余的参数parallelizationp )意味着你必须做整个事情2次,3次或更多次:

在这里输入图像说明

如果你的内存比CPU多,你可以并行计算三条独立的path – 需要三倍的内存:

在这里输入图像说明

但是,在所有现实世界的实现中,它是按照计算结果进行计算,所需的计算量增加了三倍:

在这里输入图像说明

实际上,除了p=1之外,没有人select过p因子。

什么是理想的因素?

  • 尽可能多的RAM,你可以备用
  • 尽可能多的时间,你可以备用!

奖金图表

以上graphics版本:

在这里输入图像说明

笔记:

  • 垂直轴是对数刻度
  • 成本因素(水平)本身就是log(迭代= 2 CostFactor
  • r=8曲线中突出显示

并放大到以上版本的合理区域:

在这里输入图像说明

我不想踩上面提供的优秀答案,但没有人真正谈论为什么“r”有它的价值。 Colin Percival的Scrypt纸提供的低级答案是它涉及到“内存延迟 – 带宽产品”。 但是这实际上意味着什么呢?

如果你正在做Scrypt,你应该有一个大的内存块,大部分都在主内存中。 主内存需要时间来拉。 当块跳转循环的迭代首先从大块中select一个元素混合到工作缓冲区中时,它必须等待100ns数量级的第一块数据到达。 然后它要求另一个,等待它到达。

对于r = 1,你将会进行4次Salsa20 / 8迭代 2次来自主内存的延迟读取。

这并不好,因为这意味着攻击者可以通过构build一个延迟主存的系统来获得优势。

但是,如果增加r并按比例减lessN,则可以达到与以前相同的内存要求并执行相同数量的计算 – 不过您已经为顺序访问交易了一些随机访问。 扩展顺序访问允许CPU或库有效地预取下一个需要的数据块。 虽然初始等待时间仍然存在,但是稍后的块的等待时间减less或消除将初始等待时间平均到最小等级。 因此,攻击者从改进内存技术中获益不大。

但是,随着r的增加,收益递减点也就是前面提到的“内存延迟 – 带宽产品”。 本产品表示的是在任何给定时间从主存储器传输到处理器的数据字节数。 这与高速公路相同 – 如果从A点到B点需要10分钟的时间(等待时间),并且从A点(带宽)向道路B提供10辆/分钟到B点,则A点和B包含100辆汽车。 因此,最佳的r与您可以一次请求多less个64字节的数据块有关,以掩盖该初始请求的延迟。

这提高了algorithm的速度,允许您增加N以获得更多的内存和计算量,或者根据需要增加P以实现更多计算。

还有一些其他的问题,比如“r”太多了,我还没有看到太多的讨论:

  1. 减lessN时递增r减less了内存周围的伪随机跳跃的数量。 顺序访问更容易优化,并可能给攻击者一个窗口。 正如Colin Percival在Twitter上向我指出的那样,较大的r可能会让攻击者使用更低的成本,更慢的存储技术,大大降低成本( https://twitter.com/cperciva/status/661373931870228480 )。
  2. 工作缓冲区的大小是1024r比特,所以最终将被馈送到PBKDF2中以产生Scrypt输出密钥的可能的最终产品的数目是2 ^ 1024r。 大内存块周围的跳转序列(可能的序列)是2 ^ NlogN。 这意味着有2 ^ NlogN可能的产品的记忆跳转循环。 如果1024r> NlogN,这似乎表明工作缓冲区混合不足。 尽pipe我不太确定这一点,并希望看到一个certificate或防范,但是可能在工作缓冲区的结果和跳转序列之间find相关性,这可能使攻击者有机会减less它们内存要求没有大大增加计算成本。 再一次,这是一个基于数字的观察 – 可能是因为每一轮中的一切都是如此的混合,这不是一个问题。 对于N = 2 ^ 14,r = 8远低于标准N = 2 ^ 14的这个潜在阈值,该阈值将是r = 224。

总结所有build议:

  1. selectr只是足够大的平均内存延迟对您的设备的影响,没有更多。 请记住,Colin Percival推荐的值为r = 8,对于内存技术而言似乎仍然是相当优化的,而这一点在8年内显然没有太大变化。 16可能会稍微好一些。
  2. 决定每个线程要使用多less内存,同时要记住这也会影响计算时间,并相应地设置N.
  3. (注意:在我的系统上,使用我自己的实现,p = 250(4个线程),N = 16384和r = 8需要约5秒钟),如果你能处理,启用线程与增加的内存成本。
  4. 调整时,首选较大的N和内存块大小,以增加p和计算时间。 Scrypt的主要好处来自于它大的内存块大小。

使用i5-4300(2核心,4线程)的Surface Pro 3,使用恒定128Nr = 16 MB和p = 230的Scrypt的基准testing; 左轴为秒,底轴为r值,误差为+/- 1标准偏差:

用恒定的大块大小对r值和p进行Scrypt