我使用JNA访问SocketCAN。但是我遇到了setsockopt函数的问题。
功能声明:
java.specification.version
SocketCAN使用以下结构:
int setsockopt(int sockfd, int level, int optname, const void *optval, socklen_t optlen);
可以设置一个过滤器,其中一个can_filter结构作为参数,或者多个具有can_filter结构数组的过滤器。
来自SocketCAN的示例:
struct can_filter {
canid_t can_id;
canid_t can_mask;
};
如果我将一个结构的函数定义为JNA中的参数,那么它运行没有问题:
struct can_filter rfilter[2];
rfilter[0].can_id = 0x123;
rfilter[0].can_mask = CAN_SFF_MASK;
rfilter[1].can_id = 0x200;
rfilter[1].can_mask = 0x700;
setsockopt(s, SOL_CAN_RAW, CAN_RAW_FILTER, &rfilter, sizeof(rfilter));
如果我为结构数组定义函数,那么我在init处得到一个错误:
private static native int setsockopt(int sockfd, int level, int option_name, CanFilterStruct filter, int len);
发生错误:
private static native int setsockopt(int sockfd, int level, int option_name, CanFilterStruct[] filters, int len);
这里是JNA中结构的定义:
Exception in thread "main" java.lang.ExceptionInInitializerError
at de.comp.test.App.main(App.java:42)
Caused by: java.lang.IllegalArgumentException: class [Lde.comp.jsocketcan.CanFilterStruct; is not a supported argument type (in method setsockopt in class de.comp.jsocketcan.SocketCan)
at com.sun.jna.Native.register(Native.java:1463)
at com.sun.jna.Native.register(Native.java:1396)
at com.sun.jna.Native.register(Native.java:1156)
at de.comp.jsocketcan.SocketCan.<clinit>(SocketCan.java:70)
有人可以帮助我吗?
祝你好运
答案 0 :(得分:0)
使用Structure.toArray()
获取连续分配的结构块,然后传入第一个元素。
修改强>
您的参数类型仍为CanFilterStruct
。
显式:
CanFilterStruct s = new CanFilterStruct();
CanFilterStruct[] array = (CanFilterStruct[])s.toArray(length);
lib.setsockopt(sock, SOL_CAN_RAW, CAN_RAW_FILTER, array[0], array.length * array[0].size());