## @file
# parse FDF file
#
#  Copyright (c) 2007 - 2018, Intel Corporation. All rights reserved.<BR>
#  Copyright (c) 2015, Hewlett Packard Enterprise Development, L.P.<BR>
#
#  This program and the accompanying materials
#  are licensed and made available under the terms and conditions of the BSD License
#  which accompanies this distribution.  The full text of the license may be found at
#  http://opensource.org/licenses/bsd-license.php
#
#  THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
#  WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
#

##
# Import Modules
#
from __future__ import print_function
from __future__ import absolute_import
from re import compile, DOTALL
from string import hexdigits
from uuid import UUID

from Common.BuildToolError import *
from Common import EdkLogger
from Common.Misc import PathClass, tdict, ProcessDuplicatedInf
from Common.StringUtils import NormPath, ReplaceMacro
from Common import GlobalData
from Common.Expression import *
from Common.DataType import *
from Common.MultipleWorkspace import MultipleWorkspace as mws
import Common.LongFilePathOs as os
from Common.LongFilePathSupport import OpenLongFilePath as open
from Common.RangeExpression import RangeExpression
from collections import OrderedDict

from .Fd import FD
from .Region import Region
from .Fv import FV
from .AprioriSection import AprioriSection
from .FfsInfStatement import FfsInfStatement
from .FfsFileStatement import FileStatement
from .VerSection import VerSection
from .UiSection import UiSection
from .FvImageSection import FvImageSection
from .DataSection import DataSection
from .DepexSection import DepexSection
from .CompressSection import CompressSection
from .GuidSection import GuidSection
from .Capsule import EFI_CERT_TYPE_PKCS7_GUID, EFI_CERT_TYPE_RSA2048_SHA256_GUID, Capsule
from .CapsuleData import CapsuleFfs, CapsulePayload, CapsuleFv, CapsuleFd, CapsuleAnyFile, CapsuleAfile
from .RuleComplexFile import RuleComplexFile
from .RuleSimpleFile import RuleSimpleFile
from .EfiSection import EfiSection
from .OptionRom import OPTIONROM
from .OptRomInfStatement import OptRomInfStatement, OverrideAttribs
from .OptRomFileStatement import OptRomFileStatement
from .GenFdsGlobalVariable import GenFdsGlobalVariable

T_CHAR_CR = '\r'
T_CHAR_TAB = '\t'
T_CHAR_DOUBLE_QUOTE = '\"'
T_CHAR_SINGLE_QUOTE = '\''
T_CHAR_BRACE_R = '}'

SEPARATORS = {TAB_EQUAL_SPLIT, TAB_VALUE_SPLIT, TAB_COMMA_SPLIT, '{', T_CHAR_BRACE_R}
ALIGNMENTS = {"Auto", "8", "16", "32", "64", "128", "512", "1K", "4K", "32K", "64K", "128K",
                                    "256K", "512K", "1M", "2M", "4M", "8M", "16M"}
ALIGNMENT_NOAUTO = ALIGNMENTS - {"Auto"}
CR_LB_SET = {T_CHAR_CR, TAB_LINE_BREAK}

RegionSizePattern = compile("\s*(?P<base>(?:0x|0X)?[a-fA-F0-9]+)\s*\|\s*(?P<size>(?:0x|0X)?[a-fA-F0-9]+)\s*")
RegionSizeGuidPattern = compile("\s*(?P<base>\w+\.\w+[\.\w\[\]]*)\s*\|\s*(?P<size>\w+\.\w+[\.\w\[\]]*)\s*")
RegionOffsetPcdPattern = compile("\s*(?P<base>\w+\.\w+[\.\w\[\]]*)\s*$")
ShortcutPcdPattern = compile("\s*\w+\s*=\s*(?P<value>(?:0x|0X)?[a-fA-F0-9]+)\s*\|\s*(?P<name>\w+\.\w+)\s*")
BaseAddrValuePattern = compile('^0[xX][0-9a-fA-F]+')
FileExtensionPattern = compile(r'([a-zA-Z][a-zA-Z0-9]*)')
TokenFindPattern = compile(r'([a-zA-Z0-9\-]+|\$\(TARGET\)|\*)_([a-zA-Z0-9\-]+|\$\(TOOL_CHAIN_TAG\)|\*)_([a-zA-Z0-9\-]+|\$\(ARCH\)|\*)')
AllIncludeFileList = []

# Get the closest parent
def GetParentAtLine (Line):
    for Profile in AllIncludeFileList:
        if Profile.IsLineInFile(Line):
            return Profile
    return None

# Check include loop
def IsValidInclude (File, Line):
    for Profile in AllIncludeFileList:
        if Profile.IsLineInFile(Line) and Profile.FileName == File:
            return False

    return True

def GetRealFileLine (File, Line):
    InsertedLines = 0
    for Profile in AllIncludeFileList:
        if Profile.IsLineInFile(Line):
            return Profile.GetLineInFile(Line)
        elif Line >= Profile.InsertStartLineNumber and Profile.Level == 1:
            InsertedLines += Profile.GetTotalLines()

    return (File, Line - InsertedLines)

## The exception class that used to report error messages when parsing FDF
#
# Currently the "ToolName" is set to be "FdfParser".
#
class Warning (Exception):
    ## The constructor
    #
    #   @param  self        The object pointer
    #   @param  Str         The message to record
    #   @param  File        The FDF name
    #   @param  Line        The Line number that error occurs
    #
    def __init__(self, Str, File = None, Line = None):
        FileLineTuple = GetRealFileLine(File, Line)
        self.FileName = FileLineTuple[0]
        self.LineNumber = FileLineTuple[1]
        self.OriginalLineNumber = Line
        self.Message = Str
        self.ToolName = 'FdfParser'

    def __str__(self):
        return self.Message

    # helper functions to facilitate consistency in warnings
    # each function is for a different common warning
    @staticmethod
    def Expected(Str, File, Line):
        return Warning("expected {}".format(Str), File, Line)
    @staticmethod
    def ExpectedEquals(File, Line):
        return Warning.Expected("'='", File, Line)
    @staticmethod
    def ExpectedCurlyOpen(File, Line):
        return Warning.Expected("'{'", File, Line)
    @staticmethod
    def ExpectedCurlyClose(File, Line):
        return Warning.Expected("'}'", File, Line)
    @staticmethod
    def ExpectedBracketClose(File, Line):
        return Warning.Expected("']'", File, Line)

## The Include file content class that used to record file data when parsing include file
#
# May raise Exception when opening file.
#
class IncludeFileProfile:
    ## The constructor
    #
    #   @param  self        The object pointer
    #   @param  FileName    The file that to be parsed
    #
    def __init__(self, FileName):
        self.FileName = FileName
        self.FileLinesList = []
        try:
            with open(FileName, "r") as fsock:
                self.FileLinesList = fsock.readlines()
                for index, line in enumerate(self.FileLinesList):
                    if not line.endswith(TAB_LINE_BREAK):
                        self.FileLinesList[index] += TAB_LINE_BREAK
        except:
            EdkLogger.error("FdfParser", FILE_OPEN_FAILURE, ExtraData=FileName)

        self.InsertStartLineNumber = None
        self.InsertAdjust = 0
        self.IncludeFileList = []
        self.Level = 1 # first level include file

    def GetTotalLines(self):
        TotalLines = self.InsertAdjust + len(self.FileLinesList)

        for Profile in self.IncludeFileList:
            TotalLines += Profile.GetTotalLines()

        return TotalLines

    def IsLineInFile(self, Line):
        if Line >= self.InsertStartLineNumber and Line < self.InsertStartLineNumber + self.GetTotalLines():
            return True

        return False

    def GetLineInFile(self, Line):
        if not self.IsLineInFile (Line):
            return (self.FileName, -1)

        InsertedLines = self.InsertStartLineNumber

        for Profile in self.IncludeFileList:
            if Profile.IsLineInFile(Line):
                return Profile.GetLineInFile(Line)
            elif Line >= Profile.InsertStartLineNumber:
                InsertedLines += Profile.GetTotalLines()

        return (self.FileName, Line - InsertedLines + 1)

## The FDF content class that used to record file data when parsing FDF
#
# May raise Exception when opening file.
#
class FileProfile:
    ## The constructor
    #
    #   @param  self        The object pointer
    #   @param  FileName    The file that to be parsed
    #
    def __init__(self, FileName):
        self.FileLinesList = []
        try:
            with open(FileName, "r") as fsock:
                self.FileLinesList = fsock.readlines()

        except:
            EdkLogger.error("FdfParser", FILE_OPEN_FAILURE, ExtraData=FileName)

        self.FileName = FileName
        self.PcdDict = OrderedDict()
        self.PcdLocalDict = OrderedDict()
        self.InfList = []
        self.InfDict = {'ArchTBD':[]}
        # ECC will use this Dict and List information
        self.PcdFileLineDict = {}
        self.InfFileLineList = []

        self.FdDict = {}
        self.FdNameNotSet = False
        self.FvDict = {}
        self.CapsuleDict = {}
        self.RuleDict = {}
        self.OptRomDict = {}
        self.FmpPayloadDict = {}

## The syntax parser for FDF
#
# PreprocessFile method should be called prior to ParseFile
# CycleReferenceCheck method can detect cycles in FDF contents
#
# GetNext*** procedures mean these procedures will get next token first, then make judgement.
# Get*** procedures mean these procedures will make judgement on current token only.
#
class FdfParser:
    ## The constructor
    #
    #   @param  self        The object pointer
    #   @param  FileName    The file that to be parsed
    #
    def __init__(self, FileName):
        self.Profile = FileProfile(FileName)
        self.FileName = FileName
        self.CurrentLineNumber = 1
        self.CurrentOffsetWithinLine = 0
        self.CurrentFdName = None
        self.CurrentFvName = None
        self._Token = ""
        self._SkippedChars = ""
        GlobalData.gFdfParser = self

        # Used to section info
        self._CurSection = []
        # Key: [section name, UI name, arch]
        # Value: {MACRO_NAME: MACRO_VALUE}
        self._MacroDict = tdict(True, 3)
        self._PcdDict = OrderedDict()

        self._WipeOffArea = []
        if GenFdsGlobalVariable.WorkSpaceDir == '':
            GenFdsGlobalVariable.WorkSpaceDir = os.getenv("WORKSPACE")

    ## _SkipWhiteSpace() method
    #
    #   Skip white spaces from current char.
    #
    #   @param  self        The object pointer
    #
    def _SkipWhiteSpace(self):
        while not self._EndOfFile():
            if self._CurrentChar() in {TAB_PRINTCHAR_NUL, T_CHAR_CR, TAB_LINE_BREAK, TAB_SPACE_SPLIT, T_CHAR_TAB}:
                self._SkippedChars += str(self._CurrentChar())
                self._GetOneChar()
            else:
                return
        return

    ## _EndOfFile() method
    #
    #   Judge current buffer pos is at file end
    #
    #   @param  self        The object pointer
    #   @retval True        Current File buffer position is at file end
    #   @retval False       Current File buffer position is NOT at file end
    #
    def _EndOfFile(self):
        NumberOfLines = len(self.Profile.FileLinesList)
        SizeOfLastLine = len(self.Profile.FileLinesList[-1])
        if self.CurrentLineNumber == NumberOfLines and self.CurrentOffsetWithinLine >= SizeOfLastLine - 1:
            return True
        if self.CurrentLineNumber > NumberOfLines:
            return True
        return False

    ## _EndOfLine() method
    #
    #   Judge current buffer pos is at line end
    #
    #   @param  self        The object pointer
    #   @retval True        Current File buffer position is at line end
    #   @retval False       Current File buffer position is NOT at line end
    #
    def _EndOfLine(self):
        if self.CurrentLineNumber > len(self.Profile.FileLinesList):
            return True
        SizeOfCurrentLine = len(self.Profile.FileLinesList[self.CurrentLineNumber - 1])
        if self.CurrentOffsetWithinLine >= SizeOfCurrentLine:
            return True
        return False

    ## Rewind() method
    #
    #   Reset file data buffer to the initial state
    #
    #   @param  self        The object pointer
    #   @param  DestLine    Optional new destination line number.
    #   @param  DestOffset  Optional new destination offset.
    #
    def Rewind(self, DestLine = 1, DestOffset = 0):
        self.CurrentLineNumber = DestLine
        self.CurrentOffsetWithinLine = DestOffset

    ## _UndoOneChar() method
    #
    #   Go back one char in the file buffer
    #
    #   @param  self        The object pointer
    #   @retval True        Successfully go back one char
    #   @retval False       Not able to go back one char as file beginning reached
    #
    def _UndoOneChar(self):
        if self.CurrentLineNumber == 1 and self.CurrentOffsetWithinLine == 0:
            return False
        elif self.CurrentOffsetWithinLine == 0:
            self.CurrentLineNumber -= 1
            self.CurrentOffsetWithinLine = len(self._CurrentLine()) - 1
        else:
            self.CurrentOffsetWithinLine -= 1
        return True

    ## _GetOneChar() method
    #
    #   Move forward one char in the file buffer
    #
    #   @param  self        The object pointer
    #
    def _GetOneChar(self):
        if self.CurrentOffsetWithinLine == len(self.Profile.FileLinesList[self.CurrentLineNumber - 1]) - 1:
            self.CurrentLineNumber += 1
            self.CurrentOffsetWithinLine = 0
        else:
            self.CurrentOffsetWithinLine += 1

    ## _CurrentChar() method
    #
    #   Get the char pointed to by the file buffer pointer
    #
    #   @param  self        The object pointer
    #   @retval Char        Current char
    #
    def _CurrentChar(self):
        return self.Profile.FileLinesList[self.CurrentLineNumber - 1][self.CurrentOffsetWithinLine]

    ## _NextChar() method
    #
    #   Get the one char pass the char pointed to by the file buffer pointer
    #
    #   @param  self        The object pointer
    #   @retval Char        Next char
    #
    def _NextChar(self):
        if self.CurrentOffsetWithinLine == len(self.Profile.FileLinesList[self.CurrentLineNumber - 1]) - 1:
            return self.Profile.FileLinesList[self.CurrentLineNumber][0]
        return self.Profile.FileLinesList[self.CurrentLineNumber - 1][self.CurrentOffsetWithinLine + 1]

    ## _SetCurrentCharValue() method
    #
    #   Modify the value of current char
    #
    #   @param  self        The object pointer
    #   @param  Value       The new value of current char
    #
    def _SetCurrentCharValue(self, Value):
        self.Profile.FileLinesList[self.CurrentLineNumber - 1][self.CurrentOffsetWithinLine] = Value

    ## _CurrentLine() method
    #
    #   Get the list that contains current line contents
    #
    #   @param  self        The object pointer
    #   @retval List        current line contents
    #
    def _CurrentLine(self):
        return self.Profile.FileLinesList[self.CurrentLineNumber - 1]

    def _StringToList(self):
        self.Profile.FileLinesList = [list(s) for s in self.Profile.FileLinesList]
        if not self.Profile.FileLinesList:
            EdkLogger.error('FdfParser', FILE_READ_FAILURE, 'The file is empty!', File=self.FileName)
        self.Profile.FileLinesList[-1].append(' ')

    def _ReplaceFragment(self, StartPos, EndPos, Value = ' '):
        if StartPos[0] == EndPos[0]:
            Offset = StartPos[1]
            while Offset <= EndPos[1]:
                self.Profile.FileLinesList[StartPos[0]][Offset] = Value
                Offset += 1
            return

        Offset = StartPos[1]
        while self.Profile.FileLinesList[StartPos[0]][Offset] not in CR_LB_SET:
            self.Profile.FileLinesList[StartPos[0]][Offset] = Value
            Offset += 1

        Line = StartPos[0]
        while Line < EndPos[0]:
            Offset = 0
            while self.Profile.FileLinesList[Line][Offset] not in CR_LB_SET:
                self.Profile.FileLinesList[Line][Offset] = Value
                Offset += 1
            Line += 1

        Offset = 0
        while Offset <= EndPos[1]:
            self.Profile.FileLinesList[EndPos[0]][Offset] = Value
            Offset += 1

    def _SetMacroValue(self, Macro, Value):
        if not self._CurSection:
            return

        MacroDict = {}
        if not self._MacroDict[self._CurSection[0], self._CurSection[1], self._CurSection[2]]:
            self._MacroDict[self._CurSection[0], self._CurSection[1], self._CurSection[2]] = MacroDict
        else:
            MacroDict = self._MacroDict[self._CurSection[0], self._CurSection[1], self._CurSection[2]]
        MacroDict[Macro] = Value

    def _GetMacroValue(self, Macro):
        # Highest priority
        if Macro in GlobalData.gCommandLineDefines:
            return GlobalData.gCommandLineDefines[Macro]
        if Macro in GlobalData.gGlobalDefines:
            return GlobalData.gGlobalDefines[Macro]

        if self._CurSection:
            MacroDict = self._MacroDict[
                        self._CurSection[0],
                        self._CurSection[1],
                        self._CurSection[2]
            ]
            if MacroDict and Macro in MacroDict:
                return MacroDict[Macro]

        # Lowest priority
        if Macro in GlobalData.gPlatformDefines:
            return GlobalData.gPlatformDefines[Macro]
        return None

    def _SectionHeaderParser(self, Section):
        # [Defines]
        # [FD.UiName]: use dummy instead if UI name is optional
        # [FV.UiName]
        # [Capsule.UiName]
        # [Rule]: don't take rule section into account, macro is not allowed in this section
        # [OptionRom.DriverName]
        self._CurSection = []
        Section = Section.strip()[1:-1].upper().replace(' ', '').strip(TAB_SPLIT)
        ItemList = Section.split(TAB_SPLIT)
        Item = ItemList[0]
        if Item == '' or Item == 'RULE':
            return

        if Item == TAB_COMMON_DEFINES.upper():
            self._CurSection = [TAB_COMMON, TAB_COMMON, TAB_COMMON]
        elif len(ItemList) > 1:
            self._CurSection = [ItemList[0], ItemList[1], TAB_COMMON]
        elif len(ItemList) > 0:
            self._CurSection = [ItemList[0], 'DUMMY', TAB_COMMON]

    ## PreprocessFile() method
    #
    #   Preprocess file contents, replace comments with spaces.
    #   In the end, rewind the file buffer pointer to the beginning
    #   BUGBUG: No !include statement processing contained in this procedure
    #   !include statement should be expanded at the same FileLinesList[CurrentLineNumber - 1]
    #
    #   @param  self        The object pointer
    #
    def PreprocessFile(self):
        self.Rewind()
        InComment = False
        DoubleSlashComment = False
        HashComment = False
        # HashComment in quoted string " " is ignored.
        InString = False

        while not self._EndOfFile():

            if self._CurrentChar() == T_CHAR_DOUBLE_QUOTE and not InComment:
                InString = not InString
            # meet new line, then no longer in a comment for // and '#'
            if self._CurrentChar() == TAB_LINE_BREAK:
                self.CurrentLineNumber += 1
                self.CurrentOffsetWithinLine = 0
                if InComment and DoubleSlashComment:
                    InComment = False
                    DoubleSlashComment = False
                if InComment and HashComment:
                    InComment = False
                    HashComment = False
            # check for */ comment end
            elif InComment and not DoubleSlashComment and not HashComment and self._CurrentChar() == TAB_STAR and self._NextChar() == TAB_BACK_SLASH:
                self._SetCurrentCharValue(TAB_SPACE_SPLIT)
                self._GetOneChar()
                self._SetCurrentCharValue(TAB_SPACE_SPLIT)
                self._GetOneChar()
                InComment = False
            # set comments to spaces
            elif InComment:
                self._SetCurrentCharValue(TAB_SPACE_SPLIT)
                self._GetOneChar()
            # check for // comment
            elif self._CurrentChar() == TAB_BACK_SLASH and self._NextChar() == TAB_BACK_SLASH and not self._EndOfLine():
                InComment = True
                DoubleSlashComment = True
            # check for '#' comment
            elif self._CurrentChar() == TAB_COMMENT_SPLIT and not self._EndOfLine() and not InString:
                InComment = True
                HashComment = True
            # check for /* comment start
            elif self._CurrentChar() == TAB_BACK_SLASH and self._NextChar() == TAB_STAR:
                self._SetCurrentCharValue(TAB_SPACE_SPLIT)
                self._GetOneChar()
                self._SetCurrentCharValue(TAB_SPACE_SPLIT)
                self._GetOneChar()
                InComment = True
            else:
                self._GetOneChar()

        # restore from ListOfList to ListOfString
        self.Profile.FileLinesList = ["".join(list) for list in self.Profile.FileLinesList]
        self.Rewind()

    ## PreprocessIncludeFile() method
    #
    #   Preprocess file contents, replace !include statements with file contents.
    #   In the end, rewind the file buffer pointer to the beginning
    #
    #   @param  self        The object pointer
    #
    def PreprocessIncludeFile(self):
      # nested include support
        Processed = False
        MacroDict = {}
        while self._GetNextToken():

            if self._Token == TAB_DEFINE:
                if not self._GetNextToken():
                    raise Warning.Expected("Macro name", self.FileName, self.CurrentLineNumber)
                Macro = self._Token
                if not self._IsToken(TAB_EQUAL_SPLIT):
                    raise Warning.ExpectedEquals(self.FileName, self.CurrentLineNumber)
                Value = self._GetExpression()
                MacroDict[Macro] = Value

            elif self._Token == TAB_INCLUDE:
                Processed = True
                IncludeLine = self.CurrentLineNumber
                IncludeOffset = self.CurrentOffsetWithinLine - len(TAB_INCLUDE)
                if not self._GetNextToken():
                    raise Warning.Expected("include file name", self.FileName, self.CurrentLineNumber)
                IncFileName = self._Token
                PreIndex = 0
                StartPos = IncFileName.find('$(', PreIndex)
                EndPos = IncFileName.find(')', StartPos+2)
                while StartPos != -1 and EndPos != -1:
                    Macro = IncFileName[StartPos+2: EndPos]
                    MacroVal = self._GetMacroValue(Macro)
                    if not MacroVal:
                        if Macro in MacroDict:
                            MacroVal = MacroDict[Macro]
                    if MacroVal is not None:
                        IncFileName = IncFileName.replace('$(' + Macro + ')', MacroVal, 1)
                        if MacroVal.find('$(') != -1:
                            PreIndex = StartPos
                        else:
                            PreIndex = StartPos + len(MacroVal)
                    else:
                        raise Warning("The Macro %s is not defined" %Macro, self.FileName, self.CurrentLineNumber)
                    StartPos = IncFileName.find('$(', PreIndex)
                    EndPos = IncFileName.find(')', StartPos+2)

                IncludedFile = NormPath(IncFileName)
                #
                # First search the include file under the same directory as FDF file
                #
                IncludedFile1 = PathClass(IncludedFile, os.path.dirname(self.FileName))
                ErrorCode = IncludedFile1.Validate()[0]
                if ErrorCode != 0:
                    #
                    # Then search the include file under the same directory as DSC file
                    #
                    PlatformDir = ''
                    if GenFdsGlobalVariable.ActivePlatform:
                        PlatformDir = GenFdsGlobalVariable.ActivePlatform.Dir
                    elif GlobalData.gActivePlatform:
                        PlatformDir = GlobalData.gActivePlatform.MetaFile.Dir
                    IncludedFile1 = PathClass(IncludedFile, PlatformDir)
                    ErrorCode = IncludedFile1.Validate()[0]
                    if ErrorCode != 0:
                        #
                        # Also search file under the WORKSPACE directory
                        #
                        IncludedFile1 = PathClass(IncludedFile, GlobalData.gWorkspace)
                        ErrorCode = IncludedFile1.Validate()[0]
                        if ErrorCode != 0:
                            raise Warning("The include file does not exist under below directories: \n%s\n%s\n%s\n"%(os.path.dirname(self.FileName), PlatformDir, GlobalData.gWorkspace),
                                          self.FileName, self.CurrentLineNumber)

                if not IsValidInclude (IncludedFile1.Path, self.CurrentLineNumber):
                    raise Warning("The include file {0} is causing a include loop.\n".format (IncludedFile1.Path), self.FileName, self.CurrentLineNumber)

                IncFileProfile = IncludeFileProfile(IncludedFile1.Path)

                CurrentLine = self.CurrentLineNumber
                CurrentOffset = self.CurrentOffsetWithinLine
                # list index of the insertion, note that line number is 'CurrentLine + 1'
                InsertAtLine = CurrentLine
                ParentProfile = GetParentAtLine (CurrentLine)
                if ParentProfile is not None:
                    ParentProfile.IncludeFileList.insert(0, IncFileProfile)
                    IncFileProfile.Level = ParentProfile.Level + 1
                IncFileProfile.InsertStartLineNumber = InsertAtLine + 1
                # deal with remaining portions after "!include filename", if exists.
                if self._GetNextToken():
                    if self.CurrentLineNumber == CurrentLine:
                        RemainingLine = self._CurrentLine()[CurrentOffset:]
                        self.Profile.FileLinesList.insert(self.CurrentLineNumber, RemainingLine)
                        IncFileProfile.InsertAdjust += 1
                        self.CurrentLineNumber += 1
                        self.CurrentOffsetWithinLine = 0

                for Line in IncFileProfile.FileLinesList:
                    self.Profile.FileLinesList.insert(InsertAtLine, Line)
                    self.CurrentLineNumber += 1
                    InsertAtLine += 1

                # reversely sorted to better determine error in file
                AllIncludeFileList.insert(0, IncFileProfile)

                # comment out the processed include file statement
                TempList = list(self.Profile.FileLinesList[IncludeLine - 1])
                TempList.insert(IncludeOffset, TAB_COMMENT_SPLIT)
                self.Profile.FileLinesList[IncludeLine - 1] = ''.join(TempList)
            if Processed: # Nested and back-to-back support
                self.Rewind(DestLine = IncFileProfile.InsertStartLineNumber - 1)
                Processed = False
        # Preprocess done.
        self.Rewind()

    @staticmethod
    def _GetIfListCurrentItemStat(IfList):
        if len(IfList) == 0:
            return True

        for Item in IfList:
            if Item[1] == False:
                return False

        return True

    ## PreprocessConditionalStatement() method
    #
    #   Preprocess conditional statement.
    #   In the end, rewind the file buffer pointer to the beginning
    #
    #   @param  self        The object pointer
    #
    def PreprocessConditionalStatement(self):
        # IfList is a stack of if branches with elements of list [Pos, CondSatisfied, BranchDetermined]
        IfList = []
        RegionLayoutLine = 0
        ReplacedLine = -1
        while self._GetNextToken():
            # Determine section name and the location dependent macro
            if self._GetIfListCurrentItemStat(IfList):
                if self._Token.startswith(TAB_SECTION_START):
                    Header = self._Token
                    if not self._Token.endswith(TAB_SECTION_END):
                        self._SkipToToken(TAB_SECTION_END)
                        Header += self._SkippedChars
                    if Header.find('$(') != -1:
                        raise Warning("macro cannot be used in section header", self.FileName, self.CurrentLineNumber)
                    self._SectionHeaderParser(Header)
                    continue
                # Replace macros except in RULE section or out of section
                elif self._CurSection and ReplacedLine != self.CurrentLineNumber:
                    ReplacedLine = self.CurrentLineNumber
                    self._UndoToken()
                    CurLine = self.Profile.FileLinesList[ReplacedLine - 1]
                    PreIndex = 0
                    StartPos = CurLine.find('$(', PreIndex)
                    EndPos = CurLine.find(')', StartPos+2)
                    while StartPos != -1 and EndPos != -1 and self._Token not in {TAB_IF_DEF, TAB_IF_N_DEF, TAB_IF, TAB_ELSE_IF}:
                        MacroName = CurLine[StartPos+2: EndPos]
                        MacroValue = self._GetMacroValue(MacroName)
                        if MacroValue is not None:
                            CurLine = CurLine.replace('$(' + MacroName + ')', MacroValue, 1)
                            if MacroValue.find('$(') != -1:
                                PreIndex = StartPos
                            else:
                                PreIndex = StartPos + len(MacroValue)
                        else:
                            PreIndex = EndPos + 1
                        StartPos = CurLine.find('$(', PreIndex)
                        EndPos = CurLine.find(')', StartPos+2)
                    self.Profile.FileLinesList[ReplacedLine - 1] = CurLine
                    continue

            if self._Token == TAB_DEFINE:
                if self._GetIfListCurrentItemStat(IfList):
                    if not self._CurSection:
                        raise Warning("macro cannot be defined in Rule section or out of section", self.FileName, self.CurrentLineNumber)
                    DefineLine = self.CurrentLineNumber - 1
                    DefineOffset = self.CurrentOffsetWithinLine - len(TAB_DEFINE)
                    if not self._GetNextToken():
                        raise Warning.Expected("Macro name", self.FileName, self.CurrentLineNumber)
                    Macro = self._Token
                    if not self._IsToken(TAB_EQUAL_SPLIT):
                        raise Warning.ExpectedEquals(self.FileName, self.CurrentLineNumber)

                    Value = self._GetExpression()
                    self._SetMacroValue(Macro, Value)
                    self._WipeOffArea.append(((DefineLine, DefineOffset), (self.CurrentLineNumber - 1, self.CurrentOffsetWithinLine - 1)))
            elif self._Token == 'SET':
                if not self._GetIfListCurrentItemStat(IfList):
                    continue
                SetLine = self.CurrentLineNumber - 1
                SetOffset = self.CurrentOffsetWithinLine - len('SET')
                PcdPair = self._GetNextPcdSettings()
                PcdName = "%s.%s" % (PcdPair[1], PcdPair[0])
                if not self._IsToken(TAB_EQUAL_SPLIT):
                    raise Warning.ExpectedEquals(self.FileName, self.CurrentLineNumber)

                Value = self._GetExpression()
                Value = self._EvaluateConditional(Value, self.CurrentLineNumber, 'eval', True)

                self._PcdDict[PcdName] = Value

                self.Profile.PcdDict[PcdPair] = Value
                self.SetPcdLocalation(PcdPair)
                FileLineTuple = GetRealFileLine(self.FileName, self.CurrentLineNumber)
                self.Profile.PcdFileLineDict[PcdPair] = FileLineTuple

                self._WipeOffArea.append(((SetLine, SetOffset), (self.CurrentLineNumber - 1, self.CurrentOffsetWithinLine - 1)))
            elif self._Token in {TAB_IF_DEF, TAB_IF_N_DEF, TAB_IF}:
                IfStartPos = (self.CurrentLineNumber - 1, self.CurrentOffsetWithinLine - len(self._Token))
                IfList.append([IfStartPos, None, None])

                CondLabel = self._Token
                Expression = self._GetExpression()

                if CondLabel == TAB_IF:
                    ConditionSatisfied = self._EvaluateConditional(Expression, IfList[-1][0][0] + 1, 'eval')
                else:
                    ConditionSatisfied = self._EvaluateConditional(Expression, IfList[-1][0][0] + 1, 'in')
                    if CondLabel == TAB_IF_N_DEF:
                        ConditionSatisfied = not ConditionSatisfied

                BranchDetermined = ConditionSatisfied
                IfList[-1] = [IfList[-1][0], ConditionSatisfied, BranchDetermined]
                if ConditionSatisfied:
                    self._WipeOffArea.append((IfList[-1][0], (self.CurrentLineNumber - 1, self.CurrentOffsetWithinLine - 1)))
            elif self._Token in {TAB_ELSE_IF, TAB_ELSE}:
                ElseStartPos = (self.CurrentLineNumber - 1, self.CurrentOffsetWithinLine - len(self._Token))
                if len(IfList) <= 0:
                    raise Warning("Missing !if statement", self.FileName, self.CurrentLineNumber)

                if IfList[-1][1]:
                    IfList[-1] = [ElseStartPos, False, True]
                    self._WipeOffArea.append((ElseStartPos, (self.CurrentLineNumber - 1, self.CurrentOffsetWithinLine - 1)))
                else:
                    self._WipeOffArea.append((IfList[-1][0], ElseStartPos))
                    IfList[-1] = [ElseStartPos, True, IfList[-1][2]]
                    if self._Token == TAB_ELSE_IF:
                        Expression = self._GetExpression()
                        ConditionSatisfied = self._EvaluateConditional(Expression, IfList[-1][0][0] + 1, 'eval')
                        IfList[-1] = [IfList[-1][0], ConditionSatisfied, IfList[-1][2]]

                    if IfList[-1][1]:
                        if IfList[-1][2]:
                            IfList[-1][1] = False
                        else:
                            IfList[-1][2] = True
                            self._WipeOffArea.append((IfList[-1][0], (self.CurrentLineNumber - 1, self.CurrentOffsetWithinLine - 1)))
            elif self._Token == '!endif':
                if len(IfList) <= 0:
                    raise Warning("Missing !if statement", self.FileName, self.CurrentLineNumber)
                if IfList[-1][1]:
                    self._WipeOffArea.append(((self.CurrentLineNumber - 1, self.CurrentOffsetWithinLine - len('!endif')), (self.CurrentLineNumber - 1, self.CurrentOffsetWithinLine - 1)))
                else:
                    self._WipeOffArea.append((IfList[-1][0], (self.CurrentLineNumber - 1, self.CurrentOffsetWithinLine - 1)))

                IfList.pop()
            elif not IfList:    # Don't use PCDs inside conditional directive
                if self.CurrentLineNumber <= RegionLayoutLine:
                    # Don't try the same line twice
                    continue
                SetPcd = ShortcutPcdPattern.match(self.Profile.FileLinesList[self.CurrentLineNumber - 1])
                if SetPcd:
                    self._PcdDict[SetPcd.group('name')] = SetPcd.group('value')
                    RegionLayoutLine = self.CurrentLineNumber
                    continue
                RegionSize = RegionSizePattern.match(self.Profile.FileLinesList[self.CurrentLineNumber - 1])
                if not RegionSize:
                    RegionLayoutLine = self.CurrentLineNumber
                    continue
                RegionSizeGuid = RegionSizeGuidPattern.match(self.Profile.FileLinesList[self.CurrentLineNumber])
                if not RegionSizeGuid:
                    RegionLayoutLine = self.CurrentLineNumber + 1
                    continue
                self._PcdDict[RegionSizeGuid.group('base')] = RegionSize.group('base')
                self._PcdDict[RegionSizeGuid.group('size')] = RegionSize.group('size')
                RegionLayoutLine = self.CurrentLineNumber + 1

        if IfList:
            raise Warning("Missing !endif", self.FileName, self.CurrentLineNumber)
        self.Rewind()

    def _CollectMacroPcd(self):
        MacroDict = {}

        # PCD macro
        MacroDict.update(GlobalData.gPlatformPcds)
        MacroDict.update(self._PcdDict)

        # Lowest priority
        MacroDict.update(GlobalData.gPlatformDefines)

        if self._CurSection:
            # Defines macro
            ScopeMacro = self._MacroDict[TAB_COMMON, TAB_COMMON, TAB_COMMON]
            if ScopeMacro:
                MacroDict.update(ScopeMacro)

            # Section macro
            ScopeMacro = self._MacroDict[
                        self._CurSection[0],
                        self._CurSection[1],
                        self._CurSection[2]
            ]
            if ScopeMacro:
                MacroDict.update(ScopeMacro)

        MacroDict.update(GlobalData.gGlobalDefines)
        MacroDict.update(GlobalData.gCommandLineDefines)
        for Item in GlobalData.BuildOptionPcd:
            if isinstance(Item, tuple):
                continue
            PcdName, TmpValue = Item.split(TAB_EQUAL_SPLIT)
            TmpValue = BuildOptionValue(TmpValue, {})
            MacroDict[PcdName.strip()] = TmpValue
        # Highest priority

        return MacroDict

    def _EvaluateConditional(self, Expression, Line, Op = None, Value = None):
        MacroPcdDict = self._CollectMacroPcd()
        if Op == 'eval':
            try:
                if Value:
                    return ValueExpression(Expression, MacroPcdDict)(True)
                else:
                    return ValueExpression(Expression, MacroPcdDict)()
            except WrnExpression as Excpt:
                #
                # Catch expression evaluation warning here. We need to report
                # the precise number of line and return the evaluation result
                #
                EdkLogger.warn('Parser', "Suspicious expression: %s" % str(Excpt),
                                File=self.FileName, ExtraData=self._CurrentLine(),
                                Line=Line)
                return Excpt.result
            except Exception as Excpt:
                if hasattr(Excpt, 'Pcd'):
                    if Excpt.Pcd in GlobalData.gPlatformOtherPcds:
                        Info = GlobalData.gPlatformOtherPcds[Excpt.Pcd]
                        raise Warning("Cannot use this PCD (%s) in an expression as"
                                      " it must be defined in a [PcdsFixedAtBuild] or [PcdsFeatureFlag] section"
                                      " of the DSC file (%s), and it is currently defined in this section:"
                                      " %s, line #: %d." % (Excpt.Pcd, GlobalData.gPlatformOtherPcds['DSCFILE'], Info[0], Info[1]),
                                      self.FileName, Line)
                    else:
                        raise Warning("PCD (%s) is not defined in DSC file (%s)" % (Excpt.Pcd, GlobalData.gPlatformOtherPcds['DSCFILE']),
                                      self.FileName, Line)
                else:
                    raise Warning(str(Excpt), self.FileName, Line)
        else:
            if Expression.startswith('$(') and Expression[-1] == ')':
                Expression = Expression[2:-1]
            return Expression in MacroPcdDict

    ## _IsToken() method
    #
    #   Check whether input string is found from current char position along
    #   If found, the string value is put into self._Token
    #
    #   @param  self        The object pointer
    #   @param  String      The string to search
    #   @param  IgnoreCase  Indicate case sensitive/non-sensitive search, default is case sensitive
    #   @retval True        Successfully find string, file buffer pointer moved forward
    #   @retval False       Not able to find string, file buffer pointer not changed
    #
    def _IsToken(self, String, IgnoreCase = False):
        self._SkipWhiteSpace()

        # Only consider the same line, no multi-line token allowed
        StartPos = self.CurrentOffsetWithinLine
        index = -1
        if IgnoreCase:
            index = self._CurrentLine()[self.CurrentOffsetWithinLine: ].upper().find(String.upper())
        else:
            index = self._CurrentLine()[self.CurrentOffsetWithinLine: ].find(String)
        if index == 0:
            self.CurrentOffsetWithinLine += len(String)
            self._Token = self._CurrentLine()[StartPos: self.CurrentOffsetWithinLine]
            return True
        return False

    ## _IsKeyword() method
    #
    #   Check whether input keyword is found from current char position along, whole word only!
    #   If found, the string value is put into self._Token
    #
    #   @param  self        The object pointer
    #   @param  Keyword     The string to search
    #   @param  IgnoreCase  Indicate case sensitive/non-sensitive search, default is case sensitive
    #   @retval True        Successfully find string, file buffer pointer moved forward
    #   @retval False       Not able to find string, file buffer pointer not changed
    #
    def _IsKeyword(self, KeyWord, IgnoreCase = False):
        self._SkipWhiteSpace()

        # Only consider the same line, no multi-line token allowed
        StartPos = self.CurrentOffsetWithinLine
        index = -1
        if IgnoreCase:
            index = self._CurrentLine()[self.CurrentOffsetWithinLine: ].upper().find(KeyWord.upper())
        else:
            index = self._CurrentLine()[self.CurrentOffsetWithinLine: ].find(KeyWord)
        if index == 0:
            followingChar = self._CurrentLine()[self.CurrentOffsetWithinLine + len(KeyWord)]
            if not str(followingChar).isspace() and followingChar not in SEPARATORS:
                return False
            self.CurrentOffsetWithinLine += len(KeyWord)
            self._Token = self._CurrentLine()[StartPos: self.CurrentOffsetWithinLine]
            return True
        return False

    def _GetExpression(self):
        Line = self.Profile.FileLinesList[self.CurrentLineNumber - 1]
        Index = len(Line) - 1
        while Line[Index] in CR_LB_SET:
            Index -= 1
        ExpressionString = self.Profile.FileLinesList[self.CurrentLineNumber - 1][self.CurrentOffsetWithinLine:Index+1]
        self.CurrentOffsetWithinLine += len(ExpressionString)
        ExpressionString = ExpressionString.strip()
        return ExpressionString

    ## _GetNextWord() method
    #
    #   Get next C name from file lines
    #   If found, the string value is put into self._Token
    #
    #   @param  self        The object pointer
    #   @retval True        Successfully find a C name string, file buffer pointer moved forward
    #   @retval False       Not able to find a C name string, file buffer pointer not changed
    #
    def _GetNextWord(self):
        self._SkipWhiteSpace()
        if self._EndOfFile():
            return False

        TempChar = self._CurrentChar()
        StartPos = self.CurrentOffsetWithinLine
        if (TempChar >= 'a' and TempChar <= 'z') or (TempChar >= 'A' and TempChar <= 'Z') or TempChar == '_':
            self._GetOneChar()
            while not self._EndOfLine():
                TempChar = self._CurrentChar()
                if (TempChar >= 'a' and TempChar <= 'z') or (TempChar >= 'A' and TempChar <= 'Z') \
                or (TempChar >= '0' and TempChar <= '9') or TempChar == '_' or TempChar == '-':
                    self._GetOneChar()

                else:
                    break

            self._Token = self._CurrentLine()[StartPos: self.CurrentOffsetWithinLine]
            return True

        return False

    def _GetNextPcdWord(self):
        self._SkipWhiteSpace()
        if self._EndOfFile():
            return False

        TempChar = self._CurrentChar()
        StartPos = self.CurrentOffsetWithinLine
        if (TempChar >= 'a' and TempChar <= 'z') or (TempChar >= 'A' and TempChar <= 'Z') or TempChar == '_' or TempChar == TAB_SECTION_START or TempChar == TAB_SECTION_END:
            self._GetOneChar()
            while not self._EndOfLine():
                TempChar = self._CurrentChar()
                if (TempChar >= 'a' and TempChar <= 'z') or (TempChar >= 'A' and TempChar <= 'Z') \
                or (TempChar >= '0' and TempChar <= '9') or TempChar == '_' or TempChar == '-' or TempChar == TAB_SECTION_START or TempChar == TAB_SECTION_END:
                    self._GetOneChar()

                else:
                    break

            self._Token = self._CurrentLine()[StartPos: self.CurrentOffsetWithinLine]
            return True

        return False

    ## _GetNextToken() method
    #
    #   Get next token unit before a separator
    #   If found, the string value is put into self._Token
    #
    #   @param  self        The object pointer
    #   @retval True        Successfully find a token unit, file buffer pointer moved forward
    #   @retval False       Not able to find a token unit, file buffer pointer not changed
    #
    def _GetNextToken(self):
        # Skip leading spaces, if exist.
        self._SkipWhiteSpace()
        if self._EndOfFile():
            return False
        # Record the token start position, the position of the first non-space char.
        StartPos = self.CurrentOffsetWithinLine
        StartLine = self.CurrentLineNumber
        while StartLine == self.CurrentLineNumber:
            TempChar = self._CurrentChar()
            # Try to find the end char that is not a space and not in separator tuple.
            # That is, when we got a space or any char in the tuple, we got the end of token.
            if not str(TempChar).isspace() and TempChar not in SEPARATORS:
                self._GetOneChar()
            # if we happen to meet a separator as the first char, we must proceed to get it.
            # That is, we get a token that is a separator char. normally it is the boundary of other tokens.
            elif StartPos == self.CurrentOffsetWithinLine and TempChar in SEPARATORS:
                self._GetOneChar()
                break
            else:
                break
#        else:
#            return False

        EndPos = self.CurrentOffsetWithinLine
        if self.CurrentLineNumber != StartLine:
            EndPos = len(self.Profile.FileLinesList[StartLine-1])
        self._Token = self.Profile.FileLinesList[StartLine-1][StartPos: EndPos]
        if self._Token.lower() in {TAB_IF, TAB_END_IF, TAB_ELSE_IF, TAB_ELSE, TAB_IF_DEF, TAB_IF_N_DEF, TAB_ERROR, TAB_INCLUDE}:
            self._Token = self._Token.lower()
        if StartPos != self.CurrentOffsetWithinLine:
            return True
        else:
            return False

    ## _GetNextGuid() method
    #
    #   Get next token unit before a separator
    #   If found, the GUID string is put into self._Token
    #
    #   @param  self        The object pointer
    #   @retval True        Successfully find a registry format GUID, file buffer pointer moved forward
    #   @retval False       Not able to find a registry format GUID, file buffer pointer not changed
    #
    def _GetNextGuid(self):
        if not self._GetNextToken():
            return False
        if GlobalData.gGuidPattern.match(self._Token) is not None:
            return True
        else:
            self._UndoToken()
            return False

    @staticmethod
    def _Verify(Name, Value, Scope):
        # value verification only applies to numeric values.
        if Scope not in TAB_PCD_NUMERIC_TYPES:
            return

        ValueNumber = 0
        try:
            ValueNumber = int(Value, 0)
        except:
            EdkLogger.error("FdfParser", FORMAT_INVALID, "The value is not valid dec or hex number for %s." % Name)
        if ValueNumber < 0:
            EdkLogger.error("FdfParser", FORMAT_INVALID, "The value can't be set to negative value for %s." % Name)
        if ValueNumber > MAX_VAL_TYPE[Scope]:
            EdkLogger.error("FdfParser", FORMAT_INVALID, "Too large value for %s." % Name)
        return True

    ## _UndoToken() method
    #
    #   Go back one token unit in file buffer
    #
    #   @param  self        The object pointer
    #
    def _UndoToken(self):
        self._UndoOneChar()
        while self._CurrentChar().isspace():
            if not self._UndoOneChar():
                self._GetOneChar()
                return


        StartPos = self.CurrentOffsetWithinLine
        CurrentLine = self.CurrentLineNumber
        while CurrentLine == self.CurrentLineNumber:

            TempChar = self._CurrentChar()
            # Try to find the end char that is not a space and not in separator tuple.
            # That is, when we got a space or any char in the tuple, we got the end of token.
            if not str(TempChar).isspace() and not TempChar in SEPARATORS:
                if not self._UndoOneChar():
                    return
            # if we happen to meet a separator as the first char, we must proceed to get it.
            # That is, we get a token that is a separator char. normally it is the boundary of other tokens.
            elif StartPos == self.CurrentOffsetWithinLine and TempChar in SEPARATORS:
                return
            else:
                break

        self._GetOneChar()

    ## _GetNextHexNumber() method
    #
    #   Get next HEX data before a separator
    #   If found, the HEX data is put into self._Token
    #
    #   @param  self        The object pointer
    #   @retval True        Successfully find a HEX data, file buffer pointer moved forward
    #   @retval False       Not able to find a HEX data, file buffer pointer not changed
    #
    def _GetNextHexNumber(self):
        if not self._GetNextToken():
            return False
        if GlobalData.gHexPatternAll.match(self._Token):
            return True
        else:
            self._UndoToken()
            return False

    ## _GetNextDecimalNumber() method
    #
    #   Get next decimal data before a separator
    #   If found, the decimal data is put into self._Token
    #
    #   @param  self        The object pointer
    #   @retval True        Successfully find a decimal data, file buffer pointer moved forward
    #   @retval False       Not able to find a decimal data, file buffer pointer not changed
    #
    def _GetNextDecimalNumber(self):
        if not self._GetNextToken():
            return False
        if self._Token.isdigit():
            return True
        else:
            self._UndoToken()
            return False

    def _GetNextPcdSettings(self):
        if not self._GetNextWord():
            raise Warning.Expected("<PcdTokenSpaceCName>", self.FileName, self.CurrentLineNumber)
        pcdTokenSpaceCName = self._Token

        if not self._IsToken(TAB_SPLIT):
            raise Warning.Expected(".", self.FileName, self.CurrentLineNumber)

        if not self._GetNextWord():
            raise Warning.Expected("<PcdCName>", self.FileName, self.CurrentLineNumber)
        pcdCName = self._Token

        Fields = []
        while self._IsToken(TAB_SPLIT):
            if not self._GetNextPcdWord():
                raise Warning.Expected("Pcd Fields", self.FileName, self.CurrentLineNumber)
            Fields.append(self._Token)

        return (pcdCName, pcdTokenSpaceCName,TAB_SPLIT.join(Fields))

    ## _GetStringData() method
    #
    #   Get string contents quoted in ""
    #   If found, the decimal data is put into self._Token
    #
    #   @param  self        The object pointer
    #   @retval True        Successfully find a string data, file buffer pointer moved forward
    #   @retval False       Not able to find a string data, file buffer pointer not changed
    #
    def _GetStringData(self):
        QuoteToUse = None
        if self._Token.startswith(T_CHAR_DOUBLE_QUOTE) or self._Token.startswith("L\""):
            QuoteToUse = T_CHAR_DOUBLE_QUOTE
        elif self._Token.startswith(T_CHAR_SINGLE_QUOTE) or self._Token.startswith("L\'"):
            QuoteToUse = T_CHAR_SINGLE_QUOTE
        else:
            return False

        self._UndoToken()
        self._SkipToToken(QuoteToUse)
        currentLineNumber = self.CurrentLineNumber

        if not self._SkipToToken(QuoteToUse):
            raise Warning(QuoteToUse, self.FileName, self.CurrentLineNumber)
        if currentLineNumber != self.CurrentLineNumber:
            raise Warning(QuoteToUse, self.FileName, self.CurrentLineNumber)
        self._Token = self._SkippedChars.rstrip(QuoteToUse)
        return True

    ## _SkipToToken() method
    #
    #   Search forward in file buffer for the string
    #   The skipped chars are put into self._SkippedChars
    #
    #   @param  self        The object pointer
    #   @param  String      The string to search
    #   @param  IgnoreCase  Indicate case sensitive/non-sensitive search, default is case sensitive
    #   @retval True        Successfully find the string, file buffer pointer moved forward
    #   @retval False       Not able to find the string, file buffer pointer not changed
    #
    def _SkipToToken(self, String, IgnoreCase = False):
        StartPos = self.GetFileBufferPos()

        self._SkippedChars = ""
        while not self._EndOfFile():
            index = -1
            if IgnoreCase:
                index = self._CurrentLine()[self.CurrentOffsetWithinLine: ].upper().find(String.upper())
            else:
                index = self._CurrentLine()[self.CurrentOffsetWithinLine: ].find(String)
            if index == 0:
                self.CurrentOffsetWithinLine += len(String)
                self._SkippedChars += String
                return True
            self._SkippedChars += str(self._CurrentChar())
            self._GetOneChar()

        self.SetFileBufferPos(StartPos)
        self._SkippedChars = ""
        return False

    ## GetFileBufferPos() method
    #
    #   Return the tuple of current line and offset within the line
    #
    #   @param  self        The object pointer
    #   @retval Tuple       Line number and offset pair
    #
    def GetFileBufferPos(self):
        return (self.CurrentLineNumber, self.CurrentOffsetWithinLine)

    ## SetFileBufferPos() method
    #
    #   Restore the file buffer position
    #
    #   @param  self        The object pointer
    #   @param  Pos         The new file buffer position
    #
    def SetFileBufferPos(self, Pos):
        (self.CurrentLineNumber, self.CurrentOffsetWithinLine) = Pos

    ## Preprocess() method
    #
    #   Preprocess comment, conditional directive, include directive, replace macro.
    #   Exception will be raised if syntax error found
    #
    #   @param  self        The object pointer
    #
    def Preprocess(self):
        self._StringToList()
        self.PreprocessFile()
        self.PreprocessIncludeFile()
        self._StringToList()
        self.PreprocessFile()
        self.PreprocessConditionalStatement()
        self._StringToList()
        for Pos in self._WipeOffArea:
            self._ReplaceFragment(Pos[0], Pos[1])
        self.Profile.FileLinesList = ["".join(list) for list in self.Profile.FileLinesList]

        while self._GetDefines():
            pass

    ## ParseFile() method
    #
    #   Parse the file profile buffer to extract fd, fv ... information
    #   Exception will be raised if syntax error found
    #
    #   @param  self        The object pointer
    #
    def ParseFile(self):
        try:
            self.Preprocess()
            self._GetError()
            #
            # Keep processing sections of the FDF until no new sections or a syntax error is found
            #
            while self._GetFd() or self._GetFv() or self._GetFmp() or self._GetCapsule() or self._GetRule() or self._GetOptionRom():
                pass

        except Warning as X:
            self._UndoToken()
            #'\n\tGot Token: \"%s\" from File %s\n' % (self._Token, FileLineTuple[0]) + \
            # At this point, the closest parent would be the included file itself
            Profile = GetParentAtLine(X.OriginalLineNumber)
            if Profile is not None:
                X.Message += ' near line %d, column %d: %s' \
                % (X.LineNumber, 0, Profile.FileLinesList[X.LineNumber-1])
            else:
                FileLineTuple = GetRealFileLine(self.FileName, self.CurrentLineNumber)
                X.Message += ' near line %d, column %d: %s' \
                % (FileLineTuple[1], self.CurrentOffsetWithinLine + 1, self.Profile.FileLinesList[self.CurrentLineNumber - 1][self.CurrentOffsetWithinLine:].rstrip(TAB_LINE_BREAK).rstrip(T_CHAR_CR))
            raise

    ## SectionParser() method
    #
    #   Parse the file section info
    #   Exception will be raised if syntax error found
    #
    #   @param  self          The object pointer
    #   @param  section       The section string

    def SectionParser(self, section):
        S = section.upper()
        if not S.startswith("[DEFINES") and not S.startswith("[FD.") and not S.startswith("[FV.") and not S.startswith("[CAPSULE.") \
             and not S.startswith("[RULE.") and not S.startswith("[OPTIONROM.") and not S.startswith('[FMPPAYLOAD.'):
            raise Warning("Unknown section or section appear sequence error (The correct sequence should be [DEFINES], [FD.], [FV.], [Capsule.], [Rule.], [OptionRom.], [FMPPAYLOAD.])", self.FileName, self.CurrentLineNumber)

    ## _GetDefines() method
    #
    #   Get Defines section contents and store its data into AllMacrosList
    #
    #   @param  self        The object pointer
    #   @retval True        Successfully find a Defines
    #   @retval False       Not able to find a Defines
    #
    def _GetDefines(self):
        if not self._GetNextToken():
            return False

        S = self._Token.upper()
        if S.startswith(TAB_SECTION_START) and not S.startswith("[DEFINES"):
            self.SectionParser(S)
            self._UndoToken()
            return False

        self._UndoToken()
        if not self._IsToken("[DEFINES", True):
            FileLineTuple = GetRealFileLine(self.FileName, self.CurrentLineNumber)
            #print 'Parsing String: %s in File %s, At line: %d, Offset Within Line: %d' \
            #        % (self.Profile.FileLinesList[self.CurrentLineNumber - 1][self.CurrentOffsetWithinLine:], FileLineTuple[0], FileLineTuple[1], self.CurrentOffsetWithinLine)
            raise Warning.Expected("[DEFINES", self.FileName, self.CurrentLineNumber)

        if not self._IsToken(TAB_SECTION_END):
            raise Warning.ExpectedBracketClose(self.FileName, self.CurrentLineNumber)

        while self._GetNextWord():
            # handle the SET statement
            if self._Token == 'SET':
                self._UndoToken()
                self._GetSetStatement(None)
                continue

            Macro = self._Token

            if not self._IsToken(TAB_EQUAL_SPLIT):
                raise Warning.ExpectedEquals(self.FileName, self.CurrentLineNumber)
            if not self._GetNextToken() or self._Token.startswith(TAB_SECTION_START):
                raise Warning.Expected("MACRO value", self.FileName, self.CurrentLineNumber)
            Value = self._Token

        return False

    ##_GetError() method
    def _GetError(self):
        #save the Current information
        CurrentLine = self.CurrentLineNumber
        CurrentOffset = self.CurrentOffsetWithinLine
        while self._GetNextToken():
            if self._Token == TAB_ERROR:
                EdkLogger.error('FdfParser', ERROR_STATEMENT, self._CurrentLine().replace(TAB_ERROR, '', 1), File=self.FileName, Line=self.CurrentLineNumber)
        self.CurrentLineNumber = CurrentLine
        self.CurrentOffsetWithinLine = CurrentOffset

    ## _GetFd() method
    #
    #   Get FD section contents and store its data into FD dictionary of self.Profile
    #
    #   @param  self        The object pointer
    #   @retval True        Successfully find a FD
    #   @retval False       Not able to find a FD
    #
    def _GetFd(self):
        if not self._GetNextToken():
            return False

        S = self._Token.upper()
        if S.startswith(TAB_SECTION_START) and not S.startswith("[FD."):
            if not S.startswith("[FV.") and not S.startswith('[FMPPAYLOAD.') and not S.startswith("[CAPSULE.") \
                and not S.startswith("[RULE.") and not S.startswith("[OPTIONROM."):
                raise Warning("Unknown section", self.FileName, self.CurrentLineNumber)
            self._UndoToken()
            return False

        self._UndoToken()
        if not self._IsToken("[FD.", True):
            FileLineTuple = GetRealFileLine(self.FileName, self.CurrentLineNumber)
            #print 'Parsing String: %s in File %s, At line: %d, Offset Within Line: %d' \
            #        % (self.Profile.FileLinesList[self.CurrentLineNumber - 1][self.CurrentOffsetWithinLine:], FileLineTuple[0], FileLineTuple[1], self.CurrentOffsetWithinLine)
            raise Warning.Expected("[FD.]", self.FileName, self.CurrentLineNumber)

        FdName = self._GetUiName()
        if FdName == "":
            if len (self.Profile.FdDict) == 0:
                FdName = GenFdsGlobalVariable.PlatformName
                if FdName == "" and GlobalData.gActivePlatform:
                    FdName = GlobalData.gActivePlatform.PlatformName
                self.Profile.FdNameNotSet = True
            else:
                raise Warning.Expected("FdName in [FD.] section", self.FileName, self.CurrentLineNumber)
        self.CurrentFdName = FdName.upper()

        if self.CurrentFdName in self.Profile.FdDict:
            raise Warning("Unexpected the same FD name", self.FileName, self.CurrentLineNumber)

        if not self._IsToken(TAB_SECTION_END):
            raise Warning.ExpectedBracketClose(self.FileName, self.CurrentLineNumber)

        FdObj = FD()
        FdObj.FdUiName = self.CurrentFdName
        self.Profile.FdDict[self.CurrentFdName] = FdObj

        if len (self.Profile.FdDict) > 1 and self.Profile.FdNameNotSet:
            raise Warning.Expected("all FDs have their name", self.FileName, self.CurrentLineNumber)

        Status = self._GetCreateFile(FdObj)
        if not Status:
            raise Warning("FD name error", self.FileName, self.CurrentLineNumber)

        while self._GetTokenStatements(FdObj):
            pass
        for Attr in ("BaseAddress", "Size", "ErasePolarity"):
            if getattr(FdObj, Attr) is None:
                self._GetNextToken()
                raise Warning("Keyword %s missing" % Attr, self.FileName, self.CurrentLineNumber)

        if not FdObj.BlockSizeList:
            FdObj.BlockSizeList.append((1, FdObj.Size, None))

        self._GetDefineStatements(FdObj)

        self._GetSetStatements(FdObj)

        if not self._GetRegionLayout(FdObj):
            raise Warning.Expected("region layout", self.FileName, self.CurrentLineNumber)

        while self._GetRegionLayout(FdObj):
            pass
        return True

    ## _GetUiName() method
    #
    #   Return the UI name of a section
    #
    #   @param  self        The object pointer
    #   @retval FdName      UI name
    #
    def _GetUiName(self):
        Name = ""
        if self._GetNextWord():
            Name = self._Token

        return Name

    ## _GetCreateFile() method
    #
    #   Return the output file name of object
    #
    #   @param  self        The object pointer
    #   @param  Obj         object whose data will be stored in file
    #   @retval FdName      UI name
    #
    def _GetCreateFile(self, Obj):
        if self._IsKeyword("CREATE_FILE"):
            if not self._IsToken(TAB_EQUAL_SPLIT):
                raise Warning.ExpectedEquals(self.FileName, self.CurrentLineNumber)

            if not self._GetNextToken():
                raise Warning.Expected("file name", self.FileName, self.CurrentLineNumber)

            FileName = self._Token
            Obj.CreateFileName = FileName

        return True

    def SetPcdLocalation(self,pcdpair):
        self.Profile.PcdLocalDict[pcdpair] = (self.Profile.FileName,self.CurrentLineNumber)

    ## _GetTokenStatements() method
    #
    #   Get token statements
    #
    #   @param  self        The object pointer
    #   @param  Obj         for whom token statement is got
    #
    def _GetTokenStatements(self, Obj):
        if self._IsKeyword("BaseAddress"):
            if not self._IsToken(TAB_EQUAL_SPLIT):
                raise Warning.ExpectedEquals(self.FileName, self.CurrentLineNumber)

            if not self._GetNextHexNumber():
                raise Warning.Expected("Hex base address", self.FileName, self.CurrentLineNumber)

            Obj.BaseAddress = self._Token

            if self._IsToken(TAB_VALUE_SPLIT):
                pcdPair = self._GetNextPcdSettings()
                Obj.BaseAddressPcd = pcdPair
                self.Profile.PcdDict[pcdPair] = Obj.BaseAddress
                self.SetPcdLocalation(pcdPair)
                FileLineTuple = GetRealFileLine(self.FileName, self.CurrentLineNumber)
                self.Profile.PcdFileLineDict[pcdPair] = FileLineTuple
            return True

        if self._IsKeyword("Size"):
            if not self._IsToken(TAB_EQUAL_SPLIT):
                raise Warning.ExpectedEquals(self.FileName, self.CurrentLineNumber)

            if not self._GetNextHexNumber():
                raise Warning.Expected("Hex size", self.FileName, self.CurrentLineNumber)

            Size = self._Token
            if self._IsToken(TAB_VALUE_SPLIT):
                pcdPair = self._GetNextPcdSettings()
                Obj.SizePcd = pcdPair
                self.Profile.PcdDict[pcdPair] = Size
                self.SetPcdLocalation(pcdPair)
                FileLineTuple = GetRealFileLine(self.FileName, self.CurrentLineNumber)
                self.Profile.PcdFileLineDict[pcdPair] = FileLineTuple
            Obj.Size = int(Size, 0)
            return True

        if self._IsKeyword("ErasePolarity"):
            if not self._IsToken(TAB_EQUAL_SPLIT):
                raise Warning.ExpectedEquals(self.FileName, self.CurrentLineNumber)

            if not self._GetNextToken():
                raise Warning.Expected("Erase Polarity", self.FileName, self.CurrentLineNumber)

            if not self._Token in {"1", "0"}:
                raise Warning.Expected("1 or 0 Erase Polarity", self.FileName, self.CurrentLineNumber)

            Obj.ErasePolarity = self._Token
            return True

        return self._GetBlockStatements(Obj)

    ## _GetAddressStatements() method
    #
    #   Get address statements
    #
    #   @param  self        The object pointer
    #   @param  Obj         for whom address statement is got
    #   @retval True        Successfully find
    #   @retval False       Not able to find
    #
    def _GetAddressStatements(self, Obj):
        if self._IsKeyword("BsBaseAddress"):
            if not self._IsToken(TAB_EQUAL_SPLIT):
                raise Warning.ExpectedEquals(self.FileName, self.CurrentLineNumber)

            if not self._GetNextDecimalNumber() and not self._GetNextHexNumber():
                raise Warning.Expected("address", self.FileName, self.CurrentLineNumber)

            BsAddress = int(self._Token, 0)
            Obj.BsBaseAddress = BsAddress

        if self._IsKeyword("RtBaseAddress"):
            if not self._IsToken(TAB_EQUAL_SPLIT):
                raise Warning.ExpectedEquals(self.FileName, self.CurrentLineNumber)

            if not self._GetNextDecimalNumber() and not self._GetNextHexNumber():
                raise Warning.Expected("address", self.FileName, self.CurrentLineNumber)

            RtAddress = int(self._Token, 0)
            Obj.RtBaseAddress = RtAddress

    ## _GetBlockStatements() method
    #
    #   Get block statements
    #
    #   @param  self        The object pointer
    #   @param  Obj         for whom block statement is got
    #
    def _GetBlockStatements(self, Obj):
        IsBlock = False
        while self._GetBlockStatement(Obj):
            IsBlock = True

            Item = Obj.BlockSizeList[-1]
            if Item[0] is None or Item[1] is None:
                raise Warning.Expected("block statement", self.FileName, self.CurrentLineNumber)
        return IsBlock

    ## _GetBlockStatement() method
    #
    #   Get block statement
    #
    #   @param  self        The object pointer
    #   @param  Obj         for whom block statement is got
    #   @retval True        Successfully find
    #   @retval False       Not able to find
    #
    def _GetBlockStatement(self, Obj):
        if not self._IsKeyword("BlockSize"):
            return False

        if not self._IsToken(TAB_EQUAL_SPLIT):
            raise Warning.ExpectedEquals(self.FileName, self.CurrentLineNumber)

        if not self._GetNextHexNumber() and not self._GetNextDecimalNumber():
            raise Warning.Expected("Hex or Integer block size", self.FileName, self.CurrentLineNumber)

        BlockSize = self._Token
        BlockSizePcd = None
        if self._IsToken(TAB_VALUE_SPLIT):
            PcdPair = self._GetNextPcdSettings()
            BlockSizePcd = PcdPair
            self.Profile.PcdDict[PcdPair] = BlockSize
            self.SetPcdLocalation(PcdPair)
            FileLineTuple = GetRealFileLine(self.FileName, self.CurrentLineNumber)
            self.Profile.PcdFileLineDict[PcdPair] = FileLineTuple
        BlockSize = int(BlockSize, 0)

        BlockNumber = None
        if self._IsKeyword("NumBlocks"):
            if not self._IsToken(TAB_EQUAL_SPLIT):
                raise Warning.ExpectedEquals(self.FileName, self.CurrentLineNumber)

            if not self._GetNextDecimalNumber() and not self._GetNextHexNumber():
                raise Warning.Expected("block numbers", self.FileName, self.CurrentLineNumber)

            BlockNumber = int(self._Token, 0)

        Obj.BlockSizeList.append((BlockSize, BlockNumber, BlockSizePcd))
        return True

    ## _GetDefineStatements() method
    #
    #   Get define statements
    #
    #   @param  self        The object pointer
    #   @param  Obj         for whom define statement is got
    #   @retval True        Successfully find
    #   @retval False       Not able to find
    #
    def _GetDefineStatements(self, Obj):
        while self._GetDefineStatement(Obj):
            pass

    ## _GetDefineStatement() method
    #
    #   Get define statement
    #
    #   @param  self        The object pointer
    #   @param  Obj         for whom define statement is got
    #   @retval True        Successfully find
    #   @retval False       Not able to find
    #
    def _GetDefineStatement(self, Obj):
        if self._IsKeyword(TAB_DEFINE):
            self._GetNextToken()
            Macro = self._Token
            if not self._IsToken(TAB_EQUAL_SPLIT):
                raise Warning.ExpectedEquals(self.FileName, self.CurrentLineNumber)

            if not self._GetNextToken():
                raise Warning.Expected("value", self.FileName, self.CurrentLineNumber)

            Value = self._Token
            Macro = '$(' + Macro + ')'
            Obj.DefineVarDict[Macro] = Value
            return True

        return False

    ## _GetSetStatements() method
    #
    #   Get set statements
    #
    #   @param  self        The object pointer
    #   @param  Obj         for whom set statement is got
    #   @retval True        Successfully find
    #   @retval False       Not able to find
    #
    def _GetSetStatements(self, Obj):
        while self._GetSetStatement(Obj):
            pass

    ## _GetSetStatement() method
    #
    #   Get set statement
    #
    #   @param  self        The object pointer
    #   @param  Obj         for whom set statement is got
    #   @retval True        Successfully find
    #   @retval False       Not able to find
    #
    def _GetSetStatement(self, Obj):
        if self._IsKeyword("SET"):
            PcdPair = self._GetNextPcdSettings()

            if not self._IsToken(TAB_EQUAL_SPLIT):
                raise Warning.ExpectedEquals(self.FileName, self.CurrentLineNumber)

            Value = self._GetExpression()
            Value = self._EvaluateConditional(Value, self.CurrentLineNumber, 'eval', True)

            if Obj:
                Obj.SetVarDict[PcdPair] = Value
            self.Profile.PcdDict[PcdPair] = Value
            self.SetPcdLocalation(PcdPair)
            FileLineTuple = GetRealFileLine(self.FileName, self.CurrentLineNumber)
            self.Profile.PcdFileLineDict[PcdPair] = FileLineTuple
            return True

        return False

    ## _CalcRegionExpr(self)
    #
    #   Calculate expression for offset or size of a region
    #
    #   @return: None if invalid expression
    #            Calculated number if successfully
    #
    def _CalcRegionExpr(self):
        StartPos = self.GetFileBufferPos()
        Expr = ''
        PairCount = 0
        while not self._EndOfFile():
            CurCh = self._CurrentChar()
            if CurCh == '(':
                PairCount += 1
            elif CurCh == ')':
                PairCount -= 1

            if CurCh in '|\r\n' and PairCount == 0:
                break
            Expr += CurCh
            self._GetOneChar()
        try:
            return int(
                ValueExpression(Expr,
                                self._CollectMacroPcd()
                                )(True), 0)
        except Exception:
            self.SetFileBufferPos(StartPos)
            return None

    ## _GetRegionLayout() method
    #
    #   Get region layout for FD
    #
    #   @param  self        The object pointer
    #   @param  theFd       for whom region is got
    #   @retval True        Successfully find
    #   @retval False       Not able to find
    #
    def _GetRegionLayout(self, theFd):
        Offset = self._CalcRegionExpr()
        if Offset is None:
            return False

        RegionObj = Region()
        RegionObj.Offset = Offset
        theFd.RegionList.append(RegionObj)

        if not self._IsToken(TAB_VALUE_SPLIT):
            raise Warning.Expected("'|'", self.FileName, self.CurrentLineNumber)

        Size = self._CalcRegionExpr()
        if Size is None:
            raise Warning.Expected("Region Size", self.FileName, self.CurrentLineNumber)
        RegionObj.Size = Size

        if not self._GetNextWord():
            return True

        if not self._Token in {"SET", BINARY_FILE_TYPE_FV, "FILE", "DATA", "CAPSULE", "INF"}:
            #
            # If next token is a word which is not a valid FV type, it might be part of [PcdOffset[|PcdSize]]
            # Or it might be next region's offset described by an expression which starts with a PCD.
            #    PcdOffset[|PcdSize] or OffsetPcdExpression|Size
            #
            self._UndoToken()
            IsRegionPcd = (RegionSizeGuidPattern.match(self._CurrentLine()[self.CurrentOffsetWithinLine:]) or
                           RegionOffsetPcdPattern.match(self._CurrentLine()[self.CurrentOffsetWithinLine:]))
            if IsRegionPcd:
                RegionObj.PcdOffset = self._GetNextPcdSettings()
                self.Profile.PcdDict[RegionObj.PcdOffset] = "0x%08X" % (RegionObj.Offset + int(theFd.BaseAddress, 0))
                self.SetPcdLocalation(RegionObj.PcdOffset)
                self._PcdDict['%s.%s' % (RegionObj.PcdOffset[1], RegionObj.PcdOffset[0])] = "0x%x" % RegionObj.Offset
                FileLineTuple = GetRealFileLine(self.FileName, self.CurrentLineNumber)
                self.Profile.PcdFileLineDict[RegionObj.PcdOffset] = FileLineTuple
                if self._IsToken(TAB_VALUE_SPLIT):
                    RegionObj.PcdSize = self._GetNextPcdSettings()
                    self.Profile.PcdDict[RegionObj.PcdSize] = "0x%08X" % RegionObj.Size
                    self.SetPcdLocalation(RegionObj.PcdSize)
                    self._PcdDict['%s.%s' % (RegionObj.PcdSize[1], RegionObj.PcdSize[0])] = "0x%x" % RegionObj.Size
                    FileLineTuple = GetRealFileLine(self.FileName, self.CurrentLineNumber)
                    self.Profile.PcdFileLineDict[RegionObj.PcdSize] = FileLineTuple

            if not self._GetNextWord():
                return True

        if self._Token == "SET":
            self._UndoToken()
            self._GetSetStatements(RegionObj)
            if not self._GetNextWord():
                return True

        elif self._Token == BINARY_FILE_TYPE_FV:
            self._UndoToken()
            self._GetRegionFvType(RegionObj)

        elif self._Token == "CAPSULE":
            self._UndoToken()
            self._GetRegionCapType(RegionObj)

        elif self._Token == "FILE":
            self._UndoToken()
            self._GetRegionFileType(RegionObj)

        elif self._Token == "INF":
            self._UndoToken()
            RegionObj.RegionType = "INF"
            while self._IsKeyword("INF"):
                self._UndoToken()
                ffsInf = self._ParseInfStatement()
                if not ffsInf:
                    break
                RegionObj.RegionDataList.append(ffsInf)

        elif self._Token == "DATA":
            self._UndoToken()
            self._GetRegionDataType(RegionObj)
        else:
            self._UndoToken()
            if self._GetRegionLayout(theFd):
                return True
            raise Warning("A valid region type was not found. "
                          "Valid types are [SET, FV, CAPSULE, FILE, DATA, INF]. This error occurred",
                          self.FileName, self.CurrentLineNumber)

        return True

    ## _GetRegionFvType() method
    #
    #   Get region fv data for region
    #
    #   @param  self        The object pointer
    #   @param  RegionObj   for whom region data is got
    #
    def _GetRegionFvType(self, RegionObj):
        if not self._IsKeyword(BINARY_FILE_TYPE_FV):
            raise Warning.Expected("'FV'", self.FileName, self.CurrentLineNumber)

        if not self._IsToken(TAB_EQUAL_SPLIT):
            raise Warning.ExpectedEquals(self.FileName, self.CurrentLineNumber)

        if not self._GetNextToken():
            raise Warning.Expected("FV name", self.FileName, self.CurrentLineNumber)

        RegionObj.RegionType = BINARY_FILE_TYPE_FV
        RegionObj.RegionDataList.append((self._Token).upper())

        while self._IsKeyword(BINARY_FILE_TYPE_FV):

            if not self._IsToken(TAB_EQUAL_SPLIT):
                raise Warning.ExpectedEquals(self.FileName, self.CurrentLineNumber)

            if not self._GetNextToken():
                raise Warning.Expected("FV name", self.FileName, self.CurrentLineNumber)

            RegionObj.RegionDataList.append((self._Token).upper())

    ## _GetRegionCapType() method
    #
    #   Get region capsule data for region
    #
    #   @param  self        The object pointer
    #   @param  RegionObj   for whom region data is got
    #
    def _GetRegionCapType(self, RegionObj):
        if not self._IsKeyword("CAPSULE"):
            raise Warning.Expected("'CAPSULE'", self.FileName, self.CurrentLineNumber)

        if not self._IsToken(TAB_EQUAL_SPLIT):
            raise Warning.ExpectedEquals(self.FileName, self.CurrentLineNumber)

        if not self._GetNextToken():
            raise Warning.Expected("CAPSULE name", self.FileName, self.CurrentLineNumber)

        RegionObj.RegionType = "CAPSULE"
        RegionObj.RegionDataList.append(self._Token)

        while self._IsKeyword("CAPSULE"):

            if not self._IsToken(TAB_EQUAL_SPLIT):
                raise Warning.ExpectedEquals(self.FileName, self.CurrentLineNumber)

            if not self._GetNextToken():
                raise Warning.Expected("CAPSULE name", self.FileName, self.CurrentLineNumber)

            RegionObj.RegionDataList.append(self._Token)

    ## _GetRegionFileType() method
    #
    #   Get region file data for region
    #
    #   @param  self        The object pointer
    #   @param  RegionObj   for whom region data is got
    #
    def _GetRegionFileType(self, RegionObj):
        if not self._IsKeyword("FILE"):
            raise Warning.Expected("'FILE'", self.FileName, self.CurrentLineNumber)

        if not self._IsToken(TAB_EQUAL_SPLIT):
            raise Warning.ExpectedEquals(self.FileName, self.CurrentLineNumber)

        if not self._GetNextToken():
            raise Warning.Expected("File name", self.FileName, self.CurrentLineNumber)

        RegionObj.RegionType = "FILE"
        RegionObj.RegionDataList.append(self._Token)

        while self._IsKeyword("FILE"):

            if not self._IsToken(TAB_EQUAL_SPLIT):
                raise Warning.ExpectedEquals(self.FileName, self.CurrentLineNumber)

            if not self._GetNextToken():
                raise Warning.Expected("FILE name", self.FileName, self.CurrentLineNumber)

            RegionObj.RegionDataList.append(self._Token)

    ## _GetRegionDataType() method
    #
    #   Get region array data for region
    #
    #   @param  self        The object pointer
    #   @param  RegionObj   for whom region data is got
    #
    def _GetRegionDataType(self, RegionObj):
        if not self._IsKeyword("DATA"):
            raise Warning.Expected("Region Data type", self.FileName, self.CurrentLineNumber)

        if not self._IsToken(TAB_EQUAL_SPLIT):
            raise Warning.ExpectedEquals(self.FileName, self.CurrentLineNumber)

        if not self._IsToken("{"):
            raise Warning.ExpectedCurlyOpen(self.FileName, self.CurrentLineNumber)

        if not self._GetNextHexNumber():
            raise Warning.Expected("Hex byte", self.FileName, self.CurrentLineNumber)

        if len(self._Token) > 18:
            raise Warning("Hex string can't be converted to a valid UINT64 value", self.FileName, self.CurrentLineNumber)

        # convert hex string value to byte hex string array
        AllString = self._Token
        AllStrLen = len (AllString)
        DataString = ""
        while AllStrLen > 4:
            DataString = DataString + "0x" + AllString[AllStrLen - 2: AllStrLen] + TAB_COMMA_SPLIT
            AllStrLen  = AllStrLen - 2
        DataString = DataString + AllString[:AllStrLen] + TAB_COMMA_SPLIT

        # byte value array
        if len (self._Token) <= 4:
            while self._IsToken(TAB_COMMA_SPLIT):
                if not self._GetNextHexNumber():
                    raise Warning("Invalid Hex number", self.FileName, self.CurrentLineNumber)
                if len(self._Token) > 4:
                    raise Warning("Hex byte(must be 2 digits) too long", self.FileName, self.CurrentLineNumber)
                DataString += self._Token
                DataString += TAB_COMMA_SPLIT

        if not self._IsToken(T_CHAR_BRACE_R):
            raise Warning.ExpectedCurlyClose(self.FileName, self.CurrentLineNumber)

        DataString = DataString.rstrip(TAB_COMMA_SPLIT)
        RegionObj.RegionType = "DATA"
        RegionObj.RegionDataList.append(DataString)

        while self._IsKeyword("DATA"):

            if not self._IsToken(TAB_EQUAL_SPLIT):
                raise Warning.ExpectedEquals(self.FileName, self.CurrentLineNumber)

            if not self._IsToken("{"):
                raise Warning.ExpectedCurlyOpen(self.FileName, self.CurrentLineNumber)

            if not self._GetNextHexNumber():
                raise Warning.Expected("Hex byte", self.FileName, self.CurrentLineNumber)

            if len(self._Token) > 18:
                raise Warning("Hex string can't be converted to a valid UINT64 value", self.FileName, self.CurrentLineNumber)

            # convert hex string value to byte hex string array
            AllString = self._Token
            AllStrLen = len (AllString)
            DataString = ""
            while AllStrLen > 4:
                DataString = DataString + "0x" + AllString[AllStrLen - 2: AllStrLen] + TAB_COMMA_SPLIT
                AllStrLen  = AllStrLen - 2
            DataString = DataString + AllString[:AllStrLen] + TAB_COMMA_SPLIT

            # byte value array
            if len (self._Token) <= 4:
                while self._IsToken(TAB_COMMA_SPLIT):
                    if not self._GetNextHexNumber():
                        raise Warning("Invalid Hex number", self.FileName, self.CurrentLineNumber)
                    if len(self._Token) > 4:
                        raise Warning("Hex byte(must be 2 digits) too long", self.FileName, self.CurrentLineNumber)
                    DataString += self._Token
                    DataString += TAB_COMMA_SPLIT

            if not self._IsToken(T_CHAR_BRACE_R):
                raise Warning.ExpectedCurlyClose(self.FileName, self.CurrentLineNumber)

            DataString = DataString.rstrip(TAB_COMMA_SPLIT)
            RegionObj.RegionDataList.append(DataString)

    ## _GetFv() method
    #
    #   Get FV section contents and store its data into FV dictionary of self.Profile
    #
    #   @param  self        The object pointer
    #   @retval True        Successfully find a FV
    #   @retval False       Not able to find a FV
    #
    def _GetFv(self):
        if not self._GetNextToken():
            return False

        S = self._Token.upper()
        if S.startswith(TAB_SECTION_START) and not S.startswith("[FV."):
            self.SectionParser(S)
            self._UndoToken()
            return False

        self._UndoToken()
        if not self._IsToken("[FV.", True):
            FileLineTuple = GetRealFileLine(self.FileName, self.CurrentLineNumber)
            #print 'Parsing String: %s in File %s, At line: %d, Offset Within Line: %d' \
            #        % (self.Profile.FileLinesList[self.CurrentLineNumber - 1][self.CurrentOffsetWithinLine:], FileLineTuple[0], FileLineTuple[1], self.CurrentOffsetWithinLine)
            raise Warning("Unknown Keyword '%s'" % self._Token, self.FileName, self.CurrentLineNumber)

        FvName = self._GetUiName()
        self.CurrentFvName = FvName.upper()

        if not self._IsToken(TAB_SECTION_END):
            raise Warning.ExpectedBracketClose(self.FileName, self.CurrentLineNumber)

        FvObj = FV(Name=self.CurrentFvName)
        self.Profile.FvDict[self.CurrentFvName] = FvObj

        Status = self._GetCreateFile(FvObj)
        if not Status:
            raise Warning("FV name error", self.FileName, self.CurrentLineNumber)

        self._GetDefineStatements(FvObj)

        self._GetAddressStatements(FvObj)

        while True:
            self._GetSetStatements(FvObj)

            if not (self._GetBlockStatement(FvObj) or self._GetFvBaseAddress(FvObj) or
                self._GetFvForceRebase(FvObj) or self._GetFvAlignment(FvObj) or
                self._GetFvAttributes(FvObj) or self._GetFvNameGuid(FvObj) or
                self._GetFvExtEntryStatement(FvObj) or self._GetFvNameString(FvObj)):
                break

        if FvObj.FvNameString == 'TRUE' and not FvObj.FvNameGuid:
            raise Warning("FvNameString found but FvNameGuid was not found", self.FileName, self.CurrentLineNumber)

        self._GetAprioriSection(FvObj)
        self._GetAprioriSection(FvObj)

        while True:
            isInf = self._GetInfStatement(FvObj)
            isFile = self._GetFileStatement(FvObj)
            if not isInf and not isFile:
                break

        return True

    ## _GetFvAlignment() method
    #
    #   Get alignment for FV
    #
    #   @param  self        The object pointer
    #   @param  Obj         for whom alignment is got
    #   @retval True        Successfully find a alignment statement
    #   @retval False       Not able to find a alignment statement
    #
    def _GetFvAlignment(self, Obj):
        if not self._IsKeyword("FvAlignment"):
            return False

        if not self._IsToken(TAB_EQUAL_SPLIT):
            raise Warning.ExpectedEquals(self.FileName, self.CurrentLineNumber)

        if not self._GetNextToken():
            raise Warning.Expected("alignment value", self.FileName, self.CurrentLineNumber)

        if self._Token.upper() not in {"1", "2", "4", "8", "16", "32", "64", "128", "256", "512", \
                                        "1K", "2K", "4K", "8K", "16K", "32K", "64K", "128K", "256K", "512K", \
                                        "1M", "2M", "4M", "8M", "16M", "32M", "64M", "128M", "256M", "512M", \
                                        "1G", "2G"}:
            raise Warning("Unknown alignment value '%s'" % self._Token, self.FileName, self.CurrentLineNumber)
        Obj.FvAlignment = self._Token
        return True

    ## _GetFvBaseAddress() method
    #
    #   Get BaseAddress for FV
    #
    #   @param  self        The object pointer
    #   @param  Obj         for whom FvBaseAddress is got
    #   @retval True        Successfully find a FvBaseAddress statement
    #   @retval False       Not able to find a FvBaseAddress statement
    #
    def _GetFvBaseAddress(self, Obj):
        if not self._IsKeyword("FvBaseAddress"):
            return False

        if not self._IsToken(TAB_EQUAL_SPLIT):
            raise Warning.ExpectedEquals(self.FileName, self.CurrentLineNumber)

        if not self._GetNextToken():
            raise Warning.Expected("FV base address value", self.FileName, self.CurrentLineNumber)

        if not BaseAddrValuePattern.match(self._Token.upper()):
            raise Warning("Unknown FV base address value '%s'" % self._Token, self.FileName, self.CurrentLineNumber)
        Obj.FvBaseAddress = self._Token
        return True

    ## _GetFvForceRebase() method
    #
    #   Get FvForceRebase for FV
    #
    #   @param  self        The object pointer
    #   @param  Obj         for whom FvForceRebase is got
    #   @retval True        Successfully find a FvForceRebase statement
    #   @retval False       Not able to find a FvForceRebase statement
    #
    def _GetFvForceRebase(self, Obj):
        if not self._IsKeyword("FvForceRebase"):
            return False

        if not self._IsToken(TAB_EQUAL_SPLIT):
            raise Warning.ExpectedEquals(self.FileName, self.CurrentLineNumber)

        if not self._GetNextToken():
            raise Warning.Expected("FvForceRebase value", self.FileName, self.CurrentLineNumber)

        if self._Token.upper() not in {"TRUE", "FALSE", "0", "0X0", "0X00", "1", "0X1", "0X01"}:
            raise Warning("Unknown FvForceRebase value '%s'" % self._Token, self.FileName, self.CurrentLineNumber)

        if self._Token.upper() in {"TRUE", "1", "0X1", "0X01"}:
            Obj.FvForceRebase = True
        elif self._Token.upper() in {"FALSE", "0", "0X0", "0X00"}:
            Obj.FvForceRebase = False
        else:
            Obj.FvForceRebase = None

        return True


    ## _GetFvAttributes() method
    #
    #   Get attributes for FV
    #
    #   @param  self        The object pointer
    #   @param  Obj         for whom attribute is got
    #   @retval None
    #
    def _GetFvAttributes(self, FvObj):
        IsWordToken = False
        while self._GetNextWord():
            IsWordToken = True
            name = self._Token
            if name not in {"ERASE_POLARITY", "MEMORY_MAPPED", \
                           "STICKY_WRITE", "LOCK_CAP", "LOCK_STATUS", "WRITE_ENABLED_CAP", \
                           "WRITE_DISABLED_CAP", "WRITE_STATUS", "READ_ENABLED_CAP", \
                           "READ_DISABLED_CAP", "READ_STATUS", "READ_LOCK_CAP", \
                           "READ_LOCK_STATUS", "WRITE_LOCK_CAP", "WRITE_LOCK_STATUS", \
                           "WRITE_POLICY_RELIABLE", "WEAK_ALIGNMENT", "FvUsedSizeEnable"}:
                self._UndoToken()
                return False

            if not self._IsToken(TAB_EQUAL_SPLIT):
                raise Warning.ExpectedEquals(self.FileName, self.CurrentLineNumber)

            if not self._GetNextToken() or self._Token.upper() not in {"TRUE", "FALSE", "1", "0"}:
                raise Warning.Expected("TRUE/FALSE (1/0)", self.FileName, self.CurrentLineNumber)

            FvObj.FvAttributeDict[name] = self._Token

        return IsWordToken

    ## _GetFvNameGuid() method
    #
    #   Get FV GUID for FV
    #
    #   @param  self        The object pointer
    #   @param  Obj         for whom GUID is got
    #   @retval None
    #
    def _GetFvNameGuid(self, FvObj):
        if not self._IsKeyword("FvNameGuid"):
            return False

        if not self._IsToken(TAB_EQUAL_SPLIT):
            raise Warning.ExpectedEquals(self.FileName, self.CurrentLineNumber)

        if not self._GetNextGuid():
            raise Warning.Expected("GUID value", self.FileName, self.CurrentLineNumber)

        FvObj.FvNameGuid = self._Token

        return True

    def _GetFvNameString(self, FvObj):
        if not self._IsKeyword("FvNameString"):
            return False

        if not self._IsToken(TAB_EQUAL_SPLIT):
            raise Warning.ExpectedEquals(self.FileName, self.CurrentLineNumber)

        if not self._GetNextToken() or self._Token.upper() not in {'TRUE', 'FALSE'}:
            raise Warning.Expected("TRUE or FALSE for FvNameString", self.FileName, self.CurrentLineNumber)

        FvObj.FvNameString = self._Token

        return True

    def _GetFvExtEntryStatement(self, FvObj):
        if not (self._IsKeyword("FV_EXT_ENTRY") or self._IsKeyword("FV_EXT_ENTRY_TYPE")):
            return False

        if not self._IsKeyword ("TYPE"):
            raise Warning.Expected("'TYPE'", self.FileName, self.CurrentLineNumber)

        if not self._IsToken(TAB_EQUAL_SPLIT):
            raise Warning.ExpectedEquals(self.FileName, self.CurrentLineNumber)

        if not self._GetNextHexNumber() and not self._GetNextDecimalNumber():
            raise Warning.Expected("Hex FV extension entry type value At Line ", self.FileName, self.CurrentLineNumber)

        FvObj.FvExtEntryTypeValue.append(self._Token)

        if not self._IsToken("{"):
            raise Warning.ExpectedCurlyOpen(self.FileName, self.CurrentLineNumber)

        if not self._IsKeyword("FILE") and not self._IsKeyword("DATA"):
            raise Warning.Expected("'FILE' or 'DATA'", self.FileName, self.CurrentLineNumber)

        FvObj.FvExtEntryType.append(self._Token)

        if self._Token == 'DATA':
            if not self._IsToken(TAB_EQUAL_SPLIT):
                raise Warning.ExpectedEquals(self.FileName, self.CurrentLineNumber)

            if not self._IsToken("{"):
                raise Warning.ExpectedCurlyOpen(self.FileName, self.CurrentLineNumber)

            if not self._GetNextHexNumber():
                raise Warning.Expected("Hex byte", self.FileName, self.CurrentLineNumber)

            if len(self._Token) > 4:
                raise Warning("Hex byte(must be 2 digits) too long", self.FileName, self.CurrentLineNumber)

            DataString = self._Token
            DataString += TAB_COMMA_SPLIT

            while self._IsToken(TAB_COMMA_SPLIT):
                if not self._GetNextHexNumber():
                    raise Warning("Invalid Hex number", self.FileName, self.CurrentLineNumber)
                if len(self._Token) > 4:
                    raise Warning("Hex byte(must be 2 digits) too long", self.FileName, self.CurrentLineNumber)
                DataString += self._Token
                DataString += TAB_COMMA_SPLIT

            if not self._IsToken(T_CHAR_BRACE_R):
                raise Warning.ExpectedCurlyClose(self.FileName, self.CurrentLineNumber)

            if not self._IsToken(T_CHAR_BRACE_R):
                raise Warning.ExpectedCurlyClose(self.FileName, self.CurrentLineNumber)

            DataString = DataString.rstrip(TAB_COMMA_SPLIT)
            FvObj.FvExtEntryData.append(DataString)

        if self._Token == 'FILE':
            if not self._IsToken(TAB_EQUAL_SPLIT):
                raise Warning.ExpectedEquals(self.FileName, self.CurrentLineNumber)

            if not self._GetNextToken():
                raise Warning.Expected("FV Extension Entry file path At Line ", self.FileName, self.CurrentLineNumber)

            FvObj.FvExtEntryData.append(self._Token)

            if not self._IsToken(T_CHAR_BRACE_R):
                raise Warning.ExpectedCurlyClose(self.FileName, self.CurrentLineNumber)

        return True

    ## _GetAprioriSection() method
    #
    #   Get token statements
    #
    #   @param  self        The object pointer
    #   @param  FvObj       for whom apriori is got
    #   @retval True        Successfully find apriori statement
    #   @retval False       Not able to find apriori statement
    #
    def _GetAprioriSection(self, FvObj):
        if not self._IsKeyword("APRIORI"):
            return False

        if not self._IsKeyword("PEI") and not self._IsKeyword("DXE"):
            raise Warning.Expected("Apriori file type", self.FileName, self.CurrentLineNumber)
        AprType = self._Token

        if not self._IsToken("{"):
            raise Warning.ExpectedCurlyOpen(self.FileName, self.CurrentLineNumber)

        AprSectionObj = AprioriSection()
        AprSectionObj.AprioriType = AprType

        self._GetDefineStatements(AprSectionObj)

        while True:
            IsInf = self._GetInfStatement(AprSectionObj)
            IsFile = self._GetFileStatement(AprSectionObj)
            if not IsInf and not IsFile:
                break

        if not self._IsToken(T_CHAR_BRACE_R):
            raise Warning.ExpectedCurlyClose(self.FileName, self.CurrentLineNumber)

        FvObj.AprioriSectionList.append(AprSectionObj)
        return True

    def _ParseInfStatement(self):
        if not self._IsKeyword("INF"):
            return None

        ffsInf = FfsInfStatement()
        self._GetInfOptions(ffsInf)

        if not self._GetNextToken():
            raise Warning.Expected("INF file path", self.FileName, self.CurrentLineNumber)
        ffsInf.InfFileName = self._Token
        if not ffsInf.InfFileName.endswith('.inf'):
            raise Warning.Expected(".inf file path", self.FileName, self.CurrentLineNumber)

        ffsInf.CurrentLineNum = self.CurrentLineNumber
        ffsInf.CurrentLineContent = self._CurrentLine()

        #Replace $(SAPCE) with real space
        ffsInf.InfFileName = ffsInf.InfFileName.replace('$(SPACE)', ' ')

        if ffsInf.InfFileName.replace(TAB_WORKSPACE, '').find('$') == -1:
            #do case sensitive check for file path
            ErrorCode, ErrorInfo = PathClass(NormPath(ffsInf.InfFileName), GenFdsGlobalVariable.WorkSpaceDir).Validate()
            if ErrorCode != 0:
                EdkLogger.error("GenFds", ErrorCode, ExtraData=ErrorInfo)

        NewFileName = ffsInf.InfFileName
        if ffsInf.OverrideGuid:
            NewFileName = ProcessDuplicatedInf(PathClass(ffsInf.InfFileName,GenFdsGlobalVariable.WorkSpaceDir), ffsInf.OverrideGuid, GenFdsGlobalVariable.WorkSpaceDir).Path

        if not NewFileName in self.Profile.InfList:
            self.Profile.InfList.append(NewFileName)
            FileLineTuple = GetRealFileLine(self.FileName, self.CurrentLineNumber)
            self.Profile.InfFileLineList.append(FileLineTuple)
            if ffsInf.UseArch:
                if ffsInf.UseArch not in self.Profile.InfDict:
                    self.Profile.InfDict[ffsInf.UseArch] = [ffsInf.InfFileName]
                else:
                    self.Profile.InfDict[ffsInf.UseArch].append(ffsInf.InfFileName)
            else:
                self.Profile.InfDict['ArchTBD'].append(ffsInf.InfFileName)

        if self._IsToken(TAB_VALUE_SPLIT):
            if self._IsKeyword('RELOCS_STRIPPED'):
                ffsInf.KeepReloc = False
            elif self._IsKeyword('RELOCS_RETAINED'):
                ffsInf.KeepReloc = True
            else:
                raise Warning("Unknown reloc strip flag '%s'" % self._Token, self.FileName, self.CurrentLineNumber)
        return ffsInf

    ## _GetInfStatement() method
    #
    #   Get INF statements
    #
    #   @param  self        The object pointer
    #   @param  Obj         for whom inf statement is got
    #   @retval True        Successfully find inf statement
    #   @retval False       Not able to find inf statement
    #
    def _GetInfStatement(self, Obj, ForCapsule=False):
        ffsInf = self._ParseInfStatement()
        if not ffsInf:
            return False

        if ForCapsule:
            myCapsuleFfs = CapsuleFfs()
            myCapsuleFfs.Ffs = ffsInf
            Obj.CapsuleDataList.append(myCapsuleFfs)
        else:
            Obj.FfsList.append(ffsInf)
        return True

    ## _GetInfOptions() method
    #
    #   Get options for INF
    #
    #   @param  self        The object pointer
    #   @param  FfsInfObj   for whom option is got
    #
    def _GetInfOptions(self, FfsInfObj):
        if self._IsKeyword("FILE_GUID"):
            if not self._IsToken(TAB_EQUAL_SPLIT):
                raise Warning.ExpectedEquals(self.FileName, self.CurrentLineNumber)
            if not self._GetNextGuid():
                raise Warning.Expected("GUID value", self.FileName, self.CurrentLineNumber)
            FfsInfObj.OverrideGuid = self._Token

        if self._IsKeyword("RuleOverride"):
            if not self._IsToken(TAB_EQUAL_SPLIT):
                raise Warning.ExpectedEquals(self.FileName, self.CurrentLineNumber)
            if not self._GetNextToken():
                raise Warning.Expected("Rule name", self.FileName, self.CurrentLineNumber)
            FfsInfObj.Rule = self._Token

        if self._IsKeyword("VERSION"):
            if not self._IsToken(TAB_EQUAL_SPLIT):
                raise Warning.ExpectedEquals(self.FileName, self.CurrentLineNumber)
            if not self._GetNextToken():
                raise Warning.Expected("Version", self.FileName, self.CurrentLineNumber)

            if self._GetStringData():
                FfsInfObj.Version = self._Token

        if self._IsKeyword(BINARY_FILE_TYPE_UI):
            if not self._IsToken(TAB_EQUAL_SPLIT):
                raise Warning.ExpectedEquals(self.FileName, self.CurrentLineNumber)
            if not self._GetNextToken():
                raise Warning.Expected("UI name", self.FileName, self.CurrentLineNumber)

            if self._GetStringData():
                FfsInfObj.Ui = self._Token

        if self._IsKeyword("USE"):
            if not self._IsToken(TAB_EQUAL_SPLIT):
                raise Warning.ExpectedEquals(self.FileName, self.CurrentLineNumber)
            if not self._GetNextToken():
                raise Warning.Expected("ARCH name", self.FileName, self.CurrentLineNumber)
            FfsInfObj.UseArch = self._Token


        if self._GetNextToken():
            p = compile(r'([a-zA-Z0-9\-]+|\$\(TARGET\)|\*)_([a-zA-Z0-9\-]+|\$\(TOOL_CHAIN_TAG\)|\*)_([a-zA-Z0-9\-]+|\$\(ARCH\))')
            if p.match(self._Token) and p.match(self._Token).span()[1] == len(self._Token):
                FfsInfObj.KeyStringList.append(self._Token)
                if not self._IsToken(TAB_COMMA_SPLIT):
                    return
            else:
                self._UndoToken()
                return

            while self._GetNextToken():
                if not p.match(self._Token):
                    raise Warning.Expected("KeyString \"Target_Tag_Arch\"", self.FileName, self.CurrentLineNumber)
                FfsInfObj.KeyStringList.append(self._Token)

                if not self._IsToken(TAB_COMMA_SPLIT):
                    break

    ## _GetFileStatement() method
    #
    #   Get FILE statements
    #
    #   @param  self        The object pointer
    #   @param  Obj         for whom FILE statement is got
    #   @retval True        Successfully find FILE statement
    #   @retval False       Not able to find FILE statement
    #
    def _GetFileStatement(self, Obj, ForCapsule = False):
        if not self._IsKeyword("FILE"):
            return False

        if not self._GetNextWord():
            raise Warning.Expected("FFS type", self.FileName, self.CurrentLineNumber)

        if ForCapsule and self._Token == 'DATA':
            self._UndoToken()
            self._UndoToken()
            return False

        FfsFileObj = FileStatement()
        FfsFileObj.FvFileType = self._Token

        if not self._IsToken(TAB_EQUAL_SPLIT):
            raise Warning.ExpectedEquals(self.FileName, self.CurrentLineNumber)

        if not self._GetNextGuid():
            if not self._GetNextWord():
                raise Warning.Expected("File GUID", self.FileName, self.CurrentLineNumber)
            if self._Token == 'PCD':
                if not self._IsToken("("):
                    raise Warning.Expected("'('", self.FileName, self.CurrentLineNumber)
                PcdPair = self._GetNextPcdSettings()
                if not self._IsToken(")"):
                    raise Warning.Expected("')'", self.FileName, self.CurrentLineNumber)
                self._Token = 'PCD('+PcdPair[1]+TAB_SPLIT+PcdPair[0]+')'

        FfsFileObj.NameGuid = self._Token

        self._GetFilePart(FfsFileObj)

        if ForCapsule:
            capsuleFfs = CapsuleFfs()
            capsuleFfs.Ffs = FfsFileObj
            Obj.CapsuleDataList.append(capsuleFfs)
        else:
            Obj.FfsList.append(FfsFileObj)

        return True

    ## _FileCouldHaveRelocFlag() method
    #
    #   Check whether reloc strip flag can be set for a file type.
    #
    #   @param  FileType    The file type to check with
    #   @retval True        This type could have relocation strip flag
    #   @retval False       No way to have it
    #
    @staticmethod
    def _FileCouldHaveRelocFlag (FileType):
        if FileType in {SUP_MODULE_SEC, SUP_MODULE_PEI_CORE, SUP_MODULE_PEIM, SUP_MODULE_MM_CORE_STANDALONE, 'PEI_DXE_COMBO'}:
            return True
        else:
            return False

    ## _SectionCouldHaveRelocFlag() method
    #
    #   Check whether reloc strip flag can be set for a section type.
    #
    #   @param  SectionType The section type to check with
    #   @retval True        This type could have relocation strip flag
    #   @retval False       No way to have it
    #
    @staticmethod
    def _SectionCouldHaveRelocFlag (SectionType):
        if SectionType in {BINARY_FILE_TYPE_TE, BINARY_FILE_TYPE_PE32}:
            return True
        else:
            return False

    ## _GetFilePart() method
    #
    #   Get components for FILE statement
    #
    #   @param  self        The object pointer
    #   @param  FfsFileObj   for whom component is got
    #
    def _GetFilePart(self, FfsFileObj):
        self._GetFileOpts(FfsFileObj)

        if not self._IsToken("{"):
            if self._IsKeyword('RELOCS_STRIPPED') or self._IsKeyword('RELOCS_RETAINED'):
                if self._FileCouldHaveRelocFlag(FfsFileObj.FvFileType):
                    if self._Token == 'RELOCS_STRIPPED':
                        FfsFileObj.KeepReloc = False
                    else:
                        FfsFileObj.KeepReloc = True
                else:
                    raise Warning("File type %s could not have reloc strip flag%d" % (FfsFileObj.FvFileType, self.CurrentLineNumber), self.FileName, self.CurrentLineNumber)

            if not self._IsToken("{"):
                raise Warning.ExpectedCurlyOpen(self.FileName, self.CurrentLineNumber)

        if not self._GetNextToken():
            raise Warning.Expected("File name or section data", self.FileName, self.CurrentLineNumber)

        if self._Token == BINARY_FILE_TYPE_FV:
            if not self._IsToken(TAB_EQUAL_SPLIT):
                raise Warning.ExpectedEquals(self.FileName, self.CurrentLineNumber)
            if not self._GetNextToken():
                raise Warning.Expected("FV name", self.FileName, self.CurrentLineNumber)
            FfsFileObj.FvName = self._Token

        elif self._Token == "FD":
            if not self._IsToken(TAB_EQUAL_SPLIT):
                raise Warning.ExpectedEquals(self.FileName, self.CurrentLineNumber)
            if not self._GetNextToken():
                raise Warning.Expected("FD name", self.FileName, self.CurrentLineNumber)
            FfsFileObj.FdName = self._Token

        elif self._Token in {TAB_DEFINE, "APRIORI", "SECTION"}:
            self._UndoToken()
            self._GetSectionData(FfsFileObj)

        elif hasattr(FfsFileObj, 'FvFileType') and FfsFileObj.FvFileType == 'RAW':
            self._UndoToken()
            self._GetRAWData(FfsFileObj)

        else:
            FfsFileObj.CurrentLineNum = self.CurrentLineNumber
            FfsFileObj.CurrentLineContent = self._CurrentLine()
            FfsFileObj.FileName = self._Token.replace('$(SPACE)', ' ')
            self._VerifyFile(FfsFileObj.FileName)

        if not self._IsToken(T_CHAR_BRACE_R):
            raise Warning.ExpectedCurlyClose(self.FileName, self.CurrentLineNumber)

    ## _GetRAWData() method
    #
    #   Get RAW data for FILE statement
    #
    #   @param  self         The object pointer
    #   @param  FfsFileObj   for whom section is got
    #
    def _GetRAWData(self, FfsFileObj):
        FfsFileObj.FileName = []
        FfsFileObj.SubAlignment = []
        while True:
            AlignValue = None
            if self._GetAlignment():
                if self._Token not in ALIGNMENTS:
                    raise Warning("Incorrect alignment '%s'" % self._Token, self.FileName, self.CurrentLineNumber)
                #For FFS, Auto is default option same to ""
                if not self._Token == "Auto":
                    AlignValue = self._Token
            if not self._GetNextToken():
                raise Warning.Expected("Filename value", self.FileName, self.CurrentLineNumber)

            FileName = self._Token.replace('$(SPACE)', ' ')
            if FileName == T_CHAR_BRACE_R:
                self._UndoToken()
                raise Warning.Expected("Filename value", self.FileName, self.CurrentLineNumber)

            self._VerifyFile(FileName)
            File = PathClass(NormPath(FileName), GenFdsGlobalVariable.WorkSpaceDir)
            FfsFileObj.FileName.append(File.Path)
            FfsFileObj.SubAlignment.append(AlignValue)

            if self._IsToken(T_CHAR_BRACE_R):
                self._UndoToken()
                break

        if len(FfsFileObj.SubAlignment) == 1:
            FfsFileObj.SubAlignment = FfsFileObj.SubAlignment[0]
        if len(FfsFileObj.FileName) == 1:
            FfsFileObj.FileName = FfsFileObj.FileName[0]

    ## _GetFileOpts() method
    #
    #   Get options for FILE statement
    #
    #   @param  self        The object pointer
    #   @param  FfsFileObj   for whom options is got
    #
    def _GetFileOpts(self, FfsFileObj):
        if self._GetNextToken():
            if TokenFindPattern.match(self._Token):
                FfsFileObj.KeyStringList.append(self._Token)
                if self._IsToken(TAB_COMMA_SPLIT):
                    while self._GetNextToken():
                        if not TokenFindPattern.match(self._Token):
                            raise Warning.Expected("KeyString \"Target_Tag_Arch\"", self.FileName, self.CurrentLineNumber)
                        FfsFileObj.KeyStringList.append(self._Token)

                        if not self._IsToken(TAB_COMMA_SPLIT):
                            break

            else:
                self._UndoToken()

        if self._IsKeyword("FIXED", True):
            FfsFileObj.Fixed = True

        if self._IsKeyword("CHECKSUM", True):
            FfsFileObj.CheckSum = True

        if self._GetAlignment():
            if self._Token not in ALIGNMENTS:
                raise Warning("Incorrect alignment '%s'" % self._Token, self.FileName, self.CurrentLineNumber)
            #For FFS, Auto is default option same to ""
            if not self._Token == "Auto":
                FfsFileObj.Alignment = self._Token

    ## _GetAlignment() method
    #
    #   Return the alignment value
    #
    #   @param  self        The object pointer
    #   @retval True        Successfully find alignment
    #   @retval False       Not able to find alignment
    #
    def _GetAlignment(self):
        if self._IsKeyword("Align", True):
            if not self._IsToken(TAB_EQUAL_SPLIT):
                raise Warning.ExpectedEquals(self.FileName, self.CurrentLineNumber)

            if not self._GetNextToken():
                raise Warning.Expected("alignment value", self.FileName, self.CurrentLineNumber)
            return True

        return False

    ## _GetSectionData() method
    #
    #   Get section data for FILE statement
    #
    #   @param  self        The object pointer
    #   @param  FfsFileObj   for whom section is got
    #
    def _GetSectionData(self, FfsFileObj):
        self._GetDefineStatements(FfsFileObj)

        while True:
            IsLeafSection = self._GetLeafSection(FfsFileObj)
            IsEncapSection = self._GetEncapsulationSec(FfsFileObj)
            if not IsLeafSection and not IsEncapSection:
                break

    ## _GetLeafSection() method
    #
    #   Get leaf section for Obj
    #
    #   @param  self        The object pointer
    #   @param  Obj         for whom leaf section is got
    #   @retval True        Successfully find section statement
    #   @retval False       Not able to find section statement
    #
    def _GetLeafSection(self, Obj):
        OldPos = self.GetFileBufferPos()

        if not self._IsKeyword("SECTION"):
            if len(Obj.SectionList) == 0:
                raise Warning.Expected("SECTION", self.FileName, self.CurrentLineNumber)
            else:
                return False

        AlignValue = None
        if self._GetAlignment():
            if self._Token not in ALIGNMENTS:
                raise Warning("Incorrect alignment '%s'" % self._Token, self.FileName, self.CurrentLineNumber)
            AlignValue = self._Token

        BuildNum = None
        if self._IsKeyword("BUILD_NUM"):
            if not self._IsToken(TAB_EQUAL_SPLIT):
                raise Warning.ExpectedEquals(self.FileName, self.CurrentLineNumber)

            if not self._GetNextToken():
                raise Warning.Expected("Build number value", self.FileName, self.CurrentLineNumber)

            BuildNum = self._Token

        if self._IsKeyword("VERSION"):
            if AlignValue == 'Auto':
                raise Warning("Auto alignment can only be used in PE32 or TE section ", self.FileName, self.CurrentLineNumber)
            if not self._IsToken(TAB_EQUAL_SPLIT):
                raise Warning.ExpectedEquals(self.FileName, self.CurrentLineNumber)
            if not self._GetNextToken():
                raise Warning.Expected("version", self.FileName, self.CurrentLineNumber)
            VerSectionObj = VerSection()
            VerSectionObj.Alignment = AlignValue
            VerSectionObj.BuildNum = BuildNum
            if self._GetStringData():
                VerSectionObj.StringData = self._Token
            else:
                VerSectionObj.FileName = self._Token
            Obj.SectionList.append(VerSectionObj)

        elif self._IsKeyword(BINARY_FILE_TYPE_UI):
            if AlignValue == 'Auto':
                raise Warning("Auto alignment can only be used in PE32 or TE section ", self.FileName, self.CurrentLineNumber)
            if not self._IsToken(TAB_EQUAL_SPLIT):
                raise Warning.ExpectedEquals(self.FileName, self.CurrentLineNumber)
            if not self._GetNextToken():
                raise Warning.Expected("UI", self.FileName, self.CurrentLineNumber)
            UiSectionObj = UiSection()
            UiSectionObj.Alignment = AlignValue
            if self._GetStringData():
                UiSectionObj.StringData = self._Token
            else:
                UiSectionObj.FileName = self._Token
            Obj.SectionList.append(UiSectionObj)

        elif self._IsKeyword("FV_IMAGE"):
            if AlignValue == 'Auto':
                raise Warning("Auto alignment can only be used in PE32 or TE section ", self.FileName, self.CurrentLineNumber)
            if not self._IsToken(TAB_EQUAL_SPLIT):
                raise Warning.ExpectedEquals(self.FileName, self.CurrentLineNumber)
            if not self._GetNextToken():
                raise Warning.Expected("FV name or FV file path", self.FileName, self.CurrentLineNumber)

            FvName = self._Token
            FvObj = None

            if self._IsToken("{"):
                FvObj = FV()
                FvObj.UiFvName = FvName.upper()
                self._GetDefineStatements(FvObj)

                self._GetBlockStatement(FvObj)
                self._GetSetStatements(FvObj)
                self._GetFvAlignment(FvObj)
                self._GetFvAttributes(FvObj)

                while True:
                    IsInf = self._GetInfStatement(FvObj)
                    IsFile = self._GetFileStatement(FvObj)
                    if not IsInf and not IsFile:
                        break

                if not self._IsToken(T_CHAR_BRACE_R):
                    raise Warning.ExpectedCurlyClose(self.FileName, self.CurrentLineNumber)

            FvImageSectionObj = FvImageSection()
            FvImageSectionObj.Alignment = AlignValue
            if FvObj is not None:
                FvImageSectionObj.Fv = FvObj
                FvImageSectionObj.FvName = None
            else:
                FvImageSectionObj.FvName = FvName.upper()
                FvImageSectionObj.FvFileName = FvName

            Obj.SectionList.append(FvImageSectionObj)

        elif self._IsKeyword("PEI_DEPEX_EXP") or self._IsKeyword("DXE_DEPEX_EXP") or self._IsKeyword("SMM_DEPEX_EXP"):
            if AlignValue == 'Auto':
                raise Warning("Auto alignment can only be used in PE32 or TE section ", self.FileName, self.CurrentLineNumber)
            DepexSectionObj = DepexSection()
            DepexSectionObj.Alignment = AlignValue
            DepexSectionObj.DepexType = self._Token

            if not self._IsToken(TAB_EQUAL_SPLIT):
                raise Warning.ExpectedEquals(self.FileName, self.CurrentLineNumber)
            if not self._IsToken("{"):
                raise Warning.ExpectedCurlyOpen(self.FileName, self.CurrentLineNumber)
            if not self._SkipToToken(T_CHAR_BRACE_R):
                raise Warning.Expected("Depex expression ending '}'", self.FileName, self.CurrentLineNumber)

            DepexSectionObj.Expression = self._SkippedChars.rstrip(T_CHAR_BRACE_R)
            Obj.SectionList.append(DepexSectionObj)

        else:
            if not self._GetNextWord():
                raise Warning.Expected("section type", self.FileName, self.CurrentLineNumber)

            # Encapsulation section appear, UndoToken and return
            if self._Token == "COMPRESS" or self._Token == "GUIDED":
                self.SetFileBufferPos(OldPos)
                return False

            if self._Token not in {"COMPAT16", BINARY_FILE_TYPE_PE32, BINARY_FILE_TYPE_PIC, BINARY_FILE_TYPE_TE, "FV_IMAGE", "RAW", BINARY_FILE_TYPE_DXE_DEPEX,\
                               BINARY_FILE_TYPE_UI, "VERSION", BINARY_FILE_TYPE_PEI_DEPEX, "SUBTYPE_GUID", BINARY_FILE_TYPE_SMM_DEPEX}:
                raise Warning("Unknown section type '%s'" % self._Token, self.FileName, self.CurrentLineNumber)
            if AlignValue == 'Auto'and (not self._Token == BINARY_FILE_TYPE_PE32) and (not self._Token == BINARY_FILE_TYPE_TE):
                raise Warning("Auto alignment can only be used in PE32 or TE section ", self.FileName, self.CurrentLineNumber)

            # DataSection
            DataSectionObj = DataSection()
            DataSectionObj.Alignment = AlignValue
            DataSectionObj.SecType = self._Token

            if self._IsKeyword('RELOCS_STRIPPED') or self._IsKeyword('RELOCS_RETAINED'):
                if self._FileCouldHaveRelocFlag(Obj.FvFileType) and self._SectionCouldHaveRelocFlag(DataSectionObj.SecType):
                    if self._Token == 'RELOCS_STRIPPED':
                        DataSectionObj.KeepReloc = False
                    else:
                        DataSectionObj.KeepReloc = True
                else:
                    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)

            if self._IsToken(TAB_EQUAL_SPLIT):
                if not self._GetNextToken():
                    raise Warning.Expected("section file path", self.FileName, self.CurrentLineNumber)
                DataSectionObj.SectFileName = self._Token
                self._VerifyFile(DataSectionObj.SectFileName)
            else:
                if not self._GetCglSection(DataSectionObj):
                    return False

            Obj.SectionList.append(DataSectionObj)

        return True

    ## _VerifyFile
    #
    #    Check if file exists or not:
    #      If current phase if GenFds, the file must exist;
    #      If current phase is AutoGen and the file is not in $(OUTPUT_DIRECTORY), the file must exist
    #    @param FileName: File path to be verified.
    #
    def _VerifyFile(self, FileName):
        if FileName.replace(TAB_WORKSPACE, '').find('$') != -1:
            return
        if not GlobalData.gAutoGenPhase or not self._GetMacroValue(TAB_DSC_DEFINES_OUTPUT_DIRECTORY) in FileName:
            ErrorCode, ErrorInfo = PathClass(NormPath(FileName), GenFdsGlobalVariable.WorkSpaceDir).Validate()
            if ErrorCode != 0:
                EdkLogger.error("GenFds", ErrorCode, ExtraData=ErrorInfo)

    ## _GetCglSection() method
    #
    #   Get compressed or GUIDed section for Obj
    #
    #   @param  self        The object pointer
    #   @param  Obj         for whom leaf section is got
    #   @param  AlignValue  alignment value for complex section
    #   @retval True        Successfully find section statement
    #   @retval False       Not able to find section statement
    #
    def _GetCglSection(self, Obj, AlignValue = None):

        if self._IsKeyword("COMPRESS"):
            type = "PI_STD"
            if self._IsKeyword("PI_STD") or self._IsKeyword("PI_NONE"):
                type = self._Token

            if not self._IsToken("{"):
                raise Warning.ExpectedCurlyOpen(self.FileName, self.CurrentLineNumber)

            CompressSectionObj = CompressSection()
            CompressSectionObj.Alignment = AlignValue
            CompressSectionObj.CompType = type
            # Recursive sections...
            while True:
                IsLeafSection = self._GetLeafSection(CompressSectionObj)
                IsEncapSection = self._GetEncapsulationSec(CompressSectionObj)
                if not IsLeafSection and not IsEncapSection:
                    break


            if not self._IsToken(T_CHAR_BRACE_R):
                raise Warning.ExpectedCurlyClose(self.FileName, self.CurrentLineNumber)
            Obj.SectionList.append(CompressSectionObj)
            return True

        elif self._IsKeyword("GUIDED"):
            GuidValue = None
            if self._GetNextGuid():
                GuidValue = self._Token

            AttribDict = self._GetGuidAttrib()
            if not self._IsToken("{"):
                raise Warning.ExpectedCurlyOpen(self.FileName, self.CurrentLineNumber)
            GuidSectionObj = GuidSection()
            GuidSectionObj.Alignment = AlignValue
            GuidSectionObj.NameGuid = GuidValue
            GuidSectionObj.SectionType = "GUIDED"
            GuidSectionObj.ProcessRequired = AttribDict["PROCESSING_REQUIRED"]
            GuidSectionObj.AuthStatusValid = AttribDict["AUTH_STATUS_VALID"]
            GuidSectionObj.ExtraHeaderSize = AttribDict["EXTRA_HEADER_SIZE"]
            # Recursive sections...
            while True:
                IsLeafSection = self._GetLeafSection(GuidSectionObj)
                IsEncapSection = self._GetEncapsulationSec(GuidSectionObj)
                if not IsLeafSection and not IsEncapSection:
                    break

            if not self._IsToken(T_CHAR_BRACE_R):
                raise Warning.ExpectedCurlyClose(self.FileName, self.CurrentLineNumber)
            Obj.SectionList.append(GuidSectionObj)

            return True

        return False

    ## _GetGuidAttri() method
    #
    #   Get attributes for GUID section
    #
    #   @param  self        The object pointer
    #   @retval AttribDict  Dictionary of key-value pair of section attributes
    #
    def _GetGuidAttrib(self):
        AttribDict = {}
        AttribDict["PROCESSING_REQUIRED"] = "NONE"
        AttribDict["AUTH_STATUS_VALID"] = "NONE"
        AttribDict["EXTRA_HEADER_SIZE"] = -1
        while self._IsKeyword("PROCESSING_REQUIRED") or self._IsKeyword("AUTH_STATUS_VALID") \
            or self._IsKeyword("EXTRA_HEADER_SIZE"):
            AttribKey = self._Token

            if not self._IsToken(TAB_EQUAL_SPLIT):
                raise Warning.ExpectedEquals(self.FileName, self.CurrentLineNumber)

            if not self._GetNextToken():
                raise Warning.Expected("TRUE(1)/FALSE(0)/Number", self.FileName, self.CurrentLineNumber)
            elif AttribKey == "EXTRA_HEADER_SIZE":
                Base = 10
                if self._Token[0:2].upper() == "0X":
                    Base = 16
                try:
                    AttribDict[AttribKey] = int(self._Token, Base)
                    continue
                except ValueError:
                    raise Warning.Expected("Number", self.FileName, self.CurrentLineNumber)
            elif self._Token.upper() not in {"TRUE", "FALSE", "1", "0"}:
                raise Warning.Expected("TRUE/FALSE (1/0)", self.FileName, self.CurrentLineNumber)
            AttribDict[AttribKey] = self._Token

        return AttribDict

    ## _GetEncapsulationSec() method
    #
    #   Get encapsulation section for FILE
    #
    #   @param  self        The object pointer
    #   @param  FfsFile     for whom section is got
    #   @retval True        Successfully find section statement
    #   @retval False       Not able to find section statement
    #
    def _GetEncapsulationSec(self, FfsFileObj):
        OldPos = self.GetFileBufferPos()
        if not self._IsKeyword("SECTION"):
            if len(FfsFileObj.SectionList) == 0:
                raise Warning.Expected("SECTION", self.FileName, self.CurrentLineNumber)
            else:
                return False

        AlignValue = None
        if self._GetAlignment():
            if self._Token not in ALIGNMENT_NOAUTO:
                raise Warning("Incorrect alignment '%s'" % self._Token, self.FileName, self.CurrentLineNumber)
            AlignValue = self._Token

        if not self._GetCglSection(FfsFileObj, AlignValue):
            self.SetFileBufferPos(OldPos)
            return False
        else:
            return True

    def _GetFmp(self):
        if not self._GetNextToken():
            return False
        S = self._Token.upper()
        if S.startswith(TAB_SECTION_START) and not S.startswith("[FMPPAYLOAD."):
            self.SectionParser(S)
            self._UndoToken()
            return False

        self._UndoToken()
        self._SkipToToken("[FMPPAYLOAD.", True)
        FmpUiName = self._GetUiName().upper()
        if FmpUiName in self.Profile.FmpPayloadDict:
            raise Warning("Duplicated FMP UI name found: %s" % FmpUiName, self.FileName, self.CurrentLineNumber)

        FmpData = CapsulePayload()
        FmpData.UiName = FmpUiName

        if not self._IsToken(TAB_SECTION_END):
            raise Warning.ExpectedBracketClose(self.FileName, self.CurrentLineNumber)

        if not self._GetNextToken():
            raise Warning("The FMP payload section is empty!", self.FileName, self.CurrentLineNumber)
        FmpKeyList = ['IMAGE_HEADER_INIT_VERSION', 'IMAGE_TYPE_ID', 'IMAGE_INDEX', 'HARDWARE_INSTANCE', 'CERTIFICATE_GUID', 'MONOTONIC_COUNT']
        while self._Token in FmpKeyList:
            Name = self._Token
            FmpKeyList.remove(Name)
            if not self._IsToken(TAB_EQUAL_SPLIT):
                raise Warning.ExpectedEquals(self.FileName, self.CurrentLineNumber)
            if Name == 'IMAGE_TYPE_ID':
                if not self._GetNextGuid():
                    raise Warning.Expected("GUID value for IMAGE_TYPE_ID.", self.FileName, self.CurrentLineNumber)
                FmpData.ImageTypeId = self._Token
            elif Name == 'CERTIFICATE_GUID':
                if not self._GetNextGuid():
                    raise Warning.Expected("GUID value for CERTIFICATE_GUID.", self.FileName, self.CurrentLineNumber)
                FmpData.Certificate_Guid = self._Token
                if UUID(FmpData.Certificate_Guid) != EFI_CERT_TYPE_RSA2048_SHA256_GUID and UUID(FmpData.Certificate_Guid) != EFI_CERT_TYPE_PKCS7_GUID:
                    raise Warning("Only support EFI_CERT_TYPE_RSA2048_SHA256_GUID or EFI_CERT_TYPE_PKCS7_GUID for CERTIFICATE_GUID.", self.FileName, self.CurrentLineNumber)
            else:
                if not self._GetNextToken():
                    raise Warning.Expected("value of %s" % Name, self.FileName, self.CurrentLineNumber)
                Value = self._Token
                if Name == 'IMAGE_HEADER_INIT_VERSION':
                    if FdfParser._Verify(Name, Value, 'UINT8'):
                        FmpData.Version = Value
                elif Name == 'IMAGE_INDEX':
                    if FdfParser._Verify(Name, Value, 'UINT8'):
                        FmpData.ImageIndex = Value
                elif Name == 'HARDWARE_INSTANCE':
                    if FdfParser._Verify(Name, Value, 'UINT8'):
                        FmpData.HardwareInstance = Value
                elif Name == 'MONOTONIC_COUNT':
                    if FdfParser._Verify(Name, Value, 'UINT64'):
                        FmpData.MonotonicCount = Value
                        if FmpData.MonotonicCount.upper().startswith('0X'):
                            FmpData.MonotonicCount = int(FmpData.MonotonicCount, 16)
                        else:
                            FmpData.MonotonicCount = int(FmpData.MonotonicCount)
            if not self._GetNextToken():
                break
        else:
            self._UndoToken()

        if (FmpData.MonotonicCount and not FmpData.Certificate_Guid) or (not FmpData.MonotonicCount and FmpData.Certificate_Guid):
            EdkLogger.error("FdfParser", FORMAT_INVALID, "CERTIFICATE_GUID and MONOTONIC_COUNT must be work as a pair.")

        # Only the IMAGE_TYPE_ID is required item
        if FmpKeyList and 'IMAGE_TYPE_ID' in FmpKeyList:
            raise Warning("'IMAGE_TYPE_ID' in FMP payload section.", self.FileName, self.CurrentLineNumber)
        # get the Image file and Vendor code file
        self._GetFMPCapsuleData(FmpData)
        if not FmpData.ImageFile:
            raise Warning("Missing image file in FMP payload section.", self.FileName, self.CurrentLineNumber)
        # check whether more than one Vendor code file
        if len(FmpData.VendorCodeFile) > 1:
            raise Warning("Vendor code file max of 1 per FMP payload section.", self.FileName, self.CurrentLineNumber)
        self.Profile.FmpPayloadDict[FmpUiName] = FmpData
        return True

    ## _GetCapsule() method
    #
    #   Get capsule section contents and store its data into capsule list of self.Profile
    #
    #   @param  self        The object pointer
    #   @retval True        Successfully find a capsule
    #   @retval False       Not able to find a capsule
    #
    def _GetCapsule(self):
        if not self._GetNextToken():
            return False

        S = self._Token.upper()
        if S.startswith(TAB_SECTION_START) and not S.startswith("[CAPSULE."):
            self.SectionParser(S)
            self._UndoToken()
            return False

        self._UndoToken()
        if not self._IsToken("[CAPSULE.", True):
            FileLineTuple = GetRealFileLine(self.FileName, self.CurrentLineNumber)
            #print 'Parsing String: %s in File %s, At line: %d, Offset Within Line: %d' \
            #        % (self.Profile.FileLinesList[self.CurrentLineNumber - 1][self.CurrentOffsetWithinLine:], FileLineTuple[0], FileLineTuple[1], self.CurrentOffsetWithinLine)
            raise Warning.Expected("[Capsule.]", self.FileName, self.CurrentLineNumber)

        CapsuleObj = Capsule()

        CapsuleName = self._GetUiName()
        if not CapsuleName:
            raise Warning.Expected("capsule name", self.FileName, self.CurrentLineNumber)

        CapsuleObj.UiCapsuleName = CapsuleName.upper()

        if not self._IsToken(TAB_SECTION_END):
            raise Warning.ExpectedBracketClose(self.FileName, self.CurrentLineNumber)

        if self._IsKeyword("CREATE_FILE"):
            if not self._IsToken(TAB_EQUAL_SPLIT):
                raise Warning.ExpectedEquals(self.FileName, self.CurrentLineNumber)

            if not self._GetNextToken():
                raise Warning.Expected("file name", self.FileName, self.CurrentLineNumber)

            CapsuleObj.CreateFile = self._Token

        self._GetCapsuleStatements(CapsuleObj)
        self.Profile.CapsuleDict[CapsuleObj.UiCapsuleName] = CapsuleObj
        return True

    ## _GetCapsuleStatements() method
    #
    #   Get statements for capsule
    #
    #   @param  self        The object pointer
    #   @param  Obj         for whom statements are got
    #
    def _GetCapsuleStatements(self, Obj):
        self._GetCapsuleTokens(Obj)
        self._GetDefineStatements(Obj)
        self._GetSetStatements(Obj)
        self._GetCapsuleData(Obj)

    ## _GetCapsuleTokens() method
    #
    #   Get token statements for capsule
    #
    #   @param  self        The object pointer
    #   @param  Obj         for whom token statements are got
    #
    def _GetCapsuleTokens(self, Obj):
        if not self._GetNextToken():
            return False
        while self._Token in {"CAPSULE_GUID", "CAPSULE_HEADER_SIZE", "CAPSULE_FLAGS", "OEM_CAPSULE_FLAGS", "CAPSULE_HEADER_INIT_VERSION"}:
            Name = self._Token.strip()
            if not self._IsToken(TAB_EQUAL_SPLIT):
                raise Warning.ExpectedEquals(self.FileName, self.CurrentLineNumber)
            if not self._GetNextToken():
                raise Warning.Expected("value", self.FileName, self.CurrentLineNumber)
            if Name == 'CAPSULE_FLAGS':
                if not self._Token in {"PersistAcrossReset", "PopulateSystemTable", "InitiateReset"}:
                    raise Warning.Expected("PersistAcrossReset, PopulateSystemTable, or InitiateReset", self.FileName, self.CurrentLineNumber)
                Value = self._Token.strip()
                while self._IsToken(TAB_COMMA_SPLIT):
                    Value += TAB_COMMA_SPLIT
                    if not self._GetNextToken():
                        raise Warning.Expected("value", self.FileName, self.CurrentLineNumber)
                    if not self._Token in {"PersistAcrossReset", "PopulateSystemTable", "InitiateReset"}:
                        raise Warning.Expected("PersistAcrossReset, PopulateSystemTable, or InitiateReset", self.FileName, self.CurrentLineNumber)
                    Value += self._Token.strip()
            elif Name == 'OEM_CAPSULE_FLAGS':
                Value = self._Token.strip()
                if not Value.upper().startswith('0X'):
                    raise Warning.Expected("hex value starting with 0x", self.FileName, self.CurrentLineNumber)
                try:
                    Value = int(Value, 0)
                except ValueError:
                    raise Warning.Expected("hex string failed to convert to value", self.FileName, self.CurrentLineNumber)
                if not 0x0000 <= Value <= 0xFFFF:
                    raise Warning.Expected("hex value between 0x0000 and 0xFFFF", self.FileName, self.CurrentLineNumber)
                Value = self._Token.strip()
            else:
                Value = self._Token.strip()
            Obj.TokensDict[Name] = Value
            if not self._GetNextToken():
                return False
        self._UndoToken()

    ## _GetCapsuleData() method
    #
    #   Get capsule data for capsule
    #
    #   @param  self        The object pointer
    #   @param  Obj         for whom capsule data are got
    #
    def _GetCapsuleData(self, Obj):
        while True:
            IsInf = self._GetInfStatement(Obj, True)
            IsFile = self._GetFileStatement(Obj, True)
            IsFv = self._GetFvStatement(Obj)
            IsFd = self._GetFdStatement(Obj)
            IsAnyFile = self._GetAnyFileStatement(Obj)
            IsAfile = self._GetAfileStatement(Obj)
            IsFmp = self._GetFmpStatement(Obj)
            if not (IsInf or IsFile or IsFv or IsFd or IsAnyFile or IsAfile or IsFmp):
                break

    ## _GetFMPCapsuleData() method
    #
    #   Get capsule data for FMP capsule
    #
    #   @param  self        The object pointer
    #   @param  Obj         for whom capsule data are got
    #
    def _GetFMPCapsuleData(self, Obj):
        while True:
            IsFv = self._GetFvStatement(Obj, True)
            IsFd = self._GetFdStatement(Obj, True)
            IsAnyFile = self._GetAnyFileStatement(Obj, True)
            if not (IsFv or IsFd or IsAnyFile):
                break

    ## _GetFvStatement() method
    #
    #   Get FV for capsule
    #
    #   @param  self        The object pointer
    #   @param  CapsuleObj  for whom FV is got
    #   @retval True        Successfully find a FV statement
    #   @retval False       Not able to find a FV statement
    #
    def _GetFvStatement(self, CapsuleObj, FMPCapsule = False):
        if not self._IsKeyword(BINARY_FILE_TYPE_FV):
            return False

        if not self._IsToken(TAB_EQUAL_SPLIT):
            raise Warning.ExpectedEquals(self.FileName, self.CurrentLineNumber)

        if not self._GetNextToken():
            raise Warning.Expected("FV name", self.FileName, self.CurrentLineNumber)

        if self._Token.upper() not in self.Profile.FvDict:
            raise Warning("FV name does not exist", self.FileName, self.CurrentLineNumber)

        myCapsuleFv = CapsuleFv()
        myCapsuleFv.FvName = self._Token
        if FMPCapsule:
            if not CapsuleObj.ImageFile:
                CapsuleObj.ImageFile.append(myCapsuleFv)
            else:
                CapsuleObj.VendorCodeFile.append(myCapsuleFv)
        else:
            CapsuleObj.CapsuleDataList.append(myCapsuleFv)
        return True

    ## _GetFdStatement() method
    #
    #   Get FD for capsule
    #
    #   @param  self        The object pointer
    #   @param  CapsuleObj  for whom FD is got
    #   @retval True        Successfully find a FD statement
    #   @retval False       Not able to find a FD statement
    #
    def _GetFdStatement(self, CapsuleObj, FMPCapsule = False):
        if not self._IsKeyword("FD"):
            return False

        if not self._IsToken(TAB_EQUAL_SPLIT):
            raise Warning.ExpectedEquals(self.FileName, self.CurrentLineNumber)

        if not self._GetNextToken():
            raise Warning.Expected("FD name", self.FileName, self.CurrentLineNumber)

        if self._Token.upper() not in self.Profile.FdDict:
            raise Warning("FD name does not exist", self.FileName, self.CurrentLineNumber)

        myCapsuleFd = CapsuleFd()
        myCapsuleFd.FdName = self._Token
        if FMPCapsule:
            if not CapsuleObj.ImageFile:
                CapsuleObj.ImageFile.append(myCapsuleFd)
            else:
                CapsuleObj.VendorCodeFile.append(myCapsuleFd)
        else:
            CapsuleObj.CapsuleDataList.append(myCapsuleFd)
        return True

    def _GetFmpStatement(self, CapsuleObj):
        if not self._IsKeyword("FMP_PAYLOAD"):
            if not self._IsKeyword("FMP"):
                return False

            if not self._IsKeyword("PAYLOAD"):
                self._UndoToken()
                return False

        if not self._IsToken(TAB_EQUAL_SPLIT):
            raise Warning.ExpectedEquals(self.FileName, self.CurrentLineNumber)

        if not self._GetNextToken():
            raise Warning.Expected("payload name after FMP_PAYLOAD =", self.FileName, self.CurrentLineNumber)
        Payload = self._Token.upper()
        if Payload not in self.Profile.FmpPayloadDict:
            raise Warning("This FMP Payload does not exist: %s" % self._Token, self.FileName, self.CurrentLineNumber)
        CapsuleObj.FmpPayloadList.append(self.Profile.FmpPayloadDict[Payload])
        return True

    def _ParseRawFileStatement(self):
        if not self._IsKeyword("FILE"):
            return None

        if not self._IsKeyword("DATA"):
            self._UndoToken()
            return None

        if not self._IsToken(TAB_EQUAL_SPLIT):
            raise Warning.ExpectedEquals(self.FileName, self.CurrentLineNumber)

        if not self._GetNextToken():
            raise Warning.Expected("File name", self.FileName, self.CurrentLineNumber)

        AnyFileName = self._Token
        self._VerifyFile(AnyFileName)

        if not os.path.isabs(AnyFileName):
            AnyFileName = mws.join(GenFdsGlobalVariable.WorkSpaceDir, AnyFileName)

        return AnyFileName

    ## _GetAnyFileStatement() method
    #
    #   Get AnyFile for capsule
    #
    #   @param  self        The object pointer
    #   @param  CapsuleObj  for whom AnyFile is got
    #   @retval True        Successfully find a Anyfile statement
    #   @retval False       Not able to find a AnyFile statement
    #
    def _GetAnyFileStatement(self, CapsuleObj, FMPCapsule = False):
        AnyFileName = self._ParseRawFileStatement()
        if not AnyFileName:
            return False

        myCapsuleAnyFile = CapsuleAnyFile()
        myCapsuleAnyFile.FileName = AnyFileName
        if FMPCapsule:
            if not CapsuleObj.ImageFile:
                CapsuleObj.ImageFile.append(myCapsuleAnyFile)
            else:
                CapsuleObj.VendorCodeFile.append(myCapsuleAnyFile)
        else:
            CapsuleObj.CapsuleDataList.append(myCapsuleAnyFile)
        return True

    ## _GetAfileStatement() method
    #
    #   Get Afile for capsule
    #
    #   @param  self        The object pointer
    #   @param  CapsuleObj  for whom Afile is got
    #   @retval True        Successfully find a Afile statement
    #   @retval False       Not able to find a Afile statement
    #
    def _GetAfileStatement(self, CapsuleObj):
        if not self._IsKeyword("APPEND"):
            return False

        if not self._IsToken(TAB_EQUAL_SPLIT):
            raise Warning.ExpectedEquals(self.FileName, self.CurrentLineNumber)

        if not self._GetNextToken():
            raise Warning.Expected("Afile name", self.FileName, self.CurrentLineNumber)

        AfileName = self._Token
        AfileBaseName = os.path.basename(AfileName)

        if os.path.splitext(AfileBaseName)[1]  not in {".bin", ".BIN", ".Bin", ".dat", ".DAT", ".Dat", ".data", ".DATA", ".Data"}:
            raise Warning('invalid binary file type, should be one of "bin",BINARY_FILE_TYPE_BIN,"Bin","dat","DAT","Dat","data","DATA","Data"', \
                          self.FileName, self.CurrentLineNumber)

        if not os.path.isabs(AfileName):
            AfileName = GenFdsGlobalVariable.ReplaceWorkspaceMacro(AfileName)
            self._VerifyFile(AfileName)
        else:
            if not os.path.exists(AfileName):
                raise Warning('%s does not exist' % AfileName, self.FileName, self.CurrentLineNumber)
            else:
                pass

        myCapsuleAfile = CapsuleAfile()
        myCapsuleAfile.FileName = AfileName
        CapsuleObj.CapsuleDataList.append(myCapsuleAfile)
        return True

    ## _GetRule() method
    #
    #   Get Rule section contents and store its data into rule list of self.Profile
    #
    #   @param  self        The object pointer
    #   @retval True        Successfully find a Rule
    #   @retval False       Not able to find a Rule
    #
    def _GetRule(self):
        if not self._GetNextToken():
            return False

        S = self._Token.upper()
        if S.startswith(TAB_SECTION_START) and not S.startswith("[RULE."):
            self.SectionParser(S)
            self._UndoToken()
            return False
        self._UndoToken()
        if not self._IsToken("[Rule.", True):
            FileLineTuple = GetRealFileLine(self.FileName, self.CurrentLineNumber)
            #print 'Parsing String: %s in File %s, At line: %d, Offset Within Line: %d' \
            #        % (self.Profile.FileLinesList[self.CurrentLineNumber - 1][self.CurrentOffsetWithinLine:], FileLineTuple[0], FileLineTuple[1], self.CurrentOffsetWithinLine)
            raise Warning.Expected("[Rule.]", self.FileName, self.CurrentLineNumber)

        if not self._SkipToToken(TAB_SPLIT):
            raise Warning.Expected("'.'", self.FileName, self.CurrentLineNumber)

        Arch = self._SkippedChars.rstrip(TAB_SPLIT)
        if Arch.upper() not in ARCH_SET_FULL:
            raise Warning("Unknown Arch '%s'" % Arch, self.FileName, self.CurrentLineNumber)

        ModuleType = self._GetModuleType()

        TemplateName = ""
        if self._IsToken(TAB_SPLIT):
            if not self._GetNextWord():
                raise Warning.Expected("template name", self.FileName, self.CurrentLineNumber)
            TemplateName = self._Token

        if not self._IsToken(TAB_SECTION_END):
            raise Warning.ExpectedBracketClose(self.FileName, self.CurrentLineNumber)

        RuleObj = self._GetRuleFileStatements()
        RuleObj.Arch = Arch.upper()
        RuleObj.ModuleType = ModuleType
        RuleObj.TemplateName = TemplateName
        if TemplateName == '':
            self.Profile.RuleDict['RULE'             + \
                              TAB_SPLIT              + \
                              Arch.upper()           + \
                              TAB_SPLIT              + \
                              ModuleType.upper()     ] = RuleObj
        else:
            self.Profile.RuleDict['RULE'             + \
                              TAB_SPLIT              + \
                              Arch.upper()           + \
                              TAB_SPLIT              + \
                              ModuleType.upper()     + \
                              TAB_SPLIT              + \
                              TemplateName.upper() ] = RuleObj
        return True

    ## _GetModuleType() method
    #
    #   Return the module type
    #
    #   @param  self        The object pointer
    #   @retval string      module type
    #
    def _GetModuleType(self):
        if not self._GetNextWord():
            raise Warning.Expected("Module type", self.FileName, self.CurrentLineNumber)
        if self._Token.upper() not in {
                SUP_MODULE_SEC, SUP_MODULE_PEI_CORE, SUP_MODULE_PEIM,
                SUP_MODULE_DXE_CORE, SUP_MODULE_DXE_DRIVER,
                SUP_MODULE_DXE_SAL_DRIVER, SUP_MODULE_DXE_SMM_DRIVER,
                SUP_MODULE_DXE_RUNTIME_DRIVER, SUP_MODULE_UEFI_DRIVER,
                SUP_MODULE_UEFI_APPLICATION, SUP_MODULE_USER_DEFINED,
                TAB_DEFAULT, SUP_MODULE_BASE,
                EDK_COMPONENT_TYPE_SECURITY_CORE,
                EDK_COMPONENT_TYPE_COMBINED_PEIM_DRIVER,
                EDK_COMPONENT_TYPE_PIC_PEIM,
                EDK_COMPONENT_TYPE_RELOCATABLE_PEIM, "PE32_PEIM",
                EDK_COMPONENT_TYPE_BS_DRIVER, EDK_COMPONENT_TYPE_RT_DRIVER,
                EDK_COMPONENT_TYPE_SAL_RT_DRIVER,
                EDK_COMPONENT_TYPE_APPLICATION, "ACPITABLE",
                SUP_MODULE_SMM_CORE, SUP_MODULE_MM_STANDALONE,
                SUP_MODULE_MM_CORE_STANDALONE}:
            raise Warning("Unknown Module type '%s'" % self._Token, self.FileName, self.CurrentLineNumber)
        return self._Token

    ## _GetFileExtension() method
    #
    #   Return the file extension
    #
    #   @param  self        The object pointer
    #   @retval string      file name extension
    #
    def _GetFileExtension(self):
        if not self._IsToken(TAB_SPLIT):
            raise Warning.Expected("'.'", self.FileName, self.CurrentLineNumber)

        Ext = ""
        if self._GetNextToken():
            if FileExtensionPattern.match(self._Token):
                Ext = self._Token
                return TAB_SPLIT + Ext
            else:
                raise Warning("Unknown file extension '%s'" % self._Token, self.FileName, self.CurrentLineNumber)

        else:
            raise Warning.Expected("file extension", self.FileName, self.CurrentLineNumber)

    ## _GetRuleFileStatement() method
    #
    #   Get rule contents
    #
    #   @param  self        The object pointer
    #   @retval Rule        Rule object
    #
    def _GetRuleFileStatements(self):
        if not self._IsKeyword("FILE"):
            raise Warning.Expected("FILE", self.FileName, self.CurrentLineNumber)

        if not self._GetNextWord():
            raise Warning.Expected("FFS type", self.FileName, self.CurrentLineNumber)

        Type = self._Token.strip().upper()
        if Type not in {"RAW", "FREEFORM", SUP_MODULE_SEC, SUP_MODULE_PEI_CORE, SUP_MODULE_PEIM,
                        "PEI_DXE_COMBO", "DRIVER", SUP_MODULE_DXE_CORE, EDK_COMPONENT_TYPE_APPLICATION,
                        "FV_IMAGE", "SMM", SUP_MODULE_SMM_CORE, SUP_MODULE_MM_STANDALONE,
                        SUP_MODULE_MM_CORE_STANDALONE}:
            raise Warning("Unknown FV type '%s'" % self._Token, self.FileName, self.CurrentLineNumber)

        if not self._IsToken(TAB_EQUAL_SPLIT):
            raise Warning.ExpectedEquals(self.FileName, self.CurrentLineNumber)

        if not self._IsKeyword("$(NAMED_GUID)"):
            if not self._GetNextWord():
                raise Warning.Expected("$(NAMED_GUID)", self.FileName, self.CurrentLineNumber)
            if self._Token == 'PCD':
                if not self._IsToken("("):
                    raise Warning.Expected("'('", self.FileName, self.CurrentLineNumber)
                PcdPair = self._GetNextPcdSettings()
                if not self._IsToken(")"):
                    raise Warning.Expected("')'", self.FileName, self.CurrentLineNumber)
                self._Token = 'PCD('+PcdPair[1]+TAB_SPLIT+PcdPair[0]+')'

        NameGuid = self._Token

        KeepReloc = None
        if self._IsKeyword('RELOCS_STRIPPED') or self._IsKeyword('RELOCS_RETAINED'):
            if self._FileCouldHaveRelocFlag(Type):
                if self._Token == 'RELOCS_STRIPPED':
                    KeepReloc = False
                else:
                    KeepReloc = True
            else:
                raise Warning("File type %s could not have reloc strip flag%d" % (Type, self.CurrentLineNumber), self.FileName, self.CurrentLineNumber)

        KeyStringList = []
        if self._GetNextToken():
            if TokenFindPattern.match(self._Token):
                KeyStringList.append(self._Token)
                if self._IsToken(TAB_COMMA_SPLIT):
                    while self._GetNextToken():
                        if not TokenFindPattern.match(self._Token):
                            raise Warning.Expected("KeyString \"Target_Tag_Arch\"", self.FileName, self.CurrentLineNumber)
                        KeyStringList.append(self._Token)

                        if not self._IsToken(TAB_COMMA_SPLIT):
                            break

            else:
                self._UndoToken()


        Fixed = False
        if self._IsKeyword("Fixed", True):
            Fixed = True

        CheckSum = False
        if self._IsKeyword("CheckSum", True):
            CheckSum = True

        AlignValue = ""
        if self._GetAlignment():
            if self._Token not in ALIGNMENTS:
                raise Warning("Incorrect alignment '%s'" % self._Token, self.FileName, self.CurrentLineNumber)
            #For FFS, Auto is default option same to ""
            if not self._Token == "Auto":
                AlignValue = self._Token

        if self._IsToken("{"):
            # Complex file rule expected
            NewRule = RuleComplexFile()
            NewRule.FvFileType = Type
            NewRule.NameGuid = NameGuid
            NewRule.Alignment = AlignValue
            NewRule.CheckSum = CheckSum
            NewRule.Fixed = Fixed
            NewRule.KeyStringList = KeyStringList
            if KeepReloc is not None:
                NewRule.KeepReloc = KeepReloc

            while True:
                IsEncapsulate = self._GetRuleEncapsulationSection(NewRule)
                IsLeaf = self._GetEfiSection(NewRule)
                if not IsEncapsulate and not IsLeaf:
                    break

            if not self._IsToken(T_CHAR_BRACE_R):
                raise Warning.ExpectedCurlyClose(self.FileName, self.CurrentLineNumber)

            return NewRule

        else:
            # Simple file rule expected
            if not self._GetNextWord():
                raise Warning.Expected("leaf section type", self.FileName, self.CurrentLineNumber)

            SectionName = self._Token

            if SectionName not in {
                    "COMPAT16", BINARY_FILE_TYPE_PE32,
                    BINARY_FILE_TYPE_PIC, BINARY_FILE_TYPE_TE, "FV_IMAGE",
                    "RAW",BINARY_FILE_TYPE_DXE_DEPEX, BINARY_FILE_TYPE_UI,
                    BINARY_FILE_TYPE_PEI_DEPEX, "VERSION", "SUBTYPE_GUID",
                    BINARY_FILE_TYPE_SMM_DEPEX}:
                raise Warning("Unknown leaf section name '%s'" % SectionName, self.FileName, self.CurrentLineNumber)


            if self._IsKeyword("Fixed", True):
                Fixed = True

            if self._IsKeyword("CheckSum", True):
                CheckSum = True

            SectAlignment = ""
            if self._GetAlignment():
                if self._Token not in ALIGNMENTS:
                    raise Warning("Incorrect alignment '%s'" % self._Token, self.FileName, self.CurrentLineNumber)
                if self._Token == 'Auto' and (not SectionName == BINARY_FILE_TYPE_PE32) and (not SectionName == BINARY_FILE_TYPE_TE):
                    raise Warning("Auto alignment can only be used in PE32 or TE section ", self.FileName, self.CurrentLineNumber)
                SectAlignment = self._Token

            Ext = None
            if self._IsToken(TAB_VALUE_SPLIT):
                Ext = self._GetFileExtension()
            elif not self._GetNextToken():
                raise Warning.Expected("File name", self.FileName, self.CurrentLineNumber)

            NewRule = RuleSimpleFile()
            NewRule.SectionType = SectionName
            NewRule.FvFileType = Type
            NewRule.NameGuid = NameGuid
            NewRule.Alignment = AlignValue
            NewRule.SectAlignment = SectAlignment
            NewRule.CheckSum = CheckSum
            NewRule.Fixed = Fixed
            NewRule.KeyStringList = KeyStringList
            if KeepReloc is not None:
                NewRule.KeepReloc = KeepReloc
            NewRule.FileExtension = Ext
            NewRule.FileName = self._Token
            return NewRule

    ## _GetEfiSection() method
    #
    #   Get section list for Rule
    #
    #   @param  self        The object pointer
    #   @param  Obj         for whom section is got
    #   @retval True        Successfully find section statement
    #   @retval False       Not able to find section statement
    #
    def _GetEfiSection(self, Obj):
        OldPos = self.GetFileBufferPos()
        if not self._GetNextWord():
            return False
        SectionName = self._Token

        if SectionName not in {
                    "COMPAT16", BINARY_FILE_TYPE_PE32,
                    BINARY_FILE_TYPE_PIC, BINARY_FILE_TYPE_TE, "FV_IMAGE",
                    "RAW",BINARY_FILE_TYPE_DXE_DEPEX, BINARY_FILE_TYPE_UI,
                    BINARY_FILE_TYPE_PEI_DEPEX, "VERSION", "SUBTYPE_GUID",
                    BINARY_FILE_TYPE_SMM_DEPEX, BINARY_FILE_TYPE_GUID}:
            self._UndoToken()
            return False

        if SectionName == "FV_IMAGE":
            FvImageSectionObj = FvImageSection()
            if self._IsKeyword("FV_IMAGE"):
                pass
            if self._IsToken("{"):
                FvObj = FV()
                self._GetDefineStatements(FvObj)
                self._GetBlockStatement(FvObj)
                self._GetSetStatements(FvObj)
                self._GetFvAlignment(FvObj)
                self._GetFvAttributes(FvObj)
                self._GetAprioriSection(FvObj)
                self._GetAprioriSection(FvObj)

                while True:
                    IsInf = self._GetInfStatement(FvObj)
                    IsFile = self._GetFileStatement(FvObj)
                    if not IsInf and not IsFile:
                        break

                if not self._IsToken(T_CHAR_BRACE_R):
                    raise Warning.ExpectedCurlyClose(self.FileName, self.CurrentLineNumber)
                FvImageSectionObj.Fv = FvObj
                FvImageSectionObj.FvName = None

            else:
                if not self._IsKeyword(BINARY_FILE_TYPE_FV):
                    raise Warning.Expected("'FV'", self.FileName, self.CurrentLineNumber)
                FvImageSectionObj.FvFileType = self._Token

                if self._GetAlignment():
                    if self._Token not in ALIGNMENT_NOAUTO:
                        raise Warning("Incorrect alignment '%s'" % self._Token, self.FileName, self.CurrentLineNumber)
                    FvImageSectionObj.Alignment = self._Token

                if self._IsToken(TAB_VALUE_SPLIT):
                    FvImageSectionObj.FvFileExtension = self._GetFileExtension()
                elif self._GetNextToken():
                    if self._Token not in {
                            T_CHAR_BRACE_R, "COMPAT16", BINARY_FILE_TYPE_PE32,
                            BINARY_FILE_TYPE_PIC, BINARY_FILE_TYPE_TE,
                            "FV_IMAGE", "RAW", BINARY_FILE_TYPE_DXE_DEPEX,
                            BINARY_FILE_TYPE_UI, "VERSION",
                            BINARY_FILE_TYPE_PEI_DEPEX, BINARY_FILE_TYPE_GUID,
                            BINARY_FILE_TYPE_SMM_DEPEX}:
                        FvImageSectionObj.FvFileName = self._Token
                    else:
                        self._UndoToken()
                else:
                    raise Warning.Expected("FV file name", self.FileName, self.CurrentLineNumber)

            Obj.SectionList.append(FvImageSectionObj)
            return True

        EfiSectionObj = EfiSection()
        EfiSectionObj.SectionType = SectionName

        if not self._GetNextToken():
            raise Warning.Expected("file type", self.FileName, self.CurrentLineNumber)

        if self._Token == "STRING":
            if not self._RuleSectionCouldHaveString(EfiSectionObj.SectionType):
                raise Warning("%s section could NOT have string data%d" % (EfiSectionObj.SectionType, self.CurrentLineNumber), self.FileName, self.CurrentLineNumber)

            if not self._IsToken(TAB_EQUAL_SPLIT):
                raise Warning.ExpectedEquals(self.FileName, self.CurrentLineNumber)

            if not self._GetNextToken():
                raise Warning.Expected("Quoted String", self.FileName, self.CurrentLineNumber)

            if self._GetStringData():
                EfiSectionObj.StringData = self._Token

            if self._IsKeyword("BUILD_NUM"):
                if not self._RuleSectionCouldHaveBuildNum(EfiSectionObj.SectionType):
                    raise Warning("%s section could NOT have BUILD_NUM%d" % (EfiSectionObj.SectionType, self.CurrentLineNumber), self.FileName, self.CurrentLineNumber)

                if not self._IsToken(TAB_EQUAL_SPLIT):
                    raise Warning.ExpectedEquals(self.FileName, self.CurrentLineNumber)
                if not self._GetNextToken():
                    raise Warning.Expected("Build number", self.FileName, self.CurrentLineNumber)
                EfiSectionObj.BuildNum = self._Token

        else:
            EfiSectionObj.FileType = self._Token
            self._CheckRuleSectionFileType(EfiSectionObj.SectionType, EfiSectionObj.FileType)

        if self._IsKeyword("Optional"):
            if not self._RuleSectionCouldBeOptional(EfiSectionObj.SectionType):
                raise Warning("%s section could NOT be optional%d" % (EfiSectionObj.SectionType, self.CurrentLineNumber), self.FileName, self.CurrentLineNumber)
            EfiSectionObj.Optional = True

            if self._IsKeyword("BUILD_NUM"):
                if not self._RuleSectionCouldHaveBuildNum(EfiSectionObj.SectionType):
                    raise Warning("%s section could NOT have BUILD_NUM%d" % (EfiSectionObj.SectionType, self.CurrentLineNumber), self.FileName, self.CurrentLineNumber)

                if not self._IsToken(TAB_EQUAL_SPLIT):
                    raise Warning.ExpectedEquals(self.FileName, self.CurrentLineNumber)
                if not self._GetNextToken():
                    raise Warning.Expected("Build number", self.FileName, self.CurrentLineNumber)
                EfiSectionObj.BuildNum = self._Token

        if self._GetAlignment():
            if self._Token not in ALIGNMENTS:
                raise Warning("Incorrect alignment '%s'" % self._Token, self.FileName, self.CurrentLineNumber)
            if self._Token == 'Auto' and (not SectionName == BINARY_FILE_TYPE_PE32) and (not SectionName == BINARY_FILE_TYPE_TE):
                raise Warning("Auto alignment can only be used in PE32 or TE section ", self.FileName, self.CurrentLineNumber)
            EfiSectionObj.Alignment = self._Token

        if self._IsKeyword('RELOCS_STRIPPED') or self._IsKeyword('RELOCS_RETAINED'):
            if self._SectionCouldHaveRelocFlag(EfiSectionObj.SectionType):
                if self._Token == 'RELOCS_STRIPPED':
                    EfiSectionObj.KeepReloc = False
                else:
                    EfiSectionObj.KeepReloc = True
                if Obj.KeepReloc is not None and Obj.KeepReloc != EfiSectionObj.KeepReloc:
                    raise Warning("Section type %s has reloc strip flag conflict with Rule" % EfiSectionObj.SectionType, self.FileName, self.CurrentLineNumber)
            else:
                raise Warning("Section type %s could not have reloc strip flag" % EfiSectionObj.SectionType, self.FileName, self.CurrentLineNumber)


        if self._IsToken(TAB_VALUE_SPLIT):
            EfiSectionObj.FileExtension = self._GetFileExtension()
        elif self._GetNextToken():
            if self._Token not in {
                    T_CHAR_BRACE_R, "COMPAT16", BINARY_FILE_TYPE_PE32,
                    BINARY_FILE_TYPE_PIC, BINARY_FILE_TYPE_TE,
                    "FV_IMAGE", "RAW", BINARY_FILE_TYPE_DXE_DEPEX,
                    BINARY_FILE_TYPE_UI, "VERSION",
                    BINARY_FILE_TYPE_PEI_DEPEX, BINARY_FILE_TYPE_GUID,
                    BINARY_FILE_TYPE_SMM_DEPEX}:

                if self._Token.startswith('PCD'):
                    self._UndoToken()
                    self._GetNextWord()

                    if self._Token == 'PCD':
                        if not self._IsToken("("):
                            raise Warning.Expected("'('", self.FileName, self.CurrentLineNumber)
                        PcdPair = self._GetNextPcdSettings()
                        if not self._IsToken(")"):
                            raise Warning.Expected("')'", self.FileName, self.CurrentLineNumber)
                        self._Token = 'PCD('+PcdPair[1]+TAB_SPLIT+PcdPair[0]+')'

                EfiSectionObj.FileName = self._Token

            else:
                self._UndoToken()
        else:
            raise Warning.Expected("section file name", self.FileName, self.CurrentLineNumber)

        Obj.SectionList.append(EfiSectionObj)
        return True

    ## _RuleSectionCouldBeOptional() method
    #
    #   Get whether a section could be optional
    #
    #   @param  SectionType The section type to check
    #   @retval True        section could be optional
    #   @retval False       section never optional
    #
    @staticmethod
    def _RuleSectionCouldBeOptional(SectionType):
        if SectionType in {BINARY_FILE_TYPE_DXE_DEPEX, BINARY_FILE_TYPE_UI, "VERSION", BINARY_FILE_TYPE_PEI_DEPEX, "RAW", BINARY_FILE_TYPE_SMM_DEPEX}:
            return True
        else:
            return False

    ## _RuleSectionCouldHaveBuildNum() method
    #
    #   Get whether a section could have build number information
    #
    #   @param  SectionType The section type to check
    #   @retval True        section could have build number information
    #   @retval False       section never have build number information
    #
    @staticmethod
    def _RuleSectionCouldHaveBuildNum(SectionType):
        if SectionType == "VERSION":
            return True
        else:
            return False

    ## _RuleSectionCouldHaveString() method
    #
    #   Get whether a section could have string
    #
    #   @param  SectionType The section type to check
    #   @retval True        section could have string
    #   @retval False       section never have string
    #
    @staticmethod
    def _RuleSectionCouldHaveString(SectionType):
        if SectionType in {BINARY_FILE_TYPE_UI, "VERSION"}:
            return True
        else:
            return False

    ## _CheckRuleSectionFileType() method
    #
    #   Get whether a section matches a file type
    #
    #   @param  self        The object pointer
    #   @param  SectionType The section type to check
    #   @param  FileType    The file type to check
    #
    def _CheckRuleSectionFileType(self, SectionType, FileType):
        WarningString = "Incorrect section file type '%s'"
        if SectionType == "COMPAT16":
            if FileType not in {"COMPAT16", "SEC_COMPAT16"}:
                raise Warning(WarningString % FileType, self.FileName, self.CurrentLineNumber)
        elif SectionType == BINARY_FILE_TYPE_PE32:
            if FileType not in {BINARY_FILE_TYPE_PE32, "SEC_PE32"}:
                raise Warning(WarningString % FileType, self.FileName, self.CurrentLineNumber)
        elif SectionType == BINARY_FILE_TYPE_PIC:
            if FileType not in {BINARY_FILE_TYPE_PIC, BINARY_FILE_TYPE_PIC}:
                raise Warning(WarningString % FileType, self.FileName, self.CurrentLineNumber)
        elif SectionType == BINARY_FILE_TYPE_TE:
            if FileType not in {BINARY_FILE_TYPE_TE, "SEC_TE"}:
                raise Warning(WarningString % FileType, self.FileName, self.CurrentLineNumber)
        elif SectionType == "RAW":
            if FileType not in {BINARY_FILE_TYPE_BIN, "SEC_BIN", "RAW", "ASL", "ACPI"}:
                raise Warning(WarningString % FileType, self.FileName, self.CurrentLineNumber)
        elif SectionType == BINARY_FILE_TYPE_DXE_DEPEX or SectionType == BINARY_FILE_TYPE_SMM_DEPEX:
            if FileType not in {BINARY_FILE_TYPE_DXE_DEPEX, "SEC_DXE_DEPEX", BINARY_FILE_TYPE_SMM_DEPEX}:
                raise Warning(WarningString % FileType, self.FileName, self.CurrentLineNumber)
        elif SectionType == BINARY_FILE_TYPE_UI:
            if FileType not in {BINARY_FILE_TYPE_UI, "SEC_UI"}:
                raise Warning(WarningString % FileType, self.FileName, self.CurrentLineNumber)
        elif SectionType == "VERSION":
            if FileType not in {"VERSION", "SEC_VERSION"}:
                raise Warning(WarningString % FileType, self.FileName, self.CurrentLineNumber)
        elif SectionType == BINARY_FILE_TYPE_PEI_DEPEX:
            if FileType not in {BINARY_FILE_TYPE_PEI_DEPEX, "SEC_PEI_DEPEX"}:
                raise Warning(WarningString % FileType, self.FileName, self.CurrentLineNumber)
        elif SectionType == BINARY_FILE_TYPE_GUID:
            if FileType not in {BINARY_FILE_TYPE_PE32, "SEC_GUID"}:
                raise Warning(WarningString % FileType, self.FileName, self.CurrentLineNumber)

    ## _GetRuleEncapsulationSection() method
    #
    #   Get encapsulation section for Rule
    #
    #   @param  self        The object pointer
    #   @param  theRule     for whom section is got
    #   @retval True        Successfully find section statement
    #   @retval False       Not able to find section statement
    #
    def _GetRuleEncapsulationSection(self, theRule):
        if self._IsKeyword("COMPRESS"):
            Type = "PI_STD"
            if self._IsKeyword("PI_STD") or self._IsKeyword("PI_NONE"):
                Type = self._Token

            if not self._IsToken("{"):
                raise Warning.ExpectedCurlyOpen(self.FileName, self.CurrentLineNumber)

            CompressSectionObj = CompressSection()

            CompressSectionObj.CompType = Type
            # Recursive sections...
            while True:
                IsEncapsulate = self._GetRuleEncapsulationSection(CompressSectionObj)
                IsLeaf = self._GetEfiSection(CompressSectionObj)
                if not IsEncapsulate and not IsLeaf:
                    break

            if not self._IsToken(T_CHAR_BRACE_R):
                raise Warning.ExpectedCurlyClose(self.FileName, self.CurrentLineNumber)
            theRule.SectionList.append(CompressSectionObj)

            return True

        elif self._IsKeyword("GUIDED"):
            GuidValue = None
            if self._GetNextGuid():
                GuidValue = self._Token

            if self._IsKeyword("$(NAMED_GUID)"):
                GuidValue = self._Token

            AttribDict = self._GetGuidAttrib()

            if not self._IsToken("{"):
                raise Warning.ExpectedCurlyOpen(self.FileName, self.CurrentLineNumber)
            GuidSectionObj = GuidSection()
            GuidSectionObj.NameGuid = GuidValue
            GuidSectionObj.SectionType = "GUIDED"
            GuidSectionObj.ProcessRequired = AttribDict["PROCESSING_REQUIRED"]
            GuidSectionObj.AuthStatusValid = AttribDict["AUTH_STATUS_VALID"]
            GuidSectionObj.ExtraHeaderSize = AttribDict["EXTRA_HEADER_SIZE"]

            # Efi sections...
            while True:
                IsEncapsulate = self._GetRuleEncapsulationSection(GuidSectionObj)
                IsLeaf = self._GetEfiSection(GuidSectionObj)
                if not IsEncapsulate and not IsLeaf:
                    break

            if not self._IsToken(T_CHAR_BRACE_R):
                raise Warning.ExpectedCurlyClose(self.FileName, self.CurrentLineNumber)
            theRule.SectionList.append(GuidSectionObj)

            return True

        return False

    ## _GetOptionRom() method
    #
    #   Get OptionROM section contents and store its data into OptionROM list of self.Profile
    #
    #   @param  self        The object pointer
    #   @retval True        Successfully find a OptionROM
    #   @retval False       Not able to find a OptionROM
    #
    def _GetOptionRom(self):
        if not self._GetNextToken():
            return False

        S = self._Token.upper()
        if S.startswith(TAB_SECTION_START) and not S.startswith("[OPTIONROM."):
            self.SectionParser(S)
            self._UndoToken()
            return False

        self._UndoToken()
        if not self._IsToken("[OptionRom.", True):
            raise Warning("Unknown Keyword '%s'" % self._Token, self.FileName, self.CurrentLineNumber)

        OptRomName = self._GetUiName()

        if not self._IsToken(TAB_SECTION_END):
            raise Warning.ExpectedBracketClose(self.FileName, self.CurrentLineNumber)

        OptRomObj = OPTIONROM(OptRomName)
        self.Profile.OptRomDict[OptRomName] = OptRomObj

        while True:
            isInf = self._GetOptRomInfStatement(OptRomObj)
            isFile = self._GetOptRomFileStatement(OptRomObj)
            if not isInf and not isFile:
                break

        return True

    ## _GetOptRomInfStatement() method
    #
    #   Get INF statements
    #
    #   @param  self        The object pointer
    #   @param  Obj         for whom inf statement is got
    #   @retval True        Successfully find inf statement
    #   @retval False       Not able to find inf statement
    #
    def _GetOptRomInfStatement(self, Obj):
        if not self._IsKeyword("INF"):
            return False

        ffsInf = OptRomInfStatement()
        self._GetInfOptions(ffsInf)

        if not self._GetNextToken():
            raise Warning.Expected("INF file path", self.FileName, self.CurrentLineNumber)
        ffsInf.InfFileName = self._Token
        if ffsInf.InfFileName.replace(TAB_WORKSPACE, '').find('$') == -1:
            #check for file path
            ErrorCode, ErrorInfo = PathClass(NormPath(ffsInf.InfFileName), GenFdsGlobalVariable.WorkSpaceDir).Validate()
            if ErrorCode != 0:
                EdkLogger.error("GenFds", ErrorCode, ExtraData=ErrorInfo)

        NewFileName = ffsInf.InfFileName
        if ffsInf.OverrideGuid:
            NewFileName = ProcessDuplicatedInf(PathClass(ffsInf.InfFileName,GenFdsGlobalVariable.WorkSpaceDir), ffsInf.OverrideGuid, GenFdsGlobalVariable.WorkSpaceDir).Path

        if not NewFileName in self.Profile.InfList:
            self.Profile.InfList.append(NewFileName)
            FileLineTuple = GetRealFileLine(self.FileName, self.CurrentLineNumber)
            self.Profile.InfFileLineList.append(FileLineTuple)
            if ffsInf.UseArch:
                if ffsInf.UseArch not in self.Profile.InfDict:
                    self.Profile.InfDict[ffsInf.UseArch] = [ffsInf.InfFileName]
                else:
                    self.Profile.InfDict[ffsInf.UseArch].append(ffsInf.InfFileName)
            else:
                self.Profile.InfDict['ArchTBD'].append(ffsInf.InfFileName)


        self._GetOptRomOverrides (ffsInf)

        Obj.FfsList.append(ffsInf)
        return True

    ## _GetOptRomOverrides() method
    #
    #   Get overrides for OptROM INF & FILE
    #
    #   @param  self        The object pointer
    #   @param  FfsInfObj   for whom overrides is got
    #
    def _GetOptRomOverrides(self, Obj):
        if self._IsToken('{'):
            Overrides = OverrideAttribs()
            while True:
                if self._IsKeyword("PCI_VENDOR_ID"):
                    if not self._IsToken(TAB_EQUAL_SPLIT):
                        raise Warning.ExpectedEquals(self.FileName, self.CurrentLineNumber)
                    if not self._GetNextHexNumber():
                        raise Warning.Expected("Hex vendor id", self.FileName, self.CurrentLineNumber)
                    Overrides.PciVendorId = self._Token
                    continue

                if self._IsKeyword("PCI_CLASS_CODE"):
                    if not self._IsToken(TAB_EQUAL_SPLIT):
                        raise Warning.ExpectedEquals(self.FileName, self.CurrentLineNumber)
                    if not self._GetNextHexNumber():
                        raise Warning.Expected("Hex class code", self.FileName, self.CurrentLineNumber)
                    Overrides.PciClassCode = self._Token
                    continue

                if self._IsKeyword("PCI_DEVICE_ID"):
                    if not self._IsToken(TAB_EQUAL_SPLIT):
                        raise Warning.ExpectedEquals(self.FileName, self.CurrentLineNumber)
                    # Get a list of PCI IDs
                    Overrides.PciDeviceId = ""
                    while (self._GetNextHexNumber()):
                        Overrides.PciDeviceId = "{} {}".format(Overrides.PciDeviceId, self._Token)
                    if not Overrides.PciDeviceId:
                        raise Warning.Expected("one or more Hex device ids", self.FileName, self.CurrentLineNumber)
                    continue

                if self._IsKeyword("PCI_REVISION"):
                    if not self._IsToken(TAB_EQUAL_SPLIT):
                        raise Warning.ExpectedEquals(self.FileName, self.CurrentLineNumber)
                    if not self._GetNextHexNumber():
                        raise Warning.Expected("Hex revision", self.FileName, self.CurrentLineNumber)
                    Overrides.PciRevision = self._Token
                    continue

                if self._IsKeyword("PCI_COMPRESS"):
                    if not self._IsToken(TAB_EQUAL_SPLIT):
                        raise Warning.ExpectedEquals(self.FileName, self.CurrentLineNumber)
                    if not self._GetNextToken():
                        raise Warning.Expected("TRUE/FALSE for compress", self.FileName, self.CurrentLineNumber)
                    Overrides.NeedCompress = self._Token.upper() == 'TRUE'
                    continue

                if self._IsToken(T_CHAR_BRACE_R):
                    break
                else:
                    EdkLogger.error("FdfParser", FORMAT_INVALID, File=self.FileName, Line=self.CurrentLineNumber)

            Obj.OverrideAttribs = Overrides

    ## _GetOptRomFileStatement() method
    #
    #   Get FILE statements
    #
    #   @param  self        The object pointer
    #   @param  Obj         for whom FILE statement is got
    #   @retval True        Successfully find FILE statement
    #   @retval False       Not able to find FILE statement
    #
    def _GetOptRomFileStatement(self, Obj):
        if not self._IsKeyword("FILE"):
            return False

        FfsFileObj = OptRomFileStatement()

        if not self._IsKeyword("EFI") and not self._IsKeyword(BINARY_FILE_TYPE_BIN):
            raise Warning.Expected("Binary type (EFI/BIN)", self.FileName, self.CurrentLineNumber)
        FfsFileObj.FileType = self._Token

        if not self._GetNextToken():
            raise Warning.Expected("File path", self.FileName, self.CurrentLineNumber)
        FfsFileObj.FileName = self._Token
        if FfsFileObj.FileName.replace(TAB_WORKSPACE, '').find('$') == -1:
            #check for file path
            ErrorCode, ErrorInfo = PathClass(NormPath(FfsFileObj.FileName), GenFdsGlobalVariable.WorkSpaceDir).Validate()
            if ErrorCode != 0:
                EdkLogger.error("GenFds", ErrorCode, ExtraData=ErrorInfo)

        if FfsFileObj.FileType == 'EFI':
            self._GetOptRomOverrides(FfsFileObj)

        Obj.FfsList.append(FfsFileObj)

        return True

    ## _GetCapInFd() method
    #
    #   Get Cap list contained in FD
    #
    #   @param  self        The object pointer
    #   @param  FdName      FD name
    #   @retval CapList     List of Capsule in FD
    #
    def _GetCapInFd (self, FdName):
        CapList = []
        if FdName.upper() in self.Profile.FdDict:
            FdObj = self.Profile.FdDict[FdName.upper()]
            for elementRegion in FdObj.RegionList:
                if elementRegion.RegionType == 'CAPSULE':
                    for elementRegionData in elementRegion.RegionDataList:
                        if elementRegionData.endswith(".cap"):
                            continue
                        if elementRegionData is not None and elementRegionData.upper() not in CapList:
                            CapList.append(elementRegionData.upper())
        return CapList

    ## _GetReferencedFdCapTuple() method
    #
    #   Get FV and FD list referenced by a capsule image
    #
    #   @param  self        The object pointer
    #   @param  CapObj      Capsule section to be searched
    #   @param  RefFdList   referenced FD by section
    #   @param  RefFvList   referenced FV by section
    #
    def _GetReferencedFdCapTuple(self, CapObj, RefFdList = [], RefFvList = []):
        for CapsuleDataObj in CapObj.CapsuleDataList:
            if hasattr(CapsuleDataObj, 'FvName') and CapsuleDataObj.FvName is not None and CapsuleDataObj.FvName.upper() not in RefFvList:
                RefFvList.append (CapsuleDataObj.FvName.upper())
            elif hasattr(CapsuleDataObj, 'FdName') and CapsuleDataObj.FdName is not None and CapsuleDataObj.FdName.upper() not in RefFdList:
                RefFdList.append (CapsuleDataObj.FdName.upper())
            elif CapsuleDataObj.Ffs is not None:
                if isinstance(CapsuleDataObj.Ffs, FileStatement):
                    if CapsuleDataObj.Ffs.FvName is not None and CapsuleDataObj.Ffs.FvName.upper() not in RefFvList:
                        RefFvList.append(CapsuleDataObj.Ffs.FvName.upper())
                    elif CapsuleDataObj.Ffs.FdName is not None and CapsuleDataObj.Ffs.FdName.upper() not in RefFdList:
                        RefFdList.append(CapsuleDataObj.Ffs.FdName.upper())
                    else:
                        self._GetReferencedFdFvTupleFromSection(CapsuleDataObj.Ffs, RefFdList, RefFvList)

    ## _GetFvInFd() method
    #
    #   Get FV list contained in FD
    #
    #   @param  self        The object pointer
    #   @param  FdName      FD name
    #   @retval FvList      list of FV in FD
    #
    def _GetFvInFd (self, FdName):
        FvList = []
        if FdName.upper() in self.Profile.FdDict:
            FdObj = self.Profile.FdDict[FdName.upper()]
            for elementRegion in FdObj.RegionList:
                if elementRegion.RegionType == BINARY_FILE_TYPE_FV:
                    for elementRegionData in elementRegion.RegionDataList:
                        if elementRegionData.endswith(".fv"):
                            continue
                        if elementRegionData is not None and elementRegionData.upper() not in FvList:
                            FvList.append(elementRegionData.upper())
        return FvList

    ## _GetReferencedFdFvTuple() method
    #
    #   Get FD and FV list referenced by a FFS file
    #
    #   @param  self        The object pointer
    #   @param  FfsFile     contains sections to be searched
    #   @param  RefFdList   referenced FD by section
    #   @param  RefFvList   referenced FV by section
    #
    def _GetReferencedFdFvTuple(self, FvObj, RefFdList = [], RefFvList = []):
        for FfsObj in FvObj.FfsList:
            if isinstance(FfsObj, FileStatement):
                if FfsObj.FvName is not None and FfsObj.FvName.upper() not in RefFvList:
                    RefFvList.append(FfsObj.FvName.upper())
                elif FfsObj.FdName is not None and FfsObj.FdName.upper() not in RefFdList:
                    RefFdList.append(FfsObj.FdName.upper())
                else:
                    self._GetReferencedFdFvTupleFromSection(FfsObj, RefFdList, RefFvList)

    ## _GetReferencedFdFvTupleFromSection() method
    #
    #   Get FD and FV list referenced by a FFS section
    #
    #   @param  self        The object pointer
    #   @param  FfsFile     contains sections to be searched
    #   @param  FdList      referenced FD by section
    #   @param  FvList      referenced FV by section
    #
    def _GetReferencedFdFvTupleFromSection(self, FfsFile, FdList = [], FvList = []):
        SectionStack = list(FfsFile.SectionList)
        while SectionStack != []:
            SectionObj = SectionStack.pop()
            if isinstance(SectionObj, FvImageSection):
                if SectionObj.FvName is not None and SectionObj.FvName.upper() not in FvList:
                    FvList.append(SectionObj.FvName.upper())
                if SectionObj.Fv is not None and SectionObj.Fv.UiFvName is not None and SectionObj.Fv.UiFvName.upper() not in FvList:
                    FvList.append(SectionObj.Fv.UiFvName.upper())
                    self._GetReferencedFdFvTuple(SectionObj.Fv, FdList, FvList)

            if isinstance(SectionObj, CompressSection) or isinstance(SectionObj, GuidSection):
                SectionStack.extend(SectionObj.SectionList)

    ## CycleReferenceCheck() method
    #
    #   Check whether cycle reference exists in FDF
    #
    #   @param  self        The object pointer
    #   @retval True        cycle reference exists
    #   @retval False       Not exists cycle reference
    #
    def CycleReferenceCheck(self):
        #
        # Check the cycle between FV and FD image
        #
        MaxLength = len (self.Profile.FvDict)
        for FvName in self.Profile.FvDict:
            LogStr = "\nCycle Reference Checking for FV: %s\n" % FvName
            RefFvStack = set(FvName)
            FdAnalyzedList = set()

            Index = 0
            while RefFvStack and Index < MaxLength:
                Index = Index + 1
                FvNameFromStack = RefFvStack.pop()
                if FvNameFromStack.upper() in self.Profile.FvDict:
                    FvObj = self.Profile.FvDict[FvNameFromStack.upper()]
                else:
                    continue

                RefFdList = []
                RefFvList = []
                self._GetReferencedFdFvTuple(FvObj, RefFdList, RefFvList)

                for RefFdName in RefFdList:
                    if RefFdName in FdAnalyzedList:
                        continue

                    LogStr += "FV %s contains FD %s\n" % (FvNameFromStack, RefFdName)
                    FvInFdList = self._GetFvInFd(RefFdName)
                    if FvInFdList != []:
                        for FvNameInFd in FvInFdList:
                            LogStr += "FD %s contains FV %s\n" % (RefFdName, FvNameInFd)
                            if FvNameInFd not in RefFvStack:
                                RefFvStack.add(FvNameInFd)

                            if FvName in RefFvStack or FvNameFromStack in RefFvStack:
                                EdkLogger.info(LogStr)
                                return True
                    FdAnalyzedList.add(RefFdName)

                for RefFvName in RefFvList:
                    LogStr += "FV %s contains FV %s\n" % (FvNameFromStack, RefFvName)
                    if RefFvName not in RefFvStack:
                        RefFvStack.add(RefFvName)

                    if FvName in RefFvStack or FvNameFromStack in RefFvStack:
                        EdkLogger.info(LogStr)
                        return True

        #
        # Check the cycle between Capsule and FD image
        #
        MaxLength = len (self.Profile.CapsuleDict)
        for CapName in self.Profile.CapsuleDict:
            #
            # Capsule image to be checked.
            #
            LogStr = "\n\n\nCycle Reference Checking for Capsule: %s\n" % CapName
            RefCapStack = {CapName}
            FdAnalyzedList = set()
            FvAnalyzedList = set()

            Index = 0
            while RefCapStack and Index < MaxLength:
                Index = Index + 1
                CapNameFromStack = RefCapStack.pop()
                if CapNameFromStack.upper() in self.Profile.CapsuleDict:
                    CapObj = self.Profile.CapsuleDict[CapNameFromStack.upper()]
                else:
                    continue

                RefFvList = []
                RefFdList = []
                self._GetReferencedFdCapTuple(CapObj, RefFdList, RefFvList)

                FvListLength = 0
                FdListLength = 0
                while FvListLength < len (RefFvList) or FdListLength < len (RefFdList):
                    for RefFdName in RefFdList:
                        if RefFdName in FdAnalyzedList:
                            continue

                        LogStr += "Capsule %s contains FD %s\n" % (CapNameFromStack, RefFdName)
                        for CapNameInFd in self._GetCapInFd(RefFdName):
                            LogStr += "FD %s contains Capsule %s\n" % (RefFdName, CapNameInFd)
                            if CapNameInFd not in RefCapStack:
                                RefCapStack.append(CapNameInFd)

                            if CapName in RefCapStack or CapNameFromStack in RefCapStack:
                                EdkLogger.info(LogStr)
                                return True

                        for FvNameInFd in self._GetFvInFd(RefFdName):
                            LogStr += "FD %s contains FV %s\n" % (RefFdName, FvNameInFd)
                            if FvNameInFd not in RefFvList:
                                RefFvList.append(FvNameInFd)

                        FdAnalyzedList.add(RefFdName)
                    #
                    # the number of the parsed FV and FD image
                    #
                    FvListLength = len (RefFvList)
                    FdListLength = len (RefFdList)
                    for RefFvName in RefFvList:
                        if RefFvName in FvAnalyzedList:
                            continue
                        LogStr += "Capsule %s contains FV %s\n" % (CapNameFromStack, RefFvName)
                        if RefFvName.upper() in self.Profile.FvDict:
                            FvObj = self.Profile.FvDict[RefFvName.upper()]
                        else:
                            continue
                        self._GetReferencedFdFvTuple(FvObj, RefFdList, RefFvList)
                        FvAnalyzedList.add(RefFvName)

        return False

    def GetAllIncludedFile (self):
        global AllIncludeFileList
        return AllIncludeFileList

if __name__ == "__main__":
    import sys
    try:
        test_file = sys.argv[1]
    except IndexError as v:
        print("Usage: %s filename" % sys.argv[0])
        sys.exit(1)

    parser = FdfParser(test_file)
    try:
        parser.ParseFile()
        parser.CycleReferenceCheck()
    except Warning as X:
        print(str(X))
    else:
        print("Success!")

