一种实现 Java调用C++的DLL的方法

Posted on 2012-03-15 18:14  无忧consume  阅读(271)  评论(0编辑  收藏  举报

http://topic.csdn.net/t/20020917/14/1030420.html 

感谢大家支持,这几天我在IBM中文及SUN官方网站中找了不少关于JNI的文章,受益非浅,希望有相关问题的朋友,可到那找查相关资料.   
    
  1)在   Windows   中实现   Java   本地方法   
  http://www-900.ibm.com/developerWorks/cn/java/jnimthds/index.shtml   
  2)Java   Native   Interface:   Programmer's   Guide   and   Specification     
  http://java.sun.com/docs/books/jni   
    
  上面的文章对JNI介绍非常详细,对JNI有性趣的朋友可以看看.   
    
  对于我提出的问题,我己有了成功例子,贴出来与大家分享.   
  有一myDll.dll库,接口Trim(LPSTR   lpString),功能是把lpString中的空格去掉。文件原码   
    
  如下:   
  #include   <string.h>   
  #include   <windows.h>   
    
  #ifdef   _cplusplus   
  extern   "C"{   
  #endif   
  __declspec(dllexport)   void   Trim(LPSTR   lpString)   
  {   
  int   iLength   =   strlen(lpString);   
  int   iCount   =   0;   
  char   *lpChar   =   lpString;   
  int   i;   
  for(i=0;i<iLength;i++)   
  {   
  if(   *lpChar   !=   '   '   )   
  {   
  lpString[   iCount   ]   =   *lpChar;   
  iCount   ++;   
  }   
  lpChar   ++;   
  }   
  lpString[iCount   ++]   =   0;   
  }   
    
  #ifdef   _cplusplus   
  }   
  #endif   
    
  (用VC6的cl编译该文件生成动态链接库,cl   -LD   myDll.c   -FemyDll.dll   )   
    
  这里假设我们不能得到该动态链接库的原代码,只有DLL及LIB文件,在通过JNI用java调用时   
    
  ,由于没有DLL原代码修改权限,需要我们自己用C/C++再做一个中介库DLL2,java调用这个   
    
  中介库,该中介库再调用原如的DLL库,间接实现java本地方法的调用。   
  下面是我做的例子,环境:Win2000Server,JDK1.3,VC6.0   
    
  先编一个java程序,java2dll.java,代码如下:   
  public   class   Java2dll   
  {   
    
    
    
    
  //声明要用到的本地方法cTrim由中介库(java2dll.dll)实现,它又调用了myDll.dll库的T   
    
  rim(...)函数   
  private   native   String   cTrim(String   str);   
  static   
  {   
  System.loadLibrary(   "java2dll"   );     //加载本地方法(java2dll为动态   
    
  链接库文件名)   
  }   
    
  //自己定义的一个java方法,调用本地方法cTrim(),有点多余,实际上你可直接访   
    
  问本地方法cTrim()   
  public   String   javaTrim(String   str)   
  {   
  return   cTrim(str);   
  }   
    
  //演示结果   
  public   static   void   main(String[]   args)   
  {   
  Java2dll   ss   =   new   Java2dll();   
  String   str1="I   love   You.";   
  String   str2=ss.javaTrim(str1);   
  System.out.println("调用c   DLL前:");   
  System.out.println("str1="+str1);   
  System.out.println("调用c   DLL后:");   
  System.out.println("str2="+str2);   
  }   
  }   
    
  编译该文件,生成Java2dll.class文件:     
  javac   Java2dll.java   
  生成C的头文件Java2dll.h:       
  javah   -jni   Java2dll   
    
  用C编写中介库java2dll.c   
  #include   <stdio.h>   
  #include   "java2dll.h"   
    
  JNIEXPORT   jstring   JNICALL   Java_Java2dll_cTrim   
    (JNIEnv   *env,   jobject   obj,   jstring   str)   
  {   
  const   char   *strTemp;   
  strTemp=(*env)->GetStringUTFChars(env,str,NULL);   
  //错误出现时   
  if(strTemp==NULL)   
  {   
  return   NULL;   
  }   
    
  //调用myDll.dll库中的Trim()方法,去掉strTemp中的空格   
  Trim(strTemp);   
  return   (*env)->NewStringUTF(env,   strTemp);   
    
  (*env)->ReleaseStringUTFChars(env,str,strTemp);   
  }   
  说明:如果你用C++编写,cpp文件,上面代码中的“(*env)”应改为“env”   
    
  编译生成java2ddl.dll文件。   
  用VC6的cl编译。   
  cl   -Id:\jdk13\include   -Id:\jdk13\include\win32   -LD   java2dll.c   myDll.lib   -Fejava2dll.dll   
  说明:-Id:\jdk13\include指明JNI需要的头文件.h位置,D:\JDK13为我的JDK安装目录   
  -LD   表明要生成动态链接库     
  myDll.lib或   -link     
    
  myDll.lib表明要把myDll.dll链接上,否则中介库java2dll找不到Trim(..)方法。   
  您可用cl   /?得到HELP帮助。   
    
  编译成功后,可得到中介库java2dll,运行一下,检查结果。   
  java   Java2dll   
    
  好了,你自己试一下吧。

Copyright © 2024 无忧consume
Powered by .NET 9.0 on Kubernetes