Skip to content

Commit 8358098

Browse files
committed
arm64: efi: Enable BTI codegen and add PE/COFF annotation
UEFI heavily relies on so-called protocols, which are essentially tables populated with pointers to executable code, and these are invoked indirectly using BR or BLR instructions. This makes the EFI execution context vulnerable to attacks on forward edge control flow, and so it would help if we could enable hardware enforcement (BTI) on CPUs that implement it. So let's no longer disable BTI codegen for the EFI stub, and set the newly introduced PE/COFF header flag when the kernel is built with BTI landing pads. Signed-off-by: Ard Biesheuvel <ardb@kernel.org> Reviewed-by: Mark Brown <broonie@kernel.org>
1 parent 0385855 commit 8358098

2 files changed

Lines changed: 44 additions & 30 deletions

File tree

arch/arm64/kernel/efi-header.S

Lines changed: 43 additions & 28 deletions
Original file line numberDiff line numberDiff line change
@@ -81,9 +81,47 @@
8181
.quad 0 // CertificationTable
8282
.quad 0 // BaseRelocationTable
8383

84-
#ifdef CONFIG_DEBUG_EFI
84+
#if defined(CONFIG_DEBUG_EFI) || defined(CONFIG_ARM64_BTI_KERNEL)
8585
.long .Lefi_debug_table - .L_head // DebugTable
8686
.long .Lefi_debug_table_size
87+
88+
/*
89+
* The debug table is referenced via its Relative Virtual Address (RVA),
90+
* which is only defined for those parts of the image that are covered
91+
* by a section declaration. Since this header is not covered by any
92+
* section, the debug table must be emitted elsewhere. So stick it in
93+
* the .init.rodata section instead.
94+
*
95+
* Note that the payloads themselves are permitted to have zero RVAs,
96+
* which means we can simply put those right after the section headers.
97+
*/
98+
__INITRODATA
99+
100+
.align 2
101+
.Lefi_debug_table:
102+
#ifdef CONFIG_DEBUG_EFI
103+
// EFI_IMAGE_DEBUG_DIRECTORY_ENTRY
104+
.long 0 // Characteristics
105+
.long 0 // TimeDateStamp
106+
.short 0 // MajorVersion
107+
.short 0 // MinorVersion
108+
.long IMAGE_DEBUG_TYPE_CODEVIEW // Type
109+
.long .Lefi_debug_entry_size // SizeOfData
110+
.long 0 // RVA
111+
.long .Lefi_debug_entry - .L_head // FileOffset
112+
#endif
113+
#ifdef CONFIG_ARM64_BTI_KERNEL
114+
.long 0 // Characteristics
115+
.long 0 // TimeDateStamp
116+
.short 0 // MajorVersion
117+
.short 0 // MinorVersion
118+
.long IMAGE_DEBUG_TYPE_EX_DLLCHARACTERISTICS // Type
119+
.long 4 // SizeOfData
120+
.long 0 // RVA
121+
.long .Lefi_dll_characteristics_ex - .L_head // FileOffset
122+
#endif
123+
.set .Lefi_debug_table_size, . - .Lefi_debug_table
124+
.previous
87125
#endif
88126

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

121159
#ifdef CONFIG_DEBUG_EFI
122-
/*
123-
* The debug table is referenced via its Relative Virtual Address (RVA),
124-
* which is only defined for those parts of the image that are covered
125-
* by a section declaration. Since this header is not covered by any
126-
* section, the debug table must be emitted elsewhere. So stick it in
127-
* the .init.rodata section instead.
128-
*
129-
* Note that the EFI debug entry itself may legally have a zero RVA,
130-
* which means we can simply put it right after the section headers.
131-
*/
132-
__INITRODATA
133-
134-
.align 2
135-
.Lefi_debug_table:
136-
// EFI_IMAGE_DEBUG_DIRECTORY_ENTRY
137-
.long 0 // Characteristics
138-
.long 0 // TimeDateStamp
139-
.short 0 // MajorVersion
140-
.short 0 // MinorVersion
141-
.long IMAGE_DEBUG_TYPE_CODEVIEW // Type
142-
.long .Lefi_debug_entry_size // SizeOfData
143-
.long 0 // RVA
144-
.long .Lefi_debug_entry - .L_head // FileOffset
145-
146-
.set .Lefi_debug_table_size, . - .Lefi_debug_table
147-
.previous
148-
149160
.Lefi_debug_entry:
150161
// EFI_IMAGE_DEBUG_CODEVIEW_NB10_ENTRY
151162
.ascii "NB10" // Signature
@@ -157,6 +168,10 @@
157168

158169
.set .Lefi_debug_entry_size, . - .Lefi_debug_entry
159170
#endif
171+
#ifdef CONFIG_ARM64_BTI_KERNEL
172+
.Lefi_dll_characteristics_ex:
173+
.long IMAGE_DLLCHARACTERISTICS_EX_FORWARD_CFI_COMPAT
174+
#endif
160175

161176
.balign SEGMENT_ALIGN
162177
.Lefi_header_end:

drivers/firmware/efi/libstub/Makefile

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -23,8 +23,7 @@ cflags-$(CONFIG_X86) += -m$(BITS) -D__KERNEL__ \
2323
# arm64 uses the full KBUILD_CFLAGS so it's necessary to explicitly
2424
# disable the stackleak plugin
2525
cflags-$(CONFIG_ARM64) += -fpie $(DISABLE_STACKLEAK_PLUGIN) \
26-
-fno-unwind-tables -fno-asynchronous-unwind-tables \
27-
$(call cc-option,-mbranch-protection=none)
26+
-fno-unwind-tables -fno-asynchronous-unwind-tables
2827
cflags-$(CONFIG_ARM) += -DEFI_HAVE_STRLEN -DEFI_HAVE_STRNLEN \
2928
-DEFI_HAVE_MEMCHR -DEFI_HAVE_STRRCHR \
3029
-DEFI_HAVE_STRCMP -fno-builtin -fpic \

0 commit comments

Comments
 (0)