uboot之主Makefile的分析

1、uboot版本号的确定

VERSION = 1
PATCHLEVEL = 3
SUBLEVEL = 4
EXTRAVERSION =
U_BOOT_VERSION = $(VERSION).$(PATCHLEVEL).$(SUBLEVEL)$(EXTRAVERSION)
VERSION_FILE = $(obj)include/version_autogenerated.h

U_BOOT_VERSION = $(VERSION).$(PATCHLEVEL).$(SUBLEVEL)$(EXTRAVERSION)这句代码,代表了uboot的最终格式。

例如这里U_BOOT_VERSION = 1.3.4

VERSION:主版本号

PATCHLEVEL:次版本号

SUBLEVEL:再次版本号

EXTRAVERSION:

 

2、HOSTARCH和HOSTOS的确定

HOSTARCH := $(shell uname -m | \
	sed -e s/i.86/i386/ \
	    -e s/sun4u/sparc64/ \
	    -e s/arm.*/arm/ \
	    -e s/sa110/arm/ \
	    -e s/powerpc/ppc/ \
	    -e s/ppc64/ppc/ \
	    -e s/macppc/ppc/)

(1)$(shell uname -m) :就是执行shell命令:uname -m,结果就是将当前的主机硬件架构名称,在Ubuntu中结果为i686.

(2) “ | ”:在Makefile中的含义为,把前面的表达式输出结果,作为后面表达式的输入,这里就是将i686作为后面代码sed -e s/i.86/i386/ 的输入。

(3)sed -e s/i.86/i386/  :sed就是字符串比较指令,-e代表相等的意思,s就是替换,如果比较的字符串和i.86(.代表的任意符号的意思)相等的时候,就使用i386替换该字符串输出。所以这里的HOSTARCH的结果为i386。

HOSTOS := $(shell uname -s | tr '[:upper:]' '[:lower:]' | \
	    sed -e 's/\(cygwin\).*/cygwin/')

(1)shell uname -s:shell命令uname -s,显示操作系统的名称,这里Ubuntu的结果为Linux,

(2)tr命令可以对来自标准输入的字符进行替换、压缩和删除。它可以将一组字符变成另一组字符,经常用来编写优美的单行命令,作用很强大。

[:upper:]:代表所用的大写字母。

[:lower:]:代表所有的小写字母。

$(shell uname -s | tr '[:upper:]' '[:lower:]':把所用的大写字母变成小写字母,所里这里输出linux。

备注:这里还有一种执行shell命令的方法:反引号的方式。

 

3、静默编译:即不会输出相关的一些信息。

# Allow for silent builds
ifeq (,$(findstring s,$(MAKEFLAGS)))
XECHO = echo
else
XECHO = :
endif

当我们在编译uboot的时候,可以同通过传递的参数make -s来使用该功能能。

MAKWFLAGS,代表输入的参数。

 

4、编译方法:原地编译和单独输出文件夹编译的方式。

(1)原地编译:编译出来的.o和.c直接放在一起

(2)单独输出文件:基本思路就是在编译的时候另外指定一个输出目录。

用法:指定输出文件目录

make O = 输出目录;

export BUILD_DIR = 输出目录,然后make,这两个命令都可以指定输出目录,但是第一个的优先级更好。意思就是当我们同时使用两个命令的时候,第一个命令起作用。

note:由于这两种编译方式的不同,就会导致,后面代码的差别的。也就是 OBJTREE和SRCTREE的是否相同的。

 

5、OBJTREE、SRCTREE、TOPDIR环境变量

 

OBJTREE		:= $(if $(BUILD_DIR),$(BUILD_DIR),$(CURDIR))
SRCTREE		:= $(CURDIR)
TOPDIR		:= $(SRCTREE)
LNDIR		:= $(OBJTREE)
export	TOPDIR SRCTREE OBJTREE

OBJTREE:代表编译出来的.o文件的存放目录的根目录。

SRCTREE:源码目录,也就是源代码的根目录,也就是当前目录。

总结:OBJTREE就是为了实现记录编译后的.o文件,往哪里放,就是为了实现make O=xxx的这种编译方式。

6、MKCONFIG环境变量

MKCONFIG	:= $(SRCTREE)/mkconfig
export MKCONFIG

MKCONFIG是一个环境变量,它所对应的数值,代表的是一个文件mkconfig,源码目录底下的,是一个脚本文件,就是我们的配置脚本,很重要的一个文件。

 

7、include $(obj)include/config.mk

# load ARCH, BOARD, and CPU configuration
include $(obj)include/config.mk
export    ARCH CPU BOARD VENDOR SOC

这个config.mk是配置过程中生成的makefile文件,不是源码自带的,就是我们在make x210_sd_config配置uboot的时候生成的,这个config.mk中的内容为:

ARCH   = arm
CPU    = s5pc11x
BOARD  = x210
VENDOR = samsung
SOC    = s5pc110

通过包含这个文件,将这些环境变量导出。这些环境变量,都是在配置的时候生成,例如配置目标对应的命令,会传递这几个参数:

x210_sd_config :	unconfig
	@$(MKCONFIG) $(@:_config=) arm s5pc11x x210 samsung s5pc110
	@echo "TEXT_BASE = 0xc3e00000" > $(obj)board/samsung/x210/config.mk

@$(MKCONFIG) $(@:_config=) arm s5pc11x x210 samsung s5pc110这句代码,最后六个作为参数传递给第一个脚本程序,这个脚本程序,在这个脚本程序中,会在./include目录下创建config.mk文件,并将这些环境变量传递进去。

 

8、交叉编译工具链的前缀确定:CROSS_COMPILE环境变量

ifndef CROSS_COMPILE
ifeq ($(HOSTARCH),$(ARCH))
CROSS_COMPILE =
else
ifeq ($(ARCH),ppc)
CROSS_COMPILE = ppc_8xx-
endif
ifeq ($(ARCH),arm) #我们uboot的ARCH为arm,而且编译代码的主机和执行的主机是不同
cc
endif

最终CROSS_COMPILE = /usr/local/arm/arm-2009q3/bin/arm-none-linux-gnueabi-

这里需要说明的一点为什么要区分前缀和后缀:

交叉编译工具链的确定需要前缀和后缀,这里把前缀和后缀分开,在不同框架的CPU的交叉编译工具链中,只是前缀不同,后缀完全相同,所以可以执行很好。只要确定好前缀就可以了。

还有我们也可以通过编码代码的时候,指定交叉编译工具链的前缀,而且优先级是最高的。

 

9、include $(TOPDIR)/config.mk

下面分析该文件中代码:

1、将交叉编译工具链的前缀和后缀结合

# Include the make variables (CC, etc...)
#
AS	= $(CROSS_COMPILE)as
LD	= $(CROSS_COMPILE)ld
CC	= $(CROSS_COMPILE)gcc
CPP	= $(CC) -E
AR	= $(CROSS_COMPILE)ar
NM	= $(CROSS_COMPILE)nm
LDR	= $(CROSS_COMPILE)ldr
STRIP	= $(CROSS_COMPILE)strip
OBJCOPY = $(CROSS_COMPILE)objcopy
OBJDUMP = $(CROSS_COMPILE)objdump
RANLIB	= $(CROSS_COMPILE)RANLIB

 

2、包含 sinclude $(OBJTREE)/include/autoconf.mk ,其中的部分代码

CONFIG_CMD_FAT=y
CONFIG_USB_OHCI=y
CONFIG_SYS_CLK_FREQ=24000000
CONFIG_CMD_ITEST=y
CONFIG_S3C_HSMMC=y
CONFIG_DISPLAY_BOARDINFO=y
CONFIG_CMD_XIMG=y
CONFIG_CMD_CACHE=y
CONFIG_STACKSIZE="0x40000"
CONFIG_BOOTDELAY=3
CONFIG_CHECK_MPLL_LOCK=y
CONFIG_NR_DRAM_BANKS=2
CONFIG_ETHADDR="00:40:5c:26:0a:5b"
CONFIG_CMD_CONSOLE=y
CONFIG_SW_WORKAROUND=y
CONFIG_GATEWAYIP="192.168.0.1"
CONFIG_DRIVER_DM9000=y
CONFIG_ZIMAGE_BOOT=y
CONFIG_CMD_REGINFO=y

autoconfi.mk是用来指导整个uboot编译过程的。这个文件的内容就是很多CONFIG_开头的宏定义。这些宏会影响我们uboot编译过程的走向(作用原理就在于uboot中的众多的条件编译)。在uboot代码中有很多地方使用了条件编写进行编写,这个条件编译的目的就是用来实现可移植性的。可以说uboot的源码很大程序上是拼凑出来的,同一代码包含了各种不同开发板的适用代码,用条件编译来进行区分。

这个文件也是配置过程中自动生成的。

 

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值