一.什么是交叉编译:
交叉编译 是在一个平台上生成另一个平台上的可执行代码。 我们再windows上面编写C51代码,并编译成可执行代码,如xx.hex, 是在c51上面运行,不是在windows上面运行,我们在ubuntu上面编写树莓派的代码,并编译成可执行代码,如a.out,是在树莓派上面运行,不是在ubuntu linux上面运行
编译:是在一个平台上生成在该平台上的可执行代码。
二.为什么要交叉编译:
1.因为目的平台上的资源贫乏,无法运行我们所需要编译器
2.树莓派是不是就不需要交叉编译?
错。也要 树莓派有时又是因为目的平台还没有建立,连操作系统都没有,根本谈不上运行什么编译器,操作系统也是代码,也要编译。
3.平台运行需要两样至少东西:bootloader(启动引导代码)以及操作系统核心
宿主机(host) :编辑和编译程序的平台,一般是基于X86的PC机,通常也被称为主机。
目标机(target):用户开发的系统,通常都是非X86平台。host编译得到的可执行代码在target上运行。
三.交叉编译工具链的安装
1.下载地址:https://github.com/raspberrypi/
2.从共享文件夹拷贝到工作目录:cp /mnt/hgfs/share/tools-master.zip .
3.解压:unzip tools-master.zip
4.进入目标文件夹: cd /home/wkk/lessonPI/tools-master/arm-bcm2708/gcc-linaro-arm-linux-gnueabihf-raspbian-x64/bin
5.pwd获得路径;echo $PATH 获得当前环境变量的值
6.临时有效,配置环境变量
PATH 环境变量 export PATH=/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin:/usr/games:/home/CLC/lessonPI/tools-master/arm-bcm2708/gcc-linaro-arm-linux-gnueabihf-raspbian-x64/bin
7.永久有效,配置环境变量
7.1.修改工作目录下的.bashrc 隐藏文件,配置命令终端的:vi /home/CLC/.bashrc
7.2在文件最后一行加入export PATH=/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin:/usr/games:/home/CLC/lessonPI/tools-master/arm-bcm2708/gcc-linaro-arm-linux-gnueabihf-raspbian-x64/bin
7.3.source /home/CLC/.bashrc 加载配置文件,马上生效配置。
四.交叉编译文件:
1.检查下交叉编译工具对不对:arm-linux-gnueabihf-gcc -v4.8.3
2.编译文件:arm-linux-gnueabihf-gcc xxx.c -o xxx
3.如何把编译生成的可执行文件下载到开发板:
scp clientInPi pi@192.168.43.30:/home/pi
指令 文件名 开发板用户名@开发板地址:开发板的绝对路径
五. 带wiringPi库的交叉编译如何进行
1. 正常我们先要交叉编译wiringPi库,编译出的库适合树莓派,这时候交叉编译可执行程序的试试,链接库的格式也是正确的。
2. 通过-I -L来指定:
-I(大写i)表示将路径 /home/CLC/lessonPI/WiringPi/wiringPi作为第一个寻找头文件的目录,寻找的顺序是:/home/CLC/lessonPI/WiringPi/wiringPi-->/usr/include-->/usr/local/include 。
-L 表示先以指定的路径作为第一个寻找库文件的目录,寻找的顺序是:指定路径-->/lib-->/usr/lib-->/usr/local/lib
-l(小写L) 参数就是用来指定程序要在-L指定的路径中链接的库,-l参数紧接着就是库名。
因为链接的库的格式不对,是宿主机的平台,出现以下错误
arm-linux-gnueabihf-gcc demo2.c -I /home/CLC/lessonPI/WiringPi/wiringPi -lwiringPi
/home/CLC/lessonPI/tools-master/arm-bcm2708/gcc-linaro-arm-linux-gnueabihf-raspbian-x64/bin/../lib/gcc/arm-linux-gnueabihf/4.8.3/../../../../arm-linux-gnueabihf/bin/ld: cannot find -lwiringPi
collect2: error: ld returned 1 exit status
3. 把树莓派的wringPI库拿上来用
3.1 软链接:
参考文章: https://www.cnblogs.com/zhangna1998517/p/11347364.html
概念:
1. 软链接文件有类似于Windows的快捷方式。
2. 在符号连接中,文件实际上是一个文本文件,其中包含的有另一文件的位置信息。
3. 你选定的位置上生成一个文件的镜像,不会占用磁盘空间
如何生成:
ln -s libwiringPi.so.2.50 libwiringPi.so
指令 参数 要被链接的文件 软链接文件名字
3.2硬链接:ln libwiringPi.so.2.50 libwiringPi.so
它会在你选定的位置上生成一个和源文件大小相同的文件
六.树莓派Linux源码目录树分析
1.参考资料:https://www.cnblogs.com/senior-engineer/p/4929703.html
2.大约1.3w个C文件 1100w行代码,Linux是开源,免费,LInux开源社区工作者共同维护,爱好,Linux是一个开源的,支持多架构多平台代码,可以执行非常高,但是Linux内核编译出来一般就几M. 4M,因为支持多平台,多架构,所以编译之前要配置,配置成适合的目标平台来用
ARM: 海思 友善之臂 RK 树莓派 nanoPi
X86: PowerPC MIPS
七.树莓派Linux源码配置
1.驱动代码的编写
1.1驱动代码的编译需要一个提前编译好的内核,编译内核就必须配置,配置的最终目标会生成 .config文件,该文件指导Makefile去把有用东西组织成内核
1.2 厂家配linux内核源码,比如说买了树莓派,树莓派linux内核源码
第一种方式:
cp 厂家.config .config
第二种方式:
make menuconfig 一项项配置,通常是基于厂家的config来配置
第三种方式:
完全自己来
2.如何配置树莓派的Linux内核
驱动两种加载方式:
1. 编译进内核 zImage包含了驱动
2. M 模块方式生成驱动文件xxx.ko 系统启动后,通过命令inmosd xxx.ko 加载
内核配置:
ARCH=arm CROSS_COMPILE=arm-linux-gnueabihf- KERNEL=kernel7 make bcm2709_defconfig
指定ARM架构 指定编译器 树莓派 主要核心指令
八.树莓派Linux内核编译
8.1编译:
ARCH=arm CROSS_COMPILE=arm-linux-gnueabihf- KERNEL=kernel7 make -j4 zImage modules dtbs
make指定用多少电脑资源进行编译
zImage生成内核镜像
modules要生成驱动模块
dtbs生成配置文件
8.2 编译成功后,看到源码树目录多了vmlinux,失败则无此文件,成功后,目标zImage镜像arch/arm/boot底下
8.3 打包zImage成树莓派可用的xxx.img
./scripts/mkknlimg arch/arm/boot/zImage ./kernel_new.img
8.4 数据拷贝
8.4.1mkdir data1 data2(注意权限要为可读可写)
8.4.2 挂载U盘
sudo mount /dev/sdb1 data1 一个fat分区,是boot相关的内容,kernel的img
sudo mount /dev/sdb2 data2 一个是ext4分区,也就是系统的根目录分区。
8.5安装modules, 设备驱动文件:(支持 hdmi usb wifi io ...)
sudo ARCH=arm CROSS_COMPILE=arm-linux-gnueabihf- KERNEL=kernel7 make INSTALL_MOD_PATH=/home/chenlc/data2 modules_install
8.6 安装更新 kernel.img 文件,注意镜像名字是kernel7.img
8.6.1 先备份
cd /home/chenlc/data1
cp kernel7.img kernel7OLD.img
8.6.2 再把编译新生成的拷贝到data1,起名kernel7.img
cp kernel_new.img /home/chenlc/data1/kernel7.img
8.7 拷贝配置文件
cp arch/arm/boot/dts/.*dtb* /home/chenlc/data1