交叉編譯ffmpeg so庫

下載ffmpeg庫,本文以ffmpeg-4.2.3爲例。

FFmpeg下載

編譯工具鏈

對於C/C++的編譯,通常有兩個工具 GCC 和 CLANG 。這兩個庫的區別就不介紹了,感興趣的同學自行查閱相關資料。
Google在 ndk 17 以後,把 GCC 移除了,全面推行使用 CLANG 。所以各位同學一定要注意自己的ndk環境。

NDK 下載

編譯、交叉編譯工具目錄

編譯工具鏈目錄:
android-ndk-r17c/toolchains/llvm/prebuilt/darwin-x86_64/bin
交叉編譯環境目錄:
android-ndk-r17c/sysroot

有意思的是ndk 17之後的版本中toolchains/llvm/prebuilt/darwin-x86_64路徑下也有sysroot文件夾。

1)toolchains目錄結構toolchains目錄
2)sysroot目錄結構sysroot目錄
該目錄右側列出來支持的不同CPU架構及編輯版本,我們選擇 CPU 架構 armv7a,Android版本 21爲例

armv7a-linux-androideabi21-clang
armv7a-linux-androideabi21-clang++

使用 GCC 編譯FFmpeg

下載 NDK r17c

編譯腳本

打開ffmpeg-4.2.3文件夾,創建腳本文件build_gcc_arm.sh,編輯腳本內容

CPU=armv7-a
API=21
ARCH=arm

NDK=/Users/liuhongshuo/AnroidPro/ffmpeg/android-ndk-r17c
SYSROOT=$NDK/platforms/android-$API/arch-arm
TOOLCHAIN=$NDK/toolchains/arm-linux-androideabi-4.9/prebuilt/darwin-x86_64

ISYSROOT=$NDK/sysroot
ASM=$ISYSROOT/usr/include/arm-linux-androideabi

# 要保存動態庫的目錄,這裏保存在源碼根目錄下的android/armv7-a
 PREFIX=$(pwd)/android/$CPU
ADDI_CFLAGS="-marm"

$ADDITIONAL_CONFIGURE_FLAG

function build_android
{
   echo -e "\033[32m build start \033[0m"

   ./configure \
       --target-os=android \
       --prefix=$PREFIX \
       --arch=$ARCH \
       --cpu=$CPU \
       --enable-cross-compile \
       --enable-static \
       --disable-shared \
       --disable-doc \
       --disable-ffmpeg \
       --disable-ffplay \
       --disable-ffprobe \
       --disable-avdevice \
       --disable-doc \
       --disable-symver \
       --cross-prefix=$TOOLCHAIN/bin/arm-linux-androideabi- \
       --cc=$TOOLCHAIN/bin/arm-linux-androideabi-gcc \
       --nm=$TOOLCHAIN/bin/arm-linux-androideabi-nm \
       --sysroot=$SYSROOT \
       --extra-cflags="-I$ASM -isysroot $ISYSROOT -D__ANDROID_API__=$API -U_FILE_OFFSET_BITS -Os -fPIC -DANDROID -Wno-deprecated -mfloat-abi=softfp -marm" \
       --extra-ldflags="$ADDI_LDFLAGS" \
       $ADDITIONAL_CONFIGURE_FLAG

   make clean

   make -j16
   make install

   echo -e "\033[32m build successful \033[0m"
}

function merge
{
   echo -e "\033[32m package start \033[0m"

   # 打包
   $TOOLCHAIN/bin/arm-linux-androideabi-ld \
       -rpath-link=$SYSROOT/usr/lib \
       -L$SYSROOT/usr/lib \
       -L$PREFIX/lib \
       -soname libffmpeg.so -shared -nostdlib -Bsymbolic --whole-archive --no-undefined -o \
       $PREFIX/libffmpeg.so \
       libavcodec/libavcodec.a \
       libavfilter/libavfilter.a \
       libavformat/libavformat.a \
       libavutil/libavutil.a \
       libswresample/libswresample.a \
       libswscale/libswscale.a \
       -lc -lm -lz -ldl -llog --dynamic-linker=/system/bin/linker \
       $TOOLCHAIN/lib/gcc/arm-linux-androideabi/4.9.x/libgcc.a

   # strip 精簡文件
   $TOOLCHAIN/bin/arm-linux-androideabi-strip  $PREFIX/libffmpeg.so

   echo -e "\033[32m package successful \033[0m"
}

build_android
merge

編譯配置詳解答

設置編譯針對的系統
–target-os=android \

編譯後文件的輸出目錄
–prefix=$PREFIX \

–enable-cross-compile \

編譯動態庫,shared和static的開關是相對的。
–enable-static
–disable-shared \

生成文檔,以及相關的功能模塊
–disable-doc \

禁止編譯可執行文件
–disable-programs
–disable-ffmpeg
–disable-ffplay
–disable-ffprobe
–disable-avdevice
–disable-doc
–disable-symver \

設置交叉編譯器,按照實際路徑修改就可以了。
–cross-prefix=KaTeX parse error: Undefined control sequence: \ at position 38: …x-androideabi- \̲ ̲ 設置編譯器 --cc=TOOLCHAIN/bin/arm-linux-androideabi-gcc
–nm=$TOOLCHAIN/bin/arm-linux-androideabi-nm \

設置編譯so庫的架構,當前設置爲arm,可以根據實際需求修改
–arch=arm \

設置編譯針對的平臺,可以根據實際需求進行設置,當前設置爲最低支持android-21版本,arm架構。
–sysroot=KaTeX parse error: Undefined control sequence: \ at position 9: SYSROOT \̲ ̲--extra-cflags=…ASM -isysroot $ISYSROOT -D__ANDROID_API__=21 -U_FILE_OFFSET_BITS -Os -fPIC -DANDROID -Wno-deprecated -mfloat-abi=softfp -marm" \

–extra-ldflags="$ADDI_LDFLAGS" \

啓動編譯

打開 命令終端,cd 到ffmpeg-4.2.3目錄,執行 build_gcc_arm.sh,然後喝杯咖啡等待運行結果。
在這裏插入圖片描述

使用 CLANG 編譯FFmpeg

下載NDK最新版本

編譯腳本

打開ffmpeg-4.2.3文件夾,創建腳本文件build_clang_arm.sh,編輯腳本內容

CPU=armv7-a
API=21
ARCH=arm

NDK=/Users/liuhongshuo/AnroidPro/ffmpeg/android-ndk-r20
SYSROOT=$NDK/platforms/android-$API/arch-arm
TOOLCHAIN=$NDK/toolchains/arm-linux-androideabi-4.9/prebuilt/darwin-x86_64

ISYSROOT=$NDK/sysroot
ASM=$ISYSROOT/usr/include/arm-linux-androideabi

# 要保存動態庫的目錄,這裏保存在源碼根目錄下的android/armv7-a
 PREFIX=$(pwd)/android/$CPU
ADDI_CFLAGS="-marm"

$ADDITIONAL_CONFIGURE_FLAG

function build_android
{
   echo -e "\033[32m build start \033[0m"

   ./configure \
       --target-os=android \
       --prefix=$PREFIX \
       --arch=$ARCH \
       --cpu=$CPU \
       --enable-cross-compile \
       --enable-static \
       --disable-shared \
       --disable-doc \
       --disable-ffmpeg \
       --disable-ffplay \
       --disable-ffprobe \
       --disable-avdevice \
       --disable-doc \
       --disable-symver \
       --cross-prefix=$TOOLCHAIN/bin/arm-linux-androideabi- \
       --sysroot=$SYSROOT \
       --extra-cflags="-I$ASM -isysroot $ISYSROOT -D__ANDROID_API__=$API -U_FILE_OFFSET_BITS -Os -fPIC -DANDROID -Wno-deprecated -mfloat-abi=softfp -marm" \
       --extra-ldflags="$ADDI_LDFLAGS" \
       $ADDITIONAL_CONFIGURE_FLAG

   make clean

   make -j16
   make install

   echo -e "\033[32m build successful \033[0m"
}

function merge
{
   echo -e "\033[32m package start \033[0m"

   # 打包
   $TOOLCHAIN/bin/arm-linux-androideabi-ld \
       -rpath-link=$SYSROOT/usr/lib \
       -L$SYSROOT/usr/lib \
       -L$PREFIX/lib \
       -soname libffmpeg.so -shared -nostdlib -Bsymbolic --whole-archive --no-undefined -o \
       $PREFIX/libffmpeg.so \
       libavcodec/libavcodec.a \
       libavfilter/libavfilter.a \
       libavformat/libavformat.a \
       libavutil/libavutil.a \
       libswresample/libswresample.a \
       libswscale/libswscale.a \
       -lc -lm -lz -ldl -llog --dynamic-linker=/system/bin/linker \
       $TOOLCHAIN/lib/gcc/arm-linux-androideabi/4.9.x/libgcc.a

   # strip 精簡文件
   $TOOLCHAIN/bin/arm-linux-androideabi-strip  $PREFIX/libffmpeg.so

   echo -e "\033[32m package successful \033[0m"
}

build_android
merge

啓動編譯

打開 命令終端,cd 到ffmpeg-4.2.3目錄,執行 build_clang_arm.sh。

參考文章

【Android 音視頻開發打怪升級:FFmpeg音視頻編解碼篇】

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章