Commit 825a0714 authored by Linus Torvalds's avatar Linus Torvalds
Browse files
Pull EFI updates from Ard Biesheuvel:

 - relocate the LoongArch kernel if the preferred address is already
   occupied

 - implement BTI annotations for arm64 EFI stub and zboot images

 - clean up arm64 zboot Kbuild rules for injecting the kernel code size

* tag 'efi-next-for-v6.4' of git://git.kernel.org/pub/scm/linux/kernel/git/efi/efi:
  efi/zboot: arm64: Grab code size from ELF symbol in payload
  efi/zboot: arm64: Inject kernel code size symbol into the zboot payload
  efi/zboot: Set forward edge CFI compat header flag if supported
  efi/zboot: Add BSS padding before compression
  arm64: efi: Enable BTI codegen and add PE/COFF annotation
  efi/pe: Import new BTI/IBT header flags from the spec
  efi/loongarch: Reintroduce efi_relocate_kernel() to relocate kernel
parents 17d4ded2 026b8579
Loading
Loading
Loading
Loading
+4 −0
Original line number Diff line number Diff line
@@ -42,5 +42,9 @@ $(obj)/Image.zst: $(obj)/Image FORCE
EFI_ZBOOT_PAYLOAD	:= Image
EFI_ZBOOT_BFD_TARGET	:= elf64-littleaarch64
EFI_ZBOOT_MACH_TYPE	:= ARM64
EFI_ZBOOT_FORWARD_CFI	:= $(CONFIG_ARM64_BTI_KERNEL)

EFI_ZBOOT_OBJCOPY_FLAGS	= --add-symbol zboot_code_size=0x$(shell \
				$(NM) vmlinux|grep _kernel_codesize|cut -d' ' -f1)

include $(srctree)/drivers/firmware/efi/libstub/Makefile.zboot
+43 −28
Original line number Diff line number Diff line
@@ -81,9 +81,47 @@
	.quad	0					// CertificationTable
	.quad	0					// BaseRelocationTable

#ifdef CONFIG_DEBUG_EFI
#if defined(CONFIG_DEBUG_EFI) || defined(CONFIG_ARM64_BTI_KERNEL)
	.long	.Lefi_debug_table - .L_head		// DebugTable
	.long	.Lefi_debug_table_size

	/*
	 * The debug table is referenced via its Relative Virtual Address (RVA),
	 * which is only defined for those parts of the image that are covered
	 * by a section declaration. Since this header is not covered by any
	 * section, the debug table must be emitted elsewhere. So stick it in
	 * the .init.rodata section instead.
	 *
	 * Note that the payloads themselves are permitted to have zero RVAs,
	 * which means we can simply put those right after the section headers.
	 */
	__INITRODATA

	.align	2
.Lefi_debug_table:
#ifdef CONFIG_DEBUG_EFI
	// EFI_IMAGE_DEBUG_DIRECTORY_ENTRY
	.long	0					// Characteristics
	.long	0					// TimeDateStamp
	.short	0					// MajorVersion
	.short	0					// MinorVersion
	.long	IMAGE_DEBUG_TYPE_CODEVIEW		// Type
	.long	.Lefi_debug_entry_size			// SizeOfData
	.long	0					// RVA
	.long	.Lefi_debug_entry - .L_head		// FileOffset
#endif
#ifdef CONFIG_ARM64_BTI_KERNEL
	.long	0					// Characteristics
	.long	0					// TimeDateStamp
	.short	0					// MajorVersion
	.short	0					// MinorVersion
	.long	IMAGE_DEBUG_TYPE_EX_DLLCHARACTERISTICS	// Type
	.long	4					// SizeOfData
	.long	0					// RVA
	.long	.Lefi_dll_characteristics_ex - .L_head	// FileOffset
#endif
	.set	.Lefi_debug_table_size, . - .Lefi_debug_table
	.previous
#endif

	// Section table
@@ -119,33 +157,6 @@
	.set	.Lsection_count, (. - .Lsection_table) / 40

#ifdef CONFIG_DEBUG_EFI
	/*
	 * The debug table is referenced via its Relative Virtual Address (RVA),
	 * which is only defined for those parts of the image that are covered
	 * by a section declaration. Since this header is not covered by any
	 * section, the debug table must be emitted elsewhere. So stick it in
	 * the .init.rodata section instead.
	 *
	 * Note that the EFI debug entry itself may legally have a zero RVA,
	 * which means we can simply put it right after the section headers.
	 */
	__INITRODATA

	.align	2
.Lefi_debug_table:
	// EFI_IMAGE_DEBUG_DIRECTORY_ENTRY
	.long	0					// Characteristics
	.long	0					// TimeDateStamp
	.short	0					// MajorVersion
	.short	0					// MinorVersion
	.long	IMAGE_DEBUG_TYPE_CODEVIEW		// Type
	.long	.Lefi_debug_entry_size			// SizeOfData
	.long	0					// RVA
	.long	.Lefi_debug_entry - .L_head		// FileOffset

	.set	.Lefi_debug_table_size, . - .Lefi_debug_table
	.previous

.Lefi_debug_entry:
	// EFI_IMAGE_DEBUG_CODEVIEW_NB10_ENTRY
	.ascii	"NB10"					// Signature
@@ -157,6 +168,10 @@

	.set	.Lefi_debug_entry_size, . - .Lefi_debug_entry
#endif
#ifdef CONFIG_ARM64_BTI_KERNEL
.Lefi_dll_characteristics_ex:
	.long	IMAGE_DLLCHARACTERISTICS_EX_FORWARD_CFI_COMPAT
#endif

	.balign	SEGMENT_ALIGN
.Lefi_header_end:
+4 −0
Original line number Diff line number Diff line
@@ -108,4 +108,8 @@ KVM_NVHE_ALIAS(kvm_protected_mode_initialized);

#endif /* CONFIG_KVM */

#ifdef CONFIG_EFI_ZBOOT
_kernel_codesize = ABSOLUTE(__inittext_end - _text);
#endif

#endif /* __ARM64_KERNEL_IMAGE_VARS_H */
+1 −2
Original line number Diff line number Diff line
@@ -23,8 +23,7 @@ cflags-$(CONFIG_X86) += -m$(BITS) -D__KERNEL__ \
# arm64 uses the full KBUILD_CFLAGS so it's necessary to explicitly
# disable the stackleak plugin
cflags-$(CONFIG_ARM64)		+= -fpie $(DISABLE_STACKLEAK_PLUGIN) \
				   -fno-unwind-tables -fno-asynchronous-unwind-tables \
				   $(call cc-option,-mbranch-protection=none)
				   -fno-unwind-tables -fno-asynchronous-unwind-tables
cflags-$(CONFIG_ARM)		+= -DEFI_HAVE_STRLEN -DEFI_HAVE_STRNLEN \
				   -DEFI_HAVE_MEMCHR -DEFI_HAVE_STRRCHR \
				   -DEFI_HAVE_STRCMP -fno-builtin -fpic \
+29 −14
Original line number Diff line number Diff line
# SPDX-License-Identifier: GPL-2.0

# to be include'd by arch/$(ARCH)/boot/Makefile after setting
# EFI_ZBOOT_PAYLOAD, EFI_ZBOOT_BFD_TARGET and EFI_ZBOOT_MACH_TYPE
# EFI_ZBOOT_PAYLOAD, EFI_ZBOOT_BFD_TARGET, EFI_ZBOOT_MACH_TYPE and
# EFI_ZBOOT_FORWARD_CFI

quiet_cmd_copy_and_pad = PAD     $@
      cmd_copy_and_pad = cp $< $@ && \
			 truncate -s $(shell hexdump -s16 -n4 -e '"%u"' $<) $@

# Pad the file to the size of the uncompressed image in memory, including BSS
$(obj)/vmlinux.bin: $(obj)/$(EFI_ZBOOT_PAYLOAD) FORCE
	$(call if_changed,copy_and_pad)

comp-type-$(CONFIG_KERNEL_GZIP)		:= gzip
comp-type-$(CONFIG_KERNEL_LZ4)		:= lz4
@@ -10,26 +19,32 @@ comp-type-$(CONFIG_KERNEL_LZO) := lzo
comp-type-$(CONFIG_KERNEL_XZ)		:= xzkern
comp-type-$(CONFIG_KERNEL_ZSTD)		:= zstd22

# Copy the SizeOfHeaders, SizeOfCode and SizeOfImage fields from the payload to
# the end of the compressed image. Note that this presupposes a PE header
# offset of 64 bytes, which is what arm64, RISC-V and LoongArch use.
quiet_cmd_compwithsize = $(quiet_cmd_$(comp-type-y))
      cmd_compwithsize = $(cmd_$(comp-type-y)) && ( \
			   dd status=none if=$< bs=4 count=1 skip=37 ; \
			   dd status=none if=$< bs=4 count=1 skip=23 ; \
			   dd status=none if=$< bs=4 count=1 skip=36 ) >> $@
# in GZIP, the appended le32 carrying the uncompressed size is part of the
# format, but in other cases, we just append it at the end for convenience,
# causing the original tools to complain when checking image integrity.
# So disregard it when calculating the payload size in the zimage header.
zboot-method-y                         := $(comp-type-y)_with_size
zboot-size-len-y                       := 4

$(obj)/vmlinuz: $(obj)/$(EFI_ZBOOT_PAYLOAD) FORCE
	$(call if_changed,compwithsize)
zboot-method-$(CONFIG_KERNEL_GZIP)     := gzip
zboot-size-len-$(CONFIG_KERNEL_GZIP)   := 0

OBJCOPYFLAGS_vmlinuz.o := -I binary -O $(EFI_ZBOOT_BFD_TARGET) \
$(obj)/vmlinuz: $(obj)/vmlinux.bin FORCE
	$(call if_changed,$(zboot-method-y))

OBJCOPYFLAGS_vmlinuz.o := -I binary -O $(EFI_ZBOOT_BFD_TARGET) $(EFI_ZBOOT_OBJCOPY_FLAGS) \
			  --rename-section .data=.gzdata,load,alloc,readonly,contents
$(obj)/vmlinuz.o: $(obj)/vmlinuz FORCE
	$(call if_changed,objcopy)

aflags-zboot-header-$(EFI_ZBOOT_FORWARD_CFI) := \
		-DPE_DLL_CHAR_EX=IMAGE_DLLCHARACTERISTICS_EX_FORWARD_CFI_COMPAT

AFLAGS_zboot-header.o += -DMACHINE_TYPE=IMAGE_FILE_MACHINE_$(EFI_ZBOOT_MACH_TYPE) \
			 -DZBOOT_EFI_PATH="\"$(realpath $(obj)/vmlinuz.efi.elf)\"" \
			 -DCOMP_TYPE="\"$(comp-type-y)\""
			 -DZBOOT_SIZE_LEN=$(zboot-size-len-y) \
			 -DCOMP_TYPE="\"$(comp-type-y)\"" \
			 $(aflags-zboot-header-y)

$(obj)/zboot-header.o: $(srctree)/drivers/firmware/efi/libstub/zboot-header.S FORCE
	$(call if_changed_rule,as_o_S)
@@ -44,4 +59,4 @@ OBJCOPYFLAGS_vmlinuz.efi := -O binary
$(obj)/vmlinuz.efi: $(obj)/vmlinuz.efi.elf FORCE
	$(call if_changed,objcopy)

targets += zboot-header.o vmlinuz vmlinuz.o vmlinuz.efi.elf vmlinuz.efi
targets += zboot-header.o vmlinux.bin vmlinuz vmlinuz.o vmlinuz.efi.elf vmlinuz.efi
Loading