u-boot移植之一 uboot-2015.04 Makefile分析

发布者:平静的33号最新更新时间:2022-07-25 来源: csdn关键字:u-boot  移植 手机看文章 扫描二维码
随时随地手机看文章

本文以smdk2410为例子说明uboot的生成过程

一 uboot生成

uboot生成步骤如下:

make smdk2410_defconfig

make all


二 uboot生成分析之make smdk2410_defconfig

主Makefile有如下定义:

%config: scripts_basic outputmakefile FORCE

$(Q)$(MAKE) $(build)=scripts/kconfig $@

注:u-boot-2015.04的配置与编译仿照linux重新设计,很多宏展开与linux相同,不再重新说明。

(1)目标

%config,即smdk2410_defconfig

(2)依赖

(2.1)scripts_basic

主Makefile有如下定义:

scripts_basic:

$(Q)$(MAKE) $(build)=scripts/basic

$(Q)rm -f .tmp_quiet_recordmcount

可以转换为如下形式:

scripts_basic:

make -f scripts/Makefile.build obj=scripts/basic

rm -f .tmp_quiet_recordmcount  

相当于make执行scripts/Makefile.build,并设置参数scripts/basic

在scripts/Makefile.build中有如下定义:

__build: $(if $(KBUILD_BUILTIN),$(builtin-target) $(lib-target) $(extra-y))

$(if $(KBUILD_MODULES),$(obj-m) $(modorder-target))

$(subdir-ym) $(always)

@:

其中:依赖仅仅always为fixdep,其他为空。

至于fixdep的生成过程,这里不详细说明,详见linux的make s3c2410_defconfig说明。

(2.2)outputmakefile

为空

(3)$(Q)$(MAKE) $(build)=scripts/kconfig $@

相当于make -f scripts/Makefile.build obj=scripts/kconfig smdk2410_defconfig

相当于make执行scripts/Makefile.build的smdk2410_defconfig标号,并设置obj为scripts/kconfig

其中scripts/Makefile.build包含了scripts/kconfig/Makefile,并在其中有这样的定义:

%_defconfig: $(obj)/conf

$(Q)$< --defconfig=arch/$(SRCARCH)/configs/$@ $(Kconfig)

其中,SRCARCH := ..

可以转换为如下:

smdk2410_defconfig:  scripts/kconfig/conf

scripts/kconfig/conf --defconfig=configs/smdk2410_defconfig Kconfig

相当于执行scripts/kconfig/conf程序,并输入参数--defconfig=configs/smdk2410_defconfig Kconfig

该程序会根据smdk2410的设置将配置信息综合写入主目录下的.config文件。

至于conf如何生成这里不再详述。



(4)分析总结

make smdk2410_defconfig执行如下操作:

(a)构造scripts/basic/fixdep

(b)构造scripts/kconfig/conf

(c)scripts/kconfig/conf --defconfig=configs/smdk2410_defconfig Kconfig



(5)scripts/kconfig/conf的分析

会依次解析configs/smdk2410_defconfig和Kconfig,生成symbol等列表,最后生成.config文件。

注:conf程序过于复杂,在不影响移植的情况下暂且不去分析该程序。  



三 uboot生成分析之make all

主Makefile有如下定义:

all:  $(ALL-y)

ALL-y += u-boot.srec u-boot.bin System.map binary_size_check  

其中,我们主要分析u-boot.bin,其他暂时不分析。

主Makefile有如下定义:

u-boot.bin: u-boot FORCE

$(call if_changed,objcopy)

$(call DO_STATIC_RELA,$<,$@,$(CONFIG_SYS_TEXT_BASE))

$(BOARD_SIZE_CHECK)



(1)u-boot

主Makefile有如下定义:

u-boot:   $(u-boot-init) $(u-boot-main) u-boot.lds

$(call if_changed,u-boot__)

(1.1)u-boot-init

主Makefile有如下定义:

u-boot-init := $(head-y)

主Makefile包含arch/arm/Makefile,在其中有如下定义:

head-y := arch/arm/cpu/$(CPU)/start.o

所以,u-boot-init即arch/arm/cpu/arm/start.o

(1.2)u-boot-main

主Makefile有如下定义:

u-boot-main := $(libs-y)

lib-y项目较多,具体就是一些目录下编译链接到一起的built-in.o,详见附录。

(1.3)u-boot.lds

主Makefile有如下定义:

u-boot.lds: $(LDSCRIPT) prepare FORCE

$(call if_changed_dep,cpp_lds)

(1.3.1)LDSCRIPT

主Makefile中有如下定义:

ifndef LDSCRIPT

ifeq ($(wildcard $(LDSCRIPT)),)

LDSCRIPT := $(srctree)/board/$(BOARDDIR)/u-boot.lds

endif

ifeq ($(wildcard $(LDSCRIPT)),)

LDSCRIPT := $(srctree)/$(CPUDIR)/u-boot.lds

endif

ifeq ($(wildcard $(LDSCRIPT)),)

LDSCRIPT := $(srctree)/arch/$(ARCH)/cpu/u-boot.lds

endif

endif

注:由于对于SMDK2410,LDSCRIPT和CONFIG_SYS_LDSCRIPT未定义,所以忽略部分内容。

(1.3.1.1)第一个if

首先看一下BOARDDIR定义的情况,config.mk中定义了它,但首先需要是否包含该目录。

主Makefile有如下定义:

ifneq ($(wildcard include/config/auto.conf),)

autoconf_is_old := $(shell find . -path ./$(KCONFIG_CONFIG) -newer

include/config/auto.conf)

ifeq ($(autoconf_is_old),)

include $(srctree)/config.mk

include $(srctree)/arch/$(ARCH)/Makefile

endif

endif

其中,文件include/config/auto.conf存在,KCONFIG_CONFIG为.config。

当.config比include/config/auto.conf新的时候,会返回.config。对于SMDK2410,.config先生成,autoconf_is_old为空。

因此包含了config.mk。在config.mk有如下定义:

VENDOR := $(CONFIG_SYS_VENDOR:"%"=%)

BOARD := $(CONFIG_SYS_BOARD:"%"=%)

ifneq ($(BOARD),)

ifdef  VENDOR

BOARDDIR = $(VENDOR)/$(BOARD)

else

BOARDDIR = $(BOARD)

endif

endif

在include/config/auto.conf有如下定义:

CONFIG_SYS_BOARD="smdk2410"

CONFIG_SYS_VENDOR="samsung"

所以BOARDDIR=samsung/smdk2410,

这时LDSCRIPT := board/smdk2410/u-boot.lds,不存在这个文件,进入下一个if。

(1.3.1.2)第二个if

在主config.mk下有定义如下

CPU := $(CONFIG_SYS_CPU:"%"=%)  

CPUDIR=arch/$(ARCH)/cpu$(if $(CPU),/$(CPU),)

在include/config/auto.conf有如下定义:

CONFIG_SYS_CPU="arm920t"

$(arm920t)为空

转化为如下形式:

CPUDIR=arch/arm/cpu

存在arch/arm/cpu/u-boot.lds这个文件,不会进入下个if,LDSCRIPT为arch/arm/cpu/u-boot.lds。

(1.3.2)prepare

主Makefile有如下定义

prepare: prepare0

prepare0: archprepare FORCE

$(Q)$(MAKE) $(build)=.

archprepare: prepare1 scripts_basic

prepare1: prepare2 $(version_h) $(timestamp_h) include/config/auto.conf

prepare2: prepare3 outputmakefile

prepare3: include/config/uboot.release

outputmakefile为空  

其中,scripts_basic实质是生成fixdep docproc这个的过程,在配置已经生成,这里可以忽略了。  

prepare这个伪目标执行的动作如下:

prepare0: include/config/uboot.release include/generated/version_autogenerated.h include/generated/timestamp_autogenerated.h include/config/auto.conf scripts_basic

make -f scripts/Makefile.build obj=.

又是要执行Makefile.build,这次包含了主目录下的Kbuild,其中always为include/generated/generic-asm-offsets.h,实质是生成该文件的过程,主目录下的Kbuild有该文件的标号,这里不详细说明了。

(1.3.3)$(call if_changed_dep,cpp_lds)

实质是执行了cmd_cpp_lds,然后生成一个依赖文件。

主Makefile有如下定义:

cmd_cpp_lds = $(CPP) -Wp,-MD,$(depfile) $(cpp_flags) $(LDPPFLAGS) -ansi

-D__ASSEMBLY__ -x assembler-with-cpp -P -o $@ $<

其中CPP为arm-linux-gcc -E -Wp,-MD,.u-boot.lds.d $(LDPPFLAGS) $(LDPPFLAGS) -ansi

-D__ASSEMBLY__ -x assembler-with-cpp -P -o u-boot.lds arch/arm/cpu/u-boot.lds

意思大概是将arch/arm/cpu/u-boot.lds拷贝到主目录下,并其在其中进行宏展开。

(1.4)$(call if_changed,u-boot__)

相当于执行cmd_u-boot__,在主Makefile有如下定义:

cmd_u-boot__ ?= $(LD) $(LDFLAGS) $(LDFLAGS_u-boot) -o $@

 -T u-boot.lds $(u-boot-init)                             

 --start-group $(u-boot-main) --end-group                 

 $(PLATFORM_LIBS) -Map u-boot.map

具体不展开了,这里可以清晰看出是将u-boot-init和u-boot-main内容按照u-boot.lds指定的方式链接,并生成u-boot.map文件。



(2)$(call if_changed,objcopy)

执行cmd_objcopy,主Makefile有如下定义:

cmd_objcopy = $(OBJCOPY) $(OBJCOPYFLAGS) $(OBJCOPYFLAGS_$(@F)) $< $@

转换为:

arm-linux-objcopy -O binary u-boot u-boot.bin

实质是将elf格式的u-boot转换为计算机可以直接识别的二进制文件u-boot.bin



(3)后两个命令

由于没有对应宏定义,后两行实际未执行任何内容。



(4)u-boot-init u-boot-main的生成

(4.1)u-boot-main

主Makefile有如下定义:  

u-boot-dirs   := $(patsubst %/,%,$(filter %/, $(libs-y))) tools examples

可以知道u-boot-dirs为u-boot-main的内容的目录名,并加上tools和examples

$(sort $(u-boot-init) $(u-boot-main)): $(u-boot-dirs) ;

$(u-boot-dirs): prepare scripts

$(Q)$(MAKE) $(build)=$@

以disk/built-in.o(u-boot-main中的一项)为例子说明(其他同理),并转化为:

disk: prepare scripts

make -f ./scripts/Makefile.build obj=disk

(4.1.1)依赖文件

perpare和scripts依赖文件,一再起前面说明,主要是生成一些准备文件。

(4.1.2)make -f ./scripts/Makefile.build obj=disk

再次执行scripts/Makefile.build下的__build。由于disk/Kbuild不存在,因此scripts/Makefile.build包含disk/Makfile。

__build: $(if $(KBUILD_BUILTIN),$(builtin-target) $(lib-target) $(extra-y))

$(if $(KBUILD_MODULES),$(obj-m) $(modorder-target))

$(subdir-ym) $(always)

@:

(4.1.2.1)obj-y以及生成过程

obj-y可以根据disk/Makfile和配置文件(应该是auto.conf和autoconf.mk)得知,obj-y为disk/part.o和disk/part_dos.o

scripts/Makefile.build有如如下定义:

$(obj)/%.o: $(src)/%.c $(recordmcount_source) FORCE

$(call cmd,force_checksrc)

$(call if_changed_rule,cc_o_c)  

Kbulid中如下定义

cmd = @$(echo-cmd) $(cmd_$(1)) ##实质执行了cmd_force_checksrc

if_changed_rule = $(if $(strip $(any-prereq) $(arg-check) )@set -e; $(rule_$(1))) ##如果改变执行cmd_cc_o_c

实质是执行如下动作:

cmd_force_checksrc = $(CHECK) $(CHECKFLAGS) $(c_flags) $< ;

cmd_cc_o_c = $(CC) $(c_flags) -c -o $@ $<

第一行是检测代码,CHECK实质是检测代码的工具,具体暂时不深入分析。

第二行是一个arm-linux-gcc生成.o文件的过程。

(4.1.2.2)builtin-target  

在scripts/Makefile.build有如下定义:

ifneq ($(strip $(obj-y) $(obj-m) $(obj-) $(subdir-m) $(lib-target)),)

builtin-target := $(obj)/built-in.o

endif

可以知道builtin-target := disk/built-in.o。builtin-target有如下定义:

$(builtin-target): $(obj-y) FORCE

$(call if_changed,link_o_target)  

设置是执行cmd_link_o_target

cmd_link_o_target = $(if $(strip $(obj-y)),

 $(LD) $(ld_flags) -r -o $@ $(filter $(obj-y), $^)

 $(cmd_secanalysis),

 rm -f $@; $(AR) rcs$(KBUILD_ARFLAGS) $@)

能看处这里就是把obj-y(disk/part.o和disk/part_dos.o)链接成disk/built-in.o的过程。

(4.1.2.3)其他依赖

其他依赖均为空  

(4.2)u-boot-init

参考上面u-boot-main的执行过程,如果是在arch/arm/cpu/arm920t执行相比disk目录执行,extra-y不再为空(arch/arm/cpu/arm920t/Makefile下有定义),而是start.o。并且在scripts/Makefile.build有如下定义:

$(obj)/%.o: $(src)/%.S FORCE

$(call if_changed_dep,as_o_S)

可以转化为:

arch/arm/cpu/arm920t/start.o: arch/arm/cpu/arm920t/start.S FORCE

$(call if_changed_dep,as_o_S)

相当于执行cmd_as_o_S

cmd_as_o_S       = $(CC) $(a_flags) -c -o $@ $<

这样便生成了start.o




附录A:

u-boot-init和u-boot-main的内容

u-boot-init:

arch/arm/cpu/arm920t/start.o

u-boot-main:

arch/arm/cpu/built-in.o arch/arm/cpu/arm920t/built-in.o arch/arm/lib/built-in.o board/samsung/common/built-in.o board/samsung/smdk2410/built-in.o common/built-in.o disk/built-in.o drivers/built-in.o drivers/dma/built-in.o drivers/gpio/built-in.o drivers/i2c/built-in.o drivers/mmc/built-in.o drivers/mtd/built-in.o drivers/mtd/nand/built-in.o drivers/mtd/onenand/built-in.o drivers/mtd/spi/built-in.o drivers/mtd/ubi/built-in.o drivers/net/built-in.o drivers/net/phy/built-in.o drivers/pci/built-in.o drivers/power/built-in.o drivers/power/battery/built-in.o drivers/power/fuel_gauge/built-in.o drivers/power/mfd/built-in.o drivers/power/pmic/built-in.o drivers/serial/built-in.o drivers/spi/built-in.o drivers/usb/eth/built-in.o drivers/usb/gadget/built-in.o drivers/usb/host/built-in.o drivers/usb/musb-new/built-in.o drivers/usb/musb/built-in.o drivers/usb/phy/built-in.o drivers/usb/ulpi/built-in.o fs/built-in.o lib/built-in.o net/built-in.o test/built-in.o test/dm/built-in.o



附录B

disk/part.c转化为disk/part.o的命令

arm-linux-gcc -Wp,-MD,disk/.part.o.d  -nostdinc -isystem /home/zcy/arm-linux-gcc/opt/FriendlyARM/toolschain/4.4.3/bin/../lib/gcc/arm-none-linux-gnueabi/4.4.3/include -Iinclude  -I./arch/arm/include -include ./include/linux/kconfig.h -D__KERNEL__ -D__UBOOT__ -DCONFIG_SYS_TEXT_BASE=0x0 -Wall -Wstrict-prototypes -Wno-format-security -fno-builtin -ffreestanding -Os -fno-stack-protector -g -Wno-format-nonliteral -D__ARM__ -marm -mno-thumb-interwork -mabi=aapcs-linux -mword-relocations -ffunction-sections -fdata-sections -fno-common -ffixed-r9 -msoft-float -pipe -march=armv4    -D"KBUILD_STR(s)=#s" -D"KBUILD_BASENAME=KBUILD_STR(part)"  -D"KBUILD_MODNAME=KBUILD_STR(part)" -c -o disk/part.o disk/part.c

[1] [2]
关键字:u-boot  移植 引用地址:u-boot移植之一 uboot-2015.04 Makefile分析

上一篇:u-boot移植之三 uboot-2015.04的移植过程
下一篇:linux内核移植之一 linux-4.1.4的zImage生成(Makefile分析)

推荐阅读最新更新时间:2024-10-31 13:52

S3C6410移植u-boot-2010.3(4)uboot的dnw功能添加
  由于我电脑win7上的DNW-USB驱动一直装不上,所以选择在ubuntu下完成dnw的操作实现与uImage的引导。   先给开发板的uboot添加dnw功能   具体文件可以git这里 https://github.com/plinx/uboot_dnw   1、将cmd_usbd.c拷贝到common目录下   2、添加规则到/common/Makefile # core command ... COBJS-y += cmd_usbd.o   3、将usbd-otg-hs.h,usbd-otg-hs.c拷贝到u-boot/cpu/arm1176/s3c64xx/   4、将regs.h,s3c64
[单片机]
S3C6410<font color='red'>移植</font>u-boot-2010.3(4)uboot的dnw功能添加
基于S3C2440的MiniGUI移植
随着嵌入式系统的迅速发展,图形用户界面(Graphic User Interface,GUI)需求越来越明显。MiniGUI是面向实时嵌入式系统的轻量级图形用户界面支持系统,以轻型、占用资源少、高性能、可配置等特点广泛应用于通信、医疗、工控、电子、机顶盒、多媒体等领域。本文正是针对这种需求,介绍如何在S3C240上移植MiniGUI的全过程。 1 图形用户界面MiniGUI MiniGUI是由原清华大学教师魏永明主持开发的轻量级图形系统,遵循GPL公约。所支持的操作系统已不仅仅限于Linux,它还可以在μCli nux,μC/OS-Ⅱ,eCos和VxWorks等系统上运行。已验证的硬件平台包括Intelx86,ARM(ARM
[单片机]
基于S3C2440的MiniGUI<font color='red'>移植</font>
AVR128单片机最小系统串口,外部中断,跑马灯,uCOS-II移植
实验名称:串口通信实验 功能描述:计算机通过串口向开发板发送数据,开发板将数据原样送回。 实验目的:学习串口通信 实验说明:MCU--M128 内部8M晶振 连接方式:利用串口线将开发板和计算机相连。 单片机源程序如下: /************************************************ 文件:sio.c 用途:结构化串口通信程序 ************************************************/ #include config.h #if USEUART0 siocirqueue RTbuf_UART0; #endif #if USEUART1
[单片机]
U-Boot的启动过程源码分析
U-Boot属于两个阶段的Bootloader,第一阶段的文件为cpu/arm920t/start.S和 board/smdk2410/lowlevel_init.S,前者平台相关,后者开发板相关。 U-Boot第一阶段代码分析 1、硬件设备初始化 cpu的工作模式,关闭WATCHDOG,设置FCLK、HCLK、PCLK的比例,关闭MMU、CACHE。 2、为加载Bootloader的第二阶段代码准备RAM空间 指初始化芯片 3、复制Bootloader的第二阶段代码到RAM空间中 将U-Boot的代码都复制到SDARM中 4、设置好栈 留出一段内存供后面使用 5、跳转到第二阶段代码的C入口点 在跳转之前,还要清除BSS段 U
[单片机]
at91rm9200上u-boot移植
在at91rm9200上移植u-boot ================== 准备工作================= 1.阅读at91rm9200 官方文档有关“引导程序”的章节 对at91rm9200的启动流程有个大概的了解。 at91rm9200引导流程图 Device Setup | | Boot SPI DataFlash Boot -- Download from DataFlash -- run | | TWI EEPROM Boot -- Download from EEPROM -- run | | Parallel Boot -- Download from 8-bit Device -- run | |
[单片机]
U-BOOT的启动流程及移植
1 Bootloader及u-boot简介 Bootloader 代码是芯片复位后进入操作系统之前执行的一段代码,主要用于完成由硬件启动到操作系统启动的过渡,从而为操作系统提供基本的运行环境,如初始化CPU、 堆栈、存储器系统等。Bootloader 代码与CPU 芯片的内核结构、具体型号、应用系统的配置及使用的操作系统等因素有关,其功能类似于PC机的BIOS程序。由于bootloader和CPU及电路板的配置情况有关,因此不可能有通用的bootloader ,开发时需要用户根据具体情况进行移植。嵌入式Linux系统中常用的bootloader有armboot、redboot、blob、u-boot等,其中u-boot是当前比较
[单片机]
μC/OS-III在Cortex-M3处理器上的移植
引言 μC/OS-III是一款基于优先级调度的抢占式实时内核,Micrium公司于2011年8月公开了μC/OS-III的源码,其源码遵循ANSIC标准,因而具有良好的移植性,相信其将会被移植到越来越多的处理器体系上。本文主要完成基于Cortex-M3处理器的μC/OS-III移植,通过本次移植,加深对嵌入式操作系统原理的理解。此外,在μC/OS-III移植成功的基础上进行嵌入式应用程序开发,可以把主要精力集中到应用程序上,而硬件资源交由μC/OS-III管理,从而使得嵌入式应用程序更易开发和维护,在嵌入式软硬件结构变得越来越复杂的今天具有现实意义。 1 μC/OS-III和Cortex-M3特点 相对以前的版本,μC/O
[单片机]
μC/OS-III在Cortex-M3处理器上的<font color='red'>移植</font>
uC/OS-II在ARM系统上的移植与实现
0  引言   在开发嵌入式系统时,一般选择基于ARM 和uC/ OS - II 的嵌入式开发平台,因为ARM 微处理器具有处理速度快、超低功耗、价格低廉、应用前景广泛等优点 . 将uC/ OS - II 移植到ARM 系统之后,可以充分结合两者的优势. 如果一个程序在一个环境里能工作,我们经常希望能将它移植到另一个编译系统、处理器或者操作系统上,这就是移植技术.移植技术可以使一种特定的技术在更加广泛的范围使用,使软件使用更加灵活,不局限于某一条件.uC/OS - II 是由Jean J . Labrosse 先生编写的完整的可移植、固化、裁剪的占先式实时多任务内核.uC/ OS - II 的源代码完全开放,这是其他商业实时内核无
[应用]
小广播
设计资源 培训 开发板 精华推荐

最新单片机文章
何立民专栏 单片机及嵌入式宝典

北京航空航天大学教授,20余年来致力于单片机与嵌入式系统推广工作。

换一换 更多 相关热搜器件

 
EEWorld订阅号

 
EEWorld服务号

 
汽车开发圈

电子工程世界版权所有 京B2-20211791 京ICP备10001474号-1 电信业务审批[2006]字第258号函 京公网安备 11010802033920号 Copyright © 2005-2024 EEWORLD.com.cn, Inc. All rights reserved