lists.openwall.net   lists  /  announce  owl-users  owl-dev  john-users  john-dev  passwdqc-users  yescrypt  popa3d-users  /  oss-security  kernel-hardening  musl  sabotage  tlsify  passwords  /  crypt-dev  xvendor  /  Bugtraq  Full-Disclosure  linux-kernel  linux-netdev  linux-ext4  linux-hardening  linux-cve-announce  PHC 
Open Source and information security mailing list archives
 
Hash Suite: Windows password security audit tool. GUI, reports in PDF.
[<prev] [next>] [<thread-prev] [thread-next>] [day] [month] [year] [list]
Message-ID: <4ezl3egjv36fjkxkkswcianc5cg7ui6jpqw56e4ohlwipmuxai@kvgemh72rmga>
Date: Fri, 27 Jun 2025 10:34:15 -0700
From: Josh Poimboeuf <jpoimboe@...nel.org>
To: Peter Zijlstra <peterz@...radead.org>
Cc: x86@...nel.org, linux-kernel@...r.kernel.org, 
	Petr Mladek <pmladek@...e.com>, Miroslav Benes <mbenes@...e.cz>, 
	Joe Lawrence <joe.lawrence@...hat.com>, live-patching@...r.kernel.org, Song Liu <song@...nel.org>, 
	laokz <laokz@...mail.com>, Jiri Kosina <jikos@...nel.org>, 
	Marcos Paulo de Souza <mpdesouza@...e.com>, Weinan Liu <wnliu@...gle.com>, 
	Fazla Mehrab <a.mehrab@...edance.com>, Chen Zhongjin <chenzhongjin@...wei.com>, 
	Puranjay Mohan <puranjay@...nel.org>, Dylan Hatch <dylanbhatch@...gle.com>, 
	Masahiro Yamada <masahiroy@...nel.org>
Subject: Re: [PATCH v3 42/64] kbuild,x86: Fix special section module
 permissions

On Fri, Jun 27, 2025 at 12:53:28PM +0200, Peter Zijlstra wrote:
> On Thu, Jun 26, 2025 at 04:55:29PM -0700, Josh Poimboeuf wrote:
> > An upcoming patch will add the SHF_MERGE flag to x86 __jump_table and
> > __bug_table so their entry sizes can be defined in inline asm.
> > 
> > However, those sections have SHF_WRITE, which the Clang linker (lld)
> > explicitly forbids combining with SHF_MERGE.
> > 
> > Those sections are modified at runtime and must remain writable.  While
> > SHF_WRITE is ignored by vmlinux, it's still needed for modules.
> > 
> > To work around the linker interference, remove SHF_WRITE during
> > compilation and restore it after linking the module.
> 
> This is vile... but I'm not sure I have a better solution.
> 
> Eventually we should get the toolchains fixed, but we can't very well
> mandate clang-21+ to build x86 just yet.

Yeah, I really hate this too.  I really tried to find something better,
including mucking with the linker script, but this was unfortunately the
only thing that worked.

Though, looking at it again, I realize we can localize the pain to Clang
(and the makefile) by leaving the code untouched and instead strip
SHF_WRITE before the link and re-add it afterwards.  Then we can tie
this horrible hack to specific Clang versions when it gets fixed.

Something like so:

diff --git a/arch/Kconfig b/arch/Kconfig
index a3308a220f86..350ea5df5e8d 100644
--- a/arch/Kconfig
+++ b/arch/Kconfig
@@ -1314,6 +1314,9 @@ config HAVE_NOINSTR_HACK
 config HAVE_NOINSTR_VALIDATION
 	bool
 
+config NEED_MODULE_PERMISSIONS_FIX
+	bool
+
 config HAVE_UACCESS_VALIDATION
 	bool
 	select OBJTOOL
diff --git a/arch/x86/Kconfig b/arch/x86/Kconfig
index 71019b3b54ea..0cac13c03a90 100644
--- a/arch/x86/Kconfig
+++ b/arch/x86/Kconfig
@@ -310,6 +310,7 @@ config X86
 	select HOTPLUG_SPLIT_STARTUP		if SMP && X86_32
 	select IRQ_FORCED_THREADING
 	select LOCK_MM_AND_FIND_VMA
+	select NEED_MODULE_PERMISSIONS_FIX	if LD_IS_LLD
 	select NEED_PER_CPU_EMBED_FIRST_CHUNK
 	select NEED_PER_CPU_PAGE_FIRST_CHUNK
 	select NEED_SG_DMA_LENGTH
diff --git a/scripts/Makefile.modfinal b/scripts/Makefile.modfinal
index 542ba462ed3e..cbc3213427ba 100644
--- a/scripts/Makefile.modfinal
+++ b/scripts/Makefile.modfinal
@@ -28,12 +28,37 @@ ccflags-remove-y := $(CC_FLAGS_CFI)
 .module-common.o: $(srctree)/scripts/module-common.c FORCE
 	$(call if_changed_rule,cc_o_c)
 
+
+ifdef CONFIG_NEED_MODULE_PERMISSIONS_FIX
+
+# The LLVM linker forbids SHF_MERGE+SHF_WRITE.  Hack around that by
+# temporarily removing SHF_WRITE from affected sections before linking.
+
+cmd_fix_mod_permissions_pre_link =					\
+	$(OBJCOPY) --set-section-flags __jump_table=alloc,readonly	\
+		   --set-section-flags __bug_table=alloc,readonly $@	\
+		   --set-section-flags .static_call_sites=alloc,readonly $@
+
+cmd_fix_mod_permissions_post_link =					\
+	$(OBJCOPY) --set-section-flags __jump_table=alloc,data		\
+		   --set-section-flags __bug_table=alloc,data $@	\
+		   --set-section-flags .static_call_sites=alloc,data $@
+
+endif # CONFIG_NEED_MODULE_PERMISSIONS_FIX
+
+
 quiet_cmd_ld_ko_o = LD [M]  $@
       cmd_ld_ko_o =							\
 	$(LD) -r $(KBUILD_LDFLAGS)					\
 		$(KBUILD_LDFLAGS_MODULE) $(LDFLAGS_MODULE)		\
 		-T $(objtree)/scripts/module.lds -o $@ $(filter %.o, $^)
 
+define rule_ld_ko_o
+	$(call cmd,fix_mod_permissions_pre_link)
+	$(call cmd_and_savecmd,ld_ko_o)
+	$(call cmd,fix_mod_permissions_post_link)
+endef
+
 quiet_cmd_btf_ko = BTF [M] $@
       cmd_btf_ko = 							\
 	if [ ! -f $(objtree)/vmlinux ]; then				\
@@ -46,14 +71,11 @@ quiet_cmd_btf_ko = BTF [M] $@
 # Same as newer-prereqs, but allows to exclude specified extra dependencies
 newer_prereqs_except = $(filter-out $(PHONY) $(1),$?)
 
-# Same as if_changed, but allows to exclude specified extra dependencies
-if_changed_except = $(if $(call newer_prereqs_except,$(2))$(cmd-check),      \
-	$(cmd);                                                              \
-	printf '%s\n' 'savedcmd_$@ := $(make-cmd)' > $(dot-target).cmd, @:)
+if_changed_rule_except = $(if $(call newer_prereqs_except,$(2))$(cmd-check),$(rule_$(1)),@:)
 
 # Re-generate module BTFs if either module's .ko or vmlinux changed
 %.ko: %.o %.mod.o .module-common.o $(objtree)/scripts/module.lds $(and $(CONFIG_DEBUG_INFO_BTF_MODULES),$(KBUILD_BUILTIN),$(objtree)/vmlinux) FORCE
-	+$(call if_changed_except,ld_ko_o,$(objtree)/vmlinux)
+	+$(call if_changed_rule_except,ld_ko_o,$(objtree)/vmlinux)
 ifdef CONFIG_DEBUG_INFO_BTF_MODULES
 	+$(if $(newer-prereqs),$(call cmd,btf_ko))
 endif

Powered by blists - more mailing lists

Powered by Openwall GNU/*/Linux Powered by OpenVZ