【NDK】【004】动态库管理,dll加载原理

这篇博客我们主要讲解,Java程序是如何查找dll的
根据这个查找规则,我们又该如何去管理dll文件,如何修改软件运行参数

Java程序会从哪些地方查找dll文件

  • 当前运行目录:默认为jar包所在目录,或工程代码所在根目录
  • 操作系统的path环境变量:path变量中包括的所有位置都会被查找,我们平时配JDK时,就会用到这个路径,其实就是把JDK中的类库共享给所有Java程序
  • 工程私有的path环境变量:IntelliJ Idea允许我们临时修改环境变量,但是只对当前工程代码生效,对其它工程和程序没有影响,也不会改变操作系统中的配置
  • 程序的库目录:不管是IntelliJ Idea还是Jar包,我们都可以通过Djava.library.path参数来指定dll/so库的查找位置

修改IntelliJ Idea的运行目录和环境变量

通过Run - Edit Configurations可以配置当前工程的运行目录和私有的path环境变量
除了运行目录和环境变量,我们还看到一个VM options,这个相当于jar包启动时的附加参数,比如-Djava.library.path,-Xms,-Xmx等选项,都可以在这里配置
在这里插入图片描述
我们将运行目录和环境变量都设置为C盘根目录
再将dll移动到C盘根目录,程序正常运行,说明参数修改生效
在这里插入图片描述

修改Jar包的库目录

由于Jar包本身就是一个可执行程序,所以它的运行目录就是它自己所在的目录,是不可能修改的

Jar包的库目录可以通过-Djava.library.path参数来指定
以-D开头的参数在Java代码中可以通过System.getProperty方法来获取

我们将代码打包为Jar包,通过-D参数来指定dll的库目录为lib文件夹
Jar包正常运行,说明方法有效

java -jar -Djava.library.path=./lib a.jar

在这里插入图片描述

利用这个原理,我们可以做哪些事情

  • 快速部署。在没有修改过运行目录的情况下,直接把dll扔到jar包同级目录,就可以直接使用了
  • 文件分类管理。在Jar包同级目录新建一个library文件夹,将其设置为库目录,将所有dll都放入此文件夹,就可以达到对库文件进行统一管理的目的。如果有多个jar包,还可以有多个库目录,这样可以对程序文件进行科学管理
  • 修复丢失的库文件。由于操作系统中的path环境变量一般都会包括system32,jdk等文件夹,所以我们只要把dll扔到这些目录下面,就可以被所有的软件共享。这种操作方式我们在Windows软件中也经常见到,一般我们系统缺少某某文件,百度就会告诉我们,下载xxx放入c:/windows/system32下面就行了
  • 建立共享库。我们可以指定一个固定目录,然后公司所有产品都以它作为库目录,这样就达到了资源共享目的。这种方式比较适合大公司,一来大公司组件化做得比较好,组件较多,二来有些组件体积比较大,如果每个软件都带一份,会浪费很多磁盘空间,三来也只有大公司才可能同时在客户的机子上安装多套软件。比如微软的程序,就是很典型的这种模式,很多程序之间是相互依赖的,安装一套软件前,经常需要先安装其它组件。不过由于微软的产品实在太多,版本也多,早期没有科学地进行长远规划,从而引发了一系列的负面效果,比如软件无法卸载干净,版本冲突等问题,有时只能重装系统才能解决。毕竟共享组件容易,但是组件要更新,其它产品也要更新,还要保证一份组件兼容所有产品的所有版本,实在是有点难
  • 搭建私人代码仓库。同样的道理,我们将自己常用的库文件放到一个固定位置,再把这个目录加入到操作系统的path环境变量中,以后其它工程就可以直接使用了,好比我们使用Maven一样
  • 修复编程环境。以上简单介绍了环境变量的几种应用情景,不过最大的收获还是在于,我们弄清了运行目录和环境变量的作用后,就知道如何去查看和修改它们,以后再遇到动态库找不到的问题,就可以思路清楚,轻轻松松地解决了
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章