编译一个arm内核时,有一行错误信息:
/home/yuanjp/toolchain/toolchain-rv1126/bin/arm-linux-gnueabihf-nm: 'arch/arm/boot/compressed/../../../../vmlinux': No such file
来源:
arch/arm/boot/compressed/Makefile
KBSS_SZ = $(shell echo $$(($$($(CROSS_COMPILE)nm $(obj)/../../../../vmlinux | \
sed -n -e 's/^\([^ ]*\) [AB] __bss_start$$/-0x\1/p' \
-e 's/^\([^ ]*\) [AB] __bss_stop$$/+0x\1/p') )) )
LDFLAGS_vmlinux = --defsym _kernel_bss_size=$(KBSS_SZ)
定义了一个KBSS_SZ的变量,LDFLAGS_vmlinux引用了这个变量,这个变量会访问arch/arm/boot/compressed/../../../../vmlinux这个文件。首次编译时,这个文件在编译compressed的时候,是在的,但是compressed目录不在,但是正常,LDFLAGS_vmlinux只有在链接mlinux的时候,才引用。
加了一些调试,没有结果,尝试开启make的调试,加上--debug=all
$ git diff scripts/
diff --git a/scripts/Kbuild.include b/scripts/Kbuild.include
index ce53639..bd7a507 100644
--- a/scripts/Kbuild.include
+++ b/scripts/Kbuild.include
@@ -181,7 +181,7 @@ ld-ifversion = $(shell [ $(ld-version) $(1) $(2) ] && echo $(3) || echo $(4))
# Shorthand for $(Q)$(MAKE) -f scripts/Makefile.build obj=
# Usage:
# $(Q)$(MAKE) $(build)=dir
-build := -f $(srctree)/scripts/Makefile.build obj
+build := -f $(srctree)/scripts/Makefile.build --debug=all obj
###
# Shorthand for $(Q)$(MAKE) -f scripts/Makefile.modbuiltin obj=
出现错误日志:
/home/yuanjp/proj/zynqmp/staging/source/linux-4.19-rockchip/arch/arm/boot/compressed/Makefile:148: not recursively expanding LDFLAGS_vmlinux to export to shell function
搜索出现的错误信息,找到了修复,原来是make版本更新导致的。4.4版本的Makefile,一个export的recursive ariable,在执行shell函数的时候,会展开,便于shell访问这个变量。
$ make --version
GNU Make 4.4.1
Built for x86_64-redhat-linux-gnu
Copyright (C) 1988-2023 Free Software Foundation, Inc.
License GPLv3+: GNU GPL version 3 or later <https://gnu.org/licenses/gpl.html>
This is free software: you are free to change and redistribute it.
There is NO WARRANTY, to the extent permitted by law.
参考
修复方法是:
diff --git a/Makefile b/Makefileindex dfba294ae790..658fc0e602c9 100644--- a/Makefile+++ b/Makefile@@ -549,7 +549,7 @@ LDFLAGS_MODULE = CFLAGS_KERNEL = RUSTFLAGS_KERNEL = AFLAGS_KERNEL =-export LDFLAGS_vmlinux =+LDFLAGS_vmlinux = # Use USERINCLUDE when you must reference the UAPI directories only. USERINCLUDE := \@@ -1248,6 +1248,11 @@ vmlinux.o modules.builtin.modinfo modules.builtin: vmlinux_o @: PHONY += vmlinux+# LDFLAGS_vmlinux flags from the top Makefile and arch/*/Makefile should be+# exported for building the top vmlinux, but not for building decompressors.+# They happen to have the same base name (arch/*/boot/compressed/vmlinux).+# The decompressor Makefiles should not inherit LDFLAGS_vmlinux.+vmlinux: export LDFLAGS_vmlinux := $(LDFLAGS_vmlinux) vmlinux: vmlinux.o $(KBUILD_LDS) modpost $(Q)$(MAKE) -f $(srctree)/scripts/Makefile.vmlinux