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