安全远程密码协议中的最佳变量大小

信息安全 加密 密码 验证 密码学 密钥交换
2021-08-19 13:40:16

我正在实施安全远程密码协议:

  U = <username>              -->
                                 <--    s = <salt from passwd file>
  a = random()
  A = g^a % N                 -->
                                     v = <stored password verifier>
                                     b = random()
                              <--    B = (v + g^b) % N
  p = <raw password>
  x = SHA(s | SHA(U | ":" | p))

  S = (B - g^x) ^ (a + u * x) % N    S = (A * v^u) ^ b % N
  K = SHA_Interleave(S)              K = SHA_Interleave(S)

我应该为所有变量设置多大的数字? RFC 2945建议u为 32 位,但不能更低。N 为 4096 位,g = 2。

我的目标是在没有任何不必要费用的情况下最大限度地提高安全性。s、a、b 和 u 应该有多大?最后但并非最不重要的一点是,AES 密码将使用的会话密钥 K 的最佳长度是多少?

编辑: SHA_Interleave(S) 返回每个其他字节的 SHA 哈希与剩余字节的 SHA 哈希连接,从而使结果的长度加倍。SHA256 就足够了吗?对于 AES,我需要什么大小的密钥?

1个回答

RFC 5054有更精确的建议。为了保持连贯性,必须尝试实现以比特表示的给定“安全目标”作为参数t :即,系统对计算能力高达2 t基本操作的攻击是安全的。t的传统值是 80 位,但技术的进步使得可用计算能力非常接近这个限制。由于密码学家只喜欢 2 的幂,因此现在习惯使用 128 位作为安全目标。即使对摩尔定律将持续多长时间及其含义进行了过度乐观的估计,128 位至少在接下来的 40 或 50 年内仍然是安全的,而且在此之后的预测毫无意义。

要获得t位安全性,您应该具备以下条件:

  • Diffie-Hellman 私有元素(此处为 ab)的大小应至少为2t位(因此为 256 位——顺便说一下,这是 RFC 5054 推荐的)。

  • 所涉及的散列函数通常应具有至少2t位的输出大小,在许多情况下也可以容忍较短的输出大小(2t位的输出大约具有2t的抗碰撞能力,但在许多情况下,碰撞不是问题,我们只需要2 t对原像的抵抗力,并且为此t输出位就足够了)。

  • 对称加密密钥和 MAC 密钥的长度至少应为t位(并且 AES 可以使用 128 位密钥)。

  • 理想情况下,盐的长度应为2t位,以便发生冲突的风险(不同用户的两个相同盐)低于2 -t,但您可以使用更短的盐,因为服务器可以控制它可能拥有的用户数量,并且它肯定会比2128慢很多这里说的是服务器的算力,不是攻击者的算力)。

  • 作为在线挑战,u的长度应为t位,但同样,较短的值是完全可以容忍的,因为u的大小只能在在线攻击中被利用:对于 32 位的u,攻击者有 1以 40 亿次的机会发起模拟攻击,但客户端和服务器可以看到每一次失败。同样,服务器在短时间内处理数十亿个请求时会遇到一些麻烦,而且肯定不会离散地这样做。另外,攻击者也可以尝试自己猜测密码,在相同的在线检查条件下,所以有一个u是没有意义的。 比预期的平均密码熵长——而且 32 位密码熵已经是一个乐观的数字。

  • n(素数)应该足够大,以至于离散对数模n至少有2 t困难。这种“难度”很难估计,因为它的成本与用于破坏对称加密的成本相比具有不同的性质。尽管如此,还是有试探性的。4096 位有点大材小用;我个人会对 2048 位感到非常满意。

SRP 产生一个共享秘密值S,然后通过密钥派生函数将其扩展为对称密钥材料。SHA_Interleave()是这样一个 KDF 的提议。在 RFC 5054 中,使用了TLS中定义的 KDF(名称为“伪随机函数”)。对于正确的数据隧道,您将需要四个 128 位对称密钥:一个加密密钥和一个双向的完整性检查密钥。如果您使用组合的加密和完整性模式,那么您只需要两个 128 位对称密钥(每个方向一个)。

这看起来真的像你正在用 SRP 重新发明 TLS,这在很多层面上都很难做到,你真的应该使用真正的 TLS。