(原文来自:
2006-06-18 尝试了一下用 swig 编写 JNI 程序)
总是觉得编写 JNI (Java Native Interface) 程序是件复杂的事情, 于是开始漫无目的地搜索是否有简单一点的方法, 倒是有些商业软件提供这样的功能, 比如 http://www.jniwrapper.com 就提供了通过 Java 直接调用 DLL 的功能(可惜是商业软件, 哈哈).
搜索中无意到了 swig 的网站( http://www.swig.org ), 看到一个用 swig 产生 Java 模块的例子(原来知道 swig 是因为 python 的缘故), 于是就照着例子自己尝试了一下(比例子稍微复杂一点, 另外我是用 mingw 上的 gcc 进行编译的).
源代码包括 3 个文件, Example.c, Example.i, net/thinkbase/test/Test.java
:
/** Example.c ****************************************************************/
#include <time.h>
/**A variable*/
double
PI =
3.1415927
;
/**Return n!*/
int
fact
(
int
n
) {
if
(
n <=
1
)
return
1
;
else
return
n*fact
(
n-
1
)
;
}
/**mod function*/
int
mod
(
int
x,
int
y
) {
return
(
x%y
)
;
}
/**Get time as String*/
char
* getTime
(){
time_t ltime;
time
(
<ime
)
;
return
ctime
(
<ime
)
;
}
/**to upper case*/
char
* toUpperCase
(
char
* result
){
char
* p = result;
while
(
'\0'
!=*p
){
char
c = *p;
if
( (
c >
'a'
)
&&
(
c <
'x'
) ){
*p = c-
32
;
}
p++;
}
return
result;
}
|
/** Example.i ****************************************************************/
%module Example
%
{
/* Put header files here or function declarations like below */
extern
double
PI;
extern
int
fact
(
int
n
)
;
extern
int
mod
(
int
x,
int
y
)
;
extern
char
* getTime
()
;
extern
char
* toUpperCase
(
char
* str
)
;
%
}
extern
double
PI;
extern
int
fact
(
int
n
)
;
extern
int
mod
(
int
x,
int
y
)
;
extern
char
* getTime
()
;
extern
char
* toUpperCase
(
char
* str
)
;
|
/** net/thinkbase/test/Test.java *********************************************/
package
net.thinkbase.test;
import
net.thinkbase.test.swig.Example;
public class
Test
{
public static
void
main
(
String argv
[]) {
System.loadLibrary
(
"Example"
)
;
System.out.println
(
" Example.getPI() = "
+ Example.getPI
())
;
System.out.println
(
" Example.fact(6) = "
+ Example.fact
(
6
))
;
System.loadLibrary
(
"Example"
)
;
System.out.println
(
" Example.mod(100, 30) = "
+ Example.mod
(
100
,
30
))
;
System.out.println
(
" Example.getTime() = "
+ Example.getTime
())
;
System.out.println
(
" Example.toUpperCase(\"Hello, world!\") = "
+
Example.toUpperCase
(
"Hello, world!"
))
;
}
}
|
试验步骤
建立必要的目录:
mkdir "net/thinkbase/test/swig"
mkdir ".out"
使用 swig 建立相关接口:
swig -java -package net.thinkbase.test.swig -outdir net/thinkbase/test/swig Example.i
编译 c 文件得到 dll:
gcc -c Example.c -o .out/Example.o -I%JAVA_HOME%/include -I%JAVA_HOME%/include/win32
gcc -c Example_wrap.c -o .out/Example_wrap.o -I%JAVA_HOME%/include -I%JAVA_HOME%/include/win32
gcc -shared .out/Example.o .out/Example_wrap.o -mno-cygwin -Wl,--add-stdcall-alias -o .out/Example.dll
编译测试用的 Java 程序:
javac -sourcepath . net/thinkbase/test/Test.java -d .out
运行测试:
java -cp .out -Djava.library.path=.out net.thinkbase.test.Test
运行及测试结果:
源代码可以从这里下载: