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