xref: /linux/arch/arm64/kernel/efi-header.S (revision 1ac731c529cd4d6adbce134754b51ff7d822b145)
1d2912cb1SThomas Gleixner/* SPDX-License-Identifier: GPL-2.0-only */
2b5f4a214SArd Biesheuvel/*
3b5f4a214SArd Biesheuvel * Copyright (C) 2013 - 2017 Linaro, Ltd.
4b5f4a214SArd Biesheuvel * Copyright (C) 2013, 2014 Red Hat, Inc.
5b5f4a214SArd Biesheuvel */
6b5f4a214SArd Biesheuvel
7f1eb542fSArd Biesheuvel#include <linux/pe.h>
8f1eb542fSArd Biesheuvel#include <linux/sizes.h>
9f1eb542fSArd Biesheuvel
107919385bSArd Biesheuvel	.macro	efi_signature_nop
117919385bSArd Biesheuvel#ifdef CONFIG_EFI
127919385bSArd Biesheuvel.L_head:
137919385bSArd Biesheuvel	/*
147919385bSArd Biesheuvel	 * This ccmp instruction has no meaningful effect except that
157919385bSArd Biesheuvel	 * its opcode forms the magic "MZ" signature required by UEFI.
167919385bSArd Biesheuvel	 */
177919385bSArd Biesheuvel	ccmp	x18, #0, #0xd, pl
187919385bSArd Biesheuvel#else
197919385bSArd Biesheuvel	/*
207919385bSArd Biesheuvel	 * Bootloaders may inspect the opcode at the start of the kernel
217919385bSArd Biesheuvel	 * image to decide if the kernel is capable of booting via UEFI.
227919385bSArd Biesheuvel	 * So put an ordinary NOP here, not the "MZ.." pseudo-nop above.
237919385bSArd Biesheuvel	 */
247919385bSArd Biesheuvel	nop
257919385bSArd Biesheuvel#endif
267919385bSArd Biesheuvel	.endm
277919385bSArd Biesheuvel
28b5f4a214SArd Biesheuvel	.macro	__EFI_PE_HEADER
297919385bSArd Biesheuvel#ifdef CONFIG_EFI
307919385bSArd Biesheuvel	.set	.Lpe_header_offset, . - .L_head
31f1eb542fSArd Biesheuvel	.long	PE_MAGIC
32f1eb542fSArd Biesheuvel	.short	IMAGE_FILE_MACHINE_ARM64		// Machine
33b50a3225SArd Biesheuvel	.short	.Lsection_count				// NumberOfSections
34b5f4a214SArd Biesheuvel	.long	0 					// TimeDateStamp
35b5f4a214SArd Biesheuvel	.long	0					// PointerToSymbolTable
36f328ba47SArd Biesheuvel	.long	0					// NumberOfSymbols
37b50a3225SArd Biesheuvel	.short	.Lsection_table - .Loptional_header	// SizeOfOptionalHeader
38f1eb542fSArd Biesheuvel	.short	IMAGE_FILE_DEBUG_STRIPPED | \
39f1eb542fSArd Biesheuvel		IMAGE_FILE_EXECUTABLE_IMAGE | \
40f1eb542fSArd Biesheuvel		IMAGE_FILE_LINE_NUMS_STRIPPED		// Characteristics
41f1eb542fSArd Biesheuvel
42b50a3225SArd Biesheuvel.Loptional_header:
43f1eb542fSArd Biesheuvel	.short	PE_OPT_MAGIC_PE32PLUS			// PE32+ format
44b5f4a214SArd Biesheuvel	.byte	0x02					// MajorLinkerVersion
45b5f4a214SArd Biesheuvel	.byte	0x14					// MinorLinkerVersion
46b50a3225SArd Biesheuvel	.long	__initdata_begin - .Lefi_header_end	// SizeOfCode
47cad27ef2SArd Biesheuvel	.long	__pecoff_data_size			// SizeOfInitializedData
48b5f4a214SArd Biesheuvel	.long	0					// SizeOfUninitializedData
497919385bSArd Biesheuvel	.long	__efistub_efi_pe_entry - .L_head	// AddressOfEntryPoint
507919385bSArd Biesheuvel	.long	.Lefi_header_end - .L_head		// BaseOfCode
51b5f4a214SArd Biesheuvel
52b5f4a214SArd Biesheuvel	.quad	0					// ImageBase
5376085affSArd Biesheuvel	.long	SEGMENT_ALIGN				// SectionAlignment
54b5f4a214SArd Biesheuvel	.long	PECOFF_FILE_ALIGNMENT			// FileAlignment
55b5f4a214SArd Biesheuvel	.short	0					// MajorOperatingSystemVersion
56b5f4a214SArd Biesheuvel	.short	0					// MinorOperatingSystemVersion
57148d3f71SArd Biesheuvel	.short	LINUX_EFISTUB_MAJOR_VERSION		// MajorImageVersion
58148d3f71SArd Biesheuvel	.short	LINUX_EFISTUB_MINOR_VERSION		// MinorImageVersion
59b5f4a214SArd Biesheuvel	.short	0					// MajorSubsystemVersion
60b5f4a214SArd Biesheuvel	.short	0					// MinorSubsystemVersion
61b5f4a214SArd Biesheuvel	.long	0					// Win32VersionValue
62b5f4a214SArd Biesheuvel
637919385bSArd Biesheuvel	.long	_end - .L_head				// SizeOfImage
64b5f4a214SArd Biesheuvel
65b5f4a214SArd Biesheuvel	// Everything before the kernel image is considered part of the header
667919385bSArd Biesheuvel	.long	.Lefi_header_end - .L_head		// SizeOfHeaders
67b5f4a214SArd Biesheuvel	.long	0					// CheckSum
68f1eb542fSArd Biesheuvel	.short	IMAGE_SUBSYSTEM_EFI_APPLICATION		// Subsystem
693c66bb19SArd Biesheuvel	.short	IMAGE_DLL_CHARACTERISTICS_NX_COMPAT	// DllCharacteristics
70b5f4a214SArd Biesheuvel	.quad	0					// SizeOfStackReserve
71b5f4a214SArd Biesheuvel	.quad	0					// SizeOfStackCommit
72b5f4a214SArd Biesheuvel	.quad	0					// SizeOfHeapReserve
73b5f4a214SArd Biesheuvel	.quad	0					// SizeOfHeapCommit
74b5f4a214SArd Biesheuvel	.long	0					// LoaderFlags
75b50a3225SArd Biesheuvel	.long	(.Lsection_table - .) / 8		// NumberOfRvaAndSizes
76b5f4a214SArd Biesheuvel
77b5f4a214SArd Biesheuvel	.quad	0					// ExportTable
78b5f4a214SArd Biesheuvel	.quad	0					// ImportTable
79b5f4a214SArd Biesheuvel	.quad	0					// ResourceTable
80b5f4a214SArd Biesheuvel	.quad	0					// ExceptionTable
81b5f4a214SArd Biesheuvel	.quad	0					// CertificationTable
82b5f4a214SArd Biesheuvel	.quad	0					// BaseRelocationTable
83b5f4a214SArd Biesheuvel
84*8358098bSArd Biesheuvel#if defined(CONFIG_DEBUG_EFI) || defined(CONFIG_ARM64_BTI_KERNEL)
857919385bSArd Biesheuvel	.long	.Lefi_debug_table - .L_head		// DebugTable
86b50a3225SArd Biesheuvel	.long	.Lefi_debug_table_size
87*8358098bSArd Biesheuvel
88*8358098bSArd Biesheuvel	/*
89*8358098bSArd Biesheuvel	 * The debug table is referenced via its Relative Virtual Address (RVA),
90*8358098bSArd Biesheuvel	 * which is only defined for those parts of the image that are covered
91*8358098bSArd Biesheuvel	 * by a section declaration. Since this header is not covered by any
92*8358098bSArd Biesheuvel	 * section, the debug table must be emitted elsewhere. So stick it in
93*8358098bSArd Biesheuvel	 * the .init.rodata section instead.
94*8358098bSArd Biesheuvel	 *
95*8358098bSArd Biesheuvel	 * Note that the payloads themselves are permitted to have zero RVAs,
96*8358098bSArd Biesheuvel	 * which means we can simply put those right after the section headers.
97*8358098bSArd Biesheuvel	 */
98*8358098bSArd Biesheuvel	__INITRODATA
99*8358098bSArd Biesheuvel
100*8358098bSArd Biesheuvel	.align	2
101*8358098bSArd Biesheuvel.Lefi_debug_table:
102*8358098bSArd Biesheuvel#ifdef CONFIG_DEBUG_EFI
103*8358098bSArd Biesheuvel	// EFI_IMAGE_DEBUG_DIRECTORY_ENTRY
104*8358098bSArd Biesheuvel	.long	0					// Characteristics
105*8358098bSArd Biesheuvel	.long	0					// TimeDateStamp
106*8358098bSArd Biesheuvel	.short	0					// MajorVersion
107*8358098bSArd Biesheuvel	.short	0					// MinorVersion
108*8358098bSArd Biesheuvel	.long	IMAGE_DEBUG_TYPE_CODEVIEW		// Type
109*8358098bSArd Biesheuvel	.long	.Lefi_debug_entry_size			// SizeOfData
110*8358098bSArd Biesheuvel	.long	0					// RVA
111*8358098bSArd Biesheuvel	.long	.Lefi_debug_entry - .L_head		// FileOffset
112*8358098bSArd Biesheuvel#endif
113*8358098bSArd Biesheuvel#ifdef CONFIG_ARM64_BTI_KERNEL
114*8358098bSArd Biesheuvel	.long	0					// Characteristics
115*8358098bSArd Biesheuvel	.long	0					// TimeDateStamp
116*8358098bSArd Biesheuvel	.short	0					// MajorVersion
117*8358098bSArd Biesheuvel	.short	0					// MinorVersion
118*8358098bSArd Biesheuvel	.long	IMAGE_DEBUG_TYPE_EX_DLLCHARACTERISTICS	// Type
119*8358098bSArd Biesheuvel	.long	4					// SizeOfData
120*8358098bSArd Biesheuvel	.long	0					// RVA
121*8358098bSArd Biesheuvel	.long	.Lefi_dll_characteristics_ex - .L_head	// FileOffset
122*8358098bSArd Biesheuvel#endif
123*8358098bSArd Biesheuvel	.set	.Lefi_debug_table_size, . - .Lefi_debug_table
124*8358098bSArd Biesheuvel	.previous
125b5f4a214SArd Biesheuvel#endif
126b5f4a214SArd Biesheuvel
127b5f4a214SArd Biesheuvel	// Section table
128b50a3225SArd Biesheuvel.Lsection_table:
129f1eb542fSArd Biesheuvel	.ascii	".text\0\0\0"
130b50a3225SArd Biesheuvel	.long	__initdata_begin - .Lefi_header_end	// VirtualSize
1317919385bSArd Biesheuvel	.long	.Lefi_header_end - .L_head		// VirtualAddress
132b50a3225SArd Biesheuvel	.long	__initdata_begin - .Lefi_header_end	// SizeOfRawData
1337919385bSArd Biesheuvel	.long	.Lefi_header_end - .L_head		// PointerToRawData
134b5f4a214SArd Biesheuvel
135b5f4a214SArd Biesheuvel	.long	0					// PointerToRelocations
136b5f4a214SArd Biesheuvel	.long	0					// PointerToLineNumbers
137b5f4a214SArd Biesheuvel	.short	0					// NumberOfRelocations
138b5f4a214SArd Biesheuvel	.short	0					// NumberOfLineNumbers
139f1eb542fSArd Biesheuvel	.long	IMAGE_SCN_CNT_CODE | \
140cad27ef2SArd Biesheuvel		IMAGE_SCN_MEM_READ | \
141cad27ef2SArd Biesheuvel		IMAGE_SCN_MEM_EXECUTE			// Characteristics
142cad27ef2SArd Biesheuvel
143cad27ef2SArd Biesheuvel	.ascii	".data\0\0\0"
144cad27ef2SArd Biesheuvel	.long	__pecoff_data_size			// VirtualSize
1457919385bSArd Biesheuvel	.long	__initdata_begin - .L_head		// VirtualAddress
146cad27ef2SArd Biesheuvel	.long	__pecoff_data_rawsize			// SizeOfRawData
1477919385bSArd Biesheuvel	.long	__initdata_begin - .L_head		// PointerToRawData
148cad27ef2SArd Biesheuvel
149cad27ef2SArd Biesheuvel	.long	0					// PointerToRelocations
150cad27ef2SArd Biesheuvel	.long	0					// PointerToLineNumbers
151cad27ef2SArd Biesheuvel	.short	0					// NumberOfRelocations
152cad27ef2SArd Biesheuvel	.short	0					// NumberOfLineNumbers
153cad27ef2SArd Biesheuvel	.long	IMAGE_SCN_CNT_INITIALIZED_DATA | \
154f1eb542fSArd Biesheuvel		IMAGE_SCN_MEM_READ | \
155f1eb542fSArd Biesheuvel		IMAGE_SCN_MEM_WRITE			// Characteristics
156f1eb542fSArd Biesheuvel
157b50a3225SArd Biesheuvel	.set	.Lsection_count, (. - .Lsection_table) / 40
158b5f4a214SArd Biesheuvel
159b5f4a214SArd Biesheuvel#ifdef CONFIG_DEBUG_EFI
160b50a3225SArd Biesheuvel.Lefi_debug_entry:
161b5f4a214SArd Biesheuvel	// EFI_IMAGE_DEBUG_CODEVIEW_NB10_ENTRY
162b5f4a214SArd Biesheuvel	.ascii	"NB10"					// Signature
163b5f4a214SArd Biesheuvel	.long	0					// Unknown
164b5f4a214SArd Biesheuvel	.long	0					// Unknown2
165b5f4a214SArd Biesheuvel	.long	0					// Unknown3
166b5f4a214SArd Biesheuvel
167b5f4a214SArd Biesheuvel	.asciz	VMLINUX_PATH
168b5f4a214SArd Biesheuvel
169b50a3225SArd Biesheuvel	.set	.Lefi_debug_entry_size, . - .Lefi_debug_entry
170b5f4a214SArd Biesheuvel#endif
171*8358098bSArd Biesheuvel#ifdef CONFIG_ARM64_BTI_KERNEL
172*8358098bSArd Biesheuvel.Lefi_dll_characteristics_ex:
173*8358098bSArd Biesheuvel	.long	IMAGE_DLLCHARACTERISTICS_EX_FORWARD_CFI_COMPAT
174*8358098bSArd Biesheuvel#endif
175b5f4a214SArd Biesheuvel
176a2d50c1cSArd Biesheuvel	.balign	SEGMENT_ALIGN
177b50a3225SArd Biesheuvel.Lefi_header_end:
1787919385bSArd Biesheuvel#else
1797919385bSArd Biesheuvel	.set	.Lpe_header_offset, 0x0
1807919385bSArd Biesheuvel#endif
181b5f4a214SArd Biesheuvel	.endm
182