xref: /DragonStub/docs/README.gnuefi (revision f1de0317e130286d7363f30f4f92961ab62fe191)
1*f1de0317SLoGin	-------------------------------------------------
2*f1de0317SLoGin	Building EFI Applications Using the GNU Toolchain
3*f1de0317SLoGin	-------------------------------------------------
4*f1de0317SLoGin
5*f1de0317SLoGin		David Mosberger <davidm@hpl.hp.com>
6*f1de0317SLoGin
7*f1de0317SLoGin			23 September 1999
8*f1de0317SLoGin
9*f1de0317SLoGin
10*f1de0317SLoGin		Copyright (c) 1999-2007 Hewlett-Packard Co.
11*f1de0317SLoGin		Copyright (c) 2006-2010 Intel Co.
12*f1de0317SLoGin
13*f1de0317SLoGinLast update: 04/09/2007
14*f1de0317SLoGin
15*f1de0317SLoGin* Introduction
16*f1de0317SLoGin
17*f1de0317SLoGinThis document has two parts: the first part describes how to develop
18*f1de0317SLoGinEFI applications for IA-64,x86 and x86_64 using the GNU toolchain and the EFI
19*f1de0317SLoGindevelopment environment contained in this directory.  The second part
20*f1de0317SLoGindescribes some of the more subtle aspects of how this development
21*f1de0317SLoGinenvironment works.
22*f1de0317SLoGin
23*f1de0317SLoGin
24*f1de0317SLoGin
25*f1de0317SLoGin* Part 1: Developing EFI Applications
26*f1de0317SLoGin
27*f1de0317SLoGin
28*f1de0317SLoGin** Prerequisites:
29*f1de0317SLoGin
30*f1de0317SLoGin To develop x86 and x86_64 EFI applications, the following tools are needed:
31*f1de0317SLoGin
32*f1de0317SLoGin	- gcc-3.0 or newer (gcc 2.7.2 is NOT sufficient!)
33*f1de0317SLoGin	  As of gnu-efi-3.0b, the Redhat 8.0 toolchain is known to work,
34*f1de0317SLoGin	  but the Redhat 9.0 toolchain is not currently supported.
35*f1de0317SLoGin
36*f1de0317SLoGin	- A version of "objcopy" that supports EFI applications.  To
37*f1de0317SLoGin	  check if your version includes EFI support, issue the
38*f1de0317SLoGin	  command:
39*f1de0317SLoGin
40*f1de0317SLoGin		objcopy --help
41*f1de0317SLoGin
42*f1de0317SLoGin	  Verify that the line "supported targets" contains the string
43*f1de0317SLoGin	  "efi-app-ia32" and "efi-app-x86_64" and that the "-j" option
44*f1de0317SLoGin	  accepts wildcards. The binutils release binutils-2.24
45*f1de0317SLoGin	  supports Intel64 EFI and accepts wildcard section names.
46*f1de0317SLoGin
47*f1de0317SLoGin	- For debugging purposes, it's useful to have a version of
48*f1de0317SLoGin	  "objdump" that supports EFI applications as well.  This
49*f1de0317SLoGin	  allows inspect and disassemble EFI binaries.
50*f1de0317SLoGin
51*f1de0317SLoGin To develop IA-64 EFI applications, the following tools are needed:
52*f1de0317SLoGin
53*f1de0317SLoGin	- A version of gcc newer than July 30th 1999 (older versions
54*f1de0317SLoGin	  had problems with generating position independent code).
55*f1de0317SLoGin	  As of gnu-efi-3.0b, gcc-3.1 is known to work well.
56*f1de0317SLoGin
57*f1de0317SLoGin	- A version of "objcopy" that supports EFI applications.  To
58*f1de0317SLoGin	  check if your version includes EFI support, issue the
59*f1de0317SLoGin	  command:
60*f1de0317SLoGin
61*f1de0317SLoGin		objcopy --help
62*f1de0317SLoGin
63*f1de0317SLoGin	  Verify that the line "supported targets" contains the string
64*f1de0317SLoGin	  "efi-app-ia64" and that the "-j" option accepts wildcards.
65*f1de0317SLoGin
66*f1de0317SLoGin	- For debugging purposes, it's useful to have a version of
67*f1de0317SLoGin	  "objdump" that supports EFI applications as well.  This
68*f1de0317SLoGin	  allows inspect and disassemble EFI binaries.
69*f1de0317SLoGin
70*f1de0317SLoGin
71*f1de0317SLoGin** Directory Structure
72*f1de0317SLoGin
73*f1de0317SLoGinThis EFI development environment contains the following
74*f1de0317SLoGinsubdirectories:
75*f1de0317SLoGin
76*f1de0317SLoGin inc:   This directory contains the EFI-related include files.  The
77*f1de0317SLoGin	files are taken from Intel's EFI source distribution, except
78*f1de0317SLoGin	that various fixes were applied to make it compile with the
79*f1de0317SLoGin	GNU toolchain.
80*f1de0317SLoGin
81*f1de0317SLoGin lib:   This directory contains the source code for Intel's EFI library.
82*f1de0317SLoGin	Again, the files are taken from Intel's EFI source
83*f1de0317SLoGin	distribution, with changes to make them compile with the GNU
84*f1de0317SLoGin	toolchain.
85*f1de0317SLoGin
86*f1de0317SLoGin gnuefi: This directory contains the glue necessary to convert ELF64
87*f1de0317SLoGin	binaries to EFI binaries.  Various runtime code bits, such as
88*f1de0317SLoGin	a self-relocator are included as well.  This code has been
89*f1de0317SLoGin	contributed by the Hewlett-Packard Company and is distributed
90*f1de0317SLoGin	under the GNU GPL.
91*f1de0317SLoGin
92*f1de0317SLoGin apps:	This directory contains a few simple EFI test apps.
93*f1de0317SLoGin
94*f1de0317SLoGin** Setup
95*f1de0317SLoGin
96*f1de0317SLoGinIt is necessary to edit the Makefile in the directory containing this
97*f1de0317SLoGinREADME file before EFI applications can be built.  Specifically, you
98*f1de0317SLoGinshould verify that macros CC, AS, LD, AR, RANLIB, and OBJCOPY point to
99*f1de0317SLoGinthe appropriate compiler, assembler, linker, ar, and ranlib binaries,
100*f1de0317SLoGinrespectively.
101*f1de0317SLoGin
102*f1de0317SLoGinIf you're working in a cross-development environment, be sure to set
103*f1de0317SLoGinmacro ARCH to the desired target architecture ("ia32" for x86, "x86_64" for
104*f1de0317SLoGinx86_64 and "ia64" for IA-64).  For convenience, this can also be done from
105*f1de0317SLoGinthe make command line (e.g., "make ARCH=ia64").
106*f1de0317SLoGin
107*f1de0317SLoGin
108*f1de0317SLoGin** Building
109*f1de0317SLoGin
110*f1de0317SLoGinTo build the sample EFI applications provided in subdirectory "apps",
111*f1de0317SLoGinsimply invoke "make" in the toplevel directory (the directory
112*f1de0317SLoGincontaining this README file).  This should build lib/libefi.a and
113*f1de0317SLoGingnuefi/libgnuefi.a first and then all the EFI applications such as a
114*f1de0317SLoGinapps/t6.efi.
115*f1de0317SLoGin
116*f1de0317SLoGin
117*f1de0317SLoGin** Running
118*f1de0317SLoGin
119*f1de0317SLoGinJust copy the EFI application (e.g., apps/t6.efi) to the EFI
120*f1de0317SLoGinfilesystem, boot EFI, and then select "Invoke EFI application" to run
121*f1de0317SLoGinthe application you want to test.  Alternatively, you can invoke the
122*f1de0317SLoGinIntel-provided "nshell" application and then invoke your test binary
123*f1de0317SLoGinvia the command line interface that "nshell" provides.
124*f1de0317SLoGin
125*f1de0317SLoGin
126*f1de0317SLoGin** Writing Your Own EFI Application
127*f1de0317SLoGin
128*f1de0317SLoGinSuppose you have your own EFI application in a file called
129*f1de0317SLoGin"apps/myefiapp.c".  To get this application built by the GNU EFI build
130*f1de0317SLoGinenvironment, simply add "myefiapp.efi" to macro TARGETS in
131*f1de0317SLoGinapps/Makefile.  Once this is done, invoke "make" in the top level
132*f1de0317SLoGindirectory.  This should result in EFI application apps/myefiapp.efi,
133*f1de0317SLoGinready for execution.
134*f1de0317SLoGin
135*f1de0317SLoGinThe GNU EFI build environment allows to write EFI applications as
136*f1de0317SLoGindescribed in Intel's EFI documentation, except for two differences:
137*f1de0317SLoGin
138*f1de0317SLoGin - The EFI application's entry point is always called "efi_main".  The
139*f1de0317SLoGin   declaration of this routine is:
140*f1de0317SLoGin
141*f1de0317SLoGin    EFI_STATUS efi_main (EFI_HANDLE image, EFI_SYSTEM_TABLE *systab);
142*f1de0317SLoGin
143*f1de0317SLoGin - UNICODE string literals must be written as W2U(L"Sample String")
144*f1de0317SLoGin   instead of just L"Sample String".  The W2U() macro is defined in
145*f1de0317SLoGin   <efilib.h>.  This header file also declares the function W2UCpy()
146*f1de0317SLoGin   which allows to convert a wide string into a UNICODE string and
147*f1de0317SLoGin   store the result in a programmer-supplied buffer.
148*f1de0317SLoGin
149*f1de0317SLoGin - Calls to EFI services should be made via uefi_call_wrapper(). This
150*f1de0317SLoGin   ensures appropriate parameter passing for the architecture.
151*f1de0317SLoGin
152*f1de0317SLoGin
153*f1de0317SLoGin* Part 2: Inner Workings
154*f1de0317SLoGin
155*f1de0317SLoGinWARNING: This part contains all the gory detail of how the GNU EFI
156*f1de0317SLoGintoolchain works.  Normal users do not have to worry about such
157*f1de0317SLoGindetails.  Reading this part incurs a definite risk of inducing severe
158*f1de0317SLoGinheadaches or other maladies.
159*f1de0317SLoGin
160*f1de0317SLoGinThe basic idea behind the GNU EFI build environment is to use the GNU
161*f1de0317SLoGintoolchain to build a normal ELF binary that, at the end, is converted
162*f1de0317SLoGinto an EFI binary.  EFI binaries are really just PE32+ binaries.  PE
163*f1de0317SLoGinstands for "Portable Executable" and is the object file format
164*f1de0317SLoGinMicrosoft is using on its Windows platforms.  PE is basically the COFF
165*f1de0317SLoGinobject file format with an MS-DOS2.0 compatible header slapped on in
166*f1de0317SLoGinfront of it.  The "32" in PE32+ stands for 32 bits, meaning that PE32
167*f1de0317SLoGinis a 32-bit object file format.  The plus in "PE32+" indicates that
168*f1de0317SLoGinthis format has been hacked to allow loading a 4GB binary anywhere in
169*f1de0317SLoGina 64-bit address space (unlike ELF64, however, this is not a full
170*f1de0317SLoGin64-bit object file format because the entire binary cannot span more
171*f1de0317SLoGinthan 4GB of address space).  EFI binaries are plain PE32+ binaries
172*f1de0317SLoGinexcept that the "subsystem id" differs from normal Windows binaries.
173*f1de0317SLoGinThere are two flavors of EFI binaries: "applications" and "drivers"
174*f1de0317SLoGinand each has there own subsystem id and are identical otherwise.  At
175*f1de0317SLoGinpresent, the GNU EFI build environment supports the building of EFI
176*f1de0317SLoGinapplications only, though it would be trivial to generate drivers, as
177*f1de0317SLoGinthe only difference is the subsystem id.  For more details on PE32+,
178*f1de0317SLoGinsee the spec at
179*f1de0317SLoGin
180*f1de0317SLoGin	http://msdn.microsoft.com/library/specs/msdn_pecoff.htm.
181*f1de0317SLoGin
182*f1de0317SLoGinIn theory, converting a suitable ELF64 binary to PE32+ is easy and
183*f1de0317SLoGincould be accomplished with the "objcopy" utility by specifying option
184*f1de0317SLoGin--target=efi-app-ia32 (x86) or --target=efi-app-ia64 (IA-64).  But
185*f1de0317SLoGinlife never is that easy, so here some complicating factors:
186*f1de0317SLoGin
187*f1de0317SLoGin (1) COFF sections are very different from ELF sections.
188*f1de0317SLoGin
189*f1de0317SLoGin	ELF binaries distinguish between program headers and sections.
190*f1de0317SLoGin	The program headers describe the memory segments that need to
191*f1de0317SLoGin	be loaded/initialized, whereas the sections describe what
192*f1de0317SLoGin	constitutes those segments.  In COFF (and therefore PE32+) no
193*f1de0317SLoGin	such distinction is made.  Thus, COFF sections need to be page
194*f1de0317SLoGin	aligned and have a size that is a multiple of the page size
195*f1de0317SLoGin	(4KB for EFI), whereas ELF allows sections at arbitrary
196*f1de0317SLoGin	addresses and with arbitrary sizes.
197*f1de0317SLoGin
198*f1de0317SLoGin (2) EFI binaries should be relocatable.
199*f1de0317SLoGin
200*f1de0317SLoGin	Since EFI binaries are executed in physical mode, EFI cannot
201*f1de0317SLoGin	guarantee that a given binary can be loaded at its preferred
202*f1de0317SLoGin	address.  EFI does _try_ to load a binary at it's preferred
203*f1de0317SLoGin	address, but if it can't do so, it will load it at another
204*f1de0317SLoGin	address and then relocate the binary using the contents of the
205*f1de0317SLoGin	.reloc section.
206*f1de0317SLoGin
207*f1de0317SLoGin (3) On IA-64, the EFI entry point needs to point to a function
208*f1de0317SLoGin     descriptor, not to the code address of the entry point.
209*f1de0317SLoGin
210*f1de0317SLoGin (4) The EFI specification assumes that wide characters use UNICODE
211*f1de0317SLoGin     encoding.
212*f1de0317SLoGin
213*f1de0317SLoGin	ANSI C does not specify the size or encoding that a wide
214*f1de0317SLoGin	character uses.  These choices are "implementation defined".
215*f1de0317SLoGin	On most UNIX systems, the GNU toolchain uses a wchar_t that is
216*f1de0317SLoGin	4 bytes in size.  The encoding used for such characters is
217*f1de0317SLoGin	(mostly) UCS4.
218*f1de0317SLoGin
219*f1de0317SLoGinIn the following sections, we address how the GNU EFI build
220*f1de0317SLoGinenvironment addresses each of these issues.
221*f1de0317SLoGin
222*f1de0317SLoGin
223*f1de0317SLoGin** (1) Accommodating COFF Sections
224*f1de0317SLoGin
225*f1de0317SLoGinIn order to satisfy the COFF constraint of page-sized and page-aligned
226*f1de0317SLoGinsections, the GNU EFI build environment uses the special linker script
227*f1de0317SLoGinin gnuefi/elf_$(ARCH)_efi.lds where $(ARCH) is the target architecture
228*f1de0317SLoGin("ia32" for x86, "x86_64" for x86_64 and "ia64" for IA-64).
229*f1de0317SLoGinThis script is set up to create only eight COFF section, each page aligned
230*f1de0317SLoGinand page sized.These eight sections are used to group together the much
231*f1de0317SLoGingreater number of sections that are typically present in ELF object files.
232*f1de0317SLoGinSpecifically:
233*f1de0317SLoGin
234*f1de0317SLoGin .hash (and/or .gnu.hash)
235*f1de0317SLoGin	Collects the ELF .hash info (this section _must_ be the first
236*f1de0317SLoGin	section in order to build a shared object file; the section is
237*f1de0317SLoGin	not actually loaded or used at runtime).
238*f1de0317SLoGin
239*f1de0317SLoGin	GNU binutils provides a mechanism to generate different hash info
240*f1de0317SLoGin	via --hash-style=<sysv|gnu|both> option. In this case output
241*f1de0317SLoGin	shared object will contain .hash section, .gnu.hash section or
242*f1de0317SLoGin	both. In order to generate correct output linker script preserves
243*f1de0317SLoGin	both types of hash sections.
244*f1de0317SLoGin
245*f1de0317SLoGin .text
246*f1de0317SLoGin	Collects all sections containing executable code.
247*f1de0317SLoGin
248*f1de0317SLoGin .data
249*f1de0317SLoGin	Collects read-only and read-write data, literal string data,
250*f1de0317SLoGin	global offset tables, the uninitialized data segment (bss) and
251*f1de0317SLoGin	various other sections containing data.
252*f1de0317SLoGin
253*f1de0317SLoGin	The reason read-only data is placed here instead of the in
254*f1de0317SLoGin	.text is to make it possible to disassemble the .text section
255*f1de0317SLoGin	without getting garbage due to read-only data.  Besides, since
256*f1de0317SLoGin	EFI binaries execute in physical mode, differences in page
257*f1de0317SLoGin	protection do not matter.
258*f1de0317SLoGin
259*f1de0317SLoGin	The reason the uninitialized data is placed in this section is
260*f1de0317SLoGin	that the EFI loader appears to be unable to handle sections
261*f1de0317SLoGin	that are allocated but not loaded from the binary.
262*f1de0317SLoGin
263*f1de0317SLoGin .dynamic, .dynsym, .rela, .rel, .reloc
264*f1de0317SLoGin	These sections contains the dynamic information necessary to
265*f1de0317SLoGin	self-relocate the binary (see below).
266*f1de0317SLoGin
267*f1de0317SLoGinA couple of more points worth noting about the linker script:
268*f1de0317SLoGin
269*f1de0317SLoGin o On IA-64, the global pointer symbol (__gp) needs to be placed such
270*f1de0317SLoGin   that the _entire_ EFI binary can be addressed using the signed
271*f1de0317SLoGin   22-bit offset that the "addl" instruction affords.  Specifically,
272*f1de0317SLoGin   this means that __gp should be placed at ImageBase + 0x200000.
273*f1de0317SLoGin   Strictly speaking, only a couple of symbols need to be addressable
274*f1de0317SLoGin   in this fashion, so with some care it should be possible to build
275*f1de0317SLoGin   binaries much larger than 4MB.  To get a list of symbols that need
276*f1de0317SLoGin   to be addressable in this fashion, grep the assembly files in
277*f1de0317SLoGin   directory gnuefi for the string "@gprel".
278*f1de0317SLoGin
279*f1de0317SLoGin o The link address (ImageBase) of the binary is (arbitrarily) set to
280*f1de0317SLoGin   zero.  This could be set to something larger to increase the chance
281*f1de0317SLoGin   of EFI being able to load the binary without requiring relocation.
282*f1de0317SLoGin   However, a start address of 0 makes debugging a wee bit easier
283*f1de0317SLoGin   (great for those of us who can add, but not subtract... ;-).
284*f1de0317SLoGin
285*f1de0317SLoGin o The relocation related sections (.dynamic, .rel, .rela, .reloc)
286*f1de0317SLoGin   cannot be placed inside .data because some tools in the GNU
287*f1de0317SLoGin   toolchain rely on the existence of these sections.
288*f1de0317SLoGin
289*f1de0317SLoGin o Some sections in the ELF binary intentionally get dropped when
290*f1de0317SLoGin   building the EFI binary.  Particularly noteworthy are the dynamic
291*f1de0317SLoGin   relocation sections for the .plabel and .reloc sections.  It would
292*f1de0317SLoGin   be _wrong_ to include these sections in the EFI binary because it
293*f1de0317SLoGin   would result in .reloc and .plabel being relocated twice (once by
294*f1de0317SLoGin   the EFI loader and once by the self-relocator; see below for a
295*f1de0317SLoGin   description of the latter).  Specifically, only the sections
296*f1de0317SLoGin   mentioned with the -j option in the final "objcopy" command are
297*f1de0317SLoGin   retained in the EFI binary (see Make.rules).
298*f1de0317SLoGin
299*f1de0317SLoGin
300*f1de0317SLoGin** (2) Building Relocatable Binaries
301*f1de0317SLoGin
302*f1de0317SLoGinELF binaries are normally linked for a fixed load address and are thus
303*f1de0317SLoGinnot relocatable.  The only kind of ELF object that is relocatable are
304*f1de0317SLoGinshared objects ("shared libraries").  However, even those objects are
305*f1de0317SLoGinusually not completely position independent and therefore require
306*f1de0317SLoGinruntime relocation by the dynamic loader.  For example, IA-64 binaries
307*f1de0317SLoGinnormally require relocation of the global offset table.
308*f1de0317SLoGin
309*f1de0317SLoGinThe approach to building relocatable binaries in the GNU EFI build
310*f1de0317SLoGinenvironment is to:
311*f1de0317SLoGin
312*f1de0317SLoGin (a) build an ELF shared object
313*f1de0317SLoGin
314*f1de0317SLoGin (b) link it together with a self-relocator that takes care of
315*f1de0317SLoGin     applying the dynamic relocations that may be present in the
316*f1de0317SLoGin     ELF shared object
317*f1de0317SLoGin
318*f1de0317SLoGin (c) convert the resulting image to an EFI binary
319*f1de0317SLoGin
320*f1de0317SLoGinThe self-relocator is of course architecture dependent.  The x86
321*f1de0317SLoGinversion can be found in gnuefi/reloc_ia32.c, the x86_64 version
322*f1de0317SLoGincan be found in gnuefi/reloc_x86_64.c and the IA-64 version can be
323*f1de0317SLoGinfound in gnuefi/reloc_ia64.S.
324*f1de0317SLoGin
325*f1de0317SLoGinThe self-relocator operates as follows: the startup code invokes it
326*f1de0317SLoGinright after EFI has handed off control to the EFI binary at symbol
327*f1de0317SLoGin"_start".  Upon activation, the self-relocator searches the .dynamic
328*f1de0317SLoGinsection (whose starting address is given by symbol _DYNAMIC) for the
329*f1de0317SLoGindynamic relocation information, which can be found in the DT_REL,
330*f1de0317SLoGinDT_RELSZ, and DT_RELENT entries of the dynamic table (DT_RELA,
331*f1de0317SLoGinDT_RELASZ, and DT_RELAENT in the case of rela relocations, as is the
332*f1de0317SLoGincase for IA-64).  The dynamic relocation information points to the ELF
333*f1de0317SLoGinrelocation table.  Once this table is found, the self-relocator walks
334*f1de0317SLoGinthrough it, applying each relocation one by one.  Since the EFI
335*f1de0317SLoGinbinaries are fully resolved shared objects, only a subset of all
336*f1de0317SLoGinpossible relocations need to be supported.  Specifically, on x86 only
337*f1de0317SLoGinthe R_386_RELATIVE relocation is needed.  On IA-64, the relocations
338*f1de0317SLoGinR_IA64_DIR64LSB, R_IA64_REL64LSB, and R_IA64_FPTR64LSB are needed.
339*f1de0317SLoGinNote that the R_IA64_FPTR64LSB relocation requires access to the
340*f1de0317SLoGindynamic symbol table.  This is why the .dynsym section is included in
341*f1de0317SLoGinthe EFI binary.  Another complication is that this relocation requires
342*f1de0317SLoGinmemory to hold the function descriptors (aka "procedure labels" or
343*f1de0317SLoGin"plabels").  Each function descriptor uses 16 bytes of memory.  The
344*f1de0317SLoGinIA-64 self-relocator currently reserves a static memory area that can
345*f1de0317SLoGinhold 100 of these descriptors.  If the self-relocator runs out of
346*f1de0317SLoGinspace, it causes the EFI binary to fail with error code 5
347*f1de0317SLoGin(EFI_BUFFER_TOO_SMALL).  When this happens, the manifest constant
348*f1de0317SLoGinMAX_FUNCTION_DESCRIPTORS in gnuefi/reloc_ia64.S should be increased
349*f1de0317SLoGinand the application recompiled.  An easy way to count the number of
350*f1de0317SLoGinfunction descriptors required by an EFI application is to run the
351*f1de0317SLoGincommand:
352*f1de0317SLoGin
353*f1de0317SLoGin  objdump --dynamic-reloc example.so | fgrep FPTR64 | wc -l
354*f1de0317SLoGin
355*f1de0317SLoGinassuming "example" is the name of the desired EFI application.
356*f1de0317SLoGin
357*f1de0317SLoGin
358*f1de0317SLoGin** (3) Creating the Function Descriptor for the IA-64 EFI Binaries
359*f1de0317SLoGin
360*f1de0317SLoGinAs mentioned above, the IA-64 PE32+ format assumes that the entry
361*f1de0317SLoGinpoint of the binary is a function descriptor.  A function descriptors
362*f1de0317SLoGinconsists of two double words: the first one is the code entry point
363*f1de0317SLoGinand the second is the global pointer that should be loaded before
364*f1de0317SLoGincalling the entry point.  Since the ELF toolchain doesn't know how to
365*f1de0317SLoGingenerate a function descriptor for the entry point, the startup code
366*f1de0317SLoGinin gnuefi/crt0-efi-ia64.S crafts one manually by with the code:
367*f1de0317SLoGin
368*f1de0317SLoGin	        .section .plabel, "a"
369*f1de0317SLoGin	_start_plabel:
370*f1de0317SLoGin	        data8   _start
371*f1de0317SLoGin	        data8   __gp
372*f1de0317SLoGin
373*f1de0317SLoGinthis places the procedure label for entry point _start in a section
374*f1de0317SLoGincalled ".plabel".  Now, the only problem is that _start and __gp need
375*f1de0317SLoGinto be relocated _before_ EFI hands control over to the EFI binary.
376*f1de0317SLoGinFortunately, PE32+ defines a section called ".reloc" that can achieve
377*f1de0317SLoGinthis.  Thus, in addition to manually crafting the function descriptor,
378*f1de0317SLoGinthe startup code also crafts a ".reloc" section that has will cause
379*f1de0317SLoGinthe EFI loader to relocate the function descriptor before handing over
380*f1de0317SLoGincontrol to the EFI binary (again, see the PECOFF spec mentioned above
381*f1de0317SLoGinfor details).
382*f1de0317SLoGin
383*f1de0317SLoGinA final question may be why .plabel and .reloc need to go in their own
384*f1de0317SLoGinCOFF sections.  The answer is simply: we need to be able to discard
385*f1de0317SLoGinthe relocation entries that are generated for these sections.  By
386*f1de0317SLoGinplacing them in these sections, the relocations end up in sections
387*f1de0317SLoGin".rela.plabel" and ".rela.reloc" which makes it easy to filter them
388*f1de0317SLoGinout in the filter script.  Also, the ".reloc" section needs to be in
389*f1de0317SLoGinits own section so that the objcopy program can recognize it and can
390*f1de0317SLoGincreate the correct directory entries in the PE32+ binary.
391*f1de0317SLoGin
392*f1de0317SLoGin
393*f1de0317SLoGin** (4) Convenient and Portable Generation of UNICODE String Literals
394*f1de0317SLoGin
395*f1de0317SLoGinAs of gnu-efi-3.0, we make use (and somewhat abuse) the gcc option
396*f1de0317SLoGinthat forces wide characters (WCHAR_T) to use short integers (2 bytes)
397*f1de0317SLoGininstead of integers (4 bytes). This way we match the Unicode character
398*f1de0317SLoGinsize. By abuse, we mean that we rely on the fact that the regular ASCII
399*f1de0317SLoGincharacters are encoded the same way between (short) wide characters
400*f1de0317SLoGinand Unicode and basically only use the first byte. This allows us
401*f1de0317SLoGinto just use them interchangeably.
402*f1de0317SLoGin
403*f1de0317SLoGinThe gcc option to force short wide characters is : -fshort-wchar
404*f1de0317SLoGin
405*f1de0317SLoGin			* * * The End * * *
406