我正在尝试测试一些集成了Java类和一些ROS功能的JNI代码,而我正在努力使Java方法正确链接。我已经正确地编译了针对JNI接口的本机代码(或者我认为),但是在运行时我得到了UnsatisifiedLinkError
关于我定义的第一个本机方法。此时我不确定根本原因是JVM没有正确加载.so文件(在同一目录中,我已尝试-Djava.library.path=.
)或者如果它已成功加载它并且它是没有正确找到方法。
此错误消息提供的内容很少,有没有办法获得有关究竟是什么导致它的更多信息?
我不反对发布源代码,如果它有帮助,虽然我必须做一些编辑才能上传它所以我等着看你们是否觉得它可能有用。
Talker.java:
public class Talker {
/**
* ROS Native methods
*
* Simple passthrough to the C++ native methods in the ROS layer
*/
private static native void rosAdvertise();
private static native void rosPublish();
private static native void rosSpinOnce();
{
System.loadLibrary("ros-test-native-talker");
}
public static void main(String[] args) {
rosAdvertise();
while (true) {
rosPublish();
try {
Thread.sleep(100);
} catch (InterruptedException e) {
e.printStackTrace();
}
rosSpinOnce();
}
}
}
ROS测试天然-talker.cpp:
#include "test_rostest_Talker.h"
#include "ros/ros.h"
#include "std_msgs/Time.h"
ros::Publisher outbound;
JNIEXPORT void JNICALL Java_test_rostest_Talker_rosAdvertise
(JNIEnv *, jclass) {
int argc = 0;
char **argv;
ros::init(argc, argv, "ros-native-timing-tester");
ros::NodeHandle n;
outbound = n.advertise<std_msgs::Time>("chatter", 1000);
}
JNIEXPORT void JNICALL Java_test_rostest_Talker_rosPublish
(JNIEnv *, jclass) {
ros::Time tx_timestamp = ros::Time::now();
ROS_INFO("Sending message at %d.%d", tx_timestamp.sec, tx_timestamp.nsec);
std_msgs::Time msg;
msg.data = tx_timestamp;
outbound.publish(msg);
}
JNIEXPORT void JNICALL Java_test_rostest_Talker_rosSpinOnce
(JNIEnv *, jclass) {
ros::spinOnce();
}
和输出:
rush@lubuntu64vm:~/javarostest$ java -Djava.library.path=. -cp ros-test-native-1.0-SNAPSHOT.jar test.rostest.Talker
Exception in thread "main" java.lang.UnsatisfiedLinkError: test.rostest.Talker.rosAdvertise()V
at test.rostest.Talker.rosAdvertise(Native Method)
at test.rostest.Talker.main(Talker.java:21)
答案 0 :(得分:0)
我不知道为什么但重构上面的代码会导致它起作用。如果我从主类中取出本机方法并将它们放在一个单独的类中(因此删除本机方法上的静态修饰符),它由主类调用,它们都链接并正常工作。我不确定,甚至不知道为什么,但我认为这些方法的静态修饰符导致了一些问题。