买了一块licheepi nano的板子,准备学习以下usb gadget驱动,这个板子上有一颗f1c100s的cpu。这颗cpu是arm926ej-s,内置32MB的DDR,成本很低,研究一下以后拿来做小玩意。
首先下载sdk,
链接: https://pan.baidu.com/s/1MUiKGi5fLiXYbLAkewKM1g 提取码: n1d5
上面链接是我的baidu pan,我在里面添加一个交叉编译器
1.下载盘中的两个文件
解压nano.tar.gz从中抽取kernel和u-boot,我抽取解压目录root下的kernel和u-boot
编译u-boot
make ARCH=arm licheepi_nano_spiflash_defconfig
make CROSS_COMPILE=/home/jjinl/gcc_set/gcc-linaro-7.2.1/bin/arm-linux-gnueabi-
在百度盘中下载arm gcc 7.2.1我直接解压在一个目录中,没有添加到环境变量里面,所以需要给出全路径
u-boot中主要修改的地方
1../drivers/mtd/spi/spi_flash_ids.c中添加xt25f128b的flash信息
代码:
{"xt25f128b", INFO(0x0b4018, 0x0, 64 * 1024, 256, 0) },
2.修改 ./include/configs/suniv.h,添加flash启动
代码:
#ifdef CONFIG_BOOTCOMMAND
#undef CONFIG_BOOTCOMMAND
#define CONFIG_BOOTCOMMAND "sf probe 0 50000000; " \
"sf read 0x80C00000 0x100000 0x4000; " \
"sf read 0x80008000 0x110000 0x400000; " \
"bootz 0x80008000 - 0x80C00000"
#endif
3.修改./arch/arm/dts/suniv-f1c100s-licheepi-nano.dts,添加flash分区信息
代码:
flash@0 {
#address-cells = <1>;
#size-cells = <1>;
compatible = "winbond,w25q128", "jedec,spi-nor";
reg = <0>;
spi-max-frequency = <50000000>;
/* jjinl add*/
partitions {
compatible = "fixed-partitions";
#address-cells = <1>;
#size-cells = <1>;
partition@0 {
label = "u-boot";
reg = <0x000000 0x100000>;
read-only;
};
partition@100000 {
label = "dtb";
reg = <0x100000 0x10000>;
read-only;
};
partition@110000 {
label = "kernel";
reg = <0x110000 0x400000>;
read-only;
};
partition@510000 {
label = "rootfs";
reg = <0x510000 0xAF0000>;
};
};
};
};
u-boot基本只改了这些,其它就是修改配置选项,使用编译器是gcc-linaro-7.2.1-2017.11-x86_64_arm-linux-gnueabi.tar.xz
烧写工具使用sunxi-tools
烧写u-boot到spi flash
sudo ../sunxi-tools/sunxi-fel -p spiflash-write 0 u-boot/u-boot-sunxi-with-spl.bin
### 编译内核
配置内核
make menuconfig ARCH=arm
编译内核
make ARCH=arm CROSS_COMPILE=/home/jjinl/gcc_set/gcc-linaro-7.2.1/bin/arm-linux-gnueabi-
最终生成zImage文件
内核修改的地方
1../drivers/mtd/spi-nor/spi-nor.c,添加flash的支持
代码:
{ "xt25f128b", INFO(0x0b4018, 0, 64 * 1024, 256, 0) },
2../drivers/clk/sunxi-ng/ccu-suniv.c, usb otg bug修复
代码:
static SUNXI_CCU_GATE(usb_phy0_clk, "usb-phy0", "osc24M",
0x0cc, BIT(1), 0);
// 0x0cc, BIT(8), 0);
要注意地方,这个内核包含一个.config文件,内部配置spi控制器默认不对,要选中A31 SPI
在上面我修改u-boot中的dts,实际没有使用u-boot中的dts,使用的是内核源码中dts
linux/arch/arm/boot/dts/suniv-f1c100s-licheepi-nano.dts
他也要像u-boot中做同样修改,我没有使用LCD所以我删除一部分代码
完整的dts如下
// SPDX-License-Identifier: (GPL-2.0+ OR X11)
/*
* Copyright 2018 Icenowy Zheng <icenowy@aosc.io>
*/
/dts-v1/;
#include "suniv-f1c100s.dtsi"
#include <dt-bindings/gpio/gpio.h>
/ {
model = "Lichee Pi Nano";
compatible = "licheepi,licheepi-nano", "allwinner,suniv-f1c100s",
"allwinner,suniv";
aliases {
serial0 = &uart0;
spi0 = &spi0;
};
chosen {
bootargs = "console=ttyS0,115200 earlyprintk panic=5 root=/dev/mtdblock3 rw rootfstype=jffs2 init=/linuxrc";
stdout-path = "serial0:115200n8";
};
reg_vcc3v3: vcc3v3 {
compatible = "regulator-fixed";
regulator-name = "vcc3v3";
regulator-min-microvolt = <3300000>;
regulator-max-microvolt = <3300000>;
};
};
&de {
status = "okay";
};
&mmc0 {
vmmc-supply = <®_vcc3v3>;
bus-width = <4>;
broken-cd;
status = "okay";
};
&otg_sram {
status = "okay";
};
&spi0 {
pinctrl-names = "default";
pinctrl-0 = <&spi0_pins_a>;
status = "okay";
spi-max-frequency = <50000000>;
flash: w25q128@0 {
#address-cells = <1>;
#size-cells = <1>;
compatible = "winbond,xt25f128b", "jedec,spi-nor";
reg = <0>;
spi-max-frequency = <50000000>;
partitions {
compatible = "fixed-partitions";
#address-cells = <1>;
#size-cells = <1>;
partition@0 {
label = "u-boot";
reg = <0x000000 0x100000>;
read-only;
};
partition@100000 {
label = "dtb";
reg = <0x100000 0x10000>;
read-only;
};
partition@110000 {
label = "kernel";
reg = <0x110000 0x400000>;
read-only;
};
partition@510000 {
label = "rootfs";
reg = <0x510000 0xAF0000>;
};
};
};
};
&uart0 {
pinctrl-names = "default";
pinctrl-0 = <&uart0_pins_a>;
status = "okay";
};
&usb_otg {
dr_mode = "otg";
status = "okay";
};
&usbphy {
usb0_id_det-gpio = <&pio 4 2 GPIO_ACTIVE_HIGH>; /* PE2 */
status = "okay";
};
生成文件系统,建立一个rootfs文件夹,补充必要的目录,下载busybox进行编译,
我使用的busybox是之前下载的1.32.1
配置busybox
make menuconfig
编译
make CROSS_COMPILE=/home/jjinl/gcc_set/gcc-linaro-7.2.1/bin/arm-linux-gnueabi-
安装
make install CROSS_COMPILE=/home/jjinl/gcc_set/gcc-linaro-7.2.1/bin/arm-linux-gnueabi-
最终rootfs目录有如下文件
....
生成文件系统jffs2的镜像
rm -f rootfs/bin/busybox
cp busybox-1.32.1/busybox rootfs/bin/busybox
mkfs.jffs2 -s 0x100 -e 0x10000 --pad=0xAF0000 -d rootfs/ -o jffs2.img
烧写内核:
sudo ../sunxi-tools/sunxi-fel -p spiflash-write 0x110000 linux/arch/arm/boot/zImage
烧写dtb:
sudo ../sunxi-tools/sunxi-fel -p spiflash-write 0x100000 linux/arch/arm/boot/dts/suniv-f1c100s-licheepi-nano.dtb
烧写文件系统
sudo ../sunxi-tools/sunxi-fel -p spiflash-write 0x510000 jffs2.img
整个系统重新上电,启动完成。
==========================================================================
从这个分隔符以上是搭建系统一个步骤,下面描述遇到的问题
上电启动后,内核直接panic
[ 1.156192] random: crng init done
[ 1.522992] VFS: Mounted root (jffs2 filesystem) on device 31:3.
[ 1.530200] devtmpfs: mounted
[ 1.537616] Freeing unused kernel memory: 1024K
[ 4.818583] Kernel panic - not syncing: Attempted to kill init! exitcode=0x0000000b
[ 4.818583]
[ 4.827729] CPU: 0 PID: 1 Comm: linuxrc Not tainted 4.15.0-rc8-licheepi-nano #12
[ 4.835101] Hardware name: Allwinner suniv Family
[ 4.839875] [<c010e750>] (unwind_backtrace) from [<c010b768>] (show_stack+0x10/0x14)
[ 4.847631] [<c010b768>] (show_stack) from [<c0116878>] (panic+0xb8/0x230)
[ 4.854508] [<c0116878>] (panic) from [<c0118034>] (do_exit+0x96c/0x9a4)
[ 4.861210] [<c0118034>] (do_exit) from [<c0118bb8>] (do_group_exit+0x3c/0xb4)
[ 4.868431] [<c0118bb8>] (do_group_exit) from [<c0121758>] (get_signal+0x144/0x558)
[ 4.876088] [<c0121758>] (get_signal) from [<c010a9f4>] (do_signal+0xc4/0x404)
[ 4.883314] [<c010a9f4>] (do_signal) from [<c010aefc>] (do_work_pending+0xb8/0xcc)
[ 4.890884] [<c010aefc>] (do_work_pending) from [<c0107e08>] (slow_work_pending+0xc/0x20)
[ 4.899050] Rebooting in 5 seconds..
[ 10.878284] Reboot failed -- System halted
这个问题花了很久才解决。解决办法就是换编译器重新编译busybox。上面baidu pan里面放了一个编译器 arm-2014.05-29-arm-none-linux-gnueabi-i686-pc-linux-gnu.tar.bz2。
最开始遇到这个问题,我以为是浮点不支持,在busybox添加 -mcpu=arm926ej-s -mfloat=soft,静态链接等等选项,反复试了还是不行,错误依旧。
最后想起来通过arm-linux-readelf -a 查看文件格式才发现问题所在
arm-linux-readelf -a busybox输出如下
生成的文件尽然是v7架构,我们f1c100s是arm926ej-s是armv5te架构,这肯定是无法运行
我们编译的u-boot,查看格式
生成的u-boot尽然是v5te格式,再查看内核vmlinux
这个vmlinux也是v5te,看来是编译参数除了问题
问题确认,我就写了简单的hello.c使用编译器编译添加选项,看看能否生成v5te格式的输出。
尝试过程如下:
/home/jjinl/gcc_set/gcc-linaro-7.2.1/bin/arm-linux-gnueabi-gcc hello demo_c.c
/home/jjinl/gcc_set/gcc-linaro-7.2.1/bin/arm-linux-gnueabi-gcc -o hello demo_c.c
/home/jjinl/gcc_set/gcc-linaro-7.2.1/bin/arm-linux-gnueabi-gcc -static -o hello_s demo_c.c
/home/jjinl/gcc_set/gcc-linaro-7.2.1/bin/arm-linux-gnueabi-gcc -static -g -o hello_sg demo_c.c
/home/jjinl/gcc_set/gcc-linaro-7.2.1/bin/arm-linux-gnueabi-gcc -g -o hello_g demo_c.c
/home/jjinl/gcc_set/gcc-linaro-7.2.1/bin/arm-linux-gnueabi-gcc -march=armv4t -o hello_g demo_c.c
/home/jjinl/gcc_set/gcc-linaro-7.2.1/bin/arm-linux-gnueabi-gcc -march=armv4t -mfloat-abi=soft -o hello_g demo_c.c
/home/jjinl/gcc_set/gcc-linaro-7.2.1/bin/arm-linux-gnueabi-gcc -march=armv4t -mfloat-abi=soft mtune=arm926ej-s -o hello_g demo_c.c
/home/jjinl/gcc_set/gcc-linaro-7.2.1/bin/arm-linux-gnueabi-gcc -march=armv4t -mfloat-abi=soft -mtune=arm926ej-s -o hello_g demo_c.c
/home/jjinl/gcc_set/gcc-linaro-7.2.1/bin/arm-linux-gnueabi-gcc -march=armv4t -mfloat-abi=soft -mcpu=arm926ej-s -o hello_g demo_c.c
/home/jjinl/gcc_set/gcc-linaro-7.2.1/bin/arm-linux-gnueabi-gcc -mcpu=arm926ej-s -o hello_g demo_c.c
/home/jjinl/gcc_set/gcc-linaro-7.2.1/bin/arm-linux-gnueabi-gcc -mfloat-abi=soft -mcpu=arm926ej-s -o hello_g demo_c.c
/home/jjinl/gcc_set/gcc-linaro-7.2.1/bin/arm-linux-gnueabi-gcc -static -mfloat-abi=soft -mcpu=arm926ej-s -o hello_g demo_c.c
/home/jjinl/gcc_set/gcc-linaro-7.2.1/bin/arm-linux-gnueabi-gcc -mabi=aapcs-linux -mno-thumb-interwork -mfpu=vfp -marm -march=armv5te -mtune=arm9tdmi -msoft-float -o hello_g demo_c.c
/home/jjinl/gcc_set/gcc-linaro-7.2.1/bin/arm-linux-gnueabi-gcc -nostdinc -D__KERNEL__ -mlittle-endian -Wall -Wundef -Wstrict-prototypes -Wno-trigraphs -fno-strict-aliasing -fno-common -fshort-wchar -Werror-implicit-function-declaration -Wno-format-security -std=gnu89 -fno-PIE -fno-dwarf2-cfi-asm -fno-ipa-sra -mabi=aapcs-linux -mno-thumb-interwork -mfpu=vfp -funwind-tables -marm -D__LINUX_ARM_ARCH__=5 -march=armv5te -mtune=arm9tdmi -msoft-float -Uarm -fno-delete-null-pointer-checks -Wno-frame-address -Wno-format-truncation -Wno-format-overflow -Wno-int-in-bool-context -O2 --param=allow-store-data-races=0 -DCC_HAVE_ASM_GOTO -Wframe-larger-than=1024 -fno-stack-protector -Wno-unused-but-set-variable -Wno-unused-const-variable -fomit-frame-pointer -fno-var-tracking-assignments -Wdeclaration-after-statement -Wno-pointer-sign -fno-strict-overflow -fno-stack-check -fconserve-stack -Werror=implicit-int -Werror=strict-prototypes -Werror=date-time -Werror=incompatible-pointer-types -Werror=designated-init -DKBUILD_BASENAME='"sun4i_ss_hash"' -DKBUILD_MODNAME='"sun4i_ss"' -o hello demo_c.c
/home/jjinl/gcc_set/gcc-linaro-7.2.1/bin/arm-linux-gnueabi-gcc -nostdinc -D__KERNEL__ -mlittle-endian -Wall -Wundef -Wstrict-prototypes -Wno-trigraphs -fno-strict-aliasing -fno-common -fshort-wchar -Werror-implicit-function-declaration -Wno-format-security -std=gnu89 -fno-PIE -fno-dwarf2-cfi-asm -fno-ipa-sra -mabi=aapcs-linux -mno-thumb-interwork -mfpu=vfp -funwind-tables -marm -D__LINUX_ARM_ARCH__=5 -march=armv5te -mtune=arm9tdmi -msoft-float -Uarm -fno-delete-null-pointer-checks -Wno-frame-address -Wno-format-truncation -Wno-format-overflow -Wno-int-in-bool-context -O2 --param=allow-store-data-races=0 -DCC_HAVE_ASM_GOTO -Wframe-larger-than=1024 -fno-stack-protector -Wno-unused-but-set-variable -Wno-unused-const-variable -fomit-frame-pointer -fno-var-tracking-assignments -Wdeclaration-after-statement -Wno-pointer-sign -fno-strict-overflow -fno-stack-check -fconserve-stack -Werror=implicit-int -Werror=strict-prototypes -Werror=date-time -Werror=incompatible-pointer-types -Werror=designated-init -DKBUILD_BASENAME='"sun4i_ss_hash"' -DKBUILD_MODNAME='"sun4i_ss"' -o hello demo_c.c
/home/jjinl/gcc_set/gcc-linaro-7.2.1/bin/arm-linux-gnueabi-gcc -mlittle-endian -Wall -Wundef -Wstrict-prototypes -Wno-trigraphs -fno-strict-aliasing -fno-common -fshort-wchar -Werror-implicit-function-declaration -Wno-format-security -std=gnu89 -fno-PIE -fno-dwarf2-cfi-asm -fno-ipa-sra -mabi=aapcs-linux -mno-thumb-interwork -mfpu=vfp -funwind-tables -marm -D__LINUX_ARM_ARCH__=5 -march=armv5te -mtune=arm9tdmi -msoft-float -Uarm -fno-delete-null-pointer-checks -Wno-frame-address -Wno-format-truncation -Wno-format-overflow -Wno-int-in-bool-context -O2 --param=allow-store-data-races=0 -DCC_HAVE_ASM_GOTO -Wframe-larger-than=1024 -fno-stack-protector -Wno-unused-but-set-variable -Wno-unused-const-variable -fomit-frame-pointer -fno-var-tracking-assignments -Wdeclaration-after-statement -Wno-pointer-sign -fno-strict-overflow -fno-stack-check -fconserve-stack -Werror=implicit-int -Werror=strict-prototypes -Werror=date-time -Werror=incompatible-pointer-types -Werror=designated-init -DKBUILD_BASENAME='"sun4i_ss_hash"' -DKBUILD_MODNAME='"sun4i_ss"' -o hello demo_c.c
/home/jjinl/gcc_set/gcc-linaro-7.2.1/bin/arm-linux-gnueabi-gcc -mlittle-endian -Wall -Wundef -Wstrict-prototypes -Wno-trigraphs -fno-strict-aliasing -fno-common -fshort-wchar -Werror-implicit-function-declaration -Wno-format-security -std=gnu89 -fno-PIE -fno-dwarf2-cfi-asm -fno-ipa-sra -mabi=aapcs-linux -mno-thumb-interwork -mfpu=vfp -funwind-tables -marm -march=armv5te -mtune=arm9tdmi -msoft-float -Uarm -fno-delete-null-pointer-checks -Wno-frame-address -Wno-format-truncation -Wno-format-overflow -Wno-int-in-bool-context -O2 --param=allow-store-data-races=0 -DCC_HAVE_ASM_GOTO -Wframe-larger-than=1024 -fno-stack-protector -Wno-unused-but-set-variable -Wno-unused-const-variable -fomit-frame-pointer -fno-var-tracking-assignments -Wdeclaration-after-statement -Wno-pointer-sign -fno-strict-overflow -fno-stack-check -fconserve-stack -Werror=implicit-int -Werror=strict-prototypes -Werror=date-time -Werror=incompatible-pointer-types -Werror=designated-init -DKBUILD_MODNAME='"sun4i_ss"' -o hello demo_c.c
/home/jjinl/gcc_set/gcc-linaro-7.2.1/bin/arm-linux-gnueabi-gcc -mlittle-endian -Wall -Wundef -Wstrict-prototypes -Wno-trigraphs -fno-strict-aliasing -fno-common -fshort-wchar -Werror-implicit-function-declaration -Wno-format-security -std=gnu89 -fno-PIE -fno-dwarf2-cfi-asm -fno-ipa-sra -mabi=aapcs-linux -mno-thumb-interwork -mfpu=vfp -funwind-tables -marm -march=armv5te -mtune=arm9tdmi -msoft-float -Uarm -fno-delete-null-pointer-checks -Wno-frame-address -Wno-format-truncation -Wno-format-overflow -Wno-int-in-bool-context -O2 --param=allow-store-data-races=0 -Wframe-larger-than=1024 -fno-stack-protector -Wno-unused-but-set-variable -Wno-unused-const-variable -fomit-frame-pointer -fno-var-tracking-assignments -Wdeclaration-after-statement -Wno-pointer-sign -fno-strict-overflow -fno-stack-check -fconserve-stack -Werror=implicit-int -Werror=strict-prototypes -Werror=date-time -Werror=incompatible-pointer-types -Werror=designated-init -static -o hello demo_c.c
/home/jjinl/gcc_set/gcc-linaro-7.2.1/bin/arm-linux-gnueabi-gcc -mabi=aapcs-linux -mno-thumb-interwork -mfpu=vfp -marm -march=armv5te -mtune=arm9tdmi -msoft-float -c hello_g.o demo_c.c
/home/jjinl/gcc_set/gcc-linaro-7.2.1/bin/arm-linux-gnueabi-gcc -mabi=aapcs-linux -mno-thumb-interwork -mfpu=vfp -marm -march=armv5te -mtune=arm9tdmi -msoft-float demo_c.c
/home/jjinl/gcc_set/gcc-linaro-7.2.1/bin/arm-linux-gnueabi-gcc -mabi=aapcs-linux -mno-thumb-interwork -mfpu=vfp -marm -march=armv5te -mtune=arm9tdmi -msoft-float -c demo_c.c
/home/jjinl/gcc_set/gcc-linaro-7.2.1/bin/arm-linux-gnueabi-ld -mabi=aapcs-linux -mno-thumb-interwork -mfpu=vfp -marm -march=armv5te -mtune=arm9tdmi -msoft-float demo_c.o
/home/jjinl/gcc_set/gcc-linaro-7.2.1/bin/arm-linux-gnueabi-ld -mabi=aapcs-linux -mno-thumb-interwork -mfpu=vfp -marm -march=armv5te -mtune=arm9tdmi demo_c.o
/home/jjinl/gcc_set/gcc-linaro-7.2.1/bin/arm-linux-gnueabi-ld -mcpu=arm926ej-s demo_c.o
/home/jjinl/gcc_set/gcc-linaro-7.2.1/bin/arm-linux-gnueabi-ld demo_c.o
/home/jjinl/gcc_set/gcc-linaro-7.2.1/bin/arm-linux-gnueabi-ld -mabi=aapcs-linux -mno-thumb-interwork -mfpu=vfp -marm -march=armv5te -mtune=arm9tdmi -msoft-float demo_c.o
/home/jjinl/gcc_set/gcc-linaro-7.2.1/bin/arm-linux-gnueabi-gcc -mabi=aapcs-linux -mno-thumb-interwork -mfpu=vfp -marm -march=armv5te -mtune=arm9tdmi -msoft-float -c demo_c.c
/home/jjinl/gcc_set/gcc-linaro-7.2.1/bin/arm-linux-gnueabi-ld -o test demo_c.o
不管怎么尝试最终的输出文件依旧是v7架构
网上说你可以分开先编译再链接
生成的.o文件果然是V5TE,但是链接后又变成V7架构,有可能是编译器的crt文件只有v7建构,倒编译器目录去看了以下
crt1.o是V7架构,包括所有的动态库都是V7架构,没办法我去下载linaro的4.9版本,测试以下crt文件还是v7建构,最后在网上找了找到arm-2014.05-29-arm-none-linux-gnueabi-i686-pc-linux-gnu.tar.bz2文件,它的库都是都是v5te,我测试crtbegin这个文件如下图
使用这个编译器重新编译busybox,终于可以正常启动。
或者还有什么办法使用gcc-linaro-7.2.1-2017.11-x86_64_arm-linux-gnueabi.tar.xz编译可用,请大家留言。