编译适配纯鸿蒙系统的ijkplayer中的ffmpeg库

news2024/12/28 5:02:35

    目前bilibili官方的ijkplayer播放器,是只适配Android和IOS系统的。而华为接下来即将发布纯harmony系统,是否有基于harmony系统的ijkplayer可以使用呢?

    鸿蒙版ijkplayer播放器是哪个,如何使用,这个问题,大家可以参考我另一个技术号的文章先行了解一下:鸿蒙版ijkplayer播放器示例工程适配运行

    不过上述提到的这个被鸿蒙化的ijkplayer播放器,里面的ffmpeg库是以已经编译好的ffmpeg的动态库集成进去的。对于需要修改ffmpeg代码的人来说,还需要知道如何编译适配harmony系统的ffmpeg库,从而来替代这个鸿蒙版ijkplayer中的ffmpeg库。

    因此本文想要讲解的重点是,如何从之前的安卓版的ijkplayer仓库中,将ffmpeg编译出适配harmony系统的动态库。

一、基于openHarmony环境编译开源库

    在本文主题正式开始之前,大家也可以通过我另一个技术号的这篇文章,需要先行了解一下如何基于openHarmony环境编译适配harmony系统的动态库:

    基于openHarmony环境编译开源库

二、编译前准备

    编译之前,需要搭建的编译环境,需要下载的工具等。可以先大致参考之前安卓版本的编译环境,可从这篇文章中先行了解一下编译环境即可:ijkplayer编译流程详解

    PS:其中与安卓相关的配置可以不用做。因为对应的是需要下载鸿蒙的编译工具链和文件系统等。

三、修改编译脚本

    我们从上述二中的安卓版的ijkplayer仓库中,对主要编译脚本进行修改,来进行适配。

    主要需要修改的就是android\contrib\tools下的三个脚本:do-compile-openssl.sh、do-compile-ffmpeg.sh和do-detect-env.sh。

    在修改这3个脚本之前,根据“一”中文章所述,先提前下载好鸿蒙的交叉编译工具和文件系统,并在这3个脚本的编译前置脚本中(compile-openssl.sh和compile-ffmpeg.sh),将交叉工具链和文件系统的路径export出来,或者在全局环境变量/etc/profile配置文件export出来路径,如下:

export OHOS_SYSROOT=/home/weekend/openharmony/ohos-sdk/linux/native/sysroot
export OHOS_LLVM=/home/weekend/openharmony/ohos-sdk/linux/native/llvm

    OHOS_SYSROOT和OHOS_LLVM变量在后续的脚本中都是需要的。

1、修改do-detect-env.sh

    do-detect-env.sh脚本主要用来检测编译环境的,在安卓版本中,会检查安卓sdk版本,ndk之类的。在鸿蒙版本中这些就都不需要了。我将这些都去掉。

    然后增加鸿蒙的编译工具链和文件系统的检查,如下:

if [ -z "$OHOS_LLVM" ]; then
    echo "You must define OHOS_LLVM before starting."
	echo "sysroot and llvm is necessary.\n"
    exit 1
fi

if [ -z "$OHOS_SYSROOT" ]; then
    echo "You must define OHOS_SYSROOT before starting."
    echo "sysroot and llvm is necessary.\n"
    exit 1
fi

    实际上,我在3个脚本的开头处,都会对这个进行检查。

    附上完整的修改后的 do-detect-env.sh:

#! /usr/bin/env bash
#
#--------------------
set -e
UNAME_S=$(uname -s)
UNAME_SM=$(uname -sm)
echo "build on $UNAME_SM"

echo "OHOS_SYSROOT=$OHOS_SYSROOT"
echo "OHOS_LLVM=$OHOS_LLVM"

if [ -z "$OHOS_LLVM" ]; then
    echo "You must define OHOS_LLVM before starting."
	echo "sysroot and llvm is necessary.\n"
    exit 1
fi

if [ -z "$OHOS_SYSROOT" ]; then
    echo "You must define OHOS_SYSROOT before starting."
    echo "sysroot and llvm is necessary.\n"
    exit 1
fi


# try to detect NDK version
export IJK_GCC_VER=4.9
export IJK_GCC_64_VER=4.9
export IJK_MAKE_TOOLCHAIN_FLAGS=
export IJK_MAKE_FLAG=

case "$UNAME_S" in
    Darwin)
        export IJK_MAKE_FLAG=-j`sysctl -n machdep.cpu.thread_count`
    ;;
    CYGWIN_NT-*)
        IJK_WIN_TEMP="$(cygpath -am /tmp)"
        export TEMPDIR=$IJK_WIN_TEMP/

        echo "Cygwin temp prefix=$IJK_WIN_TEMP/"
    ;;
esac

2、修改do-compile-openssl.sh

    do-compile-openssl.sh根据“二”中描述,主要是用于编译openssl的。根据上述“一”中的文章所述,主要是需要修改交叉编译工具链,和文件系统。

    将安卓NDK和交叉编译工具链相关的去掉,FF_CROSS_PREFIX=aarch64-linux-android这个是安卓的交叉工具链头,用的gcc。修改为export CC 后面跟着鸿蒙的交叉工具链是llvm目录下的clang,然后target=aarch64-linux-ohos,指明是64位的。

CLANG=$OHOS_LLVM/bin/clang

export CC="$CLANG $OHOS_CFLAGS"
export CFLAGS="$OHOS_CFLAGS --sysroot=${OHOS_SYSROOT}"

    安卓的脚本中有FF_TOOLCHAIN_TOUCH,主要是安卓的ndk中提供的用于交叉编译的一些工具包。在鸿蒙的编译中,这一块就不需要了,直接去掉。就是下面这段是不需要了的:

FF_MAKE_TOOLCHAIN_FLAGS=$IJK_MAKE_TOOLCHAIN_FLAGS
FF_MAKE_FLAGS=$IJK_MAKE_FLAG


FF_MAKE_TOOLCHAIN_FLAGS="$FF_MAKE_TOOLCHAIN_FLAGS --install-dir=$FF_TOOLCHAIN_PATH"
FF_TOOLCHAIN_TOUCH="$FF_TOOLCHAIN_PATH/touch"
if [ ! -f "$FF_TOOLCHAIN_TOUCH" ]; then
    $ANDROID_NDK/build/tools/make-standalone-toolchain.sh \
        $FF_MAKE_TOOLCHAIN_FLAGS \
        --platform=$FF_ANDROID_PLATFORM \
        --toolchain=$FF_TOOLCHAIN_NAME
    touch $FF_TOOLCHAIN_TOUCH;
fi

    只需要在后面编译的时候,指明CFLAGS=--sysroot=xxx,跟着鸿蒙的文件系统目录。

export CFLAGS="$OHOS_CFLAGS --sysroot=${OHOS_SYSROOT}"

    为了确保编译,可以将这些关键的编译相关的都export出来,如下:

export CC="$CLANG $OHOS_CFLAGS"
export CXX="$CLANGXX $OHOS_CFLAGS"
export AR=${OHOS_AR}
export AS=${OHOS_AS}
export NM=${OHOS_NM}
export STRIP=${OHOS_STRIP}
export RANLIB=${OHOS_RANLIB}
export LD=${OHOS_LD}
export LDFLAGS="--rtlib=compiler-rt -fuse-ld=lld"
export CFLAGS="$OHOS_CFLAGS --sysroot=${OHOS_SYSROOT}"

    附上完整的do-compile-openssl.sh供参考,我暂时只保留是arm的32位,64位和x86的64位这三个常用的cpu架构编译。具体如下:

#! /usr/bin/env bash
#--------------------
set -e
if [ -z "$OHOS_LLVM" ]; then
    echo "You must define OHOS_LLVM before starting."
	echo "sysroot and llvm is necessary.\n"
    exit 1
fi

if [ -z "$OHOS_SYSROOT" ]; then
    echo "You must define OHOS_SYSROOT before starting."
    echo "sysroot and llvm is necessary.\n"
    exit 1
fi

#--------------------
# common defines
FF_ARCH=$1
if [ -z "$FF_ARCH" ]; then
    echo "You must specific an architecture 'arm, armv7a, x86, ...'.\n"
    exit 1
fi


FF_BUILD_ROOT=`pwd`

FF_BUILD_NAME=
FF_SOURCE=
FF_CROSS_PREFIX=

FF_CFG_FLAGS=
FF_PLATFORM_CFG_FLAGS=

FF_EXTRA_CFLAGS=
FF_EXTRA_LDFLAGS=

# compile
CLANG=$OHOS_LLVM/bin/clang
CLANGXX=$OHOS_LLVM/bin/clang++
OHOS_AR=$OHOS_LLVM/bin/llvm-ar
OHOS_AS=$OHOS_LLVM/bin/llvm-as
OHOS_NM=$OHOS_LLVM/bin/llvm-nm
OHOS_RANLIB=$OHOS_LLVM/bin/llvm-ranlib
OHOS_STRIP=$OHOS_LLVM/bin/llvm-strip
OBJDUMP=$OHOS_LLVM/bin/llvm-objdump
OHOS_LD=$OHOS_LLVM/bin/ld.lld

OHOS_LIBS="-L${OHOS_LLVM}/lib"
OHOS_INCS="-I${OHOS_LLVM}/include"

OHOS_CFLAGS=

#--------------------
echo ""
echo "--------------------"
echo "[*] do detect env"
echo "--------------------"
. ./tools/do-detect-env.sh
FF_MAKE_FLAGS=$IJK_MAKE_FLAG


#----- armv7a begin -----
if [ "$FF_ARCH" = "armv7a" ]; then
    FF_BUILD_NAME=openssl-armv7a
    FF_SOURCE=$FF_BUILD_ROOT/$FF_BUILD_NAME

    FF_PLATFORM_CFG_FLAGS="linux-armv4"
	OHOS_CFLAGS="--target=arm-linux-ohos -march=armv7-a"


elif [ "$FF_ARCH" = "arm64" ]; then
    FF_BUILD_NAME=openssl-arm64
    FF_SOURCE=$FF_BUILD_ROOT/$FF_BUILD_NAME

    FF_PLATFORM_CFG_FLAGS="linux-aarch64"
	OHOS_CFLAGS="--target=aarch64-linux-ohos"
	
elif [ "$FF_ARCH" = "x86_64" ]; then
    FF_BUILD_NAME=openssl-x86_64
    FF_SOURCE=$FF_BUILD_ROOT/$FF_BUILD_NAME

    FF_PLATFORM_CFG_FLAGS="linux-x86_64"
	OHOS_CFLAGS="--target=x86_64-linux-ohos"

else
    echo "unknown architecture $FF_ARCH";
    exit 1
fi


FF_SYSROOT=$OHOS_SYSROOT
FF_PREFIX=$FF_BUILD_ROOT/build/$FF_BUILD_NAME/output

mkdir -p $FF_PREFIX
# mkdir -p $FF_SYSROOT

#--------------------
echo ""
echo "--------------------"
echo "[*] check openssl env"
echo "--------------------"
export CC="$CLANG $OHOS_CFLAGS"
export CXX="$CLANGXX $OHOS_CFLAGS"
export AR=${OHOS_AR}
export AS=${OHOS_AS}
export NM=${OHOS_NM}
export STRIP=${OHOS_STRIP}
export RANLIB=${OHOS_RANLIB}
export LD=${OHOS_LD}
export LDFLAGS="--rtlib=compiler-rt -fuse-ld=lld"
export CFLAGS="$OHOS_CFLAGS --sysroot=${OHOS_SYSROOT}"
export COMMON_FF_CFG_FLAGS=

FF_CFG_FLAGS="$FF_CFG_FLAGS $COMMON_FF_CFG_FLAGS"

#--------------------
# Standard options:
FF_CFG_FLAGS="$FF_CFG_FLAGS zlib-dynamic"
FF_CFG_FLAGS="$FF_CFG_FLAGS no-asm"
FF_CFG_FLAGS="$FF_CFG_FLAGS no-shared"
FF_CFG_FLAGS="$FF_CFG_FLAGS -fPIC"
FF_CFG_FLAGS="$FF_CFG_FLAGS --openssldir=$FF_PREFIX"
FF_CFG_FLAGS="$FF_CFG_FLAGS $FF_PLATFORM_CFG_FLAGS"

#--------------------
echo ""
echo "--------------------"
echo "[*] configurate openssl"
echo "--------------------"
cd $FF_SOURCE
#if [ -f "./Makefile" ]; then
#    echo 'reuse configure'
#else
    echo "./Configure $FF_CFG_FLAGS"
    ./Configure $FF_CFG_FLAGS
#fi

#--------------------
echo ""
echo "--------------------"
echo "[*] compile openssl"
echo "--------------------"
make depend
make $FF_MAKE_FLAGS
make install_sw

#--------------------
echo ""
echo "--------------------"
echo "[*] link openssl"
echo "--------------------"

3、修改do-compile-ffmpeg.sh

    这个脚本就是真正编译ffmpeg的了,与“2”中的openssl类似,主要是需要修改交叉编译工具链,和文件系统。

    同样的与安卓相关的FF_TOOLCHAIN_TOUCH这一段可以去掉的:

FF_TOOLCHAIN_TOUCH="$FF_TOOLCHAIN_PATH/touch"
if [ ! -f "$FF_TOOLCHAIN_TOUCH" ]; then
    $ANDROID_NDK/build/tools/make-standalone-toolchain.sh \
        $FF_MAKE_TOOLCHAIN_FLAGS \
        --platform=$FF_ANDROID_PLATFORM \
        --toolchain=$FF_TOOLCHAIN_NAME
    touch $FF_TOOLCHAIN_TOUCH;
fi

    将交叉编译工具链中提供的工具等,都export出来,这些可能有些不一定用到,但是export出来有利无害:   

CLANG=$OHOS_LLVM/bin/clang
CLANGXX=$OHOS_LLVM/bin/clang++
OHOS_AR=$OHOS_LLVM/bin/llvm-ar
OHOS_AS=$OHOS_LLVM/bin/llvm-as
OHOS_NM=$OHOS_LLVM/bin/llvm-nm
OHOS_RANLIB=$OHOS_LLVM/bin/llvm-ranlib
OHOS_STRIP=$OHOS_LLVM/bin/llvm-strip
OBJDUMP=$OHOS_LLVM/bin/llvm-objdump
OHOS_LD=$OHOS_LLVM/bin/ld.lld

OHOS_LIBS="-L${OHOS_LLVM}/lib"
OHOS_INCS="-I${OHOS_LLVM}/include"

    同样的将安卓NDK和交叉编译工具链相关的去掉,以arm的64位为例,FF_CROSS_PREFIX=aarch64-linux-android这个是安卓的交叉工具链头,修改为export CC 后面跟着鸿蒙的交叉工具链是llvm目录下的clang,然后FF_EXTRA_CFLAGS和FF_EXTRA_LDFLAGS需要target=aarch64-linux-ohos,指明是64位的,如下:

    FF_EXTRA_CFLAGS="$FF_EXTRA_CFLAGS --target=x86_64-linux-ohos"
    FF_EXTRA_LDFLAGS="$FF_EXTRA_LDFLAGS --target=x86_64-linux-ohos"

    还需要将相关的系统所需头文件,lib库等指明,用于后续编译链接使用:

 OHOS_LIBS="$OHOS_LIBS -L${OHOS_SYSROOT}/usr/lib/aarch64-linux-ohos"
 OHOS_INCS="$OHOS_INCS -I${OHOS_SYSROOT}/usr/include/aarch64-linux-ohos"

    后续会用到CC、LD、AR、STRIP这些,需要都指明一下:

export CC=${CLANG}
export LD=${OHOS_LD}
export AR=${OHOS_AR}
export STRIP=${OHOS_STRIP}

    在ffmpeg的configure中,需要加上--cc,--ld,--strip,如下:

if [ -f "./config.h" ]; then
    echo 'reuse configure'
else
    which $CC
    ./configure $FF_CFG_FLAGS \
        --cc=${CLANG} \
        --ld=${CLANG} \
        --strip=${STRIP} \
        --extra-cflags="$FF_CFLAGS $FF_EXTRA_CFLAGS" \
        --extra-ldflags="$FF_DEP_LIBS $FF_EXTRA_LDFLAGS"
    make clean
fi

    然后在最后的CC编译链接成动态库中,需要将刚才的OHOS_LIBS和OHOS_INCS都加上,不然编译链接会报找不到一些系统的基本库之类。同时为了保持跟鸿蒙版ijkplayer中的ffmpeg库名字一致,将库名改为.z.so结尾。(这个貌似是无所谓的)。如下:

$CC -lm -lz -shared --sysroot=$FF_SYSROOT -Wl,--no-undefined -Wl,-z,noexecstack $FF_EXTRA_LDFLAGS \
    -Wl,-soname,libqfffmpeg.z.so \
    $FF_C_OBJ_FILES \
    $FF_ASM_OBJ_FILES \
    $OHOS_LIBS \
    $OHOS_INCS \
    $FF_DEP_LIBS \
    -o $FF_PREFIX/libqfffmpeg.z.so

    另外在编译过程中发现--enable-asm和--enable-inline-asm打开的话,会编译不过,所以这2个改为disable的:

    FF_CFG_FLAGS="$FF_CFG_FLAGS --disable-asm"
    FF_CFG_FLAGS="$FF_CFG_FLAGS --disable-inline-asm"

    附上完整的do-compile-ffmpeg.sh供参考,我暂时只保留是arm的32位,64位和x86的64位这三个常用的cpu架构编译。具体如下:

#! /usr/bin/env bash
#
#--------------------
echo "===================="
echo "[*] build ffmpeg and check env $1"
echo "===================="
set -e


#--------------------
# common defines
FF_ARCH=$1
FF_BUILD_OPT=$2
echo "FF_ARCH=$FF_ARCH"
echo "FF_BUILD_OPT=$FF_BUILD_OPT"
if [ -z "$FF_ARCH" ]; then
    echo "You must specific an architecture 'arm, armv7a, x86, ...'."
    echo ""
    exit 1
fi

if [ -z "$OHOS_LLVM" ]; then
    echo "You must define OHOS_LLVM before starting."
	echo "sysroot and llvm is necessary.\n"
    exit 1
fi

if [ -z "$OHOS_SYSROOT" ]; then
    echo "You must define OHOS_SYSROOT before starting."
    echo "sysroot and llvm is necessary.\n"
    exit 1
fi


FF_BUILD_ROOT=`pwd`

FF_BUILD_NAME=
FF_SOURCE=
FF_CROSS_PREFIX=
FF_DEP_OPENSSL_INC=
FF_DEP_OPENSSL_LIB=

FF_DEP_LIBSOXR_INC=
FF_DEP_LIBSOXR_LIB=

FF_CFG_FLAGS=

FF_EXTRA_CFLAGS=
FF_EXTRA_LDFLAGS=
FF_DEP_LIBS=

FF_MODULE_DIRS="compat libavcodec libavfilter libavformat libavutil libswresample libswscale"
FF_ASSEMBLER_SUB_DIRS=


#--------------------
echo ""
echo "--------------------"
echo "[*] do detect env"
echo "--------------------"
. ./tools/do-detect-env.sh
FF_MAKE_FLAGS=$IJK_MAKE_FLAG

# compile
CLANG=$OHOS_LLVM/bin/clang
CLANGXX=$OHOS_LLVM/bin/clang++
OHOS_AR=$OHOS_LLVM/bin/llvm-ar
OHOS_AS=$OHOS_LLVM/bin/llvm-as
OHOS_NM=$OHOS_LLVM/bin/llvm-nm
OHOS_RANLIB=$OHOS_LLVM/bin/llvm-ranlib
OHOS_STRIP=$OHOS_LLVM/bin/llvm-strip
OBJDUMP=$OHOS_LLVM/bin/llvm-objdump
OHOS_LD=$OHOS_LLVM/bin/ld.lld

OHOS_LIBS="-L${OHOS_LLVM}/lib"
OHOS_INCS="-I${OHOS_LLVM}/include"

#----- armv7a begin -----
if [ "$FF_ARCH" = "armv7a" ]; then
    FF_BUILD_NAME=ffmpeg-armv7a
    FF_BUILD_NAME_OPENSSL=openssl-armv7a
    FF_BUILD_NAME_LIBSOXR=libsoxr-armv7a
    FF_SOURCE=$FF_BUILD_ROOT/$FF_BUILD_NAME

    FF_CFG_FLAGS="$FF_CFG_FLAGS --arch=arm --cpu=cortex-a8"
    FF_CFG_FLAGS="$FF_CFG_FLAGS --enable-neon"
    FF_CFG_FLAGS="$FF_CFG_FLAGS --enable-thumb"
	
    OHOS_LIBS="$OHOS_LIBS -L${OHOS_SYSROOT}/usr/lib/arm-linux-ohos"
    OHOS_INCS="$OHOS_INCS -I${OHOS_SYSROOT}/usr/include/arm-linux-ohos"

    FF_EXTRA_CFLAGS="$FF_EXTRA_CFLAGS -march=armv7-a -mcpu=cortex-a8 -mfpu=vfpv3-d16 -mfloat-abi=softfp -mthumb --target=arm-linux-ohos"
    FF_EXTRA_LDFLAGS="$FF_EXTRA_LDFLAGS -Wl,--fix-cortex-a8 --target=arm-linux-ohos"

    FF_ASSEMBLER_SUB_DIRS="arm"

elif [ "$FF_ARCH" = "arm64" ]; then
    FF_BUILD_NAME=ffmpeg-arm64
    FF_BUILD_NAME_OPENSSL=openssl-arm64
    FF_BUILD_NAME_LIBSOXR=libsoxr-arm64
    FF_SOURCE=$FF_BUILD_ROOT/$FF_BUILD_NAME

    FF_CFG_FLAGS="$FF_CFG_FLAGS --arch=aarch64 --enable-yasm"
	
    OHOS_LIBS="$OHOS_LIBS -L${OHOS_SYSROOT}/usr/lib/aarch64-linux-ohos"
    OHOS_INCS="$OHOS_INCS -I${OHOS_SYSROOT}/usr/include/aarch64-linux-ohos"

    FF_EXTRA_CFLAGS="$FF_EXTRA_CFLAGS --target=aarch64-linux-ohos"
    FF_EXTRA_LDFLAGS="$FF_EXTRA_LDFLAGS --target=aarch64-linux-ohos"

    FF_ASSEMBLER_SUB_DIRS="aarch64 neon"
	
elif [ "$FF_ARCH" = "x86_64" ]; then
    FF_BUILD_NAME=ffmpeg-x86_64
    FF_BUILD_NAME_OPENSSL=openssl-x86_64
    FF_BUILD_NAME_LIBSOXR=libsoxr-x86_64
    FF_SOURCE=$FF_BUILD_ROOT/$FF_BUILD_NAME

    FF_CFG_FLAGS="$FF_CFG_FLAGS --arch=x86_64 --enable-yasm"
	
    OHOS_LIBS="$OHOS_LIBS -L${OHOS_SYSROOT}/usr/lib/x86_64-linux-ohos"
    OHOS_INCS="$OHOS_INCS -I${OHOS_SYSROOT}/usr/include/x86_64-linux-ohos"

    FF_EXTRA_CFLAGS="$FF_EXTRA_CFLAGS --target=x86_64-linux-ohos"
    FF_EXTRA_LDFLAGS="$FF_EXTRA_LDFLAGS --target=x86_64-linux-ohos"

    FF_ASSEMBLER_SUB_DIRS="x86"	

else
    echo "unknown architecture $FF_ARCH";
    exit 1
fi

if [ ! -d $FF_SOURCE ]; then
    echo ""
    echo "!! ERROR"
    echo "!! Can not find FFmpeg directory for $FF_BUILD_NAME"
    echo "!! Run 'sh init-android.sh' first"
    echo ""
    exit 1
fi

FF_SYSROOT=$OHOS_SYSROOT
FF_PREFIX=$FF_BUILD_ROOT/build/$FF_BUILD_NAME/output
FF_DEP_OPENSSL_INC=$FF_BUILD_ROOT/build/$FF_BUILD_NAME_OPENSSL/output/include
FF_DEP_OPENSSL_LIB=$FF_BUILD_ROOT/build/$FF_BUILD_NAME_OPENSSL/output/lib
FF_DEP_LIBSOXR_INC=$FF_BUILD_ROOT/build/$FF_BUILD_NAME_LIBSOXR/output/include
FF_DEP_LIBSOXR_LIB=$FF_BUILD_ROOT/build/$FF_BUILD_NAME_LIBSOXR/output/lib

case "$UNAME_S" in
    CYGWIN_NT-*)
        FF_SYSROOT="$(cygpath -am $FF_SYSROOT)"
        FF_PREFIX="$(cygpath -am $FF_PREFIX)"
    ;;
esac


mkdir -p $FF_PREFIX
# mkdir -p $FF_SYSROOT

#--------------------
echo ""
echo "--------------------"
echo "[*] check ffmpeg env"
echo "--------------------"
export CC=${CLANG}
export LD=${OHOS_LD}
export AR=${OHOS_AR}
export STRIP=${OHOS_STRIP}

FF_CFLAGS="-O3 -Wall -pipe \
    -std=c99 \
    -ffast-math \
    -fstrict-aliasing -Werror=strict-aliasing \
    -Wno-psabi -Wa,--noexecstack \
    -DANDROID -DNDEBUG"

# cause av_strlcpy crash with gcc4.7, gcc4.8
# -fmodulo-sched -fmodulo-sched-allow-regmoves

# --enable-thumb is OK
#FF_CFLAGS="$FF_CFLAGS -mthumb"

# not necessary
#FF_CFLAGS="$FF_CFLAGS -finline-limit=300"

export COMMON_FF_CFG_FLAGS=
. $FF_BUILD_ROOT/config/module.sh


#--------------------
# with openssl
if [ -f "${FF_DEP_OPENSSL_LIB}/libssl.a" ]; then
    echo "OpenSSL detected"
# FF_CFG_FLAGS="$FF_CFG_FLAGS --enable-nonfree"
    FF_CFG_FLAGS="$FF_CFG_FLAGS --enable-openssl"

    FF_CFLAGS="$FF_CFLAGS -I${FF_DEP_OPENSSL_INC}"
    FF_DEP_LIBS="$FF_DEP_LIBS -L${FF_DEP_OPENSSL_LIB} -lssl -lcrypto"
fi

FF_CFG_FLAGS="$FF_CFG_FLAGS $COMMON_FF_CFG_FLAGS"

#--------------------
# Standard options:
FF_CFG_FLAGS="$FF_CFG_FLAGS --prefix=$FF_PREFIX"

# Advanced options (experts only):
FF_CFG_FLAGS="$FF_CFG_FLAGS "
FF_CFG_FLAGS="$FF_CFG_FLAGS --enable-cross-compile"
FF_CFG_FLAGS="$FF_CFG_FLAGS --target-os=linux"
FF_CFG_FLAGS="$FF_CFG_FLAGS --enable-pic"
# FF_CFG_FLAGS="$FF_CFG_FLAGS --disable-symver"

if [ "$FF_ARCH" = "x86" ]; then
    FF_CFG_FLAGS="$FF_CFG_FLAGS --disable-asm"
else
    # Optimization options (experts only):
    FF_CFG_FLAGS="$FF_CFG_FLAGS --disable-asm"
    FF_CFG_FLAGS="$FF_CFG_FLAGS --disable-inline-asm"
fi

case "$FF_BUILD_OPT" in
    debug)
        FF_CFG_FLAGS="$FF_CFG_FLAGS --disable-optimizations"
        FF_CFG_FLAGS="$FF_CFG_FLAGS --enable-debug"
        FF_CFG_FLAGS="$FF_CFG_FLAGS --disable-small"
    ;;
    *)
        FF_CFG_FLAGS="$FF_CFG_FLAGS --enable-optimizations"
        FF_CFG_FLAGS="$FF_CFG_FLAGS --enable-debug"
        FF_CFG_FLAGS="$FF_CFG_FLAGS --enable-small"
    ;;
esac

#--------------------
echo ""
echo "--------------------"
echo "[*] configurate ffmpeg"
echo "--------------------"
cd $FF_SOURCE
if [ -f "./config.h" ]; then
    echo 'reuse configure'
else
    which $CC
    ./configure $FF_CFG_FLAGS \
        --cc=${CLANG} \
        --ld=${CLANG} \
        --strip=${STRIP} \
        --extra-cflags="$FF_CFLAGS $FF_EXTRA_CFLAGS" \
        --extra-ldflags="$FF_DEP_LIBS $FF_EXTRA_LDFLAGS"
    make clean
fi

#--------------------
echo ""
echo "--------------------"
echo "[*] compile ffmpeg"
echo "--------------------"
cp config.* $FF_PREFIX
make $FF_MAKE_FLAGS > /dev/null
make install
mkdir -p $FF_PREFIX/include/libffmpeg
cp -f config.h $FF_PREFIX/include/libffmpeg/config.h

#--------------------
echo ""
echo "--------------------"
echo "[*] link ffmpeg"
echo "--------------------"
echo $FF_EXTRA_LDFLAGS

FF_C_OBJ_FILES=
FF_ASM_OBJ_FILES=
for MODULE_DIR in $FF_MODULE_DIRS
do
    C_OBJ_FILES="$MODULE_DIR/*.o"
    if ls $C_OBJ_FILES 1> /dev/null 2>&1; then
        echo "link $MODULE_DIR/*.o"
        FF_C_OBJ_FILES="$FF_C_OBJ_FILES $C_OBJ_FILES"
    fi

    for ASM_SUB_DIR in $FF_ASSEMBLER_SUB_DIRS
    do
        ASM_OBJ_FILES="$MODULE_DIR/$ASM_SUB_DIR/*.o"
        if ls $ASM_OBJ_FILES 1> /dev/null 2>&1; then
            echo "link $MODULE_DIR/$ASM_SUB_DIR/*.o"
            FF_ASM_OBJ_FILES="$FF_ASM_OBJ_FILES $ASM_OBJ_FILES"
        fi
    done
done

$CC -lm -lz -shared --sysroot=$FF_SYSROOT -Wl,--no-undefined -Wl,-z,noexecstack $FF_EXTRA_LDFLAGS \
    -Wl,-soname,libqfffmpeg.z.so \
    $FF_C_OBJ_FILES \
    $FF_ASM_OBJ_FILES \
    $OHOS_LIBS \
    $OHOS_INCS \
    $FF_DEP_LIBS \
    -o $FF_PREFIX/libqfffmpeg.z.so

mysedi() {
    f=$1
    exp=$2
    n=`basename $f`
    cp $f /tmp/$n
    sed $exp /tmp/$n > $f
    rm /tmp/$n
}

echo ""
echo "--------------------"
echo "[*] create files for shared ffmpeg"
echo "--------------------"
rm -rf $FF_PREFIX/shared
mkdir -p $FF_PREFIX/shared/lib/pkgconfig
ln -s $FF_PREFIX/include $FF_PREFIX/shared/include
ln -s $FF_PREFIX/libqfffmpeg.z.so $FF_PREFIX/shared/lib/libqfffmpeg.z.so
cp $FF_PREFIX/lib/pkgconfig/*.pc $FF_PREFIX/shared/lib/pkgconfig
for f in $FF_PREFIX/lib/pkgconfig/*.pc; do
    # in case empty dir
    if [ ! -f $f ]; then
        continue
    fi
    cp $f $FF_PREFIX/shared/lib/pkgconfig
    f=$FF_PREFIX/shared/lib/pkgconfig/`basename $f`
    # OSX sed doesn't have in-place(-i)
    mysedi $f 's/\/output/\/output\/shared/g'
    mysedi $f 's/-lavcodec/-lijkffmpeg/g'
    mysedi $f 's/-lavfilter/-lijkffmpeg/g'
    mysedi $f 's/-lavformat/-lijkffmpeg/g'
    mysedi $f 's/-lavutil/-lijkffmpeg/g'
    mysedi $f 's/-lswresample/-lijkffmpeg/g'
    mysedi $f 's/-lswscale/-lijkffmpeg/g'
done

    以上便是最关键的3个脚本的修改,按照上述修改后,便可编译适配纯harmony系统的ffmpeg库。大家可以将我上述附上的3个完整的脚本复制出来跟原本安卓版的脚本进行对比,可以更清晰地知道修改什么地方。

四、编译

    修改脚本之后,便可跟安卓一样运行脚本编译。

    先编译openssl:

./compile-openssl.sh clean
./compile-openssl.sh all

    然后编译ffmpeg:

./compile-ffmpeg.sh clean
./compile-ffmpeg.sh all

    编译完成后,在contrib/build下会有对应cpu架构的ffmpeg和openssl产物文件夹。例如我编译arm64的:

    在ffmpeg-arm64的output目录下,就有最终编译好的libqfffmpeg.z.so动态库:

    亲测替换到鸿蒙版的ijkplayer中,可以正常运行。至此文章结束。

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

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

相关文章

Linux 第二十二章

🐶博主主页:ᰔᩚ. 一怀明月ꦿ ❤️‍🔥专栏系列:线性代数,C初学者入门训练,题解C,C的使用文章,「初学」C,linux 🔥座右铭:“不要等到什么都没有了…

基于FPGA的累加器及数码管显示VHDL代码Quartus仿真

名称:基于FPGA的累加器及数码管显示VHDL代码Quartus仿真(文末获取) 软件:Quartus 语言:VHDL 代码功能: 累加器及数码管显示 1、可以通过按键输入1~9 2、数字输入后进行累加,将累加结果显示…

Day 26 数据库日志管理

数据库日志管理 一:日志管理 1.日志分类 ​ 错误日志 :启动,停止,关闭失败报错。rpm安装日志位置 /var/log/mysqld.log ​ 通用查询日志:所有的查询都记下来 ​ 二进制日志:实现备份,增量备份…

rockchip sensors da215s适配

一 、 RK3568 da215s适配 ,增加一个新的 sensor 驱动需做一些适配工作。 SOC:RK3568 KERNEL:Android 12 二、 Android sensors 架构 三、 Sensors hal 与 kernel driver 的通信框图 四、 Rockchip sensors hal 介绍 代码路径: hardw…

RapidJSON介绍

1.简介 RapidJSON 是一个 C 的 JSON 解析库,由腾讯开源。 支持 SAX 和 DOM 风格的 API,并且可以解析、生成和查询 JSON 数据。RapidJSON 快。它的性能可与strlen() 相比。可支持 SSE2/SSE4.2 加速。RapidJSON 独立。它不依赖于 BOOST 等外部库。它甚至…

上位机图像处理和嵌入式模块部署(树莓派4b镜像烧录经验总结)

【 声明:版权所有,欢迎转载,请勿用于商业用途。 联系信箱:feixiaoxing 163.com】 陆陆续续也烧录了好多次树莓派的镜像了,这里面有的时候很快,有的时候很慢。特别是烧录慢的时候,也不知道是自己…

crossover怎么打开软件 mac怎么下载steam crossover下载的软件怎么运行

CrossOver是一款Mac和Linux平台上的类虚拟机软件,通过CrossOver可以运行Windows的可执行文件。如果你是Mac用户且需要使用CrossOver,但是不知道CrossOver怎么打开软件,如果你想在Mac电脑上玩Windows游戏,但不知道怎么下载Steam&am…

大模型改变了哪些工作方式?

大模型的崛起深刻改变了我们的工作方式。如今,许多行业已广泛应用大型机器学习模型,实现了自动化数据处理、智能决策和高效分析。这一变革不仅释放了大量人力资源,使得人们能够专注于更具创造性的任务,还大幅提升了工作效率和准确…

【mobx-入门与思考】

介绍 mobx 是 nodejs生态中的框架, 主要用于做状态管理,可以监控变量状态的变化。 nodejs中除了mobx,还有个redux,也是做状态管理的,都是比较成熟的框架,二者的选择可以参考 【nodejs状态管理: Redux VS M…

录屏软件哪个好用?这4款不容错过!

在现代社会中,信息的传递和分享变得越来越重要。一个好的录屏软件能够帮助我们将想要分享的信息快速直观地展示给他人。 通过下文推荐的4款录屏软件,我们可以轻松地分享自己的知识、经验和见解,让更多的人受益。 方法一:QQ软件进…

服务器2080ti驱动的卸载与安装

服务器2080ti驱动的卸载与安装 前言1、下载驱动2、驱动卸载与安装2.1 卸载原来驱动2.2 安装新驱动 3、查看安装情况 前言 安装transformers库,运行bert模型时出错,显示torch版本太低,要2.0以上的,所以更新显卡驱动,重…

基于FPGA的数字电子钟VHDL代码Quartus仿真

名称:基于FPGA的数字电子钟VHDL代码Quartus仿真(文末获取) 软件:Quartus 语言:VHDL 代码功能: 数字电子钟 1)设计一个能显示秒、分、时的24小时数字钟 2)用数码管显示出时,分,…

MFC列表控件用ADO添加数据实例

1、本程序基于前期我的博客文章《MFC用ADO连接ACESS数据库实例(免费源码下载)》 程序功能通过编辑框、组合框实时将数据写入ACESS数据库并在列表控件上显示。 2、在主界面资源视图上加上一个按钮控件、两个静态文本、一个编辑框IDC_EDIT1变量名name、一个组合框IDC_COMBO1变量名…

网络机顶盒哪个好?2024畅销网络机顶盒排行榜

因买网络机顶盒踩雷的人不在少数,许多不懂网络机顶盒哪个好的消费者在挑选时会参考网络机顶盒排行榜,这次小编带来了业内最新发布的热销网络机顶盒排行榜,想买网络机顶盒可以看看入围的以下品牌,是目前最受消费者欢迎的品牌。 一&…

参数配置不生效导致海思1151芯片TPC功率超大,引起性能恶化。

• 【Wi-Fi领域】【现网案例4】参数配置不生效导致海思1151芯片TPC功率超大,引起性能恶化。 【问题描述】XXX客户反馈OLT-HG8245W5-6T–Wi-Fi–WA8021V5-LAN-PC组网概率出现近距离测速只有20Mbps 【问题单】DTS2022101410914 【问题分析】 在客户反馈此问题后&#…

面试集中营—JVM篇

一、JVM内存模型 线程独占:栈,本地方法栈,程序计数器; 线程共享:堆,方法区 虚拟机栈:线程私有的,线程执行方法是会创建一个栈阵,用来存储局部变量表,操作栈,…

W801学习笔记二十二:英语背单词学习应用——下

续上篇: W801学习笔记二十一:英语背单词学习应用——上 五、处理用户交互 由于英语也是采用了和唐诗一样的《三分钟限时挑战》《五十题竞速挑战》《零错误闯关挑战》,所以用户交互的逻辑和唐诗是一样的。所以,我们抽一个基类&a…

高级数据结构与算法习题(9)

一、判断题 1、Let S be the set of activities in Activity Selection Problem. Then the earliest finish activity am​ must be included in all the maximum-size subset of mutually compatible activities of S. T F 解析:F。设S是活动选择问题中的一…

Golang Map类型

文章目录 Map介绍Map的定义方式Map的增删查改新增和修改Map元素查找Map元素删除Map元素遍历Map元素 Map元素排序Map切片 Map介绍 Map介绍 在Go中,map是哈希表的引用,是一种key-value数据结构。map类型写作map[K]V,其中K和V分别对应key和value…

深度学习之基于Tensorflow卷积神经网络智能体操健身系统

欢迎大家点赞、收藏、关注、评论啦 ,由于篇幅有限,只展示了部分核心代码。 文章目录 一项目简介 二、功能三、系统四. 总结 一项目简介 一、项目背景 随着人们健康意识的提高和数字化技术的快速发展,智能健身系统逐渐成为健身领域的新趋势。…