1 | /** @file
|
---|
2 |
|
---|
3 | VfrCompiler main class and main function.
|
---|
4 |
|
---|
5 | Copyright (c) 2004 - 2019, Intel Corporation. All rights reserved.<BR>
|
---|
6 | SPDX-License-Identifier: BSD-2-Clause-Patent
|
---|
7 |
|
---|
8 | **/
|
---|
9 |
|
---|
10 | #include "stdio.h"
|
---|
11 | #include "stdlib.h"
|
---|
12 | #include "string.h"
|
---|
13 | #include "VfrCompiler.h"
|
---|
14 | #include "CommonLib.h"
|
---|
15 | #include "EfiUtilityMsgs.h"
|
---|
16 |
|
---|
17 | PACKAGE_DATA gCBuffer;
|
---|
18 | PACKAGE_DATA gRBuffer;
|
---|
19 | CVfrStringDB gCVfrStringDB;
|
---|
20 |
|
---|
21 | VOID
|
---|
22 | CVfrCompiler::DebugError (
|
---|
23 | IN CHAR8 *FileName,
|
---|
24 | IN UINT32 LineNumber,
|
---|
25 | IN UINT32 MessageCode,
|
---|
26 | IN CONST CHAR8 *Text,
|
---|
27 | IN CONST CHAR8 *MsgFmt,
|
---|
28 | ...
|
---|
29 | )
|
---|
30 | {
|
---|
31 | va_list List;
|
---|
32 | va_start (List, MsgFmt);
|
---|
33 | PrintMessage ((CHAR8 *) "ERROR", FileName, LineNumber, MessageCode, (CHAR8 *) Text, (CHAR8 *) MsgFmt, List);
|
---|
34 | va_end (List);
|
---|
35 | }
|
---|
36 |
|
---|
37 | VOID
|
---|
38 | CVfrCompiler::SET_RUN_STATUS (
|
---|
39 | IN COMPILER_RUN_STATUS Status
|
---|
40 | )
|
---|
41 | {
|
---|
42 | mRunStatus = Status;
|
---|
43 | }
|
---|
44 |
|
---|
45 | BOOLEAN
|
---|
46 | CVfrCompiler::IS_RUN_STATUS (
|
---|
47 | IN COMPILER_RUN_STATUS Status
|
---|
48 | )
|
---|
49 | {
|
---|
50 | return mRunStatus == Status;
|
---|
51 | }
|
---|
52 |
|
---|
53 | VOID
|
---|
54 | CVfrCompiler::OptionInitialization (
|
---|
55 | IN INT32 Argc,
|
---|
56 | IN CHAR8 **Argv
|
---|
57 | )
|
---|
58 | {
|
---|
59 | INT32 Index;
|
---|
60 | EFI_STATUS Status;
|
---|
61 |
|
---|
62 | Status = EFI_SUCCESS;
|
---|
63 | SetUtilityName ((CHAR8*) PROGRAM_NAME);
|
---|
64 |
|
---|
65 | mOptions.VfrFileName = NULL;
|
---|
66 | mOptions.RecordListFile = NULL;
|
---|
67 | mOptions.CreateRecordListFile = FALSE;
|
---|
68 | mOptions.CreateIfrPkgFile = FALSE;
|
---|
69 | mOptions.PkgOutputFileName = NULL;
|
---|
70 | mOptions.COutputFileName = NULL;
|
---|
71 | mOptions.OutputDirectory = NULL;
|
---|
72 | mOptions.PreprocessorOutputFileName = NULL;
|
---|
73 | mOptions.VfrBaseFileName = NULL;
|
---|
74 | mOptions.IncludePaths = NULL;
|
---|
75 | mOptions.SkipCPreprocessor = TRUE;
|
---|
76 | mOptions.CPreprocessorOptions = NULL;
|
---|
77 | mOptions.HasOverrideClassGuid = FALSE;
|
---|
78 | mOptions.WarningAsError = FALSE;
|
---|
79 | mOptions.AutoDefault = FALSE;
|
---|
80 | mOptions.CheckDefault = FALSE;
|
---|
81 | memset (&mOptions.OverrideClassGuid, 0, sizeof (EFI_GUID));
|
---|
82 |
|
---|
83 | if (Argc == 1) {
|
---|
84 | Usage ();
|
---|
85 | SET_RUN_STATUS (STATUS_DEAD);
|
---|
86 | return;
|
---|
87 | }
|
---|
88 |
|
---|
89 | for (Index = 1; (Index < Argc) && (Argv[Index][0] == '-'); Index++) {
|
---|
90 | if ((stricmp(Argv[Index], "-h") == 0) || (stricmp(Argv[Index], "--help") == 0)) {
|
---|
91 | Usage ();
|
---|
92 | SET_RUN_STATUS (STATUS_DEAD);
|
---|
93 | return;
|
---|
94 | } else if (stricmp(Argv[Index], "--version") == 0) {
|
---|
95 | Version ();
|
---|
96 | SET_RUN_STATUS (STATUS_DEAD);
|
---|
97 | return;
|
---|
98 | } else if (stricmp(Argv[Index], "-l") == 0) {
|
---|
99 | mOptions.CreateRecordListFile = TRUE;
|
---|
100 | gCIfrRecordInfoDB.TurnOn ();
|
---|
101 | } else if (stricmp(Argv[Index], "-i") == 0) {
|
---|
102 | Index++;
|
---|
103 | if ((Index >= Argc) || (Argv[Index][0] == '-')) {
|
---|
104 | DebugError (NULL, 0, 1001, "Missing option", "-i missing path argument");
|
---|
105 | goto Fail;
|
---|
106 | }
|
---|
107 |
|
---|
108 | AppendIncludePath(Argv[Index]);
|
---|
109 | } else if (stricmp(Argv[Index], "-o") == 0 || stricmp(Argv[Index], "--output-directory") == 0 || stricmp(Argv[Index], "-od") == 0) {
|
---|
110 | Index++;
|
---|
111 | if ((Index >= Argc) || (Argv[Index][0] == '-')) {
|
---|
112 | DebugError (NULL, 0, 1001, "Missing option", "-o missing output directory name");
|
---|
113 | goto Fail;
|
---|
114 | }
|
---|
115 |
|
---|
116 | mOptions.OutputDirectory = (CHAR8 *) malloc (strlen (Argv[Index]) + strlen ("\\") + 1);
|
---|
117 | if (mOptions.OutputDirectory == NULL) {
|
---|
118 | DebugError (NULL, 0, 4001, "Resource: memory can't be allocated", NULL);
|
---|
119 | goto Fail;
|
---|
120 | }
|
---|
121 | strcpy (mOptions.OutputDirectory, Argv[Index]);
|
---|
122 |
|
---|
123 | CHAR8 lastChar = mOptions.OutputDirectory[strlen(mOptions.OutputDirectory) - 1];
|
---|
124 | if ((lastChar != '/') && (lastChar != '\\')) {
|
---|
125 | if (strchr(mOptions.OutputDirectory, '/') != NULL) {
|
---|
126 | strcat (mOptions.OutputDirectory, "/");
|
---|
127 | } else {
|
---|
128 | strcat (mOptions.OutputDirectory, "\\");
|
---|
129 | }
|
---|
130 | }
|
---|
131 | DebugMsg (NULL, 0, 9, (CHAR8 *) "Output Directory", (CHAR8 *) "%s", mOptions.OutputDirectory);
|
---|
132 | } else if (stricmp(Argv[Index], "-b") == 0 || stricmp(Argv[Index], "--create-ifr-package") == 0 || stricmp(Argv[Index], "-ibin") == 0) {
|
---|
133 | mOptions.CreateIfrPkgFile = TRUE;
|
---|
134 | } else if (stricmp(Argv[Index], "-n") == 0 || stricmp(Argv[Index], "--no-pre-processing") == 0 || stricmp(Argv[Index], "-nopp") == 0) {
|
---|
135 | mOptions.SkipCPreprocessor = TRUE;
|
---|
136 | } else if (stricmp(Argv[Index], "-f") == 0 || stricmp(Argv[Index], "--pre-processing-flag") == 0 || stricmp(Argv[Index], "-ppflag") == 0) {
|
---|
137 | Index++;
|
---|
138 | if ((Index >= Argc) || (Argv[Index][0] == '-')) {
|
---|
139 | DebugError (NULL, 0, 1001, "Missing option", "-od - missing C-preprocessor argument");
|
---|
140 | goto Fail;
|
---|
141 | }
|
---|
142 |
|
---|
143 | AppendCPreprocessorOptions (Argv[Index]);
|
---|
144 | } else if (stricmp(Argv[Index], "-s") == 0|| stricmp(Argv[Index], "--string-db") == 0) {
|
---|
145 | Index++;
|
---|
146 | if ((Index >= Argc) || (Argv[Index][0] == '-')) {
|
---|
147 | DebugError (NULL, 0, 1001, "Missing option", "-s missing input string file name");
|
---|
148 | goto Fail;
|
---|
149 | }
|
---|
150 | gCVfrStringDB.SetStringFileName(Argv[Index]);
|
---|
151 | DebugMsg (NULL, 0, 9, (CHAR8 *) "Input string file path", (CHAR8 *) "%s", Argv[Index]);
|
---|
152 | } else if ((stricmp (Argv[Index], "-g") == 0) || (stricmp (Argv[Index], "--guid") == 0)) {
|
---|
153 | Index++;
|
---|
154 | Status = StringToGuid (Argv[Index], &mOptions.OverrideClassGuid);
|
---|
155 | if (EFI_ERROR (Status)) {
|
---|
156 | DebugError (NULL, 0, 1000, "Invalid format:", "%s", Argv[Index]);
|
---|
157 | goto Fail;
|
---|
158 | }
|
---|
159 | mOptions.HasOverrideClassGuid = TRUE;
|
---|
160 | } else if (stricmp(Argv[Index], "-w") == 0 || stricmp(Argv[Index], "--warning-as-error") == 0) {
|
---|
161 | mOptions.WarningAsError = TRUE;
|
---|
162 | } else if (stricmp(Argv[Index], "-a") == 0 ||stricmp(Argv[Index], "--autodefault") == 0) {
|
---|
163 | mOptions.AutoDefault = TRUE;
|
---|
164 | } else if (stricmp(Argv[Index], "-d") == 0 ||stricmp(Argv[Index], "--checkdefault") == 0) {
|
---|
165 | mOptions.CheckDefault = TRUE;
|
---|
166 | } else {
|
---|
167 | DebugError (NULL, 0, 1000, "Unknown option", "unrecognized option %s", Argv[Index]);
|
---|
168 | goto Fail;
|
---|
169 | }
|
---|
170 | }
|
---|
171 |
|
---|
172 | if (Index != Argc - 1) {
|
---|
173 | DebugError (NULL, 0, 1001, "Missing option", "VFR file name is not specified.");
|
---|
174 | goto Fail;
|
---|
175 | } else {
|
---|
176 | mOptions.VfrFileName = (CHAR8 *) malloc (strlen (Argv[Index]) + 1);
|
---|
177 | if (mOptions.VfrFileName == NULL) {
|
---|
178 | DebugError (NULL, 0, 4001, "Resource: memory can't be allocated", NULL);
|
---|
179 | goto Fail;
|
---|
180 | }
|
---|
181 | strcpy (mOptions.VfrFileName, Argv[Index]);
|
---|
182 |
|
---|
183 | if (mOptions.OutputDirectory == NULL) {
|
---|
184 | mOptions.OutputDirectory = (CHAR8 *) malloc (1);
|
---|
185 | if (mOptions.OutputDirectory == NULL) {
|
---|
186 | DebugError (NULL, 0, 4001, "Resource: memory can't be allocated", NULL);
|
---|
187 | goto Fail;
|
---|
188 | }
|
---|
189 | mOptions.OutputDirectory[0] = '\0';
|
---|
190 | }
|
---|
191 | }
|
---|
192 |
|
---|
193 | if (SetBaseFileName() != 0) {
|
---|
194 | goto Fail;
|
---|
195 | }
|
---|
196 | if (SetPkgOutputFileName () != 0) {
|
---|
197 | goto Fail;
|
---|
198 | }
|
---|
199 | if (SetCOutputFileName() != 0) {
|
---|
200 | goto Fail;
|
---|
201 | }
|
---|
202 | if (SetPreprocessorOutputFileName () != 0) {
|
---|
203 | goto Fail;
|
---|
204 | }
|
---|
205 | if (SetRecordListFileName () != 0) {
|
---|
206 | goto Fail;
|
---|
207 | }
|
---|
208 | return;
|
---|
209 |
|
---|
210 | Fail:
|
---|
211 | SET_RUN_STATUS (STATUS_DEAD);
|
---|
212 |
|
---|
213 | mOptions.CreateRecordListFile = FALSE;
|
---|
214 | mOptions.CreateIfrPkgFile = FALSE;
|
---|
215 |
|
---|
216 | if (mOptions.VfrFileName != NULL) {
|
---|
217 | free (mOptions.VfrFileName);
|
---|
218 | mOptions.VfrFileName = NULL;
|
---|
219 | }
|
---|
220 | if (mOptions.VfrBaseFileName != NULL) {
|
---|
221 | free (mOptions.VfrBaseFileName);
|
---|
222 | mOptions.VfrBaseFileName = NULL;
|
---|
223 | }
|
---|
224 | if (mOptions.OutputDirectory != NULL) {
|
---|
225 | free (mOptions.OutputDirectory);
|
---|
226 | mOptions.OutputDirectory = NULL;
|
---|
227 | }
|
---|
228 | if (mOptions.PkgOutputFileName != NULL) {
|
---|
229 | free (mOptions.PkgOutputFileName);
|
---|
230 | mOptions.PkgOutputFileName = NULL;
|
---|
231 | }
|
---|
232 | if (mOptions.COutputFileName != NULL) {
|
---|
233 | free (mOptions.COutputFileName);
|
---|
234 | mOptions.COutputFileName = NULL;
|
---|
235 | }
|
---|
236 | if (mOptions.PreprocessorOutputFileName != NULL) {
|
---|
237 | free (mOptions.PreprocessorOutputFileName);
|
---|
238 | mOptions.PreprocessorOutputFileName = NULL;
|
---|
239 | }
|
---|
240 | if (mOptions.RecordListFile != NULL) {
|
---|
241 | free (mOptions.RecordListFile);
|
---|
242 | mOptions.RecordListFile = NULL;
|
---|
243 | }
|
---|
244 | if (mOptions.IncludePaths != NULL) {
|
---|
245 | delete mOptions.IncludePaths;
|
---|
246 | mOptions.IncludePaths = NULL;
|
---|
247 | }
|
---|
248 | if (mOptions.CPreprocessorOptions != NULL) {
|
---|
249 | delete mOptions.CPreprocessorOptions;
|
---|
250 | mOptions.CPreprocessorOptions = NULL;
|
---|
251 | }
|
---|
252 | }
|
---|
253 |
|
---|
254 | VOID
|
---|
255 | CVfrCompiler::AppendIncludePath (
|
---|
256 | IN CHAR8 *PathStr
|
---|
257 | )
|
---|
258 | {
|
---|
259 | UINT32 Len = 0;
|
---|
260 | CHAR8 *IncludePaths = NULL;
|
---|
261 |
|
---|
262 | Len = strlen (" -I ") + strlen (PathStr) + 1;
|
---|
263 | if (mOptions.IncludePaths != NULL) {
|
---|
264 | Len += strlen (mOptions.IncludePaths);
|
---|
265 | }
|
---|
266 | IncludePaths = new CHAR8[Len];
|
---|
267 | if (IncludePaths == NULL) {
|
---|
268 | DebugError (NULL, 0, 4001, "Resource: memory can't be allocated", NULL);
|
---|
269 | return;
|
---|
270 | }
|
---|
271 | IncludePaths[0] = '\0';
|
---|
272 | if (mOptions.IncludePaths != NULL) {
|
---|
273 | strcat (IncludePaths, mOptions.IncludePaths);
|
---|
274 | }
|
---|
275 | strcat (IncludePaths, " -I ");
|
---|
276 | strcat (IncludePaths, PathStr);
|
---|
277 | if (mOptions.IncludePaths != NULL) {
|
---|
278 | delete[] mOptions.IncludePaths;
|
---|
279 | }
|
---|
280 | mOptions.IncludePaths = IncludePaths;
|
---|
281 | }
|
---|
282 |
|
---|
283 | VOID
|
---|
284 | CVfrCompiler::AppendCPreprocessorOptions (
|
---|
285 | IN CHAR8 *Options
|
---|
286 | )
|
---|
287 | {
|
---|
288 | UINT32 Len = 0;
|
---|
289 | CHAR8 *Opt = NULL;
|
---|
290 |
|
---|
291 | Len = strlen (Options) + strlen (" ") + 1;
|
---|
292 | if (mOptions.CPreprocessorOptions != NULL) {
|
---|
293 | Len += strlen (mOptions.CPreprocessorOptions);
|
---|
294 | }
|
---|
295 | Opt = new CHAR8[Len];
|
---|
296 | if (Opt == NULL) {
|
---|
297 | DebugError (NULL, 0, 4001, "Resource: memory can't be allocated", NULL);
|
---|
298 | return;
|
---|
299 | }
|
---|
300 | Opt[0] = 0;
|
---|
301 | if (mOptions.CPreprocessorOptions != NULL) {
|
---|
302 | strcat (Opt, mOptions.CPreprocessorOptions);
|
---|
303 | }
|
---|
304 | strcat (Opt, " ");
|
---|
305 | strcat (Opt, Options);
|
---|
306 | if (mOptions.CPreprocessorOptions != NULL) {
|
---|
307 | delete[] mOptions.CPreprocessorOptions;
|
---|
308 | }
|
---|
309 | mOptions.CPreprocessorOptions = Opt;
|
---|
310 | }
|
---|
311 |
|
---|
312 | INT8
|
---|
313 | CVfrCompiler::SetBaseFileName (
|
---|
314 | VOID
|
---|
315 | )
|
---|
316 | {
|
---|
317 | CHAR8 *pFileName, *pPath, *pExt;
|
---|
318 |
|
---|
319 | if (mOptions.VfrFileName == NULL) {
|
---|
320 | return -1;
|
---|
321 | }
|
---|
322 |
|
---|
323 | pFileName = mOptions.VfrFileName;
|
---|
324 | while (
|
---|
325 | ((pPath = strchr (pFileName, '\\')) != NULL) ||
|
---|
326 | ((pPath = strchr (pFileName, '/')) != NULL)
|
---|
327 | )
|
---|
328 | {
|
---|
329 | pFileName = pPath + 1;
|
---|
330 | }
|
---|
331 |
|
---|
332 | if (pFileName == NULL) {
|
---|
333 | return -1;
|
---|
334 | }
|
---|
335 |
|
---|
336 | if ((pExt = strchr (pFileName, '.')) == NULL) {
|
---|
337 | return -1;
|
---|
338 | }
|
---|
339 |
|
---|
340 | *pExt = '\0';
|
---|
341 |
|
---|
342 | mOptions.VfrBaseFileName = (CHAR8 *) malloc (strlen (pFileName) + 1);
|
---|
343 | if (mOptions.VfrBaseFileName == NULL) {
|
---|
344 | *pExt = '.';
|
---|
345 | return -1;
|
---|
346 | }
|
---|
347 |
|
---|
348 | strcpy (mOptions.VfrBaseFileName, pFileName);
|
---|
349 | *pExt = '.';
|
---|
350 |
|
---|
351 | return 0;
|
---|
352 | }
|
---|
353 |
|
---|
354 | INT8
|
---|
355 | CVfrCompiler::SetPkgOutputFileName (
|
---|
356 | VOID
|
---|
357 | )
|
---|
358 | {
|
---|
359 | INTN Length;
|
---|
360 |
|
---|
361 | if (mOptions.VfrBaseFileName == NULL) {
|
---|
362 | return -1;
|
---|
363 | }
|
---|
364 |
|
---|
365 | Length = strlen (mOptions.OutputDirectory) +
|
---|
366 | strlen (mOptions.VfrBaseFileName) +
|
---|
367 | strlen (VFR_PACKAGE_FILENAME_EXTENSION) +
|
---|
368 | 1;
|
---|
369 |
|
---|
370 | mOptions.PkgOutputFileName = (CHAR8 *) malloc (Length);
|
---|
371 | if (mOptions.PkgOutputFileName == NULL) {
|
---|
372 | return -1;
|
---|
373 | }
|
---|
374 |
|
---|
375 | strcpy (mOptions.PkgOutputFileName, mOptions.OutputDirectory);
|
---|
376 | strcat (mOptions.PkgOutputFileName, mOptions.VfrBaseFileName);
|
---|
377 | strcat (mOptions.PkgOutputFileName, VFR_PACKAGE_FILENAME_EXTENSION);
|
---|
378 |
|
---|
379 | return 0;
|
---|
380 | }
|
---|
381 |
|
---|
382 | INT8
|
---|
383 | CVfrCompiler::SetCOutputFileName (
|
---|
384 | VOID
|
---|
385 | )
|
---|
386 | {
|
---|
387 | INTN Length;
|
---|
388 |
|
---|
389 | if (mOptions.VfrBaseFileName == NULL) {
|
---|
390 | return -1;
|
---|
391 | }
|
---|
392 |
|
---|
393 | Length = strlen (mOptions.OutputDirectory) +
|
---|
394 | strlen (mOptions.VfrBaseFileName) +
|
---|
395 | strlen (".c") +
|
---|
396 | 1;
|
---|
397 |
|
---|
398 | mOptions.COutputFileName = (CHAR8 *) malloc (Length);
|
---|
399 | if (mOptions.COutputFileName == NULL) {
|
---|
400 | return -1;
|
---|
401 | }
|
---|
402 |
|
---|
403 | strcpy (mOptions.COutputFileName, mOptions.OutputDirectory);
|
---|
404 | strcat (mOptions.COutputFileName, mOptions.VfrBaseFileName);
|
---|
405 | strcat (mOptions.COutputFileName, ".c");
|
---|
406 |
|
---|
407 | return 0;
|
---|
408 | }
|
---|
409 |
|
---|
410 | INT8
|
---|
411 | CVfrCompiler::SetPreprocessorOutputFileName (
|
---|
412 | VOID
|
---|
413 | )
|
---|
414 | {
|
---|
415 | INTN Length;
|
---|
416 |
|
---|
417 | if (mOptions.VfrBaseFileName == NULL) {
|
---|
418 | return -1;
|
---|
419 | }
|
---|
420 |
|
---|
421 | Length = strlen (mOptions.OutputDirectory) +
|
---|
422 | strlen (mOptions.VfrBaseFileName) +
|
---|
423 | strlen (VFR_PREPROCESS_FILENAME_EXTENSION) +
|
---|
424 | 1;
|
---|
425 |
|
---|
426 | mOptions.PreprocessorOutputFileName = (CHAR8 *) malloc (Length);
|
---|
427 | if (mOptions.PreprocessorOutputFileName == NULL) {
|
---|
428 | return -1;
|
---|
429 | }
|
---|
430 |
|
---|
431 | strcpy (mOptions.PreprocessorOutputFileName, mOptions.OutputDirectory);
|
---|
432 | strcat (mOptions.PreprocessorOutputFileName, mOptions.VfrBaseFileName);
|
---|
433 | strcat (mOptions.PreprocessorOutputFileName, VFR_PREPROCESS_FILENAME_EXTENSION);
|
---|
434 |
|
---|
435 | return 0;
|
---|
436 | }
|
---|
437 |
|
---|
438 | INT8
|
---|
439 | CVfrCompiler::SetRecordListFileName (
|
---|
440 | VOID
|
---|
441 | )
|
---|
442 | {
|
---|
443 | INTN Length;
|
---|
444 |
|
---|
445 | if (mOptions.VfrBaseFileName == NULL) {
|
---|
446 | return -1;
|
---|
447 | }
|
---|
448 |
|
---|
449 | Length = strlen (mOptions.OutputDirectory) +
|
---|
450 | strlen (mOptions.VfrBaseFileName) +
|
---|
451 | strlen (VFR_RECORDLIST_FILENAME_EXTENSION) +
|
---|
452 | 1;
|
---|
453 |
|
---|
454 | mOptions.RecordListFile = (CHAR8 *) malloc (Length);
|
---|
455 | if (mOptions.RecordListFile == NULL) {
|
---|
456 | return -1;
|
---|
457 | }
|
---|
458 |
|
---|
459 | strcpy (mOptions.RecordListFile, mOptions.OutputDirectory);
|
---|
460 | strcat (mOptions.RecordListFile, mOptions.VfrBaseFileName);
|
---|
461 | strcat (mOptions.RecordListFile, VFR_RECORDLIST_FILENAME_EXTENSION);
|
---|
462 |
|
---|
463 | return 0;
|
---|
464 | }
|
---|
465 |
|
---|
466 | CVfrCompiler::CVfrCompiler (
|
---|
467 | IN INT32 Argc,
|
---|
468 | IN CHAR8 **Argv
|
---|
469 | )
|
---|
470 | {
|
---|
471 | mPreProcessCmd = (CHAR8 *) PREPROCESSOR_COMMAND;
|
---|
472 | mPreProcessOpt = (CHAR8 *) PREPROCESSOR_OPTIONS;
|
---|
473 |
|
---|
474 | SET_RUN_STATUS (STATUS_STARTED);
|
---|
475 |
|
---|
476 | OptionInitialization(Argc, Argv);
|
---|
477 |
|
---|
478 | if ((IS_RUN_STATUS(STATUS_FAILED)) || (IS_RUN_STATUS(STATUS_DEAD))) {
|
---|
479 | return;
|
---|
480 | }
|
---|
481 |
|
---|
482 | SET_RUN_STATUS(STATUS_INITIALIZED);
|
---|
483 | }
|
---|
484 |
|
---|
485 | CVfrCompiler::~CVfrCompiler (
|
---|
486 | VOID
|
---|
487 | )
|
---|
488 | {
|
---|
489 | if (mOptions.VfrFileName != NULL) {
|
---|
490 | free (mOptions.VfrFileName);
|
---|
491 | mOptions.VfrFileName = NULL;
|
---|
492 | }
|
---|
493 |
|
---|
494 | if (mOptions.VfrBaseFileName != NULL) {
|
---|
495 | free (mOptions.VfrBaseFileName);
|
---|
496 | mOptions.VfrBaseFileName = NULL;
|
---|
497 | }
|
---|
498 |
|
---|
499 | if (mOptions.OutputDirectory != NULL) {
|
---|
500 | free (mOptions.OutputDirectory);
|
---|
501 | mOptions.OutputDirectory = NULL;
|
---|
502 | }
|
---|
503 |
|
---|
504 | if (mOptions.PkgOutputFileName != NULL) {
|
---|
505 | free (mOptions.PkgOutputFileName);
|
---|
506 | mOptions.PkgOutputFileName = NULL;
|
---|
507 | }
|
---|
508 |
|
---|
509 | if (mOptions.COutputFileName != NULL) {
|
---|
510 | free (mOptions.COutputFileName);
|
---|
511 | mOptions.COutputFileName = NULL;
|
---|
512 | }
|
---|
513 |
|
---|
514 | if (mOptions.PreprocessorOutputFileName != NULL) {
|
---|
515 | free (mOptions.PreprocessorOutputFileName);
|
---|
516 | mOptions.PreprocessorOutputFileName = NULL;
|
---|
517 | }
|
---|
518 |
|
---|
519 | if (mOptions.RecordListFile != NULL) {
|
---|
520 | free (mOptions.RecordListFile);
|
---|
521 | mOptions.RecordListFile = NULL;
|
---|
522 | }
|
---|
523 |
|
---|
524 | if (mOptions.IncludePaths != NULL) {
|
---|
525 | delete[] mOptions.IncludePaths;
|
---|
526 | mOptions.IncludePaths = NULL;
|
---|
527 | }
|
---|
528 |
|
---|
529 | if (mOptions.CPreprocessorOptions != NULL) {
|
---|
530 | delete[] mOptions.CPreprocessorOptions;
|
---|
531 | mOptions.CPreprocessorOptions = NULL;
|
---|
532 | }
|
---|
533 |
|
---|
534 | SET_RUN_STATUS(STATUS_DEAD);
|
---|
535 | }
|
---|
536 |
|
---|
537 | VOID
|
---|
538 | CVfrCompiler::Usage (
|
---|
539 | VOID
|
---|
540 | )
|
---|
541 | {
|
---|
542 | UINT32 Index;
|
---|
543 | CONST CHAR8 *Help[] = {
|
---|
544 | " ",
|
---|
545 | "VfrCompile version " VFR_COMPILER_VERSION "Build " __BUILD_VERSION,
|
---|
546 | "Copyright (c) 2004-2016 Intel Corporation. All rights reserved.",
|
---|
547 | " ",
|
---|
548 | "Usage: VfrCompile [options] VfrFile",
|
---|
549 | " ",
|
---|
550 | "Options:",
|
---|
551 | " -h, --help prints this help",
|
---|
552 | " --version prints version info",
|
---|
553 | " -l create an output IFR listing file",
|
---|
554 | " -o DIR, --output-directory DIR",
|
---|
555 | " deposit all output files to directory OutputDir",
|
---|
556 | " default is current directory",
|
---|
557 | " -b, --create-ifr-package",
|
---|
558 | " create an IFR HII pack file",
|
---|
559 | " -n, --no-pre-processing",
|
---|
560 | " do not preprocessing input file",
|
---|
561 | " -s, --string-db",
|
---|
562 | " input uni string package file",
|
---|
563 | " -g, --guid",
|
---|
564 | " override class guid input",
|
---|
565 | " format is xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx",
|
---|
566 | " -w --warning-as-error",
|
---|
567 | " treat warning as an error",
|
---|
568 | " -a --autodefaut generate default value for question opcode if some default is missing",
|
---|
569 | " -d --checkdefault check the default information in a question opcode",
|
---|
570 | NULL
|
---|
571 | };
|
---|
572 | for (Index = 0; Help[Index] != NULL; Index++) {
|
---|
573 | fprintf (stdout, "%s\n", Help[Index]);
|
---|
574 | }
|
---|
575 | }
|
---|
576 |
|
---|
577 | VOID
|
---|
578 | CVfrCompiler::Version (
|
---|
579 | VOID
|
---|
580 | )
|
---|
581 | {
|
---|
582 | UINT32 Index;
|
---|
583 | CONST CHAR8 *Help[] = {
|
---|
584 | "VfrCompile version " VFR_COMPILER_VERSION "Build " __BUILD_VERSION,
|
---|
585 | NULL
|
---|
586 | };
|
---|
587 | for (Index = 0; Help[Index] != NULL; Index++) {
|
---|
588 | fprintf (stdout, "%s\n", Help[Index]);
|
---|
589 | }
|
---|
590 | }
|
---|
591 |
|
---|
592 | VOID
|
---|
593 | CVfrCompiler::PreProcess (
|
---|
594 | VOID
|
---|
595 | )
|
---|
596 | {
|
---|
597 | FILE *pVfrFile = NULL;
|
---|
598 | UINT32 CmdLen = 0;
|
---|
599 | CHAR8 *PreProcessCmd = NULL;
|
---|
600 |
|
---|
601 | if (!IS_RUN_STATUS(STATUS_INITIALIZED)) {
|
---|
602 | goto Fail;
|
---|
603 | }
|
---|
604 |
|
---|
605 | if (mOptions.SkipCPreprocessor == TRUE) {
|
---|
606 | goto Out;
|
---|
607 | }
|
---|
608 |
|
---|
609 | if ((pVfrFile = fopen (LongFilePath (mOptions.VfrFileName), "r")) == NULL) {
|
---|
610 | DebugError (NULL, 0, 0001, "Error opening the input VFR file", "%s", mOptions.VfrFileName);
|
---|
611 | goto Fail;
|
---|
612 | }
|
---|
613 | fclose (pVfrFile);
|
---|
614 |
|
---|
615 | CmdLen = strlen (mPreProcessCmd) + strlen (mPreProcessOpt) +
|
---|
616 | strlen (mOptions.VfrFileName) + strlen (mOptions.PreprocessorOutputFileName);
|
---|
617 | if (mOptions.CPreprocessorOptions != NULL) {
|
---|
618 | CmdLen += strlen (mOptions.CPreprocessorOptions);
|
---|
619 | }
|
---|
620 | if (mOptions.IncludePaths != NULL) {
|
---|
621 | CmdLen += strlen (mOptions.IncludePaths);
|
---|
622 | }
|
---|
623 |
|
---|
624 | PreProcessCmd = new CHAR8[CmdLen + 10];
|
---|
625 | if (PreProcessCmd == NULL) {
|
---|
626 | DebugError (NULL, 0, 4001, "Resource: memory can't be allocated", NULL);
|
---|
627 | goto Fail;
|
---|
628 | }
|
---|
629 | strcpy (PreProcessCmd, mPreProcessCmd), strcat (PreProcessCmd, " ");
|
---|
630 | strcat (PreProcessCmd, mPreProcessOpt), strcat (PreProcessCmd, " ");
|
---|
631 | if (mOptions.IncludePaths != NULL) {
|
---|
632 | strcat (PreProcessCmd, mOptions.IncludePaths), strcat (PreProcessCmd, " ");
|
---|
633 | }
|
---|
634 | if (mOptions.CPreprocessorOptions != NULL) {
|
---|
635 | strcat (PreProcessCmd, mOptions.CPreprocessorOptions), strcat (PreProcessCmd, " ");
|
---|
636 | }
|
---|
637 | strcat (PreProcessCmd, mOptions.VfrFileName), strcat (PreProcessCmd, " > ");
|
---|
638 | strcat (PreProcessCmd, mOptions.PreprocessorOutputFileName);
|
---|
639 |
|
---|
640 | if (system (PreProcessCmd) != 0) {
|
---|
641 | DebugError (NULL, 0, 0003, "Error parsing file", "failed to spawn C preprocessor on VFR file %s\n", PreProcessCmd);
|
---|
642 | goto Fail;
|
---|
643 | }
|
---|
644 |
|
---|
645 | delete[] PreProcessCmd;
|
---|
646 |
|
---|
647 | Out:
|
---|
648 | SET_RUN_STATUS (STATUS_PREPROCESSED);
|
---|
649 | return;
|
---|
650 |
|
---|
651 | Fail:
|
---|
652 | if (!IS_RUN_STATUS(STATUS_DEAD)) {
|
---|
653 | SET_RUN_STATUS (STATUS_FAILED);
|
---|
654 | }
|
---|
655 | delete[] PreProcessCmd;
|
---|
656 | }
|
---|
657 |
|
---|
658 | extern UINT8 VfrParserStart (IN FILE *, IN INPUT_INFO_TO_SYNTAX *);
|
---|
659 |
|
---|
660 | VOID
|
---|
661 | CVfrCompiler::Compile (
|
---|
662 | VOID
|
---|
663 | )
|
---|
664 | {
|
---|
665 | FILE *pInFile = NULL;
|
---|
666 | CHAR8 *InFileName = NULL;
|
---|
667 | INPUT_INFO_TO_SYNTAX InputInfo;
|
---|
668 |
|
---|
669 | if (!IS_RUN_STATUS(STATUS_PREPROCESSED)) {
|
---|
670 | goto Fail;
|
---|
671 | }
|
---|
672 |
|
---|
673 | InFileName = (mOptions.SkipCPreprocessor == TRUE) ? mOptions.VfrFileName : mOptions.PreprocessorOutputFileName;
|
---|
674 |
|
---|
675 | gCVfrErrorHandle.SetInputFile (InFileName);
|
---|
676 | gCVfrErrorHandle.SetWarningAsError(mOptions.WarningAsError);
|
---|
677 |
|
---|
678 | if ((pInFile = fopen (LongFilePath (InFileName), "r")) == NULL) {
|
---|
679 | DebugError (NULL, 0, 0001, "Error opening the input file", "%s", InFileName);
|
---|
680 | goto Fail;
|
---|
681 | }
|
---|
682 |
|
---|
683 | if (mOptions.HasOverrideClassGuid) {
|
---|
684 | InputInfo.OverrideClassGuid = &mOptions.OverrideClassGuid;
|
---|
685 | } else {
|
---|
686 | InputInfo.OverrideClassGuid = NULL;
|
---|
687 | }
|
---|
688 |
|
---|
689 | if (VfrParserStart (pInFile, &InputInfo) != 0) {
|
---|
690 | goto Fail;
|
---|
691 | }
|
---|
692 |
|
---|
693 | fclose (pInFile);
|
---|
694 | pInFile = NULL;
|
---|
695 |
|
---|
696 | if (gCFormPkg.HavePendingUnassigned () == TRUE) {
|
---|
697 | gCFormPkg.PendingAssignPrintAll ();
|
---|
698 | goto Fail;
|
---|
699 | }
|
---|
700 |
|
---|
701 | SET_RUN_STATUS (STATUS_COMPILEED);
|
---|
702 | return;
|
---|
703 |
|
---|
704 | Fail:
|
---|
705 | if (!IS_RUN_STATUS(STATUS_DEAD)) {
|
---|
706 | DebugError (NULL, 0, 0003, "Error parsing", "compile error in file %s", InFileName);
|
---|
707 | SET_RUN_STATUS (STATUS_FAILED);
|
---|
708 | }
|
---|
709 | if (pInFile != NULL) {
|
---|
710 | fclose (pInFile);
|
---|
711 | }
|
---|
712 | }
|
---|
713 |
|
---|
714 | VOID
|
---|
715 | CVfrCompiler::AdjustBin (
|
---|
716 | VOID
|
---|
717 | )
|
---|
718 | {
|
---|
719 | EFI_VFR_RETURN_CODE Status;
|
---|
720 |
|
---|
721 | if (!IS_RUN_STATUS(STATUS_COMPILEED)) {
|
---|
722 | return;
|
---|
723 | }
|
---|
724 |
|
---|
725 | if (gNeedAdjustOpcode) {
|
---|
726 | //
|
---|
727 | // When parsing the Vfr, has created some opcodes, now need to update the record info.
|
---|
728 | //
|
---|
729 | gCIfrRecordInfoDB.IfrUpdateRecordInfoForDynamicOpcode (FALSE);
|
---|
730 | }
|
---|
731 |
|
---|
732 | //
|
---|
733 | // Check whether need to check default info for question or auto add default for question.
|
---|
734 | //
|
---|
735 | if (mOptions.AutoDefault || mOptions.CheckDefault) {
|
---|
736 | gCIfrRecordInfoDB.IfrCheckAddDefaultRecord (mOptions.AutoDefault, mOptions.CheckDefault);
|
---|
737 | }
|
---|
738 |
|
---|
739 | //
|
---|
740 | // Check Binary Code consistent between Form and IfrRecord
|
---|
741 | //
|
---|
742 |
|
---|
743 | //
|
---|
744 | // Get Package Data and IfrRecord Data
|
---|
745 | //
|
---|
746 | gCFormPkg.BuildPkg (gCBuffer);
|
---|
747 | gCIfrRecordInfoDB.IfrRecordOutput (gRBuffer);
|
---|
748 |
|
---|
749 | //
|
---|
750 | // Compare Form and Record data
|
---|
751 | //
|
---|
752 | if (gCBuffer.Buffer != NULL && gRBuffer.Buffer != NULL) {
|
---|
753 | UINT32 Index;
|
---|
754 | if (gCBuffer.Size != gRBuffer.Size) {
|
---|
755 | DebugError (NULL, 0, 0001, "Error parsing vfr file", " %s. FormBinary Size 0x%X is not same to RecordBuffer Size 0x%X", mOptions.VfrFileName, gCBuffer.Size, gRBuffer.Size);
|
---|
756 | }
|
---|
757 | for (Index = 0; Index < gCBuffer.Size; Index ++) {
|
---|
758 | if (gCBuffer.Buffer[Index] != gRBuffer.Buffer[Index]) {
|
---|
759 | break;
|
---|
760 | }
|
---|
761 | }
|
---|
762 | if (Index != gCBuffer.Size) {
|
---|
763 | DebugError (NULL, 0, 0001, "Error parsing vfr file", " %s. the 0x%X byte is different between Form and Record", mOptions.VfrFileName, Index);
|
---|
764 | }
|
---|
765 | DebugMsg (NULL, 0, 9, (CHAR8 *) "IFR Buffer", (CHAR8 *) "Form Buffer same to Record Buffer and Size is 0x%X", Index);
|
---|
766 | } else if (gCBuffer.Buffer == NULL && gRBuffer.Buffer == NULL) {
|
---|
767 | //ok
|
---|
768 | } else {
|
---|
769 | DebugError (NULL, 0, 0001, "Error parsing vfr file", " %s.Buffer not allocated.", mOptions.VfrFileName);
|
---|
770 | }
|
---|
771 |
|
---|
772 | return;
|
---|
773 | }
|
---|
774 |
|
---|
775 | VOID
|
---|
776 | CVfrCompiler::GenBinary (
|
---|
777 | VOID
|
---|
778 | )
|
---|
779 | {
|
---|
780 | FILE *pFile = NULL;
|
---|
781 |
|
---|
782 | if (!IS_RUN_STATUS(STATUS_COMPILEED)) {
|
---|
783 | goto Fail;
|
---|
784 | }
|
---|
785 |
|
---|
786 | if (mOptions.CreateIfrPkgFile == TRUE) {
|
---|
787 | if ((pFile = fopen (LongFilePath (mOptions.PkgOutputFileName), "wb")) == NULL) {
|
---|
788 | DebugError (NULL, 0, 0001, "Error opening file", "%s", mOptions.PkgOutputFileName);
|
---|
789 | goto Fail;
|
---|
790 | }
|
---|
791 | if (gCFormPkg.BuildPkg (pFile, &gRBuffer) != VFR_RETURN_SUCCESS) {
|
---|
792 | fclose (pFile);
|
---|
793 | goto Fail;
|
---|
794 | }
|
---|
795 | fclose (pFile);
|
---|
796 | }
|
---|
797 |
|
---|
798 | SET_RUN_STATUS (STATUS_GENBINARY);
|
---|
799 |
|
---|
800 | return;
|
---|
801 |
|
---|
802 | Fail:
|
---|
803 | if (!IS_RUN_STATUS(STATUS_DEAD)) {
|
---|
804 | SET_RUN_STATUS (STATUS_FAILED);
|
---|
805 | }
|
---|
806 | }
|
---|
807 |
|
---|
808 | static const char *gSourceFileHeader[] = {
|
---|
809 | "//",
|
---|
810 | "// DO NOT EDIT -- auto-generated file",
|
---|
811 | "//",
|
---|
812 | "// This file is generated by the vfrcompiler utility",
|
---|
813 | "//",
|
---|
814 | NULL
|
---|
815 | };
|
---|
816 |
|
---|
817 | VOID
|
---|
818 | CVfrCompiler::GenCFile (
|
---|
819 | VOID
|
---|
820 | )
|
---|
821 | {
|
---|
822 | FILE *pFile;
|
---|
823 | UINT32 Index;
|
---|
824 |
|
---|
825 | if (!IS_RUN_STATUS(STATUS_GENBINARY)) {
|
---|
826 | goto Fail;
|
---|
827 | }
|
---|
828 |
|
---|
829 | if (!mOptions.CreateIfrPkgFile) {
|
---|
830 | if ((pFile = fopen (LongFilePath (mOptions.COutputFileName), "w")) == NULL) {
|
---|
831 | DebugError (NULL, 0, 0001, "Error opening output C file", "%s", mOptions.COutputFileName);
|
---|
832 | goto Fail;
|
---|
833 | }
|
---|
834 |
|
---|
835 | for (Index = 0; gSourceFileHeader[Index] != NULL; Index++) {
|
---|
836 | fprintf (pFile, "%s\n", gSourceFileHeader[Index]);
|
---|
837 | }
|
---|
838 |
|
---|
839 | if (gCFormPkg.GenCFile (mOptions.VfrBaseFileName, pFile, &gRBuffer) != VFR_RETURN_SUCCESS) {
|
---|
840 | fclose (pFile);
|
---|
841 | goto Fail;
|
---|
842 | }
|
---|
843 | fclose (pFile);
|
---|
844 | }
|
---|
845 |
|
---|
846 | SET_RUN_STATUS (STATUS_FINISHED);
|
---|
847 | return;
|
---|
848 |
|
---|
849 | Fail:
|
---|
850 | if (!IS_RUN_STATUS(STATUS_DEAD)) {
|
---|
851 | SET_RUN_STATUS (STATUS_FAILED);
|
---|
852 | }
|
---|
853 | }
|
---|
854 |
|
---|
855 | VOID
|
---|
856 | CVfrCompiler::GenRecordListFile (
|
---|
857 | VOID
|
---|
858 | )
|
---|
859 | {
|
---|
860 | CHAR8 *InFileName = NULL;
|
---|
861 | FILE *pInFile = NULL;
|
---|
862 | FILE *pOutFile = NULL;
|
---|
863 | CHAR8 LineBuf[MAX_VFR_LINE_LEN];
|
---|
864 | UINT32 LineNo;
|
---|
865 |
|
---|
866 | InFileName = (mOptions.SkipCPreprocessor == TRUE) ? mOptions.VfrFileName : mOptions.PreprocessorOutputFileName;
|
---|
867 |
|
---|
868 | if (mOptions.CreateRecordListFile == TRUE && InFileName != NULL && mOptions.RecordListFile != NULL) {
|
---|
869 | if ((InFileName[0] == '\0') || (mOptions.RecordListFile[0] == '\0')) {
|
---|
870 | return;
|
---|
871 | }
|
---|
872 |
|
---|
873 | if ((pInFile = fopen (LongFilePath (InFileName), "r")) == NULL) {
|
---|
874 | DebugError (NULL, 0, 0001, "Error opening the input VFR preprocessor output file", "%s", InFileName);
|
---|
875 | return;
|
---|
876 | }
|
---|
877 |
|
---|
878 | if ((pOutFile = fopen (LongFilePath (mOptions.RecordListFile), "w")) == NULL) {
|
---|
879 | DebugError (NULL, 0, 0001, "Error opening the record list file", "%s", mOptions.RecordListFile);
|
---|
880 | goto Err1;
|
---|
881 | }
|
---|
882 |
|
---|
883 | fprintf (pOutFile, "//\n// VFR compiler version " VFR_COMPILER_VERSION __BUILD_VERSION "\n//\n");
|
---|
884 | LineNo = 0;
|
---|
885 | while (!feof (pInFile)) {
|
---|
886 | if (fgets (LineBuf, MAX_VFR_LINE_LEN, pInFile) != NULL) {
|
---|
887 | fprintf (pOutFile, "%s", LineBuf);
|
---|
888 | LineNo++;
|
---|
889 | gCIfrRecordInfoDB.IfrRecordOutput (pOutFile, LineNo);
|
---|
890 | }
|
---|
891 | }
|
---|
892 |
|
---|
893 | fprintf (pOutFile, "\n//\n// All Opcode Record List \n//\n");
|
---|
894 | gCIfrRecordInfoDB.IfrRecordOutput (pOutFile, 0);
|
---|
895 | gCVfrVarDataTypeDB.Dump(pOutFile);
|
---|
896 |
|
---|
897 | fclose (pOutFile);
|
---|
898 | fclose (pInFile);
|
---|
899 | }
|
---|
900 |
|
---|
901 | return;
|
---|
902 |
|
---|
903 | Err1:
|
---|
904 | fclose (pInFile);
|
---|
905 | }
|
---|
906 |
|
---|
907 | int
|
---|
908 | main (
|
---|
909 | IN int Argc,
|
---|
910 | IN char **Argv
|
---|
911 | )
|
---|
912 | {
|
---|
913 | COMPILER_RUN_STATUS Status;
|
---|
914 |
|
---|
915 | SetPrintLevel(WARNING_LOG_LEVEL);
|
---|
916 | CVfrCompiler Compiler(Argc, Argv);
|
---|
917 |
|
---|
918 | Compiler.PreProcess();
|
---|
919 | Compiler.Compile();
|
---|
920 | Compiler.AdjustBin();
|
---|
921 | Compiler.GenBinary();
|
---|
922 | Compiler.GenCFile();
|
---|
923 | Compiler.GenRecordListFile ();
|
---|
924 |
|
---|
925 | Status = Compiler.RunStatus ();
|
---|
926 | if ((Status == STATUS_DEAD) || (Status == STATUS_FAILED)) {
|
---|
927 | return 2;
|
---|
928 | }
|
---|
929 |
|
---|
930 | if (gCBuffer.Buffer != NULL) {
|
---|
931 | delete[] gCBuffer.Buffer;
|
---|
932 | }
|
---|
933 |
|
---|
934 | if (gRBuffer.Buffer != NULL) {
|
---|
935 | delete[] gRBuffer.Buffer;
|
---|
936 | }
|
---|
937 |
|
---|
938 | return GetUtilityStatus ();
|
---|
939 | }
|
---|
940 |
|
---|
941 |
|
---|