一.前提环境
1.Mac: M1 11.4 arm64
2.Qt: Qt5.12.7.
3.FFmpeg:4.2.2
二.遇到的问题
1.ld: symbol(s) not found for architecture x86_64
Mac m1默认编译出来的ffmpeg架构是arm64的,而Qt5.12.7编的程序是macx86_64位的,直接在Qt中引入会报错ld: symbol(s) not found for architecture x86_64,所以这里编译ffmpeg版本的时候需要指定arch为x86_64编译。
编译FFmpeg脚本如下:
# Configure
echo Configure for x86_64
./configure \
--disable-x86asm \
--cc=clang \
--sysroot=/Applications/Xcode.app/Contents/Developer/Platforms/MacOSX.platform/Developer/SDKs/MacOSX11.3.sdk \
--target-os=darwin \
--arch=x86_64 \
--cpu=x86_64 \
--extra-cflags='-arch x86_64 -I/usr/local/include' \
--extra-ldflags='-arch x86_64 -L/usr/local/lib -isysroot /Applications/Xcode.app/Contents/Developer/Platforms/MacOSX.platform/Developer/SDKs/MacOSX11.3.sdk ' \
--enable-cross-compile
#--prefix=mac_x86_64 \
#--disable-swscale-alpha \
#--disable-doc \
#--disable-ffmpeg \
#--disable-ffplay \
#--disable-ffprobe \
#--disable-ffserver \
#--disable-asm \
#--disable-debug \
#--enable-libmp3lame
#
## Make
#make clean
##make
#make && make install
编译完成之后可以用以下命令验证库文件的架构
2.qt中cmake pkg引入遇到的问题
ffmpeg编译好之后是会有pc文件的,在make install 指定的目录下的lib中,编写简单程序的时候我们可以直接用 pkg-config --libs 库名称 来引入库目录而不需要自己再写-L路径.
在qt用cmake建立工程,在CmakeLists.txt中引入ffmpeg路径,一开始我是用的pkg-config方式,但是一直报错。
#cmake引入ffmpeg
set(PKG_CONFIG_EXECUTABLE "/opt/homebrew/bin/pkg-config")
find_package(PkgConfig REQUIRED)
pkg_check_modules(ffmpeg REQUIRED IMPORTED_TARGET libavutil)
target_link_libraries(testArch PRIVATE Qt5::Widgets
PkgConfig::ffmpeg)
这里报错的文件都是ffmpeg依赖的系统文件,一开始我以为是找不到系统文件目录,改了半天,后面还是没法,就放弃用pkg-config这种引入方式了。
改成了直接引入头文件与库文件,如下:
#设置ffmpeg头文件和库路径
set(FFMPEG_PREFIX_PATH /Users/zego/QtProject/testArch/External/FFMPEG/x86_64)
include_directories(
${FFMPEG_PREFIX_PATH}/include/
)
#find_library(AVUTIL_LIBRARY avutil)
FIND_LIBRARY(AVUTIL_LIBRARY avutil ${FFMPEG_PREFIX_PATH}/lib)
target_link_libraries(testArch PRIVATE Qt5::Widgets
${AVUTIL_LIBRARY})
这种方式就能成功编译过。
然后我想为什么直接引入能编译过,为啥用pkg引入的方式不行。想了一下,直接在终端写了个测试文件,引入ffmpeg的文件.
编译命令为:clang -o ffmpeg_test ffmpeg_test_x86_64.c `pkg-config --libs libavutil` --target=x86_64-apple-darwin
注意这里要加上target,不然会报如下错:
ld: warning: ignoring file /usr/local/lib/libavutil.a, building for macOS-arm64 but attempting to link with file built for macOS-x86_64
Undefined symbols for architecture arm64:
编译结果:
可以看出编译是通过的,而且可以运行,但是为什么在qt中cmake引入就会报错呢。
接下来是如何解决为什么pkg引入方式不行的处理方法:
第一步:使用set(CMAKE_VERBOSE_MAKEFILE ON )显示执行构建过程中详细的信息,因为qt中默认cmake编译是不打印具体信息的,要找错误我们肯定要看一下具体信息是什么。
第二步:查看直接引入头文件编译成功的打印信息,如下。
可以看到使用pkgcofig报错找不到的文件在编译过程中是没有出现的,在仔细观察一下,可以看到编译过程中使用了-iframework, -isystem参数,从这里我猜测是不是那些文件已经包含在这里,我们不需要再引入了,为了验证这个猜测,将libavutil.pc依赖的framework都删除掉,然后在qt中进行编译。
果不其然,编译成功。
利用clang++ --help查看一下信息:
这样子就明白了。