我需要使用 AEAD 在两个用户之间共享信息,其中一部分必须加密,一部分应以明文形式保存。
使用 AES/GCM 加密消息后,是否有 API 可以检查密文标签并访问关联数据?
我使用 Java 7 和 bouncycastle 作为提供程序,并且我已成功使用相应的 API 加密和解密我的数据:
private byte[] encrypt(SecretKey key, byte[] nonce, byte[] message, byte[] associatedData) throws ... {
Cipher aeadCipher = Cipher.getInstance(AES_GCM_NOPADDING);
aeadCipher.init(Cipher.ENCRYPT_MODE, kint, new GCMParameterSpec(GCM_MAC_SIZE, nonce);
aeadCipher.updateAAD(associatedData);
return aeadCipher.doFinal(message);
}
private byte[] decrypt(SecretKey key, byte[] nonce, byte[] cipherText, byte[] associatedData) throws ... {
Cipher aeadCipher = Cipher.getInstance(AES_GCM_NOPADDING);
aeadCipher.init(Cipher.DECRYPT_MODE, kint, new GCMParameterSpec(GCM_MAC_SIZE, nonce);
aeadCipher.updateAAD(associatedData);
return aeadCipher.doFinal(cipherText);
}
Run Code Online (Sandbox Code Playgroud)
然而,据我了解,AES/GCM 密文应该已经包含可能影响解密的参数(随机数和关联数据)。因此,我希望能够从密文中检索它们,而不是必须将它们与密文一起存储并将它们传递给解密函数。此外,我希望能够运行完整性检查(计算标签)并对关联数据运行一些检查,而不必完全解密消息。
是否有一个 API 可以实现这一点,但我可能错过了?
到目前为止,我已经检查过:
没有隐式格式将 GCM 的所有输入数据存储在特定位置。Java API 已经有点奇怪了,因为它自动将标签放在末尾。这使得算法与Cipher类更加兼容,但原则上标签只需要与密文一起保存——在哪里并不重要。现在您遇到的问题是,您不知道 AAD 在哪里结束,密文在哪里开始。
因此,您可以做的就是创建自己的格式(也许您的 AAD 具有静态大小,因此您可以连接),或者可以使用预定义的容器格式。有一个互联网草案 指定了如何在加密消息语法 (CMS) 中使用这两种模式。然后,AAD 可以存储在经过身份验证的属性中,其中还应包括所需的参数(包括包含随机数的 IV)。
如果您感到自虐,您也可以尝试在 GCM 模式下使用 XML 加密,但要注意验证 XML 真实性方面的许多陷阱(例如,请注意您实际上正在验证要使用的数据)。
Bouncy Castle 似乎使用 GCM 提供对 CMS 的支持。
| 归档时间: |
|
| 查看次数: |
4418 次 |
| 最近记录: |