当前位置:编程学习 > JAVA >>

j2me下bouncycastle加密的问题,困扰很久了!

 

做j2me下数据加密的测试,在网上搜寻到的代码:J2ME上实现对数据的DES加密.pdf,按着该文档里面的代码在Eclipse下:

1、新建一个工程如jiami,设置java文件目录于src下,E:\workspace\jiami\src\jiami.java
2、导入lcrypto-j2me-145.zip,把lcrypto-j2me-145.zip解压后看到里面有zips文件夹,按教材把他里面的cldc_crypto.zip解压,得到java和org个文件,然后把这2个文件夹复制到刚才的src下,在工程里选择project--properties--J2ME--Java Build Path--Libraries--Add External Class Folder,然后选择刚才src目录,这样就将用到的相关class导入到工程中。
3、编写代码,代码完成后在Eclipse没有任何错误提示,但就是在运行时在console提示错误:
Running with storage root C:\Documents and Settings\steelyoung\j2mewtk\2.5.2\appdb\DefaultColorPhone
Running with locale: Chinese_People's Republic of China.936
Running in the identified_third_party security domain
No audio device found.
Key:111111111
Text:11111111
java.lang.NoClassDefFoundError: org/bouncycastle/crypto/BlockCipher
 at jiami.DESExe(+91)
 at jiami.commandAction(+29)
 at javax.microedition.lcdui.Display$DisplayAccessor.commandAction(+282)
 at javax.microedition.lcdui.Display$DisplayManagerImpl.commandAction(+10)
 at com.sun.midp.lcdui.DefaultEventHandler.commandEvent(+68)
 at com.sun.midp.lcdui.AutomatedEventHandler.commandEvent(+47)
 at com.sun.midp.lcdui.DefaultEventHandler$QueuedEventHandler.handleVmEvent(+186)
 
 按提示是找不到BlockCliher这个class文件,但不论我怎样导入含有这个class的包或者文件,每次运行都是同样的错误,在工程确实是有这个BlockCipher.class的,真不知道在哪里错了,我在文件头部写上import org.bouncycastle.crypto.BlockCipher.*;Eclipse确提示The import org.bouncycastle.crypto.BlockCipher is never used。
 
 以下是源代码(Eclipse下没有任何错误提示),请高手帮忙看看哪里错了!这个问题困扰一个星期了,在网上也搜寻了答案,就是没有解决办法!

 

 

jiami.java

 

import javax.microedition.midlet.*;
import javax.microedition.lcdui.*;
import org.bouncycastle.crypto.*;
import org.bouncycastle.crypto.engines.*;
import org.bouncycastle.crypto.modes.*;
import org.bouncycastle.crypto.params.*;

 

public class jiami extends MIDlet implements CommandListener{
   private Display m_display;
   private Command cmdExit;
   private Command cmdEncrypt;
   private Form m_DisForm;
   private TextField m_KeyText;
   private TextField m_OriginalText;
   private TextField m_EncyptText;
   private TextField m_DecyptText;
 public jiami() {
  m_display = Display.getDisplay(this);
  cmdEncrypt = new Command("cmdEncrypt", Command.OK, 2);
     cmdExit = new Command("Exit", Command.EXIT, 1);
     m_KeyText = new TextField("Key","",50,TextField.ANY);
     m_OriginalText = new TextField("原文","",50,TextField.ANY);
     m_EncyptText = new TextField("加密后","",50,TextField.ANY);
     m_DecyptText = new TextField("解密后","",50,TextField.ANY);
     m_DisForm = new Form("加密解密");
     m_DisForm.addCommand(cmdEncrypt);
     m_DisForm.addCommand(cmdExit);
     m_DisForm.append(m_KeyText);
     m_DisForm.append(m_OriginalText);
     m_DisForm.append(m_EncyptText);
     m_DisForm.append(m_DecyptText);
     m_DisForm.setCommandListener(this);
 }

 protected void destroyApp(boolean arg0) {
 }
 protected void pauseApp() {
 }
 protected void startApp() {
  m_display.setCurrent(m_DisForm);
 }
 public void commandAction(Command cmd,Displayable disp){
  if(cmd ==cmdExit){
   destroyApp(false);
   notifyDestroyed();
   }
  if(cmd == cmdEncrypt){
   DESExe();
  }
 }

 private void DESExe(){
   String Text = "";
   String Key;
   byte[] msg;
   String strMsg;
   Key = m_KeyText.getString();
   Text = m_OriginalText.getString();
   System.out.println("Key:"+Key);
   System.out.println("Text:"+Text);
   if(Key.equals("")||Text.equals("")){
    m_KeyText.setString("请输入密钥,原文!");
    return;
  }

  Encryptor encryptor =  new Encryptor(Key);
  try{
   msg = encryptor.encryptString(Text);
   strMsg = new String(msg,0,msg.length);
   System.out.println("encode:"+strMsg);
    m_EncyptText.setString(strMsg);
    strMsg = encryptor.decryptString(msg);
    System.out.println("decode:"+strMsg);
    m_DecyptText.setString(strMsg);
  }
  catch(Exception e){
  }

  }
 //封装类
 public class Encryptor {
  private BufferedBlockCipher cipher;
  private KeyParameter key;
  public Encryptor(byte[] key){
   cipher = new BufferedBlockCipher(
                 new CBCBlockCipher(
                 new BlowfishEngine() ) );
   this.key = new KeyParameter(key);

  }
  public Encryptor(String key){
   this(key.getBytes());
  }

  private byte[] callCipher(byte[] data) throws CryptoException {
   int size = cipher.getOutputSize(data.length);
   byte[] result = new byte[size];
   int olen = cipher.processBytes(data,0,data.length,result,0);
   olen += cipher.doFinal(result,olen);
   if(olen< size){
    byte[] tmp = new byte[olen];
    System.arraycopy(result,0,tmp,0,olen);
    result = tmp;
   }
   return result;
 }
 //加密数据
 public synchronized byte[] encrypt (byte[] data) throws CryptoException{
  if(data == null || data.length == 0){
   return new byte[0];
  }
  cipher.init(true,key);
   return callCipher(data);
 }
 //加密一个串
 public byte[] encryptString(String data) throws CryptoException {
  if(data == null || data.length()==0){
   return new byte[0];
  }
  return encrypt(data.getBytes());
 }
 //解密数据
 public synchronized byte[] decrypt(byte[] data) throws CryptoException{
  if(data == null || data.length==0 ){
   return new byte[0];
  }
  cipher.init(false,key);
  return callCipher(data);
 }
 //下面的代码用于解密刚才加密的数据
 public String decryptString(byte[] data) throws CryptoException{
  if(data == null || data.length==0){
   return "";
  }
  return new String(decrypt(data));
 }
 }
}

 
--------------------编程问答-------------------- --------------------编程问答-------------------- 你的问题解决了没啊? --------------------编程问答-------------------- 我最近也遇到这个问题了.. 解决了吗 --------------------编程问答-------------------- 提供一种思路 制作自己的bouncy castle的jar包

7. 使用bouncy castle加解密,运行MIDlet时,提示java.lang.NoClassDefFoundError: java/security/SecureRandom: Cannot create class in system package

制作自己的bouncy castle的jar包
This is indeed a working technique however you won’t be able to use a debug like that->You will either get a security exception and an error or you won’t be able to figure out your code throught all the weird names that the obfuscator uses. And as you know you cannot make a program without debuger. 

There is a far simpler and cleaner solution for this:Create your own bouncy castle. Open your Eclipse IDE (I’ve used eclipse for that I’m sure you can do it with NetBeans too thought).

The whole problem with bouncy castle that make obfuscating neccessary is that is has two packages under tha java name. 

java.security
 Java.math

Why the did that is a little bit unclear to me (they claim compatibility reasons in their FAQ).So we are going to change these names. 

Create a new JavaME project in eclipse. Right click on the source folder and select Import->File System. Select the folder that contains bouncy’s castle source code(it’s in the src folder of where you unzipped your bouncy caslte). Click import. Now you see all bouncy’s castle packages which contain the .java files. Our two illegal packages should be on the top. 

Right click on java.security and java.math(they contain the SecureRandom.java and the BigInteger.Java). Select Refactor->Rename. Now give your new name of the package. Let’s say javafake.security and javafake.math. The “update references” and update subpackages should be ticked. This will automaticly rename alla the references to your new name. Click OK. It should give you some warnings but ignore them. 

If it gives you an error due encoding CP1253 go to Window->Preferences->General->Workspace and change the default encoding to UTF-8 and repeat. Now you have your own code time to export it to a jar.

Right clock on the src folder of our package->Export->Jar file and give it a name (e.g mybouncycastle). CLick ok aaaand you are done. 

Now got to your project and simply import your jar. 

Voila : you have your own bouncy castle that doesn’t need any obfuscation or anything. No need to mess with Proguard and security exceptions. On the downside your program is going to be a little bit bigger but at least you would be able to debug. If you find the file to big simply remove whatever packages you don’t use or you can develop your program with debugger and use obfuscator simply for deploying.

Cheers.
补充:Java ,  J2ME
CopyRight © 2012 站长网 编程知识问答 www.zzzyk.com All Rights Reserved
部份技术文章来自网络,