0

我尝试在我的网络软件中使用 chacha20 加密,但我遇到了问题

如果我加密 4 字节数据:0x01 0x02 0x03 0x04在服务器上

并获取密文:0xd2 0xd3 0xc4 0xd5,然后将其发送给客户端

客户端一次可能会收到 <= 4 个字节

前提是客户0xd2 0xd3一开始只接受recv,

它可以正确解密数据并获取明文0x01 0x02

但是当客户端接收最后 2 个字节时0xc4 0xd5

似乎无法使用相同的随机数和密钥解密数据

那么有没有办法解决这个问题

在发送之前添加长度数据作为前缀是一种解决方案,但这很奇怪,因为我使用的是流密码。

4

2 回答 2

3

而不是重新启动 ChaCha20 密码实例(或更一般地说,context)你应该让它保持活动状态。

大多数加密 API 将允许您执行零碎的加密/解密。这通常意味着update为第一部分和第二部分调用一个方法,通常final在检测到明文/密文结尾时调用一个方法。根据 API,您应该期望这些方法中的每一个都有输出。

只有当您的 API 不允许您正确处理流时,您才应该聚合密文并对完整密文执行解密。

于 2017-12-03T15:06:03.723 回答
1

ChaCha20 使用密钥和随机数生成一个流。让(S0, S1, S2, S3)(M0, M1, M2, M3)的第一个字节和消息的前 4 个字节。

密文将被计算为(M0⊕S0, M1⊕S1, M2⊕S2, M3⊕S3)。这是如果你有M0...M3现成的。

如果你加密(M0, M1)然后(M2, M3)使用相同的密钥和随机数,你最终会得到(M0⊕S0, M1⊕S1)and (M2⊕S0, M3⊕S1)。无法使用(C0⊕S0, C1⊕S1, C2⊕S2, C3⊕S3).

更糟糕的是,因为S0S1已经被不同的消息重用,攻击者可以在知道任何消息的情况下恢复它们。

为了避免这种情况,最简单的做法是缓冲数据直到达到块大小,然后加密整个块,而不是尝试加密部分块。

于 2017-12-03T10:58:54.780 回答