Shell生成支持x264的ffmpeg安卓全平台so

news2024/11/29 2:32:12

安卓 FFmpeg系列

第一章 Ubuntu生成ffmpeg安卓全平台so
第二章 Windows生成ffmpeg安卓全平台so
第三章 生成支持x264的ffmpeg安卓全平台so(本章)


文章目录

  • 安卓 FFmpeg系列
  • 前言
  • 一、实现步骤
    • 1、下载x264源码
    • 2、交叉编译生成.a
    • 3、加入x264配置
    • 4、编译ffmpeg
  • 二、完整代码
  • 三、生成好的包
  • 四、使用示例
    • 1、基本用法
      • (1)查看用法
      • (2)确认ffmpeg版本
      • (3)生成so
    • 2、ubuntu中使用
    • 3、windows msys2中使用
  • 总结


前言

前两张实现了ffmpeg全平台so的生成,但是ffmpeg依赖的第三方库是需要另外编译的,所以本章将提供编译x264库并加入ffmpeg的方法。本章提供的脚本在ubuntu以及windows的wsl、msys2都适用。


一、实现步骤

定义交叉编译相关变量

#ndk api版本 -可配置
API=24
#cpu 架构 -可配置 :armv7-a、armv8-a、i686、x86-64
CPU=x86-64
#msys则可设置为windows
OS=linux
#需要ANDROID_NDK_HOME指定ndk目录
TOOLCHAIN=$ANDROID_NDK_HOME/toolchains/llvm/prebuilt/$OS-x86_64
echo $TOOLCHAIN
SYSROOT=$TOOLCHAIN/sysroot
PREFIX=$(pwd)/output/ffmpeg${FFMPEG_VERSION}/${API}/${CPU}
PACKAGE_PREFIX=$PACKAGE_SOURCE_DIR/.output/${API}/${CPU}
export CC=${CROSS_PREFIX}clang
export CXX=${CROSS_PREFIX}clang++
case $CPU in
armv7-a)
  ARCH=arm
  CROSS_PREFIX=$TOOLCHAIN/bin/armv7a-linux-androideabi$API-
  ;;
armv8-a)
  ARCH=arm64
  CROSS_PREFIX=$TOOLCHAIN/bin/aarch64-linux-android$API-
  ;;
i686)
  ARCH=x86
  CROSS_PREFIX=$TOOLCHAIN/bin/i686-linux-android$API-
  FFMPEG_EXTRA_CONFIGURE_FLAGS=--disable-asm
  ;;
x86-64)
  ARCH=x86_64
  CROSS_PREFIX=$TOOLCHAIN/bin/x86_64-linux-android$API-
  ;;

1、下载x264源码

 wget https://code.videolan.org/videolan/x264/-/archive/master/x264-master.tar.bz2
 tar -xf $PACKET_X264.tar.bz2

2、交叉编译生成.a

在x264源码目录执行如下操作。其中X264_OUTPUT_DIR 为输出目录,ARCH为cpu架构

./configure \
    --prefix=$X264_OUTPUT_DIR \
    --enable-static \
    --enable-pic \
    --host=$ARCH-linux \
    --disable-opencl \
    --disable-cli \
    --cross-prefix=$CROSS_PREFIX \
    --sysroot=$SYSROOT \
    FFMPEG_EXTRA_CONFIGURE_FLAGS
make -j$(nproc) 
make install

3、加入x264配置

FFMPEG_EXTRA_CFLAGS="$FFMPEG_EXTRA_CFLAGS -I$X264_OUTPUT_DIR/include"
FFMPEG_EXTRA_LDFLAGS="$FFMPEG_EXTRA_LDFLAGS -L$X264_OUTPUT_DIR/lib"
FFMPEG_EXTRA_CONFIGURE_FLAGS="$FFMPEG_EXTRA_CONFIGURE_FLAGS --enable-encoder=libx264 --enable-libx264"
export PKG_CONFIG_PATH="$PKG_CONFIG_PATH:$X264_OUTPUT_DIR/lib/pkgconfig"

4、编译ffmpeg

 ./configure --target-os=android \
    --prefix=$PREFIX \
    --arch=$ARCH \
    --cpu=$CPU \
    --cc=$CC \
    --cxx=$CXX \
    --disable-ffmpeg \
    --disable-ffplay \
    --disable-ffprobe \
    --enable-gpl \
    --cross-prefix=$CROSS_PREFIX \
    --enable-cross-compile \
    --enable-jni \
    --enable-mediacodec \
    --enable-decoder=h264_mediacodec \
    --enable-decoder=hevc_mediacodec \
    --enable-decoder=vp8_mediacodec \
    --enable-decoder=vp9_mediacodec \
    --enable-decoder=mpeg2_mediacodec \
    --enable-decoder=mpeg4_mediacodec \
    --sysroot=$SYSROOT \
    --extra-cflags="-Os -fpic -DVK_ENABLE_BETA_EXTENSIONS=0 -march=$CPU $FFMPEG_EXTRA_CFLAGS" \
    --extra-ldflags="$FFMPEG_EXTRA_LDFLAGS" \
    --pkg-config="pkg-config --static" \
    $SHARED_OR_STATIC_FLAG \
    $FFMPEG_EXTRA_CONFIGURE_FLAGS
make -j$(nproc)
make install

二、完整代码

下列代码可以在ubuntu、wsl ubuntu、msys2中执行。无需任何额外操作,只需调用脚本即可生成so。可以指定cpu、安卓api、以及ffmpeg版本号。如果没有指定ANDROID_NDK_HOME会自动下载ndk,x264源码也会自动下载以及ffmpeg源码也会自动下载,然后自动生成so。同时还会生成ffmpeg.so,是ffmpeg可执行程序,笔者将其生成了so,其内包含的main符号可以直接调用,以输入命令行
注:合并所有库到libffmpeg.so的方式本文暂不提供。
下列代码可复制保存为build.sh直接执行。

set -e
show_usage() {
  echo "usage:
      -p is cpu (armv7-a、armv8-a、i686、x86-64) 
      -a is android api number
      -f is ffmpeg version
      -h is help
   "
}
#ffmpeg版本 -可配置
FFMPEG_VERSION=4.3.6
#ndk api版本 -可配置
API=24
#cpu 架构 -可配置 :armv7-a、armv8-a、i686、x86-64
CPU=x86-64
while getopts "p:a:f:h" arg; do
  case $arg in
  p)
    CPU=$OPTARG
    ;;
  a)
    API=$OPTARG
    ;;
  f)
    FFMPEG_VERSION=$OPTARG
    ;;
  h)
    show_usage
    exit 1 
    ;;
  ?)
    echo "unkonw argument"
    show_usage
    exit 1
    ;;
  esac
done
OS=$(uname -o)
echo $OS
if [ $OS == "Msys" ]; then
  OS="windows"
  NDK_URL="https://googledownloads.cn/android/repository/android-ndk-r26d-windows.zip"
  NDK_SHA1="c7ea35ffe916082876611da1a6d5618d15430c29"
else
  OS="linux"
  NDK_URL=" https://googledownloads.cn/android/repository/android-ndk-r26d-linux.zip"
  NDK_SHA1="fcdad75a765a46a9cf6560353f480db251d14765"

fi
echo "************************************Build Info*********************************"
echo "Host os :$OS"
echo "Target cpu :$CPU"
echo "Android api :$API"
echo "FFmpeg version :$FFMPEG_VERSION"
echo "************************************Build Info End*****************************"
PACKAGE_SOURCE_DIR=$(pwd)/.package
#下载NDK
if [ ! -d "$PACKAGE_SOURCE_DIR" ]; then
  mkdir $PACKAGE_SOURCE_DIR
fi
if [ ! -d "$ANDROID_NDK_HOME" ]; then
  pushd $PACKAGE_SOURCE_DIR
  if [ ! -d "ndk" ]; then
    if [ -e "ndk.zip" ]; then
      sha1=$(sha1sum ndk.zip)
    fi
	sha1=($sha1)
    echo "${sha1[0]}"
    if [ "$sha1" != "$NDK_SHA1" ]; then
      if [ -e "ndk.zip" ]; then
        rm ndk.zip
      fi
      echo ndk Downloading...
      wget $NDK_URL -O ndk.zip
	  exit 1
    fi
    if [ -d "ndk" ]; then
      rm -rf ndk
    fi
    unzip ndk.zip -d ndk
  fi
  ANDROID_NDK_HOME=$PACKAGE_SOURCE_DIR/ndk/$(ls ndk)
  popd
fi
#下载NDK -end
TOOLCHAIN=$ANDROID_NDK_HOME/toolchains/llvm/prebuilt/$OS-x86_64
echo $TOOLCHAIN

SYSROOT=$TOOLCHAIN/sysroot
case $CPU in
armv7-a)
  ARCH=arm
  CROSS_PREFIX=$TOOLCHAIN/bin/armv7a-linux-androideabi$API-
  USR_LIB=$SYSROOT/usr/lib/armv7a-linux-androideabi/$API
  ;;
armv8-a)
  ARCH=arm64
  CROSS_PREFIX=$TOOLCHAIN/bin/aarch64-linux-android$API-
  USR_LIB=$SYSROOT/usr/lib/aarch64-linux-android/$API
  ;;
i686)
  ARCH=x86
  CROSS_PREFIX=$TOOLCHAIN/bin/i686-linux-android$API-
  USR_LIB=$SYSROOT/usr/lib/i686-linux-android/$API
  FFMPEG_EXTRA_CONFIGURE_FLAGS=--disable-asm
  ;;
x86-64)
  ARCH=x86_64
  CROSS_PREFIX=$TOOLCHAIN/bin/x86_64-linux-android$API-
  USR_LIB=$SYSROOT/usr/lib/x86_64-linux-android/$API
  ;;
esac
PREFIX=$(pwd)/output/ffmpeg${FFMPEG_VERSION}/${API}/${CPU}
PACKAGE_PREFIX=$PACKAGE_SOURCE_DIR/.output/${API}/${CPU}
export CC=${CROSS_PREFIX}clang
export CXX=${CROSS_PREFIX}clang++
CROSS_PREFIX=$TOOLCHAIN/bin/llvm-
#x264
pushd $PACKAGE_SOURCE_DIR
PACKET_X264=x264-master
X264_OUTPUT_DIR=$PACKAGE_PREFIX/x264
FFMPEG_EXTRA_LINK_LIBRARY="$FFMPEG_EXTRA_LINK_LIBRARY $X264_OUTPUT_DIR/lib/libx264.a"
FFMPEG_EXTRA_CFLAGS="$FFMPEG_EXTRA_CFLAGS -I$X264_OUTPUT_DIR/include"
FFMPEG_EXTRA_LDFLAGS="$FFMPEG_EXTRA_LDFLAGS -L$X264_OUTPUT_DIR/lib"
FFMPEG_EXTRA_CONFIGURE_FLAGS="$FFMPEG_EXTRA_CONFIGURE_FLAGS --enable-encoder=libx264 --enable-libx264"
export PKG_CONFIG_PATH="$PKG_CONFIG_PATH:$X264_OUTPUT_DIR/lib/pkgconfig"
if [ ! -e "$X264_OUTPUT_DIR/lib/libx264.a" ]; then
  if [ ! -d "$PACKET_X264" ]; then
    echo x264 Downloading...
    wget https://code.videolan.org/videolan/x264/-/archive/master/x264-master.tar.bz2
    tar -xf $PACKET_X264.tar.bz2
  fi
  if [ "$ARCH" != "x64" ]; then
    PACKET_X264_EXTRA_CONFIGURE_FLAG="--disable-asm"
  fi
  echo x264 Configuring...
  pushd $PACKET_X264
  ./configure \
    --prefix=$X264_OUTPUT_DIR \
    --enable-static \
    --enable-pic \
    --host=$ARCH-linux \
    --disable-opencl \
    --disable-cli \
    --cross-prefix=$CROSS_PREFIX \
    --sysroot=$SYSROOT \
    $PACKET_X264_EXTRA_CONFIGURE_FLAG
  echo x264 Building...
  if [ -e "Makefile" ]; then
    make clean
  fi
  make -j$(nproc) -s
  echo x264 Installing...
  make install
  popd
  popd
fi
#x264 -end
#ffmpeg
pushd $PACKAGE_SOURCE_DIR
FFMPEG_SOURCE_DIR=$(pwd)/ffmpeg$FFMPEG_VERSION
if [ ! -d "$FFMPEG_SOURCE_DIR" ]; then
  echo ffmpeg Downloading...
  git clone -b n$FFMPEG_VERSION --depth 1 https://git.ffmpeg.org/ffmpeg.git $FFMPEG_SOURCE_DIR
  tar -xf $PACKET_X264.tar.bz2
fi
pushd $FFMPEG_SOURCE_DIR
build_ffmpeg() {
  #./configure -h
  # echo ffmpeg surport decoders...
  # ./configure --list-decoders
  # echo ffmpeg surport hwaccels...
  # ./configure --list-hwaccels
  echo ffmpeg Configuring...
  ./configure --target-os=android \
    --prefix=$PREFIX \
    --arch=$ARCH \
    --cpu=$CPU \
    --cc=$CC \
    --cxx=$CXX \
    --disable-ffmpeg \
    --disable-ffplay \
    --disable-ffprobe \
    --enable-gpl \
    --cross-prefix=$CROSS_PREFIX \
    --enable-cross-compile \
    --enable-jni \
    --enable-mediacodec \
    --enable-decoder=h264_mediacodec \
    --enable-decoder=hevc_mediacodec \
    --enable-decoder=vp8_mediacodec \
    --enable-decoder=vp9_mediacodec \
    --enable-decoder=mpeg2_mediacodec \
    --enable-decoder=mpeg4_mediacodec \
    --sysroot=$SYSROOT \
    --extra-cflags="-Os -fpic -DVK_ENABLE_BETA_EXTENSIONS=0 -march=$CPU $FFMPEG_EXTRA_CFLAGS" \
    --extra-ldflags="$FFMPEG_EXTRA_LDFLAGS" \
    --pkg-config="pkg-config --static" \
    $SHARED_OR_STATIC_FLAG \
    $FFMPEG_EXTRA_CONFIGURE_FLAGS
  echo ffmpeg Building...
  if [ -e "Makefile" ]; then
    make clean
  fi
  make -j$(nproc)
  echo ffmpeg Installing...
  make install
}
# SHARED_OR_STATIC_FLAG="--disable-shared --enable-static"
# echo "ffmpeg build static library"
# build_ffmpeg
SHARED_OR_STATIC_FLAG="--enable-shared  --disable-static"
echo "ffmpeg build shared library"
build_ffmpeg
$CC -shared -fPIC \
  $(find $FFMPEG_SOURCE_DIR/fftools -name '*.c' -and -not -name 'ffplay.c' -and -not -name 'ffprobe.c' -and -not -name 'ffplay_renderer.c' -and -not -name 'ffmpeg_qsv.c' -and -not -name 'ffmpeg_videotoolbox.c') \
  -I$FFMPEG_SOURCE_DIR -lm \
  $(find $PREFIX/lib -name "*.so" -and -not -name 'ffmpeg.so' -type f -print) \
  -o $PREFIX/lib/ffmpeg.so
popd
popd
echo "Generated files in: $PREFIX"
#ffmpeg -end

三、生成好的包

已加入第二章生成好的包里。


四、使用示例

1、基本用法

创建一个ffmpeg-android目录,将完整代码复制保存为build.sh

(1)查看用法

./build.sh -h

在这里插入图片描述

(2)确认ffmpeg版本

ffmpeg版本参考:https://git.ffmpeg.org/ffmpeg.git 去掉前缀n
在这里插入图片描述

(3)生成so

生成全平台、api24、ffmpeg6.1.1的so

arm

./build.sh -p armv7-a -a 24 -f 6.1.1

arm64

./build.sh -p armv8-a -a 24 -f 6.1.1

x86

./build.sh -p i686 -a 24 -f 6.1.1

x64

./build.sh -p x86-64 -a 24 -f 6.1.1

生成好的so在build.sh脚本所在目录的output文件夹下
在这里插入图片描述

2、ubuntu中使用

wsl、虚拟机都可以。参考第一章安装必要的工具。

sudo apt install git unzip
./build.sh -p armv7-a -a 24 -f 6.1.1

3、windows msys2中使用

在msys2生成需要参考第二章配置环境,以及安装必要的工具。

pacman -S unzip git
./build.sh -p armv7-a -a 24 -f 6.1.1

总结

以上就是今天讲述的内容,生成ffmpeg安卓so其实并不难,如果熟悉交叉编译以及shell,编译起来还是比较简单的,尤其是想生成最小或者完整依赖的包,最好还是自己生成。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/1670539.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

数字水印 | Python 基于离散小波变换 DWT 的图像水印嵌入(下)

🍍原文: 基于 dwt (离散小波变换) 实现彩色图像水印嵌入部分_2.0 🍍写在前面: 本文在原文的基础上进行了代码补全。 正文 修改了尺寸变换导致的图像失真问题,同时简化了部分代码。 效果确实很好😉 1 通道…

15W 3KVAC隔离 宽电压输入 AC/DC 电源模块——TP15AL系列

TP15AL系列产品是一款小体积裸板式电源,该系列电源输出功率为15W,具有低漏电流小于0.35mA,隔离耐压高达3KV等特点。产品安全可靠,EMC性能好,该系列产品广泛应用于智能家居、充电桩、安防、物联、工控等行业中,如应用于电磁兼容比较恶劣的环境…

Kerberos修改协议为TCP

部署前 修改模板/home/cloud-setup/deploy-forklift/mids/forklift-basic/kde/v1.0/impl/plays/roles/krb5-client/templates/krb5.conf.j2 添加如下参数 udp_preference_limit 1 部署后 界面修改 添加如下参数,并勾选下发配置按钮,重启刷新服务

Linux-04

账号管理 添加账号 useradd 选项 用户名 useradd -m dai删除帐号 userdel 选项 用户名 userdel -r dai修改帐号 usermod 选项 用户名usermod -d /home/user dai (修改位置)切换帐号 su username su dai退出账号 exit $表示普通用户 #表示超级用户&#…

源代码防泄密的关键点:烧录管控

源代码作为企业技术核心的一部分,其保密性和安全性显得尤为重要。然而,随着开源文化的发展,以及开发过程中不可避免的与外界交流,源代码防泄密工作面临着前所未有的挑战。特别是在烧录过程中,由于涉及到硬件层面的操作…

PyWebIO,用 Python 写网站

在Python的世界里,PyWebIO是一个简单而强大的库,它能让你的Python脚本快速拥有一个交互式的网页界面。想象一下,你不需要懂得前端开发,就能创建出用户友好的网页应用,这是多么酷的一件事!今天,我…

排序-快速排序(Quick Sort)

快排的简介 快速排序(Quick Sort)是一种高效的排序算法,采用分治法的策略,其基本思想是选择一个基准元素,通过一趟排序将待排序的数据分割成独立的两部分,其中一部分的所有数据都比另外一部分的所有数据要…

aop获取方法运行时间

Slf4j Component Aspect//aop类 public class TimeAspect {/*Around 环绕通知 用ProceedingJoinPoint Before 前置通知 用JoinPoint(是ProceedingJoinPoint的父类型),用它可以获得方法执行的相关信息,如目标类名,方法…

我是如何免费抵御一个多月的 DDos/CC 攻击的?

今天明月给大家详细分享一下我的博客是如何免费抵御了长达一个多月的 DDos/CC 攻击的,在【现在 DDos/CC 攻击门槛低的可怕!】一文里明月就说过现在 DDos/CC 攻击几乎是没有门槛的,任何一个老鼠屎在群里看到你的博客都可以轻松便捷的发动一次 …

ADOP带你了解:800G OSFP光收发器:演进发布

引言 随着云计算、大数据和人工智能等技术的不断进步,对数据中心的带宽和处理能力要求也在不断提高。在这样的背景下,800G OSFP光收发器的问世,为我们提供了更高速度和更高效率的数据传输解决方案。 800G OSFP光收发器演进路线 路线 1&…

CSS3私有前缀+新增盒模型相关属性+新增背景属性(如果想知道CSS3私有前缀、新增盒模型相关属性的知识点,那么只看这一篇就足够了!)

前言:CSS3 是CSS2 的升级版本,它在CSS2 的基础上,新增了很多强大的新功能,从而解决一些实际面临的问题。 ✨✨✨这里是秋刀鱼不做梦的BLOG ✨✨✨想要了解更多内容可以访问我的主页秋刀鱼不做梦-CSDN博客 先让我们看一下本篇文章的…

vue3 自定义调控参数-简易生成器

vue3 自定义调控参数-简易生成器 文章目录 封装生成器控件如下父组件使用如下: 此功能好像是某厂的在线视频笔试题,当时写完也没有结果。。。我觉得此 demo 适用场景:自定义动态表单时需要定制字段、用户自定义信息等 封装生成器控件如下 /…

阿里云短信提示被攻击怎么解决!!

你是否收到过这样的短信,【阿里云】尊敬的用户:您的IP: 实例名称: 受到攻击流量已超过云盾DDoS基础防护的带宽峰值,服务器的所有访问已被屏蔽,如果35分钟后攻击停止将自动解除否则会延期解除。详情请登录云盾控制台DDo…

SPSS之主成分分析

SPSS中主成分分析功能在【分析】--【降维】--【因子分析】中完成(在SPSS软件中,主成分分析与因子分析均在【因子分析】模块中完成)。 求解主成分通常从分析原始变量的协方差矩阵或相关矩阵着手。 (1)当变量取值的度量…

MySQL中的子查询

子查询,在一个查询语句中又出现了查询语句 子查询可以出现在from和where后面 from 表子查询(结果一般为多行多列)把查询结果继续当一张表对待 where 标量子查询(结果集只有一行一列)查询身高最高的学生,查询到一个最高身高 列子查询(结果集只有一行多列) 对上表进行如下操作 …

STM32 PWM 计数器模式和对齐

STM32 PWM 计数器模式和对齐 1. TIM高级定时器简介2. TIM计数模式2.1 向上计数2.2 向下计数2.3 中心对齐模式(向上/向下计数)2.4 重复计数 3. PWM输出模式3.1 举例看下PWM中心对齐模式,设置参数如下: 4. FOC中PWM相关设置说明4.1 …

webpack如何自定义一个loader

我们在使用脚手架的搭建项目的时候往往都会帮我们配置好所需的loader,接下来讲一下我们要如何自己写一个loader应用到项目中(完整代码在最后) 1. 首先搭建一个项目并找到webpack配置文件(webpack.config.js) 在modul…

arcgis_滑坡易发性评价数据处理过程

arcgis_LSM数据处理过程 地形因子处理环境因子处理获取坐标点的方法arcgis问题arcgis进行克里格插值更改投影方式中国地质数据下载站python矢量转栅格重采样设置像元大小一致,设置环境保证栅格对齐 地形因子处理 原始数据:DEM Elevation: 重采样 Slope、Aspect 设置环境保障…

java入门详细教程——day01

目录 1. Java入门 1.1 Java是什么? 1.2 Java语言的历史 1.3 Java语言的分类 1.4 Java语言的特点 1.4.1 先编译再解释运行 1.4.2 跨平台 1.5 JRE和JDK(记忆) 1.6 JDK的下载和安装(应用) 1.6.1 下载 1.6.2 安…

四款不同类型的企业防泄密软件推荐

在数字化快速发展的今天,企业数据的安全与保密显得愈发重要。防泄密软件作为一种专门的数据保护工具,已经逐渐成为企业不可或缺的安全屏障。本文将深入探讨防泄密软件对企业的意义,并介绍一些市面上主流的防泄密软件。 首先,防泄密…