Bug description
To reproduce the error:
- Checkout Linux kernel source tree from Linus Torvald's tree. I am at: 00dcf5d ("Merge tag 'acpi-6.9-rc4' of git://git.kernel.org/pub/scm/linux/kernel/git/rafael/linux-pm")
- Get clang prebuilts. I am at:
clang-r522817.
Then do the following:
PATH=$PATH:/path/to/clang-r522817/bin/ make ARCH=arm64 LLVM=1 tinyconfig
PATH=$PATH:/path/to/clang-r522817/bin/ make ARCH=arm64 LLVM=1 menuconfig
In menuconfig, enable the following:
LTO_CLANG_THIN=y: Enables LTO
IKCONFIG=y: Enables /proc/config.gz
HEADERS_INSTALL=y: Any config will do. I use this one as an example.
Then:
PATH=$PATH:/path/to/clang-r522817/bin/ make ARCH=arm64 LLVM=1 -j64
zcat kernel/config_data.gz | grep HEADER
scripts/extract-ikconfig vmlinux | grep HEADER
The last two commands will both say CONFIG_HEADERS_INSTALL=y.
Now, run PATH=$PATH:/path/to/clang-r522817/bin/ make ARCH=arm64 LLVM=1 menuconfig again, and disable HEADERS_INSTALL, then build again:
PATH=$PATH:/path/to/clang-r522817/bin/ make ARCH=arm64 LLVM=1 -j64
zcat kernel/config_data.gz | grep HEADER
scripts/extract-ikconfig vmlinux | grep HEADER
The first command will emit # CONFIG_HEADERS_INSTALL is not set correctly, but the last command will still emit CONFIG_HEADERS_INSTALL=y.
Analysis
The config_data.gz file is embedded in vmlinux using a .incbin instruction: https://github.com/torvalds/linux/blob/96fca68c4fbf77a8185eb10f7557e23352732ea2/kernel/configs.c#L28
From the build log and from the output of the above commands, Kbuild correctly updates kernel/config_data.gz, but the change is not reflected in vmlinux, even though it is rebuilt.
LTO (specifically caching) may play a part in this.
- If I disable LTO in the above
make menuconfig commands, vmlinux will correctly have # CONFIG_HEADERS_INSTALL is not set.
- In addition, if I delete
.thinlto-cache directory (--thinlto-cache-dir 1) before rebuilding, vmlinux will also correctly have # CONFIG_HEADERS_INSTALL is not set.
- If I apply this workaround, this will link
configs.o with -fno-lto, and vmlinux will also correctly have # CONFIG_HEADERS_INSTALL is not set.
From 10eacc104cb39c26a753796c981e46d0cba233c2 Mon Sep 17 00:00:00 2001
From: Yifan Hong <elsk@google.com>
Date: Mon, 8 Apr 2024 23:49:38 -0700
Subject: [PATCH] config: Disable LTO on kernel/configs.o
Signed-off-by: Yifan Hong <elsk@google.com>
---
kernel/Makefile | 4 ++++
1 file changed, 4 insertions(+)
diff --git a/kernel/Makefile b/kernel/Makefile
index 2e0dac3da346..0db1e9357668 100644
--- a/kernel/Makefile
+++ b/kernel/Makefile
@@ -140,6 +140,10 @@ obj-$(CONFIG_SCF_TORTURE_TEST) += scftorture.o
$(obj)/configs.o: $(obj)/config_data.gz
+# Disable LTO on configs.o so changes in .config is reflected
+# in vmlinux.
+CFLAGS_REMOVE_configs.o += $(CC_FLAGS_LTO)
+
targets += config_data config_data.gz
$(obj)/config_data.gz: $(obj)/config_data FORCE
$(call if_changed,gzip)
--
2.44.0.769.g3c40516874-goog
Hence, I believe this is a bug in LTO caching. Please help, thanks!
I am going to upload this workaround patch to Linux upstream, but the root issue should be fixed.
Bug description
To reproduce the error:
clang-r522817.Then do the following:
In menuconfig, enable the following:
LTO_CLANG_THIN=y: Enables LTOIKCONFIG=y: Enables /proc/config.gzHEADERS_INSTALL=y: Any config will do. I use this one as an example.Then:
The last two commands will both say
CONFIG_HEADERS_INSTALL=y.Now, run
PATH=$PATH:/path/to/clang-r522817/bin/ make ARCH=arm64 LLVM=1 menuconfigagain, and disableHEADERS_INSTALL, then build again:The first command will emit
# CONFIG_HEADERS_INSTALL is not setcorrectly, but the last command will still emitCONFIG_HEADERS_INSTALL=y.Analysis
The
config_data.gzfile is embedded in vmlinux using a.incbininstruction: https://github.com/torvalds/linux/blob/96fca68c4fbf77a8185eb10f7557e23352732ea2/kernel/configs.c#L28From the build log and from the output of the above commands, Kbuild correctly updates kernel/config_data.gz, but the change is not reflected in vmlinux, even though it is rebuilt.
LTO (specifically caching) may play a part in this.
make menuconfigcommands, vmlinux will correctly have# CONFIG_HEADERS_INSTALL is not set..thinlto-cachedirectory (--thinlto-cache-dir1) before rebuilding, vmlinux will also correctly have# CONFIG_HEADERS_INSTALL is not set.configs.owith-fno-lto, and vmlinux will also correctly have# CONFIG_HEADERS_INSTALL is not set.Hence, I believe this is a bug in LTO caching. Please help, thanks!
I am going to upload this workaround patch to Linux upstream, but the root issue should be fixed.
Footnotes
https://github.com/torvalds/linux/blob/96fca68c4fbf77a8185eb10f7557e23352732ea2/Makefile#L945 ↩