]> git.proxmox.com Git - mirror_edk2.git/blame - BaseTools/Source/C/GenFw/ElfConvert.c
License header updated to match correct format.
[mirror_edk2.git] / BaseTools / Source / C / GenFw / ElfConvert.c
CommitLineData
f51461c8 1/** @file\r
97fa0ee9 2Elf convert solution\r
f51461c8 3\r
97fa0ee9 4Copyright (c) 2010 - 2014, Intel Corporation. All rights reserved.<BR>\r
f51461c8
LG
5\r
6This program and the accompanying materials are licensed and made available \r
7under the terms and conditions of the BSD License which accompanies this \r
8distribution. The full text of the license may be found at \r
9http://opensource.org/licenses/bsd-license.php\r
10\r
11THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,\r
12WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.\r
13\r
14**/\r
15\r
16#include "WinNtInclude.h"\r
17\r
18#ifndef __GNUC__\r
19#include <windows.h>\r
20#include <io.h>\r
21#endif\r
22#include <stdio.h>\r
23#include <stdlib.h>\r
24#include <string.h>\r
25#include <time.h>\r
26#include <ctype.h>\r
27\r
28#include <Common/UefiBaseTypes.h>\r
29#include <IndustryStandard/PeImage.h>\r
30\r
31#include "EfiUtilityMsgs.h"\r
32\r
33#include "GenFw.h"\r
34#include "ElfConvert.h"\r
35#include "Elf32Convert.h"\r
36#include "Elf64Convert.h"\r
37\r
38//\r
39// Result Coff file in memory.\r
40//\r
41UINT8 *mCoffFile = NULL;\r
42\r
43//\r
44// COFF relocation data\r
45//\r
46EFI_IMAGE_BASE_RELOCATION *mCoffBaseRel;\r
47UINT16 *mCoffEntryRel;\r
48\r
49//\r
50// Current offset in coff file.\r
51//\r
52UINT32 mCoffOffset;\r
53\r
54//\r
55// Offset in Coff file of headers and sections.\r
56//\r
57UINT32 mTableOffset;\r
58\r
59//\r
60//*****************************************************************************\r
61// Common ELF Functions\r
62//*****************************************************************************\r
63//\r
64\r
65VOID\r
66CoffAddFixupEntry(\r
67 UINT16 Val\r
68 )\r
69{\r
70 *mCoffEntryRel = Val;\r
71 mCoffEntryRel++;\r
72 mCoffBaseRel->SizeOfBlock += 2;\r
73 mCoffOffset += 2;\r
74}\r
75\r
76VOID\r
77CoffAddFixup(\r
78 UINT32 Offset,\r
79 UINT8 Type\r
80 )\r
81{\r
82 if (mCoffBaseRel == NULL\r
83 || mCoffBaseRel->VirtualAddress != (Offset & ~0xfff)) {\r
84 if (mCoffBaseRel != NULL) {\r
85 //\r
86 // Add a null entry (is it required ?)\r
87 //\r
88 CoffAddFixupEntry (0);\r
89 \r
90 //\r
91 // Pad for alignment.\r
92 //\r
93 if (mCoffOffset % 4 != 0)\r
94 CoffAddFixupEntry (0);\r
95 }\r
96\r
97 mCoffFile = realloc (\r
98 mCoffFile,\r
99 mCoffOffset + sizeof(EFI_IMAGE_BASE_RELOCATION) + 2*0x1000\r
100 );\r
101 memset (\r
102 mCoffFile + mCoffOffset, 0,\r
103 sizeof(EFI_IMAGE_BASE_RELOCATION) + 2*0x1000\r
104 );\r
105\r
106 mCoffBaseRel = (EFI_IMAGE_BASE_RELOCATION*)(mCoffFile + mCoffOffset);\r
107 mCoffBaseRel->VirtualAddress = Offset & ~0xfff;\r
108 mCoffBaseRel->SizeOfBlock = sizeof(EFI_IMAGE_BASE_RELOCATION);\r
109\r
110 mCoffEntryRel = (UINT16 *)(mCoffBaseRel + 1);\r
111 mCoffOffset += sizeof(EFI_IMAGE_BASE_RELOCATION);\r
112 }\r
113\r
114 //\r
115 // Fill the entry.\r
116 //\r
117 CoffAddFixupEntry((UINT16) ((Type << 12) | (Offset & 0xfff)));\r
118}\r
119\r
120VOID\r
121CreateSectionHeader (\r
122 const CHAR8 *Name,\r
123 UINT32 Offset,\r
124 UINT32 Size,\r
125 UINT32 Flags\r
126 )\r
127{\r
128 EFI_IMAGE_SECTION_HEADER *Hdr;\r
129 Hdr = (EFI_IMAGE_SECTION_HEADER*)(mCoffFile + mTableOffset);\r
130\r
131 strcpy((char *)Hdr->Name, Name);\r
132 Hdr->Misc.VirtualSize = Size;\r
133 Hdr->VirtualAddress = Offset;\r
134 Hdr->SizeOfRawData = Size;\r
135 Hdr->PointerToRawData = Offset;\r
136 Hdr->PointerToRelocations = 0;\r
137 Hdr->PointerToLinenumbers = 0;\r
138 Hdr->NumberOfRelocations = 0;\r
139 Hdr->NumberOfLinenumbers = 0;\r
140 Hdr->Characteristics = Flags;\r
141\r
142 mTableOffset += sizeof (EFI_IMAGE_SECTION_HEADER);\r
143}\r
144\r
145//\r
146//*****************************************************************************\r
147// Functions called from GenFw main code.\r
148//*****************************************************************************\r
149//\r
150\r
151INTN\r
152IsElfHeader (\r
153 UINT8 *FileBuffer\r
154)\r
155{\r
156 return (FileBuffer[EI_MAG0] == ELFMAG0 && \r
157 FileBuffer[EI_MAG1] == ELFMAG1 &&\r
158 FileBuffer[EI_MAG2] == ELFMAG2 &&\r
159 FileBuffer[EI_MAG3] == ELFMAG3);\r
160}\r
161\r
162BOOLEAN\r
163ConvertElf (\r
164 UINT8 **FileBuffer,\r
165 UINT32 *FileLength\r
166 )\r
167{\r
168 ELF_FUNCTION_TABLE ElfFunctions;\r
169 UINT8 EiClass;\r
170\r
171 //\r
172 // Determine ELF type and set function table pointer correctly.\r
173 //\r
174 VerboseMsg ("Check Elf Image Header");\r
175 EiClass = (*FileBuffer)[EI_CLASS];\r
176 if (EiClass == ELFCLASS32) {\r
177 if (!InitializeElf32 (*FileBuffer, &ElfFunctions)) {\r
178 return FALSE;\r
179 }\r
180 } else if (EiClass == ELFCLASS64) {\r
181 if (!InitializeElf64 (*FileBuffer, &ElfFunctions)) {\r
182 return FALSE;\r
183 }\r
184 } else {\r
185 Error (NULL, 0, 3000, "Unsupported", "ELF EI_CLASS not supported.");\r
186 return FALSE;\r
187 }\r
188\r
189 //\r
190 // Compute sections new address.\r
191 // \r
192 VerboseMsg ("Compute sections new address.");\r
193 ElfFunctions.ScanSections ();\r
194\r
195 //\r
196 // Write and relocate sections.\r
197 //\r
198 VerboseMsg ("Write and relocate sections.");\r
199 ElfFunctions.WriteSections (SECTION_TEXT);\r
200 ElfFunctions.WriteSections (SECTION_DATA);\r
201 ElfFunctions.WriteSections (SECTION_HII);\r
202\r
203 //\r
204 // Translate and write relocations.\r
205 //\r
206 VerboseMsg ("Translate and write relocations.");\r
207 ElfFunctions.WriteRelocations ();\r
208\r
209 //\r
210 // Write debug info.\r
211 //\r
212 VerboseMsg ("Write debug info.");\r
213 ElfFunctions.WriteDebug ();\r
214\r
215 //\r
216 // Make sure image size is correct before returning the new image.\r
217 //\r
218 VerboseMsg ("Set image size.");\r
219 ElfFunctions.SetImageSize ();\r
220\r
221 //\r
222 // Replace.\r
223 //\r
224 free (*FileBuffer);\r
225 *FileBuffer = mCoffFile;\r
226 *FileLength = mCoffOffset;\r
227\r
228 //\r
229 // Free resources used by ELF functions.\r
230 //\r
231 ElfFunctions.CleanUp ();\r
232 \r
233 return TRUE;\r
234}\r