]> git.proxmox.com Git - mirror_edk2.git/blob - Tools/CodeTools/TianoTools/GenCRC32Section/GenCRC32Section.c
Restructuring for better separation of Tool packages.
[mirror_edk2.git] / Tools / CodeTools / TianoTools / GenCRC32Section / GenCRC32Section.c
1 /*++
2
3 Copyright (c) 2004, Intel Corporation
4 All rights reserved. This program and the accompanying materials
5 are licensed and made available under the terms and conditions of the BSD License
6 which accompanies this distribution. The full text of the license may be found at
7 http://opensource.org/licenses/bsd-license.php
8
9 THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
10 WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
11
12 Module Name:
13
14 GenCRC32Section.c
15
16 Abstract:
17
18 This file contains functions required to generate a Firmware File System
19 file. The code is compliant with the Tiano C Coding standards.
20
21 --*/
22
23 #include "GenCRC32Section.h"
24
25 #define TOOLVERSION "0.2"
26
27 #define UTILITY_NAME "GenCrc32Section"
28
29 EFI_GUID gEfiCrc32SectionGuid = EFI_CRC32_GUIDED_SECTION_EXTRACTION_PROTOCOL_GUID;
30
31 EFI_STATUS
32 SignSectionWithCrc32 (
33 IN OUT UINT8 *FileBuffer,
34 IN OUT UINT32 *BufferSize,
35 IN UINT32 DataSize
36 )
37 /*++
38
39 Routine Description:
40
41 Signs the section with CRC32 and add GUIDed section header for the
42 signed data. data stays in same location (overwrites source data).
43
44 Arguments:
45
46 FileBuffer - Buffer containing data to sign
47
48 BufferSize - On input, the size of FileBuffer. On output, the size of
49 actual section data (including added section header).
50
51 DataSize - Length of data to Sign
52
53 Key - Key to use when signing. Currently only CRC32 is supported.
54
55 Returns:
56
57 EFI_SUCCESS - Successful
58 EFI_OUT_OF_RESOURCES - Not enough resource to complete the operation.
59
60 --*/
61 {
62
63 UINT32 Crc32Checksum;
64 EFI_STATUS Status;
65 UINT32 TotalSize;
66 CRC32_SECTION_HEADER Crc32Header;
67 UINT8 *SwapBuffer;
68
69 Crc32Checksum = 0;
70 SwapBuffer = NULL;
71
72 if (DataSize == 0) {
73 *BufferSize = 0;
74
75 return EFI_SUCCESS;
76 }
77
78 Status = CalculateCrc32 (FileBuffer, DataSize, &Crc32Checksum);
79 if (EFI_ERROR (Status)) {
80 return Status;
81 }
82
83 TotalSize = DataSize + CRC32_SECTION_HEADER_SIZE;
84 Crc32Header.GuidSectionHeader.CommonHeader.Type = EFI_SECTION_GUID_DEFINED;
85 Crc32Header.GuidSectionHeader.CommonHeader.Size[0] = (UINT8) (TotalSize & 0xff);
86 Crc32Header.GuidSectionHeader.CommonHeader.Size[1] = (UINT8) ((TotalSize & 0xff00) >> 8);
87 Crc32Header.GuidSectionHeader.CommonHeader.Size[2] = (UINT8) ((TotalSize & 0xff0000) >> 16);
88 memcpy (&(Crc32Header.GuidSectionHeader.SectionDefinitionGuid), &gEfiCrc32SectionGuid, sizeof (EFI_GUID));
89 Crc32Header.GuidSectionHeader.Attributes = EFI_GUIDED_SECTION_AUTH_STATUS_VALID;
90 Crc32Header.GuidSectionHeader.DataOffset = CRC32_SECTION_HEADER_SIZE;
91 Crc32Header.CRC32Checksum = Crc32Checksum;
92
93 SwapBuffer = (UINT8 *) malloc (DataSize);
94 if (SwapBuffer == NULL) {
95 return EFI_OUT_OF_RESOURCES;
96 }
97
98 memcpy (SwapBuffer, FileBuffer, DataSize);
99 memcpy (FileBuffer, &Crc32Header, CRC32_SECTION_HEADER_SIZE);
100 memcpy (FileBuffer + CRC32_SECTION_HEADER_SIZE, SwapBuffer, DataSize);
101
102 //
103 // Make sure section ends on a DWORD boundary
104 //
105 while ((TotalSize & 0x03) != 0) {
106 FileBuffer[TotalSize] = 0;
107 TotalSize++;
108 }
109
110 *BufferSize = TotalSize;
111
112 if (SwapBuffer != NULL) {
113 free (SwapBuffer);
114 }
115
116 return EFI_SUCCESS;
117 }
118
119 VOID
120 PrintUsage (
121 VOID
122 )
123 {
124 printf ("Usage:\n");
125 printf (UTILITY_NAME " -i \"inputfile1\" \"inputfile2\" -o \"outputfile\" \n");
126 printf (" -i \"inputfile\":\n ");
127 printf (" specifies the input files that would be signed to CRC32 Guided section.\n");
128 printf (" -o \"outputfile\":\n");
129 printf (" specifies the output file that is a CRC32 Guided section.\n");
130 }
131
132 INT32
133 ReadFilesContentsIntoBuffer (
134 IN CHAR8 *argv[],
135 IN INT32 Start,
136 IN OUT UINT8 **FileBuffer,
137 IN OUT UINT32 *BufferSize,
138 OUT UINT32 *ContentSize,
139 IN INT32 MaximumArguments
140 )
141 {
142 INT32 Index;
143 CHAR8 *FileName;
144 FILE *InputFile;
145 UINT8 Temp;
146 UINT32 Size;
147
148 FileName = NULL;
149 InputFile = NULL;
150 Size = 0;
151 Index = 0;
152
153 //
154 // read all input files into one file buffer
155 //
156 while (argv[Start + Index][0] != '-') {
157
158 FileName = argv[Start + Index];
159 InputFile = fopen (FileName, "rb");
160 if (InputFile == NULL) {
161 Error (NULL, 0, 0, FileName, "failed to open input binary file");
162 return -1;
163 }
164
165 fread (&Temp, sizeof (UINT8), 1, InputFile);
166 while (!feof (InputFile)) {
167 (*FileBuffer)[Size++] = Temp;
168 fread (&Temp, sizeof (UINT8), 1, InputFile);
169 }
170
171 fclose (InputFile);
172 InputFile = NULL;
173
174 //
175 // Make sure section ends on a DWORD boundary
176 //
177 while ((Size & 0x03) != 0) {
178 (*FileBuffer)[Size] = 0;
179 Size++;
180 }
181
182 Index++;
183 if (Index == MaximumArguments) {
184 break;
185 }
186 }
187
188 *ContentSize = Size;
189 return Index;
190 }
191
192 int
193 main (
194 INT32 argc,
195 CHAR8 *argv[]
196 )
197 {
198 FILE *OutputFile;
199 UINT8 *FileBuffer;
200 UINT32 BufferSize;
201 EFI_STATUS Status;
202 UINT32 ContentSize;
203 CHAR8 *OutputFileName;
204 INT32 ReturnValue;
205 INT32 Index;
206
207 OutputFile = NULL;
208 FileBuffer = NULL;
209 ContentSize = 0;
210 OutputFileName = NULL;
211
212 SetUtilityName (UTILITY_NAME);
213
214 if (argc == 1) {
215 PrintUsage ();
216 return -1;
217 }
218
219 BufferSize = 1024 * 1024 * 16;
220 FileBuffer = (UINT8 *) malloc (BufferSize * sizeof (UINT8));
221 if (FileBuffer == NULL) {
222 Error (NULL, 0, 0, "memory allocation failed", NULL);
223 return -1;
224 }
225
226 ZeroMem (FileBuffer, BufferSize);
227
228 for (Index = 0; Index < argc; Index++) {
229 if (strcmpi (argv[Index], "-i") == 0) {
230 ReturnValue = ReadFilesContentsIntoBuffer (
231 argv,
232 (Index + 1),
233 &FileBuffer,
234 &BufferSize,
235 &ContentSize,
236 (argc - (Index + 1))
237 );
238 if (ReturnValue == -1) {
239 Error (NULL, 0, 0, "failed to read file contents", NULL);
240 return -1;
241 }
242
243 Index += ReturnValue;
244 }
245
246 if (strcmpi (argv[Index], "-o") == 0) {
247 OutputFileName = argv[Index + 1];
248 }
249 }
250
251 OutputFile = fopen (OutputFileName, "wb");
252 if (OutputFile == NULL) {
253 Error (NULL, 0, 0, OutputFileName, "failed to open output binary file");
254 free (FileBuffer);
255 return -1;
256 }
257
258 /*
259 //
260 // make sure section ends on a DWORD boundary ??
261 //
262 while ( (Size & 0x03) != 0 ) {
263 FileBuffer[Size] = 0;
264 Size ++;
265 }
266 */
267 Status = SignSectionWithCrc32 (FileBuffer, &BufferSize, ContentSize);
268 if (EFI_ERROR (Status)) {
269 Error (NULL, 0, 0, "failed to sign section", NULL);
270 free (FileBuffer);
271 fclose (OutputFile);
272 return -1;
273 }
274
275 ContentSize = fwrite (FileBuffer, sizeof (UINT8), BufferSize, OutputFile);
276 if (ContentSize != BufferSize) {
277 Error (NULL, 0, 0, "failed to write output buffer", NULL);
278 ReturnValue = -1;
279 } else {
280 ReturnValue = 0;
281 }
282
283 free (FileBuffer);
284 fclose (OutputFile);
285 return ReturnValue;
286 }