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