Chinaunix首页 | 论坛 | 博客
  • 博客访问: 277796
  • 博文数量: 83
  • 博客积分: 2393
  • 博客等级: 大尉
  • 技术积分: 640
  • 用 户 组: 普通用户
  • 注册时间: 2006-04-24 15:14
文章分类

全部博文(83)

文章存档

2019年(21)

2011年(5)

2010年(2)

2009年(1)

2008年(9)

2007年(33)

2006年(12)

我的朋友

分类: Java

2007-07-22 20:34:02

因项目需要说要使用一个由c编写的动态作为加密算法进行调用因此提前学习一下jni的使用方法,在网上也搜索到了不少资料,不过有好多资料差不多都一样的,看资料挺简单的不过用真正写个例子确实出现了不少问题,我用的环境是solaris就是
因为是测试的学习的例子所以写的不是很规范不过例子是可以使用的,以下是java的代码,以下代码只表示调用和编写的基本方法,没有什么实际的意义。
 
 

public class testparam
 {

/*定义加载的动态连接库的名称在这里的param名称对应的是系统库名称是libparam.so使用的动态库方式*/
         static {
                 System.loadLibrary("param");
         }

      //定义调用的本地方法,
         public native void sayworld(byte[] msg);
         public native byte[] getmsg();

         
         public String getreturnmsg(){
                 byte[] msg=getmsg();
                 String rs=new String(msg);
                 return rs;
         }
         public void saymsg(String msg){
                 byte[] msgbyte=msg.getBytes();
                 byte[] temp={0};
                 byte[] param=new byte[msgbyte.length+temp.length];
                 System.arraycopy(msgbyte,0,param,0,msgbyte.length);
                 System.arraycopy(temp,0,param,msgbyte.length,temp.length);

                 sayworld(param);
         }
         public static void main(String args[]){
                 testparam p=new testparam();
                 p.saymsg("hello world!");
                 p.saymsg("hello world!\n");
                 p.saymsg("heheheheheheheheheheheheheheheheheheheheheheheeheheheh\t\b\n\r");
                 String abc=p.getreturnmsg();
                 System.out.println(abc+":getmsg()");
         }
 }

 

使用javac名称对上述文件进行编译生成class文件,然后使用javah命令使用class文件生成.h头文件,生成的头文件如下:

 

/* DO NOT EDIT THIS FILE - it is machine generated */
 #include <jni.h>
 /* Header for class testparam */

 #ifndef _Included_testparam
 #define _Included_testparam
 #ifdef __cplusplus
 extern "C" {
 #endif
 /*
  * Class: testparam
  * Method: sayworld
  * Signature: ([B)V
  */

 JNIEXPORT void JNICALL Java_testparam_sayworld
   (JNIEnv *, jobject, jbyteArray);

 /*
  * Class: testparam
  * Method: getmsg
  * Signature: ()[B
  */

 JNIEXPORT jbyteArray JNICALL Java_testparam_getmsg
   (JNIEnv *, jobject);

 #ifdef __cplusplus
 }
 #endif
 #endif

 

根据.h文件中的方法定义开始编写.c文件,.c文件的内容如下:

 

#include "testparam.h"
 #include "jni.h"
 #include <stdio.h>
  JNIEXPORT void JNICALL Java_testparam_sayworld
    (JNIEnv *env, jobject obj, jbyteArray msg)
 {
         jbyte *msgarr=(*env)->GetByteArrayElements(env,msg,0);
         char * chmsg=(char *)msgarr;
         printf("%s\n",chmsg);
 }
 JNIEXPORT jbyteArray JNICALL Java_testparam_getmsg
   (JNIEnv *env, jobject obj)
 {
         char *b="aaaaaaaaaaaaaaa";
         jbyteArray abc= (*env)->NewByteArray(env,10);
         (*env)->SetByteArrayRegion(env,abc,0,10,(const signed char*)b);
         return abc;
 }

 

使用如下命令进行编译.c文件使其生成目标文件,其中paramfun.c为上边的c文件名称

cc -c paramfun.c -I/usr/jdk/instances/jdk1.5.0/include -I/usr/jdk/instances/jdk1.5.0/include/solaris

 

在生成目标文件后,使用如下命令生成动态库文件:

 

cc -o libpara.so -G paramfun.o

至此动态连接库生成可以运行java的class进行调用察看运行结果

使用如下命令运行,

 

java -Djava.library.path=. testparam

由于编译生成的动态连接文件在当前目录下所以需要制定java的java.library.path目录,从当前目录开始加载动态库文件

阅读(1329) | 评论(1) | 转发(0) |
0

上一篇:jni实践

下一篇:aix系统设置nfs服务

给主人留下些什么吧!~~