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