springboot环境下java调用c程序生成动态链接库(.so文件),并调用(基于JNI,Ubuntu)

(237) 2024-01-19 18:01:03

参考文档:

springboot环境下java调用c程序生成动态链接库(.so文件),并调用(基于JNI,Ubuntu)

写得比较详细,但是在实践过程中还是遇到了很多问题,所以在此记录我的过程

代码还是传到GitHub上:https://github.com/SAGE-likeWu/jni_example


项目整体结构如下:注意so文件的位置

springboot环境下java调用c程序生成动态链接库(.so文件),并调用(基于JNI,Ubuntu) (https://mushiming.com/)  第1张

1.项目搭建

具体操作就不详细写了,简单的mvc结构,主要是为了跑通。

config:配置类

controller:web的api接口

dto:传输对象

service:服务层,逻辑处理

2.生成.so文件

jni:创建.so文件的对接类,为了测试跑通只是一个简单的整数加法

springboot环境下java调用c程序生成动态链接库(.so文件),并调用(基于JNI,Ubuntu) (https://mushiming.com/)  第2张

然后就是javah生成包含可以和java对接的c接口

具体操作写在了另一篇博客(这一步是最坑的,参考的那篇文档也没有说清楚):

springboot环境下java调用c程序生成动态链接库(.so文件),并调用(基于JNI,Ubuntu)

生成头文件后:将头文件移动到native文件夹下(jni.h无所谓,可以忽略,放在这里没什么用,除非改改头文件里#include "jni.h")

springboot环境下java调用c程序生成动态链接库(.so文件),并调用(基于JNI,Ubuntu) (https://mushiming.com/)  第3张

然后写add.c文件,就是写头文件里的接口

#include "com_zk_demo_jni_AddJni.h"
JNIEXPORT jint JNICALL Java_com_zk_demo_jni_AddJni_Add
  (JNIEnv * env, jclass jc, jint x, jint y){
    return x+y;
  }

最后编译生成.so文件:jni.h文件就在jdk的include里,所以这里需要指明它的位置,注意替换为你自己jdk的路径

sudo gcc -fPIC -I ~/jdk1.8.0_191/include -I ~/jdk1.8.0_191/include/linux -shared -o libadd.so add.c 

springboot环境下java调用c程序生成动态链接库(.so文件),并调用(基于JNI,Ubuntu) (https://mushiming.com/)  第4张

3.在spring boot调用.so文件

util:工具类,NativeLaoder是网上的一个在项目中加载.so文件的类

springboot环境下java调用c程序生成动态链接库(.so文件),并调用(基于JNI,Ubuntu) (https://mushiming.com/)  第5张

调用过程:在service中需要调用定义的c方法时,

先加载, NativeLoader.loader( "native" );(红框1)

然后再调用java与c的对接类:(红框2)

springboot环境下java调用c程序生成动态链接库(.so文件),并调用(基于JNI,Ubuntu) (https://mushiming.com/)  第6张

4.运行效果

浏览器打开

http://localhost:8080/swagger-ui.html#

调用add函数,

springboot环境下java调用c程序生成动态链接库(.so文件),并调用(基于JNI,Ubuntu) (https://mushiming.com/)  第7张

返回:成功跑通

springboot环境下java调用c程序生成动态链接库(.so文件),并调用(基于JNI,Ubuntu) (https://mushiming.com/)  第8张

后台过程

springboot环境下java调用c程序生成动态链接库(.so文件),并调用(基于JNI,Ubuntu) (https://mushiming.com/)  第9张

后续

这是在运行过程中动态加载,我看到过一篇博客说可以在项目启动时加载,具体是否需要这样设置看我后续的需求吧。

总之,终于跑通了。

 

 

THE END

发表回复