举一反三,相信您看懂并操作了本文章所说的之后,任何交叉编译对您来说都不是难题,很多时候只是对环境的配置。 不要吝啬分享您所学到的知识。任何问题到最后都会解决的,所以不要急。
前言
通常,开源软件最终都会使用 Makefile 来编译或安装,但 Makefile 的生成一般都会有下面几种方式:
- 源码直接提供了 Makefile 文件;
- 由 configure 脚本生成 Makefile ;
- 由autogen 脚本生成 Makefile 。
接下来我们就讲解第二种,源码中提供 configure 脚本来生成 Makefile 的。
交叉编译 – 源码提供 Configure 脚本
Makefle 指定 编译器
CROSS_COMPILE=/opt/arm-anykav500-linux-uclibcgnueabi/bin/arm-anykav500-linux-uclibcgnueab-
CC=${CROSS_COMPILE}gcc
(arm-anykav500-linux-uclibcgnueab-gcc 这个指的就是我们的交叉编译器,不同的板子交叉编译器是不一样的)
进入主题(以 sqlite3 为例子)
- 下载源码库
wget https://www.sqlite.org/2021/sqlite-autoconf-3350400.tar.gz
- 解压源码库,进入有 configure 的文件夹
tar -zxvf sqlite-autoconf-3350400.tar.gz
- 在使用 configure 脚本生成 Makefile 文件之前,需要先导出交叉编译器工具链相应的环境变量
export CROSS_COMPILE=/opt/arm-anykav500-linux-uclibcgnueabi/bin/arm-anykav500-linux-uclibcgnueab-
export CC=${CROSS_COMPILE}gcc
export AS=${CROSS_COMPILE}as
export AR=${CROSS_COMPILE}ar
export LD=${CROSS_COMPILE}ld
export NM=${CROSS_COMPILE}nm
export RANLIB=${CROSS_COMPILE}ranlib
export OBJDUMP=${CROSS_COMPILE}objdump
export STRIP=${CROSS_COMPILE}strip
- 接下来执行 configure 脚本,它将会根据这些环境变量来生成相应的 Makefile 文件。
./configure --prefix=/usr/local/sqlite/ --build=i686-pc-linux --host=arm-linux --enable-static
解析上面 configure 的参数:
–prefix 用来指定执行 make install 时的目标文件安装路径,需要注意的是这里必须使用绝对路径;
–build=i686-pc-linux 用来指定交叉编译的宿主机平台,这里为 i686-pc-linux ;
–host=arm-linux 用来指定交叉编译的目标运行平台,这里为 arm-linux;
–enable-static 用来指定在编译生成动态库的同时,还生成静态库文件;
上面的这些选项基本上是开源源代码 ./confgure 的 通用选项,除此以外不同的软件包还提供其它不同的 feature 选项。在执行这个脚本之前,我们通常会使用 –help 选项查看其使用帮助信息,看看这个软件包可以提供哪些其它的功能或选项。
./configure --help
在 configure 完成之后,它将会生成 Makefile 文件。打开Makefile文件,我们将会看到所有编译器工具都替换成交叉编译器工具链,安装目录 prefix 参数也替换成了我们在 ./configure 时传入的参数:
-
生成 Makefile 文件之后,我们就可以 make、sudo make install 了
-
查看编译生成的 sqlite 可执行程序格式
-
将编译输出的文件打包拷贝到 目标运行平台 上
-
在 目标主机上解压缩
假设是在 /mnt/ 目录下解压
- 接下来我们在目标主机上导出可执行文件和动态库的路径,就可以测试 sqlite 命令了。
export LD_LIBRARY_PATH=/mnt/sqlite/lib:$LD_LIBRARY_PATH
export PATH=/mnt/sqlite/bin:$PATH
sqlite3 --version
3.42.0 2023-05-16 12:36:15 831d0fb2836b71c9bc51067c49fee4b8f18047814f2ff22d817d25195cf350b0
当然,如果我们有 root 的权限,也可以把 可执行文件拷贝到 /usr/bin 路径下,把动态库文件拷贝到 /usr/lib 下,这样我们就可以直接使用了。
编写程序验证
程序
/*********************************************************************************
* Copyright: (C) 2024 Zhu Lijun
* All rights reserved.
*
* Filename: test.c
* Description: This file tests sqlte3 whether can work after crossing compile sqlite3 lib.
*
* Version: 1.0.0(04/07/2024)
* Author: zhulijun <3262465970@qq.com>
* ChangeLog: 1, Release initial version on "04/07/2024 10:36:35 AM"
*
********************************************************************************/
#include <stdio.h>
#include <sqlite3.h>
int main(int argc, char* argv[])
{
sqlite3 *db;
char *zErrMsg = 0;
int rc;
rc = sqlite3_open("test.db", &db);
if( rc ){
printf("Can't open database: %s\n", sqlite3_errmsg(db));
return -1;
}
else{
printf("Opened database successfully\n");
}
sqlite3_close(db);
}
编译程序 —— Makefile
CROSS_COMPILE=/opt/arm-anykav500-linux-uclibcgnueabi/bin/arm-anykav500-linux-uclibcgnueabi-
CC=${CROSS_COMPILE}gcc
AR=${CROSS_COMPILE}ar
TARGET=test.c
OUTPUT=test
all:
${CC} ${TARGET} -o ${OUTPUT} -I /usr/local/sqlite/include -L /usr/local/sqlite/lib -lsqlite3
将编译出来的文件 test 传输到目标平台上,并执行它
执行成功~~