使用ECDH公钥包装密钥



前言:我不知道在这里还是在Crypto网站上问这个问题更合适。随意移动或删除或任何适当的SE操作。


我被要求帮助更新一些加密软件。总的来说,该软件已经完成了以下步骤,其中没有一个是特别不寻常的。为了简化发布,我省略了错误处理和Provider参数:

1) 生成一个随机对称密钥,用于AES-128(或AES-256,作必要修改):

KeyGenerator keygen = KeyGenerator.getInstance("AES");
keygen.init (128, a_SecureRandom_instance);
SecretKey sessionKey = keygen.generateKey();

2) 包装对称密钥,具体取决于用户是否正在使用
2a)。。。来自密钥对的RSA公钥:

// OAEP wasn't used in this software for hysterical raisins
Cipher wrapper = Cipher.getInstance("RSA/ECB/PKCS1Padding");
wrapper.init (Cipher.WRAP_MODE, user_RSA_PublicKey);

2b)。。。密码短语:

SecretKey stretched = ...passphrase stretched through a PBKDF like bcrypt...;
// I don't remember whether it's specified as "AES" or "AESWrap" here
Cipher wrapper = Cipher.getInstance("AES or AESWrap/ECB/NoPadding");
wrapper.init (Cipher.WRAP_MODE, stretched);

2c)任一路由,会话密钥被包装:

byte[] wrapped = wrapper.wrap(sessionKey);

3) 会话密钥用于使用Cipher.ENCRYPT_MODE和随机IV创建Cipher,然后通过它运行大量数据。这部分非常标准,但如果你真的想查看CipherInputStream的使用情况,我可以发布它。包装好的会话密钥与加密数据和一堆HMAC一起存储。

稍后在解密时,用户提供RSA私钥或用于扩展的密码短语;软件打开对称密钥并解密数据。

所有这些都已经运行了一段时间。但当然,RSA密钥对越来越大,速度越来越慢,因此他们希望支持上述步骤#2的额外可能性,其中使用椭圆曲线算法生成公钥(通常情况下为P384ECDH)。这就是我们感到困惑的地方。

Cipher wrapper = Cipher.getInstance("RSA/ECB/PKCS1Padding")调用中似乎没有针对椭圆曲线的JCE替换算法/变换。Java文档中唯一列出的是"ECIES",它似乎(?)更倾向于多方密钥协议?

我能为Java内置JCE找到的所有API,甚至是浏览Bouncy Castle,都只在密钥协议和传输的上下文中提到ECDH密钥,它们用于生成对称密钥,而不是包装现有密钥。

我觉得我们在这里遗漏了一些东西,可能是因为糟糕的假设。Cipher.wrap()真的不是ECDH密钥的选项吗?或者它,但我们需要做一些时髦的事情来创建ECIESCipher实例?

RSA是一种用于加密和签名的算法(或者根据您的看法,是两种非常相似但不同的算法)。RSA加密可以加密作为(较低级别)密钥的数据,在这种情况下,它被称为包装。

DH是一种密钥协商算法,具有经典形式(也称为整数、Zp、modp或有限域/FF)和椭圆曲线形式(ECDH)。请注意,至少对于经典DH,原始协议值g^a^b mod n=g^b^a mod n具有足够的数学结构,人们不愿意直接将其用作密钥,因此我们通过密钥推导函数(缩写为KDF)运行它。我不清楚ECDH值是否真的需要KDF,至少对于常用的X9/NIST曲线,包括P384(如果你愿意,你可以在crypto.SX上查看或询问),但使用KDF既便宜又可靠,所以我们这样做

我从来没有听过任何有能力的人呼叫(EC)DH密钥传输,因为它特别不是。它包含在密钥交换中,该术语旨在涵盖运输和协议的(有用的)联盟。

您可以使用(EC)DH创建加密方案,方法是使用约定(和派生)值作为对称加密的密钥,并且的(EC)IES我不知道是什么让你认为IES是另一回事。现代实践是对称加密应该经过身份验证,IES的标准化形式作为一个单独的方案使用CBC加密和HMAC身份验证,尽管你可以有效地设计一个使用例如GCM的方案。

正如您所看到的,BouncyCastle提供程序提供DH(经典)或EC IES"的实现;具有{AES,DESEDE}-CBC"(在1.56之前的版本中,有时会省略-CBC),使用P1363a中的KDF2和SHA1、指示的CBC密码和HMAC-SHA1。"标准"(Sun/Oracle/Open)提供程序没有,但您可以将原始协议操作、KDF以及对称加密和MAC结合起来,以产生相同的结果。

这与CMS-formerly-PKCS7与经典DH和ECDH以及PGP与ECDH的操作相似(尽管在一些细节上不同)。(PGP不支持经典DH;它使用ElGamal加密代替RSA。)更不用说TLS(有时通过1.2,总是在1.3中)和SSH,它们使用经典或EC DH"交换"(这里是交互式的,通常是短暂的,而不是至少具有静态接收器)来产生秘密,该秘密被派生并用作对称加密和数据验证的密钥材料。

最新更新