编译脚本
NDK编译工具链 r17c
#NDK目录 r17c是最后一个支持gcc的ndk
export NDK_HOME=/Users/loki/Desktop/tools/ndk/android-ndk-r17c
#生成交叉编译链工具
toolchain=${NDK_HOME}/build/tools/make-standalone-toolchain.sh
#生成交叉编译链保存在当前目录子文件夹android-toolchain
install_root=`pwd`/android-toolchain
#生成32位库最低支持到android4.3,64位库最低支持到android5.0 最新版的ffmpeg,x264需要最低 android-23 就是 android 6.0 因为cabs()等函数。
platforms=(
"android-23"
"android-23"
"android-23"
"android-23"
"android-23"
)
#支持以下5种cpu框架
archs=(
"arm"
"arm"
"arm64"
"x86"
"x86_64"
)
#cpu型号
abis=(
"armeabi"
"armeabi-v7a"
"arm64-v8a"
"x86"
"x86_64"
)
echo $NDK_HOME
echo "安装在目录:$install_root"
num=${#abis[@]}
for ((i=0; i<num; i++))
do
bash $toolchain --arch=${archs[i]} --platform=${platforms[i]} --abis=${abis[i]} --install-dir=$install_root/${abis[i]}
done
x264编译脚本
#!/bin/bash
NDK=/Users/loki/Desktop/tools/ndk/android-ndk-r17c
TOOL_ROOT=$NDK/android-toolchain
#五种类型cpu编译链
android_toolchains=(
"armeabi"
"armeabi-v7a"
"arm64-v8a"
"x86"
"x86_64"
)
#优化编译项
extra_cflags=(
"-march=armv5te -msoft-float -D__ANDROID__ -D__ARM_ARCH_5TE__ -D__ARM_ARCH_5TEJ__"
"-march=armv7-a -mfloat-abi=softfp -mfpu=neon -mthumb -D__ANDROID__ -D__ARM_ARCH_7__ -D__ARM_ARCH_7A__ -D__ARM_ARCH_7R__ -D__ARM_ARCH_7M__ -D__ARM_ARCH_7S__"
"-march=armv8-a -D__ANDROID__ -D__ARM_ARCH_8__ -D__ARM_ARCH_8A__"
"-march=i686 -mtune=i686 -m32 -mmmx -msse2 -msse3 -mssse3 -D__ANDROID__ -D__i686__"
"-march=core-avx-i -mtune=core-avx-i -m64 -mmmx -msse2 -msse3 -mssse3 -msse4.1 -msse4.2 -mpopcnt -D__ANDROID__ -D__x86_64__"
)
extra_ldflags="-nostdlib"
configure="--disable-cli \
--enable-static \
--enable-shared \
--disable-opencl \
--enable-strip \
--disable-cli \
--disable-win32thread \
--disable-avs \
--disable-swscale \
--disable-lavf \
--disable-ffms \
--disable-gpac \
--disable-lsmash"
#针对各版本不同的编译项
extra_configure=(
"--disable-asm"
""
""
"--disable-asm"
"--disable-asm"
)
#交叉编译后的运行环境
hosts=(
"arm-linux-androideabi"
"arm-linux-androideabi"
"aarch64-linux-android"
"i686-linux-android"
"x86_64-linux-android"
)
#交叉编译工具前缀
cross_prefix=(
"arm-linux-androideabi-"
"arm-linux-androideabi-"
"aarch64-linux-android-"
"i686-linux-android-"
"x86_64-linux-android-"
)
PREFIX=$(pwd)/libs/
function build_x264
{
index=$1
export PATH=$TOOL_ROOT/${android_toolchains[index]}/bin:$PATH
echo "开始配置${android_toolchains[index]}版本"
#交叉编译最重要的是配置--host、--cross-prefix、sysroot、以及extra-cflags和extra-ldflags
./configure ${configure} \
${extra_configure[index]} \
--prefix=$PREFIX/${android_toolchains[index]} \
--host=${hosts[index]} \
--cross-prefix=${cross_prefix[index]} \
--sysroot=$TOOL_ROOT/${android_toolchains[index]}/sysroot \
--extra-cflags="${extra_cflags[index]}" \
--extra-ldflags="$extra_ldflags"
make clean
echo "开始编译并安装${android_toolchains[i]}版本"
make -j4 & make install
}
for (( i = 0; i < 5; i++ )); do
build_x264 i
done
ffmpeg编译脚本
#!/bin/bash
NDK=/Users/loki/Desktop/tools/ndk/android-ndk-r17c
TOOL_ROOT=$NDK/android-toolchain
#五种类型cpu编译链
android_toolchains=(
"armeabi"
"armeabi-v7a"
"arm64-v8a"
"x86"
"x86_64"
)
#优化编译项
extra_cflags=(
"-std=gnu11 -march=armv5te -msoft-float -D__ANDROID__ -D__ARM_ARCH_5TE__ -D__ARM_ARCH_5TEJ__"
"-std=gnu11 -march=armv7-a -mfloat-abi=softfp -mfpu=neon -mthumb -D__ANDROID__ -D__ARM_ARCH_7__ -D__ARM_ARCH_7A__ -D__ARM_ARCH_7R__ -D__ARM_ARCH_7M__ -D__ARM_ARCH_7S__"
"-std=gnu11 -march=armv8-a -D__ANDROID__ -D__ARM_ARCH_8__ -D__ARM_ARCH_8A__"
"-std=gnu11 -march=i686 -mtune=i686 -m32 -mmmx -msse2 -msse3 -mssse3 -D__ANDROID__ -D__i686__"
"-std=gnu11 -march=core-avx-i -mtune=core-avx-i -m64 -mmmx -msse2 -msse3 -mssse3 -msse4.1 -msse4.2 -mpopcnt -D__ANDROID__ -D__x86_64__"
)
#共同配置项,可以额外增加相关配置,详情可查看源文件目录下configure
#--disable-indev=v4l2 #解决libavdevice/v4l2.c:135:9: error: assigning to 'int (*)(int, unsigned long, ...)'
configure="--enable-gpl \
--enable-version3 \
--enable-nonfree \
--enable-static \
--disable-shared \
--enable-small \
--disable-programs \
--disable-ffmpeg \
--disable-doc \
--disable-htmlpages \
--disable-manpages \
--disable-podpages \
--disable-txtpages \
--disable-hwaccels \
--disable-filters \
--disable-muxers \
--disable-avdevice \
--disable-indevs \
--disable-outdevs \
--disable-debug \
--disable-postproc \
--enable-avdevice \
--disable-symver \
--disable-stripping \
--disable-encoders --enable-encoder=libx264 \
--disable-decoders --enable-decoder=h264 \
--disable-demuxers --enable-demuxer=h264 \
--enable-libx264"
#针对各版本不同的编译项
extra_configure=(
"--disable-asm"
""
""
"--disable-asm"
"--disable-asm"
)
#交叉编译工具前缀
cross_prefix=(
"arm-linux-androideabi"
"arm-linux-androideabi"
"aarch64-linux-android"
"i686-linux-android"
"x86_64-linux-android"
)
#支持以下5种cpu框架
archs=(
"arm"
"arm"
"arm64"
"x86"
"x86_64"
)
PREFIX=./libs/
function build_one
{
i=$1
export PATH=$TOOL_ROOT/${android_toolchains[i]}/bin:$PATH
export PATH=$TOOL_ROOT/${android_toolchains[i]}/${cross_prefix[i]}/bin:$PATH
echo "开始配置${android_toolchains[i]}版本"
extra_include="./x264/libs/${android_toolchains[i]}/include"
extra_lib="./x264/libs/${android_toolchains[i]}/lib"
SYSROOT=$TOOL_ROOT/${android_toolchains[i]}/sysroot
GCC=$TOOL_ROOT/${android_toolchains[i]}/lib/gcc/${cross_prefix[i]}/4.9.x/libgcc.a
./configure ${configure} \
${extra_configure[i]} \
--prefix=$PREFIX/${android_toolchains[i]} \
--enable-cross-compile \
--target-os=android \
--arch=${archs[i]} \
--cross-prefix=${cross_prefix[i]}- \
--sysroot=$SYSROOT \
--extra-cflags="${extra_cflags[i]} -I$extra_include" \
--extra-ldflags="-L$extra_lib"
make clean
echo "开始编译并安装${android_toolchains[i]}版本"
make -j4
make install
# 链接动态库: 将多个库打包为一个动态库
ld \
-rpath-link=$SYSROOT/usr/lib \
-L$SYSROOT/usr/lib \
-L$PREFIX/${android_toolchains[i]}/lib \
-L$extra_lib \
-soname libffmpeg.so -shared -nostdlib -Bsymbolic --whole-archive --no-undefined -o \
$PREFIX/${android_toolchains[i]}/libffmpeg.so \
libavcodec/libavcodec.a \
libavfilter/libavfilter.a \
libswresample/libswresample.a \
libavformat/libavformat.a \
libavutil/libavutil.a \
libswscale/libswscale.a \
$extra_lib/libx264.a \
-lc -lm -lz -ldl -llog --dynamic-linker=/system/bin/linker \
$GCC
}
build_one 1
build_one 2
遇到的问题
ffmpeg avformat_alloc_output_context2: flv -22 - Invalid argument
编译ffmpeg时未加入flv封装格式,--enable-muxer=flv
toolchains/llvm/prebuilt/darwin-x86_64/bin/armv7a-linux-androideabi19-clang is unable to create an executable file.
avformat_write_header -22 - Invalid argument
写入头之前需要使用avformat_new_stream
创建好对应的Stream
avformat_alloc_output_context2 -22 - Invalid argument
avformat_alloc_output_context2
方法参数需指定转码格式
如果是将RTMP stream转为flv文件,需将最后一个参数写为明确的.flv格式文件地址,
avformat_alloc_output_context2(&outFormatContext,
NULL,
NULL,
"/sdcard/a3.flv"); //RTMP
如果是将RTMP串流逐帧处理,需将第三个参数写为flv
avformat_alloc_output_context2(&outFormatContext,
NULL,
"flv",
NULL); //RTMP