前言
本文主要记录bluez的Ubuntu编译和arm交叉编译方法,以及编译过程中遇到的问题和解决方案。
1 源码下载
2 PC编译(Ubuntu22.04)
2.1 解压并进入解压目录
tar -xvf bluez-5.66.tar.xz #解压
cd bluez-5.66/ #进入解压目录
2.2 配置环境
在源码目录下新建一个脚本auto.sh,增加脚本文件可执行权限,并执行脚本(等待报错)。
vi auto.sh #新建脚本
#脚本内容起始
./configure --prefix=/opt/bluez/pc_install \
--mandir=/opt/bluez/pc_install/usr/share/man \
--sysconfdir=/opt/bluez/pc_install/etc \
--localstatedir=/opt/bluez/pc_install/var \
-enable-tools -enable-test --enable-experimental --enable-maintainer-mode --disable-udev \
--enable-library --enable-shared=yes --enable-network --enable-health \
--enable-cups --enable-threads --enable-pie --enable-deprecated \
#脚本内容结束
chmod 777 auto.sh #可执行权限
./auto.sh #执行脚本
迎接第一个错误(看最后一行),缺少glib
那就安装glib,安装结束后,再次执行auto.sh
sudo apt-get install libglib2.0-dev
./auto.sh
迎接第二个错误(看最后一行),缺少dbus(但是可以看到glib检查通过了,第一个错误已解决)
同样的,安装dbus,安装结束后,再次执行auto.sh
sudo apt-get install libdbus-1-dev
./auto.sh
接下来都是同理,缺什么咱就安装什么即可。
缺libical,安装,再次执行
sudo apt-get install libical-dev
./auto.sh
缺readline,安装,再次执行
sudo apt-get install libreadline-dev
./auto.sh
缺rst2man,安装,再次执行
sudo apt-get install python-docutils
./auto.sh
这次没有安装成功,提示没有软件包。
尝试更新软件源,但是无效,还是安装失败。
sudo apt-get update
尝试修复依赖问题,还是无效。
sudo apt-get -f install
尝试安装python3-docutils,安装成功!
sudo apt-get install python3-docutils
python-docutils是一个python库,在Ubutun22.04中,python-docutils可能不再作为一个独立的包存在,而是作为python3-docutils的一部分。
再次执行,可以看到已经配置成功了。接下来就是编译和安装。
./auto.sh
2.3 编译和安装
sudo make
sudo make install
安装结束后的目录参考如下
3 arm交叉编译
3.1 glib库编译
在进行glib编译的前还需要先编译libffi和zlib这两个库
3.1.1 libffi编译
3.1.1.1 源码下载
官网:libffi
版本:libffi-3.4.5
wget https://github.com/libffi/libffi/releases/download/v3.4.5/libffi-3.4.5.tar.gz
下载过程有一点慢
3.1.1.2 解压并进入解压目录
tar -xvf libffi-3.4.5.tar.gz
cd libffi-3.4.5/
3.1.1.3 配置环境
./configure --prefix=$(pwd)/install --host=arm-linux-gnueabihf CC=/usr/local/arm/gcc-linaro-4.9.4-2017.01-x86_64_arm-linux-gnueabihf/bin/arm-linux-gnueabihf-gcc
CC配置成交叉编译器的绝对路径,否则编译可能出错。
3.1.1.4 编译和安装
make
make install
安装后install目录
3.1.2 zlib编译
3.1.2.1 源码下载
官网: zlib Home Site
版本:zlib-1.3.1.tar.xz
3.1.2.2 解压并进入解压目录
tar -xvf zlib-1.3.1.tar.xz
cd zlib-1.3.1/
3.1.2.3 配置环境
./configure --prefix=$(pwd)/install
3.1.2.4 编译和安装
make CC=/usr/local/arm/gcc-linaro-4.9.4-2017.01-x86_64_arm-linux-gnueabihf/bin/arm-linux-gnueabihf-gcc
make install
zlib不支持通过configure配置编译器,所以要手动来指定编译器
CC建议配置成绝对路径,否则有可能出错。
安装后install目录参考如下。
3.1.2 glib编译
3.1.2.1 源码下载
官网:https://download.gnome.org/sources/glib/2.40/glib-2.40.2.tar.xz
版本:glib-2.40.2.tar.xz
glib-2.80.tar.xz解压后目录下没有configure文件。
3.1.2.2 解压并进入解压目录
tar -xvf glib-2.40.2.tar.xz
cd glib-2.40.2/
3.1.2.3 配置环境
首先源码目录下新建一个文件glib.cache,然后输入以下内容
vi glib.cache
#内容如下
glib_cv_long_long_format=ll
glib_cv_stack_grows=no
glib_cv_have_strlcpy=no
glib_cv_have_qsort_r=yes
glib_cv_va_val_copy=yes
glib_cv_uscore=no
glib_cv_rtldglobal_broken=no
ac_cv_func_posix_getpwuid_r=yes
ac_cv_func_posix_getgrgid_r=yes
然后再建一个脚本文件auto.sh,输入以下内容
vi auto.sh
#内容如下
./configure --prefix=$(pwd)/install \
CC=/usr/local/arm/gcc-linaro-4.9.4-2017.01-x86_64_arm-linux-gnueabihf/bin/arm-linux-gnueabihf-gcc \
--host=arm-linux-gnueabihf \
LIBFFI_CFLAGS="-I/home/wjj/projects/wireless/UB64/Bluetooth/tools/bluez/source/libffi-3.4.5/install/include" \
LIBFFI_LIBS="-lffi -L/home/wjj/projects/wireless/UB64/Bluetooth/tools/bluez/source/libffi-3.4.5/install/lib" \
ZLIB_CFLAGS="-I/home/wjj/projects/wireless/UB64/Bluetooth/tools/bluez/source/zlib-1.3.1/install/include" \
ZLIB_LIBS="-lz -L/home/wjj/projects/wireless/UB64/Bluetooth/tools/bluez/source/zlib-1.3.1/install/lib" \
--cache-file=glib.cache --disable-selinux --disable-xattr --disable-libelf
执行脚本auto.sh
chmod 777 auto.sh
vi auto.sh
出现如下错误提示
安装gettext,安装结束后,重新执行auto.sh脚本
sudo apt-get update
sudo apt-get install gettext
可以看到成功生成Makefile,配置成功。
3.1.2.4 编译和安装
make
make install
安装结束后install目录参考如下。
3.2 dbus编译
3.2.1 expat编译
3.2.1.1 源码下载
官网:Welcome to Expat! · Expat XML parser
版本:Expat 2.6.2
3.2.1.2 解压并进入解压目录
tar -xvf expat-2.6.2.tar.xz
cd expat-2.6.2/
3.2.1.3 配置环境
./configure --prefix=$(pwd)/install --host=arm-linux-gnueabihf CC=/usr/local/arm/gcc-linaro-4.9.4-2017.01-x86_64_arm-linux-gnueabihf/bin/arm-linux-gnueabihf-gcc --enable-shared
3.2.1.4 编译和安装
make
make install
编译安装结束后,install目录参考如下。
3.2.2 dbus编译
3.2.2.1 源码下载
dbus-1.15.8.tar.xz解压后目录下没有configure文件。
3.2.2.2 解压并进入解压目录
tar xvf dbus-1.15.0.tar.xz
cd dbus-1.15.0
3.2.2.3 配置环境
源码目录下新建脚本auto.sh,输入以下内容
vi auto.sh
#内容如下
./configure --prefix=$(pwd)/install \
--host=arm-linux-gnueabihf \
CC=/usr/local/arm/gcc-linaro-4.9.4-2017.01-x86_64_arm-linux-gnueabihf/bin/arm-linux-gnueabihf-gcc \
CXX=/usr/local/arm/gcc-linaro-4.9.4-2017.01-x86_64_arm-linux-gnueabihf/bin/arm-linux-gnueabihf-g++ \
--with-xml=expat --without-x \
EXPAT_LIBS="-L/home/wjj/projects/wireless/UB64/Bluetooth/tools/bluez/source/expat-2.6.2/install/lib -lexpat" \
EXPAT_CFLAGS="-I/home/wjj/projects/wireless/UB64/Bluetooth/tools/bluez/source/expat-2.6.2/install/include/" \
enable_selinux="no" --disable-tests
执行脚本auto.sh
chmod 777 auto.sh
./auto.sh
生成Makefile,配置成功。
3.2.2.4 编译和安装
make
make install
安装结束后install目录参考如下。
3.3 libical编译
3.3.1 源码下载
官网:Releases · libical/libical · GitHub
版本:https://github.com/libical/libical/releases/download/v1.0.1/libical-1.0.1.tar.gz
3.3.2 解压并进入解压目录
tar xvf libical-1.0.1.tar.gz
cd libical-1.0.1/
3.3.3 配置环境
libical的编译需要用到cmake,确保已经安装cmake。
在终端执行以下命令
mkdir build #创建目录
cd build/ #进入目录
export CC=/usr/local/arm/gcc-linaro-4.9.4-2017.01-x86_64_arm-linux-gnueabihf/bin/arm-linux-gnueabihf-gcc
export CXX=/usr/local/arm/gcc-linaro-4.9.4-2017.01-x86_64_arm-linux-gnueabihf/bin/arm-linux-gnueabihf-g++
cmake -DCMAKE_INSTALL_PREFIX=$(pwd)/install -DCMAKE_BUILD_TYPE=Release -DSHARED_ONLY=yes ..
同样的方法对libical3.0.18和3.0.11编译失败。
3.3.4 编译和安装
make
make install
编译安装结束后,install目录参考如下。
3.4 readline编译
readline的编译需要ncurses库,先编译ncurses库。
3.4.1 ncurses编译
3.4.1.1 源码下载
3.4.1.2 解压并进入解压目录
tar xvf ncurses-6.4.tar.gz
cd ncurses-6.4/
3.4.1.3 配置环境
./configure --prefix=$(pwd)/install --host=arm-linux-gnueabihf --with-shared
3.4.1.4 编译和安装
make
make install
make install时会提示如下错误,这是因为strip的时候用的是ubuntu自带的strip,而不是arm-linux-gnueabihf-strip,strip
命令用于去除符号信息,以减少最终安装包的大小,所以忽略即可。
安装结束后install目录参考如下。
3.4.2 readline编译
3.4.2.1 源码下载
3.4.2.2 解压并进入解压目录
tar -xvf readline-8.2.tar.gz
cd readline-8.2/
3.4.2.3 配置环境
创建auto.sh脚本,用于配置交叉编译环境和ncurses的头文件和库文件路径。
vi auto.sh #创建脚本
#输入以下内容
./configure \
--host=arm-linux-gnueabihf \
CC=/usr/local/arm/gcc-linaro-4.9.4-2017.01-x86_64_arm-linux-gnueabihf/bin/arm-linux-gnueabihf-gcc \
--prefix=$(pwd)/install \
SHLIB_LIBS="-lncurses -L/home/wjj/projects/wireless/UB64/Bluetooth/tools/bluez/source/ncurses-6.4/install/lib" \
SHLIB_CFLAGS="-I/home/wjj/projects/wireless/UB64/Bluetooth/tools/bluez/source/ncurses-6.4/install/include" \
执行脚本auto.sh
chmod 777 auto.sh
./auto.sh
生成Makefile,配置成功。
3.4.2.4 编译和安装
make
make install
安装结束后install目录参考如下。
到这里为止,bluez的依赖库编译完成,接下来进入正题---bluze的编译。
================================================================
3.5 bluez编译
3.5.1 源码下载
参考本文第一章节1 源码下载
3.5.2 解压并进入解压目录
tar -xvf bluez-5.66.tar.xz #解压
cd bluez-5.66/ #进入解压目录
3.5.3 配置环境
创建一个新目录mypkgconfig,用于存放前面所有依赖库编译生成的pkgconfig。
然后把mypkgconfig的路径添加到环境变量
export PKG_CONFIG_PATH=/home/wjj/projects/wireless/UB64/Bluetooth/tools/bluez/mypkgconfig:$PKG_CONFIG_PATH
创建脚本auto.sh,内容参考如下。其中注意需要手动指定readline编译安装后头文件和库文件路径,否则可能找不到。
注意:这里是参考的网上文章,在配置项中有一个参数disable-udev。如果enable-udev,这里编译的时候会提示找不到libudev。
vi auto.sh
#输入以下内容
./configure --prefix=$(pwd)/install \
--host=arm-linux-gnueabi \
CC=/usr/local/arm/gcc-linaro-4.9.4-2017.01-x86_64_arm-linux-gnueabihf/bin/arm-linux-gnueabihf-gcc \
--mandir=$(pwd)/install/usr/share/man \
--sysconfdir=$(pwd)/install/pc/etc \
--localstatedir=$(pwd)/install/var \
-enable-tools -enable-test --enable-experimental --enable-maintainer-mode --disable-udev \
--enable-library --enable-shared=yes --enable-network --enable-health \
--enable-cups --enable-threads --enable-pie --enable-deprecated \
LDFLAGS="-L/home/wjj/projects/wireless/UB64/Bluetooth/tools/bluez/source/readline-8.2/install/lib -L/home/wjj/projects/wireless/UB64/Bluetooth/tools/bluez/source/ncurses-6.4/install/lib" \
CFLAGS="-I/home/wjj/projects/wireless/UB64/Bluetooth/tools/bluez/source/readline-8.2/install/include" \
执行脚本auto.sh
chmod 777 auto.sh
./auto.sh
打开Makefile,按照下图修改(最后一行LIBS = -lreadline -lncurses)
3.5.4 编译和安装
编译(make)后提示有很多函数重定义
根据提示打开readline.h文件,注释对应函数的声明,参考如下。
重新编译(make),提示下图错误
根据提示打开isotest.c,将592行和597行的%zd修改成%lld。
重新编译就可以通过了,然后安装。
make
sudo make install
安装结束后install目录参考如下。
至此,bluez的交叉编译完成。
补充:eudev编译
上文中编译bluez的时候,在配置项中有一个参数disable-udev。如果enable-udev,编译的时候会提示找不到libudev。需要交叉编译eudev。
源码下载:
https://dev.gentoo.org/~blueness/eudev/eudev-3.2.5.tar.gz
解压并进入解压目录:
tar -xvf eudev-3.2.5.tar.gz
cd eudev-3.2.5
配置环境:
mkdir build
./configure CC=/usr/local/arm/gcc-linaro-4.9.4-2017.01-x86_64_arm-linux-gnueabihf/bin/arm-linux-gnueabihf-gcc AR=/usr/local/arm/gcc-linaro-4.9.4-2017.01-x86_64_arm-linux-gnueabihf/bin/arm-linux-gnueabihf-ar --host=arm-linux-gnueabihf --prefix=$(pwd)/build --disable-kmod --disable-blkid --disable-selinux
注意:编译的时候如果提示找不到selinux.h,可以增加配置项disable-selinux
编译和安装
make
make install
安装完成后,会在目录/build/lib下生成libudev.so。