可用在JavaME上的加密包Bouncy Castle的使用

Bouncy Castle(http://www.bouncycastle.org/)是一个庞大的加密类库,支持Java和C#,其中Java部分发布的源代码压缩包就有24M左右,支持JDK 1.0~5.0,支持J2ME(现在叫JavaME)。
但是,这个类库使用起来并不那么方便,它并没有与普通Java类库那样以Jar形式发布立即可用的二进制类库,而只发布源代码,源代码包含了多份,包括JDK1.0,JDK1.1,JDK1.2,JDK1.3,JDK1.4,JDK1.5,J2ME等,每种环境都有少量文件不一样,有多个用于Ant的build xml,分别用于各种不同的JDK,但是每个xml定义了多个target,不知道哪个target才能build出可用的类库来,选中了其中某个target有可能会出现错误,build不下去。文档太简单,基本没讲到怎么生成可用的类库,网上的相关文档也很少。我尝试了两天才终于把第一个MIDP加密测试程序运行成功。
我的应用只是实现Java ME的加密,所以这里讲的只是针对JavaME的,JavaSE应该会简单一点。

打开下载下来的压缩包(crypto-138.zip),会发现里面有一堆文件夹和一堆文件,其中一个文件夹叫j2me,于是第一反应就是打开它看看里面是什么,发现里面只有少量的源代码文件,看来这只是适用于j2me的一部分源代码而已,其他通用的部分不在这里。
还有一个j2me.xml,是一个Ant的build文件,在eclipse里面用ant打开以后,发现里面有很多target,除了what(输出一些信息)和init(建立几个目录,复制一些文件)这两个能执行成功之外,其他几乎都是失败的,所以通过这个东西是搞不出我们可用的classes来的。
没办法,只有一个个目录地看,在一个zips目录里面发现cldc_sources.zip,里面的源代码文件有很多,有点像了,于是就把它解压后放到一个Eclipse ME测试项目的src目录下,找到org.bouncycastle.crypto.examples包,里面有个MIDPTest.java文件,还有个midp_test.jad,看来这个是用来测试用的MIDP了,调出WTK的模拟器来运行一下,果然是,成功了。
下一步是在手机上运行。如果不混淆,生成的JAR包有1.6M之巨,不管了,先试一下。安装到手机上,到最后出现“授权失败”的提示,安装不成功。记起原来找文档时在index.html里面看到有这么一句话:The final caveat to this is that as the j2me distribution includes some compatibility classes starting in the java package, you need to use an obfuscator to change the package names before attempting to import a midlet using the BC API. 似乎因为用于j2me的版本有几个以java开头的包,里面包含了一些兼容类,可能是用于补充CLDC的不足,由于java开头的包是系统包,是不允许修改的,所以不处理过的话安装会失败。必须先用混淆器弄一下才行。Eclipse ME配置混淆器十分简单,我使用的是ProGuard。参照http://www.cnjm.net/eclipseme/docs/configuring.html配置即可。然后运行Create Obfuscated Package生成混淆过的包,只有13K。安装在Nokia 6681上,成功,运行,也成功了。尝试修改一下MIDPTest.java,在whichCipher方法里面,把返回值改为其他数字(0-4),就可以修改加密方式,但是由于DES加密使用的密钥长度为64bit,而默认的key是"0123456789abcdef0123456789abcdef",运行DES是会提示密钥太长,我开始以为把key改为4个字符就可以(因为Java使用Unicode,每个字符2字节,4个字符8字节=64bit),却出现了数组越界的异常,其实这个key并不是直接用作密钥,还要经过处理的。尝试了8个字符也不行,最后发现16个字符就可以了,应该是每两个字符对应一个16进制数。测试程序是对“www.bouncycastle.org”这个字符串进行加密和解密,速度还是挺快的,几乎感觉不到需要时间(在手机上启动Java程序本来就比较慢)。

中间还碰到一个问题,由于我是把源代码直接复制到一个原来建立好的MIDP项目里,那个MIDP项目里已经有个默认的JAD文件,但是里面没有表示要运行的Midlet,生成Jar包之后,安装到手机上到最后会出现安装文件无效的提示。打开那个JAD文件,在Midlets标签里点击Add按钮,把org.bouncycastle.crypto.examples.MIDPTest添加进去即可。

以上测试使用的环境是:
JDK 1.5.02
Eclipse 3.2.0
Eclipse ME 1.7.7 http://eclipseme.org
Sun WTK 2.5.2 for CLDC
ProGuard 4.1 http://proguard.sourceforge.net/



刚刚发现Bouncy Castle的下载页面 http://www.bouncycastle.org/latest_releases.html里面有专用于J2ME的源代码发行包,里面只包含用于J2ME的代码,如果仅用在J2ME下的话,这个应该比较简单,不用找半天。
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
以下是一个 Java 使用 Bouncy Castle 库实现 GPG 加密的示例代码: ```java import java.io.*; import java.security.*; import java.security.spec.InvalidKeySpecException; import java.util.*; import java.util.zip.*; import org.bouncycastle.bcpg.*; import org.bouncycastle.bcpg.attr.*; import org.bouncycastle.openpgp.*; import org.bouncycastle.openpgp.operator.*; import org.bouncycastle.openpgp.operator.bc.*; public class GpgEncrypt { public static void main(String[] args) throws Exception { Security.addProvider(new BouncyCastleProvider()); String publicKeyPath = "/path/to/public/key.asc"; String outputFilePath = "/path/to/output/file.gpg"; String inputFilePath = "/path/to/input/file.txt"; FileInputStream publicKeyInputStream = new FileInputStream(publicKeyPath); PGPPublicKey publicKey = readPublicKey(publicKeyInputStream); FileOutputStream outputStream = new FileOutputStream(outputFilePath); encryptFile(outputStream, inputFilePath, publicKey); outputStream.flush(); outputStream.close(); publicKeyInputStream.close(); } private static PGPPublicKey readPublicKey(InputStream inputStream) throws IOException, PGPException { PGPObjectFactory pgpObjectFactory = new PGPObjectFactory(PGPUtil.getDecoderStream(inputStream)); PGPPublicKeyRing publicKeyRing = (PGPPublicKeyRing) pgpObjectFactory.nextObject(); PGPPublicKey publicKey = publicKeyRing.getPublicKey(); if (publicKey == null) { throw new IllegalArgumentException("Public key not found in the key ring."); } return publicKey; } private static void encryptFile(OutputStream outputStream, String inputFilePath, PGPPublicKey publicKey) throws IOException, NoSuchProviderException, PGPException { PGPCompressedDataGenerator compressedDataGenerator = new PGPCompressedDataGenerator(CompressionAlgorithmTags.ZIP); PGPUtil.writeFileToLiteralData(compressedDataGenerator.open(outputStream), PGPLiteralData.BINARY, new File(inputFilePath)); JcePGPDataEncryptorBuilder dataEncryptorBuilder = new JcePGPDataEncryptorBuilder(SymmetricKeyAlgorithmTags.AES_256).setSecureRandom(new SecureRandom()); PGPEncryptedDataGenerator encryptedDataGenerator = new PGPEncryptedDataGenerator(dataEncryptorBuilder); encryptedDataGenerator.addMethod(new BcPublicKeyKeyEncryptionMethodGenerator(publicKey)); OutputStream encryptedOutputStream = encryptedDataGenerator.open(compressedDataGenerator.open(outputStream), new byte[PGPUtil.BUFFER_SIZE]); compressedDataGenerator.close(); OutputStream armoredOutputStream = new ArmoredOutputStream(encryptedOutputStream); armoredOutputStream.flush(); armoredOutputStream.close(); encryptedOutputStream.close(); } } ``` 该代码使用 Bouncy Castle 库中的类实现了 GPG 的加密功能,具体实现方式如下: 1. 读取公钥:从指定的文件中读取 GPG 公钥,将其转换为 `PGPPublicKey` 实例。 2. 加密文件:使用 `PGPCompressedDataGenerator` 将要加密的文件进行 Zip 压缩,然后使用 `PGPEncryptedDataGenerator` 和 `BcPublicKeyKeyEncryptionMethodGenerator` 将压缩后的数据加密并写入输出流中。 3. 输出加密数据:使用 `ArmoredOutputStream` 将加密数据转换为 ASCII 码格式,并将其写入输出流中。 通过以上步骤,即可实现 GPG 加密并输出加密数据。同时,解密时也需要使用 Bouncy Castle 库中的类进行解密操作。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值