目录
4.3、使用uboot的tftp将linux内核、设备树以及Ramdisk写入QSPI Flash
一、准备
1、一台装有Ubuntu的虚拟机。
2、一块有zynq7000系列的板卡
3、vivado开发环境,版本2016.4
4、u-boot、device-tree、kernel以及randisk.image.gz。
二、设置交叉编译环境
1、下载交叉编译链
xilinx-2011.09-50-arm-xilinx-linux-gnueabi.bin,直接搜这个,网上有资源。
2、安装依赖库
sudo apt-get install lib32ncurses5 lib32z1
3、修改shell
sudo dpkg-reconfigure -plow dash,在出现的界面中选no
4、安装
./xilinx-2011.09-50-arm-xilinx-linux-gnueabi.bin,如果提示权限不够,则使用chmod 777添加权限,安装过程一直enter就行
5、配置环境
a)export CROSS_COMPILE=arm-xilinx-linux-gnueabi-
export PATH=/root/CodeSourcery/Sourcery_CodeBench_Lite_for_Xilinx_GNU_Linux/bin:$PATH
注意第二行命令,要根据你实际安装的路径进行设置,如果你安装的时候是用root安装的,则上面的配置是正确的,如果用普通用户,则安装路径可能位于/home/usrname/CodeSourcery/Sourcery_CodeBench_Lite_for_Xilinx_GNU_Linux/bin
上述方法在下次登录时环境变量失效
b) 修改.bashrc文件:
# vi ~/.bashrc
在里面加入:
export PATH="$PATH: /root/CodeSourcery/Sourcery_CodeBench_Lite_for_Xilinx_GNU_Linux/bin "
该方法修改的环境变量在下次登录terminal时生效。
6、验证
arm-xilinx-linux-gnueabi-gcc -v
注:在编译时如果报错:error: unrecognized command line option "-std=gnu11",说明编译器不支持此选项,那么在Makefile中替换此选项-std=gnu11。替换成-std=gnu99或-std=c99或-std=c11等,主要看编译器都支持哪些编译选项,笔者的支持-std=gnu99,。因此在Makefile中替换选项-std=gnu11为-std=gnu99
三、编译u-boot、内核、dtb和制作randisk
3.1、移植u-boot
这一小节用于新版本(2019.1)的u-boot移植
在使用新版u-boot时,发现u-boot也支持设备树。设备树位置arch/arm/dts下面。在移植时:
1)通过拷贝zynq-zed.dts然后修改文件名为zynq-xx.dts,主要注意修改memory的大小,然后一些设备的添加或者删除。
2)拷贝zynq_zed_defconfig,然后修改文件名为zynq_xx_defconfig,然后修改CONFIG_DEFAULT_DEVICE_TREE="zynq-xx"
3.2、编译u-boot
2.1“cd”进入u-boot源码根目录,选择待编译板配置,这里我们使用zynq_zc70x_config
make CROSS_COMPILE=arm-xilinx-linux-gnueabi- zynq_zc70x_config
2.2 执行以下命令编译u-boot
make CROSS_COMPILE=arm-xilinx-linux-gnueabi-
2.3使用命令将生成的u-boot更名为u-boot.elf
mv u-boot u-boot.elf
注:1)如果涉及到修改环境变量的话,请进入到include/configs/zynq-common.h进行修改。注意一个问题,就是uboot默认的env环境变量保存的位置。这里也可以修改u-boot启动时内核、devicetree和文件系统的在FLASH的起始地址以及长度。由于我们使用的QSPI启动,所以需要修改修改内核、设备树及内存文件系统在QSPI的起始位置,步骤如下:
1)切换到bootloader源码目录,打开include/configs/zynq-common.h文件。使用vi zynq-common.h修改以下内核、设备树及内存文件系统在QSPI的起始位置
2)另外一个就是涉及到修改DDR SIZE的大小,include/configs/zynq_zed.h修改#define PHYS_SDRAM_1_SIZE (1024 * 1024 * 1024)
3.3、编译内核
3.1 进入linux源码根目录,选择平台配置命令,生成makefile。xilinx_zynq_defconfig在 arch/arm/configs目录下
make ARCH=arm CROSS_COMPILE=arm-xilinx-linux-gnueabi- xilinx_zynq_defconfig
3.2使用命令进入配置内核界面,配置内核
make ARCH=arm CROSS_COMPILE=arm-xilinx-linux-gnueabi- menuconfig
3.3内核配置修改完成后,保存内核配置,编译内核
make ARCH=arm CROSS_COMPILE=arm-xilinx-linux-gnueabi- UIMAGE_LOADADDR=0x3000000 uImage
注:uImage镜像存放路径:linux_root/arch/arm/boot/。
3.4、编译DTB
4.1设备树源文件存放路径:linux root/arch/arm/boot/dts/ zynq-zc702.dts。
4.2将linux_root/arch/arm/boot/dts/zynq-zc702.dts复制到linux根目录下,重命名为zynq-zc7035.dts,执行以下命令编译dts文件,生成dtb文件:
$./scripts/dtc/dtc -I dts-O dtb -o ./devicetree.dtb ./zynq-zc7035.dts
3.5、制作修改ramdisk文件系统
制作ramdisk用到的是xilinx官方下载的uramdisk.image.gz
5.1去掉 mkimage 生成的 64 bytes 的文件头,生成新的 ramdisk.image.gz。
$dd if=uramdisk.image.gz bs=64 skip=1 of=ramdisk.image.gz
5.2 将ramdisk.image.gz拷贝到开发虚拟机中,解压压缩包:
gunzip ramdisk.image.gz
5.3虚拟机上挂载根文件系统:
chmod u+rwx ramdisk.image
mkdir -p tmp_mnt/
sudo mount -o loop ramdisk.image tmp_mnt/
5.4 进入tmp_mnt目录,根据需求修改
cd tmp_mnt/
5.5同步文件系统并卸载ramdisk
$ sync
$ sudo umount tmp_mnt
5.6用 gzip 压缩 ramdisk.image,生成 ramdisk.image.gz
$ gzip -9 ramdisk.image
5.7用 mkimage 添加文件头,生成新的 uramdisk.image.gz 供 u-boot 使用
$ mkimage -A arm -T ramdisk -C gzip -n Ramdisk -d ramdisk.image.gz uramdisk.image.gz
5.8删除临时文件 ramdisk.image.gz
$ rm ramdisk.image.gz
四、生成fsbl以及QSPI程序固化
4.1、生成fsbl
首先,需要一个板卡的硬件工程,并用vivado软件打开。
1.1 打开工程后,在Flow Navigator窗口中单击如下按钮生成bit文件:
4.1.2 导出硬件信息
成功生成bit文件后,若vivado project目录下无*.sdk文件夹,则直接Export Hardware,并在弹出的对话框中选中Include bitstream。
4.1.3选择File->Launch SDK,进入sdk工程
4.1.4选择File->New->Application Project
4.1.5弹出新建工程界面,输入Project name “zynq_fsbl”,点击“next”
4.1.6选择“Zynq FSBL”,点击finish
4.1.7编译zynq_fsbl工程,工程debug目录下的zynq_fsbl.elf就是需要的fsbl文件
4.2、生成启动文件BOOT.BIN并固化
4.2.1 选择菜单xilinx Tools->Create Boot Image
4.2.2 选择fsbl.bif的存放地址,选择生成bin文件还是mcs文件,然后依次添加fsbl.elf(BootLoader)、bit文件(这里没有用到PL)、应用程序elf文件(这里就是linux的u-boot.elf),最终生成用于固化的bin或者mcs文件。
4.2.3 将生成的BOOT.BIN文件下载到QSPI FLASH
选择菜单选择菜单 Xilinx Tools->Program Flash,在弹出的对话框中选择需要下载的文件,点击Program开始固化程序。
4.2.4 固化完成后断电重启就可以看到u-boot的启动信息。
4.3、使用uboot的tftp将linux内核、设备树以及Ramdisk写入QSPI Flash
uboot启动后进入到uboot命令行,我们需要用到的命令主要是sf命令:
sf erase 从设定地址开始,擦除设定大小的存储空间
sf read 将Flash中内容读到内存中
sf write 将内存中内容写到内存中
setenv serverip 192.168.1.104 设置tftp服务器的IP
tftpboot 0x8000 uImage 将uImage写到内存地址0x8000的位置
4.3.1烧写内核到QSPI Flash
setenv serverip 192.168.1.104 设置tftp服务器的IP
sf probe 0 0 0 初始化QSPI Flash
sf erase 0x100000 0x400000 从0x100000开始擦除,大小0x400000
tftpboot 0x8000 uImage 将文件uImage传输到内存地址0x8000的位置
sf write 0x8000 0x100000 0x400000 将内存地址0x8000开始,大小0x400000的内容写到Flash的0x100000地址
4.3.2 烧写设备树、文件系统
方法与内核烧写一样