]> git.proxmox.com Git - mirror_edk2.git/blame - BaseTools/Source/Python/GenFds/FdfParser.py
There is a limitation on WINDOWS OS for the length of entire file path can’t be large...
[mirror_edk2.git] / BaseTools / Source / Python / GenFds / FdfParser.py
CommitLineData
30fdf114
LG
1## @file\r
2# parse FDF file\r
3#\r
2bc3256c 4# Copyright (c) 2007 - 2014, Intel Corporation. All rights reserved.<BR>\r
30fdf114 5#\r
40d841f6 6# This program and the accompanying materials\r
30fdf114
LG
7# are licensed and made available under the terms and conditions of the BSD License\r
8# which accompanies this distribution. The full text of the license may be found at\r
9# http://opensource.org/licenses/bsd-license.php\r
10#\r
11# THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,\r
12# WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.\r
13#\r
14\r
15##\r
16# Import Modules\r
17#\r
0d2711a6
LG
18import re\r
19\r
30fdf114
LG
20import Fd\r
21import Region\r
22import Fv\r
23import AprioriSection\r
24import FfsInfStatement\r
25import FfsFileStatement\r
26import VerSection\r
27import UiSection\r
28import FvImageSection\r
29import DataSection\r
30import DepexSection\r
31import CompressSection\r
32import GuidSection\r
33import Capsule\r
34import CapsuleData\r
35import Rule\r
36import RuleComplexFile\r
37import RuleSimpleFile\r
38import EfiSection\r
39import Vtf\r
40import ComponentStatement\r
41import OptionRom\r
42import OptRomInfStatement\r
43import OptRomFileStatement\r
44\r
52302d4d 45from GenFdsGlobalVariable import GenFdsGlobalVariable\r
30fdf114
LG
46from Common.BuildToolError import *\r
47from Common import EdkLogger\r
14c48571 48from Common.Misc import PathClass\r
49from Common.String import NormPath\r
0d2711a6
LG
50import Common.GlobalData as GlobalData\r
51from Common.Expression import *\r
df692f02 52from Common import GlobalData\r
2bcc713e 53from Common.String import ReplaceMacro\r
30fdf114 54\r
d0acc87a
LG
55from Common.Misc import tdict\r
56\r
30fdf114 57import re\r
1be2ed90
HC
58import Common.LongFilePathOs as os\r
59from Common.LongFilePathSupport import OpenLongFilePath as open\r
30fdf114
LG
60\r
61##define T_CHAR_SPACE ' '\r
62##define T_CHAR_NULL '\0'\r
63##define T_CHAR_CR '\r'\r
64##define T_CHAR_TAB '\t'\r
65##define T_CHAR_LF '\n'\r
66##define T_CHAR_SLASH '/'\r
67##define T_CHAR_BACKSLASH '\\'\r
68##define T_CHAR_DOUBLE_QUOTE '\"'\r
69##define T_CHAR_SINGLE_QUOTE '\''\r
70##define T_CHAR_STAR '*'\r
71##define T_CHAR_HASH '#'\r
72\r
73(T_CHAR_SPACE, T_CHAR_NULL, T_CHAR_CR, T_CHAR_TAB, T_CHAR_LF, T_CHAR_SLASH, \\r
74T_CHAR_BACKSLASH, T_CHAR_DOUBLE_QUOTE, T_CHAR_SINGLE_QUOTE, T_CHAR_STAR, T_CHAR_HASH) = \\r
75(' ', '\0', '\r', '\t', '\n', '/', '\\', '\"', '\'', '*', '#')\r
76\r
77SEPERATOR_TUPLE = ('=', '|', ',', '{', '}')\r
78\r
0d2711a6
LG
79RegionSizePattern = re.compile("\s*(?P<base>(?:0x|0X)?[a-fA-F0-9]+)\s*\|\s*(?P<size>(?:0x|0X)?[a-fA-F0-9]+)\s*")\r
80RegionSizeGuidPattern = re.compile("\s*(?P<base>\w+\.\w+)\s*\|\s*(?P<size>\w+\.\w+)\s*")\r
2bc3256c 81RegionOffsetPcdPattern = re.compile("\s*(?P<base>\w+\.\w+)\s*$")\r
64b2609f 82ShortcutPcdPattern = re.compile("\s*\w+\s*=\s*(?P<value>(?:0x|0X)?[a-fA-F0-9]+)\s*\|\s*(?P<name>\w+\.\w+)\s*")\r
0d2711a6 83\r
30fdf114 84IncludeFileList = []\r
30fdf114
LG
85\r
86def GetRealFileLine (File, Line):\r
87\r
88 InsertedLines = 0\r
89 for Profile in IncludeFileList:\r
90 if Line >= Profile.InsertStartLineNumber and Line < Profile.InsertStartLineNumber + Profile.InsertAdjust + len(Profile.FileLinesList):\r
91 return (Profile.FileName, Line - Profile.InsertStartLineNumber + 1)\r
92 if Line >= Profile.InsertStartLineNumber + Profile.InsertAdjust + len(Profile.FileLinesList):\r
93 InsertedLines += Profile.InsertAdjust + len(Profile.FileLinesList)\r
94\r
95 return (File, Line - InsertedLines)\r
96\r
97## The exception class that used to report error messages when parsing FDF\r
98#\r
99# Currently the "ToolName" is set to be "FDF Parser".\r
100#\r
101class Warning (Exception):\r
102 ## The constructor\r
103 #\r
104 # @param self The object pointer\r
105 # @param Str The message to record\r
106 # @param File The FDF name\r
107 # @param Line The Line number that error occurs\r
108 #\r
109 def __init__(self, Str, File = None, Line = None):\r
110\r
111 FileLineTuple = GetRealFileLine(File, Line)\r
112 self.FileName = FileLineTuple[0]\r
113 self.LineNumber = FileLineTuple[1]\r
114 self.Message = Str\r
115 self.ToolName = 'FdfParser'\r
116\r
117 def __str__(self):\r
118 return self.Message\r
119\r
120## The MACRO class that used to record macro value data when parsing include file\r
121#\r
122#\r
123class MacroProfile :\r
124 ## The constructor\r
125 #\r
126 # @param self The object pointer\r
127 # @param FileName The file that to be parsed\r
128 #\r
129 def __init__(self, FileName, Line):\r
130 self.FileName = FileName\r
131 self.DefinedAtLine = Line\r
132 self.MacroName = None\r
133 self.MacroValue = None\r
134\r
135## The Include file content class that used to record file data when parsing include file\r
136#\r
137# May raise Exception when opening file.\r
138#\r
139class IncludeFileProfile :\r
140 ## The constructor\r
141 #\r
142 # @param self The object pointer\r
143 # @param FileName The file that to be parsed\r
144 #\r
145 def __init__(self, FileName):\r
146 self.FileName = FileName\r
147 self.FileLinesList = []\r
148 try:\r
149 fsock = open(FileName, "rb", 0)\r
150 try:\r
151 self.FileLinesList = fsock.readlines()\r
152 finally:\r
153 fsock.close()\r
154\r
155 except:\r
156 EdkLogger.error("FdfParser", FILE_OPEN_FAILURE, ExtraData=FileName)\r
157\r
158 self.InsertStartLineNumber = None\r
159 self.InsertAdjust = 0\r
160\r
161## The FDF content class that used to record file data when parsing FDF\r
162#\r
163# May raise Exception when opening file.\r
164#\r
165class FileProfile :\r
166 ## The constructor\r
167 #\r
168 # @param self The object pointer\r
169 # @param FileName The file that to be parsed\r
170 #\r
171 def __init__(self, FileName):\r
172 self.FileLinesList = []\r
173 try:\r
174 fsock = open(FileName, "rb", 0)\r
175 try:\r
176 self.FileLinesList = fsock.readlines()\r
177 finally:\r
178 fsock.close()\r
179\r
180 except:\r
181 EdkLogger.error("FdfParser", FILE_OPEN_FAILURE, ExtraData=FileName)\r
182\r
183\r
184 self.PcdDict = {}\r
185 self.InfList = []\r
d0acc87a
LG
186 # ECC will use this Dict and List information\r
187 self.PcdFileLineDict = {}\r
188 self.InfFileLineList = []\r
189 \r
30fdf114 190 self.FdDict = {}\r
52302d4d 191 self.FdNameNotSet = False\r
30fdf114 192 self.FvDict = {}\r
fd171542 193 self.CapsuleDict = {}\r
30fdf114
LG
194 self.VtfList = []\r
195 self.RuleDict = {}\r
196 self.OptRomDict = {}\r
197\r
198## The syntax parser for FDF\r
199#\r
200# PreprocessFile method should be called prior to ParseFile\r
201# CycleReferenceCheck method can detect cycles in FDF contents\r
202#\r
203# GetNext*** procedures mean these procedures will get next token first, then make judgement.\r
204# Get*** procedures mean these procedures will make judgement on current token only.\r
205#\r
206class FdfParser:\r
207 ## The constructor\r
208 #\r
209 # @param self The object pointer\r
210 # @param FileName The file that to be parsed\r
211 #\r
212 def __init__(self, FileName):\r
213 self.Profile = FileProfile(FileName)\r
214 self.FileName = FileName\r
215 self.CurrentLineNumber = 1\r
216 self.CurrentOffsetWithinLine = 0\r
217 self.CurrentFdName = None\r
218 self.CurrentFvName = None\r
219 self.__Token = ""\r
220 self.__SkippedChars = ""\r
221\r
d0acc87a
LG
222 # Used to section info\r
223 self.__CurSection = []\r
224 # Key: [section name, UI name, arch]\r
225 # Value: {MACRO_NAME : MACRO_VALUE}\r
226 self.__MacroDict = tdict(True, 3)\r
227 self.__PcdDict = {}\r
228\r
30fdf114 229 self.__WipeOffArea = []\r
14c48571 230 if GenFdsGlobalVariable.WorkSpaceDir == '':\r
231 GenFdsGlobalVariable.WorkSpaceDir = os.getenv("WORKSPACE")\r
30fdf114
LG
232\r
233 ## __IsWhiteSpace() method\r
234 #\r
235 # Whether char at current FileBufferPos is whitespace\r
236 #\r
237 # @param self The object pointer\r
238 # @param Char The char to test\r
239 # @retval True The char is a kind of white space\r
240 # @retval False The char is NOT a kind of white space\r
241 #\r
242 def __IsWhiteSpace(self, Char):\r
243 if Char in (T_CHAR_NULL, T_CHAR_CR, T_CHAR_SPACE, T_CHAR_TAB, T_CHAR_LF):\r
244 return True\r
245 else:\r
246 return False\r
247\r
248 ## __SkipWhiteSpace() method\r
249 #\r
250 # Skip white spaces from current char, return number of chars skipped\r
251 #\r
252 # @param self The object pointer\r
253 # @retval Count The number of chars skipped\r
254 #\r
255 def __SkipWhiteSpace(self):\r
256 Count = 0\r
257 while not self.__EndOfFile():\r
258 Count += 1\r
259 if self.__CurrentChar() in (T_CHAR_NULL, T_CHAR_CR, T_CHAR_LF, T_CHAR_SPACE, T_CHAR_TAB):\r
260 self.__SkippedChars += str(self.__CurrentChar())\r
261 self.__GetOneChar()\r
262\r
263 else:\r
264 Count = Count - 1\r
265 return Count\r
266\r
267 ## __EndOfFile() method\r
268 #\r
269 # Judge current buffer pos is at file end\r
270 #\r
271 # @param self The object pointer\r
272 # @retval True Current File buffer position is at file end\r
273 # @retval False Current File buffer position is NOT at file end\r
274 #\r
275 def __EndOfFile(self):\r
276 NumberOfLines = len(self.Profile.FileLinesList)\r
277 SizeOfLastLine = len(self.Profile.FileLinesList[-1])\r
278 if self.CurrentLineNumber == NumberOfLines and self.CurrentOffsetWithinLine >= SizeOfLastLine - 1:\r
279 return True\r
280 elif self.CurrentLineNumber > NumberOfLines:\r
281 return True\r
282 else:\r
283 return False\r
284\r
285 ## __EndOfLine() method\r
286 #\r
287 # Judge current buffer pos is at line end\r
288 #\r
289 # @param self The object pointer\r
290 # @retval True Current File buffer position is at line end\r
291 # @retval False Current File buffer position is NOT at line end\r
292 #\r
293 def __EndOfLine(self):\r
294 if self.CurrentLineNumber > len(self.Profile.FileLinesList):\r
295 return True\r
296 SizeOfCurrentLine = len(self.Profile.FileLinesList[self.CurrentLineNumber - 1])\r
297 if self.CurrentOffsetWithinLine >= SizeOfCurrentLine:\r
298 return True\r
299 else:\r
300 return False\r
301\r
302 ## Rewind() method\r
303 #\r
304 # Reset file data buffer to the initial state\r
305 #\r
306 # @param self The object pointer\r
307 #\r
308 def Rewind(self):\r
309 self.CurrentLineNumber = 1\r
310 self.CurrentOffsetWithinLine = 0\r
311\r
312 ## __UndoOneChar() method\r
313 #\r
314 # Go back one char in the file buffer\r
315 #\r
316 # @param self The object pointer\r
317 # @retval True Successfully go back one char\r
318 # @retval False Not able to go back one char as file beginning reached\r
319 #\r
320 def __UndoOneChar(self):\r
321\r
322 if self.CurrentLineNumber == 1 and self.CurrentOffsetWithinLine == 0:\r
323 return False\r
324 elif self.CurrentOffsetWithinLine == 0:\r
325 self.CurrentLineNumber -= 1\r
326 self.CurrentOffsetWithinLine = len(self.__CurrentLine()) - 1\r
327 else:\r
328 self.CurrentOffsetWithinLine -= 1\r
329 return True\r
330\r
331 ## __GetOneChar() method\r
332 #\r
333 # Move forward one char in the file buffer\r
334 #\r
335 # @param self The object pointer\r
336 #\r
337 def __GetOneChar(self):\r
338 if self.CurrentOffsetWithinLine == len(self.Profile.FileLinesList[self.CurrentLineNumber - 1]) - 1:\r
0d2711a6
LG
339 self.CurrentLineNumber += 1\r
340 self.CurrentOffsetWithinLine = 0\r
30fdf114 341 else:\r
0d2711a6 342 self.CurrentOffsetWithinLine += 1\r
30fdf114
LG
343\r
344 ## __CurrentChar() method\r
345 #\r
346 # Get the char pointed to by the file buffer pointer\r
347 #\r
348 # @param self The object pointer\r
349 # @retval Char Current char\r
350 #\r
351 def __CurrentChar(self):\r
352 return self.Profile.FileLinesList[self.CurrentLineNumber - 1][self.CurrentOffsetWithinLine]\r
353\r
354 ## __NextChar() method\r
355 #\r
356 # Get the one char pass the char pointed to by the file buffer pointer\r
357 #\r
358 # @param self The object pointer\r
359 # @retval Char Next char\r
360 #\r
361 def __NextChar(self):\r
362 if self.CurrentOffsetWithinLine == len(self.Profile.FileLinesList[self.CurrentLineNumber - 1]) - 1:\r
363 return self.Profile.FileLinesList[self.CurrentLineNumber][0]\r
364 else:\r
365 return self.Profile.FileLinesList[self.CurrentLineNumber - 1][self.CurrentOffsetWithinLine + 1]\r
366\r
367 ## __SetCurrentCharValue() method\r
368 #\r
369 # Modify the value of current char\r
370 #\r
371 # @param self The object pointer\r
372 # @param Value The new value of current char\r
373 #\r
374 def __SetCurrentCharValue(self, Value):\r
375 self.Profile.FileLinesList[self.CurrentLineNumber - 1][self.CurrentOffsetWithinLine] = Value\r
376\r
377 ## __CurrentLine() method\r
378 #\r
379 # Get the list that contains current line contents\r
380 #\r
381 # @param self The object pointer\r
382 # @retval List current line contents\r
383 #\r
384 def __CurrentLine(self):\r
385 return self.Profile.FileLinesList[self.CurrentLineNumber - 1]\r
386\r
387 def __StringToList(self):\r
388 self.Profile.FileLinesList = [list(s) for s in self.Profile.FileLinesList]\r
389 self.Profile.FileLinesList[-1].append(' ')\r
390\r
30fdf114
LG
391 def __ReplaceFragment(self, StartPos, EndPos, Value = ' '):\r
392 if StartPos[0] == EndPos[0]:\r
393 Offset = StartPos[1]\r
394 while Offset <= EndPos[1]:\r
395 self.Profile.FileLinesList[StartPos[0]][Offset] = Value\r
396 Offset += 1\r
397 return\r
398\r
399 Offset = StartPos[1]\r
400 while self.Profile.FileLinesList[StartPos[0]][Offset] not in ('\r', '\n'):\r
401 self.Profile.FileLinesList[StartPos[0]][Offset] = Value\r
402 Offset += 1\r
403\r
404 Line = StartPos[0]\r
405 while Line < EndPos[0]:\r
406 Offset = 0\r
407 while self.Profile.FileLinesList[Line][Offset] not in ('\r', '\n'):\r
408 self.Profile.FileLinesList[Line][Offset] = Value\r
409 Offset += 1\r
410 Line += 1\r
411\r
412 Offset = 0\r
413 while Offset <= EndPos[1]:\r
414 self.Profile.FileLinesList[EndPos[0]][Offset] = Value\r
415 Offset += 1\r
416\r
417\r
d5d56f1b
LG
418 def __GetMacroName(self):\r
419 if not self.__GetNextToken():\r
420 raise Warning("expected Macro name", self.FileName, self.CurrentLineNumber)\r
421 MacroName = self.__Token\r
422 NotFlag = False\r
423 if MacroName.startswith('!'):\r
424 NotFlag = True\r
425 MacroName = MacroName[1:].strip()\r
426 \r
427 if not MacroName.startswith('$(') or not MacroName.endswith(')'):\r
428 raise Warning("Macro name expected(Please use '$(%(Token)s)' if '%(Token)s' is a macro.)" % {"Token" : MacroName},\r
429 self.FileName, self.CurrentLineNumber)\r
430 MacroName = MacroName[2:-1]\r
431 return MacroName, NotFlag\r
d0acc87a
LG
432\r
433 def __SetMacroValue(self, Macro, Value):\r
434 if not self.__CurSection:\r
435 return\r
436\r
437 MacroDict = {}\r
438 if not self.__MacroDict[self.__CurSection[0], self.__CurSection[1], self.__CurSection[2]]:\r
439 self.__MacroDict[self.__CurSection[0], self.__CurSection[1], self.__CurSection[2]] = MacroDict\r
440 else:\r
441 MacroDict = self.__MacroDict[self.__CurSection[0], self.__CurSection[1], self.__CurSection[2]]\r
442 MacroDict[Macro] = Value\r
443\r
444 def __GetMacroValue(self, Macro):\r
445 # Highest priority\r
446 if Macro in GlobalData.gCommandLineDefines:\r
447 return GlobalData.gCommandLineDefines[Macro]\r
448 if Macro in GlobalData.gGlobalDefines:\r
449 return GlobalData.gGlobalDefines[Macro]\r
450\r
451 if self.__CurSection:\r
452 MacroDict = self.__MacroDict[\r
453 self.__CurSection[0],\r
454 self.__CurSection[1],\r
455 self.__CurSection[2]\r
456 ]\r
457 if MacroDict and Macro in MacroDict:\r
458 return MacroDict[Macro]\r
459\r
460 # Lowest priority\r
461 if Macro in GlobalData.gPlatformDefines:\r
462 return GlobalData.gPlatformDefines[Macro]\r
463 return None\r
464\r
465 def __SectionHeaderParser(self, Section):\r
466 # [Defines]\r
467 # [FD.UiName]: use dummy instead if UI name is optional\r
468 # [FV.UiName]\r
469 # [Capsule.UiName]\r
470 # [Rule]: don't take rule section into account, macro is not allowed in this section\r
471 # [VTF.arch.UiName, arch]\r
472 # [OptionRom.DriverName]\r
473 self.__CurSection = []\r
474 Section = Section.strip()[1:-1].upper().replace(' ', '').strip('.')\r
475 ItemList = Section.split('.')\r
476 Item = ItemList[0]\r
477 if Item == '' or Item == 'RULE':\r
478 return\r
479\r
480 if Item == 'DEFINES':\r
481 self.__CurSection = ['COMMON', 'COMMON', 'COMMON']\r
482 elif Item == 'VTF' and len(ItemList) == 3:\r
483 UiName = ItemList[2]\r
484 Pos = UiName.find(',')\r
485 if Pos != -1:\r
486 UiName = UiName[:Pos]\r
487 self.__CurSection = ['VTF', UiName, ItemList[1]]\r
488 elif len(ItemList) > 1:\r
489 self.__CurSection = [ItemList[0], ItemList[1], 'COMMON']\r
490 elif len(ItemList) > 0:\r
491 self.__CurSection = [ItemList[0], 'DUMMY', 'COMMON']\r
492\r
30fdf114
LG
493 ## PreprocessFile() method\r
494 #\r
495 # Preprocess file contents, replace comments with spaces.\r
496 # In the end, rewind the file buffer pointer to the beginning\r
497 # BUGBUG: No !include statement processing contained in this procedure\r
498 # !include statement should be expanded at the same FileLinesList[CurrentLineNumber - 1]\r
499 #\r
500 # @param self The object pointer\r
501 #\r
502 def PreprocessFile(self):\r
503\r
504 self.Rewind()\r
505 InComment = False\r
506 DoubleSlashComment = False\r
507 HashComment = False\r
508 # HashComment in quoted string " " is ignored.\r
509 InString = False\r
510\r
511 while not self.__EndOfFile():\r
512\r
513 if self.__CurrentChar() == T_CHAR_DOUBLE_QUOTE and not InComment:\r
514 InString = not InString\r
515 # meet new line, then no longer in a comment for // and '#'\r
516 if self.__CurrentChar() == T_CHAR_LF:\r
517 self.CurrentLineNumber += 1\r
518 self.CurrentOffsetWithinLine = 0\r
519 if InComment and DoubleSlashComment:\r
520 InComment = False\r
521 DoubleSlashComment = False\r
522 if InComment and HashComment:\r
523 InComment = False\r
524 HashComment = False\r
525 # check for */ comment end\r
526 elif InComment and not DoubleSlashComment and not HashComment and self.__CurrentChar() == T_CHAR_STAR and self.__NextChar() == T_CHAR_SLASH:\r
527 self.__SetCurrentCharValue(T_CHAR_SPACE)\r
528 self.__GetOneChar()\r
529 self.__SetCurrentCharValue(T_CHAR_SPACE)\r
530 self.__GetOneChar()\r
531 InComment = False\r
532 # set comments to spaces\r
533 elif InComment:\r
534 self.__SetCurrentCharValue(T_CHAR_SPACE)\r
535 self.__GetOneChar()\r
536 # check for // comment\r
537 elif self.__CurrentChar() == T_CHAR_SLASH and self.__NextChar() == T_CHAR_SLASH and not self.__EndOfLine():\r
538 InComment = True\r
539 DoubleSlashComment = True\r
540 # check for '#' comment\r
541 elif self.__CurrentChar() == T_CHAR_HASH and not self.__EndOfLine() and not InString:\r
542 InComment = True\r
543 HashComment = True\r
544 # check for /* comment start\r
545 elif self.__CurrentChar() == T_CHAR_SLASH and self.__NextChar() == T_CHAR_STAR:\r
546 self.__SetCurrentCharValue( T_CHAR_SPACE)\r
547 self.__GetOneChar()\r
548 self.__SetCurrentCharValue( T_CHAR_SPACE)\r
549 self.__GetOneChar()\r
550 InComment = True\r
551 else:\r
552 self.__GetOneChar()\r
553\r
554 # restore from ListOfList to ListOfString\r
555 self.Profile.FileLinesList = ["".join(list) for list in self.Profile.FileLinesList]\r
556 self.Rewind()\r
557\r
558 ## PreprocessIncludeFile() method\r
559 #\r
560 # Preprocess file contents, replace !include statements with file contents.\r
561 # In the end, rewind the file buffer pointer to the beginning\r
562 #\r
563 # @param self The object pointer\r
564 #\r
565 def PreprocessIncludeFile(self):\r
566\r
567 while self.__GetNextToken():\r
568\r
569 if self.__Token == '!include':\r
570 IncludeLine = self.CurrentLineNumber\r
571 IncludeOffset = self.CurrentOffsetWithinLine - len('!include')\r
572 if not self.__GetNextToken():\r
573 raise Warning("expected include file name", self.FileName, self.CurrentLineNumber)\r
574 IncFileName = self.__Token\r
2bcc713e 575 __IncludeMacros = {}\r
d0acc87a
LG
576 for Macro in ['WORKSPACE', 'ECP_SOURCE', 'EFI_SOURCE', 'EDK_SOURCE']:\r
577 MacroVal = self.__GetMacroValue(Macro)\r
578 if MacroVal:\r
579 __IncludeMacros[Macro] = MacroVal\r
580\r
581 try:\r
582 IncludedFile = NormPath(ReplaceMacro(IncFileName, __IncludeMacros, RaiseError=True))\r
583 except:\r
584 raise Warning("only these system environment variables are permitted to start the path of the included file: "\r
585 "$(WORKSPACE), $(ECP_SOURCE), $(EFI_SOURCE), $(EDK_SOURCE)",\r
586 self.FileName, self.CurrentLineNumber)\r
2bcc713e
LG
587 #\r
588 # First search the include file under the same directory as FDF file\r
589 #\r
590 IncludedFile1 = PathClass(IncludedFile, os.path.dirname(self.FileName))\r
591 ErrorCode = IncludedFile1.Validate()[0]\r
592 if ErrorCode != 0:\r
593 #\r
594 # Then search the include file under the same directory as DSC file\r
595 #\r
d0acc87a
LG
596 PlatformDir = ''\r
597 if GenFdsGlobalVariable.ActivePlatform:\r
598 PlatformDir = GenFdsGlobalVariable.ActivePlatform.Dir\r
599 elif GlobalData.gActivePlatform:\r
600 PlatformDir = GlobalData.gActivePlatform.MetaFile.Dir\r
601 IncludedFile1 = PathClass(IncludedFile, PlatformDir)\r
2bcc713e
LG
602 ErrorCode = IncludedFile1.Validate()[0]\r
603 if ErrorCode != 0:\r
604 #\r
605 # Also search file under the WORKSPACE directory\r
606 #\r
607 IncludedFile1 = PathClass(IncludedFile, GlobalData.gWorkspace)\r
608 ErrorCode = IncludedFile1.Validate()[0]\r
609 if ErrorCode != 0:\r
d0acc87a 610 raise Warning("The include file does not exist under below directories: \n%s\n%s\n%s\n"%(os.path.dirname(self.FileName), PlatformDir, GlobalData.gWorkspace), \r
2bcc713e 611 self.FileName, self.CurrentLineNumber)\r
30fdf114 612\r
2bcc713e 613 IncFileProfile = IncludeFileProfile(IncludedFile1.Path)\r
30fdf114
LG
614\r
615 CurrentLine = self.CurrentLineNumber\r
616 CurrentOffset = self.CurrentOffsetWithinLine\r
617 # list index of the insertion, note that line number is 'CurrentLine + 1'\r
618 InsertAtLine = CurrentLine\r
619 IncFileProfile.InsertStartLineNumber = InsertAtLine + 1\r
620 # deal with remaining portions after "!include filename", if exists.\r
621 if self.__GetNextToken():\r
622 if self.CurrentLineNumber == CurrentLine:\r
623 RemainingLine = self.__CurrentLine()[CurrentOffset:]\r
624 self.Profile.FileLinesList.insert(self.CurrentLineNumber, RemainingLine)\r
625 IncFileProfile.InsertAdjust += 1\r
626 self.CurrentLineNumber += 1\r
627 self.CurrentOffsetWithinLine = 0\r
628\r
629 for Line in IncFileProfile.FileLinesList:\r
630 self.Profile.FileLinesList.insert(InsertAtLine, Line)\r
631 self.CurrentLineNumber += 1\r
632 InsertAtLine += 1\r
633\r
634 IncludeFileList.append(IncFileProfile)\r
635\r
636 # comment out the processed include file statement\r
637 TempList = list(self.Profile.FileLinesList[IncludeLine - 1])\r
638 TempList.insert(IncludeOffset, '#')\r
639 self.Profile.FileLinesList[IncludeLine - 1] = ''.join(TempList)\r
640\r
641 self.Rewind()\r
0d2711a6 642 \r
da92f276
LG
643 def __GetIfListCurrentItemStat(self, IfList):\r
644 if len(IfList) == 0:\r
645 return True\r
646 \r
647 for Item in IfList:\r
648 if Item[1] == False:\r
649 return False\r
650 \r
651 return True\r
0d2711a6 652 \r
6780eef1 653 ## PreprocessConditionalStatement() method\r
30fdf114 654 #\r
6780eef1 655 # Preprocess conditional statement.\r
30fdf114
LG
656 # In the end, rewind the file buffer pointer to the beginning\r
657 #\r
658 # @param self The object pointer\r
659 #\r
660 def PreprocessConditionalStatement(self):\r
661 # IfList is a stack of if branches with elements of list [Pos, CondSatisfied, BranchDetermined]\r
662 IfList = []\r
0d2711a6 663 RegionLayoutLine = 0\r
d0acc87a 664 ReplacedLine = -1\r
30fdf114 665 while self.__GetNextToken():\r
d0acc87a
LG
666 # Determine section name and the location dependent macro\r
667 if self.__GetIfListCurrentItemStat(IfList):\r
668 if self.__Token.startswith('['):\r
669 Header = self.__Token\r
670 if not self.__Token.endswith(']'):\r
671 self.__SkipToToken(']')\r
672 Header += self.__SkippedChars\r
673 if Header.find('$(') != -1:\r
674 raise Warning("macro cannot be used in section header", self.FileName, self.CurrentLineNumber)\r
675 self.__SectionHeaderParser(Header)\r
676 continue\r
677 # Replace macros except in RULE section or out of section\r
678 elif self.__CurSection and ReplacedLine != self.CurrentLineNumber:\r
679 ReplacedLine = self.CurrentLineNumber\r
680 self.__UndoToken()\r
681 CurLine = self.Profile.FileLinesList[ReplacedLine - 1]\r
682 PreIndex = 0\r
683 StartPos = CurLine.find('$(', PreIndex)\r
684 EndPos = CurLine.find(')', StartPos+2)\r
64b2609f 685 while StartPos != -1 and EndPos != -1 and self.__Token not in ['!ifdef', '!ifndef', '!if', '!elseif']:\r
d0acc87a
LG
686 MacroName = CurLine[StartPos+2 : EndPos]\r
687 MacorValue = self.__GetMacroValue(MacroName)\r
688 if MacorValue != None:\r
689 CurLine = CurLine.replace('$(' + MacroName + ')', MacorValue, 1)\r
690 if MacorValue.find('$(') != -1:\r
691 PreIndex = StartPos\r
692 else:\r
693 PreIndex = StartPos + len(MacorValue)\r
694 else:\r
695 PreIndex = EndPos + 1\r
696 StartPos = CurLine.find('$(', PreIndex)\r
697 EndPos = CurLine.find(')', StartPos+2)\r
698 self.Profile.FileLinesList[ReplacedLine - 1] = CurLine\r
699 continue\r
700\r
30fdf114 701 if self.__Token == 'DEFINE':\r
d0acc87a
LG
702 if self.__GetIfListCurrentItemStat(IfList):\r
703 if not self.__CurSection:\r
704 raise Warning("macro cannot be defined in Rule section or out of section", self.FileName, self.CurrentLineNumber)\r
da92f276
LG
705 DefineLine = self.CurrentLineNumber - 1\r
706 DefineOffset = self.CurrentOffsetWithinLine - len('DEFINE')\r
707 if not self.__GetNextToken():\r
708 raise Warning("expected Macro name", self.FileName, self.CurrentLineNumber)\r
709 Macro = self.__Token\r
710 if not self.__IsToken( "="):\r
711 raise Warning("expected '='", self.FileName, self.CurrentLineNumber)\r
712 \r
d0acc87a
LG
713 Value = self.__GetExpression()\r
714 self.__SetMacroValue(Macro, Value)\r
da92f276 715 self.__WipeOffArea.append(((DefineLine, DefineOffset), (self.CurrentLineNumber - 1, self.CurrentOffsetWithinLine - 1)))\r
0d2711a6 716 elif self.__Token == 'SET':\r
64b2609f
LG
717 SetLine = self.CurrentLineNumber - 1\r
718 SetOffset = self.CurrentOffsetWithinLine - len('SET')\r
0d2711a6
LG
719 PcdPair = self.__GetNextPcdName()\r
720 PcdName = "%s.%s" % (PcdPair[1], PcdPair[0])\r
721 if not self.__IsToken( "="):\r
722 raise Warning("expected '='", self.FileName, self.CurrentLineNumber)\r
723\r
d0acc87a
LG
724 Value = self.__GetExpression()\r
725 Value = self.__EvaluateConditional(Value, self.CurrentLineNumber, 'eval', True)\r
30fdf114 726\r
d0acc87a 727 self.__PcdDict[PcdName] = Value\r
64b2609f
LG
728\r
729 self.Profile.PcdDict[PcdPair] = Value\r
730 FileLineTuple = GetRealFileLine(self.FileName, self.CurrentLineNumber)\r
731 self.Profile.PcdFileLineDict[PcdPair] = FileLineTuple\r
732\r
733 self.__WipeOffArea.append(((SetLine, SetOffset), (self.CurrentLineNumber - 1, self.CurrentOffsetWithinLine - 1)))\r
30fdf114
LG
734 elif self.__Token in ('!ifdef', '!ifndef', '!if'):\r
735 IfStartPos = (self.CurrentLineNumber - 1, self.CurrentOffsetWithinLine - len(self.__Token))\r
736 IfList.append([IfStartPos, None, None])\r
0d2711a6 737\r
30fdf114 738 CondLabel = self.__Token\r
0d2711a6 739 Expression = self.__GetExpression()\r
d5d56f1b 740 \r
30fdf114 741 if CondLabel == '!if':\r
0d2711a6 742 ConditionSatisfied = self.__EvaluateConditional(Expression, IfList[-1][0][0] + 1, 'eval')\r
30fdf114 743 else:\r
0d2711a6
LG
744 ConditionSatisfied = self.__EvaluateConditional(Expression, IfList[-1][0][0] + 1, 'in')\r
745 if CondLabel == '!ifndef':\r
30fdf114 746 ConditionSatisfied = not ConditionSatisfied\r
30fdf114 747\r
0d2711a6
LG
748 BranchDetermined = ConditionSatisfied\r
749 IfList[-1] = [IfList[-1][0], ConditionSatisfied, BranchDetermined]\r
750 if ConditionSatisfied:\r
751 self.__WipeOffArea.append((IfList[-1][0], (self.CurrentLineNumber - 1, self.CurrentOffsetWithinLine - 1))) \r
30fdf114
LG
752 elif self.__Token in ('!elseif', '!else'):\r
753 ElseStartPos = (self.CurrentLineNumber - 1, self.CurrentOffsetWithinLine - len(self.__Token))\r
754 if len(IfList) <= 0:\r
755 raise Warning("Missing !if statement", self.FileName, self.CurrentLineNumber)\r
0d2711a6 756\r
30fdf114
LG
757 if IfList[-1][1]:\r
758 IfList[-1] = [ElseStartPos, False, True]\r
759 self.__WipeOffArea.append((ElseStartPos, (self.CurrentLineNumber - 1, self.CurrentOffsetWithinLine - 1)))\r
760 else:\r
761 self.__WipeOffArea.append((IfList[-1][0], ElseStartPos))\r
762 IfList[-1] = [ElseStartPos, True, IfList[-1][2]]\r
763 if self.__Token == '!elseif':\r
0d2711a6
LG
764 Expression = self.__GetExpression()\r
765 ConditionSatisfied = self.__EvaluateConditional(Expression, IfList[-1][0][0] + 1, 'eval')\r
30fdf114
LG
766 IfList[-1] = [IfList[-1][0], ConditionSatisfied, IfList[-1][2]]\r
767\r
768 if IfList[-1][1]:\r
769 if IfList[-1][2]:\r
770 IfList[-1][1] = False\r
771 else:\r
772 IfList[-1][2] = True\r
773 self.__WipeOffArea.append((IfList[-1][0], (self.CurrentLineNumber - 1, self.CurrentOffsetWithinLine - 1)))\r
30fdf114 774 elif self.__Token == '!endif':\r
d0acc87a
LG
775 if len(IfList) <= 0:\r
776 raise Warning("Missing !if statement", self.FileName, self.CurrentLineNumber)\r
30fdf114
LG
777 if IfList[-1][1]:\r
778 self.__WipeOffArea.append(((self.CurrentLineNumber - 1, self.CurrentOffsetWithinLine - len('!endif')), (self.CurrentLineNumber - 1, self.CurrentOffsetWithinLine - 1)))\r
779 else:\r
780 self.__WipeOffArea.append((IfList[-1][0], (self.CurrentLineNumber - 1, self.CurrentOffsetWithinLine - 1)))\r
781\r
782 IfList.pop()\r
0d2711a6
LG
783 elif not IfList: # Don't use PCDs inside conditional directive\r
784 if self.CurrentLineNumber <= RegionLayoutLine:\r
785 # Don't try the same line twice\r
786 continue\r
64b2609f
LG
787 SetPcd = ShortcutPcdPattern.match(self.Profile.FileLinesList[self.CurrentLineNumber - 1])\r
788 if SetPcd:\r
789 self.__PcdDict[SetPcd.group('name')] = SetPcd.group('value')\r
790 RegionLayoutLine = self.CurrentLineNumber\r
791 continue\r
0d2711a6
LG
792 RegionSize = RegionSizePattern.match(self.Profile.FileLinesList[self.CurrentLineNumber - 1])\r
793 if not RegionSize:\r
794 RegionLayoutLine = self.CurrentLineNumber\r
795 continue\r
796 RegionSizeGuid = RegionSizeGuidPattern.match(self.Profile.FileLinesList[self.CurrentLineNumber])\r
797 if not RegionSizeGuid:\r
798 RegionLayoutLine = self.CurrentLineNumber + 1\r
799 continue\r
d0acc87a
LG
800 self.__PcdDict[RegionSizeGuid.group('base')] = RegionSize.group('base')\r
801 self.__PcdDict[RegionSizeGuid.group('size')] = RegionSize.group('size')\r
0d2711a6
LG
802 RegionLayoutLine = self.CurrentLineNumber + 1\r
803\r
804 if IfList:\r
30fdf114
LG
805 raise Warning("Missing !endif", self.FileName, self.CurrentLineNumber)\r
806 self.Rewind()\r
807\r
d0acc87a
LG
808 def __CollectMacroPcd(self):\r
809 MacroDict = {}\r
810\r
811 # PCD macro\r
64b2609f 812 MacroDict.update(GlobalData.gPlatformPcds)\r
d0acc87a
LG
813 MacroDict.update(self.__PcdDict)\r
814\r
815 # Lowest priority\r
816 MacroDict.update(GlobalData.gPlatformDefines)\r
817\r
818 if self.__CurSection:\r
819 # Defines macro\r
820 ScopeMacro = self.__MacroDict['COMMON', 'COMMON', 'COMMON']\r
821 if ScopeMacro:\r
822 MacroDict.update(ScopeMacro)\r
823 \r
824 # Section macro\r
825 ScopeMacro = self.__MacroDict[\r
826 self.__CurSection[0],\r
827 self.__CurSection[1],\r
828 self.__CurSection[2]\r
829 ]\r
830 if ScopeMacro:\r
831 MacroDict.update(ScopeMacro)\r
832\r
833 MacroDict.update(GlobalData.gGlobalDefines)\r
834 MacroDict.update(GlobalData.gCommandLineDefines)\r
835 # Highest priority\r
836\r
837 return MacroDict\r
838\r
0d2711a6 839 def __EvaluateConditional(self, Expression, Line, Op = None, Value = None):\r
30fdf114 840 FileLineTuple = GetRealFileLine(self.FileName, Line)\r
d0acc87a 841 MacroPcdDict = self.__CollectMacroPcd()\r
0d2711a6
LG
842 if Op == 'eval':\r
843 try:\r
d0acc87a
LG
844 if Value:\r
845 return ValueExpression(Expression, MacroPcdDict)(True)\r
846 else:\r
847 return ValueExpression(Expression, MacroPcdDict)()\r
0d2711a6
LG
848 except WrnExpression, Excpt:\r
849 # \r
850 # Catch expression evaluation warning here. We need to report\r
851 # the precise number of line and return the evaluation result\r
852 #\r
853 EdkLogger.warn('Parser', "Suspicious expression: %s" % str(Excpt),\r
854 File=self.FileName, ExtraData=self.__CurrentLine(), \r
855 Line=Line)\r
856 return Excpt.result\r
857 except Exception, Excpt:\r
64b2609f
LG
858 if hasattr(Excpt, 'Pcd'):\r
859 if Excpt.Pcd in GlobalData.gPlatformOtherPcds:\r
860 Info = GlobalData.gPlatformOtherPcds[Excpt.Pcd]\r
861 raise Warning("Cannot use this PCD (%s) in an expression as"\r
862 " it must be defined in a [PcdsFixedAtBuild] or [PcdsFeatureFlag] section"\r
863 " of the DSC file (%s), and it is currently defined in this section:"\r
864 " %s, line #: %d." % (Excpt.Pcd, GlobalData.gPlatformOtherPcds['DSCFILE'], Info[0], Info[1]),\r
865 *FileLineTuple)\r
866 else:\r
867 raise Warning("PCD (%s) is not defined in DSC file (%s)" % (Excpt.Pcd, GlobalData.gPlatformOtherPcds['DSCFILE']),\r
868 *FileLineTuple)\r
869 else:\r
870 raise Warning(str(Excpt), *FileLineTuple)\r
0d2711a6
LG
871 else:\r
872 if Expression.startswith('$(') and Expression[-1] == ')':\r
873 Expression = Expression[2:-1] \r
d0acc87a 874 return Expression in MacroPcdDict\r
30fdf114
LG
875\r
876 ## __IsToken() method\r
877 #\r
878 # Check whether input string is found from current char position along\r
879 # If found, the string value is put into self.__Token\r
880 #\r
881 # @param self The object pointer\r
882 # @param String The string to search\r
883 # @param IgnoreCase Indicate case sensitive/non-sensitive search, default is case sensitive\r
884 # @retval True Successfully find string, file buffer pointer moved forward\r
885 # @retval False Not able to find string, file buffer pointer not changed\r
886 #\r
887 def __IsToken(self, String, IgnoreCase = False):\r
888 self.__SkipWhiteSpace()\r
889\r
890 # Only consider the same line, no multi-line token allowed\r
891 StartPos = self.CurrentOffsetWithinLine\r
892 index = -1\r
893 if IgnoreCase:\r
894 index = self.__CurrentLine()[self.CurrentOffsetWithinLine : ].upper().find(String.upper())\r
895 else:\r
896 index = self.__CurrentLine()[self.CurrentOffsetWithinLine : ].find(String)\r
897 if index == 0:\r
898 self.CurrentOffsetWithinLine += len(String)\r
899 self.__Token = self.__CurrentLine()[StartPos : self.CurrentOffsetWithinLine]\r
900 return True\r
901 return False\r
902\r
903 ## __IsKeyword() method\r
904 #\r
905 # Check whether input keyword is found from current char position along, whole word only!\r
906 # If found, the string value is put into self.__Token\r
907 #\r
908 # @param self The object pointer\r
909 # @param Keyword The string to search\r
910 # @param IgnoreCase Indicate case sensitive/non-sensitive search, default is case sensitive\r
911 # @retval True Successfully find string, file buffer pointer moved forward\r
912 # @retval False Not able to find string, file buffer pointer not changed\r
913 #\r
914 def __IsKeyword(self, KeyWord, IgnoreCase = False):\r
915 self.__SkipWhiteSpace()\r
916\r
917 # Only consider the same line, no multi-line token allowed\r
918 StartPos = self.CurrentOffsetWithinLine\r
919 index = -1\r
920 if IgnoreCase:\r
921 index = self.__CurrentLine()[self.CurrentOffsetWithinLine : ].upper().find(KeyWord.upper())\r
922 else:\r
923 index = self.__CurrentLine()[self.CurrentOffsetWithinLine : ].find(KeyWord)\r
924 if index == 0:\r
925 followingChar = self.__CurrentLine()[self.CurrentOffsetWithinLine + len(KeyWord)]\r
926 if not str(followingChar).isspace() and followingChar not in SEPERATOR_TUPLE:\r
927 return False\r
928 self.CurrentOffsetWithinLine += len(KeyWord)\r
929 self.__Token = self.__CurrentLine()[StartPos : self.CurrentOffsetWithinLine]\r
930 return True\r
931 return False\r
932\r
0d2711a6
LG
933 def __GetExpression(self):\r
934 Line = self.Profile.FileLinesList[self.CurrentLineNumber - 1]\r
935 Index = len(Line) - 1\r
936 while Line[Index] in ['\r', '\n']:\r
937 Index -= 1\r
938 ExpressionString = self.Profile.FileLinesList[self.CurrentLineNumber - 1][self.CurrentOffsetWithinLine:Index+1]\r
939 self.CurrentOffsetWithinLine += len(ExpressionString)\r
940 ExpressionString = ExpressionString.strip()\r
941 return ExpressionString\r
942\r
30fdf114
LG
943 ## __GetNextWord() method\r
944 #\r
945 # Get next C name from file lines\r
946 # If found, the string value is put into self.__Token\r
947 #\r
948 # @param self The object pointer\r
949 # @retval True Successfully find a C name string, file buffer pointer moved forward\r
950 # @retval False Not able to find a C name string, file buffer pointer not changed\r
951 #\r
952 def __GetNextWord(self):\r
953 self.__SkipWhiteSpace()\r
954 if self.__EndOfFile():\r
955 return False\r
956\r
957 TempChar = self.__CurrentChar()\r
958 StartPos = self.CurrentOffsetWithinLine\r
959 if (TempChar >= 'a' and TempChar <= 'z') or (TempChar >= 'A' and TempChar <= 'Z') or TempChar == '_':\r
960 self.__GetOneChar()\r
961 while not self.__EndOfLine():\r
962 TempChar = self.__CurrentChar()\r
963 if (TempChar >= 'a' and TempChar <= 'z') or (TempChar >= 'A' and TempChar <= 'Z') \\r
964 or (TempChar >= '0' and TempChar <= '9') or TempChar == '_' or TempChar == '-':\r
965 self.__GetOneChar()\r
966\r
967 else:\r
968 break\r
969\r
970 self.__Token = self.__CurrentLine()[StartPos : self.CurrentOffsetWithinLine]\r
971 return True\r
972\r
973 return False\r
974\r
975 ## __GetNextToken() method\r
976 #\r
977 # Get next token unit before a seperator\r
978 # If found, the string value is put into self.__Token\r
979 #\r
980 # @param self The object pointer\r
981 # @retval True Successfully find a token unit, file buffer pointer moved forward\r
982 # @retval False Not able to find a token unit, file buffer pointer not changed\r
983 #\r
984 def __GetNextToken(self):\r
985 # Skip leading spaces, if exist.\r
986 self.__SkipWhiteSpace()\r
987 if self.__EndOfFile():\r
988 return False\r
989 # Record the token start position, the position of the first non-space char.\r
990 StartPos = self.CurrentOffsetWithinLine\r
991 StartLine = self.CurrentLineNumber\r
d0acc87a 992 while StartLine == self.CurrentLineNumber:\r
30fdf114
LG
993 TempChar = self.__CurrentChar()\r
994 # Try to find the end char that is not a space and not in seperator tuple.\r
995 # That is, when we got a space or any char in the tuple, we got the end of token.\r
996 if not str(TempChar).isspace() and TempChar not in SEPERATOR_TUPLE:\r
997 self.__GetOneChar()\r
998 # if we happen to meet a seperator as the first char, we must proceed to get it.\r
999 # That is, we get a token that is a seperator char. nomally it is the boundary of other tokens.\r
1000 elif StartPos == self.CurrentOffsetWithinLine and TempChar in SEPERATOR_TUPLE:\r
1001 self.__GetOneChar()\r
1002 break\r
1003 else:\r
1004 break\r
1005# else:\r
1006# return False\r
1007\r
1008 EndPos = self.CurrentOffsetWithinLine\r
1009 if self.CurrentLineNumber != StartLine:\r
1010 EndPos = len(self.Profile.FileLinesList[StartLine-1])\r
1011 self.__Token = self.Profile.FileLinesList[StartLine-1][StartPos : EndPos]\r
1012 if StartPos != self.CurrentOffsetWithinLine:\r
1013 return True\r
1014 else:\r
1015 return False\r
1016\r
1017 def __GetNextOp(self):\r
1018 # Skip leading spaces, if exist.\r
1019 self.__SkipWhiteSpace()\r
1020 if self.__EndOfFile():\r
1021 return False\r
1022 # Record the token start position, the position of the first non-space char.\r
1023 StartPos = self.CurrentOffsetWithinLine\r
1024 while not self.__EndOfLine():\r
1025 TempChar = self.__CurrentChar()\r
1026 # Try to find the end char that is not a space\r
1027 if not str(TempChar).isspace():\r
1028 self.__GetOneChar()\r
1029 else:\r
1030 break\r
1031 else:\r
1032 return False\r
1033\r
1034 if StartPos != self.CurrentOffsetWithinLine:\r
1035 self.__Token = self.__CurrentLine()[StartPos : self.CurrentOffsetWithinLine]\r
1036 return True\r
1037 else:\r
1038 return False\r
1039 ## __GetNextGuid() method\r
1040 #\r
1041 # Get next token unit before a seperator\r
1042 # If found, the GUID string is put into self.__Token\r
1043 #\r
1044 # @param self The object pointer\r
1045 # @retval True Successfully find a registry format GUID, file buffer pointer moved forward\r
1046 # @retval False Not able to find a registry format GUID, file buffer pointer not changed\r
1047 #\r
1048 def __GetNextGuid(self):\r
1049\r
1050 if not self.__GetNextToken():\r
1051 return False\r
1052 p = re.compile('[a-fA-F0-9]{8}-[a-fA-F0-9]{4}-[a-fA-F0-9]{4}-[a-fA-F0-9]{4}-[a-fA-F0-9]{12}')\r
1053 if p.match(self.__Token) != None:\r
1054 return True\r
1055 else:\r
1056 self.__UndoToken()\r
1057 return False\r
1058\r
1059 ## __UndoToken() method\r
1060 #\r
1061 # Go back one token unit in file buffer\r
1062 #\r
1063 # @param self The object pointer\r
1064 #\r
1065 def __UndoToken(self):\r
1066 self.__UndoOneChar()\r
1067 while self.__CurrentChar().isspace():\r
1068 if not self.__UndoOneChar():\r
1069 self.__GetOneChar()\r
1070 return\r
1071\r
1072\r
1073 StartPos = self.CurrentOffsetWithinLine\r
1074 CurrentLine = self.CurrentLineNumber\r
1075 while CurrentLine == self.CurrentLineNumber:\r
1076\r
1077 TempChar = self.__CurrentChar()\r
1078 # Try to find the end char that is not a space and not in seperator tuple.\r
1079 # That is, when we got a space or any char in the tuple, we got the end of token.\r
1080 if not str(TempChar).isspace() and not TempChar in SEPERATOR_TUPLE:\r
1081 if not self.__UndoOneChar():\r
d0acc87a 1082 return\r
30fdf114
LG
1083 # if we happen to meet a seperator as the first char, we must proceed to get it.\r
1084 # That is, we get a token that is a seperator char. nomally it is the boundary of other tokens.\r
1085 elif StartPos == self.CurrentOffsetWithinLine and TempChar in SEPERATOR_TUPLE:\r
1086 return\r
1087 else:\r
1088 break\r
1089\r
1090 self.__GetOneChar()\r
1091\r
1092 ## __HexDigit() method\r
1093 #\r
1094 # Whether char input is a Hex data bit\r
1095 #\r
1096 # @param self The object pointer\r
1097 # @param TempChar The char to test\r
1098 # @retval True The char is a Hex data bit\r
1099 # @retval False The char is NOT a Hex data bit\r
1100 #\r
1101 def __HexDigit(self, TempChar):\r
1102 if (TempChar >= 'a' and TempChar <= 'f') or (TempChar >= 'A' and TempChar <= 'F') \\r
1103 or (TempChar >= '0' and TempChar <= '9'):\r
1104 return True\r
1105 else:\r
1106 return False\r
1107\r
1108 def __IsHex(self, HexStr):\r
1109 if not HexStr.upper().startswith("0X"):\r
1110 return False\r
1111 if len(self.__Token) <= 2:\r
1112 return False\r
1113 charList = [c for c in HexStr[2 : ] if not self.__HexDigit( c)]\r
1114 if len(charList) == 0:\r
1115 return True\r
1116 else:\r
1117 return False\r
1118 ## __GetNextHexNumber() method\r
1119 #\r
1120 # Get next HEX data before a seperator\r
1121 # If found, the HEX data is put into self.__Token\r
1122 #\r
1123 # @param self The object pointer\r
1124 # @retval True Successfully find a HEX data, file buffer pointer moved forward\r
1125 # @retval False Not able to find a HEX data, file buffer pointer not changed\r
1126 #\r
1127 def __GetNextHexNumber(self):\r
1128 if not self.__GetNextToken():\r
1129 return False\r
1130 if self.__IsHex(self.__Token):\r
1131 return True\r
1132 else:\r
1133 self.__UndoToken()\r
1134 return False\r
1135\r
1136 ## __GetNextDecimalNumber() method\r
1137 #\r
1138 # Get next decimal data before a seperator\r
1139 # If found, the decimal data is put into self.__Token\r
1140 #\r
1141 # @param self The object pointer\r
1142 # @retval True Successfully find a decimal data, file buffer pointer moved forward\r
1143 # @retval False Not able to find a decimal data, file buffer pointer not changed\r
1144 #\r
1145 def __GetNextDecimalNumber(self):\r
1146 if not self.__GetNextToken():\r
1147 return False\r
1148 if self.__Token.isdigit():\r
1149 return True\r
1150 else:\r
1151 self.__UndoToken()\r
1152 return False\r
1153\r
1154 ## __GetNextPcdName() method\r
1155 #\r
1156 # Get next PCD token space C name and PCD C name pair before a seperator\r
1157 # If found, the decimal data is put into self.__Token\r
1158 #\r
1159 # @param self The object pointer\r
1160 # @retval Tuple PCD C name and PCD token space C name pair\r
1161 #\r
1162 def __GetNextPcdName(self):\r
1163 if not self.__GetNextWord():\r
1164 raise Warning("expected format of <PcdTokenSpaceCName>.<PcdCName>", self.FileName, self.CurrentLineNumber)\r
1165 pcdTokenSpaceCName = self.__Token\r
1166\r
1167 if not self.__IsToken( "."):\r
1168 raise Warning("expected format of <PcdTokenSpaceCName>.<PcdCName>", self.FileName, self.CurrentLineNumber)\r
1169\r
1170 if not self.__GetNextWord():\r
1171 raise Warning("expected format of <PcdTokenSpaceCName>.<PcdCName>", self.FileName, self.CurrentLineNumber)\r
1172 pcdCName = self.__Token\r
1173\r
1174 return (pcdCName, pcdTokenSpaceCName)\r
1175\r
1176 ## __GetStringData() method\r
1177 #\r
1178 # Get string contents quoted in ""\r
1179 # If found, the decimal data is put into self.__Token\r
1180 #\r
1181 # @param self The object pointer\r
1182 # @retval True Successfully find a string data, file buffer pointer moved forward\r
1183 # @retval False Not able to find a string data, file buffer pointer not changed\r
1184 #\r
1185 def __GetStringData(self):\r
1186 if self.__Token.startswith("\"") or self.__Token.startswith("L\""):\r
1187 self.__UndoToken()\r
1188 self.__SkipToToken("\"")\r
1189 currentLineNumber = self.CurrentLineNumber\r
1190\r
1191 if not self.__SkipToToken("\""):\r
1192 raise Warning("Missing Quote \" for String", self.FileName, self.CurrentLineNumber)\r
1193 if currentLineNumber != self.CurrentLineNumber:\r
1194 raise Warning("Missing Quote \" for String", self.FileName, self.CurrentLineNumber)\r
1195 self.__Token = self.__SkippedChars.rstrip('\"')\r
1196 return True\r
1197\r
1198 elif self.__Token.startswith("\'") or self.__Token.startswith("L\'"):\r
1199 self.__UndoToken()\r
1200 self.__SkipToToken("\'")\r
1201 currentLineNumber = self.CurrentLineNumber\r
1202\r
1203 if not self.__SkipToToken("\'"):\r
1204 raise Warning("Missing Quote \' for String", self.FileName, self.CurrentLineNumber)\r
1205 if currentLineNumber != self.CurrentLineNumber:\r
1206 raise Warning("Missing Quote \' for String", self.FileName, self.CurrentLineNumber)\r
1207 self.__Token = self.__SkippedChars.rstrip('\'')\r
1208 return True\r
1209\r
1210 else:\r
1211 return False\r
1212\r
1213 ## __SkipToToken() method\r
1214 #\r
1215 # Search forward in file buffer for the string\r
1216 # The skipped chars are put into self.__SkippedChars\r
1217 #\r
1218 # @param self The object pointer\r
1219 # @param String The string to search\r
1220 # @param IgnoreCase Indicate case sensitive/non-sensitive search, default is case sensitive\r
1221 # @retval True Successfully find the string, file buffer pointer moved forward\r
1222 # @retval False Not able to find the string, file buffer pointer not changed\r
1223 #\r
1224 def __SkipToToken(self, String, IgnoreCase = False):\r
1225 StartPos = self.GetFileBufferPos()\r
1226\r
1227 self.__SkippedChars = ""\r
1228 while not self.__EndOfFile():\r
1229 index = -1\r
1230 if IgnoreCase:\r
1231 index = self.__CurrentLine()[self.CurrentOffsetWithinLine : ].upper().find(String.upper())\r
1232 else:\r
1233 index = self.__CurrentLine()[self.CurrentOffsetWithinLine : ].find(String)\r
1234 if index == 0:\r
1235 self.CurrentOffsetWithinLine += len(String)\r
1236 self.__SkippedChars += String\r
1237 return True\r
1238 self.__SkippedChars += str(self.__CurrentChar())\r
1239 self.__GetOneChar()\r
1240\r
1241 self.SetFileBufferPos( StartPos)\r
1242 self.__SkippedChars = ""\r
1243 return False\r
1244\r
1245 ## GetFileBufferPos() method\r
1246 #\r
1247 # Return the tuple of current line and offset within the line\r
1248 #\r
1249 # @param self The object pointer\r
1250 # @retval Tuple Line number and offset pair\r
1251 #\r
1252 def GetFileBufferPos(self):\r
1253 return (self.CurrentLineNumber, self.CurrentOffsetWithinLine)\r
1254\r
1255 ## SetFileBufferPos() method\r
1256 #\r
1257 # Restore the file buffer position\r
1258 #\r
1259 # @param self The object pointer\r
1260 # @param Pos The new file buffer position\r
1261 #\r
1262 def SetFileBufferPos(self, Pos):\r
1263 (self.CurrentLineNumber, self.CurrentOffsetWithinLine) = Pos\r
1264\r
d40b2ee6
LG
1265 ## Preprocess() method\r
1266 #\r
1267 # Preprocess comment, conditional directive, include directive, replace macro.\r
1268 # Exception will be raised if syntax error found\r
1269 #\r
1270 # @param self The object pointer\r
1271 #\r
1272 def Preprocess(self):\r
1273 self.__StringToList()\r
1274 self.PreprocessFile()\r
1275 self.PreprocessIncludeFile()\r
1276 self.__StringToList()\r
1277 self.PreprocessFile()\r
1278 self.PreprocessConditionalStatement()\r
1279 self.__StringToList()\r
1280 for Pos in self.__WipeOffArea:\r
1281 self.__ReplaceFragment(Pos[0], Pos[1])\r
1282 self.Profile.FileLinesList = ["".join(list) for list in self.Profile.FileLinesList]\r
1283\r
1284 while self.__GetDefines():\r
1285 pass\r
d40b2ee6 1286\r
30fdf114
LG
1287 ## ParseFile() method\r
1288 #\r
1289 # Parse the file profile buffer to extract fd, fv ... information\r
1290 # Exception will be raised if syntax error found\r
1291 #\r
1292 # @param self The object pointer\r
1293 #\r
1294 def ParseFile(self):\r
1295\r
1296 try:\r
d40b2ee6 1297 self.Preprocess()\r
30fdf114
LG
1298 while self.__GetFd():\r
1299 pass\r
1300\r
1301 while self.__GetFv():\r
1302 pass\r
1303\r
1304 while self.__GetCapsule():\r
1305 pass\r
1306\r
1307 while self.__GetVtf():\r
1308 pass\r
1309\r
1310 while self.__GetRule():\r
1311 pass\r
1312 \r
1313 while self.__GetOptionRom():\r
1314 pass\r
1315\r
1316 except Warning, X:\r
1317 self.__UndoToken()\r
1318 FileLineTuple = GetRealFileLine(self.FileName, self.CurrentLineNumber)\r
1319 #'\n\tGot Token: \"%s\" from File %s\n' % (self.__Token, FileLineTuple[0]) + \\r
1320 X.Message += ' near line %d, column %d: %s' \\r
1321 % (FileLineTuple[1], self.CurrentOffsetWithinLine + 1, self.Profile.FileLinesList[self.CurrentLineNumber - 1][self.CurrentOffsetWithinLine :].rstrip('\n').rstrip('\r'))\r
1322 raise\r
1323\r
1324 ## __GetDefines() method\r
1325 #\r
1326 # Get Defines section contents and store its data into AllMacrosList\r
1327 #\r
1328 # @param self The object pointer\r
1329 # @retval True Successfully find a Defines\r
1330 # @retval False Not able to find a Defines\r
1331 #\r
1332 def __GetDefines(self):\r
1333\r
1334 if not self.__GetNextToken():\r
1335 return False\r
1336\r
1337 S = self.__Token.upper()\r
1338 if S.startswith("[") and not S.startswith("[DEFINES"):\r
1339 if not S.startswith("[FD.") and not S.startswith("[FV.") and not S.startswith("[CAPSULE.") \\r
1340 and not S.startswith("[VTF.") and not S.startswith("[RULE.") and not S.startswith("[OPTIONROM."):\r
1341 raise Warning("Unknown section or section appear sequence error (The correct sequence should be [DEFINES], [FD.], [FV.], [Capsule.], [VTF.], [Rule.], [OptionRom.])", self.FileName, self.CurrentLineNumber)\r
1342 self.__UndoToken()\r
1343 return False\r
1344\r
1345 self.__UndoToken()\r
1346 if not self.__IsToken("[DEFINES", True):\r
1347 FileLineTuple = GetRealFileLine(self.FileName, self.CurrentLineNumber)\r
1348 #print 'Parsing String: %s in File %s, At line: %d, Offset Within Line: %d' \\r
1349 # % (self.Profile.FileLinesList[self.CurrentLineNumber - 1][self.CurrentOffsetWithinLine :], FileLineTuple[0], FileLineTuple[1], self.CurrentOffsetWithinLine)\r
1350 raise Warning("expected [DEFINES", self.FileName, self.CurrentLineNumber)\r
1351\r
1352 if not self.__IsToken( "]"):\r
1353 raise Warning("expected ']'", self.FileName, self.CurrentLineNumber)\r
1354\r
1355 while self.__GetNextWord():\r
6780eef1
LG
1356 # handle the SET statement\r
1357 if self.__Token == 'SET':\r
1358 self.__UndoToken()\r
1359 self.__GetSetStatement(None)\r
1360 continue\r
1361 \r
30fdf114
LG
1362 Macro = self.__Token\r
1363 \r
1364 if not self.__IsToken("="):\r
1365 raise Warning("expected '='", self.FileName, self.CurrentLineNumber)\r
1366 if not self.__GetNextToken() or self.__Token.startswith('['):\r
1367 raise Warning("expected MACRO value", self.FileName, self.CurrentLineNumber)\r
1368 Value = self.__Token\r
30fdf114
LG
1369\r
1370 return False\r
1371\r
1372 ## __GetFd() method\r
1373 #\r
1374 # Get FD section contents and store its data into FD dictionary of self.Profile\r
1375 #\r
1376 # @param self The object pointer\r
1377 # @retval True Successfully find a FD\r
1378 # @retval False Not able to find a FD\r
1379 #\r
1380 def __GetFd(self):\r
1381\r
1382 if not self.__GetNextToken():\r
1383 return False\r
1384\r
1385 S = self.__Token.upper()\r
1386 if S.startswith("[") and not S.startswith("[FD."):\r
1387 if not S.startswith("[FV.") and not S.startswith("[CAPSULE.") \\r
1388 and not S.startswith("[VTF.") and not S.startswith("[RULE.") and not S.startswith("[OPTIONROM."):\r
1389 raise Warning("Unknown section", self.FileName, self.CurrentLineNumber)\r
1390 self.__UndoToken()\r
1391 return False\r
1392\r
1393 self.__UndoToken()\r
1394 if not self.__IsToken("[FD.", True):\r
1395 FileLineTuple = GetRealFileLine(self.FileName, self.CurrentLineNumber)\r
1396 #print 'Parsing String: %s in File %s, At line: %d, Offset Within Line: %d' \\r
1397 # % (self.Profile.FileLinesList[self.CurrentLineNumber - 1][self.CurrentOffsetWithinLine :], FileLineTuple[0], FileLineTuple[1], self.CurrentOffsetWithinLine)\r
1398 raise Warning("expected [FD.]", self.FileName, self.CurrentLineNumber)\r
1399\r
1400 FdName = self.__GetUiName()\r
52302d4d
LG
1401 if FdName == "":\r
1402 if len (self.Profile.FdDict) == 0:\r
1403 FdName = GenFdsGlobalVariable.PlatformName\r
d0acc87a
LG
1404 if FdName == "" and GlobalData.gActivePlatform:\r
1405 FdName = GlobalData.gActivePlatform.PlatformName\r
52302d4d
LG
1406 self.Profile.FdNameNotSet = True\r
1407 else:\r
1408 raise Warning("expected FdName in [FD.] section", self.FileName, self.CurrentLineNumber)\r
30fdf114 1409 self.CurrentFdName = FdName.upper()\r
52302d4d
LG
1410 \r
1411 if self.CurrentFdName in self.Profile.FdDict:\r
1412 raise Warning("Unexpected the same FD name", self.FileName, self.CurrentLineNumber)\r
30fdf114
LG
1413\r
1414 if not self.__IsToken( "]"):\r
1415 raise Warning("expected ']'", self.FileName, self.CurrentLineNumber)\r
1416\r
1417 FdObj = Fd.FD()\r
1418 FdObj.FdUiName = self.CurrentFdName\r
1419 self.Profile.FdDict[self.CurrentFdName] = FdObj\r
52302d4d
LG
1420\r
1421 if len (self.Profile.FdDict) > 1 and self.Profile.FdNameNotSet:\r
1422 raise Warning("expected all FDs have their name", self.FileName, self.CurrentLineNumber)\r
1423\r
30fdf114
LG
1424 Status = self.__GetCreateFile(FdObj)\r
1425 if not Status:\r
1426 raise Warning("FD name error", self.FileName, self.CurrentLineNumber)\r
1427\r
e8a47801
LG
1428 while self.__GetTokenStatements(FdObj):\r
1429 pass\r
1430 for Attr in ("BaseAddress", "Size", "ErasePolarity"):\r
1431 if getattr(FdObj, Attr) == None:\r
1432 self.__GetNextToken()\r
1433 raise Warning("Keyword %s missing" % Attr, self.FileName, self.CurrentLineNumber)\r
1434\r
1435 if not FdObj.BlockSizeList:\r
1436 FdObj.BlockSizeList.append((1, FdObj.Size, None))\r
30fdf114
LG
1437\r
1438 self.__GetDefineStatements(FdObj)\r
1439\r
1440 self.__GetSetStatements(FdObj)\r
1441\r
1442 if not self.__GetRegionLayout(FdObj):\r
1443 raise Warning("expected region layout", self.FileName, self.CurrentLineNumber)\r
1444\r
1445 while self.__GetRegionLayout(FdObj):\r
1446 pass\r
1447 return True\r
1448\r
1449 ## __GetUiName() method\r
1450 #\r
1451 # Return the UI name of a section\r
1452 #\r
1453 # @param self The object pointer\r
1454 # @retval FdName UI name\r
1455 #\r
1456 def __GetUiName(self):\r
1457 Name = ""\r
1458 if self.__GetNextWord():\r
1459 Name = self.__Token\r
1460\r
1461 return Name\r
1462\r
1463 ## __GetCreateFile() method\r
1464 #\r
1465 # Return the output file name of object\r
1466 #\r
1467 # @param self The object pointer\r
1468 # @param Obj object whose data will be stored in file\r
1469 # @retval FdName UI name\r
1470 #\r
1471 def __GetCreateFile(self, Obj):\r
1472\r
1473 if self.__IsKeyword( "CREATE_FILE"):\r
1474 if not self.__IsToken( "="):\r
1475 raise Warning("expected '='", self.FileName, self.CurrentLineNumber)\r
1476\r
1477 if not self.__GetNextToken():\r
1478 raise Warning("expected file name", self.FileName, self.CurrentLineNumber)\r
1479\r
1480 FileName = self.__Token\r
1481 Obj.CreateFileName = FileName\r
1482\r
1483 return True\r
1484\r
1485 ## __GetTokenStatements() method\r
1486 #\r
1487 # Get token statements\r
1488 #\r
1489 # @param self The object pointer\r
1490 # @param Obj for whom token statement is got\r
30fdf114
LG
1491 #\r
1492 def __GetTokenStatements(self, Obj):\r
e8a47801
LG
1493 if self.__IsKeyword( "BaseAddress"):\r
1494 if not self.__IsToken( "="):\r
1495 raise Warning("expected '='", self.FileName, self.CurrentLineNumber)\r
1496 \r
1497 if not self.__GetNextHexNumber():\r
1498 raise Warning("expected Hex base address", self.FileName, self.CurrentLineNumber)\r
1499 \r
1500 Obj.BaseAddress = self.__Token\r
1501 \r
1502 if self.__IsToken( "|"):\r
1503 pcdPair = self.__GetNextPcdName()\r
1504 Obj.BaseAddressPcd = pcdPair\r
1505 self.Profile.PcdDict[pcdPair] = Obj.BaseAddress\r
1506 FileLineTuple = GetRealFileLine(self.FileName, self.CurrentLineNumber)\r
1507 self.Profile.PcdFileLineDict[pcdPair] = FileLineTuple\r
1508 return True\r
30fdf114 1509\r
e8a47801
LG
1510 if self.__IsKeyword( "Size"):\r
1511 if not self.__IsToken( "="):\r
1512 raise Warning("expected '='", self.FileName, self.CurrentLineNumber)\r
1513 \r
1514 if not self.__GetNextHexNumber():\r
1515 raise Warning("expected Hex size", self.FileName, self.CurrentLineNumber)\r
30fdf114 1516\r
e8a47801
LG
1517 Size = self.__Token\r
1518 if self.__IsToken( "|"):\r
1519 pcdPair = self.__GetNextPcdName()\r
1520 Obj.SizePcd = pcdPair\r
1521 self.Profile.PcdDict[pcdPair] = Size\r
1522 FileLineTuple = GetRealFileLine(self.FileName, self.CurrentLineNumber)\r
1523 self.Profile.PcdFileLineDict[pcdPair] = FileLineTuple\r
1524 Obj.Size = long(Size, 0)\r
1525 return True\r
30fdf114 1526\r
e8a47801
LG
1527 if self.__IsKeyword( "ErasePolarity"):\r
1528 if not self.__IsToken( "="):\r
1529 raise Warning("expected '='", self.FileName, self.CurrentLineNumber)\r
1530 \r
1531 if not self.__GetNextToken():\r
1532 raise Warning("expected Erase Polarity", self.FileName, self.CurrentLineNumber)\r
1533 \r
1534 if self.__Token != "1" and self.__Token != "0":\r
1535 raise Warning("expected 1 or 0 Erase Polarity", self.FileName, self.CurrentLineNumber)\r
1536 \r
1537 Obj.ErasePolarity = self.__Token\r
1538 return True\r
30fdf114 1539\r
e8a47801 1540 return self.__GetBlockStatements(Obj)\r
30fdf114
LG
1541\r
1542 ## __GetAddressStatements() method\r
1543 #\r
1544 # Get address statements\r
1545 #\r
1546 # @param self The object pointer\r
1547 # @param Obj for whom address statement is got\r
1548 # @retval True Successfully find\r
1549 # @retval False Not able to find\r
1550 #\r
1551 def __GetAddressStatements(self, Obj):\r
1552\r
1553 if self.__IsKeyword("BsBaseAddress"):\r
1554 if not self.__IsToken( "="):\r
1555 raise Warning("expected '='", self.FileName, self.CurrentLineNumber)\r
1556\r
1557 if not self.__GetNextDecimalNumber() and not self.__GetNextHexNumber():\r
1558 raise Warning("expected address", self.FileName, self.CurrentLineNumber)\r
1559\r
1560 BsAddress = long(self.__Token, 0)\r
1561 Obj.BsBaseAddress = BsAddress\r
1562\r
1563 if self.__IsKeyword("RtBaseAddress"):\r
1564 if not self.__IsToken( "="):\r
1565 raise Warning("expected '='", self.FileName, self.CurrentLineNumber)\r
1566\r
1567 if not self.__GetNextDecimalNumber() and not self.__GetNextHexNumber():\r
1568 raise Warning("expected address", self.FileName, self.CurrentLineNumber)\r
1569\r
1570 RtAddress = long(self.__Token, 0)\r
1571 Obj.RtBaseAddress = RtAddress\r
1572\r
1573 ## __GetBlockStatements() method\r
1574 #\r
1575 # Get block statements\r
1576 #\r
1577 # @param self The object pointer\r
1578 # @param Obj for whom block statement is got\r
30fdf114
LG
1579 #\r
1580 def __GetBlockStatements(self, Obj):\r
e8a47801 1581 IsBlock = False\r
30fdf114 1582 while self.__GetBlockStatement(Obj):\r
e8a47801 1583 IsBlock = True\r
52302d4d 1584 \r
e8a47801 1585 Item = Obj.BlockSizeList[-1]\r
52302d4d 1586 if Item[0] == None or Item[1] == None:\r
6780eef1 1587 raise Warning("expected block statement", self.FileName, self.CurrentLineNumber)\r
e8a47801 1588 return IsBlock\r
30fdf114
LG
1589\r
1590 ## __GetBlockStatement() method\r
1591 #\r
1592 # Get block statement\r
1593 #\r
1594 # @param self The object pointer\r
1595 # @param Obj for whom block statement is got\r
1596 # @retval True Successfully find\r
1597 # @retval False Not able to find\r
1598 #\r
1599 def __GetBlockStatement(self, Obj):\r
1600 if not self.__IsKeyword( "BlockSize"):\r
1601 return False\r
1602\r
1603 if not self.__IsToken( "="):\r
1604 raise Warning("expected '='", self.FileName, self.CurrentLineNumber)\r
1605\r
1606 if not self.__GetNextHexNumber() and not self.__GetNextDecimalNumber():\r
6780eef1 1607 raise Warning("expected Hex or Integer block size", self.FileName, self.CurrentLineNumber)\r
30fdf114
LG
1608\r
1609 BlockSize = self.__Token\r
1610 BlockSizePcd = None\r
1611 if self.__IsToken( "|"):\r
1612 PcdPair = self.__GetNextPcdName()\r
1613 BlockSizePcd = PcdPair\r
1614 self.Profile.PcdDict[PcdPair] = BlockSize\r
d0acc87a
LG
1615 FileLineTuple = GetRealFileLine(self.FileName, self.CurrentLineNumber)\r
1616 self.Profile.PcdFileLineDict[PcdPair] = FileLineTuple\r
52302d4d 1617 BlockSize = long(BlockSize, 0)\r
30fdf114
LG
1618\r
1619 BlockNumber = None\r
1620 if self.__IsKeyword( "NumBlocks"):\r
1621 if not self.__IsToken( "="):\r
1622 raise Warning("expected '='", self.FileName, self.CurrentLineNumber)\r
1623\r
1624 if not self.__GetNextDecimalNumber() and not self.__GetNextHexNumber():\r
1625 raise Warning("expected block numbers", self.FileName, self.CurrentLineNumber)\r
1626\r
1627 BlockNumber = long(self.__Token, 0)\r
1628\r
1629 Obj.BlockSizeList.append((BlockSize, BlockNumber, BlockSizePcd))\r
1630 return True\r
1631\r
1632 ## __GetDefineStatements() method\r
1633 #\r
1634 # Get define statements\r
1635 #\r
1636 # @param self The object pointer\r
1637 # @param Obj for whom define statement is got\r
1638 # @retval True Successfully find\r
1639 # @retval False Not able to find\r
1640 #\r
1641 def __GetDefineStatements(self, Obj):\r
1642 while self.__GetDefineStatement( Obj):\r
1643 pass\r
1644\r
1645 ## __GetDefineStatement() method\r
1646 #\r
1647 # Get define statement\r
1648 #\r
1649 # @param self The object pointer\r
1650 # @param Obj for whom define statement is got\r
1651 # @retval True Successfully find\r
1652 # @retval False Not able to find\r
1653 #\r
1654 def __GetDefineStatement(self, Obj):\r
1655 if self.__IsKeyword("DEFINE"):\r
1656 self.__GetNextToken()\r
1657 Macro = self.__Token\r
1658 if not self.__IsToken( "="):\r
1659 raise Warning("expected '='", self.FileName, self.CurrentLineNumber)\r
1660\r
1661 if not self.__GetNextToken():\r
1662 raise Warning("expected value", self.FileName, self.CurrentLineNumber)\r
1663\r
1664 Value = self.__Token\r
1665 Macro = '$(' + Macro + ')'\r
1666 Obj.DefineVarDict[Macro] = Value\r
1667 return True\r
1668\r
1669 return False\r
1670\r
1671 ## __GetSetStatements() method\r
1672 #\r
1673 # Get set statements\r
1674 #\r
1675 # @param self The object pointer\r
1676 # @param Obj for whom set statement is got\r
1677 # @retval True Successfully find\r
1678 # @retval False Not able to find\r
1679 #\r
1680 def __GetSetStatements(self, Obj):\r
1681 while self.__GetSetStatement(Obj):\r
1682 pass\r
1683\r
1684 ## __GetSetStatement() method\r
1685 #\r
1686 # Get set statement\r
1687 #\r
1688 # @param self The object pointer\r
1689 # @param Obj for whom set statement is got\r
1690 # @retval True Successfully find\r
1691 # @retval False Not able to find\r
1692 #\r
1693 def __GetSetStatement(self, Obj):\r
1694 if self.__IsKeyword("SET"):\r
1695 PcdPair = self.__GetNextPcdName()\r
1696\r
1697 if not self.__IsToken( "="):\r
1698 raise Warning("expected '='", self.FileName, self.CurrentLineNumber)\r
1699\r
d0acc87a
LG
1700 Value = self.__GetExpression()\r
1701 Value = self.__EvaluateConditional(Value, self.CurrentLineNumber, 'eval', True)\r
30fdf114 1702\r
6780eef1
LG
1703 if Obj:\r
1704 Obj.SetVarDict[PcdPair] = Value\r
30fdf114 1705 self.Profile.PcdDict[PcdPair] = Value\r
d0acc87a
LG
1706 FileLineTuple = GetRealFileLine(self.FileName, self.CurrentLineNumber)\r
1707 self.Profile.PcdFileLineDict[PcdPair] = FileLineTuple\r
30fdf114
LG
1708 return True\r
1709\r
1710 return False\r
1711\r
4afd3d04
LG
1712 ## __CalcRegionExpr(self)\r
1713 #\r
1714 # Calculate expression for offset or size of a region\r
1715 #\r
1716 # @return: None if invalid expression\r
1717 # Calculated number if successfully\r
1718 #\r
1719 def __CalcRegionExpr(self):\r
1720 StartPos = self.GetFileBufferPos()\r
1721 Expr = ''\r
1722 PairCount = 0\r
1723 while not self.__EndOfFile():\r
1724 CurCh = self.__CurrentChar()\r
1725 if CurCh == '(':\r
1726 PairCount += 1\r
1727 elif CurCh == ')':\r
1728 PairCount -= 1\r
1729\r
1730 if CurCh in '|\r\n' and PairCount == 0:\r
1731 break\r
1732 Expr += CurCh\r
1733 self.__GetOneChar()\r
1734 try:\r
1735 return long(\r
1736 ValueExpression(Expr,\r
2bc3256c 1737 self.__CollectMacroPcd()\r
4afd3d04
LG
1738 )(True),0)\r
1739 except Exception:\r
1740 self.SetFileBufferPos(StartPos)\r
1741 return None\r
1742\r
30fdf114
LG
1743 ## __GetRegionLayout() method\r
1744 #\r
1745 # Get region layout for FD\r
1746 #\r
1747 # @param self The object pointer\r
1748 # @param Fd for whom region is got\r
1749 # @retval True Successfully find\r
1750 # @retval False Not able to find\r
1751 #\r
1752 def __GetRegionLayout(self, Fd):\r
4afd3d04
LG
1753 Offset = self.__CalcRegionExpr() \r
1754 if Offset == None:\r
30fdf114
LG
1755 return False\r
1756\r
1757 RegionObj = Region.Region()\r
4afd3d04 1758 RegionObj.Offset = Offset\r
30fdf114
LG
1759 Fd.RegionList.append(RegionObj)\r
1760\r
1761 if not self.__IsToken( "|"):\r
1762 raise Warning("expected '|'", self.FileName, self.CurrentLineNumber)\r
1763\r
4afd3d04
LG
1764 Size = self.__CalcRegionExpr()\r
1765 if Size == None:\r
30fdf114 1766 raise Warning("expected Region Size", self.FileName, self.CurrentLineNumber)\r
4afd3d04 1767 RegionObj.Size = Size\r
30fdf114
LG
1768\r
1769 if not self.__GetNextWord():\r
1770 return True\r
1771\r
fd171542 1772 if not self.__Token in ("SET", "FV", "FILE", "DATA", "CAPSULE"):\r
2bc3256c
LG
1773 #\r
1774 # If next token is a word which is not a valid FV type, it might be part of [PcdOffset[|PcdSize]]\r
1775 # Or it might be next region's offset described by an expression which starts with a PCD.\r
1776 # PcdOffset[|PcdSize] or OffsetPcdExpression|Size\r
1777 #\r
30fdf114 1778 self.__UndoToken()\r
2bc3256c
LG
1779 IsRegionPcd = (RegionSizeGuidPattern.match(self.__CurrentLine()[self.CurrentOffsetWithinLine:]) or\r
1780 RegionOffsetPcdPattern.match(self.__CurrentLine()[self.CurrentOffsetWithinLine:]))\r
1781 if IsRegionPcd:\r
1782 RegionObj.PcdOffset = self.__GetNextPcdName()\r
1783 self.Profile.PcdDict[RegionObj.PcdOffset] = "0x%08X" % (RegionObj.Offset + long(Fd.BaseAddress, 0))\r
1784 self.__PcdDict['%s.%s' % (RegionObj.PcdOffset[1], RegionObj.PcdOffset[0])] = "0x%x" % RegionObj.Offset\r
d0acc87a 1785 FileLineTuple = GetRealFileLine(self.FileName, self.CurrentLineNumber)\r
2bc3256c
LG
1786 self.Profile.PcdFileLineDict[RegionObj.PcdOffset] = FileLineTuple\r
1787 if self.__IsToken( "|"):\r
1788 RegionObj.PcdSize = self.__GetNextPcdName()\r
1789 self.Profile.PcdDict[RegionObj.PcdSize] = "0x%08X" % RegionObj.Size\r
1790 self.__PcdDict['%s.%s' % (RegionObj.PcdSize[1], RegionObj.PcdSize[0])] = "0x%x" % RegionObj.Size\r
1791 FileLineTuple = GetRealFileLine(self.FileName, self.CurrentLineNumber)\r
1792 self.Profile.PcdFileLineDict[RegionObj.PcdSize] = FileLineTuple\r
30fdf114
LG
1793\r
1794 if not self.__GetNextWord():\r
1795 return True\r
1796\r
1797 if self.__Token == "SET":\r
1798 self.__UndoToken()\r
1799 self.__GetSetStatements( RegionObj)\r
1800 if not self.__GetNextWord():\r
1801 return True\r
1802\r
fd171542 1803 elif self.__Token == "FV":\r
30fdf114
LG
1804 self.__UndoToken()\r
1805 self.__GetRegionFvType( RegionObj)\r
1806\r
fd171542 1807 elif self.__Token == "CAPSULE":\r
1808 self.__UndoToken()\r
1809 self.__GetRegionCapType( RegionObj)\r
1810\r
30fdf114
LG
1811 elif self.__Token == "FILE":\r
1812 self.__UndoToken()\r
1813 self.__GetRegionFileType( RegionObj)\r
1814\r
79b74a03 1815 elif self.__Token == "DATA":\r
30fdf114
LG
1816 self.__UndoToken()\r
1817 self.__GetRegionDataType( RegionObj)\r
79b74a03 1818 else:\r
2bc3256c
LG
1819 self.__UndoToken()\r
1820 if self.__GetRegionLayout(Fd):\r
1821 return True\r
79b74a03
LG
1822 raise Warning("A valid region type was not found. "\r
1823 "Valid types are [SET, FV, CAPSULE, FILE, DATA]. This error occurred",\r
1824 self.FileName, self.CurrentLineNumber)\r
30fdf114
LG
1825\r
1826 return True\r
1827\r
1828 ## __GetRegionFvType() method\r
1829 #\r
1830 # Get region fv data for region\r
1831 #\r
1832 # @param self The object pointer\r
1833 # @param RegionObj for whom region data is got\r
1834 #\r
1835 def __GetRegionFvType(self, RegionObj):\r
1836\r
1837 if not self.__IsKeyword( "FV"):\r
1838 raise Warning("expected Keyword 'FV'", self.FileName, self.CurrentLineNumber)\r
1839\r
1840 if not self.__IsToken( "="):\r
1841 raise Warning("expected '='", self.FileName, self.CurrentLineNumber)\r
1842\r
1843 if not self.__GetNextToken():\r
1844 raise Warning("expected FV name", self.FileName, self.CurrentLineNumber)\r
1845\r
1846 RegionObj.RegionType = "FV"\r
1847 RegionObj.RegionDataList.append(self.__Token)\r
1848\r
1849 while self.__IsKeyword( "FV"):\r
1850\r
1851 if not self.__IsToken( "="):\r
1852 raise Warning("expected '='", self.FileName, self.CurrentLineNumber)\r
1853\r
1854 if not self.__GetNextToken():\r
1855 raise Warning("expected FV name", self.FileName, self.CurrentLineNumber)\r
1856\r
1857 RegionObj.RegionDataList.append(self.__Token)\r
1858\r
fd171542 1859 ## __GetRegionCapType() method\r
1860 #\r
1861 # Get region capsule data for region\r
1862 #\r
1863 # @param self The object pointer\r
1864 # @param RegionObj for whom region data is got\r
1865 #\r
1866 def __GetRegionCapType(self, RegionObj):\r
1867\r
1868 if not self.__IsKeyword("CAPSULE"):\r
1869 raise Warning("expected Keyword 'CAPSULE'", self.FileName, self.CurrentLineNumber)\r
1870\r
1871 if not self.__IsToken("="):\r
1872 raise Warning("expected '='", self.FileName, self.CurrentLineNumber)\r
1873\r
1874 if not self.__GetNextToken():\r
1875 raise Warning("expected CAPSULE name", self.FileName, self.CurrentLineNumber)\r
1876\r
1877 RegionObj.RegionType = "CAPSULE"\r
1878 RegionObj.RegionDataList.append(self.__Token)\r
1879\r
1880 while self.__IsKeyword("CAPSULE"):\r
1881\r
1882 if not self.__IsToken("="):\r
1883 raise Warning("expected '='", self.FileName, self.CurrentLineNumber)\r
1884\r
1885 if not self.__GetNextToken():\r
1886 raise Warning("expected CAPSULE name", self.FileName, self.CurrentLineNumber)\r
1887\r
1888 RegionObj.RegionDataList.append(self.__Token)\r
1889\r
30fdf114
LG
1890 ## __GetRegionFileType() method\r
1891 #\r
1892 # Get region file data for region\r
1893 #\r
1894 # @param self The object pointer\r
1895 # @param RegionObj for whom region data is got\r
1896 #\r
1897 def __GetRegionFileType(self, RegionObj):\r
1898\r
1899 if not self.__IsKeyword( "FILE"):\r
1900 raise Warning("expected Keyword 'FILE'", self.FileName, self.CurrentLineNumber)\r
1901\r
1902 if not self.__IsToken( "="):\r
1903 raise Warning("expected '='", self.FileName, self.CurrentLineNumber)\r
1904\r
1905 if not self.__GetNextToken():\r
1906 raise Warning("expected File name", self.FileName, self.CurrentLineNumber)\r
1907\r
1908 RegionObj.RegionType = "FILE"\r
1909 RegionObj.RegionDataList.append( self.__Token)\r
1910\r
1911 while self.__IsKeyword( "FILE"):\r
1912\r
1913 if not self.__IsToken( "="):\r
1914 raise Warning("expected '='", self.FileName, self.CurrentLineNumber)\r
1915\r
1916 if not self.__GetNextToken():\r
1917 raise Warning("expected FILE name", self.FileName, self.CurrentLineNumber)\r
1918\r
1919 RegionObj.RegionDataList.append(self.__Token)\r
1920\r
1921 ## __GetRegionDataType() method\r
1922 #\r
1923 # Get region array data for region\r
1924 #\r
1925 # @param self The object pointer\r
1926 # @param RegionObj for whom region data is got\r
1927 #\r
1928 def __GetRegionDataType(self, RegionObj):\r
1929\r
1930 if not self.__IsKeyword( "DATA"):\r
1931 raise Warning("expected Region Data type", self.FileName, self.CurrentLineNumber)\r
1932\r
1933 if not self.__IsToken( "="):\r
1934 raise Warning("expected '='", self.FileName, self.CurrentLineNumber)\r
1935\r
1936 if not self.__IsToken( "{"):\r
1937 raise Warning("expected '{'", self.FileName, self.CurrentLineNumber)\r
1938\r
1939 if not self.__GetNextHexNumber():\r
1940 raise Warning("expected Hex byte", self.FileName, self.CurrentLineNumber)\r
1941\r
636f2be6
LG
1942 if len(self.__Token) > 18:\r
1943 raise Warning("Hex string can't be converted to a valid UINT64 value", self.FileName, self.CurrentLineNumber)\r
1944\r
1945 # convert hex string value to byte hex string array\r
1946 AllString = self.__Token\r
1947 AllStrLen = len (AllString)\r
1948 DataString = ""\r
1949 while AllStrLen > 4:\r
1950 DataString = DataString + "0x" + AllString[AllStrLen - 2: AllStrLen] + ","\r
1951 AllStrLen = AllStrLen - 2\r
1952 DataString = DataString + AllString[:AllStrLen] + ","\r
1953\r
1954 # byte value array\r
1955 if len (self.__Token) <= 4:\r
1956 while self.__IsToken(","):\r
1957 if not self.__GetNextHexNumber():\r
1958 raise Warning("Invalid Hex number", self.FileName, self.CurrentLineNumber)\r
1959 if len(self.__Token) > 4:\r
1960 raise Warning("Hex byte(must be 2 digits) too long", self.FileName, self.CurrentLineNumber)\r
1961 DataString += self.__Token\r
1962 DataString += ","\r
30fdf114
LG
1963\r
1964 if not self.__IsToken( "}"):\r
1965 raise Warning("expected '}'", self.FileName, self.CurrentLineNumber)\r
1966\r
1967 DataString = DataString.rstrip(",")\r
1968 RegionObj.RegionType = "DATA"\r
1969 RegionObj.RegionDataList.append( DataString)\r
1970\r
1971 while self.__IsKeyword( "DATA"):\r
1972\r
1973 if not self.__IsToken( "="):\r
1974 raise Warning("expected '='", self.FileName, self.CurrentLineNumber)\r
1975\r
1976 if not self.__IsToken( "{"):\r
1977 raise Warning("expected '{'", self.FileName, self.CurrentLineNumber)\r
1978\r
1979 if not self.__GetNextHexNumber():\r
1980 raise Warning("expected Hex byte", self.FileName, self.CurrentLineNumber)\r
1981\r
636f2be6
LG
1982 if len(self.__Token) > 18:\r
1983 raise Warning("Hex string can't be converted to a valid UINT64 value", self.FileName, self.CurrentLineNumber)\r
1984\r
1985 # convert hex string value to byte hex string array\r
1986 AllString = self.__Token\r
1987 AllStrLen = len (AllString)\r
1988 DataString = ""\r
1989 while AllStrLen > 4:\r
1990 DataString = DataString + "0x" + AllString[AllStrLen - 2: AllStrLen] + ","\r
1991 AllStrLen = AllStrLen - 2\r
1992 DataString = DataString + AllString[:AllStrLen] + ","\r
1993\r
1994 # byte value array\r
1995 if len (self.__Token) <= 4:\r
1996 while self.__IsToken(","):\r
1997 if not self.__GetNextHexNumber():\r
1998 raise Warning("Invalid Hex number", self.FileName, self.CurrentLineNumber)\r
1999 if len(self.__Token) > 4:\r
2000 raise Warning("Hex byte(must be 2 digits) too long", self.FileName, self.CurrentLineNumber)\r
2001 DataString += self.__Token\r
2002 DataString += ","\r
30fdf114
LG
2003\r
2004 if not self.__IsToken( "}"):\r
2005 raise Warning("expected '}'", self.FileName, self.CurrentLineNumber)\r
2006\r
2007 DataString = DataString.rstrip(",")\r
2008 RegionObj.RegionDataList.append( DataString)\r
2009\r
2010 ## __GetFv() method\r
2011 #\r
2012 # Get FV section contents and store its data into FV dictionary of self.Profile\r
2013 #\r
2014 # @param self The object pointer\r
2015 # @retval True Successfully find a FV\r
2016 # @retval False Not able to find a FV\r
2017 #\r
2018 def __GetFv(self):\r
2019 if not self.__GetNextToken():\r
2020 return False\r
2021\r
2022 S = self.__Token.upper()\r
2023 if S.startswith("[") and not S.startswith("[FV."):\r
2024 if not S.startswith("[CAPSULE.") \\r
2025 and not S.startswith("[VTF.") and not S.startswith("[RULE.") and not S.startswith("[OPTIONROM."):\r
2026 raise Warning("Unknown section or section appear sequence error (The correct sequence should be [FD.], [FV.], [Capsule.], [VTF.], [Rule.], [OptionRom.])", self.FileName, self.CurrentLineNumber)\r
2027 self.__UndoToken()\r
2028 return False\r
2029\r
2030 self.__UndoToken()\r
2031 if not self.__IsToken("[FV.", True):\r
2032 FileLineTuple = GetRealFileLine(self.FileName, self.CurrentLineNumber)\r
2033 #print 'Parsing String: %s in File %s, At line: %d, Offset Within Line: %d' \\r
2034 # % (self.Profile.FileLinesList[self.CurrentLineNumber - 1][self.CurrentOffsetWithinLine :], FileLineTuple[0], FileLineTuple[1], self.CurrentOffsetWithinLine)\r
2035 raise Warning("Unknown Keyword '%s'" % self.__Token, self.FileName, self.CurrentLineNumber)\r
2036\r
2037 FvName = self.__GetUiName()\r
2038 self.CurrentFvName = FvName.upper()\r
2039\r
2040 if not self.__IsToken( "]"):\r
2041 raise Warning("expected ']'", self.FileName, self.CurrentLineNumber)\r
2042\r
2043 FvObj = Fv.FV()\r
2044 FvObj.UiFvName = self.CurrentFvName\r
2045 self.Profile.FvDict[self.CurrentFvName] = FvObj\r
2046\r
2047 Status = self.__GetCreateFile(FvObj)\r
2048 if not Status:\r
2049 raise Warning("FV name error", self.FileName, self.CurrentLineNumber)\r
2050\r
2051 self.__GetDefineStatements(FvObj)\r
2052\r
2053 self.__GetAddressStatements(FvObj)\r
2054\r
b303ea72
LG
2055 FvObj.FvExtEntryTypeValue = []\r
2056 FvObj.FvExtEntryType = []\r
2057 FvObj.FvExtEntryData = []\r
2058 while True:\r
e8a47801
LG
2059 self.__GetSetStatements(FvObj)\r
2060\r
2061 if not (self.__GetBlockStatement(FvObj) or self.__GetFvBaseAddress(FvObj) or \r
2062 self.__GetFvForceRebase(FvObj) or self.__GetFvAlignment(FvObj) or \r
2063 self.__GetFvAttributes(FvObj) or self.__GetFvNameGuid(FvObj) or \r
2064 self.__GetFvExtEntryStatement(FvObj)):\r
b303ea72
LG
2065 break\r
2066\r
30fdf114
LG
2067 self.__GetAprioriSection(FvObj, FvObj.DefineVarDict.copy())\r
2068 self.__GetAprioriSection(FvObj, FvObj.DefineVarDict.copy())\r
2069\r
2070 while True:\r
2071 isInf = self.__GetInfStatement(FvObj, MacroDict = FvObj.DefineVarDict.copy())\r
2072 isFile = self.__GetFileStatement(FvObj, MacroDict = FvObj.DefineVarDict.copy())\r
2073 if not isInf and not isFile:\r
2074 break\r
2075\r
2076 return True\r
2077\r
2078 ## __GetFvAlignment() method\r
2079 #\r
2080 # Get alignment for FV\r
2081 #\r
2082 # @param self The object pointer\r
2083 # @param Obj for whom alignment is got\r
2084 # @retval True Successfully find a alignment statement\r
2085 # @retval False Not able to find a alignment statement\r
2086 #\r
2087 def __GetFvAlignment(self, Obj):\r
2088\r
2089 if not self.__IsKeyword( "FvAlignment"):\r
2090 return False\r
2091\r
2092 if not self.__IsToken( "="):\r
2093 raise Warning("expected '='", self.FileName, self.CurrentLineNumber)\r
2094\r
2095 if not self.__GetNextToken():\r
2096 raise Warning("expected alignment value", self.FileName, self.CurrentLineNumber)\r
2097\r
2098 if self.__Token.upper() not in ("1", "2", "4", "8", "16", "32", "64", "128", "256", "512", \\r
2099 "1K", "2K", "4K", "8K", "16K", "32K", "64K", "128K", "256K", "512K", \\r
2100 "1M", "2M", "4M", "8M", "16M", "32M", "64M", "128M", "256M", "512M", \\r
2101 "1G", "2G"):\r
2102 raise Warning("Unknown alignment value '%s'" % self.__Token, self.FileName, self.CurrentLineNumber)\r
2103 Obj.FvAlignment = self.__Token\r
2104 return True\r
4234283c
LG
2105 \r
2106 ## __GetFvBaseAddress() method\r
2107 #\r
2108 # Get BaseAddress for FV\r
2109 #\r
2110 # @param self The object pointer\r
2111 # @param Obj for whom FvBaseAddress is got\r
2112 # @retval True Successfully find a FvBaseAddress statement\r
2113 # @retval False Not able to find a FvBaseAddress statement\r
2114 #\r
2115 def __GetFvBaseAddress(self, Obj):\r
2116\r
2117 if not self.__IsKeyword("FvBaseAddress"):\r
2118 return False\r
2119\r
2120 if not self.__IsToken( "="):\r
2121 raise Warning("expected '='", self.FileName, self.CurrentLineNumber)\r
2122\r
2123 if not self.__GetNextToken():\r
2124 raise Warning("expected FV base address value", self.FileName, self.CurrentLineNumber)\r
2125\r
2126 IsValidBaseAddrValue = re.compile('^0[x|X][0-9a-fA-F]+')\r
2127\r
2128 if not IsValidBaseAddrValue.match(self.__Token.upper()):\r
79b74a03 2129 raise Warning("Unknown FV base address value '%s'" % self.__Token, self.FileName, self.CurrentLineNumber)\r
4234283c 2130 Obj.FvBaseAddress = self.__Token\r
0d2711a6
LG
2131 return True \r
2132 \r
79b74a03
LG
2133 ## __GetFvForceRebase() method\r
2134 #\r
2135 # Get FvForceRebase for FV\r
2136 #\r
2137 # @param self The object pointer\r
2138 # @param Obj for whom FvForceRebase is got\r
2139 # @retval True Successfully find a FvForceRebase statement\r
2140 # @retval False Not able to find a FvForceRebase statement\r
2141 #\r
2142 def __GetFvForceRebase(self, Obj):\r
2143\r
2144 if not self.__IsKeyword("FvForceRebase"):\r
2145 return False\r
2146\r
2147 if not self.__IsToken( "="):\r
2148 raise Warning("expected '='", self.FileName, self.CurrentLineNumber)\r
2149\r
2150 if not self.__GetNextToken():\r
2151 raise Warning("expected FvForceRebase value", self.FileName, self.CurrentLineNumber)\r
30fdf114 2152\r
79b74a03
LG
2153 if self.__Token.upper() not in ["TRUE", "FALSE", "0", "0X0", "0X00", "1", "0X1", "0X01"]:\r
2154 raise Warning("Unknown FvForceRebase value '%s'" % self.__Token, self.FileName, self.CurrentLineNumber)\r
2155 \r
2156 if self.__Token.upper() in ["TRUE", "1", "0X1", "0X01"]:\r
2157 Obj.FvForceRebase = True\r
2158 elif self.__Token.upper() in ["FALSE", "0", "0X0", "0X00"]:\r
2159 Obj.FvForceRebase = False\r
2160 else:\r
2161 Obj.FvForceRebase = None\r
2162 \r
2163 return True\r
0d2711a6
LG
2164\r
2165\r
30fdf114
LG
2166 ## __GetFvAttributes() method\r
2167 #\r
2168 # Get attributes for FV\r
2169 #\r
2170 # @param self The object pointer\r
2171 # @param Obj for whom attribute is got\r
2172 # @retval None\r
2173 #\r
2174 def __GetFvAttributes(self, FvObj):\r
2bc3256c 2175 IsWordToken = False\r
30fdf114 2176 while self.__GetNextWord():\r
2bc3256c 2177 IsWordToken = True\r
30fdf114
LG
2178 name = self.__Token\r
2179 if name not in ("ERASE_POLARITY", "MEMORY_MAPPED", \\r
2180 "STICKY_WRITE", "LOCK_CAP", "LOCK_STATUS", "WRITE_ENABLED_CAP", \\r
2181 "WRITE_DISABLED_CAP", "WRITE_STATUS", "READ_ENABLED_CAP", \\r
2182 "READ_DISABLED_CAP", "READ_STATUS", "READ_LOCK_CAP", \\r
2183 "READ_LOCK_STATUS", "WRITE_LOCK_CAP", "WRITE_LOCK_STATUS", \\r
e8a47801 2184 "WRITE_POLICY_RELIABLE", "WEAK_ALIGNMENT"):\r
30fdf114 2185 self.__UndoToken()\r
e8a47801 2186 return False\r
30fdf114
LG
2187\r
2188 if not self.__IsToken( "="):\r
2189 raise Warning("expected '='", self.FileName, self.CurrentLineNumber)\r
2190\r
2191 if not self.__GetNextToken() or self.__Token.upper() not in ("TRUE", "FALSE", "1", "0"):\r
2192 raise Warning("expected TRUE/FALSE (1/0)", self.FileName, self.CurrentLineNumber)\r
2193\r
2194 FvObj.FvAttributeDict[name] = self.__Token\r
2195\r
2bc3256c 2196 return IsWordToken\r
30fdf114
LG
2197 \r
2198 ## __GetFvNameGuid() method\r
2199 #\r
2200 # Get FV GUID for FV\r
2201 #\r
2202 # @param self The object pointer\r
2203 # @param Obj for whom GUID is got\r
2204 # @retval None\r
2205 #\r
2206 def __GetFvNameGuid(self, FvObj):\r
2207\r
2208 if not self.__IsKeyword( "FvNameGuid"):\r
e8a47801 2209 return False\r
30fdf114
LG
2210\r
2211 if not self.__IsToken( "="):\r
2212 raise Warning("expected '='", self.FileName, self.CurrentLineNumber)\r
2213\r
2214 if not self.__GetNextGuid():\r
2215 raise Warning("expected FV GUID value", self.FileName, self.CurrentLineNumber)\r
2216\r
2217 FvObj.FvNameGuid = self.__Token\r
2218\r
e8a47801 2219 return True\r
30fdf114 2220\r
b303ea72
LG
2221 def __GetFvExtEntryStatement(self, FvObj):\r
2222\r
2223 if not self.__IsKeyword( "FV_EXT_ENTRY"):\r
2224 return False\r
2225\r
2226 if not self.__IsKeyword ("TYPE"):\r
2227 raise Warning("expected 'TYPE'", self.FileName, self.CurrentLineNumber)\r
2228 \r
2229 if not self.__IsToken( "="):\r
2230 raise Warning("expected '='", self.FileName, self.CurrentLineNumber)\r
2231\r
2232 if not self.__GetNextHexNumber() and not self.__GetNextDecimalNumber():\r
2233 raise Warning("expected Hex FV extension entry type value At Line ", self.FileName, self.CurrentLineNumber)\r
2234\r
2235 FvObj.FvExtEntryTypeValue += [self.__Token]\r
2236\r
2237 if not self.__IsToken( "{"):\r
2238 raise Warning("expected '{'", self.FileName, self.CurrentLineNumber)\r
2239\r
2240 if not self.__IsKeyword ("FILE") and not self.__IsKeyword ("DATA"):\r
2241 raise Warning("expected 'FILE' or 'DATA'", self.FileName, self.CurrentLineNumber)\r
2242\r
2243 FvObj.FvExtEntryType += [self.__Token]\r
2244\r
2245 if self.__Token == 'DATA':\r
2246\r
2247 if not self.__IsToken( "="):\r
2248 raise Warning("expected '='", self.FileName, self.CurrentLineNumber)\r
2249 \r
2250 if not self.__IsToken( "{"):\r
2251 raise Warning("expected '{'", self.FileName, self.CurrentLineNumber)\r
2252\r
2253 if not self.__GetNextHexNumber():\r
2254 raise Warning("expected Hex byte", self.FileName, self.CurrentLineNumber)\r
2255\r
2256 if len(self.__Token) > 4:\r
2257 raise Warning("Hex byte(must be 2 digits) too long", self.FileName, self.CurrentLineNumber)\r
2258\r
2259 DataString = self.__Token\r
2260 DataString += ","\r
2261\r
2262 while self.__IsToken(","):\r
2263 if not self.__GetNextHexNumber():\r
2264 raise Warning("Invalid Hex number", self.FileName, self.CurrentLineNumber)\r
2265 if len(self.__Token) > 4:\r
2266 raise Warning("Hex byte(must be 2 digits) too long", self.FileName, self.CurrentLineNumber)\r
2267 DataString += self.__Token\r
2268 DataString += ","\r
2269\r
2270 if not self.__IsToken( "}"):\r
2271 raise Warning("expected '}'", self.FileName, self.CurrentLineNumber)\r
2272\r
2273 if not self.__IsToken( "}"):\r
2274 raise Warning("expected '}'", self.FileName, self.CurrentLineNumber)\r
2275\r
2276 DataString = DataString.rstrip(",")\r
2277 FvObj.FvExtEntryData += [DataString]\r
2278\r
2279 if self.__Token == 'FILE':\r
2280 \r
2281 if not self.__IsToken( "="):\r
2282 raise Warning("expected '='", self.FileName, self.CurrentLineNumber)\r
2283 \r
2284 if not self.__GetNextToken():\r
2285 raise Warning("expected FV Extension Entry file path At Line ", self.FileName, self.CurrentLineNumber)\r
2286 \r
2287 FvObj.FvExtEntryData += [self.__Token]\r
2288\r
2289 if not self.__IsToken( "}"):\r
2290 raise Warning("expected '}'", self.FileName, self.CurrentLineNumber)\r
2291\r
2292 return True\r
2293\r
30fdf114
LG
2294 ## __GetAprioriSection() method\r
2295 #\r
2296 # Get token statements\r
2297 #\r
2298 # @param self The object pointer\r
2299 # @param FvObj for whom apriori is got\r
2300 # @param MacroDict dictionary used to replace macro\r
2301 # @retval True Successfully find apriori statement\r
2302 # @retval False Not able to find apriori statement\r
2303 #\r
2304 def __GetAprioriSection(self, FvObj, MacroDict = {}):\r
2305\r
2306 if not self.__IsKeyword( "APRIORI"):\r
2307 return False\r
2308\r
2309 if not self.__IsKeyword("PEI") and not self.__IsKeyword("DXE"):\r
2310 raise Warning("expected Apriori file type", self.FileName, self.CurrentLineNumber)\r
2311 AprType = self.__Token\r
2312\r
2313 if not self.__IsToken( "{"):\r
2314 raise Warning("expected '{'", self.FileName, self.CurrentLineNumber)\r
2315\r
2316 AprSectionObj = AprioriSection.AprioriSection()\r
2317 AprSectionObj.AprioriType = AprType\r
2318\r
2319 self.__GetDefineStatements(AprSectionObj)\r
2320 MacroDict.update(AprSectionObj.DefineVarDict)\r
2321\r
2322 while True:\r
2323 IsInf = self.__GetInfStatement( AprSectionObj, MacroDict = MacroDict)\r
2324 IsFile = self.__GetFileStatement( AprSectionObj)\r
2325 if not IsInf and not IsFile:\r
2326 break\r
2327\r
2328 if not self.__IsToken( "}"):\r
2329 raise Warning("expected '}'", self.FileName, self.CurrentLineNumber)\r
2330\r
2331 FvObj.AprioriSectionList.append(AprSectionObj)\r
2332 return True\r
2333\r
2334 ## __GetInfStatement() method\r
2335 #\r
2336 # Get INF statements\r
2337 #\r
2338 # @param self The object pointer\r
2339 # @param Obj for whom inf statement is got\r
2340 # @param MacroDict dictionary used to replace macro\r
2341 # @retval True Successfully find inf statement\r
2342 # @retval False Not able to find inf statement\r
2343 #\r
2344 def __GetInfStatement(self, Obj, ForCapsule = False, MacroDict = {}):\r
2345\r
2346 if not self.__IsKeyword( "INF"):\r
2347 return False\r
2348\r
2349 ffsInf = FfsInfStatement.FfsInfStatement()\r
2350 self.__GetInfOptions( ffsInf)\r
2351\r
2352 if not self.__GetNextToken():\r
2353 raise Warning("expected INF file path", self.FileName, self.CurrentLineNumber)\r
2354 ffsInf.InfFileName = self.__Token\r
64b2609f
LG
2355\r
2356 ffsInf.CurrentLineNum = self.CurrentLineNumber\r
2357 ffsInf.CurrentLineContent = self.__CurrentLine()\r
2358\r
14c48571 2359 if ffsInf.InfFileName.replace('$(WORKSPACE)', '').find('$') == -1:\r
2360 #do case sensitive check for file path\r
2361 ErrorCode, ErrorInfo = PathClass(NormPath(ffsInf.InfFileName), GenFdsGlobalVariable.WorkSpaceDir).Validate()\r
2362 if ErrorCode != 0:\r
2363 EdkLogger.error("GenFds", ErrorCode, ExtraData=ErrorInfo)\r
30fdf114 2364\r
30fdf114
LG
2365 if not ffsInf.InfFileName in self.Profile.InfList:\r
2366 self.Profile.InfList.append(ffsInf.InfFileName)\r
d0acc87a
LG
2367 FileLineTuple = GetRealFileLine(self.FileName, self.CurrentLineNumber)\r
2368 self.Profile.InfFileLineList.append(FileLineTuple)\r
30fdf114
LG
2369\r
2370 if self.__IsToken('|'):\r
2371 if self.__IsKeyword('RELOCS_STRIPPED'):\r
2372 ffsInf.KeepReloc = False\r
2373 elif self.__IsKeyword('RELOCS_RETAINED'):\r
2374 ffsInf.KeepReloc = True\r
2375 else:\r
2376 raise Warning("Unknown reloc strip flag '%s'" % self.__Token, self.FileName, self.CurrentLineNumber)\r
79b74a03 2377 \r
30fdf114
LG
2378 if ForCapsule:\r
2379 capsuleFfs = CapsuleData.CapsuleFfs()\r
2380 capsuleFfs.Ffs = ffsInf\r
2381 Obj.CapsuleDataList.append(capsuleFfs)\r
2382 else:\r
2383 Obj.FfsList.append(ffsInf)\r
2384 return True\r
2385\r
2386 ## __GetInfOptions() method\r
2387 #\r
2388 # Get options for INF\r
2389 #\r
2390 # @param self The object pointer\r
2391 # @param FfsInfObj for whom option is got\r
2392 #\r
2393 def __GetInfOptions(self, FfsInfObj):\r
2394\r
2395 if self.__IsKeyword( "RuleOverride"):\r
2396 if not self.__IsToken( "="):\r
2397 raise Warning("expected '='", self.FileName, self.CurrentLineNumber)\r
2398 if not self.__GetNextToken():\r
2399 raise Warning("expected Rule name", self.FileName, self.CurrentLineNumber)\r
2400 FfsInfObj.Rule = self.__Token\r
2401\r
2402 if self.__IsKeyword( "VERSION"):\r
2403 if not self.__IsToken( "="):\r
2404 raise Warning("expected '='", self.FileName, self.CurrentLineNumber)\r
2405 if not self.__GetNextToken():\r
2406 raise Warning("expected Version", self.FileName, self.CurrentLineNumber)\r
2407\r
2408 if self.__GetStringData():\r
2409 FfsInfObj.Version = self.__Token\r
2410\r
2411 if self.__IsKeyword( "UI"):\r
2412 if not self.__IsToken( "="):\r
2413 raise Warning("expected '='", self.FileName, self.CurrentLineNumber)\r
2414 if not self.__GetNextToken():\r
2415 raise Warning("expected UI name", self.FileName, self.CurrentLineNumber)\r
2416\r
2417 if self.__GetStringData():\r
2418 FfsInfObj.Ui = self.__Token\r
2419\r
2420 if self.__IsKeyword( "USE"):\r
2421 if not self.__IsToken( "="):\r
2422 raise Warning("expected '='", self.FileName, self.CurrentLineNumber)\r
2423 if not self.__GetNextToken():\r
2424 raise Warning("expected ARCH name", self.FileName, self.CurrentLineNumber)\r
2425 FfsInfObj.UseArch = self.__Token\r
2426\r
2427 \r
2428 if self.__GetNextToken():\r
2429 p = re.compile(r'([a-zA-Z0-9\-]+|\$\(TARGET\)|\*)_([a-zA-Z0-9\-]+|\$\(TOOL_CHAIN_TAG\)|\*)_([a-zA-Z0-9\-]+|\$\(ARCH\)|\*)')\r
2430 if p.match(self.__Token):\r
2431 FfsInfObj.KeyStringList.append(self.__Token)\r
2432 if not self.__IsToken(","):\r
2433 return\r
2434 else:\r
2435 self.__UndoToken()\r
2436 return\r
2437\r
2438 while self.__GetNextToken():\r
2439 if not p.match(self.__Token):\r
2440 raise Warning("expected KeyString \"Target_Tag_Arch\"", self.FileName, self.CurrentLineNumber)\r
2441 FfsInfObj.KeyStringList.append(self.__Token)\r
2442\r
2443 if not self.__IsToken(","):\r
2444 break\r
2445\r
2446 ## __GetFileStatement() method\r
2447 #\r
2448 # Get FILE statements\r
2449 #\r
2450 # @param self The object pointer\r
2451 # @param Obj for whom FILE statement is got\r
2452 # @param MacroDict dictionary used to replace macro\r
2453 # @retval True Successfully find FILE statement\r
2454 # @retval False Not able to find FILE statement\r
2455 #\r
2456 def __GetFileStatement(self, Obj, ForCapsule = False, MacroDict = {}):\r
2457\r
2458 if not self.__IsKeyword( "FILE"):\r
2459 return False\r
2460\r
30fdf114
LG
2461 if not self.__GetNextWord():\r
2462 raise Warning("expected FFS type", self.FileName, self.CurrentLineNumber)\r
b36d134f
LG
2463\r
2464 if ForCapsule and self.__Token == 'DATA':\r
2465 self.__UndoToken()\r
2466 self.__UndoToken()\r
2467 return False\r
2468 \r
2469 FfsFileObj = FfsFileStatement.FileStatement()\r
30fdf114
LG
2470 FfsFileObj.FvFileType = self.__Token\r
2471\r
2472 if not self.__IsToken( "="):\r
2473 raise Warning("expected '='", self.FileName, self.CurrentLineNumber)\r
2474\r
2475 if not self.__GetNextGuid():\r
2476 if not self.__GetNextWord():\r
2477 raise Warning("expected File GUID", self.FileName, self.CurrentLineNumber)\r
2478 if self.__Token == 'PCD':\r
2479 if not self.__IsToken( "("):\r
2480 raise Warning("expected '('", self.FileName, self.CurrentLineNumber)\r
2481 PcdPair = self.__GetNextPcdName()\r
2482 if not self.__IsToken( ")"):\r
2483 raise Warning("expected ')'", self.FileName, self.CurrentLineNumber)\r
2484 self.__Token = 'PCD('+PcdPair[1]+'.'+PcdPair[0]+')'\r
2485 \r
2486 FfsFileObj.NameGuid = self.__Token\r
79b74a03 2487 \r
30fdf114
LG
2488 self.__GetFilePart( FfsFileObj, MacroDict.copy())\r
2489\r
2490 if ForCapsule:\r
2491 capsuleFfs = CapsuleData.CapsuleFfs()\r
2492 capsuleFfs.Ffs = FfsFileObj\r
2493 Obj.CapsuleDataList.append(capsuleFfs)\r
2494 else:\r
2495 Obj.FfsList.append(FfsFileObj)\r
2496\r
2497 return True\r
2498\r
2499 ## __FileCouldHaveRelocFlag() method\r
2500 #\r
2501 # Check whether reloc strip flag can be set for a file type.\r
2502 #\r
2503 # @param self The object pointer\r
2504 # @param FileType The file type to check with\r
2505 # @retval True This type could have relocation strip flag\r
2506 # @retval False No way to have it\r
2507 #\r
2508\r
2509 def __FileCouldHaveRelocFlag (self, FileType):\r
2510 if FileType in ('SEC', 'PEI_CORE', 'PEIM', 'PEI_DXE_COMBO'):\r
2511 return True\r
2512 else:\r
2513 return False\r
2514\r
2515 ## __SectionCouldHaveRelocFlag() method\r
2516 #\r
2517 # Check whether reloc strip flag can be set for a section type.\r
2518 #\r
2519 # @param self The object pointer\r
2520 # @param SectionType The section type to check with\r
2521 # @retval True This type could have relocation strip flag\r
2522 # @retval False No way to have it\r
2523 #\r
2524\r
2525 def __SectionCouldHaveRelocFlag (self, SectionType):\r
2526 if SectionType in ('TE', 'PE32'):\r
2527 return True\r
2528 else:\r
2529 return False\r
2530\r
2531 ## __GetFilePart() method\r
2532 #\r
2533 # Get components for FILE statement\r
2534 #\r
2535 # @param self The object pointer\r
2536 # @param FfsFileObj for whom component is got\r
2537 # @param MacroDict dictionary used to replace macro\r
2538 #\r
2539 def __GetFilePart(self, FfsFileObj, MacroDict = {}):\r
2540\r
2541 self.__GetFileOpts( FfsFileObj)\r
2542\r
2543 if not self.__IsToken("{"):\r
4afd3d04
LG
2544 if self.__IsKeyword('RELOCS_STRIPPED') or self.__IsKeyword('RELOCS_RETAINED'):\r
2545 if self.__FileCouldHaveRelocFlag(FfsFileObj.FvFileType):\r
2546 if self.__Token == 'RELOCS_STRIPPED':\r
2547 FfsFileObj.KeepReloc = False\r
2548 else:\r
2549 FfsFileObj.KeepReloc = True\r
2550 else:\r
2551 raise Warning("File type %s could not have reloc strip flag%d" % (FfsFileObj.FvFileType, self.CurrentLineNumber), self.FileName, self.CurrentLineNumber)\r
2552\r
2553 if not self.__IsToken("{"):\r
30fdf114
LG
2554 raise Warning("expected '{'", self.FileName, self.CurrentLineNumber)\r
2555\r
2556 if not self.__GetNextToken():\r
2557 raise Warning("expected File name or section data", self.FileName, self.CurrentLineNumber)\r
2558\r
2559 if self.__Token == "FV":\r
2560 if not self.__IsToken( "="):\r
2561 raise Warning("expected '='", self.FileName, self.CurrentLineNumber)\r
2562 if not self.__GetNextToken():\r
2563 raise Warning("expected FV name", self.FileName, self.CurrentLineNumber)\r
2564 FfsFileObj.FvName = self.__Token\r
2565\r
2566 elif self.__Token == "FD":\r
2567 if not self.__IsToken( "="):\r
2568 raise Warning("expected '='", self.FileName, self.CurrentLineNumber)\r
2569 if not self.__GetNextToken():\r
2570 raise Warning("expected FD name", self.FileName, self.CurrentLineNumber)\r
2571 FfsFileObj.FdName = self.__Token\r
2572\r
2573 elif self.__Token in ("DEFINE", "APRIORI", "SECTION"):\r
2574 self.__UndoToken()\r
2575 self.__GetSectionData( FfsFileObj, MacroDict)\r
2576 else:\r
64b2609f
LG
2577 FfsFileObj.CurrentLineNum = self.CurrentLineNumber\r
2578 FfsFileObj.CurrentLineContent = self.__CurrentLine()\r
30fdf114 2579 FfsFileObj.FileName = self.__Token\r
2bc3256c 2580 self.__VerifyFile(FfsFileObj.FileName)\r
0d2711a6 2581\r
30fdf114
LG
2582 if not self.__IsToken( "}"):\r
2583 raise Warning("expected '}'", self.FileName, self.CurrentLineNumber)\r
2584\r
2585 ## __GetFileOpts() method\r
2586 #\r
2587 # Get options for FILE statement\r
2588 #\r
2589 # @param self The object pointer\r
2590 # @param FfsFileObj for whom options is got\r
2591 #\r
2592 def __GetFileOpts(self, FfsFileObj):\r
2593\r
2594 if self.__GetNextToken():\r
2595 Pattern = re.compile(r'([a-zA-Z0-9\-]+|\$\(TARGET\)|\*)_([a-zA-Z0-9\-]+|\$\(TOOL_CHAIN_TAG\)|\*)_([a-zA-Z0-9\-]+|\$\(ARCH\)|\*)')\r
2596 if Pattern.match(self.__Token):\r
2597 FfsFileObj.KeyStringList.append(self.__Token)\r
2598 if self.__IsToken(","):\r
2599 while self.__GetNextToken():\r
2600 if not Pattern.match(self.__Token):\r
2601 raise Warning("expected KeyString \"Target_Tag_Arch\"", self.FileName, self.CurrentLineNumber)\r
2602 FfsFileObj.KeyStringList.append(self.__Token)\r
2603\r
2604 if not self.__IsToken(","):\r
2605 break\r
2606\r
2607 else:\r
2608 self.__UndoToken()\r
2609\r
2610 if self.__IsKeyword( "FIXED", True):\r
2611 FfsFileObj.Fixed = True\r
2612\r
2613 if self.__IsKeyword( "CHECKSUM", True):\r
2614 FfsFileObj.CheckSum = True\r
2615\r
2616 if self.__GetAlignment():\r
9053bc51 2617 if self.__Token not in ("Auto", "8", "16", "32", "64", "128", "512", "1K", "4K", "32K" ,"64K"):\r
2618 raise Warning("Incorrect alignment '%s'" % self.__Token, self.FileName, self.CurrentLineNumber)\r
2619 #For FFS, Auto is default option same to ""\r
2620 if not self.__Token == "Auto":\r
2621 FfsFileObj.Alignment = self.__Token\r
30fdf114
LG
2622\r
2623 ## __GetAlignment() method\r
2624 #\r
2625 # Return the alignment value\r
2626 #\r
2627 # @param self The object pointer\r
2628 # @retval True Successfully find alignment\r
2629 # @retval False Not able to find alignment\r
2630 #\r
2631 def __GetAlignment(self):\r
2632 if self.__IsKeyword( "Align", True):\r
2633 if not self.__IsToken( "="):\r
2634 raise Warning("expected '='", self.FileName, self.CurrentLineNumber)\r
2635\r
2636 if not self.__GetNextToken():\r
2637 raise Warning("expected alignment value", self.FileName, self.CurrentLineNumber)\r
2638 return True\r
2639\r
2640 return False\r
2641\r
2642 ## __GetFilePart() method\r
2643 #\r
2644 # Get section data for FILE statement\r
2645 #\r
2646 # @param self The object pointer\r
2647 # @param FfsFileObj for whom section is got\r
2648 # @param MacroDict dictionary used to replace macro\r
2649 #\r
2650 def __GetSectionData(self, FfsFileObj, MacroDict = {}):\r
2651 Dict = {}\r
2652 Dict.update(MacroDict)\r
2653\r
2654 self.__GetDefineStatements(FfsFileObj)\r
2655\r
2656 Dict.update(FfsFileObj.DefineVarDict)\r
2657 self.__GetAprioriSection(FfsFileObj, Dict.copy())\r
2658 self.__GetAprioriSection(FfsFileObj, Dict.copy())\r
2659\r
2660 while True:\r
2661 IsLeafSection = self.__GetLeafSection(FfsFileObj, Dict)\r
2662 IsEncapSection = self.__GetEncapsulationSec(FfsFileObj)\r
2663 if not IsLeafSection and not IsEncapSection:\r
2664 break\r
2665\r
2666 ## __GetLeafSection() method\r
2667 #\r
2668 # Get leaf section for Obj\r
2669 #\r
2670 # @param self The object pointer\r
2671 # @param Obj for whom leaf section is got\r
2672 # @param MacroDict dictionary used to replace macro\r
2673 # @retval True Successfully find section statement\r
2674 # @retval False Not able to find section statement\r
2675 #\r
2676 def __GetLeafSection(self, Obj, MacroDict = {}):\r
2677\r
2678 OldPos = self.GetFileBufferPos()\r
2679\r
2680 if not self.__IsKeyword( "SECTION"):\r
2681 if len(Obj.SectionList) == 0:\r
2682 raise Warning("expected SECTION", self.FileName, self.CurrentLineNumber)\r
2683 else:\r
2684 return False\r
2685\r
2686 AlignValue = None\r
2687 if self.__GetAlignment():\r
52302d4d
LG
2688 if self.__Token not in ("Auto", "8", "16", "32", "64", "128", "512", "1K", "4K", "32K" ,"64K"):\r
2689 raise Warning("Incorrect alignment '%s'" % self.__Token, self.FileName, self.CurrentLineNumber)\r
30fdf114
LG
2690 AlignValue = self.__Token\r
2691\r
2692 BuildNum = None\r
2693 if self.__IsKeyword( "BUILD_NUM"):\r
2694 if not self.__IsToken( "="):\r
2695 raise Warning("expected '='", self.FileName, self.CurrentLineNumber)\r
2696\r
2697 if not self.__GetNextToken():\r
2698 raise Warning("expected Build number value", self.FileName, self.CurrentLineNumber)\r
2699\r
2700 BuildNum = self.__Token\r
2701\r
2702 if self.__IsKeyword( "VERSION"):\r
52302d4d
LG
2703 if AlignValue == 'Auto':\r
2704 raise Warning("Auto alignment can only be used in PE32 or TE section ", self.FileName, self.CurrentLineNumber)\r
30fdf114
LG
2705 if not self.__IsToken( "="):\r
2706 raise Warning("expected '='", self.FileName, self.CurrentLineNumber)\r
2707 if not self.__GetNextToken():\r
2708 raise Warning("expected version", self.FileName, self.CurrentLineNumber)\r
2709 VerSectionObj = VerSection.VerSection()\r
2710 VerSectionObj.Alignment = AlignValue\r
2711 VerSectionObj.BuildNum = BuildNum\r
2712 if self.__GetStringData():\r
2713 VerSectionObj.StringData = self.__Token\r
2714 else:\r
2715 VerSectionObj.FileName = self.__Token\r
2716 Obj.SectionList.append(VerSectionObj)\r
52302d4d 2717 \r
30fdf114 2718 elif self.__IsKeyword( "UI"):\r
52302d4d
LG
2719 if AlignValue == 'Auto':\r
2720 raise Warning("Auto alignment can only be used in PE32 or TE section ", self.FileName, self.CurrentLineNumber)\r
30fdf114
LG
2721 if not self.__IsToken( "="):\r
2722 raise Warning("expected '='", self.FileName, self.CurrentLineNumber)\r
2723 if not self.__GetNextToken():\r
2724 raise Warning("expected UI", self.FileName, self.CurrentLineNumber)\r
2725 UiSectionObj = UiSection.UiSection()\r
2726 UiSectionObj.Alignment = AlignValue\r
2727 if self.__GetStringData():\r
2728 UiSectionObj.StringData = self.__Token\r
2729 else:\r
2730 UiSectionObj.FileName = self.__Token\r
2731 Obj.SectionList.append(UiSectionObj)\r
2732\r
2733 elif self.__IsKeyword( "FV_IMAGE"):\r
52302d4d
LG
2734 if AlignValue == 'Auto':\r
2735 raise Warning("Auto alignment can only be used in PE32 or TE section ", self.FileName, self.CurrentLineNumber)\r
30fdf114
LG
2736 if not self.__IsToken( "="):\r
2737 raise Warning("expected '='", self.FileName, self.CurrentLineNumber)\r
2738 if not self.__GetNextToken():\r
2739 raise Warning("expected FV name or FV file path", self.FileName, self.CurrentLineNumber)\r
2740\r
2741 FvName = self.__Token\r
2742 FvObj = None\r
2743\r
2744 if self.__IsToken( "{"):\r
2745 FvObj = Fv.FV()\r
2746 FvObj.UiFvName = FvName.upper()\r
2747 self.__GetDefineStatements(FvObj)\r
2748 MacroDict.update(FvObj.DefineVarDict)\r
2749 self.__GetBlockStatement(FvObj)\r
2750 self.__GetSetStatements(FvObj)\r
2751 self.__GetFvAlignment(FvObj)\r
2752 self.__GetFvAttributes(FvObj)\r
2753 self.__GetAprioriSection(FvObj, MacroDict.copy())\r
2754 self.__GetAprioriSection(FvObj, MacroDict.copy())\r
2755\r
2756 while True:\r
2757 IsInf = self.__GetInfStatement(FvObj, MacroDict.copy())\r
2758 IsFile = self.__GetFileStatement(FvObj, MacroDict.copy())\r
2759 if not IsInf and not IsFile:\r
2760 break\r
2761\r
2762 if not self.__IsToken( "}"):\r
2763 raise Warning("expected '}'", self.FileName, self.CurrentLineNumber)\r
2764\r
2765 FvImageSectionObj = FvImageSection.FvImageSection()\r
2766 FvImageSectionObj.Alignment = AlignValue\r
2767 if FvObj != None:\r
2768 FvImageSectionObj.Fv = FvObj\r
2769 FvImageSectionObj.FvName = None\r
2770 else:\r
2771 FvImageSectionObj.FvName = FvName.upper()\r
2772 FvImageSectionObj.FvFileName = FvName\r
2773\r
2774 Obj.SectionList.append(FvImageSectionObj)\r
2775\r
2776 elif self.__IsKeyword("PEI_DEPEX_EXP") or self.__IsKeyword("DXE_DEPEX_EXP") or self.__IsKeyword("SMM_DEPEX_EXP"):\r
52302d4d
LG
2777 if AlignValue == 'Auto':\r
2778 raise Warning("Auto alignment can only be used in PE32 or TE section ", self.FileName, self.CurrentLineNumber)\r
30fdf114
LG
2779 DepexSectionObj = DepexSection.DepexSection()\r
2780 DepexSectionObj.Alignment = AlignValue\r
2781 DepexSectionObj.DepexType = self.__Token\r
2782\r
2783 if not self.__IsToken( "="):\r
2784 raise Warning("expected '='", self.FileName, self.CurrentLineNumber)\r
2785 if not self.__IsToken( "{"):\r
2786 raise Warning("expected '{'", self.FileName, self.CurrentLineNumber)\r
2787 if not self.__SkipToToken( "}"):\r
2788 raise Warning("expected Depex expression ending '}'", self.FileName, self.CurrentLineNumber)\r
2789\r
2790 DepexSectionObj.Expression = self.__SkippedChars.rstrip('}')\r
2791 Obj.SectionList.append(DepexSectionObj)\r
2792\r
2793 else:\r
30fdf114
LG
2794 if not self.__GetNextWord():\r
2795 raise Warning("expected section type", self.FileName, self.CurrentLineNumber)\r
2796\r
2797 # Encapsulation section appear, UndoToken and return\r
2798 if self.__Token == "COMPRESS" or self.__Token == "GUIDED":\r
2799 self.SetFileBufferPos(OldPos)\r
2800 return False\r
2801\r
2802 if self.__Token not in ("COMPAT16", "PE32", "PIC", "TE", "FV_IMAGE", "RAW", "DXE_DEPEX",\\r
2803 "UI", "VERSION", "PEI_DEPEX", "SUBTYPE_GUID", "SMM_DEPEX"):\r
2804 raise Warning("Unknown section type '%s'" % self.__Token, self.FileName, self.CurrentLineNumber)\r
52302d4d
LG
2805 if AlignValue == 'Auto'and (not self.__Token == 'PE32') and (not self.__Token == 'TE'):\r
2806 raise Warning("Auto alignment can only be used in PE32 or TE section ", self.FileName, self.CurrentLineNumber)\r
2807\r
30fdf114
LG
2808 # DataSection\r
2809 DataSectionObj = DataSection.DataSection()\r
2810 DataSectionObj.Alignment = AlignValue\r
2811 DataSectionObj.SecType = self.__Token\r
2812\r
2813 if self.__IsKeyword('RELOCS_STRIPPED') or self.__IsKeyword('RELOCS_RETAINED'):\r
2814 if self.__FileCouldHaveRelocFlag(Obj.FvFileType) and self.__SectionCouldHaveRelocFlag(DataSectionObj.SecType):\r
2815 if self.__Token == 'RELOCS_STRIPPED':\r
2816 DataSectionObj.KeepReloc = False\r
2817 else:\r
2818 DataSectionObj.KeepReloc = True\r
2819 else:\r
2820 raise Warning("File type %s, section type %s, could not have reloc strip flag%d" % (Obj.FvFileType, DataSectionObj.SecType, self.CurrentLineNumber), self.FileName, self.CurrentLineNumber)\r
2821\r
2822 if self.__IsToken("="):\r
2823 if not self.__GetNextToken():\r
2824 raise Warning("expected section file path", self.FileName, self.CurrentLineNumber)\r
2825 DataSectionObj.SectFileName = self.__Token\r
2bc3256c 2826 self.__VerifyFile(DataSectionObj.SectFileName)\r
30fdf114
LG
2827 else:\r
2828 if not self.__GetCglSection(DataSectionObj):\r
2829 return False\r
2830\r
2831 Obj.SectionList.append(DataSectionObj)\r
2832\r
2833 return True\r
2834\r
2bc3256c
LG
2835 ## __VerifyFile\r
2836 #\r
2837 # Check if file exists or not:\r
2838 # If current phase if GenFds, the file must exist;\r
2839 # If current phase is AutoGen and the file is not in $(OUTPUT_DIRECTORY), the file must exist\r
2840 # @param FileName: File path to be verified.\r
2841 #\r
2842 def __VerifyFile(self, FileName):\r
2843 if FileName.replace('$(WORKSPACE)', '').find('$') != -1:\r
2844 return\r
2845 if not GlobalData.gAutoGenPhase or not self.__GetMacroValue("OUTPUT_DIRECTORY") in FileName:\r
2846 ErrorCode, ErrorInfo = PathClass(NormPath(FileName), GenFdsGlobalVariable.WorkSpaceDir).Validate()\r
2847 if ErrorCode != 0:\r
2848 EdkLogger.error("GenFds", ErrorCode, ExtraData=ErrorInfo)\r
2849\r
30fdf114
LG
2850 ## __GetCglSection() method\r
2851 #\r
2852 # Get compressed or GUIDed section for Obj\r
2853 #\r
2854 # @param self The object pointer\r
2855 # @param Obj for whom leaf section is got\r
2856 # @param AlignValue alignment value for complex section\r
2857 # @retval True Successfully find section statement\r
2858 # @retval False Not able to find section statement\r
2859 #\r
2860 def __GetCglSection(self, Obj, AlignValue = None):\r
2861\r
2862 if self.__IsKeyword( "COMPRESS"):\r
2863 type = "PI_STD"\r
2864 if self.__IsKeyword("PI_STD") or self.__IsKeyword("PI_NONE"):\r
2865 type = self.__Token\r
2866\r
2867 if not self.__IsToken("{"):\r
2868 raise Warning("expected '{'", self.FileName, self.CurrentLineNumber)\r
2869\r
2870 CompressSectionObj = CompressSection.CompressSection()\r
2871 CompressSectionObj.Alignment = AlignValue\r
2872 CompressSectionObj.CompType = type\r
2873 # Recursive sections...\r
2874 while True:\r
2875 IsLeafSection = self.__GetLeafSection(CompressSectionObj)\r
2876 IsEncapSection = self.__GetEncapsulationSec(CompressSectionObj)\r
2877 if not IsLeafSection and not IsEncapSection:\r
2878 break\r
2879\r
2880\r
2881 if not self.__IsToken( "}"):\r
2882 raise Warning("expected '}'", self.FileName, self.CurrentLineNumber)\r
2883 Obj.SectionList.append(CompressSectionObj)\r
2884\r
2885# else:\r
2886# raise Warning("Compress type not known")\r
2887\r
2888 return True\r
2889\r
2890 elif self.__IsKeyword( "GUIDED"):\r
2891 GuidValue = None\r
2892 if self.__GetNextGuid():\r
2893 GuidValue = self.__Token\r
2894\r
2895 AttribDict = self.__GetGuidAttrib()\r
2896 if not self.__IsToken("{"):\r
2897 raise Warning("expected '{'", self.FileName, self.CurrentLineNumber)\r
2898 GuidSectionObj = GuidSection.GuidSection()\r
2899 GuidSectionObj.Alignment = AlignValue\r
2900 GuidSectionObj.NameGuid = GuidValue\r
2901 GuidSectionObj.SectionType = "GUIDED"\r
2902 GuidSectionObj.ProcessRequired = AttribDict["PROCESSING_REQUIRED"]\r
2903 GuidSectionObj.AuthStatusValid = AttribDict["AUTH_STATUS_VALID"]\r
25918452 2904 GuidSectionObj.ExtraHeaderSize = AttribDict["EXTRA_HEADER_SIZE"]\r
30fdf114
LG
2905 # Recursive sections...\r
2906 while True:\r
2907 IsLeafSection = self.__GetLeafSection(GuidSectionObj)\r
2908 IsEncapSection = self.__GetEncapsulationSec(GuidSectionObj)\r
2909 if not IsLeafSection and not IsEncapSection:\r
2910 break\r
2911\r
2912 if not self.__IsToken( "}"):\r
2913 raise Warning("expected '}'", self.FileName, self.CurrentLineNumber)\r
2914 Obj.SectionList.append(GuidSectionObj)\r
2915\r
2916 return True\r
2917\r
2918 return False\r
2919\r
2920 ## __GetGuidAttri() method\r
2921 #\r
2922 # Get attributes for GUID section\r
2923 #\r
2924 # @param self The object pointer\r
2925 # @retval AttribDict Dictionary of key-value pair of section attributes\r
2926 #\r
2927 def __GetGuidAttrib(self):\r
2928\r
2929 AttribDict = {}\r
14c48571 2930 AttribDict["PROCESSING_REQUIRED"] = "NONE"\r
2931 AttribDict["AUTH_STATUS_VALID"] = "NONE"\r
25918452
LG
2932 AttribDict["EXTRA_HEADER_SIZE"] = -1\r
2933 while self.__IsKeyword("PROCESSING_REQUIRED") or self.__IsKeyword("AUTH_STATUS_VALID") \\r
2934 or self.__IsKeyword("EXTRA_HEADER_SIZE"):\r
30fdf114
LG
2935 AttribKey = self.__Token\r
2936\r
2937 if not self.__IsToken("="):\r
2938 raise Warning("expected '='", self.FileName, self.CurrentLineNumber)\r
2939\r
25918452
LG
2940 if not self.__GetNextToken():\r
2941 raise Warning("expected TRUE(1)/FALSE(0)/Number", self.FileName, self.CurrentLineNumber)\r
2942 elif AttribKey == "EXTRA_HEADER_SIZE":\r
2943 Base = 10\r
2944 if self.__Token[0:2].upper() == "0X":\r
2945 Base = 16\r
2946 try:\r
2947 AttribDict[AttribKey] = int(self.__Token, Base)\r
2948 continue\r
2949 except ValueError:\r
2950 raise Warning("expected Number", self.FileName, self.CurrentLineNumber)\r
2951 elif self.__Token.upper() not in ("TRUE", "FALSE", "1", "0"):\r
30fdf114
LG
2952 raise Warning("expected TRUE/FALSE (1/0)", self.FileName, self.CurrentLineNumber)\r
2953 AttribDict[AttribKey] = self.__Token\r
2954\r
2955 return AttribDict\r
2956\r
2957 ## __GetEncapsulationSec() method\r
2958 #\r
2959 # Get encapsulation section for FILE\r
2960 #\r
2961 # @param self The object pointer\r
2962 # @param FfsFile for whom section is got\r
2963 # @retval True Successfully find section statement\r
2964 # @retval False Not able to find section statement\r
2965 #\r
2966 def __GetEncapsulationSec(self, FfsFileObj):\r
2967\r
2968 OldPos = self.GetFileBufferPos()\r
2969 if not self.__IsKeyword( "SECTION"):\r
2970 if len(FfsFileObj.SectionList) == 0:\r
2971 raise Warning("expected SECTION", self.FileName, self.CurrentLineNumber)\r
2972 else:\r
2973 return False\r
2974\r
2975 AlignValue = None\r
2976 if self.__GetAlignment():\r
52302d4d
LG
2977 if self.__Token not in ("8", "16", "32", "64", "128", "512", "1K", "4K", "32K" ,"64K"):\r
2978 raise Warning("Incorrect alignment '%s'" % self.__Token, self.FileName, self.CurrentLineNumber)\r
30fdf114
LG
2979 AlignValue = self.__Token\r
2980\r
2981 if not self.__GetCglSection(FfsFileObj, AlignValue):\r
2982 self.SetFileBufferPos(OldPos)\r
2983 return False\r
2984 else:\r
2985 return True\r
2986\r
2987 ## __GetCapsule() method\r
2988 #\r
2989 # Get capsule section contents and store its data into capsule list of self.Profile\r
2990 #\r
2991 # @param self The object pointer\r
2992 # @retval True Successfully find a capsule\r
2993 # @retval False Not able to find a capsule\r
2994 #\r
2995 def __GetCapsule(self):\r
2996\r
2997 if not self.__GetNextToken():\r
2998 return False\r
2999\r
3000 S = self.__Token.upper()\r
3001 if S.startswith("[") and not S.startswith("[CAPSULE."):\r
3002 if not S.startswith("[VTF.") and not S.startswith("[RULE.") and not S.startswith("[OPTIONROM."):\r
3003 raise Warning("Unknown section or section appear sequence error (The correct sequence should be [FD.], [FV.], [Capsule.], [VTF.], [Rule.], [OptionRom.])", self.FileName, self.CurrentLineNumber)\r
3004 self.__UndoToken()\r
3005 return False\r
3006\r
3007 self.__UndoToken()\r
3008 if not self.__IsToken("[CAPSULE.", True):\r
3009 FileLineTuple = GetRealFileLine(self.FileName, self.CurrentLineNumber)\r
3010 #print 'Parsing String: %s in File %s, At line: %d, Offset Within Line: %d' \\r
3011 # % (self.Profile.FileLinesList[self.CurrentLineNumber - 1][self.CurrentOffsetWithinLine :], FileLineTuple[0], FileLineTuple[1], self.CurrentOffsetWithinLine)\r
3012 raise Warning("expected [Capsule.]", self.FileName, self.CurrentLineNumber)\r
3013\r
3014 CapsuleObj = Capsule.Capsule()\r
3015\r
3016 CapsuleName = self.__GetUiName()\r
3017 if not CapsuleName:\r
3018 raise Warning("expected capsule name", self.FileName, self.CurrentLineNumber)\r
3019\r
3020 CapsuleObj.UiCapsuleName = CapsuleName.upper()\r
3021\r
3022 if not self.__IsToken( "]"):\r
3023 raise Warning("expected ']'", self.FileName, self.CurrentLineNumber)\r
3024\r
3025 if self.__IsKeyword("CREATE_FILE"):\r
3026 if not self.__IsToken( "="):\r
3027 raise Warning("expected '='", self.FileName, self.CurrentLineNumber)\r
3028\r
3029 if not self.__GetNextToken():\r
3030 raise Warning("expected file name", self.FileName, self.CurrentLineNumber)\r
3031\r
3032 CapsuleObj.CreateFile = self.__Token\r
3033\r
3034 self.__GetCapsuleStatements(CapsuleObj)\r
fd171542 3035 self.Profile.CapsuleDict[CapsuleObj.UiCapsuleName] = CapsuleObj\r
30fdf114
LG
3036 return True\r
3037\r
3038 ## __GetCapsuleStatements() method\r
3039 #\r
3040 # Get statements for capsule\r
3041 #\r
3042 # @param self The object pointer\r
3043 # @param Obj for whom statements are got\r
3044 #\r
3045 def __GetCapsuleStatements(self, Obj):\r
3046 self.__GetCapsuleTokens(Obj)\r
3047 self.__GetDefineStatements(Obj)\r
3048 self.__GetSetStatements(Obj)\r
30fdf114
LG
3049 self.__GetCapsuleData(Obj)\r
3050\r
fd171542 3051 ## __GetCapsuleTokens() method\r
30fdf114
LG
3052 #\r
3053 # Get token statements for capsule\r
3054 #\r
3055 # @param self The object pointer\r
3056 # @param Obj for whom token statements are got\r
3057 #\r
3058 def __GetCapsuleTokens(self, Obj):\r
b303ea72
LG
3059 if not self.__GetNextToken():\r
3060 return False\r
e8a47801 3061 while self.__Token in ("CAPSULE_GUID", "CAPSULE_HEADER_SIZE", "CAPSULE_FLAGS", "OEM_CAPSULE_FLAGS"):\r
b303ea72
LG
3062 Name = self.__Token.strip()\r
3063 if not self.__IsToken("="):\r
3064 raise Warning("expected '='", self.FileName, self.CurrentLineNumber)\r
3065 if not self.__GetNextToken():\r
3066 raise Warning("expected value", self.FileName, self.CurrentLineNumber)\r
3067 if Name == 'CAPSULE_FLAGS':\r
3068 if not self.__Token in ("PersistAcrossReset", "PopulateSystemTable", "InitiateReset"):\r
3069 raise Warning("expected PersistAcrossReset, PopulateSystemTable, or InitiateReset", self.FileName, self.CurrentLineNumber)\r
3070 Value = self.__Token.strip()\r
3071 while self.__IsToken(","):\r
3072 Value += ','\r
3073 if not self.__GetNextToken():\r
3074 raise Warning("expected value", self.FileName, self.CurrentLineNumber)\r
3075 if not self.__Token in ("PersistAcrossReset", "PopulateSystemTable", "InitiateReset"):\r
3076 raise Warning("expected PersistAcrossReset, PopulateSystemTable, or InitiateReset", self.FileName, self.CurrentLineNumber)\r
3077 Value += self.__Token.strip()\r
e8a47801
LG
3078 elif Name == 'OEM_CAPSULE_FLAGS':\r
3079 Value = self.__Token.strip()\r
2bc3256c
LG
3080 if not Value.upper().startswith('0X'):\r
3081 raise Warning("expected hex value between 0x0000 and 0xFFFF", self.FileName, self.CurrentLineNumber)\r
e8a47801
LG
3082 try:\r
3083 Value = int(Value, 0)\r
3084 except ValueError:\r
2bc3256c 3085 raise Warning("expected hex value between 0x0000 and 0xFFFF", self.FileName, self.CurrentLineNumber)\r
e8a47801 3086 if not 0x0000 <= Value <= 0xFFFF:\r
2bc3256c 3087 raise Warning("expected hex value between 0x0000 and 0xFFFF", self.FileName, self.CurrentLineNumber)\r
e8a47801 3088 Value = self.__Token.strip()\r
b303ea72
LG
3089 else:\r
3090 Value = self.__Token.strip()\r
3091 Obj.TokensDict[Name] = Value \r
3092 if not self.__GetNextToken():\r
3093 return False\r
3094 self.__UndoToken()\r
30fdf114
LG
3095\r
3096 ## __GetCapsuleData() method\r
3097 #\r
3098 # Get capsule data for capsule\r
3099 #\r
3100 # @param self The object pointer\r
3101 # @param Obj for whom capsule data are got\r
3102 #\r
3103 def __GetCapsuleData(self, Obj):\r
3104\r
3105 while True:\r
3106 IsInf = self.__GetInfStatement(Obj, True)\r
3107 IsFile = self.__GetFileStatement(Obj, True)\r
3108 IsFv = self.__GetFvStatement(Obj)\r
b36d134f
LG
3109 IsFd = self.__GetFdStatement(Obj)\r
3110 IsAnyFile = self.__GetAnyFileStatement(Obj)\r
2bc3256c
LG
3111 IsAfile = self.__GetAfileStatement(Obj)\r
3112 if not (IsInf or IsFile or IsFv or IsFd or IsAnyFile or IsAfile):\r
30fdf114
LG
3113 break\r
3114\r
3115 ## __GetFvStatement() method\r
3116 #\r
3117 # Get FV for capsule\r
3118 #\r
3119 # @param self The object pointer\r
3120 # @param CapsuleObj for whom FV is got\r
3121 # @retval True Successfully find a FV statement\r
3122 # @retval False Not able to find a FV statement\r
3123 #\r
3124 def __GetFvStatement(self, CapsuleObj):\r
3125\r
3126 if not self.__IsKeyword("FV"):\r
3127 return False\r
3128\r
3129 if not self.__IsToken("="):\r
3130 raise Warning("expected '='", self.FileName, self.CurrentLineNumber)\r
3131\r
3132 if not self.__GetNextToken():\r
3133 raise Warning("expected FV name", self.FileName, self.CurrentLineNumber)\r
3134\r
2bcc713e
LG
3135 if self.__Token.upper() not in self.Profile.FvDict.keys():\r
3136 raise Warning("FV name does not exist", self.FileName, self.CurrentLineNumber)\r
3137\r
30fdf114
LG
3138 CapsuleFv = CapsuleData.CapsuleFv()\r
3139 CapsuleFv.FvName = self.__Token\r
3140 CapsuleObj.CapsuleDataList.append(CapsuleFv)\r
3141 return True\r
3142\r
b36d134f
LG
3143 ## __GetFdStatement() method\r
3144 #\r
3145 # Get FD for capsule\r
3146 #\r
3147 # @param self The object pointer\r
3148 # @param CapsuleObj for whom FD is got\r
3149 # @retval True Successfully find a FD statement\r
3150 # @retval False Not able to find a FD statement\r
3151 #\r
3152 def __GetFdStatement(self, CapsuleObj):\r
3153\r
3154 if not self.__IsKeyword("FD"):\r
3155 return False\r
3156\r
3157 if not self.__IsToken("="):\r
3158 raise Warning("expected '='", self.FileName, self.CurrentLineNumber)\r
3159\r
3160 if not self.__GetNextToken():\r
3161 raise Warning("expected FD name", self.FileName, self.CurrentLineNumber)\r
3162\r
2bcc713e
LG
3163 if self.__Token.upper() not in self.Profile.FdDict.keys():\r
3164 raise Warning("FD name does not exist", self.FileName, self.CurrentLineNumber)\r
3165\r
b36d134f
LG
3166 CapsuleFd = CapsuleData.CapsuleFd()\r
3167 CapsuleFd.FdName = self.__Token\r
3168 CapsuleObj.CapsuleDataList.append(CapsuleFd)\r
3169 return True\r
3170\r
3171 ## __GetAnyFileStatement() method\r
3172 #\r
3173 # Get AnyFile for capsule\r
3174 #\r
3175 # @param self The object pointer\r
3176 # @param CapsuleObj for whom AnyFile is got\r
3177 # @retval True Successfully find a Anyfile statement\r
3178 # @retval False Not able to find a AnyFile statement\r
3179 #\r
3180 def __GetAnyFileStatement(self, CapsuleObj):\r
3181\r
3182 if not self.__IsKeyword("FILE"):\r
3183 return False\r
3184\r
3185 if not self.__IsKeyword("DATA"):\r
3186 self.__UndoToken()\r
3187 return False\r
3188\r
3189 if not self.__IsToken("="):\r
3190 raise Warning("expected '='", self.FileName, self.CurrentLineNumber)\r
3191\r
3192 if not self.__GetNextToken():\r
3193 raise Warning("expected File name", self.FileName, self.CurrentLineNumber)\r
3194 \r
3195 AnyFileName = self.__Token\r
3196 AnyFileName = GenFdsGlobalVariable.ReplaceWorkspaceMacro(AnyFileName)\r
3197 if not os.path.exists(AnyFileName):\r
3198 raise Warning("File %s not exists"%AnyFileName, self.FileName, self.CurrentLineNumber)\r
3199\r
3200 CapsuleAnyFile = CapsuleData.CapsuleAnyFile()\r
3201 CapsuleAnyFile.FileName = AnyFileName\r
3202 CapsuleObj.CapsuleDataList.append(CapsuleAnyFile)\r
3203 return True\r
2bc3256c
LG
3204 \r
3205 ## __GetAfileStatement() method\r
3206 #\r
3207 # Get Afile for capsule\r
3208 #\r
3209 # @param self The object pointer\r
3210 # @param CapsuleObj for whom Afile is got\r
3211 # @retval True Successfully find a Afile statement\r
3212 # @retval False Not able to find a Afile statement\r
3213 #\r
3214 def __GetAfileStatement(self, CapsuleObj):\r
3215\r
3216 if not self.__IsKeyword("APPEND"):\r
3217 return False\r
3218\r
3219 if not self.__IsToken("="):\r
3220 raise Warning("expected '='", self.FileName, self.CurrentLineNumber)\r
3221\r
3222 if not self.__GetNextToken():\r
3223 raise Warning("expected Afile name", self.FileName, self.CurrentLineNumber)\r
3224 \r
3225 AfileName = self.__Token\r
3226 AfileBaseName = os.path.basename(AfileName)\r
3227 \r
3228 if os.path.splitext(AfileBaseName)[1] not in [".bin",".BIN",".Bin",".dat",".DAT",".Dat",".data",".DATA",".Data"]:\r
3229 raise Warning('invalid binary file type, should be one of "bin","BIN","Bin","dat","DAT","Dat","data","DATA","Data"', \\r
3230 self.FileName, self.CurrentLineNumber)\r
3231 \r
3232 if not os.path.isabs(AfileName):\r
3233 AfileName = GenFdsGlobalVariable.ReplaceWorkspaceMacro(AfileName)\r
3234 self.__VerifyFile(AfileName)\r
3235 else:\r
3236 if not os.path.exists(AfileName):\r
3237 raise Warning('%s does not exist' % AfileName, self.FileName, self.CurrentLineNumber)\r
3238 else:\r
3239 pass\r
3240\r
3241 CapsuleAfile = CapsuleData.CapsuleAfile()\r
3242 CapsuleAfile.FileName = AfileName\r
3243 CapsuleObj.CapsuleDataList.append(CapsuleAfile)\r
3244 return True\r
b36d134f 3245\r
30fdf114
LG
3246 ## __GetRule() method\r
3247 #\r
3248 # Get Rule section contents and store its data into rule list of self.Profile\r
3249 #\r
3250 # @param self The object pointer\r
3251 # @retval True Successfully find a Rule\r
3252 # @retval False Not able to find a Rule\r
3253 #\r
3254 def __GetRule(self):\r
3255\r
3256 if not self.__GetNextToken():\r
3257 return False\r
3258\r
3259 S = self.__Token.upper()\r
3260 if S.startswith("[") and not S.startswith("[RULE."):\r
3261 if not S.startswith("[OPTIONROM."):\r
3262 raise Warning("Unknown section or section appear sequence error (The correct sequence should be [FD.], [FV.], [Capsule.], [VTF.], [Rule.], [OptionRom.])", self.FileName, self.CurrentLineNumber)\r
3263 self.__UndoToken()\r
3264 return False\r
3265 self.__UndoToken()\r
3266 if not self.__IsToken("[Rule.", True):\r
3267 FileLineTuple = GetRealFileLine(self.FileName, self.CurrentLineNumber)\r
3268 #print 'Parsing String: %s in File %s, At line: %d, Offset Within Line: %d' \\r
3269 # % (self.Profile.FileLinesList[self.CurrentLineNumber - 1][self.CurrentOffsetWithinLine :], FileLineTuple[0], FileLineTuple[1], self.CurrentOffsetWithinLine)\r
3270 raise Warning("expected [Rule.]", self.FileName, self.CurrentLineNumber)\r
3271\r
3272 if not self.__SkipToToken("."):\r
3273 raise Warning("expected '.'", self.FileName, self.CurrentLineNumber)\r
3274\r
3275 Arch = self.__SkippedChars.rstrip(".")\r
4afd3d04 3276 if Arch.upper() not in ("IA32", "X64", "IPF", "EBC", "ARM", "AARCH64", "COMMON"):\r
30fdf114
LG
3277 raise Warning("Unknown Arch '%s'" % Arch, self.FileName, self.CurrentLineNumber)\r
3278\r
3279 ModuleType = self.__GetModuleType()\r
3280\r
3281 TemplateName = ""\r
3282 if self.__IsToken("."):\r
3283 if not self.__GetNextWord():\r
3284 raise Warning("expected template name", self.FileName, self.CurrentLineNumber)\r
3285 TemplateName = self.__Token\r
3286\r
3287 if not self.__IsToken( "]"):\r
3288 raise Warning("expected ']'", self.FileName, self.CurrentLineNumber)\r
3289\r
3290 RuleObj = self.__GetRuleFileStatements()\r
3291 RuleObj.Arch = Arch.upper()\r
3292 RuleObj.ModuleType = ModuleType\r
3293 RuleObj.TemplateName = TemplateName\r
3294 if TemplateName == '' :\r
3295 self.Profile.RuleDict['RULE' + \\r
3296 '.' + \\r
3297 Arch.upper() + \\r
3298 '.' + \\r
3299 ModuleType.upper() ] = RuleObj\r
3300 else :\r
3301 self.Profile.RuleDict['RULE' + \\r
3302 '.' + \\r
3303 Arch.upper() + \\r
3304 '.' + \\r
3305 ModuleType.upper() + \\r
3306 '.' + \\r
3307 TemplateName.upper() ] = RuleObj\r
3308# self.Profile.RuleList.append(rule)\r
3309 return True\r
3310\r
3311 ## __GetModuleType() method\r
3312 #\r
3313 # Return the module type\r
3314 #\r
3315 # @param self The object pointer\r
3316 # @retval string module type\r
3317 #\r
3318 def __GetModuleType(self):\r
3319\r
3320 if not self.__GetNextWord():\r
3321 raise Warning("expected Module type", self.FileName, self.CurrentLineNumber)\r
3322 if self.__Token.upper() not in ("SEC", "PEI_CORE", "PEIM", "DXE_CORE", \\r
3323 "DXE_DRIVER", "DXE_SAL_DRIVER", \\r
3324 "DXE_SMM_DRIVER", "DXE_RUNTIME_DRIVER", \\r
3325 "UEFI_DRIVER", "UEFI_APPLICATION", "USER_DEFINED", "DEFAULT", "BASE", \\r
3326 "SECURITY_CORE", "COMBINED_PEIM_DRIVER", "PIC_PEIM", "RELOCATABLE_PEIM", \\r
b303ea72 3327 "PE32_PEIM", "BS_DRIVER", "RT_DRIVER", "SAL_RT_DRIVER", "APPLICATION", "ACPITABLE", "SMM_CORE"):\r
30fdf114
LG
3328 raise Warning("Unknown Module type '%s'" % self.__Token, self.FileName, self.CurrentLineNumber)\r
3329 return self.__Token\r
3330\r
3331 ## __GetFileExtension() method\r
3332 #\r
3333 # Return the file extension\r
3334 #\r
3335 # @param self The object pointer\r
3336 # @retval string file name extension\r
3337 #\r
3338 def __GetFileExtension(self):\r
3339 if not self.__IsToken("."):\r
3340 raise Warning("expected '.'", self.FileName, self.CurrentLineNumber)\r
3341\r
3342 Ext = ""\r
3343 if self.__GetNextToken():\r
3344 Pattern = re.compile(r'([a-zA-Z][a-zA-Z0-9]*)')\r
3345 if Pattern.match(self.__Token):\r
3346 Ext = self.__Token\r
3347 return '.' + Ext\r
3348 else:\r
3349 raise Warning("Unknown file extension '%s'" % self.__Token, self.FileName, self.CurrentLineNumber)\r
3350\r
3351 else:\r
3352 raise Warning("expected file extension", self.FileName, self.CurrentLineNumber)\r
3353\r
3354 ## __GetRuleFileStatement() method\r
3355 #\r
3356 # Get rule contents\r
3357 #\r
3358 # @param self The object pointer\r
3359 # @retval Rule Rule object\r
3360 #\r
3361 def __GetRuleFileStatements(self):\r
3362\r
3363 if not self.__IsKeyword("FILE"):\r
3364 raise Warning("expected FILE", self.FileName, self.CurrentLineNumber)\r
3365\r
3366 if not self.__GetNextWord():\r
3367 raise Warning("expected FFS type", self.FileName, self.CurrentLineNumber)\r
3368\r
3369 Type = self.__Token.strip().upper()\r
3370 if Type not in ("RAW", "FREEFORM", "SEC", "PEI_CORE", "PEIM",\\r
b303ea72 3371 "PEI_DXE_COMBO", "DRIVER", "DXE_CORE", "APPLICATION", "FV_IMAGE", "SMM", "SMM_CORE"):\r
30fdf114
LG
3372 raise Warning("Unknown FV type '%s'" % self.__Token, self.FileName, self.CurrentLineNumber)\r
3373\r
3374 if not self.__IsToken("="):\r
3375 raise Warning("expected '='", self.FileName, self.CurrentLineNumber)\r
3376\r
3377 if not self.__IsKeyword("$(NAMED_GUID)"):\r
3378 if not self.__GetNextWord():\r
3379 raise Warning("expected $(NAMED_GUID)", self.FileName, self.CurrentLineNumber)\r
3380 if self.__Token == 'PCD':\r
3381 if not self.__IsToken( "("):\r
3382 raise Warning("expected '('", self.FileName, self.CurrentLineNumber)\r
3383 PcdPair = self.__GetNextPcdName()\r
3384 if not self.__IsToken( ")"):\r
3385 raise Warning("expected ')'", self.FileName, self.CurrentLineNumber)\r
3386 self.__Token = 'PCD('+PcdPair[1]+'.'+PcdPair[0]+')'\r
3387 \r
3388 NameGuid = self.__Token\r
3389\r
3390 KeepReloc = None\r
3391 if self.__IsKeyword('RELOCS_STRIPPED') or self.__IsKeyword('RELOCS_RETAINED'):\r
3392 if self.__FileCouldHaveRelocFlag(Type):\r
3393 if self.__Token == 'RELOCS_STRIPPED':\r
3394 KeepReloc = False\r
3395 else:\r
3396 KeepReloc = True\r
3397 else:\r
3398 raise Warning("File type %s could not have reloc strip flag%d" % (Type, self.CurrentLineNumber), self.FileName, self.CurrentLineNumber)\r
3399\r
3400 KeyStringList = []\r
3401 if self.__GetNextToken():\r
3402 Pattern = re.compile(r'([a-zA-Z0-9\-]+|\$\(TARGET\)|\*)_([a-zA-Z0-9\-]+|\$\(TOOL_CHAIN_TAG\)|\*)_([a-zA-Z0-9\-]+|\$\(ARCH\)|\*)')\r
3403 if Pattern.match(self.__Token):\r
3404 KeyStringList.append(self.__Token)\r
3405 if self.__IsToken(","):\r
3406 while self.__GetNextToken():\r
3407 if not Pattern.match(self.__Token):\r
3408 raise Warning("expected KeyString \"Target_Tag_Arch\"", self.FileName, self.CurrentLineNumber)\r
3409 KeyStringList.append(self.__Token)\r
3410\r
3411 if not self.__IsToken(","):\r
3412 break\r
3413\r
3414 else:\r
3415 self.__UndoToken()\r
3416\r
3417\r
3418 Fixed = False\r
3419 if self.__IsKeyword("Fixed", True):\r
3420 Fixed = True\r
3421\r
3422 CheckSum = False\r
3423 if self.__IsKeyword("CheckSum", True):\r
3424 CheckSum = True\r
3425\r
3426 AlignValue = ""\r
3427 if self.__GetAlignment():\r
52302d4d 3428 if self.__Token not in ("Auto", "8", "16", "32", "64", "128", "512", "1K", "4K", "32K" ,"64K"):\r
30fdf114 3429 raise Warning("Incorrect alignment '%s'" % self.__Token, self.FileName, self.CurrentLineNumber)\r
52302d4d
LG
3430 #For FFS, Auto is default option same to ""\r
3431 if not self.__Token == "Auto":\r
3432 AlignValue = self.__Token\r
30fdf114
LG
3433\r
3434 if self.__IsToken("{"):\r
3435 # Complex file rule expected\r
3436 Rule = RuleComplexFile.RuleComplexFile()\r
3437 Rule.FvFileType = Type\r
3438 Rule.NameGuid = NameGuid\r
3439 Rule.Alignment = AlignValue\r
3440 Rule.CheckSum = CheckSum\r
3441 Rule.Fixed = Fixed\r
3442 Rule.KeyStringList = KeyStringList\r
3443 if KeepReloc != None:\r
3444 Rule.KeepReloc = KeepReloc\r
3445\r
3446 while True:\r
3447 IsEncapsulate = self.__GetRuleEncapsulationSection(Rule)\r
3448 IsLeaf = self.__GetEfiSection(Rule)\r
3449 if not IsEncapsulate and not IsLeaf:\r
3450 break\r
3451\r
3452 if not self.__IsToken("}"):\r
3453 raise Warning("expected '}'", self.FileName, self.CurrentLineNumber)\r
3454\r
3455 return Rule\r
3456\r
30fdf114
LG
3457 else:\r
3458 # Simple file rule expected\r
3459 if not self.__GetNextWord():\r
3460 raise Warning("expected leaf section type", self.FileName, self.CurrentLineNumber)\r
3461\r
3462 SectionName = self.__Token\r
3463\r
3464 if SectionName not in ("COMPAT16", "PE32", "PIC", "TE", "FV_IMAGE", "RAW", "DXE_DEPEX",\\r
3465 "UI", "PEI_DEPEX", "VERSION", "SUBTYPE_GUID", "SMM_DEPEX"):\r
3466 raise Warning("Unknown leaf section name '%s'" % SectionName, self.FileName, self.CurrentLineNumber)\r
3467\r
3468\r
3469 if self.__IsKeyword("Fixed", True):\r
3470 Fixed = True\r
3471\r
3472 if self.__IsKeyword("CheckSum", True):\r
3473 CheckSum = True\r
3474\r
52302d4d 3475 SectAlignment = ""\r
30fdf114 3476 if self.__GetAlignment():\r
52302d4d 3477 if self.__Token not in ("Auto", "8", "16", "32", "64", "128", "512", "1K", "4K", "32K" ,"64K"):\r
30fdf114 3478 raise Warning("Incorrect alignment '%s'" % self.__Token, self.FileName, self.CurrentLineNumber)\r
52302d4d
LG
3479 if self.__Token == 'Auto' and (not SectionName == 'PE32') and (not SectionName == 'TE'):\r
3480 raise Warning("Auto alignment can only be used in PE32 or TE section ", self.FileName, self.CurrentLineNumber)\r
3481 SectAlignment = self.__Token\r
3482\r
3483 Ext = None\r
3484 if self.__IsToken('|'):\r
3485 Ext = self.__GetFileExtension()\r
3486 elif not self.__GetNextToken():\r
30fdf114
LG
3487 raise Warning("expected File name", self.FileName, self.CurrentLineNumber)\r
3488\r
3489 Rule = RuleSimpleFile.RuleSimpleFile()\r
3490 Rule.SectionType = SectionName\r
3491 Rule.FvFileType = Type\r
3492 Rule.NameGuid = NameGuid\r
3493 Rule.Alignment = AlignValue\r
52302d4d 3494 Rule.SectAlignment = SectAlignment\r
30fdf114
LG
3495 Rule.CheckSum = CheckSum\r
3496 Rule.Fixed = Fixed\r
30fdf114
LG
3497 Rule.KeyStringList = KeyStringList\r
3498 if KeepReloc != None:\r
3499 Rule.KeepReloc = KeepReloc\r
52302d4d
LG
3500 Rule.FileExtension = Ext\r
3501 Rule.FileName = self.__Token\r
30fdf114
LG
3502 return Rule\r
3503\r
3504 ## __GetEfiSection() method\r
3505 #\r
3506 # Get section list for Rule\r
3507 #\r
3508 # @param self The object pointer\r
3509 # @param Obj for whom section is got\r
3510 # @retval True Successfully find section statement\r
3511 # @retval False Not able to find section statement\r
3512 #\r
3513 def __GetEfiSection(self, Obj):\r
3514\r
3515 OldPos = self.GetFileBufferPos()\r
3516 if not self.__GetNextWord():\r
3517 return False\r
3518 SectionName = self.__Token\r
3519\r
3520 if SectionName not in ("COMPAT16", "PE32", "PIC", "TE", "FV_IMAGE", "RAW", "DXE_DEPEX",\\r
3521 "UI", "VERSION", "PEI_DEPEX", "GUID", "SMM_DEPEX"):\r
3522 self.__UndoToken()\r
3523 return False\r
3524\r
3525 if SectionName == "FV_IMAGE":\r
3526 FvImageSectionObj = FvImageSection.FvImageSection()\r
3527 if self.__IsKeyword("FV_IMAGE"):\r
3528 pass\r
3529 if self.__IsToken( "{"):\r
3530 FvObj = Fv.FV()\r
3531 self.__GetDefineStatements(FvObj)\r
3532 self.__GetBlockStatement(FvObj)\r
3533 self.__GetSetStatements(FvObj)\r
3534 self.__GetFvAlignment(FvObj)\r
3535 self.__GetFvAttributes(FvObj)\r
3536 self.__GetAprioriSection(FvObj)\r
3537 self.__GetAprioriSection(FvObj)\r
3538\r
3539 while True:\r
3540 IsInf = self.__GetInfStatement(FvObj)\r
3541 IsFile = self.__GetFileStatement(FvObj)\r
3542 if not IsInf and not IsFile:\r
3543 break\r
3544\r
3545 if not self.__IsToken( "}"):\r
3546 raise Warning("expected '}'", self.FileName, self.CurrentLineNumber)\r
3547 FvImageSectionObj.Fv = FvObj\r
3548 FvImageSectionObj.FvName = None\r
3549\r
3550 else:\r
3551 if not self.__IsKeyword("FV"):\r
3552 raise Warning("expected 'FV'", self.FileName, self.CurrentLineNumber)\r
3553 FvImageSectionObj.FvFileType = self.__Token\r
3554\r
30fdf114
LG
3555 if self.__GetAlignment():\r
3556 if self.__Token not in ("8", "16", "32", "64", "128", "512", "1K", "4K", "32K" ,"64K"):\r
3557 raise Warning("Incorrect alignment '%s'" % self.__Token, self.FileName, self.CurrentLineNumber)\r
3558 FvImageSectionObj.Alignment = self.__Token\r
3559\r
3560 if self.__IsToken('|'):\r
3561 FvImageSectionObj.FvFileExtension = self.__GetFileExtension()\r
3562 elif self.__GetNextToken():\r
3563 if self.__Token not in ("}", "COMPAT16", "PE32", "PIC", "TE", "FV_IMAGE", "RAW", "DXE_DEPEX",\\r
3564 "UI", "VERSION", "PEI_DEPEX", "GUID", "SMM_DEPEX"):\r
3565 FvImageSectionObj.FvFileName = self.__Token\r
3566 else:\r
3567 self.__UndoToken()\r
3568 else:\r
3569 raise Warning("expected FV file name", self.FileName, self.CurrentLineNumber)\r
3570\r
3571 Obj.SectionList.append(FvImageSectionObj)\r
3572 return True\r
3573\r
3574 EfiSectionObj = EfiSection.EfiSection()\r
3575 EfiSectionObj.SectionType = SectionName\r
3576\r
3577 if not self.__GetNextToken():\r
3578 raise Warning("expected file type", self.FileName, self.CurrentLineNumber)\r
3579\r
3580 if self.__Token == "STRING":\r
3581 if not self.__RuleSectionCouldHaveString(EfiSectionObj.SectionType):\r
3582 raise Warning("%s section could NOT have string data%d" % (EfiSectionObj.SectionType, self.CurrentLineNumber), self.FileName, self.CurrentLineNumber)\r
3583\r
3584 if not self.__IsToken('='):\r
3585 raise Warning("expected '='", self.FileName, self.CurrentLineNumber)\r
3586\r
3587 if not self.__GetNextToken():\r
3588 raise Warning("expected Quoted String", self.FileName, self.CurrentLineNumber)\r
3589\r
3590 if self.__GetStringData():\r
3591 EfiSectionObj.StringData = self.__Token\r
3592\r
3593 if self.__IsKeyword("BUILD_NUM"):\r
3594 if not self.__RuleSectionCouldHaveBuildNum(EfiSectionObj.SectionType):\r
3595 raise Warning("%s section could NOT have BUILD_NUM%d" % (EfiSectionObj.SectionType, self.CurrentLineNumber), self.FileName, self.CurrentLineNumber)\r
3596\r
3597 if not self.__IsToken("="):\r
3598 raise Warning("expected '='", self.FileName, self.CurrentLineNumber)\r
3599 if not self.__GetNextToken():\r
3600 raise Warning("expected Build number", self.FileName, self.CurrentLineNumber)\r
3601 EfiSectionObj.BuildNum = self.__Token\r
3602\r
3603 else:\r
3604 EfiSectionObj.FileType = self.__Token\r
3605 self.__CheckRuleSectionFileType(EfiSectionObj.SectionType, EfiSectionObj.FileType)\r
3606\r
3607 if self.__IsKeyword("Optional"):\r
3608 if not self.__RuleSectionCouldBeOptional(EfiSectionObj.SectionType):\r
3609 raise Warning("%s section could NOT be optional%d" % (EfiSectionObj.SectionType, self.CurrentLineNumber), self.FileName, self.CurrentLineNumber)\r
3610 EfiSectionObj.Optional = True\r
3611\r
3612 if self.__IsKeyword("BUILD_NUM"):\r
3613 if not self.__RuleSectionCouldHaveBuildNum(EfiSectionObj.SectionType):\r
3614 raise Warning("%s section could NOT have BUILD_NUM%d" % (EfiSectionObj.SectionType, self.CurrentLineNumber), self.FileName, self.CurrentLineNumber)\r
3615\r
3616 if not self.__IsToken("="):\r
3617 raise Warning("expected '='", self.FileName, self.CurrentLineNumber)\r
3618 if not self.__GetNextToken():\r
3619 raise Warning("expected Build number", self.FileName, self.CurrentLineNumber)\r
3620 EfiSectionObj.BuildNum = self.__Token\r
3621\r
3622 if self.__GetAlignment():\r
52302d4d
LG
3623 if self.__Token not in ("Auto", "8", "16", "32", "64", "128", "512", "1K", "4K", "32K" ,"64K"):\r
3624 raise Warning("Incorrect alignment '%s'" % self.__Token, self.FileName, self.CurrentLineNumber)\r
3625 if self.__Token == 'Auto' and (not SectionName == 'PE32') and (not SectionName == 'TE'):\r
3626 raise Warning("Auto alignment can only be used in PE32 or TE section ", self.FileName, self.CurrentLineNumber)\r
30fdf114
LG
3627 EfiSectionObj.Alignment = self.__Token\r
3628\r
3629 if self.__IsKeyword('RELOCS_STRIPPED') or self.__IsKeyword('RELOCS_RETAINED'):\r
3630 if self.__SectionCouldHaveRelocFlag(EfiSectionObj.SectionType):\r
3631 if self.__Token == 'RELOCS_STRIPPED':\r
3632 EfiSectionObj.KeepReloc = False\r
3633 else:\r
3634 EfiSectionObj.KeepReloc = True\r
3635 if Obj.KeepReloc != None and Obj.KeepReloc != EfiSectionObj.KeepReloc:\r
3636 raise Warning("Section type %s has reloc strip flag conflict with Rule" % EfiSectionObj.SectionType, self.FileName, self.CurrentLineNumber)\r
3637 else:\r
3638 raise Warning("Section type %s could not have reloc strip flag" % EfiSectionObj.SectionType, self.FileName, self.CurrentLineNumber)\r
3639\r
3640\r
3641 if self.__IsToken('|'):\r
3642 EfiSectionObj.FileExtension = self.__GetFileExtension()\r
3643 elif self.__GetNextToken():\r
3644 if self.__Token not in ("}", "COMPAT16", "PE32", "PIC", "TE", "FV_IMAGE", "RAW", "DXE_DEPEX",\\r
3645 "UI", "VERSION", "PEI_DEPEX", "GUID", "SMM_DEPEX"):\r
3646 \r
3647 if self.__Token.startswith('PCD'):\r
3648 self.__UndoToken()\r
3649 self.__GetNextWord()\r
3650 \r
3651 if self.__Token == 'PCD':\r
3652 if not self.__IsToken( "("):\r
3653 raise Warning("expected '('", self.FileName, self.CurrentLineNumber)\r
3654 PcdPair = self.__GetNextPcdName()\r
3655 if not self.__IsToken( ")"):\r
3656 raise Warning("expected ')'", self.FileName, self.CurrentLineNumber)\r
3657 self.__Token = 'PCD('+PcdPair[1]+'.'+PcdPair[0]+')'\r
3658 \r
3659 EfiSectionObj.FileName = self.__Token \r
3660 \r
3661 else:\r
3662 self.__UndoToken()\r
3663 else:\r
3664 raise Warning("expected section file name", self.FileName, self.CurrentLineNumber)\r
3665\r
3666 Obj.SectionList.append(EfiSectionObj)\r
3667 return True\r
3668\r
3669 ## __RuleSectionCouldBeOptional() method\r
3670 #\r
3671 # Get whether a section could be optional\r
3672 #\r
3673 # @param self The object pointer\r
3674 # @param SectionType The section type to check\r
3675 # @retval True section could be optional\r
3676 # @retval False section never optional\r
3677 #\r
3678 def __RuleSectionCouldBeOptional(self, SectionType):\r
3679 if SectionType in ("DXE_DEPEX", "UI", "VERSION", "PEI_DEPEX", "RAW", "SMM_DEPEX"):\r
3680 return True\r
3681 else:\r
3682 return False\r
3683\r
3684 ## __RuleSectionCouldHaveBuildNum() method\r
3685 #\r
3686 # Get whether a section could have build number information\r
3687 #\r
3688 # @param self The object pointer\r
3689 # @param SectionType The section type to check\r
3690 # @retval True section could have build number information\r
3691 # @retval False section never have build number information\r
3692 #\r
3693 def __RuleSectionCouldHaveBuildNum(self, SectionType):\r
3694 if SectionType in ("VERSION"):\r
3695 return True\r
3696 else:\r
3697 return False\r
3698\r
3699 ## __RuleSectionCouldHaveString() method\r
3700 #\r
3701 # Get whether a section could have string\r
3702 #\r
3703 # @param self The object pointer\r
3704 # @param SectionType The section type to check\r
3705 # @retval True section could have string\r
3706 # @retval False section never have string\r
3707 #\r
3708 def __RuleSectionCouldHaveString(self, SectionType):\r
3709 if SectionType in ("UI", "VERSION"):\r
3710 return True\r
3711 else:\r
3712 return False\r
3713\r
3714 ## __CheckRuleSectionFileType() method\r
3715 #\r
3716 # Get whether a section matches a file type\r
3717 #\r
3718 # @param self The object pointer\r
3719 # @param SectionType The section type to check\r
3720 # @param FileType The file type to check\r
3721 #\r
3722 def __CheckRuleSectionFileType(self, SectionType, FileType):\r
3723 if SectionType == "COMPAT16":\r
3724 if FileType not in ("COMPAT16", "SEC_COMPAT16"):\r
3725 raise Warning("Incorrect section file type '%s'" % FileType, self.FileName, self.CurrentLineNumber)\r
3726 elif SectionType == "PE32":\r
3727 if FileType not in ("PE32", "SEC_PE32"):\r
3728 raise Warning("Incorrect section file type '%s'" % FileType, self.FileName, self.CurrentLineNumber)\r
3729 elif SectionType == "PIC":\r
3730 if FileType not in ("PIC", "PIC"):\r
3731 raise Warning("Incorrect section file type '%s'" % FileType, self.FileName, self.CurrentLineNumber)\r
3732 elif SectionType == "TE":\r
3733 if FileType not in ("TE", "SEC_TE"):\r
3734 raise Warning("Incorrect section file type '%s'" % FileType, self.FileName, self.CurrentLineNumber)\r
3735 elif SectionType == "RAW":\r
3736 if FileType not in ("BIN", "SEC_BIN", "RAW", "ASL", "ACPI"):\r
3737 raise Warning("Incorrect section file type '%s'" % FileType, self.FileName, self.CurrentLineNumber)\r
b303ea72
LG
3738 elif SectionType == "DXE_DEPEX" or SectionType == "SMM_DEPEX":\r
3739 if FileType not in ("DXE_DEPEX", "SEC_DXE_DEPEX", "SMM_DEPEX"):\r
30fdf114
LG
3740 raise Warning("Incorrect section file type '%s'" % FileType, self.FileName, self.CurrentLineNumber)\r
3741 elif SectionType == "UI":\r
3742 if FileType not in ("UI", "SEC_UI"):\r
3743 raise Warning("Incorrect section file type '%s'" % FileType, self.FileName, self.CurrentLineNumber)\r
3744 elif SectionType == "VERSION":\r
3745 if FileType not in ("VERSION", "SEC_VERSION"):\r
3746 raise Warning("Incorrect section file type '%s'" % FileType, self.FileName, self.CurrentLineNumber)\r
3747 elif SectionType == "PEI_DEPEX":\r
3748 if FileType not in ("PEI_DEPEX", "SEC_PEI_DEPEX"):\r
3749 raise Warning("Incorrect section file type '%s'" % FileType, self.FileName, self.CurrentLineNumber)\r
3750 elif SectionType == "GUID":\r
3751 if FileType not in ("PE32", "SEC_GUID"):\r
3752 raise Warning("Incorrect section file type '%s'" % FileType, self.FileName, self.CurrentLineNumber)\r
3753\r
3754 ## __GetRuleEncapsulationSection() method\r
3755 #\r
3756 # Get encapsulation section for Rule\r
3757 #\r
3758 # @param self The object pointer\r
3759 # @param Rule for whom section is got\r
3760 # @retval True Successfully find section statement\r
3761 # @retval False Not able to find section statement\r
3762 #\r
3763 def __GetRuleEncapsulationSection(self, Rule):\r
3764\r
3765 if self.__IsKeyword( "COMPRESS"):\r
3766 Type = "PI_STD"\r
3767 if self.__IsKeyword("PI_STD") or self.__IsKeyword("PI_NONE"):\r
3768 Type = self.__Token\r
3769\r
3770 if not self.__IsToken("{"):\r
3771 raise Warning("expected '{'", self.FileName, self.CurrentLineNumber)\r
3772\r
3773 CompressSectionObj = CompressSection.CompressSection()\r
3774\r
3775 CompressSectionObj.CompType = Type\r
3776 # Recursive sections...\r
3777 while True:\r
3778 IsEncapsulate = self.__GetRuleEncapsulationSection(CompressSectionObj)\r
3779 IsLeaf = self.__GetEfiSection(CompressSectionObj)\r
3780 if not IsEncapsulate and not IsLeaf:\r
3781 break\r
3782\r
3783 if not self.__IsToken( "}"):\r
3784 raise Warning("expected '}'", self.FileName, self.CurrentLineNumber)\r
3785 Rule.SectionList.append(CompressSectionObj)\r
3786\r
3787 return True\r
3788\r
3789 elif self.__IsKeyword( "GUIDED"):\r
3790 GuidValue = None\r
3791 if self.__GetNextGuid():\r
3792 GuidValue = self.__Token\r
3793\r
3794 if self.__IsKeyword( "$(NAMED_GUID)"):\r
3795 GuidValue = self.__Token\r
3796\r
3797 AttribDict = self.__GetGuidAttrib()\r
3798\r
3799 if not self.__IsToken("{"):\r
3800 raise Warning("expected '{'", self.FileName, self.CurrentLineNumber)\r
3801 GuidSectionObj = GuidSection.GuidSection()\r
3802 GuidSectionObj.NameGuid = GuidValue\r
3803 GuidSectionObj.SectionType = "GUIDED"\r
3804 GuidSectionObj.ProcessRequired = AttribDict["PROCESSING_REQUIRED"]\r
3805 GuidSectionObj.AuthStatusValid = AttribDict["AUTH_STATUS_VALID"]\r
25918452 3806 GuidSectionObj.ExtraHeaderSize = AttribDict["EXTRA_HEADER_SIZE"]\r
30fdf114
LG
3807\r
3808 # Efi sections...\r
3809 while True:\r
3810 IsEncapsulate = self.__GetRuleEncapsulationSection(GuidSectionObj)\r
3811 IsLeaf = self.__GetEfiSection(GuidSectionObj)\r
3812 if not IsEncapsulate and not IsLeaf:\r
3813 break\r
3814\r
3815 if not self.__IsToken( "}"):\r
3816 raise Warning("expected '}'", self.FileName, self.CurrentLineNumber)\r
3817 Rule.SectionList.append(GuidSectionObj)\r
3818\r
3819 return True\r
3820\r
3821 return False\r
3822\r
3823 ## __GetVtf() method\r
3824 #\r
3825 # Get VTF section contents and store its data into VTF list of self.Profile\r
3826 #\r
3827 # @param self The object pointer\r
3828 # @retval True Successfully find a VTF\r
3829 # @retval False Not able to find a VTF\r
3830 #\r
3831 def __GetVtf(self):\r
3832\r
3833 if not self.__GetNextToken():\r
3834 return False\r
3835\r
3836 S = self.__Token.upper()\r
3837 if S.startswith("[") and not S.startswith("[VTF."):\r
3838 if not S.startswith("[RULE.") and not S.startswith("[OPTIONROM."):\r
3839 raise Warning("Unknown section or section appear sequence error (The correct sequence should be [FD.], [FV.], [Capsule.], [VTF.], [Rule.], [OptionRom.])", self.FileName, self.CurrentLineNumber)\r
3840 self.__UndoToken()\r
3841 return False\r
3842\r
3843 self.__UndoToken()\r
3844 if not self.__IsToken("[VTF.", True):\r
3845 FileLineTuple = GetRealFileLine(self.FileName, self.CurrentLineNumber)\r
3846 #print 'Parsing String: %s in File %s, At line: %d, Offset Within Line: %d' \\r
3847 # % (self.Profile.FileLinesList[self.CurrentLineNumber - 1][self.CurrentOffsetWithinLine :], FileLineTuple[0], FileLineTuple[1], self.CurrentOffsetWithinLine)\r
3848 raise Warning("expected [VTF.]", self.FileName, self.CurrentLineNumber)\r
3849\r
3850 if not self.__SkipToToken("."):\r
3851 raise Warning("expected '.'", self.FileName, self.CurrentLineNumber)\r
3852\r
3853 Arch = self.__SkippedChars.rstrip(".").upper()\r
4afd3d04 3854 if Arch not in ("IA32", "X64", "IPF", "ARM", "AARCH64"):\r
30fdf114
LG
3855 raise Warning("Unknown Arch '%s'" % Arch, self.FileName, self.CurrentLineNumber)\r
3856\r
3857 if not self.__GetNextWord():\r
3858 raise Warning("expected VTF name", self.FileName, self.CurrentLineNumber)\r
3859 Name = self.__Token.upper()\r
3860\r
3861 VtfObj = Vtf.Vtf()\r
3862 VtfObj.UiName = Name\r
3863 VtfObj.KeyArch = Arch\r
3864\r
3865 if self.__IsToken(","):\r
3866 if not self.__GetNextWord():\r
3867 raise Warning("expected Arch list", self.FileName, self.CurrentLineNumber)\r
4afd3d04 3868 if self.__Token.upper() not in ("IA32", "X64", "IPF", "ARM", "AARCH64"):\r
30fdf114
LG
3869 raise Warning("Unknown Arch '%s'" % self.__Token, self.FileName, self.CurrentLineNumber)\r
3870 VtfObj.ArchList = self.__Token.upper()\r
3871\r
3872 if not self.__IsToken( "]"):\r
3873 raise Warning("expected ']'", self.FileName, self.CurrentLineNumber)\r
3874\r
3875 if self.__IsKeyword("IA32_RST_BIN"):\r
3876 if not self.__IsToken("="):\r
3877 raise Warning("expected '='", self.FileName, self.CurrentLineNumber)\r
3878\r
3879 if not self.__GetNextToken():\r
3880 raise Warning("expected Reset file", self.FileName, self.CurrentLineNumber)\r
3881\r
3882 VtfObj.ResetBin = self.__Token\r
6310ffd7 3883 if VtfObj.ResetBin.replace('$(WORKSPACE)', '').find('$') == -1:\r
3884 #check for file path\r
3885 ErrorCode, ErrorInfo = PathClass(NormPath(VtfObj.ResetBin), GenFdsGlobalVariable.WorkSpaceDir).Validate()\r
3886 if ErrorCode != 0:\r
3887 EdkLogger.error("GenFds", ErrorCode, ExtraData=ErrorInfo)\r
30fdf114
LG
3888\r
3889 while self.__GetComponentStatement(VtfObj):\r
3890 pass\r
3891\r
3892 self.Profile.VtfList.append(VtfObj)\r
3893 return True\r
3894\r
3895 ## __GetComponentStatement() method\r
3896 #\r
3897 # Get components in VTF\r
3898 #\r
3899 # @param self The object pointer\r
3900 # @param VtfObj for whom component is got\r
3901 # @retval True Successfully find a component\r
3902 # @retval False Not able to find a component\r
3903 #\r
3904 def __GetComponentStatement(self, VtfObj):\r
3905\r
3906 if not self.__IsKeyword("COMP_NAME"):\r
3907 return False\r
3908\r
3909 if not self.__IsToken("="):\r
3910 raise Warning("expected '='", self.FileName, self.CurrentLineNumber)\r
3911\r
3912 if not self.__GetNextWord():\r
3913 raise Warning("expected Component Name", self.FileName, self.CurrentLineNumber)\r
3914\r
3915 CompStatementObj = ComponentStatement.ComponentStatement()\r
3916 CompStatementObj.CompName = self.__Token\r
3917\r
3918 if not self.__IsKeyword("COMP_LOC"):\r
3919 raise Warning("expected COMP_LOC", self.FileName, self.CurrentLineNumber)\r
3920\r
3921 if not self.__IsToken("="):\r
3922 raise Warning("expected '='", self.FileName, self.CurrentLineNumber)\r
3923\r
3924 CompStatementObj.CompLoc = ""\r
3925 if self.__GetNextWord():\r
3926 CompStatementObj.CompLoc = self.__Token\r
3927 if self.__IsToken('|'):\r
3928 if not self.__GetNextWord():\r
3929 raise Warning("Expected Region Name", self.FileName, self.CurrentLineNumber)\r
3930\r
3931 if self.__Token not in ("F", "N", "S"): #, "H", "L", "PH", "PL"): not support\r
3932 raise Warning("Unknown location type '%s'" % self.__Token, self.FileName, self.CurrentLineNumber)\r
3933\r
3934 CompStatementObj.FilePos = self.__Token\r
3935 else:\r
3936 self.CurrentLineNumber += 1\r
3937 self.CurrentOffsetWithinLine = 0\r
3938\r
3939 if not self.__IsKeyword("COMP_TYPE"):\r
3940 raise Warning("expected COMP_TYPE", self.FileName, self.CurrentLineNumber)\r
3941\r
3942 if not self.__IsToken("="):\r
3943 raise Warning("expected '='", self.FileName, self.CurrentLineNumber)\r
3944\r
3945 if not self.__GetNextToken():\r
3946 raise Warning("expected Component type", self.FileName, self.CurrentLineNumber)\r
3947 if self.__Token not in ("FIT", "PAL_B", "PAL_A", "OEM"):\r
3948 if not self.__Token.startswith("0x") or len(self.__Token) < 3 or len(self.__Token) > 4 or \\r
3949 not self.__HexDigit(self.__Token[2]) or not self.__HexDigit(self.__Token[-1]):\r
3950 raise Warning("Unknown location type '%s'" % self.__Token, self.FileName, self.CurrentLineNumber)\r
3951 CompStatementObj.CompType = self.__Token\r
3952\r
3953 if not self.__IsKeyword("COMP_VER"):\r
3954 raise Warning("expected COMP_VER", self.FileName, self.CurrentLineNumber)\r
3955\r
3956 if not self.__IsToken("="):\r
3957 raise Warning("expected '='", self.FileName, self.CurrentLineNumber)\r
3958\r
3959 if not self.__GetNextToken():\r
3960 raise Warning("expected Component version", self.FileName, self.CurrentLineNumber)\r
3961\r
9fd2164e 3962 Pattern = re.compile('-$|[0-9a-fA-F]{1,2}\.[0-9a-fA-F]{1,2}$', re.DOTALL)\r
30fdf114
LG
3963 if Pattern.match(self.__Token) == None:\r
3964 raise Warning("Unknown version format '%s'" % self.__Token, self.FileName, self.CurrentLineNumber)\r
3965 CompStatementObj.CompVer = self.__Token\r
3966\r
3967 if not self.__IsKeyword("COMP_CS"):\r
3968 raise Warning("expected COMP_CS", self.FileName, self.CurrentLineNumber)\r
3969\r
3970 if not self.__IsToken("="):\r
3971 raise Warning("expected '='", self.FileName, self.CurrentLineNumber)\r
3972\r
3973 if not self.__GetNextToken():\r
3974 raise Warning("expected Component CS", self.FileName, self.CurrentLineNumber)\r
3975 if self.__Token not in ("1", "0"):\r
3976 raise Warning("Unknown Component CS '%s'" % self.__Token, self.FileName, self.CurrentLineNumber)\r
3977 CompStatementObj.CompCs = self.__Token\r
3978\r
3979\r
3980 if not self.__IsKeyword("COMP_BIN"):\r
3981 raise Warning("expected COMP_BIN", self.FileName, self.CurrentLineNumber)\r
3982\r
3983 if not self.__IsToken("="):\r
3984 raise Warning("expected '='", self.FileName, self.CurrentLineNumber)\r
3985\r
3986 if not self.__GetNextToken():\r
3987 raise Warning("expected Component file", self.FileName, self.CurrentLineNumber)\r
3988\r
3989 CompStatementObj.CompBin = self.__Token\r
6310ffd7 3990 if CompStatementObj.CompBin != '-' and CompStatementObj.CompBin.replace('$(WORKSPACE)', '').find('$') == -1:\r
3991 #check for file path\r
3992 ErrorCode, ErrorInfo = PathClass(NormPath(CompStatementObj.CompBin), GenFdsGlobalVariable.WorkSpaceDir).Validate()\r
3993 if ErrorCode != 0:\r
3994 EdkLogger.error("GenFds", ErrorCode, ExtraData=ErrorInfo)\r
30fdf114
LG
3995\r
3996 if not self.__IsKeyword("COMP_SYM"):\r
3997 raise Warning("expected COMP_SYM", self.FileName, self.CurrentLineNumber)\r
3998\r
3999 if not self.__IsToken("="):\r
4000 raise Warning("expected '='", self.FileName, self.CurrentLineNumber)\r
4001\r
4002 if not self.__GetNextToken():\r
4003 raise Warning("expected Component symbol file", self.FileName, self.CurrentLineNumber)\r
4004\r
4005 CompStatementObj.CompSym = self.__Token\r
6310ffd7 4006 if CompStatementObj.CompSym != '-' and CompStatementObj.CompSym.replace('$(WORKSPACE)', '').find('$') == -1:\r
4007 #check for file path\r
4008 ErrorCode, ErrorInfo = PathClass(NormPath(CompStatementObj.CompSym), GenFdsGlobalVariable.WorkSpaceDir).Validate()\r
4009 if ErrorCode != 0:\r
4010 EdkLogger.error("GenFds", ErrorCode, ExtraData=ErrorInfo)\r
30fdf114
LG
4011\r
4012 if not self.__IsKeyword("COMP_SIZE"):\r
4013 raise Warning("expected COMP_SIZE", self.FileName, self.CurrentLineNumber)\r
4014\r
4015 if not self.__IsToken("="):\r
4016 raise Warning("expected '='", self.FileName, self.CurrentLineNumber)\r
4017\r
4018 if self.__IsToken("-"):\r
4019 CompStatementObj.CompSize = self.__Token\r
4020 elif self.__GetNextDecimalNumber():\r
4021 CompStatementObj.CompSize = self.__Token\r
4022 elif self.__GetNextHexNumber():\r
4023 CompStatementObj.CompSize = self.__Token\r
4024 else:\r
4025 raise Warning("Unknown size '%s'" % self.__Token, self.FileName, self.CurrentLineNumber)\r
4026\r
4027 VtfObj.ComponentStatementList.append(CompStatementObj)\r
4028 return True\r
4029\r
4030 ## __GetOptionRom() method\r
4031 #\r
4032 # Get OptionROM section contents and store its data into OptionROM list of self.Profile\r
4033 #\r
4034 # @param self The object pointer\r
4035 # @retval True Successfully find a OptionROM\r
4036 # @retval False Not able to find a OptionROM\r
4037 #\r
4038 def __GetOptionRom(self):\r
4039\r
4040 if not self.__GetNextToken():\r
4041 return False\r
4042\r
4043 S = self.__Token.upper()\r
4044 if S.startswith("[") and not S.startswith("[OPTIONROM."):\r
4045 raise Warning("Unknown section or section appear sequence error (The correct sequence should be [FD.], [FV.], [Capsule.], [VTF.], [Rule.], [OptionRom.])", self.FileName, self.CurrentLineNumber)\r
4046 \r
4047 self.__UndoToken()\r
4048 if not self.__IsToken("[OptionRom.", True):\r
4049 raise Warning("Unknown Keyword '%s'" % self.__Token, self.FileName, self.CurrentLineNumber)\r
4050\r
4051 OptRomName = self.__GetUiName()\r
4052\r
4053 if not self.__IsToken( "]"):\r
4054 raise Warning("expected ']'", self.FileName, self.CurrentLineNumber)\r
4055\r
4056 OptRomObj = OptionRom.OPTIONROM()\r
4057 OptRomObj.DriverName = OptRomName\r
4058 self.Profile.OptRomDict[OptRomName] = OptRomObj\r
4059\r
4060 while True:\r
4061 isInf = self.__GetOptRomInfStatement(OptRomObj)\r
4062 isFile = self.__GetOptRomFileStatement(OptRomObj)\r
4063 if not isInf and not isFile:\r
4064 break\r
4065 \r
4066 return True\r
4067\r
4068 ## __GetOptRomInfStatement() method\r
4069 #\r
4070 # Get INF statements\r
4071 #\r
4072 # @param self The object pointer\r
4073 # @param Obj for whom inf statement is got\r
4074 # @retval True Successfully find inf statement\r
4075 # @retval False Not able to find inf statement\r
4076 #\r
4077 def __GetOptRomInfStatement(self, Obj):\r
4078\r
4079 if not self.__IsKeyword( "INF"):\r
4080 return False\r
4081\r
4082 ffsInf = OptRomInfStatement.OptRomInfStatement()\r
4083 self.__GetInfOptions( ffsInf)\r
4084\r
4085 if not self.__GetNextToken():\r
4086 raise Warning("expected INF file path", self.FileName, self.CurrentLineNumber)\r
4087 ffsInf.InfFileName = self.__Token\r
6310ffd7 4088 if ffsInf.InfFileName.replace('$(WORKSPACE)', '').find('$') == -1:\r
4089 #check for file path\r
4090 ErrorCode, ErrorInfo = PathClass(NormPath(ffsInf.InfFileName), GenFdsGlobalVariable.WorkSpaceDir).Validate()\r
4091 if ErrorCode != 0:\r
4092 EdkLogger.error("GenFds", ErrorCode, ExtraData=ErrorInfo)\r
30fdf114
LG
4093\r
4094 if not ffsInf.InfFileName in self.Profile.InfList:\r
4095 self.Profile.InfList.append(ffsInf.InfFileName)\r
d0acc87a
LG
4096 FileLineTuple = GetRealFileLine(self.FileName, self.CurrentLineNumber)\r
4097 self.Profile.InfFileLineList.append(FileLineTuple)\r
30fdf114
LG
4098\r
4099 \r
4100 self.__GetOptRomOverrides (ffsInf)\r
4101 \r
4102 Obj.FfsList.append(ffsInf)\r
4103 return True\r
4104\r
4105 ## __GetOptRomOverrides() method\r
4106 #\r
4107 # Get overrides for OptROM INF & FILE\r
4108 #\r
4109 # @param self The object pointer\r
4110 # @param FfsInfObj for whom overrides is got\r
4111 #\r
4112 def __GetOptRomOverrides(self, Obj):\r
4113 if self.__IsToken('{'):\r
4114 Overrides = OptionRom.OverrideAttribs()\r
fd171542 4115 while True:\r
4116 if self.__IsKeyword( "PCI_VENDOR_ID"):\r
4117 if not self.__IsToken( "="):\r
4118 raise Warning("expected '='", self.FileName, self.CurrentLineNumber)\r
4119 if not self.__GetNextHexNumber():\r
4120 raise Warning("expected Hex vendor id", self.FileName, self.CurrentLineNumber)\r
4121 Overrides.PciVendorId = self.__Token\r
4122 continue\r
4123\r
4124 if self.__IsKeyword( "PCI_CLASS_CODE"):\r
4125 if not self.__IsToken( "="):\r
4126 raise Warning("expected '='", self.FileName, self.CurrentLineNumber)\r
4127 if not self.__GetNextHexNumber():\r
4128 raise Warning("expected Hex class code", self.FileName, self.CurrentLineNumber)\r
4129 Overrides.PciClassCode = self.__Token\r
4130 continue\r
4131\r
4132 if self.__IsKeyword( "PCI_DEVICE_ID"):\r
4133 if not self.__IsToken( "="):\r
4134 raise Warning("expected '='", self.FileName, self.CurrentLineNumber)\r
4135 if not self.__GetNextHexNumber():\r
4136 raise Warning("expected Hex device id", self.FileName, self.CurrentLineNumber)\r
4137\r
4138 Overrides.PciDeviceId = self.__Token\r
4139 continue\r
4140\r
4141 if self.__IsKeyword( "PCI_REVISION"):\r
4142 if not self.__IsToken( "="):\r
4143 raise Warning("expected '='", self.FileName, self.CurrentLineNumber)\r
4144 if not self.__GetNextHexNumber():\r
4145 raise Warning("expected Hex revision", self.FileName, self.CurrentLineNumber)\r
4146 Overrides.PciRevision = self.__Token\r
4147 continue\r
4148\r
79b74a03 4149 if self.__IsKeyword( "PCI_COMPRESS"):\r
fd171542 4150 if not self.__IsToken( "="):\r
4151 raise Warning("expected '='", self.FileName, self.CurrentLineNumber)\r
4152 if not self.__GetNextToken():\r
4153 raise Warning("expected TRUE/FALSE for compress", self.FileName, self.CurrentLineNumber)\r
4154 Overrides.NeedCompress = self.__Token.upper() == 'TRUE'\r
4155 continue\r
4156\r
4157 if self.__IsToken( "}"):\r
4158 break\r
4159 else:\r
4160 EdkLogger.error("FdfParser", FORMAT_INVALID, File=self.FileName, Line=self.CurrentLineNumber)\r
4161\r
30fdf114
LG
4162 Obj.OverrideAttribs = Overrides\r
4163 \r
4164 ## __GetOptRomFileStatement() method\r
4165 #\r
4166 # Get FILE statements\r
4167 #\r
4168 # @param self The object pointer\r
4169 # @param Obj for whom FILE statement is got\r
4170 # @retval True Successfully find FILE statement\r
4171 # @retval False Not able to find FILE statement\r
4172 #\r
4173 def __GetOptRomFileStatement(self, Obj):\r
4174\r
4175 if not self.__IsKeyword( "FILE"):\r
4176 return False\r
4177\r
4178 FfsFileObj = OptRomFileStatement.OptRomFileStatement()\r
4179\r
4180 if not self.__IsKeyword("EFI") and not self.__IsKeyword("BIN"):\r
4181 raise Warning("expected Binary type (EFI/BIN)", self.FileName, self.CurrentLineNumber)\r
4182 FfsFileObj.FileType = self.__Token\r
4183\r
4184 if not self.__GetNextToken():\r
4185 raise Warning("expected File path", self.FileName, self.CurrentLineNumber)\r
4186 FfsFileObj.FileName = self.__Token\r
6310ffd7 4187 if FfsFileObj.FileName.replace('$(WORKSPACE)', '').find('$') == -1:\r
4188 #check for file path\r
4189 ErrorCode, ErrorInfo = PathClass(NormPath(FfsFileObj.FileName), GenFdsGlobalVariable.WorkSpaceDir).Validate()\r
4190 if ErrorCode != 0:\r
4191 EdkLogger.error("GenFds", ErrorCode, ExtraData=ErrorInfo)\r
30fdf114
LG
4192\r
4193 if FfsFileObj.FileType == 'EFI':\r
4194 self.__GetOptRomOverrides(FfsFileObj)\r
4195 \r
4196 Obj.FfsList.append(FfsFileObj)\r
4197\r
4198 return True\r
fd171542 4199\r
4200 ## __GetCapInFd() method\r
4201 #\r
4202 # Get Cap list contained in FD\r
4203 #\r
4204 # @param self The object pointer\r
4205 # @param FdName FD name\r
4206 # @retval CapList List of Capsule in FD\r
4207 #\r
4208 def __GetCapInFd (self, FdName):\r
4209\r
4210 CapList = []\r
4211 if FdName.upper() in self.Profile.FdDict.keys():\r
4212 FdObj = self.Profile.FdDict[FdName.upper()]\r
4213 for elementRegion in FdObj.RegionList:\r
4214 if elementRegion.RegionType == 'CAPSULE':\r
4215 for elementRegionData in elementRegion.RegionDataList:\r
4216 if elementRegionData.endswith(".cap"):\r
4217 continue\r
4218 if elementRegionData != None and elementRegionData.upper() not in CapList:\r
4219 CapList.append(elementRegionData.upper())\r
4220 return CapList\r
4221\r
4222 ## __GetReferencedFdCapTuple() method\r
4223 #\r
4224 # Get FV and FD list referenced by a capsule image\r
4225 #\r
4226 # @param self The object pointer\r
4227 # @param CapObj Capsule section to be searched\r
4228 # @param RefFdList referenced FD by section\r
4229 # @param RefFvList referenced FV by section\r
4230 #\r
4231 def __GetReferencedFdCapTuple(self, CapObj, RefFdList = [], RefFvList = []):\r
4232\r
4233 for CapsuleDataObj in CapObj.CapsuleDataList :\r
b36d134f 4234 if hasattr(CapsuleDataObj, 'FvName') and CapsuleDataObj.FvName != None and CapsuleDataObj.FvName.upper() not in RefFvList:\r
fd171542 4235 RefFvList.append (CapsuleDataObj.FvName.upper())\r
b36d134f
LG
4236 elif hasattr(CapsuleDataObj, 'FdName') and CapsuleDataObj.FdName != None and CapsuleDataObj.FdName.upper() not in RefFdList:\r
4237 RefFdList.append (CapsuleDataObj.FdName.upper()) \r
fd171542 4238 elif CapsuleDataObj.Ffs != None:\r
b36d134f
LG
4239 if isinstance(CapsuleDataObj.Ffs, FfsFileStatement.FileStatement):\r
4240 if CapsuleDataObj.Ffs.FvName != None and CapsuleDataObj.Ffs.FvName.upper() not in RefFvList:\r
4241 RefFvList.append(CapsuleDataObj.Ffs.FvName.upper())\r
4242 elif CapsuleDataObj.Ffs.FdName != None and CapsuleDataObj.Ffs.FdName.upper() not in RefFdList:\r
4243 RefFdList.append(CapsuleDataObj.Ffs.FdName.upper())\r
4244 else:\r
4245 self.__GetReferencedFdFvTupleFromSection(CapsuleDataObj.Ffs, RefFdList, RefFvList)\r
fd171542 4246\r
30fdf114
LG
4247 ## __GetFvInFd() method\r
4248 #\r
4249 # Get FV list contained in FD\r
4250 #\r
4251 # @param self The object pointer\r
4252 # @param FdName FD name\r
4253 # @retval FvList list of FV in FD\r
4254 #\r
4255 def __GetFvInFd (self, FdName):\r
4256\r
4257 FvList = []\r
4258 if FdName.upper() in self.Profile.FdDict.keys():\r
4259 FdObj = self.Profile.FdDict[FdName.upper()]\r
4260 for elementRegion in FdObj.RegionList:\r
4261 if elementRegion.RegionType == 'FV':\r
4262 for elementRegionData in elementRegion.RegionDataList:\r
fd171542 4263 if elementRegionData.endswith(".fv"):\r
4264 continue\r
30fdf114
LG
4265 if elementRegionData != None and elementRegionData.upper() not in FvList:\r
4266 FvList.append(elementRegionData.upper())\r
4267 return FvList\r
4268\r
4269 ## __GetReferencedFdFvTuple() method\r
4270 #\r
4271 # Get FD and FV list referenced by a FFS file\r
4272 #\r
4273 # @param self The object pointer\r
4274 # @param FfsFile contains sections to be searched\r
4275 # @param RefFdList referenced FD by section\r
4276 # @param RefFvList referenced FV by section\r
4277 #\r
4278 def __GetReferencedFdFvTuple(self, FvObj, RefFdList = [], RefFvList = []):\r
4279\r
4280 for FfsObj in FvObj.FfsList:\r
4281 if isinstance(FfsObj, FfsFileStatement.FileStatement):\r
4282 if FfsObj.FvName != None and FfsObj.FvName.upper() not in RefFvList:\r
4283 RefFvList.append(FfsObj.FvName.upper())\r
4284 elif FfsObj.FdName != None and FfsObj.FdName.upper() not in RefFdList:\r
4285 RefFdList.append(FfsObj.FdName.upper())\r
4286 else:\r
4287 self.__GetReferencedFdFvTupleFromSection(FfsObj, RefFdList, RefFvList)\r
4288\r
4289 ## __GetReferencedFdFvTupleFromSection() method\r
4290 #\r
4291 # Get FD and FV list referenced by a FFS section\r
4292 #\r
4293 # @param self The object pointer\r
4294 # @param FfsFile contains sections to be searched\r
4295 # @param FdList referenced FD by section\r
4296 # @param FvList referenced FV by section\r
4297 #\r
4298 def __GetReferencedFdFvTupleFromSection(self, FfsFile, FdList = [], FvList = []):\r
4299\r
4300 SectionStack = []\r
4301 SectionStack.extend(FfsFile.SectionList)\r
4302 while SectionStack != []:\r
4303 SectionObj = SectionStack.pop()\r
4304 if isinstance(SectionObj, FvImageSection.FvImageSection):\r
4305 if SectionObj.FvName != None and SectionObj.FvName.upper() not in FvList:\r
4306 FvList.append(SectionObj.FvName.upper())\r
4307 if SectionObj.Fv != None and SectionObj.Fv.UiFvName != None and SectionObj.Fv.UiFvName.upper() not in FvList:\r
4308 FvList.append(SectionObj.Fv.UiFvName.upper())\r
4309 self.__GetReferencedFdFvTuple(SectionObj.Fv, FdList, FvList)\r
4310\r
4311 if isinstance(SectionObj, CompressSection.CompressSection) or isinstance(SectionObj, GuidSection.GuidSection):\r
4312 SectionStack.extend(SectionObj.SectionList)\r
4313\r
4314 ## CycleReferenceCheck() method\r
4315 #\r
4316 # Check whether cycle reference exists in FDF\r
4317 #\r
4318 # @param self The object pointer\r
4319 # @retval True cycle reference exists\r
4320 # @retval False Not exists cycle reference\r
4321 #\r
4322 def CycleReferenceCheck(self):\r
fd171542 4323 #\r
4324 # Check the cycle between FV and FD image\r
4325 #\r
4326 MaxLength = len (self.Profile.FvDict)\r
4327 for FvName in self.Profile.FvDict.keys():\r
4328 LogStr = "\nCycle Reference Checking for FV: %s\n" % FvName\r
4329 RefFvStack = []\r
4330 RefFvStack.append(FvName)\r
4331 FdAnalyzedList = []\r
4332 \r
4333 Index = 0\r
4334 while RefFvStack != [] and Index < MaxLength:\r
4335 Index = Index + 1\r
4336 FvNameFromStack = RefFvStack.pop()\r
4337 if FvNameFromStack.upper() in self.Profile.FvDict.keys():\r
4338 FvObj = self.Profile.FvDict[FvNameFromStack.upper()]\r
4339 else:\r
4340 continue\r
30fdf114 4341\r
fd171542 4342 RefFdList = []\r
4343 RefFvList = []\r
4344 self.__GetReferencedFdFvTuple(FvObj, RefFdList, RefFvList)\r
30fdf114 4345\r
fd171542 4346 for RefFdName in RefFdList:\r
4347 if RefFdName in FdAnalyzedList:\r
30fdf114
LG
4348 continue\r
4349\r
fd171542 4350 LogStr += "FV %s contains FD %s\n" % (FvNameFromStack, RefFdName)\r
4351 FvInFdList = self.__GetFvInFd(RefFdName)\r
4352 if FvInFdList != []:\r
4353 for FvNameInFd in FvInFdList:\r
4354 LogStr += "FD %s contains FV %s\n" % (RefFdName,FvNameInFd)\r
4355 if FvNameInFd not in RefFvStack:\r
4356 RefFvStack.append(FvNameInFd)\r
4357\r
4358 if FvName in RefFvStack or FvNameFromStack in RefFvStack:\r
4359 EdkLogger.info(LogStr)\r
4360 return True\r
4361 FdAnalyzedList.append(RefFdName)\r
30fdf114 4362\r
fd171542 4363 for RefFvName in RefFvList:\r
4364 LogStr += "FV %s contains FV %s\n" % (FvNameFromStack, RefFvName)\r
4365 if RefFvName not in RefFvStack:\r
4366 RefFvStack.append(RefFvName)\r
4367\r
4368 if FvName in RefFvStack or FvNameFromStack in RefFvStack:\r
4369 EdkLogger.info(LogStr)\r
4370 return True\r
4371\r
4372 #\r
4373 # Check the cycle between Capsule and FD image\r
4374 #\r
4375 MaxLength = len (self.Profile.CapsuleDict)\r
4376 for CapName in self.Profile.CapsuleDict.keys():\r
4377 #\r
4378 # Capsule image to be checked.\r
4379 #\r
4380 LogStr = "\n\n\nCycle Reference Checking for Capsule: %s\n" % CapName\r
4381 RefCapStack = []\r
4382 RefCapStack.append(CapName)\r
4383 FdAnalyzedList = []\r
4384 FvAnalyzedList = []\r
4385 \r
4386 Index = 0\r
4387 while RefCapStack != [] and Index < MaxLength:\r
4388 Index = Index + 1\r
4389 CapNameFromStack = RefCapStack.pop()\r
4390 if CapNameFromStack.upper() in self.Profile.CapsuleDict.keys():\r
4391 CapObj = self.Profile.CapsuleDict[CapNameFromStack.upper()]\r
4392 else:\r
4393 continue\r
4394\r
4395 RefFvList = []\r
4396 RefFdList = []\r
4397 self.__GetReferencedFdCapTuple(CapObj, RefFdList, RefFvList)\r
4398\r
4399 FvListLength = 0\r
4400 FdListLength = 0\r
4401 while FvListLength < len (RefFvList) or FdListLength < len (RefFdList):\r
30fdf114
LG
4402 for RefFdName in RefFdList:\r
4403 if RefFdName in FdAnalyzedList:\r
4404 continue\r
4405\r
fd171542 4406 LogStr += "Capsule %s contains FD %s\n" % (CapNameFromStack, RefFdName)\r
4407 CapInFdList = self.__GetCapInFd(RefFdName)\r
4408 if CapInFdList != []:\r
4409 for CapNameInFd in CapInFdList:\r
4410 LogStr += "FD %s contains Capsule %s\n" % (RefFdName,CapNameInFd)\r
4411 if CapNameInFd not in RefCapStack:\r
4412 RefCapStack.append(CapNameInFd)\r
4413\r
4414 if CapName in RefCapStack or CapNameFromStack in RefCapStack:\r
4415 EdkLogger.info(LogStr)\r
4416 return True\r
4417\r
30fdf114
LG
4418 FvInFdList = self.__GetFvInFd(RefFdName)\r
4419 if FvInFdList != []:\r
fd171542 4420 for FvNameInFd in FvInFdList:\r
4421 LogStr += "FD %s contains FV %s\n" % (RefFdName,FvNameInFd)\r
4422 if FvNameInFd not in RefFvList:\r
4423 RefFvList.append(FvNameInFd)\r
30fdf114 4424\r
fd171542 4425 FdAnalyzedList.append(RefFdName)\r
4426 #\r
4427 # the number of the parsed FV and FD image\r
4428 #\r
4429 FvListLength = len (RefFvList)\r
4430 FdListLength = len (RefFdList)\r
30fdf114 4431 for RefFvName in RefFvList:\r
fd171542 4432 if RefFvName in FvAnalyzedList:\r
4433 continue\r
4434 LogStr += "Capsule %s contains FV %s\n" % (CapNameFromStack, RefFvName)\r
4435 if RefFvName.upper() in self.Profile.FvDict.keys():\r
4436 FvObj = self.Profile.FvDict[RefFvName.upper()]\r
4437 else:\r
4438 continue\r
4439 self.__GetReferencedFdFvTuple(FvObj, RefFdList, RefFvList)\r
4440 FvAnalyzedList.append(RefFvName)\r
30fdf114 4441\r
fd171542 4442 return False\r
30fdf114
LG
4443\r
4444if __name__ == "__main__":\r
b36d134f
LG
4445 import sys\r
4446 try:\r
4447 test_file = sys.argv[1]\r
4448 except IndexError, v:\r
4449 print "Usage: %s filename" % sys.argv[0]\r
4450 sys.exit(1)\r
4451\r
4452 parser = FdfParser(test_file)\r
30fdf114
LG
4453 try:\r
4454 parser.ParseFile()\r
4455 parser.CycleReferenceCheck()\r
4456 except Warning, X:\r
b36d134f 4457 print str(X)\r
30fdf114
LG
4458 else:\r
4459 print "Success!"\r
4460\r