H5W3
当前位置:H5W3 > 问答 > 正文

Java解密和加密是否与SJCL兼容?

我需要同时使用Java(在Android上)和SJCL加密和解密数据(我可以合理地切换到另一个JS加密库,但是对SJCL很熟悉,因此,如果可能的话,最好坚持使用它)。

我的SJCL端工作正常,但是在Java端,我不确定是否需要使用哪些参数来设置 key 生成器和密码。到目前为止,我用于解密的代码是:

SecretKeyFactory factory = SecretKeyFactory.getInstance("PBKDF2WithHmacSHA256");
KeySpec spec = new PBEKeySpec(password.toCharArray(), salt, 1024, 256);
SecretKey tmp = factory.generateSecret(spec);
SecretKey secret = new SecretKeySpec(tmp.getEncoded(), "AES");
Cipher cipher = Cipher.getInstance("AES/CBC/PKCS5Padding");
cipher.init(Cipher.DECRYPT_MODE, secret, new IvParameterSpec(iv));
String plaintext = new String(cipher.doFinal(ciphertext), "UTF-8");
return plaintext;

从SJCL产生的JSON对象中提取salt,iv和密文作为字符串,然后使用Base64解码器将其解码为字节数组。

不幸的是,我对此有一些问题,上面的代码不起作用。

我的第一个问题是PBKDF2WithHmacSHA256似乎不是公认的 key 生成算法。我不能完全确定这就是我想要的,但是根据阅读SJCL文档看,它似乎是正确的吗? Java确实可以识别PBKDF2WithHmacSHA1,但这似乎与SJCL实现的算法不同。

其次,如果尝试使用SHA1 key 算法,则会收到有关无效 key 大小的错误。我需要安装一些东西以启用具有256位 key 的AES吗?告诉 key 工厂产生一个128位 key 可以正常工作(尽管显然与使用256位 key 的SJCL不兼容)。

第三,我应该使用哪种密码模式?我很确定CBC是不对的… SJCL的文档同时提到了CCM和OCB,但是Java似乎并没有现成的支持这两种方法-再次,我是否需要安装一些东西才能使这项工作正常进行? SJCL默认使用哪一个?

最后,即使我选择了使Java不会提示缺少算法的参数,它也会提示解码SJCL输出所提供的IV的长度错误,这肯定看起来像是:结果输出中有17个字节,而不是AES显然要求16。我只是忽略最后一个字节吗?

最佳答案

我还没有尝试过(最后我不再使用Javascript加密,而是使用带有bouncycaSTLe的嵌入式Java applet来处理通信),但是GnuCrypto(一个bouncycaSTLe分支)支持PBKDFWithHmacSHA256。 SJCL中的固定字符编码处理大概可以修复IV(?)的意外长度,因此这只会离开密码模式。从这一点来看,似乎最简单的方法是将一个相对简单的密码模式(例如CTR)作为SJCL的附件来实现,即使对于不熟悉该代码的人也应该只需要几个小时的工作,之后这仅仅是对SJCL使用的JSON编码数据包进行编码和解码的问题(应该很简单)。

作为替代方案,尽管该算法是专有的,但肯定可以为Java实现OCB模式,因为根据GPL(http://www.cs.ucdavis.edu)分发了软件的公共(public)专利授权书(http://www.cs.ucdavis.edu/~rogaway/ocb/grant.htm)。

有趣的是,我想知道GnuCrypto是否会接受OCB模式支持的补丁吗? GnuCrypto是在具有库免除GPL的情况下分发的,该许可证看起来像是“自由软件基金会发布的GNU通用公共(public)许可证的任何版本”,因此从理论上讲,这至少应该是可能的。

本文地址:H5W3 » Java解密和加密是否与SJCL兼容?

评论 0

  • 昵称 (必填)
  • 邮箱 (必填)
  • 网址