1.下载ffmpe源码
2.交叉编译配置
我们的目的是在windows PC上编译出android系统可用的so库,这就涉及到交叉编译。下面先来科普一下交叉编译的概念。
2.1 什么是交叉编译?
交叉编译是在一个平台上生成另一个平台上的可执行代码。比如我们在windows、mac上编译生成android平台上的dex、so,其实就是交叉编译。交叉编译有几个概念:
- build:构建工具。如gcc、clang。
- host:编译程序的平台,一般都是基于x86的pc机。
- target:运行编译程序的平台。比如MIPS、ARM。
举个例子,build:clang,host:windows-x86_64,target:ARM,就是在64为windows PC上用clang工具链交叉编译可以在ARM平台上运行的程序
交叉编译工具链通常会提供如下几个工具:
- CC:编译器,对C源文件进行编译处理,生成汇编文件。
- AS:将汇编文件生成目标文件(汇编文件使用的是指令助记符,AS将它翻译成机器码)。
- AR:打包器,用于库操作,可以通过该工具从一个库中删除或者增加目标代码模块。
- LD:链接器,为前面生成的目标代码分配地址空间,将多个目标文件链接成一个库或者是可执行文件。
- GDB:调试工具,可以对运行过程中的程序进行代码调试工作。
- STRIP:以最终生成的可执行文件或者库文件作为输入,然后消除掉其中的源码。
- NM:查看静态库文件中的符号表。
- Objdump:查看静态库或者动态库的方法签名。
比如Android NDK,其交叉工具编译链llvm,在prebuilt\windows-x86_64\bin目录下就包含了对应的clang、as、ar、ld、nm、strip等工具,如下图所示:

2.2 ffmpeg交叉编译配置
接下来我们开始配置ffmpeg的编译参数。结合2.1内容,我们这次交叉编译的三个要素为: build:clang,host:windows-x86_64,target=ARM,其中编译工具为Android NDK的独立工具链。 有一点需要注意,NDK从r18开始弃用gcc,改用llvm,网上很多配置都是gcc的,照抄配置会导致编译报错或者生成不了so文件。
在ffmpeg的根目录下新建build_android.sh脚本,内容如下:
#!/bin/bash
export TMPDIR=C:/ffmpeg/fftemp
NDK=C:/android-sdk/ndk-bundle
TOOLCHAIN=$NDK/toolchains/llvm/prebuilt/windows-x86_64
SYSROOT=$TOOLCHAIN/sysroot
PREFIX=$TMPDIR/output
./configure \
--prefix=$PREFIX \
--target-os=android \
--arch=arm \
--enable-shared \
--disable-static \
--disable-doc \
--disable-ffmpeg \
--disable-ffplay \
--disable-ffprobe \
--disable-avdevice \
--disable-symver \
--disable-everything \
--enable-cross-compile \
--sysroot=$SYSROOT \
--cross-prefix=$TOOLCHAIN/bin/arm-linux-androideabi- \
--cc=$PLATFORM/bin/armv7a-linux-androideabi16-clang \
--extra-cflags="-I$SYSROOT/usr/include" \
--extra-ldflags="-L$SYSROOT/usr/lib" \
make clean
make -j4
make install
最后来解释一下几个关键配置的含义:
target-os
指定编译的目标平台,在./configure文件中用到了,当target-os为android时,默认用clang编译
if test "$target_os" = android; then
cc_default="clang"
fi
ar_default="${cross_prefix}${ar_default}"
cc_default="${cross_prefix}${cc_default}"
cxx_default="${cross_prefix}${cxx_default}"
nm_default="${cross_prefix}${nm_default}"
cc
指定C编译器的路径
cc=$PLATFORM/bin/armv7a-linux-androideabi16-clang,这个配置就是指定NDK中clang的路径

cross-prefix
指定交叉编译工具文件路径的统一前缀。各个工具的最终文件路径为:cross-prefix + 工具名,比如上面脚本的prefix为TOOLCHAIN/bin/arm-linux-androideabi-,那么ar工具的路径即为TOOLCHAIN/bin/arm-linux-androideabi-ar
ar
静态库制作工具,类似unix上的ar命令,通常将编译生成的.o文件链接以后打包成一个libXXXX.a文件
--ar=$TOOLCHAIN/bin/arm-linux-androideabi-ar,这个配置就是指定NDK中ar工具的路径
nm
查看目标文件(.o)中的符号
--nm=$TOOLCHAIN/bin/arm-linux-androideabi-nm,这个配置就是指定NDK中nm工具的路径
3.编译
运行./build_android.sh,最终会在PREFIX目录下生成lib和include目录,分别存放so和头文件


如果遇到编译问题,请参考文章ffmpeg常见编译问题及其解决方案
有关ffmpeg编译的更多细节请翻阅: ffmpeg官方编译指导文档
项目源码地址:
Gitee:gitee.com/huaisu2020/…
Github:github.com/xh2009cn/An…