动态库和静态库那些事

动态库和静态库那些事,第1张

文章目录
  • 前言
  • 一、静态库使用中的一些坑
  • 二、动态库使用中的坑和注意事项,规避等
  • 三、项目中的动态库静态库常用基本问题


前言

经常使用到arm架构下静态库(.a)和动态库(.so),在使用过程中踩到不少坑,以此写下经鄙人验之谈,和需要了解和 学习的人一起互相学习。持续跟进追加,希望有一些我没有遇到的,欢迎补充。
(该行文内容使用在Makefile中,针对CMake部分后陆续更新)

一、静态库使用中的一些坑

链接顺序问题
1)第一种方式使用Xlinker解决,例如

LIBS += foot.a
LIBS += bar.a
${LD} 其他选项等略 -Xlinker "-(" $(LIBS) -Xlinker "-)"

2)另外一种方法为当静态库调用比较少时, 可以使用foot.a bar.a foot.a方式,即交换位置方式, 该方式不推荐,可以当做测试使用。

LIBS += foot.a
LIBS += bar.a
LIBS += foot.a
二、动态库使用中的坑和注意事项,规避等

c++调用c
如果c中的接口(一般为h文件)没有添加如下

#ifndef __cplusplus
extern "C" {
#endif

void footfunc(const struct *IN, struct *OUT);
#ifndef __cplusplus
}
#endif

会导致链接错误,解决方式一种是接口中增加上面预编译代码段,如果对方没有提供源码,需要在调用方使用 如上代码包裹。

c文件名重命名cpp后缀
有时候使用第三方的库和demo(c实现),但需要在demo中增加c++的接口库实现,比如libjson库,librtsp等, 将c文件重命名cpp文件,出现一系列的问题(c++语法严谨,可能会修改一些不严谨才能通过编译)。另外一个问题就是c中接口(通常为.h文件)增加如下的预编译段需要删除,只保留接口。
项目: HI3519A venc RTSP推流

extern "C" {
#endif

void footfunc(const struct *IN, struct *OUT);
#ifndef __cplusplus
}
#endif

一些低级错误导致
比如有时候批量修改某些变量等,部分没有修改对,导致编译错误。

源文件编译动态库增加-fPIC

@$(CPP) $(CPPOPTS) -fPIC $(DEFINES)
三、项目中的动态库静态库常用基本问题

1)运行可执行文件报如下error cannot open shared object file: No such file or directory,解决方案是在运行的当前shell中增加动态库的路径(改路径一般为用户自定义的位置,非系统路径)

export LD_LIBRARY_PATH=$LD_LIBRARY_PATH:${需要链接的动态库绝对路径}

2)当不清楚可执行文件调用了哪些库,可以使用ldd 可执行文件方式查看使用了哪些.so(动态库),该方式也可以看出没有链接到哪些动态库,如下可以看出来一些库是没有被链接,可通过系统搜索对应的动态库 find . -name librealsense2.so.2.49,然后使用1)中的方式装载。

ldd 你的可执行文件
linux-vdso.so.1 (0x0000007f8c558000)
	libMvCameraControl.so => /opt/MVS/lib/aarch64/libMvCameraControl.so (0x0000007f8c144000)
	librealsense2.so.2.49 => not found
	libMVbotdolly.so => not found
	libBaseAlgSDK.so => not found
	libmaxvision_algorithm_sdk_aarch64.so => not found
	libmax_thread.so => not found
	libmem_manager.so => not found
	librtspserver.so => not found
	libv4l_cap.so => not found
	libjetsonmedia.so => not found
	libopencv_core.so.4.5 => not found
	libopencv_imgcodecs.so.4.5 => not found
	libopencv_imgproc.so.4.5 => not found
	libopencv_videoio.so.4.5 => not found
	libpthread.so.0 => /lib/aarch64-linux-gnu/libpthread.so.0 (0x0000007f8c0f5000)
	libz.so.1 => /lib/aarch64-linux-gnu/libz.so.1 (0x0000007f8c0c8000)
	libstdc++.so.6 => /usr/lib/aarch64-linux-gnu/libstdc++.so.6 (0x0000007f8bf34000)
	libm.so.6 => /lib/aarch64-linux-gnu/libm.so.6 (0x0000007f8be7b000)
	libgcc_s.so.1 => /lib/aarch64-linux-gnu/libgcc_s.so.1 (0x0000007f8be57000)
	libc.so.6 => /lib/aarch64-linux-gnu/libc.so.6 (0x0000007f8bcfe000)
	/lib/ld-linux-aarch64.so.1 (0x0000007f8c52c000)
	libGCBase_gcc48_v3_0.so => /opt/MVS/lib/aarch64/libGCBase_gcc48_v3_0.so (0x0000007f8bcd5000)
	libGenApi_gcc48_v3_0.so => /opt/MVS/lib/aarch64/libGenApi_gcc48_v3_0.so (0x0000007f8b835000)
	libXmlParser_gcc48_v3_0.so => /opt/MVS/lib/aarch64/libXmlParser_gcc48_v3_0.so (0x0000007f8b6da000)
	libdl.so.2 => /lib/aarch64-linux-gnu/libdl.so.2 (0x0000007f8b6c5000)
	libMathParser_gcc48_v3_0.so => /opt/MVS/lib/aarch64/libMathParser_gcc48_v3_0.so (0x0000007f8b6ab000)
	libLog_gcc48_v3_0.so => /opt/MVS/lib/aarch64/libLog_gcc48_v3_0.so (0x0000007f8b692000)
	libNodeMapData_gcc48_v3_0.so => /opt/MVS/lib/aarch64/libNodeMapData_gcc48_v3_0.so (0x0000007f8b668000)

3)一些压缩包打包经过win系统,软连接会失效,压缩包尽量在linux下同下解压缩,不然只能一个个采用ln -s的方式做头疼的事情了。
4)做文件系统等,如果静态库比较多,软连接也比较多, 尽量做成压缩包方式,脚本中尽量不要做ln -s的事情。
5)关于使用动态库还是静态库, 如果是测试可执行,简单 *** 作无需过多安装,使用静态库方式, 否则使用动态库。

欢迎分享,转载请注明来源:内存溢出

原文地址: http://outofmemory.cn/langs/1295964.html

(0)
打赏 微信扫一扫 微信扫一扫 支付宝扫一扫 支付宝扫一扫
上一篇 2022-06-10
下一篇 2022-06-10

发表评论

登录后才能评论

评论列表(0条)

保存