彩虹表如何解决碰撞?

信息安全 彩虹桌
2021-09-08 00:30:26

我明白了它的要点。它就像是蛮力攻击和查找表之间的中间地带,它存储每个链的起始明文和结束哈希,其中链是通过减少和哈希制成的。

我不明白的是:

  1. 据说彩虹表可以解决碰撞问题,但为什么一开始碰撞就这么重要呢?
  2. 据说彩虹表通过对链中的每一列使用不同的归约函数来解决冲突,但这如何防止冲突呢?归约函数不只是您从哈希中获取的随机字符吗?那么,如果您使用前 8 个字符而不是后 8 个字符,会有什么区别呢?
2个回答

当前投票率最高的答案似乎并没有真正对您的问题做出适当的回应。我将尝试同时回答您的两个问题。

每列相同的归约函数

假设您对每一列使用相同的归约函数,并且有一个包含 2 行和 3 列的基本表。

P1  --R-->  P1'  --R-->  P1'' --R-->  P1'''
P2  --R-->  P2'  --R-->  P1'  --R-->  P1''

这里,an--R-->表示一个散列,然后是一个归约。P1, P2, P1', ...代表密码。如您所见,第二条链发生了碰撞。该值P1'已在第一个链中遇到。

注意之后会发生什么。

由于在减少 后的散列P1'与第一个链中的完全相同,因此我们得到了一个已经计算过的值。如果我们更进一步,从 开始的第二条链部分将P1'成为从 开始的第一条链部分的精确副本P1'

所以实际上,这就是碰撞不好的原因。第二个链合并到第一个链中。我们的表中有重复的结果,导致浪费存储空间和计算时间。

每列不同的归约函数

这一次,让我们看看如果我们对每一列使用不同的归约会发生什么。减少由--RX-->X号表示。

P1  --R1-->  P1'  --R2-->  P1'' --R3-->  P1'''
P2  --R1-->  P2'  --R2-->  P1'  --R3-->  P2''

再次,P1'在两个链中都遇到了。但是,由于归约函数不同,因此P1'在第二个链中计算的值不会P1''像在第一个链中那样导致 。这有效地解决了第一个示例中的合并问题。

请注意,这并不能解决每个链合并。观察以下示例中发生的情况:

P1  --R1-->  P1'  --R2-->  P1''  --R3-->  P1'''
P2  --R1-->  P1'  --R2-->  P1''  --R3-->  P1'''

这次碰撞发生在两条链的第一列。由于它发生在同一列中,因此每个下一个归约函数都将相同,并且链会再次合并。不过这种情况发生的概率比较低。

碰撞是 Rainbow Tables 唯一的问题。具有讽刺意味的是,对于散列算法而言,冲突被视为一件坏事,但在 Rainbow Tables 的情况下,相当定期地产生冲突的散列算法将更加安全。

据说彩虹表可以解决碰撞问题,但为什么一开始碰撞就这么重要呢?

给定的哈希可能由多个明文生成(这称为冲突),这对于链来说是一个大问题,因为它会导致开始不同的链收敛到一个。此外,您还会遇到循环,这是在将哈希简化为在链中的前一个点进行哈希处理的明文时引起的。

据说彩虹表通过对链中的每一列使用不同的归约函数来解决冲突,但这如何防止冲突呢?归约函数不只是您从哈希中获取的随机字符吗?那么,如果您使用前 8 个字符而不是后 8 个字符,会有什么区别呢?处理碰撞的方式是 Rainbow Tables 与 1980 年开发的前身的不同之处。

前身通过使用许多小表解决了某些明文永远不会被简化的问题。每个小表使用不同的归约函数。这并不能完全解决问题,但确实有帮助。

为了解决链合并和循环,每条链都以“不同点”结束;以某种方式唯一的散列,例如前 4 个字符为 0 的散列。链继续运行,直到到达一个不同的点。如果两条链在相同的不同点结束,则链中某处发生了冲突,其中一条链被丢弃。如果一条链生成了异常长的时间而没有达到一个明显的点,则怀疑是循环(其中哈希链最终减少并哈希到链中的先前哈希)。这样做的问题是,如果发生冲突,可能有一个完整的分支必须被切断并且不会进入链中,并且循环将导致链中循环之前的所有哈希被丢弃。同样,所有花费在生成该链上的时间都将被浪费,并且仅在不同的点结束,您就有了可变长度的链。这意味着您可能必须在其他链结束很久之后继续检查特别长的链中的哈希。

我从这里得到了适当的灵感:http: //kestas.kuliukas.com/RainbowTables/