【发布时间】:2012-04-10 01:45:32
【问题描述】:
在过去几年中,我们创建了一个使用 X25 协议的程序。它是用 C 语言制作的,适用于装有 Solaris 5.9 的 Sun-Fire 机器。
最近,我们正在同一台机器上使用 java 6,我们正在尝试调整 C 中的旧程序以通过 jni 使用 java。
所以我对旧的C程序做了一些修改,并创建了一个名为x25lib.so的共享库
但是我在使用 jni 和 X25 时发现了一个运行时问题:当通过 jni 从 java 调用 C 函数时,C 代码的工作方式与从另一个 C 程序调用时不同。
具体来说,使用jni,共享库中的C代码可以正常工作,直到调用系统调用connect(),然后返回-1,
但是从另一个 C 程序调用我的共享库的相同 C 代码返回 0(ok)
在这两种情况下,共享库中的 C 代码都没有接收外部参数,所以条件是一样的,我不明白从 java 加载我的“x25lib.so”共享库是否有一点不同会导致@ C 中的 987654323@ 失败。
使用 java 中的“truss”命令我发现了错误:
/2: connect(5, 0xFD878B75, 112, 1) Err#22 EINVAL
相同,但从另一个 C 程序调用共享库:
connect(4, 0xFFBFE794, 114, 1) = 0
所以它只适用于纯 C,
在 solaris 5.9 中使用 jni 和 X25 是否还有其他注意事项?
重要提示:共享库中的 C 代码在两种情况下都是相同的。
编译时间:
一个。创建x25lib.so
cc -w -fd -G -Kpic subs.o -L/opt/SUNWconn/lib -R/opt/SUNWconn/lib -lsockx25
-lsocket -lnsl -I"/SDK/jdk/include/" -I"/SDK/jdk/include/solaris/"
-o x25lib.so -h x25lib.so x25jni.c
b.使用该共享库创建测试 C 程序:
cc -w x25lib.so -o x25test x25test.c
where `x25test.c` contains:
#include <stdio.h>
main()
{
java_x25();
}
c。使用java:
public class X25 {
static {
System.load("/home/x25lib.so");
}
public native void ejecutaComando();
}
public class TestX25 {
public static void main(String ... args) {
X25 x25 = new X25();
x25.ejecutaComando();
}
}
然后在C代码共享库中:
/*
* Class: X25
* Method: ejecutaComando
* Signature: ()V
*/
JNIEXPORT void JNICALL Java_X25_ejecutaComando
(JNIEnv *env, jobject obj)
{
java_x25();
}
所以最后两个程序(java y C)在共享库中调用完全相同的 C 代码:
java_x25()
没有参数,所以执行相同的代码。
为什么从 C 调用时运行良好,从 java 调用时失败?
感谢您的建议。
【问题讨论】:
-
您确定您的独立“C”代码与您的 JNI 代码相同吗?
-
感谢您的回答 EJP。是的,代码是相同的,这是我的挫败感。我编辑了我的问题并添加了 jni 代码,您可以看到它被调用的代码与独立 C 代码中的代码相同。
标签: java java-native-interface solaris