目录
1.前言
本文主要就Hi3556v200的U-boot+Liteos方案的编译流程做简要介绍,主要通过make过程的打印来逐步理清编译的过程,本文主要结合编译的打印信息介绍u-boot-hi3556v200.bin的编译过程
U-boot版本:u-boot-2016.11
2.目标依赖
主要目标依赖关系位于uboot/u-boot-2016.11/arch/arm/cpu/armv7/hi3556v200/hw_compressed/Makefile文件
3.编译流程
3.1 image_data.gzip目标
#主Makefile
BINIMAGE=$(CURDIR)/u-boot.bin TOPDIR=$(CURDIR)
image_data.gzip: $(BINIMAGE)
./gzip -fNqc -7 $< > $@
依赖于编译的通用的uboot.bin
编译命令如下:
./gzip -fNqc -7 /data_old/x/Hi3559V200_SmartCam_V5.0.0.1/osdrv/opensource/uboot/u-boot-2016.11/u-boot.bin > image_data.gzip
3.2 $(SRC)目标
SSRC := arch/arm/cpu/armv7/$(SOC)/start.S \
arch/arm/cpu/armv7/$(SOC)/reset.S \
arch/arm/cpu/armv7/$(SOC)/uart.S \
arch/arm/cpu/armv7/$(SOC)/init_registers.c \
arch/arm/cpu/armv7/$(SOC)/lowlevel_init_v300.c \
drivers/ddr/hisilicon/default/ddr_training_impl.c \
drivers/ddr/hisilicon/default/ddr_training_ctl.c \
drivers/ddr/hisilicon/default/ddr_training_boot.c \
drivers/ddr/hisilicon/default/ddr_training_console.c \
drivers/ddr/hisilicon/$(SOC)/ddr_training_custom.c \
lib/hw_dec/hw_decompress.c \
lib/hw_dec/hw_decompress_$(SOC).c \
lib/hw_dec/hw_decompress_v1.c \
lib/hw_dec/hw_decompress_v1.h
SSRC += arch/arm/cpu/armv7/$(SOC)/emmc_boot.c \
arch/arm/cpu/armv7/$(SOC)/himci_boot.c \
arch/arm/lib/div0.c
SRC := $(notdir $(SSRC))
编译规则如下:
$(SRC):
ln -sf ../../../../../../$(filter %/$@,$(SSRC)) $@
主要是在uboot/u-boot-2016.11/arch/arm/cpu/armv7/hi3556v200/hw_compressed/下对SSRC 的文件创建软链接,如为drivers/ddr/hisilicon/default/ddr_training_boot.c创建软链接文件名ddr_training_boot.c
3.3 $(START)目标
START := start.o
%.o: %.S
$(CC) -D__ASSEMBLY__ $(CFLAGS) -o $@ $< -c
TEXTBASE := 0x80700000
CFLAGS :=-g -Os -fno-builtin -ffreestanding \
-D__KERNEL__ -DTEXT_BASE=$(TEXTBASE) \
-I$(TOPDIR)/include \
-I$(TOPDIR)/drivers/ddr/hisilicon/default \
-I$(TOPDIR)/drivers/ddr/hisilicon/$(SOC) \
-I$(TOPDIR)/arch/arm/include \
-I$(TOPDIR)/lib/hw_dec \
-fno-pic -ffunction-sections \
-fdata-sections -fno-common -ffixed-r9 \
-fno-common -pipe -march=armv7-a \
-Wall -Wstrict-prototypes -fno-stack-protector \
-D__LINUX_ARM_ARCH__=7 -D__ARM__ \
-DCONFIG_MMC\
$(MKFLAGS) -fno-strict-aliasing
ifeq ($(ENABLE_MINI_BOOT),y)
CFLAGS += -DENABLE_MINI_BOOT
UBOOT_LDS := u-boot-mini.lds
else
CFLAGS += -g
UBOOT_LDS := u-boot.lds
endif
编译start.S文件,生成start.o
3.4 $(COBJS)之%.o目标
COBJS := lowlevel_init_v300.o \
init_registers.o \
uart.o \
ddr_training_impl.o \
ddr_training_ctl.o \
ddr_training_boot.o \
ddr_training_custom.o \
ddr_training_console.o \
startup.o \
image_data.o \
reset.o
%.o: %.c
$(CC) $(CFLAGS) -Wall -Wstrict-prototypes \
-fno-stack-protector -o $@ $< -c
%.o: %.S
$(CC) -D__ASSEMBLY__ $(CFLAGS) -o $@ $< -c
编译$(COBJS)中的文件
3.5 $(COBJS)之image_data.o目标
image_data.S定义如下,它实际是将image_data.gzip文件嵌入到汇编.S文件中
.section .image,#alloc
.globl input_data
/*gzip source addr must be 16 bytes aligned*/
.balign 16
input_data:
.incbin "image_data.gzip"
.globl input_data_end
input_data_end:
根据编译规则,将生成image_data.o文件,它实际包含了通用uboot.bin的压缩文件
image_data.o: image_data.S image_data.gzip
$(CC) -D__ASSEMBLY__ $(CFLAGS) -o $@ $< -c
3.6 $(BOOT).elf目标
$(BOOT).elf: image_data.gzip $(SRC) $(START) $(COBJS)
$(LD) -Bstatic -T $(UBOOT_LDS) -Ttext $(TEXTBASE) $(START) \
$(COBJS) -Map $(BOOT).map -o $@
$(OBJDUMP) -d $@ > $@.asm
链接命令如下:
arm-himix400-linux-ld -Bstatic -T u-boot.lds -Ttext 0x80700000 start.o
lowlevel_init_v300.o init_registers.o uart.o ddr_training_impl.o ddr_training_ctl.o ddr_training_boot.o ddr_training_custom.o ddr_training_console.o startup.o image_data.o reset.o emmc_boot.o div0.o -Map u-boot-hi3556v200.map -o u-boot-hi3556v200.elf
链接脚本中指定了链接地址为0x80700000 ,最终链接生成了u-boot-hi3556v200.elf文件
3.7 $(BOOT).tmp目标
$(BOOT).tmp: $(BOOT).elf
$(OBJCOPY) -O srec $< $(BOOT).srec
$(OBJCOPY) -j .text -O binary $< $(BOOT).text
$(OBJCOPY) --gap-fill=0xff -O binary $< $@
arm-himix400-linux-objcopy -O srec u-boot-hi3556v200.elf u-boot-hi3556v200.srec
arm-himix400-linux-objcopy -j .text -O binary u-boot-hi3556v200.elf u-boot-hi3556v200.text
arm-himix400-linux-objcopy --gap-fill=0xff -O binary u-boot-hi3556v200.elf u-boot-hi3556v200.tmp
生成u-boot-hi3556v200.tmp的 binary格式
3.8 $(BOOT).bin目标
BOOT := u-boot-$(SOC)
REG := $(wildcard $(TOPDIR)/*.reg $(TOPDIR)/.reg)
.PHONY: $(BOOT).bin
$(BOOT).bin: $(BOOT).tmp regfile
@dd if=./$(BOOT).tmp of=./tmp1 bs=1 count=64 2>/dev/null
@dd if=$(REG) of=./tmp2 bs=8192 conv=sync 2>/dev/null
@dd if=./$(BOOT).tmp of=./tmp3 bs=1 skip=8256 2>/dev/null
@cat tmp1 tmp2 tmp3 > $(BOOT).bin
@rm -f tmp1 tmp2 tmp3
@chmod 754 $(BOOT).bin
@cp -fv $@ $(TOPDIR)
@echo $(BOOT).bin is Ready.
- 通过dd将u-boot-hi3556v200.tmp写入tmp1文件
- 将reg文件写入tmp2文件
- 将u-boot-hi3556v200.tmp跳过8256字节写入tmp3文件(TODO)
- 最终将tmp1,tmp2,tmp3写入u-boot-hi3556v200.bin文件
4.readelf查看u-boot-hi3556v200.bin
ubuntu@ct-srv12:~/Hi3559V200_SmartCam_V5.0.0.1/osdrv/opensource/uboot/u-boot-2016.11/arch/arm/cpu/armv7/hi3556v200/hw_compressed$ arm-himix100-linux-readelf -S u-boot-hi3556v200.elf
There are 22 section headers, starting at offset 0x45b18:
Section Headers:
[Nr] Name Type Addr Off Size ES Flg Lk Inf Al
[ 0] NULL 00000000 000000 000000 00 0 0 0
[ 1] .text PROGBITS 80700000 008000 0051d4 00 AX 0 0 64
[ 2] .image PROGBITS 807051e0 00d1e0 02587b 00 A 0 0 16
[ 3] .rodata PROGBITS 8072aa5c 032a5c 0000cb 00 A 0 0 4
[ 4] .bss.hw_blk_total NOBITS 8072ab28 032b28 000004 00 WA 0 0 4
[ 5] .bss.hw_dec_cur_b NOBITS 8072ab2c 032b28 000004 00 WA 0 0 4
[ 6] .bss.hw_dec_eop NOBITS 8072ab30 032b28 000004 00 WA 0 0 4
[ 7] .bss.hw_dec_sop NOBITS 8072ab34 032b28 000004 00 WA 0 0 4
[ 8] .bss.hw_dec_type NOBITS 8072ab38 032b28 000004 00 WA 0 0 4
[ 9] .ARM.attributes ARM_ATTRIBUTES 00000000 032b27 00002b 00 0 0 1
[10] .comment PROGBITS 00000000 032b52 00002d 01 MS 0 0 1
[11] .debug_line PROGBITS 00000000 032b7f 001a6f 00 0 0 1
[12] .debug_info PROGBITS 00000000 0345ee 006712 00 0 0 1
[13] .debug_abbrev PROGBITS 00000000 03ad00 00137b 00 0 0 1
[14] .debug_aranges PROGBITS 00000000 03c080 000418 00 0 0 8
[15] .debug_str PROGBITS 00000000 03c498 001680 01 MS 0 0 1
[16] .debug_loc PROGBITS 00000000 03db18 0049a9 00 0 0 1
[17] .debug_ranges PROGBITS 00000000 0424c1 000a18 00 0 0 1
[18] .debug_frame PROGBITS 00000000 042edc 000a60 00 0 0 4
[19] .symtab SYMTAB 00000000 04393c 001650 10 20 245 4
[20] .strtab STRTAB 00000000 044f8c 000a82 00 0 0 1
[21] .shstrtab STRTAB 00000000 045a0e 00010a 00 0 0 1
Key to Flags:
W (write), A (alloc), X (execute), M (merge), S (strings), I (info),
L (link order), O (extra OS processing required), G (group), T (TLS),
C (compressed), x (unknown), o (OS specific), E (exclude),
y (purecode), p (processor specific)
最终生成的u-boot-hi3556v200.bin图示如下:
其中ddr_cmd.bin为drivers/ddr/hisilicon/default/cmd_bin/ddr_cmd.bin,用于ddr training,它被嵌入到汇编文件/drivers/ddr/hisilicon/default/ddr_cmd_loc.S中
/* DDR Training command codes location. Copy from DDR to SRAM to train DDR. */
.section .image,#alloc
.globl ddr_training_cmd_start
ddr_training_cmd_start:
.incbin "drivers/ddr/hisilicon/default/cmd_bin/ddr_cmd.bin"
.globl ddr_training_cmd_end
ddr_training_cmd_end: