efi: Add GRUB_PE32_MAGIC definition
[grub.git] / include / grub / efi / pe32.h
1 /*
2  *  GRUB  --  GRand Unified Bootloader
3  *  Copyright (C) 2006,2007,2008,2009  Free Software Foundation, Inc.
4  *
5  *  GRUB is free software: you can redistribute it and/or modify
6  *  it under the terms of the GNU General Public License as published by
7  *  the Free Software Foundation, either version 3 of the License, or
8  *  (at your option) any later version.
9  *
10  *  GRUB is distributed in the hope that it will be useful,
11  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
12  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
13  *  GNU General Public License for more details.
14  *
15  *  You should have received a copy of the GNU General Public License
16  *  along with GRUB.  If not, see <http://www.gnu.org/licenses/>.
17  */
18
19 #ifndef GRUB_EFI_PE32_HEADER
20 #define GRUB_EFI_PE32_HEADER    1
21
22 #include <grub/types.h>
23
24 /* The MSDOS compatibility stub. This was copied from the output of
25    objcopy, and it is not necessary to care about what this means.  */
26 #define GRUB_PE32_MSDOS_STUB \
27   { \
28     0x4d, 0x5a, 0x90, 0x00, 0x03, 0x00, 0x00, 0x00, \
29     0x04, 0x00, 0x00, 0x00, 0xff, 0xff, 0x00, 0x00, \
30     0xb8, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, \
31     0x40, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, \
32     0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, \
33     0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, \
34     0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, \
35     0x00, 0x00, 0x00, 0x00, 0x80, 0x00, 0x00, 0x00, \
36     0x0e, 0x1f, 0xba, 0x0e, 0x00, 0xb4, 0x09, 0xcd, \
37     0x21, 0xb8, 0x01, 0x4c, 0xcd, 0x21, 0x54, 0x68, \
38     0x69, 0x73, 0x20, 0x70, 0x72, 0x6f, 0x67, 0x72, \
39     0x61, 0x6d, 0x20, 0x63, 0x61, 0x6e, 0x6e, 0x6f, \
40     0x74, 0x20, 0x62, 0x65, 0x20, 0x72, 0x75, 0x6e, \
41     0x20, 0x69, 0x6e, 0x20, 0x44, 0x4f, 0x53, 0x20, \
42     0x6d, 0x6f, 0x64, 0x65, 0x2e, 0x0d, 0x0d, 0x0a, \
43     0x24, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00  \
44   }
45
46 #define GRUB_PE32_MSDOS_STUB_SIZE       0x80
47
48 #define GRUB_PE32_MAGIC                 0x5a4d
49
50 /* According to the spec, the minimal alignment is 512 bytes...
51    But some examples (such as EFI drivers in the Intel
52    Sample Implementation) use 32 bytes (0x20) instead, and it seems
53    to be working. For now, GRUB uses 512 bytes for safety.  */
54 #define GRUB_PE32_SECTION_ALIGNMENT     0x200
55 #define GRUB_PE32_FILE_ALIGNMENT        GRUB_PE32_SECTION_ALIGNMENT
56
57 struct grub_pe32_coff_header
58 {
59   grub_uint16_t machine;
60   grub_uint16_t num_sections;
61   grub_uint32_t time;
62   grub_uint32_t symtab_offset;
63   grub_uint32_t num_symbols;
64   grub_uint16_t optional_header_size;
65   grub_uint16_t characteristics;
66 };
67
68 #define GRUB_PE32_MACHINE_I386                  0x14c
69 #define GRUB_PE32_MACHINE_IA64                  0x200
70 #define GRUB_PE32_MACHINE_X86_64                0x8664
71 #define GRUB_PE32_MACHINE_ARMTHUMB_MIXED        0x01c2
72 #define GRUB_PE32_MACHINE_ARM64                 0xAA64
73
74 #define GRUB_PE32_RELOCS_STRIPPED               0x0001
75 #define GRUB_PE32_EXECUTABLE_IMAGE              0x0002
76 #define GRUB_PE32_LINE_NUMS_STRIPPED            0x0004
77 #define GRUB_PE32_LOCAL_SYMS_STRIPPED           0x0008
78 #define GRUB_PE32_AGGRESSIVE_WS_TRIM            0x0010
79 #define GRUB_PE32_LARGE_ADDRESS_AWARE           0x0020
80 #define GRUB_PE32_16BIT_MACHINE                 0x0040
81 #define GRUB_PE32_BYTES_REVERSED_LO             0x0080
82 #define GRUB_PE32_32BIT_MACHINE                 0x0100
83 #define GRUB_PE32_DEBUG_STRIPPED                0x0200
84 #define GRUB_PE32_REMOVABLE_RUN_FROM_SWAP       0x0400
85 #define GRUB_PE32_SYSTEM                        0x1000
86 #define GRUB_PE32_DLL                           0x2000
87 #define GRUB_PE32_UP_SYSTEM_ONLY                0x4000
88 #define GRUB_PE32_BYTES_REVERSED_HI             0x8000
89
90 struct grub_pe32_data_directory
91 {
92   grub_uint32_t rva;
93   grub_uint32_t size;
94 };
95
96 struct grub_pe32_optional_header
97 {
98   grub_uint16_t magic;
99   grub_uint8_t major_linker_version;
100   grub_uint8_t minor_linker_version;
101   grub_uint32_t code_size;
102   grub_uint32_t data_size;
103   grub_uint32_t bss_size;
104   grub_uint32_t entry_addr;
105   grub_uint32_t code_base;
106
107   grub_uint32_t data_base;
108   grub_uint32_t image_base;
109
110   grub_uint32_t section_alignment;
111   grub_uint32_t file_alignment;
112   grub_uint16_t major_os_version;
113   grub_uint16_t minor_os_version;
114   grub_uint16_t major_image_version;
115   grub_uint16_t minor_image_version;
116   grub_uint16_t major_subsystem_version;
117   grub_uint16_t minor_subsystem_version;
118   grub_uint32_t reserved;
119   grub_uint32_t image_size;
120   grub_uint32_t header_size;
121   grub_uint32_t checksum;
122   grub_uint16_t subsystem;
123   grub_uint16_t dll_characteristics;
124
125   grub_uint32_t stack_reserve_size;
126   grub_uint32_t stack_commit_size;
127   grub_uint32_t heap_reserve_size;
128   grub_uint32_t heap_commit_size;
129
130   grub_uint32_t loader_flags;
131   grub_uint32_t num_data_directories;
132
133   /* Data directories.  */
134   struct grub_pe32_data_directory export_table;
135   struct grub_pe32_data_directory import_table;
136   struct grub_pe32_data_directory resource_table;
137   struct grub_pe32_data_directory exception_table;
138   struct grub_pe32_data_directory certificate_table;
139   struct grub_pe32_data_directory base_relocation_table;
140   struct grub_pe32_data_directory debug;
141   struct grub_pe32_data_directory architecture;
142   struct grub_pe32_data_directory global_ptr;
143   struct grub_pe32_data_directory tls_table;
144   struct grub_pe32_data_directory load_config_table;
145   struct grub_pe32_data_directory bound_import;
146   struct grub_pe32_data_directory iat;
147   struct grub_pe32_data_directory delay_import_descriptor;
148   struct grub_pe32_data_directory com_runtime_header;
149   struct grub_pe32_data_directory reserved_entry;
150 };
151
152 struct grub_pe64_optional_header
153 {
154   grub_uint16_t magic;
155   grub_uint8_t major_linker_version;
156   grub_uint8_t minor_linker_version;
157   grub_uint32_t code_size;
158   grub_uint32_t data_size;
159   grub_uint32_t bss_size;
160   grub_uint32_t entry_addr;
161   grub_uint32_t code_base;
162
163   grub_uint64_t image_base;
164
165   grub_uint32_t section_alignment;
166   grub_uint32_t file_alignment;
167   grub_uint16_t major_os_version;
168   grub_uint16_t minor_os_version;
169   grub_uint16_t major_image_version;
170   grub_uint16_t minor_image_version;
171   grub_uint16_t major_subsystem_version;
172   grub_uint16_t minor_subsystem_version;
173   grub_uint32_t reserved;
174   grub_uint32_t image_size;
175   grub_uint32_t header_size;
176   grub_uint32_t checksum;
177   grub_uint16_t subsystem;
178   grub_uint16_t dll_characteristics;
179
180   grub_uint64_t stack_reserve_size;
181   grub_uint64_t stack_commit_size;
182   grub_uint64_t heap_reserve_size;
183   grub_uint64_t heap_commit_size;
184
185   grub_uint32_t loader_flags;
186   grub_uint32_t num_data_directories;
187
188   /* Data directories.  */
189   struct grub_pe32_data_directory export_table;
190   struct grub_pe32_data_directory import_table;
191   struct grub_pe32_data_directory resource_table;
192   struct grub_pe32_data_directory exception_table;
193   struct grub_pe32_data_directory certificate_table;
194   struct grub_pe32_data_directory base_relocation_table;
195   struct grub_pe32_data_directory debug;
196   struct grub_pe32_data_directory architecture;
197   struct grub_pe32_data_directory global_ptr;
198   struct grub_pe32_data_directory tls_table;
199   struct grub_pe32_data_directory load_config_table;
200   struct grub_pe32_data_directory bound_import;
201   struct grub_pe32_data_directory iat;
202   struct grub_pe32_data_directory delay_import_descriptor;
203   struct grub_pe32_data_directory com_runtime_header;
204   struct grub_pe32_data_directory reserved_entry;
205 };
206
207 #define GRUB_PE32_PE32_MAGIC    0x10b
208 #define GRUB_PE32_PE64_MAGIC    0x20b
209
210 #define GRUB_PE32_SUBSYSTEM_EFI_APPLICATION     10
211
212 #define GRUB_PE32_NUM_DATA_DIRECTORIES  16
213
214 struct grub_pe32_section_table
215 {
216   char name[8];
217   grub_uint32_t virtual_size;
218   grub_uint32_t virtual_address;
219   grub_uint32_t raw_data_size;
220   grub_uint32_t raw_data_offset;
221   grub_uint32_t relocations_offset;
222   grub_uint32_t line_numbers_offset;
223   grub_uint16_t num_relocations;
224   grub_uint16_t num_line_numbers;
225   grub_uint32_t characteristics;
226 };
227
228 #define GRUB_PE32_SCN_CNT_CODE                  0x00000020
229 #define GRUB_PE32_SCN_CNT_INITIALIZED_DATA      0x00000040
230 #define GRUB_PE32_SCN_MEM_DISCARDABLE           0x02000000
231 #define GRUB_PE32_SCN_MEM_EXECUTE               0x20000000
232 #define GRUB_PE32_SCN_MEM_READ                  0x40000000
233 #define GRUB_PE32_SCN_MEM_WRITE                 0x80000000
234
235 #define GRUB_PE32_SCN_ALIGN_1BYTES              0x00100000
236 #define GRUB_PE32_SCN_ALIGN_2BYTES              0x00200000
237 #define GRUB_PE32_SCN_ALIGN_4BYTES              0x00300000
238 #define GRUB_PE32_SCN_ALIGN_8BYTES              0x00400000
239 #define GRUB_PE32_SCN_ALIGN_16BYTES             0x00500000
240 #define GRUB_PE32_SCN_ALIGN_32BYTES             0x00600000
241 #define GRUB_PE32_SCN_ALIGN_64BYTES             0x00700000
242
243 #define GRUB_PE32_SCN_ALIGN_SHIFT               20
244 #define GRUB_PE32_SCN_ALIGN_MASK                7
245
246 #define GRUB_PE32_SIGNATURE_SIZE 4
247
248 struct grub_pe32_header
249 {
250   /* This should be filled in with GRUB_PE32_MSDOS_STUB.  */
251   grub_uint8_t msdos_stub[GRUB_PE32_MSDOS_STUB_SIZE];
252
253   /* This is always PE\0\0.  */
254   char signature[GRUB_PE32_SIGNATURE_SIZE];
255
256   /* The COFF file header.  */
257   struct grub_pe32_coff_header coff_header;
258
259 #if GRUB_TARGET_SIZEOF_VOID_P == 8
260   /* The Optional header.  */
261   struct grub_pe64_optional_header optional_header;
262 #else
263   /* The Optional header.  */
264   struct grub_pe32_optional_header optional_header;
265 #endif
266 };
267
268 struct grub_pe32_fixup_block
269 {
270   grub_uint32_t page_rva;
271   grub_uint32_t block_size;
272   grub_uint16_t entries[0];
273 };
274
275 #define GRUB_PE32_FIXUP_ENTRY(type, offset)     (((type) << 12) | (offset))
276
277 #define GRUB_PE32_REL_BASED_ABSOLUTE    0
278 #define GRUB_PE32_REL_BASED_HIGH        1
279 #define GRUB_PE32_REL_BASED_LOW         2
280 #define GRUB_PE32_REL_BASED_HIGHLOW     3
281 #define GRUB_PE32_REL_BASED_HIGHADJ     4
282 #define GRUB_PE32_REL_BASED_MIPS_JMPADDR 5
283 #define GRUB_PE32_REL_BASED_ARM_MOV32A  5
284 #define GRUB_PE32_REL_BASED_SECTION     6
285 #define GRUB_PE32_REL_BASED_REL         7
286 #define GRUB_PE32_REL_BASED_ARM_MOV32T  7
287 #define GRUB_PE32_REL_BASED_IA64_IMM64  9
288 #define GRUB_PE32_REL_BASED_DIR64       10
289 #define GRUB_PE32_REL_BASED_HIGH3ADJ    11
290
291 struct grub_pe32_symbol
292 {
293   union
294   {
295     char short_name[8];
296     grub_uint32_t long_name[2];
297   };
298
299   grub_uint32_t value;
300   grub_uint16_t section;
301   grub_uint16_t type;
302   grub_uint8_t storage_class;
303   grub_uint8_t num_aux;
304 } GRUB_PACKED;
305
306 #define GRUB_PE32_SYM_CLASS_EXTERNAL    2
307 #define GRUB_PE32_SYM_CLASS_STATIC      3
308 #define GRUB_PE32_SYM_CLASS_FILE        0x67
309
310 #define GRUB_PE32_DT_FUNCTION           0x20
311
312 struct grub_pe32_reloc
313 {
314   grub_uint32_t offset;
315   grub_uint32_t symtab_index;
316   grub_uint16_t type;
317 } GRUB_PACKED;
318
319 #define GRUB_PE32_REL_I386_DIR32        0x6
320 #define GRUB_PE32_REL_I386_REL32        0x14
321
322 #endif /* ! GRUB_EFI_PE32_HEADER */