mirror of
git://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
synced 2025-09-04 20:19:47 +08:00

The .rela.dyn section contains runtime relocations and is only emitted
for a relocatable kernel.
riscv uses this section to relocate the kernel at runtime but that section
is stripped from vmlinux. That prevents kexec to successfully load vmlinux
since it does not contain the relocations info needed.
Fixes: 559d1e45a1
("riscv: Use --emit-relocs in order to move .rela.dyn in init")
Tested-by: Björn Töpel <bjorn@rivosinc.com>
Reviewed-by: Björn Töpel <bjorn@rivosinc.com>
Acked-by: Ard Biesheuvel <ardb@kernel.org>
Link: https://lore.kernel.org/r/20250408072851.90275-1-alexghiti@rivosinc.com
Signed-off-by: Alexandre Ghiti <alexghiti@rivosinc.com>
134 lines
3.7 KiB
Makefile
134 lines
3.7 KiB
Makefile
# SPDX-License-Identifier: GPL-2.0-only
|
|
|
|
PHONY := __default
|
|
__default: vmlinux
|
|
|
|
include include/config/auto.conf
|
|
include $(srctree)/scripts/Kbuild.include
|
|
include $(srctree)/scripts/Makefile.lib
|
|
|
|
targets :=
|
|
|
|
ifdef CONFIG_ARCH_VMLINUX_NEEDS_RELOCS
|
|
vmlinux-final := vmlinux.unstripped
|
|
|
|
quiet_cmd_strip_relocs = RSTRIP $@
|
|
cmd_strip_relocs = $(OBJCOPY) --remove-section='.rel*' --remove-section=!'.rel*.dyn' $< $@
|
|
|
|
vmlinux: $(vmlinux-final) FORCE
|
|
$(call if_changed,strip_relocs)
|
|
|
|
targets += vmlinux
|
|
else
|
|
vmlinux-final := vmlinux
|
|
endif
|
|
|
|
%.o: %.c FORCE
|
|
$(call if_changed_rule,cc_o_c)
|
|
|
|
%.o: %.S FORCE
|
|
$(call if_changed_rule,as_o_S)
|
|
|
|
# Built-in dtb
|
|
# ---------------------------------------------------------------------------
|
|
|
|
quiet_cmd_wrap_dtbs = WRAP $@
|
|
cmd_wrap_dtbs = { \
|
|
echo '\#include <asm-generic/vmlinux.lds.h>'; \
|
|
echo '.section .dtb.init.rodata,"a"'; \
|
|
while read dtb; do \
|
|
symbase=__dtb_$$(basename -s .dtb "$${dtb}" | tr - _); \
|
|
echo '.balign STRUCT_ALIGNMENT'; \
|
|
echo ".global $${symbase}_begin"; \
|
|
echo "$${symbase}_begin:"; \
|
|
echo '.incbin "'$$dtb'" '; \
|
|
echo ".global $${symbase}_end"; \
|
|
echo "$${symbase}_end:"; \
|
|
done < $<; \
|
|
} > $@
|
|
|
|
.builtin-dtbs.S: .builtin-dtbs-list FORCE
|
|
$(call if_changed,wrap_dtbs)
|
|
|
|
quiet_cmd_gen_dtbs_list = GEN $@
|
|
cmd_gen_dtbs_list = \
|
|
$(if $(CONFIG_BUILTIN_DTB_NAME), echo "arch/$(SRCARCH)/boot/dts/$(CONFIG_BUILTIN_DTB_NAME).dtb",:) > $@
|
|
|
|
.builtin-dtbs-list: arch/$(SRCARCH)/boot/dts/dtbs-list FORCE
|
|
$(call if_changed,$(if $(CONFIG_BUILTIN_DTB_ALL),copy,gen_dtbs_list))
|
|
|
|
targets += .builtin-dtbs-list
|
|
|
|
ifdef CONFIG_GENERIC_BUILTIN_DTB
|
|
targets += .builtin-dtbs.S .builtin-dtbs.o
|
|
$(vmlinux-final): .builtin-dtbs.o
|
|
endif
|
|
|
|
# vmlinux
|
|
# ---------------------------------------------------------------------------
|
|
|
|
ifdef CONFIG_MODULES
|
|
targets += .vmlinux.export.o
|
|
$(vmlinux-final): .vmlinux.export.o
|
|
endif
|
|
|
|
ifdef CONFIG_ARCH_WANTS_PRE_LINK_VMLINUX
|
|
$(vmlinux-final): arch/$(SRCARCH)/tools/vmlinux.arch.o
|
|
|
|
arch/$(SRCARCH)/tools/vmlinux.arch.o: vmlinux.o FORCE
|
|
$(Q)$(MAKE) $(build)=arch/$(SRCARCH)/tools $@
|
|
endif
|
|
|
|
ARCH_POSTLINK := $(wildcard $(srctree)/arch/$(SRCARCH)/Makefile.postlink)
|
|
|
|
# Final link of vmlinux with optional arch pass after final link
|
|
cmd_link_vmlinux = \
|
|
$< "$(LD)" "$(KBUILD_LDFLAGS)" "$(LDFLAGS_vmlinux)" "$@"; \
|
|
$(if $(ARCH_POSTLINK), $(MAKE) -f $(ARCH_POSTLINK) $@, true)
|
|
|
|
targets += $(vmlinux-final)
|
|
$(vmlinux-final): scripts/link-vmlinux.sh vmlinux.o $(KBUILD_LDS) FORCE
|
|
+$(call if_changed_dep,link_vmlinux)
|
|
ifdef CONFIG_DEBUG_INFO_BTF
|
|
$(vmlinux-final): $(RESOLVE_BTFIDS)
|
|
endif
|
|
|
|
ifdef CONFIG_BUILDTIME_TABLE_SORT
|
|
vmlinux: scripts/sorttable
|
|
endif
|
|
|
|
# module.builtin.ranges
|
|
# ---------------------------------------------------------------------------
|
|
ifdef CONFIG_BUILTIN_MODULE_RANGES
|
|
__default: modules.builtin.ranges
|
|
|
|
quiet_cmd_modules_builtin_ranges = GEN $@
|
|
cmd_modules_builtin_ranges = gawk -f $(real-prereqs) > $@
|
|
|
|
targets += modules.builtin.ranges
|
|
modules.builtin.ranges: $(srctree)/scripts/generate_builtin_ranges.awk \
|
|
modules.builtin vmlinux.map vmlinux.o.map FORCE
|
|
$(call if_changed,modules_builtin_ranges)
|
|
|
|
vmlinux.map: $(vmlinux-final)
|
|
@:
|
|
|
|
endif
|
|
|
|
# Add FORCE to the prerequisites of a target to force it to be always rebuilt.
|
|
# ---------------------------------------------------------------------------
|
|
|
|
PHONY += FORCE
|
|
FORCE:
|
|
|
|
# Read all saved command lines and dependencies for the $(targets) we
|
|
# may be building above, using $(if_changed{,_dep}). As an
|
|
# optimization, we don't need to read them if the target does not
|
|
# exist, we will rebuild anyway in that case.
|
|
|
|
existing-targets := $(wildcard $(sort $(targets)))
|
|
|
|
-include $(foreach f,$(existing-targets),$(dir $(f)).$(notdir $(f)).cmd)
|
|
|
|
.PHONY: $(PHONY)
|