Makefile常用函数及特殊变量
Makefile 中的 -f -g等的含义
Makefile中4种赋值运算符
1、按照 makefile 文件顺序解析
1.1 linux 内核版本号
VERSION = 5
PATCHLEVEL = 15
SUBLEVEL = 163
EXTRAVERSION =
NAME = Trick or Treat
VERSION 主版本号
PATCHLEVEL 补丁版本号
SUBLEVEL 次版本号
EXTRAVERSION 附加版本信息
NAME 版本名字
1.2 排查 make 目标格式
$(if $(filter __%, $(MAKECMDGOALS)), \
$(error targets prefixed with '__' are only for internal use))
双下划线 目标只在 make 内部使用,不能作为指定目标
MAKECMDGOALS 预定义的 makefile 变量,用来保存make 的目标
filter 过滤函数,过滤出命令行目标中双下划线开头的目标,用来提示这些目标无效
1.3 定义默认目标
PHONY := __all
__all:
makefie 中的第一个目标也就是默认目标,并将目标保存到 PHONY 变量中
1.4 定义全局变量
ifneq ($(sub_make_done),1)
...
...
...
endif # sub_make_done
sub_make_done 存在的意义,构建框架存在递归调用的行为,而对于有全局影响的一些变量和规则需要在递归之前处理,因此需要通过 sub_make_done 完成对这些内容的保护,只在第一次进入主makefile的时候才会运行
1.4.1 屏蔽 make 的内置规则和内置变量
MAKEFLAGS += -rR
1.4.1.1 变量
打印 makefile 的变量到 xxx 中
make -p >> xxx
makefile中的变量可以分为4类,
第一类: 环境变量, 比较重要的是PATH, PWD 就不一一列举了。
第二类: 内置变量或叫默认变量(default), 比较重要的是cc, CXX, .INCLUDE_DIRS, .DEFAULT_GOAL等ak
第三类: 自动变量
第四类: makefile 中定义的变量
1.4.1.2 规则
同上
1.4.2 locale 本地环境设置
# Avoid funny character set dependencies
unexport LC_ALL
LC_COLLATE=C
LC_NUMERIC=C
export LC_COLLATE LC_NUMERIC
# Avoid interference with shell env settings
unexport GREP_OPTIONS
LC_ALL 的设置不传给子 makefile
LC_COLLATE 设置比较和排序习惯为 POSIX 标准
LC_NUMERIC 设置数字标准为POSIX 标准
将 LC_COLLATE LC_NUMERIC 的设置传给子makefile
GREP_OPTIONS shell 下 grep 的环境变量,避免与 shell 本身设置冲突
1.4.3 编译日志打印方式
ifeq ("$(origin V)", "command line")
KBUILD_VERBOSE = $(V)
endif
ifndef KBUILD_VERBOSE
KBUILD_VERBOSE = 0
endif
ifeq ($(KBUILD_VERBOSE),1)
quiet =
Q =
else
quiet=quiet_
Q = @
endif
# If the user is running make -s (silent mode), suppress echoing of
# commands
# make-4.0 (and later) keep single letter options in the 1st word of MAKEFLAGS.
ifeq ($(filter 3.%,$(MAKE_VERSION)),)
silence:=$(findstring s,$(firstword -$(MAKEFLAGS)))
else
silence:=$(findstring s,$(filter-out --%,$(MAKEFLAGS)))
endif
ifeq ($(silence),s)
quiet=silent_
KBUILD_VERBOSE = 0
endif
export quiet Q KBUILD_VERBOSE
这里是对日志打印的解析,最终会获取到 quiet Q KBUILD_VERBOSE 三个变量的值
命令行定义了 V,则 KBUILD_VERBOSE 就等于 V 的值,否则 KBUILD_VERBOSE 值为 0
我们这里用 quiet = Q = 替换掉原来的逻辑,及默认是打印日志的 KBUILD_VERBOSE 默认值修改为 1
KBUILD_VERBOSE = 1
quiet =
Q =
export quiet Q KBUILD_VERBOSE
1.5 KBUILD_SRC 变量
当前 KBUILD_SRC 变量默认为空,这种判断条件默认是支持的,先放着不用管
ifeq ($(KBUILD_SRC),)
ifneq ($(KBUILD_SRC),)
@$(kecho) ' Using $(srctree) as source for U-Boot'
$(Q)if [ -f $(srctree)/.config -o -d $(srctree)/include/config ]; then \
echo >&2 " $(srctree) is not clean, please run 'make mrproper'"; \
echo >&2 " in the '$(srctree)' directory.";\
/bin/false; \
fi;
endif
ifneq ($(KBUILD_SRC),)
@$(kecho) ' Using $(srctree) as source for U-Boot'
$(Q)if [ -f $(srctree)/.config -o -d $(srctree)/include/config ]; then \
echo >&2 " $(srctree) is not clean, please run 'make mrproper'"; \
echo >&2 " in the '$(srctree)' directory.";\
/bin/false; \
fi;
endif
UBOOTINCLUDE := \
-Iinclude \
$(if $(KBUILD_SRC), -I$(srctree)/include) \
$(if $(CONFIG_SYS_THUMB_BUILD), $(if $(CONFIG_HAS_THUMB2),, \
-I$(srctree)/arch/$(ARCH)/thumb1/include),) \
-I$(srctree)/arch/$(ARCH)/include \
-include $(srctree)/include/linux/kconfig.h
ifeq ($(KBUILD_SRC),)
# building in the source tree
srctree := .
else
ifeq ($(KBUILD_SRC)/,$(dir $(CURDIR)))
# building in a subdirectory of the source tree
srctree := ..
else
srctree := $(KBUILD_SRC)
endif
endif
1.6 编译结果输出目录定义
ifeq ("$(origin O)", "command line")
KBUILD_OUTPUT := $(O)
endif
命令函输入 make O=output/
我们不规定编译目标输出目录则 KBUILD_OUTPUT 为空
如果 在命令行定义了 make O=output/ 这里逻辑先不关注,那么此时
saved-output :=
KBUILD_OUTPUT :=
skip-makefile :=
1.7 文件检查
ifeq ("$(origin C)", "command line")
KBUILD_CHECKSRC = $(C)
endif
ifndef KBUILD_CHECKSRC
KBUILD_CHECKSRC = 0
endif
1.8 ko 编译
ifeq ("$(origin M)", "command line")
KBUILD_EXTMOD := $(M)
endif
PHONY += all
ifeq ($(KBUILD_EXTMOD),)
_all: all
else
_all: modules
endif
VPATH := $(srctree)$(if $(KBUILD_EXTMOD),:$(KBUILD_EXTMOD))
export MODVERDIR := $(if $(KBUILD_EXTMOD),$(firstword $(KBUILD_EXTMOD))/).tmp_versions
clean: $(clean-dirs)
$(call cmd,rmdirs)
$(call cmd,rmfiles)
@find $(if $(KBUILD_EXTMOD), $(KBUILD_EXTMOD), .) $(RCS_FIND_IGNORE) \
\( -name '*.[oas]' -o -name '*.ko' -o -name '.*.cmd' \
-o -name '*.ko.*' -o -name '*.su' -o -name '*.cfgtmp' \
-o -name '.*.d' -o -name '.*.tmp' -o -name '*.mod.c' \
-o -name '*.symtypes' -o -name 'modules.order' \
-o -name modules.builtin -o -name '.tmp_*.o.*' \
-o -name '*.gcno' \) -type f -print | xargs rm -f
ifeq ($(KBUILD_EXTMOD),)
build-dir = $(patsubst %/,%,$(dir $@))
target-dir = $(dir $@)
else
zap-slash=$(filter-out .,$(patsubst %/,%,$(dir $@)))
build-dir = $(KBUILD_EXTMOD)$(if $(zap-slash),/$(zap-slash))
target-dir = $(if $(KBUILD_EXTMOD),$(dir $<),$(dir $@))
endif
ifeq ($(MAKECMDGOALS),modules)
KBUILD_BUILTIN := $(if $(CONFIG_MODVERSIONS),1)
endif
# Modules
/: prepare scripts FORCE
$(cmd_crmodverdir)
$(Q)$(MAKE) KBUILD_MODULES=$(if $(CONFIG_MODULES),1) \
$(build)=$(build-dir)
%/: prepare scripts FORCE
$(cmd_crmodverdir)
$(Q)$(MAKE) KBUILD_MODULES=$(if $(CONFIG_MODULES),1) \
$(build)=$(build-dir)
%.ko: prepare scripts FORCE
$(cmd_crmodverdir)
$(Q)$(MAKE) KBUILD_MODULES=$(if $(CONFIG_MODULES),1) \
$(build)=$(build-dir) $(@:.ko=.o)
$(Q)$(MAKE) -f ./scripts/Makefile.modpost
1.9 优化 srctree objtree VPATH 相关变量
# building in the source tree
srctree := .
objtree := .
src := $(srctree)
obj := $(objtree)
VPATH := $(srctree)
export srctree objtree VPATH
1.10 HOSTARCH HOSTOS 机器环境变量获取和处理
HOSTARCH := $(shell uname -m | \
sed -e s/i.86/x86/ \
-e s/sun4u/sparc64/ \
-e s/arm.*/arm/ \
-e s/sa110/arm/ \
-e s/ppc64/powerpc/ \
-e s/ppc/powerpc/ \
-e s/macppc/powerpc/\
-e s/sh.*/sh/) #
HOSTOS := $(shell uname -s | tr '[:upper:]' '[:lower:]' | \
sed -e 's/\(cygwin\).*/cygwin/')
export HOSTARCH HOSTOS
ifeq ($(HOSTOS),cygwin)
HOSTCFLAGS += -ansi
endif
ifeq ($(HOSTOS),darwin)
# get major and minor product version (e.g. '10' and '6' for Snow Leopard)
DARWIN_MAJOR_VERSION = $(shell sw_vers -productVersion | cut -f 1 -d '.')
DARWIN_MINOR_VERSION = $(shell sw_vers -productVersion | cut -f 2 -d '.')
os_x_before = $(shell if [ $(DARWIN_MAJOR_VERSION) -le $(1) -a \
$(DARWIN_MINOR_VERSION) -le $(2) ] ; then echo "$(3)"; else echo "$(4)"; fi ;)
# Snow Leopards build environment has no longer restrictions as described above
HOSTCC = $(call os_x_before, 10, 5, "cc", "gcc")
HOSTCFLAGS += $(call os_x_before, 10, 4, "-traditional-cpp")
HOSTLDFLAGS += $(call os_x_before, 10, 5, "-multiply_defined suppress")
# since Lion (10.7) ASLR is on by default, but we use linker generated lists
# in some host tools which is a problem then ... so disable ASLR for these
# tools
HOSTLDFLAGS += $(call os_x_before, 10, 7, "", "-Xlinker -no_pie")
endif
1.11 CROSS_COMPILE 变量设置
ifeq ($(HOSTARCH),$(ARCH))
CROSS_COMPILE ?=
endif
CROSS_COMPILE = arm-linux-gnueabihf-
CROSS_COMPILE 在命令行已经定义过,并且 HOSTARCH 和 ARCH 不一样
1.12 ARCH 环境变量
ARCH = arm
include arch/$(ARCH)/Makefile
LDSCRIPT := ./arch/arm/cpu/u-boot.lds
# turn jbsr into jsr for m68k
ifeq ($(ARCH),m68k)
ifeq ($(findstring 3.4,$(shell $(CC) --version)),3.4)
KBUILD_AFLAGS += -Wa,-gstabs,-S
endif
endif
UBOOTINCLUDE := \
-Iinclude \
$(if $(CONFIG_SYS_THUMB_BUILD), $(if $(CONFIG_HAS_THUMB2),, \
-I./arch/$(ARCH)/thumb1/include),) \
-I./arch/$(ARCH)/include \
-include ./include/linux/kconfig.h
PLATFORM_LIBGCC = arch/$(ARCH)/lib/lib.a
MKIMAGEFLAGS_u-boot.img = -A $(ARCH) -T firmware -C none -O u-boot \
-a $(CONFIG_SYS_TEXT_BASE) -e $(CONFIG_SYS_UBOOT_START) \
-n "U-Boot $(UBOOTRELEASE) for $(BOARD) board"
MKIMAGEFLAGS_u-boot-spl.img = -A $(ARCH) -T firmware -C none \
-a $(CONFIG_SPL_TEXT_BASE) -e $(CONFIG_SPL_TEXT_BASE) -n XLOADER
cmd_u-boot_payload ?= $(LD) $(LDFLAGS_EFI_PAYLOAD) -o $@ \
-T u-boot-payload.lds arch/x86/cpu/call32.o \
lib/efi/efi.o lib/efi/efi_stub.o u-boot.bin.o \
$(addprefix arch/$(ARCH)/lib/efi/,$(EFISTUB))
MKIMAGEFLAGS_u-boot-spl.pbl = -n ./$(CONFIG_SYS_FSL_PBL_RCW:"%"=%) \
-R ./$(CONFIG_SYS_FSL_PBL_PBI:"%"=%) -T pblimage \
-A $(ARCH) -a $(CONFIG_SPL_TEXT_BASE)
ifeq ($(ARCH),arm)
UBOOT_BINLOAD := u-boot.img
else
UBOOT_BINLOAD := u-boot.bin
endif
checkstack:
$(OBJDUMP) -d u-boot $$(find . -name u-boot-spl) | \
$(PERL) $(src)/scripts/checkstack.pl $(ARCH)
1.13 CONFIG_SHELL 环境变量
CONFIG_SHELL := $(shell if [ -x "$$BASH" ]; then echo $$BASH; \
else if [ -x /bin/bash ]; then echo /bin/bash; \
else echo sh; fi ; fi)
1.14 KCONFIG_CONFIG
1.15 mixed-targets 命令行定义多个目标,并且其中有 config 目标
ifneq ($(filter config %config,$(MAKECMDGOALS)),)
config-targets := 1
ifneq ($(words $(MAKECMDGOALS)),1)
mixed-targets := 1
endif
endif
ifeq ($(mixed-targets),1)
# ===========================================================================
# We're called with mixed targets (*config and build targets).
# Handle them one by one.
PHONY += $(MAKECMDGOALS) __build_one_by_one
$(filter-out __build_one_by_one, $(MAKECMDGOALS)): __build_one_by_one
@:
__build_one_by_one:
$(Q)set -e; \
for i in $(MAKECMDGOALS); do \
$(MAKE) -f ./Makefile $$i; \
done
else
2、基于 makefile 文件目标解析
__all scripts_basic outputmakefile all bzImage bzdisk fdimage fdimage144 fdimage288 hdimage
isoimage install vdso_install prepare0 autoksyms_recursive scripts prepare archprepare
remove-stale-files asm-generic uapi-asm-generic headerdep headers_install archheaders
archscripts headers headers_check scripts_unifdef resolve_btfids_clean kselftest
kselftest-merge scripts_dtc dt_binding_check modules modules_prepare modules_sign
__modinst_pre archclean vmlinuxclean _mrproper_scripts mrproper distclean help xmldocs
latexdocs pdfdocs htmldocs epubdocs cleandocs linkcheckdocs dochelp refcheckdocs
scripts_gdb modules modules_install modules_check descend init usr arch/x86 kernel certs
mm fs ipc security crypto block io_uring drivers sound samples net virt arch/x86/pci
arch/x86/power arch/x86/video lib arch/x86/lib _clean_Documentation _clean_arch/x86
_clean_arch/x86/lib _clean_arch/x86/math-emu _clean_arch/x86/pci _clean_arch/x86/power
_clean_arch/x86/video _clean_block _clean_certs _clean_crypto _clean_drivers _clean_fs
_clean_init _clean_io_uring _clean_ipc _clean_kernel _clean_lib _clean_mm _clean_net
_clean_samples _clean_security _clean_sound _clean_usr _clean_virt clean nsdeps clang-tidy
clang-analyzer includecheck versioncheck coccicheck export_report checkstack kernelrelease
kernelversion image_name FORCE
2.1 __all
__all 是 Make 文件的第一个目标,也是默认目标
target ... : prerequisites ...
command
ifeq ($(KBUILD_EXTMOD),)
__all: all
else
__all: modules
endif
target : 是一个目标文件,可以是任意的实际文件,也可以是一个标签;
prerequisites: 是生成目标文件所依赖的文件或目标;
command: 生成目标的命令或者规则,依赖文件通过一定的规则生成目标文件;
这是一个文件的依赖关系,也就是说,target这一个或多个的目标文件依赖于prerequisites中的文件,其生成规则定义在command中。说白一点就是说,prerequisites中如果有一个以上的文件比target文件要新的话,command所定义的命令就会被执行。这就是Makefile的规则。也就是Makefile中最核心的内容。
在 makefile 中,第一个目标被认为是默认目标
2.2 scripts_basic
scripts_basic:
$(Q)$(MAKE) $(build)=scripts/basic
Q 是由命令行 V 控制用来表示要不要打印 Q 后面的编译命令
MAKE 特殊环境变量即 make
build 定义在 scripts/Kbuild.include
build := -f $(srctree)/scripts/Makefile.build obj
make -f $(srctree)/scripts/Makefile.build obj=scripts/basic
2.3 all
# The all: target is the default when no target is given on the
# command line.
# This allow a user to issue only 'make' to build a kernel including modules
# Defaults to vmlinux, but the arch makefile usually adds further targets
all: vmlinux
ifdef CONFIG_OF_EARLY_FLATTREE
all: dtbs
endif
ifdef CONFIG_MODULES
# By default, build modules as well
all: modules
ifdef CONFIG_GDB_SCRIPTS
all: scripts_gdb
endif
2.4 vmlinux
vmlinux: scripts/link-vmlinux.sh autoksyms_recursive $(vmlinux-deps) FORCE
+$(call if_changed_dep,link-vmlinux)
2.5 %config
%config: scripts_basic outputmakefile FORCE
$(Q)$(MAKE) $(build)=scripts/kconfig $@
make -f ./scripts/Makefile.build obj=scripts/kconfig mx6ull_14x14_ddr512_emmc_defconfig
2.5.1 ./scripts/Makefile.build 文件解析
2.5.1.1 8到17 行
********************************源码*****************************
# Modified for U-Boot
prefix := tpl
src := $(patsubst $(prefix)/%,%,$(obj))
ifeq ($(obj),$(src))
prefix := spl
src := $(patsubst $(prefix)/%,%,$(obj))
ifeq ($(obj),$(src))
prefix := .
endif
endif
********************************过程*****************************
prefix := tpl
src := $(patsubst tpl/%,%,scripts/kconfig) 把 scripts/kconfig 能匹配到 tpl/% 的部分替换成 % 并输出
src := scripts/kconfig
ifeq (scripts/kconfig, scripts/kconfig)
prefix := spl
src := $(patsubst spl/%,%,scripts/kconfig) 把 scripts/kconfig 能匹配到 spl/% 的部分替换成 % 并输出
src := scripts/kconfig
ifeq (scripts/kconfig, scripts/kconfig)
prefix := .
********************************结果*****************************
obj=scripts/kconfig
src := scripts/kconfig
prefix := .
2.5.1.2 19到20 行
********************************源码*****************************
PHONY := __build
__build:
********************************过程*****************************
__build: 是 Makefile.build 的第一个目标也是默认目标
********************************结果*****************************
__build: 是 Makefile.build 的第一个目标也是默认目标
2.5.1.3 22 行到 43 行
********************************源码*****************************
# Init all relevant variables used in kbuild files so
# 1) they have correct type
# 2) they do not inherit any value from the environment
obj-y :=
obj-m :=
lib-y :=
lib-m :=
always :=
targets :=
subdir-y :=
subdir-m :=
EXTRA_AFLAGS :=
EXTRA_CFLAGS :=
EXTRA_CPPFLAGS :=
EXTRA_LDFLAGS :=
asflags-y :=
ccflags-y :=
cppflags-y :=
ldflags-y :=
subdir-asflags-y :=
subdir-ccflags-y :=
********************************结果*****************************
定义相关变量
2.5.1.4 45行到51行
********************************源码*****************************
# Read auto.conf if it exists, otherwise ignore
# Modified for U-Boot
-include include/config/auto.conf
-include $(prefix)/include/autoconf.mk
include scripts/Makefile.uncmd_spl
include scripts/Kbuild.include
********************************过程*****************************
-include include/config/auto.conf
-include ./include/autoconf.mk
include scripts/Makefile.uncmd_spl
include scripts/Kbuild.include
这里 -include 和 include 的区别
-include 包含的文件如果不存在,则忽略继续执行
include 包含的文件如果不存在,则会报错退出编译
********************************结果*****************************
包含 auto.conf autoconf.mk Makefile.uncmd_spl Kbuild.include 四个文件
2.5.1.5 53行到54行
********************************源码*****************************
# For backward compatibility check that these variables do not change
save-cflags := $(CFLAGS)
********************************过程*****************************
CFLAGS 没有定义,值为空所以 save-cflags 的值也是空
********************************结果*****************************
save-cflags :=
2.5.1.6 56行到59行
********************************源码*****************************
# The filename Kbuild has precedence over Makefile
kbuild-dir := $(if $(filter /%,$(src)),$(src),$(srctree)/$(src))
kbuild-file := $(if $(wildcard $(kbuild-dir)/Kbuild),$(kbuild-dir)/Kbuild,$(kbuild-dir)/Makefile)
include $(kbuild-file)
********************************过程*****************************
kbuild-dir := $(if $(filter /%, scripts/kconfig), scripts/kconfig, ./scripts/kconfig)
从 scripts/kconfig 中筛选出符合 /% 的字符串,可以看到是没有的
kbuild-dir := $(if $(NULL), scripts/kconfig, ./scripts/kconfig)
kbuild-dir := ./scripts/kconfig
kbuild-file := $(if $(wildcard ./scripts/kconfig/Kbuild),./scripts/kconfig/Kbuild,./scripts/kconfig/Makefile)
查找 ./scripts/kconfig/Kbuild 文件是不存在的,返回一个空值
kbuild-file := $(if NULL,./scripts/kconfig/Kbuild,./scripts/kconfig/Makefile)
kbuild-file := ./scripts/kconfig/Makefile
include ./scripts/kconfig/Makefile
********************************结果*****************************
include ./scripts/kconfig/Makefile 包含 ./scripts/kconfig/Makefile 文件
加载 ./scripts/kconfig/Makefile
make -f ./scripts/Makefile.build obj=scripts/kconfig mx6ull_14x14_ddr512_emmc_defconfig 目标是
mx6ull_14x14_ddr512_emmc_defconfig 所以执行
%_defconfig: $(obj)/conf
$(Q)$< $(silent) --defconfig=arch/$(SRCARCH)/configs/$@ $(Kconfig)
2.5.1.7 ./scripts/kconfig/Makefile 113行到114行
********************************源码*****************************
%_defconfig: $(obj)/conf
$(Q)$< $(silent) --defconfig=arch/$(SRCARCH)/configs/$@ $(Kconfig)
********************************过程*****************************
mx6ull_14x14_ddr512_emmc_defconfig 匹配到 %_defconfig: $(obj)/conf
mx6ull_14x14_ddr512_emmc_defconfig: scripts/kconfig/conf
$< $(silent) --defconfig=arch/$(SRCARCH)/configs/$@ $(Kconfig)
$< 表示第一个依赖文件
$@ 表示目标文件
Kconfig := Kconfig
SRCARCH := ..
silent =
mx6ull_14x14_ddr512_emmc_defconfig: scripts/kconfig/conf
scripts/kconfig/conf --defconfig=arch/../configs/mx6ull_14x14_ddr512_emmc_defconfig Kconfig
********************************结果*****************************
2.5.1.7 61行到64行
********************************源码*****************************
# Added for U-Boot
asflags-y += $(PLATFORM_CPPFLAGS)
ccflags-y += $(PLATFORM_CPPFLAGS)
cppflags-y += $(PLATFORM_CPPFLAGS)
********************************过程*****************************
arch/arm/cpu/armv7/config.mk:13:PLATFORM_CPPFLAGS += $(PF_NO_UNALIGNED)
arch/arm/Makefile:40:PLATFORM_CPPFLAGS += $(arch-y) $(tune-y)
arch/arm/Makefile:44:PLATFORM_CPPFLAGS += $(patsubst %,-I$(srctree)/%include,$(machdirs))
arch/arm/config.mk:22:PLATFORM_CPPFLAGS += -D__ARM__
arch/arm/config.mk:70:PLATFORM_CPPFLAGS += $(PF_CPPFLAGS_ARM) $(PF_CPPFLAGS_ABI)
arch/arm/config.mk:109:PLATFORM_CPPFLAGS += $(call cc-option, -mword-relocations)
arch/arm/config.mk:110:PLATFORM_CPPFLAGS += $(call cc-option, -fno-pic)
config.mk:16:PLATFORM_CPPFLAGS :=
config.mk:64:PLATFORM_CPPFLAGS += -finstrument-functions -DFTRACE
config.mk:69:PLATFORM_CPPFLAGS += -DCONFIG_USE_STDINT
config.mk:76:PLATFORM_CPPFLAGS += $(RELFLAGS)
config.mk:77:PLATFORM_CPPFLAGS += -pipe
config.mk:82:export PLATFORM_CPPFLAGS
arch/arm/cpu/armv7/config.mk 中 PF_NO_UNALIGNED := $(call cc-option, -mno-unaligned-access,)
PLATFORM_CPPFLAGS += $(call cc-option, -mno-unaligned-access,)
PLATFORM_CPPFLAGS 这个值有点复杂,这里先打印出结果看下
编译config
PLATFORM_CPPFLAGS =
全编:
PLATFORM_CPPFLAGS = -D__ARM__ -marm -mno-thumb-interwork -mabi=aapcs-linux -mword-relocations -fno-pic -mno-unaligned-access -ffunction-sections -fdata-sections -fno-common -ffixed-r9 -msoft-float -pipe -march=armv7-a
打印出来编译 config
asflags-y =
ccflags-y =
cppflags-y =
********************************结果*****************************
asflags-y =
ccflags-y =
cppflags-y =
2.5.1.8 66行到71行
********************************源码*****************************
# If the save-* variables changed error out
ifeq ($(KBUILD_NOPEDANTIC),)
ifneq ("$(save-cflags)","$(CFLAGS)")
$(error CFLAGS was changed in "$(kbuild-file)". Fix it to use ccflags-y)
endif
endif
********************************过程*****************************
不知道 KBUILD_NOPEDANTIC 和 CFLAGS 是干什么的,但是这里不涉及,先不关注
********************************结果*****************************
不关注
2.5.1.9 73行
********************************源码*****************************
include scripts/Makefile.lib
********************************结果*****************************
包含 scripts/Makefile.lib 文件
2.5.1.10 75行到80行
********************************源码*****************************
ifdef host-progs
ifneq ($(hostprogs-y),$(host-progs))
$(warning kbuild: $(obj)/Makefile - Usage of host-progs is deprecated. Please replace with hostprogs-y!)
hostprogs-y += $(host-progs)
endif
endif
********************************过程*****************************
host-progs 没有看到定义,这里也忽略,hostprogs-y 打印出来为空
********************************结果*****************************
hostprogs-y =
2.5.1.11 82到85行
********************************源码*****************************
# Do not include host rules unless needed
ifneq ($(hostprogs-y)$(hostprogs-m),)
include scripts/Makefile.host
endif
********************************过程*****************************
hostprogs-m 打印出来也为空
********************************结果*****************************
不加载 scripts/Makefile.host 文件
2.5.1.12 87行到96行
********************************源码*****************************
# Uncommented for U-Boot
# We need to create output dicrectory for SPL and TPL even for in-tree build
#ifneq ($(KBUILD_SRC),)
# Create output directory if not already present
_dummy := $(shell [ -d $(obj) ] || mkdir -p $(obj))
# Create directories for object files if directory does not exist
# Needed when obj-y := dir/file.o syntax is used
_dummy := $(foreach d,$(obj-dirs), $(shell [ -d $(d) ] || mkdir -p $(d)))
#endif
********************************过程*****************************
前面已知 KBUILD_SRC 是空,所有这个判断条件进不去
********************************结果*****************************
这段不会执行
2.5.1.13 98行到 100行
********************************源码*****************************
ifndef obj
$(warning kbuild: Makefile.build is included improperly)
endif
********************************过程*****************************
没有定义 obj 则打印告警,已知 obj=scripts/kconfig 所以告警不会打印
********************************结果*****************************
不会打印告警
2.5.1.14 104行到106行
********************************源码*****************************
ifneq ($(strip $(lib-y) $(lib-m) $(lib-)),)
lib-target := $(obj)/lib.a
endif
********************************过程*****************************
ifneq ($(strip $(lib-y) $(lib-m) $(lib-)),)去除 $(lib-y) $(lib-m) $(lib-) 两端的空格
打印出来 lib-y lib-m lib- 都是空,那么这里 lib-target 也就是空
lib-target 打印出来也是空,和分析结果一致
********************************结果*****************************
lib-y =
lib-m =
lib- =
lib-target =
2.5.1.15 108行到110行
********************************源码*****************************
ifneq ($(strip $(obj-y) $(obj-m) $(obj-) $(subdir-m) $(lib-target)),)
builtin-target := $(obj)/built-in.o
endif
********************************过程*****************************
ifneq ($(strip $(obj-y) $(obj-m) $(obj-) $(subdir-m) $(lib-target)),) 去除 $(obj-y) $(obj-m) $(obj-) $(subdir-m) $(lib-target) 两端空格
打印出来 $(obj-y) $(obj-m) $(obj-) $(subdir-m) $(lib-target) 都是空,那么 builtin-target 也应该为空
打印出来 builtin-target 也是空和分析结果一致
********************************结果*****************************
obj-y =
obj-m =
obj- =
subdir-m =
lib-target =
builtin-target =
2.5.1.16 112行
********************************源码*****************************
modorder-target := $(obj)/modules.order
********************************过程*****************************
********************************结果*****************************
2.5.1.17
********************************源码*****************************
********************************过程*****************************
********************************结果*****************************
2.5.1.18
********************************源码*****************************
********************************过程*****************************
********************************结果*****************************