需求:
1. 纯静态编译ffmpeg ,即ldd ./ffmpeg 的结果是:not a dynamic executable
2. 修改ffmpeg 项目,添加自定义功能库
3. 自定义库由c++实现,要求能被纯c的ffmpeg项目调用
4. 自定义库必须使用g++ 的一些高级特性编译,要求g++支持c++11
5. 自定义库使用了pthread库 和openmp 库
6. 自定义库使用了opencv 3.0.0库,
7. 禁用所有的图形显示库x11,xcb,声音设备avdevice等等,静态链接这些库,会很痛苦。
动手之前需要注意:
A. ffmpeg.org (
CentOS或
Ubuntu)的方法是不能达到需求1的,因为它大量使用包管理软件(yum 或apt-get)安装一些ffmpeg的依赖库,而这些依赖库大多是动态版本(.so.*) 。这就使得编译ffmpeg时,无法静态链接这些依赖库。因而,非开发工具(如gcc g++ pkg-config aotoconf etc )的依赖库(如ass,freetype,sdl theora, jpeg png,etc),需要手动下载它们的源码(以及这些依赖库的依赖库),然后编译得到静态库(.a)。一般来说,这些依赖库多数是configure 配置,然后make,make install。
./configure *** --enable-shared=no --enable-static=yes --with-***=/dir
B.自定义功能库也类似于上述方法写好myfunc.cpp,然后g++编译,ar打包成.a。但是由于我们写好的cpp要求c++11特性,而CentOS6.5上的gcc/g++版本为4.4.7不支持c++11。因而,需要安装gcc4.8以上版本。从repo里面无法安装较新的gcc的话,只能自行下载gcc源码,自行编译了。然而发现了一个第三方的编译好的工具链
devtool3,它提供了gcc 4.9.2 以及配套的binutils工具。然而,不要急,先不要安装它,看完本注意事项。
C.要求c++打包的库能够被ffmpeg的项目链接,要求libstdc++.a (-lstdc++);能够使用openmp,要求libgomp.a ( -fopenmp); libstdc++.a可以通过yum install libstdc++-static得到,但是libgomp.a则没有对应的方法。
综合B和C的注意事项,我们应该自行编译gcc,而不是使用系统自带的gcc或者yum apt-get下载安装的,因为自行编译gcc能够直接得到libstdc++.a和libgomp.a这些静态库。我选用的版本是gcc4.8.4,同样地配置它编译出静态库。配套的Binutils也需要重新编译。
D. glibc是GNU的标准C库实现,如果要静态链接glibc这些底层的库_——libc.a,libm.a,librt.a,libdl.a,libpthread.a ,需要安装glibc的静态版本
#yum install glibc-static,
#whereis libc.a(找到路径)
#cp 路径/libc.a ~mydir/(其它4个库类似,重新拷贝到一个新的位置,以防链接时优先选择动态链接,当然把这个路径放在LDFLAGS最前面)
E.opencv 和ffmpeg在配置阶段(分别使用cmake和configure),务必关闭所有的与图形IO相关的依赖,因为图形库的静态版本,太难找了,依赖关系特别冗长繁杂。
F. 最终链接ffmpeg时候,由于ffmpeg依赖了一些库如x264,x265,freetype等,它们各自依赖了glibc的一些库如librt,libm,libc,libdl。因而原始命令(#make -n|grep ffmpeg_g)中glibc的一些库(libm,libc,librt,libdl,libpthread)被反复调用,分布于多个地方,如下:
gcc -Llibavcodec -Llibavdevice -Llibavfilter -Llibavformat -Llibavresample -Llibavutil -Llibpostproc -Llibswscale -Llibswresample -L/home/ffmpeg/ffmpeg_sjtu/lib -Wl,--as-needed -Wl,-z,noexecstack -Wl,--warn-common -Wl,-rpath-link=libpostproc:libswresample:libswscale:libavfilter:libavdevice:libavformat:libavcodec:libavutil:libavresample -o ffmpeg_g cmdutils.o ffmpeg_opt.o ffmpeg_filter.o ffmpeg.o -lavdevice -lavfilter -lavformat -lavcodec -lpostproc -lswresample -lswscale -lavutil -L/home/ffmpeg/ffmpeg_build/lib -lx265 -lstdc++-lm -lrt -ldl -L/home/ffmpeg/ffmpeg_build/lib -lx264 -lpthread -lm -ldl -L/home/ffmpeg/ffmpeg_build/lib -lvpx -lm -lpthread -L/home/ffmpeg/ffmpeg_build/lib -lvpx -lm -lpthread -L/home/ffmpeg/ffmpeg_build/lib -lvpx -lm -lpthread -L/home/ffmpeg/ffmpeg_build/lib -lvpx -lm -lpthread -ltheoraenc -ltheoradec -logg -L/home/ffmpeg/ffmpeg_build/lib -lopus -lm -lmp3lame -L/home/ffmpeg/ffmpeg_build/lib -lfribidi -L/home/ffmpeg/ffmpeg_build/lib -lfreetype -lz -L/home/ffmpeg/ffmpeg_build/lib -lfontconfig -lxml2 -llzma -lm -lfreetype -lz -L/home/ffmpeg/ffmpeg_build/lib -lfdk-aac -lm -L/home/ffmpeg/ffmpeg_build/lib -lass -lharfbuzz -lfontconfig -lenca -lfribidi -lxml2 -llzma -lm -lfreetype -lz -lm -llzma -lbz2 -lz -pthread -lrt -lstdc++ -L/home/ffmpeg/sjtu_fruc/lib -lsjtu_fruc -fopenmp -L/usr/local/lib -L/usr/local/share/OpenCV/3rdparty/lib -lopencv_shape -lopencv_stitching -lopencv_objdetect -lopencv_superres -lopencv_videostab -lopencv_calib3d -lopencv_features2d -lopencv_highgui -lopencv_videoio -lopencv_imgcodecs -lopencv_video -lopencv_photo -lopencv_ml -lopencv_imgproc -lopencv_flann -lopencv_core -lopencv_hal -lzlib -llibjpeg -llibwebp -llibpng -llibtiff -llibjasper -ltbb -lippicv -lstdc++ -ldl -lm -lpthread -lrt
因此,为了能够静态链接glibc的几个库,需要手动修改这条最终的链接命令:把所有glibc的库放到最后,以如下方式:
-lm -lrt -ldl -lm -lpthread -lrt -static -lc
注意,-static -lc (libc.a)必须放到最后(pthread之后),因为pthread和c库有函数重定义的冲突。
这条语句最终为:
printf "LD\t%s\n" ffmpeg_g; gcc -Llibavcodec -Llibavdevice -Llibavfilter -Llibavformat -Llibavresample -Llibavutil -Llibpostproc -Llibswscale -Llibswresample -L/home/ffmpeg/ffmpeg_sjtu/lib -Wl,--as-needed -Wl,-z,noexecstack -Wl,--warn-common -Wl,-rpath-link=libpostproc:libswresample:libswscale:libavfilter:libavdevice:libavformat:libavcodec:libavutil:libavresample -o ffmpeg_g cmdutils.o ffmpeg_opt.o ffmpeg_filter.o ffmpeg.o -lavdevice -lavfilter -lavformat -lavcodec -lpostproc -lswresample -lswscale -lavutil -L/home/ffmpeg/ffmpeg_build/lib -lx265 -L/home/ffmpeg/ffmpeg_build/lib -lx264 -L/home/ffmpeg/ffmpeg_build/lib -lvpx -L/home/ffmpeg/ffmpeg_build/lib -lvpx -L/home/ffmpeg/ffmpeg_build/lib -lvpx -L/home/ffmpeg/ffmpeg_build/lib -lvpx -ltheoraenc -ltheoradec -logg -L/home/ffmpeg/ffmpeg_build/lib -lopus -lmp3lame -L/home/ffmpeg/ffmpeg_build/lib -lfribidi -L/home/ffmpeg/ffmpeg_build/lib -lfreetype -lz -L/home/ffmpeg/ffmpeg_build/lib -lfontconfig -lxml2 -llzma -lfreetype -lz -L/home/ffmpeg/ffmpeg_build/lib -lfdk-aac -L/home/ffmpeg/ffmpeg_build/lib -lass -lharfbuzz -lfontconfig -lenca -lfribidi -lxml2 -llzma -lfreetype -lz -llzma -lbz2 -lz -L/home/ffmpeg/sjtu_fruc/lib -lsjtu_fruc -fopenmp -L/usr/local/lib -L/usr/local/share/OpenCV/3rdparty/lib -lopencv_shape -lopencv_stitching -lopencv_objdetect -lopencv_superres -lopencv_videostab -lopencv_calib3d -lopencv_features2d -lopencv_highgui -lopencv_videoio -lopencv_imgcodecs -lopencv_video -lopencv_photo -lopencv_ml -lopencv_imgproc -lopencv_flann -lopencv_core -lopencv_hal -lzlib -llibjpeg -llibwebp -llibpng -llibtiff -llibjasper -ltbb -lippicv -lstdc++ -lm -lrt -ldl -lm -lpthread -lrt -static -lc
尽管它执行会报出一些warnning,但是,不影响生成ffmpeg_g可执行文件。
然后执行,
#cp ffmpeg_g ffmpeg
#strip ffmpeg
即可
测试ffmpeg
- 亲测VS2010纯静态编译QT4.8.0,实现VS2010编译调试Qt程序,QtCreator静态发布程序(图文并茂,非常详细)
下载源代码,注意一定是源码压缩包如qt-everywhere-opensource-src-4.8.0.zip,不是Qt发布的已编译的不同版本的标准库如qt-win-opensource-4.8.0- ...
- VS2010使用静态编译的qt库(Qt 5)
Qt 5引入了一种新的编写方式. Qt开发界面很方便,但发布程序就不那么方便了,你的把引用到的dll一起发布才行,要是能静态编译就好了,发布的时候只有一个exe多方便. 虽然以前为了方便,直接安装的q ...
- VS2010使用静态编译的qt库
Qt开发界面很方便,但发布程序就不那么方便了,你的把引用到的dll一起发布才行,要是能静态编译就好了,发布的时候只有一个exe多方便. 虽然以前为了方便,直接安装的qt-windows-opensou ...
- 静态编译Qt5.4.1和Qt WebKit
图灵社区文章地址:http://www.ituring.com.cn/article/195148WebKit是个好东西,做爬虫.显示网页还是想用HTML来做桌面应用的界面都可以用他,不过一直以来都觉 ...
- 静态编译Qt5.4.1和Qt WebKit(网事如风的blog)good
blog文章地址:http://godebug.org/index.php/archives/133/ WebKit是个好东西,做爬虫.显示网页还是想用HTML来做桌面应用的界面都可以用他,不过一直以 ...
- Qt库的静态编译
一.准备软件1. MinGW (C:\Qt\MinGW)http://pan.baidu.com/share/link?shareid=174269&uk=673227135这个文件解 ...
- Android导入第三方静态库.a编译成动态库.so
http://ikinglai.blog.51cto.com/6220785/1324985 在Android开发的时候,经常会使用到用c或c++编写的第三方的静态库.如果有源码的话,可以直接跟你自己 ...
- Linux下快速静态编译Qt以及Qt动态/静态版本共存(提供了编译4.6,5.6的精通编译脚本,并且apt-get install 需要的库也全列出来了。还有分析问题的心理过程)good
qt4.6 Linux./configure -static -release -confirm-license -opensource -qt-zlib -qt-libpng -qt-libjpeg ...
- 实战FFmpeg--编译iOS平台使用的FFmpeg库(支持arm64的FFmpeg2.6.2)
编译环境:Mac OS X 10.10.2 ,Xcode 6.3 iOS SDK 8.3 FFmpeg库的下载地址是 http://www.ffmpeg.org/releases/ . ...
随机推荐
- iOS 平台如何使用 TestFlight 进行 Beta 测试
使用 TestFlight,你可以向测试人员发布你 App 的 prerelease 版本来收集反馈信息,为将来发布 App 的正式版做准备.现在 TestFlight 是一个可选功能,你也可以不使用 ...
- vue2+element组件库开发
Vue2:https://cn.vuejs.org/v2/guide/single-file-components.html element组件库:http://element-cn.eleme.io ...
- LR报错 No buffer space available Try changing the registry value 端口号不够用了
报错:Action.c(6): Error -27796: Failed to connect to server "10.16.137.8:10035": [10055] No ...
- urllib.urlencode() 无法encode中文, UnicodeEncodeError
urllib.urlencode() 无法encode中文, UnicodeEncodeError, 具体错误内容如下:File "/System/Library/Frameworks/Py ...
- python 基础 9.6 设计表结构
一. 设计表结构 在操作设计数据库之前,我们先要设计数据库表结构,我们就来分析分析经典的学生,课程,成绩,老师这几者他们之间的关系,我们先来分析各个主体他们直接有什么属性,并确定表结构,在实际开 ...
- SecureCRT的Home+End+Del键映射
在securecrt界面:工具 → 键映射编辑器,在弹出的键盘中: 1.点击“home”,会弹出一个窗口,在“发送字符串”中输入:\033[1~ 2.点击“end”,会弹出一个窗口,在“发送字符串”中 ...
- why factory pattern and when to use factory pattern
1 factory pattern本质上就是对对象创建进行抽象 抽象的好处是显然的,可以方便用户去获取对象. 2 使用factory pattern的时机 第一,当一个对象的创建依赖于其它很多对象的时 ...
- Feign-独立使用-实战
目录 写在前面 1.1.1. 短连接API的接口准备 1.1.2. 申明远程接口的本地代理 1.1.3. 远程API的本地调用 写在最后 疯狂创客圈 亿级流量 高并发IM 学习实战 疯狂创客圈 Jav ...
- 如何在ubuntun中安装intellij idea 2018并破解
相比eclipse软件,intellij idea的操作更方便.功能更多,几乎集成了所有的java框架. 安装步骤如下: 1 在https://www.jetbrains.com/idea/网站上下载 ...
- Android中关于系统Dialog无法全屏的问题(dialog样式)
自定义一个Dialog,继承了系统Dialog的样式.这时候会发现,即使布局文件中写的width和height都是match_parent,依然无法达到全屏的效果. 原因是:系统dialog的样式.默 ...