Ejemplo n.º 1
0
    def GenPackageHeader(self, ContainerFile):
        Logger.Debug(2, "Generate PackageHeader ...")
        DefinesDict = {}

        #
        # Update all defines item in database
        #
        DefObj = self.DecParser.GetDefineSectionObject()
        for Item in DefObj.GetDefines():
            #
            # put items into Dict except for PackageName, Guid, Version, DEC_SPECIFICATION
            #
            SkipItemList = [TAB_DEC_DEFINES_PACKAGE_NAME, \
                TAB_DEC_DEFINES_PACKAGE_GUID, TAB_DEC_DEFINES_PACKAGE_VERSION, \
                TAB_DEC_DEFINES_DEC_SPECIFICATION, TAB_DEC_DEFINES_PKG_UNI_FILE]
            if Item.Key in SkipItemList:
                continue
            DefinesDict['%s = %s' % (Item.Key, Item.Value)] = TAB_ARCH_COMMON

        self.SetBaseName(DefObj.GetPackageName())
        self.SetVersion(DefObj.GetPackageVersion())
#        self.SetName(DefObj.GetPackageName() + ' Version ' + \
#                     DefObj.GetPackageVersion())
        self.SetName(os.path.splitext(self.GetFileName())[0])
        self.SetGuid(DefObj.GetPackageGuid())
        if DefObj.GetPackageUniFile():
            ValidateUNIFilePath(DefObj.GetPackageUniFile())
            self.UniFileClassObject = \
            UniFileClassObject([PathClass(os.path.join(DefObj.GetPackagePath(), DefObj.GetPackageUniFile()))])
        else:
            self.UniFileClassObject = None

        if DefinesDict:
            UserExtension = UserExtensionObject()
            UserExtension.SetDefinesDict(DefinesDict)
            UserExtension.SetIdentifier('DefineModifiers')
            UserExtension.SetUserID('EDK2')
            self.SetUserExtensionList(
                self.GetUserExtensionList() + [UserExtension]
            )

        #
        # Get File header information
        #
        if self.UniFileClassObject:
            Lang = TAB_LANGUAGE_EN_X
        else:
            Lang = TAB_LANGUAGE_EN_US
        Abstract, Description, Copyright, License = \
            ParseHeaderCommentSection(self.DecParser.GetHeadComment(),
                                      ContainerFile)
        if Abstract:
            self.SetAbstract((Lang, Abstract))
        if Description:
            self.SetDescription((Lang, Description))
        if Copyright:
            self.SetCopyright(('', Copyright))
        if License:
            self.SetLicense(('', License))

        #
        # Get Binary header information
        #
        if self.DecParser.BinaryHeadComment:
            Abstract, Description, Copyright, License = \
                ParseHeaderCommentSection(self.DecParser.BinaryHeadComment,
                                      ContainerFile, True)

            if not Abstract  or not Description or not Copyright or not License:
                Logger.Error('MkPkg',
                             FORMAT_INVALID,
                             ST.ERR_INVALID_BINARYHEADER_FORMAT,
                             ContainerFile)
            else:
                self.SetBinaryHeaderAbstract((Lang, Abstract))
                self.SetBinaryHeaderDescription((Lang, Description))
                self.SetBinaryHeaderCopyright(('', Copyright))
                self.SetBinaryHeaderLicense(('', License))

        BinaryAbstractList = []
        BinaryDescriptionList = []

        #Get Binary header from UNI file
        # Initialize the UniStrDict dictionary, top keys are language codes
        UniStrDict = {}
        if self.UniFileClassObject:
            UniStrDict = self.UniFileClassObject.OrderedStringList
            for Lang in UniStrDict:
                for StringDefClassObject in UniStrDict[Lang]:
                    Lang = GetLanguageCode1766(Lang)
                    if StringDefClassObject.StringName == TAB_DEC_BINARY_ABSTRACT:
                        if (Lang, ConvertSpecialUnicodes(StringDefClassObject.StringValue)) \
                        not in self.GetBinaryHeaderAbstract():
                            BinaryAbstractList.append((Lang, ConvertSpecialUnicodes(StringDefClassObject.StringValue)))
                    if StringDefClassObject.StringName == TAB_DEC_BINARY_DESCRIPTION:
                        if (Lang, ConvertSpecialUnicodes(StringDefClassObject.StringValue)) \
                        not in self.GetBinaryHeaderDescription():
                            BinaryDescriptionList.append((Lang,
                                                          ConvertSpecialUnicodes(StringDefClassObject.StringValue)))
        #Combine Binary header from DEC file and UNI file
        BinaryAbstractList = self.GetBinaryHeaderAbstract() + BinaryAbstractList
        BinaryDescriptionList = self.GetBinaryHeaderDescription() + BinaryDescriptionList
        BinaryCopyrightList = self.GetBinaryHeaderCopyright()
        BinaryLicenseList = self.GetBinaryHeaderLicense()
        #Generate the UserExtensionObject for TianoCore."BinaryHeader"
        if BinaryAbstractList or BinaryDescriptionList or BinaryCopyrightList or BinaryLicenseList:
            BinaryUserExtension = UserExtensionObject()
            BinaryUserExtension.SetBinaryAbstract(BinaryAbstractList)
            BinaryUserExtension.SetBinaryDescription(BinaryDescriptionList)
            BinaryUserExtension.SetBinaryCopyright(BinaryCopyrightList)
            BinaryUserExtension.SetBinaryLicense(BinaryLicenseList)
            BinaryUserExtension.SetIdentifier(TAB_BINARY_HEADER_IDENTIFIER)
            BinaryUserExtension.SetUserID(TAB_BINARY_HEADER_USERID)
            self.SetUserExtensionList(self.GetUserExtensionList() + [BinaryUserExtension])
Ejemplo n.º 2
0
    def _GenModuleHeader(self):
        Logger.Debug(2, "Generate ModuleHeader ...")
        #
        # Get all defines information form InfParser Object
        #
        RecordSet = self.Parser.InfDefSection.Defines
        #
        # Should only have one ArchString Item.
        #
        ArchString = RecordSet.keys()[0]
        ArchList = GetSplitValueList(ArchString, ' ')
        ArchList = ConvertArchList(ArchList)
        HasCalledFlag = False
        #
        # Get data from Sdict()
        #
        ValueList = RecordSet[ArchString]
        self.SetFileName(self.FileName)
        self.SetFullPath(self.FullPath)
        #
        # The INF's filename (without the directory path or the extension)
        # must be used for the value of the
        # ModuleSurfaceArea.Header.Name element
        #
        self.SetName(os.path.splitext(os.path.basename(self.FileName))[0])
        self.WorkspaceDir = " "
        #
        # CombinePath and ModulePath
        #
        CombinePath = GetRelativePath(self.FullPath, self.WorkSpace)
        self.SetCombinePath(CombinePath)
        ModulePath = os.path.split(CombinePath)[0]
        ModuleRelativePath = ModulePath
        if self.GetPackagePath() != '':
            ModuleRelativePath = GetRelativePath(ModulePath,
                                                 self.GetPackagePath())
        self.SetModulePath(ModuleRelativePath)
        #
        # For Define Seciton Items.
        #
        DefineObj = ValueList
        #
        # Convert UEFI/PI version to decimal number
        #
        if DefineObj.GetUefiSpecificationVersion() != None:
            __UefiVersion = DefineObj.GetUefiSpecificationVersion().GetValue()
            __UefiVersion = ConvertVersionToDecimal(__UefiVersion)
            self.SetUefiSpecificationVersion(str(__UefiVersion))
        if DefineObj.GetPiSpecificationVersion() != None:
            __PiVersion = DefineObj.GetPiSpecificationVersion().GetValue()
            __PiVersion = ConvertVersionToDecimal(__PiVersion)

            self.SetPiSpecificationVersion(str(__PiVersion))
        SpecList = DefineObj.GetSpecification()
        NewSpecList = []
        for SpecItem in SpecList:
            NewSpecList.append(
                (SpecItem[0], ConvertVersionToDecimal(SpecItem[1])))
        self.SetSpecList(NewSpecList)

        #
        # must exist items in INF define section
        # MODULE_TYPE/BASE_NAME/INF_VERSION/FILE_GUID/VERSION_STRING
        #
        if DefineObj.GetModuleType() == None:
            Logger.Error("InfParser",
                         FORMAT_INVALID,
                         ST.ERR_INF_PARSER_DEFINE_SECTION_MUST_ITEM_NOT_EXIST %
                         ("MODULE_TYPE"),
                         File=self.FullPath)
        else:
            self.SetModuleType(DefineObj.GetModuleType().GetValue())
            ModuleType = DefineObj.GetModuleType().GetValue()
            if ModuleType:
                #
                # Drivers and applications are not allowed to have a MODULE_TYPE of "BASE". Only
                # libraries are permitted to a have a MODULE_TYPE of "BASE".
                #
                if len(DefineObj.LibraryClass) == 0 and ModuleType == 'BASE':
                    Logger.Error(
                        "InfParser",
                        FORMAT_INVALID,
                        ST.ERR_INF_PARSER_MODULETYPE_INVALID,
                        File=self.FullPath,
                        Line=DefineObj.ModuleType.CurrentLine.LineNo,
                        ExtraData=DefineObj.ModuleType.CurrentLine.LineString)
                self.LibModuleTypeList.append(ModuleType)
        if DefineObj.GetBaseName() == None:
            Logger.Error("InfParser",
                         FORMAT_INVALID,
                         ST.ERR_INF_PARSER_DEFINE_SECTION_MUST_ITEM_NOT_EXIST %
                         ("BASE_NAME"),
                         File=self.FullPath)
        else:
            self.SetBaseName(DefineObj.GetBaseName().GetValue())
        if DefineObj.GetModuleUniFileName():
            self.UniFileClassObject = UniFileClassObject(
                [PathClass(DefineObj.GetModuleUniFileName())])
        else:
            self.UniFileClassObject = None
        if DefineObj.GetInfVersion() == None:
            Logger.Error("InfParser",
                         FORMAT_INVALID,
                         ST.ERR_INF_PARSER_DEFINE_SECTION_MUST_ITEM_NOT_EXIST %
                         ("INF_VERSION"),
                         File=self.FullPath)
        else:
            self.SetVersion(DefineObj.GetInfVersion().GetValue())
        if DefineObj.GetFileGuid() == None:
            Logger.Error("InfParser",
                         FORMAT_INVALID,
                         ST.ERR_INF_PARSER_DEFINE_SECTION_MUST_ITEM_NOT_EXIST %
                         ("FILE_GUID"),
                         File=self.FullPath)
        else:
            self.SetGuid(DefineObj.GetFileGuid().GetValue())
        if DefineObj.GetVersionString() == None:
            #
            # VERSION_STRING is missing from the [Defines] section, tools must assume that the module's version is 0.
            #
            self.SetVersion('0')
        else:
            #
            # Get version of INF
            #
            if DefineObj.GetVersionString().GetValue() != "":
                #
                # EDK2 inf
                #
                VersionString = DefineObj.GetVersionString().GetValue()
                if len(VersionString) > 0:
                    VersionString = ConvertVersionToDecimal(VersionString)
                    self.SetVersion(VersionString)
            else:
                #
                # EDK1 inf
                #
                Logger.Error("Parser",
                             PARSER_ERROR,
                             ST.ERR_INF_PARSER_NOT_SUPPORT_EDKI_INF,
                             ExtraData=self.FullPath,
                             RaiseError=Logger.IS_RAISE_ERROR)
        #
        # if there is Shadow, Should judge the MODULE_TYPE in
        # SEC, PEI_CORE and PEIM
        #
        if DefineObj.GetShadow():
            ModuleTypeValue = DefineObj.GetModuleType().GetValue()
            if not (ModuleTypeValue == 'SEC' or ModuleTypeValue == 'PEI_CORE'
                    or ModuleTypeValue == 'PEIM'):
                Logger.Error("InfParser",
                             FORMAT_INVALID,
                             ST.ERR_INF_PARSER_DEFINE_SHADOW_INVALID,
                             File=self.FullPath)

        if DefineObj.GetPcdIsDriver() != None:
            self.SetPcdIsDriver(DefineObj.GetPcdIsDriver().GetValue())
        #
        # LIBRARY_CLASS
        #
        self._GenModuleHeaderLibClass(DefineObj, ArchList)
        #
        # CUSTOM_MAKEFILE
        #
        self.CustomMakefile = DefineObj.GetCustomMakefile()
        #
        # Externs in Defines section
        # Only one define section, so just call once.
        #
        if not HasCalledFlag:
            self._GenModuleHeaderExterns(DefineObj)
            HasCalledFlag = True
        #
        # each module has only one module header
        #
        self.SetSupArchList(ArchList)
        #
        # Get Hob/BootMode/EventList information
        #
        self._GenSpecialComments()
        #
        # put all define statement into user-extension sections
        #
        DefinesDictNew = GenModuleHeaderUserExt(DefineObj, ArchString)
        if DefinesDictNew:
            UserExtension = CommonObject.UserExtensionObject()
            UserExtension.SetDefinesDict(DefinesDictNew)
            UserExtension.SetIdentifier('DefineModifiers')
            UserExtension.SetUserID('EDK2')
            self.SetUserExtensionList(self.GetUserExtensionList() +
                                      [UserExtension])
        #
        # Get all meta-file header information
        # the record is list of items formated:
        # [LineValue, Arch, StartLine, ID, Third]
        #
        InfHeaderObj = self.Parser.InfHeader
        #
        # Put header information into POM object
        #
        if self.UniFileClassObject:
            Lang = DT.TAB_LANGUAGE_EN_X
        else:
            Lang = DT.TAB_LANGUAGE_EN_US
        if InfHeaderObj.GetAbstract():
            self.SetAbstract((Lang, InfHeaderObj.GetAbstract()))
        if InfHeaderObj.GetDescription():
            self.SetDescription((Lang, InfHeaderObj.GetDescription()))
        if InfHeaderObj.GetCopyright():
            self.SetCopyright(('', InfHeaderObj.GetCopyright()))
        if InfHeaderObj.GetLicense():
            self.SetLicense(('', InfHeaderObj.GetLicense()))
        #
        # Put Binary header information into POM object
        #
        InfBinaryHeaderObj = self.Parser.InfBinaryHeader
        if InfBinaryHeaderObj.GetAbstract():
            self.SetBinaryHeaderAbstract(
                (Lang, InfBinaryHeaderObj.GetAbstract()))
        if InfBinaryHeaderObj.GetDescription():
            self.SetBinaryHeaderDescription(
                (Lang, InfBinaryHeaderObj.GetDescription()))
        if InfBinaryHeaderObj.GetCopyright():
            self.SetBinaryHeaderCopyright(
                ('', InfBinaryHeaderObj.GetCopyright()))
        if InfBinaryHeaderObj.GetLicense():
            self.SetBinaryHeaderLicense(('', InfBinaryHeaderObj.GetLicense()))
            Line = Line.replace(UNICODE_NON_BREAKING_CHAR, NON_BREAKING_CHAR)

            Line = Line.replace(u'\\\\', u'\u0006')
            Line = Line.replace(u'\\r\\n', CR + LF)
            Line = Line.replace(u'\\n', CR + LF)
            Line = Line.replace(u'\\r', CR)
            Line = Line.replace(u'\\t', u'\t')
            Line = Line.replace(u'''\"''', u'''"''')
            Line = Line.replace(u'\t', u' ')
            Line = Line.replace(u'\u0006', u'\\')

            # IncList = gINCLUDE_PATTERN.findall(Line)
            IncList = []
            if len(IncList) == 1:
                for Dir in [File.Dir] + self.IncludePathList:
                    IncFile = PathClass(str(IncList[0]), Dir)
                    self.IncFileList.append(IncFile)
                    if os.path.isfile(IncFile.Path):
                        Lines.extend(self.PreProcess(IncFile, True))
                        break
                else:
                    EdkLogger.Error("Unicode File Parser", 
                                    ToolError.FILE_NOT_FOUND, 
                                    Message="Cannot find include file", 
                                    ExtraData=str(IncList[0]))
                continue

            #
            # Check if single line has correct '"'
            #
            if Line.startswith(u'#string') and Line.find(u'#language') > -1 and Line.find('"') > Line.find(u'#language'):
Ejemplo n.º 4
0
    def PreProcess(self, File, IsIncludeFile=False):
        if not os.path.exists(File.Path) or not os.path.isfile(File.Path):
            EdkLogger.Error("Unicode File Parser",
                            ToolError.FILE_NOT_FOUND,
                            ExtraData=File.Path)

        #
        # Check file header of the Uni file
        #
        if not CheckUTF16FileHeader(File.Path):
            EdkLogger.Error(
                "Unicode File Parser",
                ToolError.FORMAT_INVALID,
                ExtraData=
                'The file %s is either invalid UTF-16LE or it is missing the BOM.'
                % File.Path)

        try:
            FileIn = codecs.open(File.Path, mode='rb',
                                 encoding='utf_16').readlines()
        except UnicodeError:
            FileIn = codecs.open(File.Path, mode='rb',
                                 encoding='utf_16_le').readlines()
        except:
            EdkLogger.Error("Unicode File Parser",
                            ToolError.FILE_OPEN_FAILURE,
                            ExtraData=File.Path)

        #
        # get the file header
        #
        Lines = []
        HeaderStart = False
        HeaderEnd = False
        if not self.UniFileHeader:
            FirstGenHeader = True
        else:
            FirstGenHeader = False
        for Line in FileIn:
            Line = Line.strip()
            if Line == u'':
                continue
            if Line.startswith(DT.TAB_COMMENT_EDK1_SPLIT) and (Line.find(DT.TAB_HEADER_COMMENT) > -1) \
                and not HeaderEnd and not HeaderStart:
                HeaderStart = True
            if not Line.startswith(DT.TAB_COMMENT_EDK1_SPLIT
                                   ) and HeaderStart and not HeaderEnd:
                HeaderEnd = True
            if Line.startswith(
                    DT.TAB_COMMENT_EDK1_SPLIT
            ) and HeaderStart and not HeaderEnd and FirstGenHeader:
                self.UniFileHeader += Line + '\r\n'
                continue

        #
        # Use unique identifier
        #
        FindFlag = -1
        LineCount = 0
        MultiLineFeedExits = False
        #
        # 0: initial value
        # 1: signle String entry exist
        # 2: line feed exist under the some signle String entry
        #
        StringEntryExistsFlag = 0
        for Line in FileIn:
            Line = FileIn[LineCount]
            LineCount += 1
            Line = Line.strip()
            #
            # Ignore comment line and empty line
            #
            if Line == u'' or Line.startswith(u'//'):
                #
                # Change the single line String entry flag status
                #
                if StringEntryExistsFlag == 1:
                    StringEntryExistsFlag = 2
                #
                # If the '#string' line and the '#language' line are not in the same line,
                # there should be only one line feed character betwwen them
                #
                if MultiLineFeedExits:
                    EdkLogger.Error("Unicode File Parser",
                                    ToolError.FORMAT_INVALID,
                                    ExtraData=File.Path)
                continue

            MultiLineFeedExits = False
            #
            # Process comment embeded in string define lines
            #
            FindFlag = Line.find(u'//')
            if FindFlag != -1 and Line.find(u'//') < Line.find(u'"'):
                Line = Line.replace(Line[FindFlag:], u' ')
                if FileIn[LineCount].strip().startswith('#language'):
                    Line = Line + FileIn[LineCount]
                    FileIn[LineCount - 1] = Line
                    FileIn[LineCount] = '\r\n'
                    LineCount -= 1
                    for Index in xrange(LineCount + 1, len(FileIn) - 1):
                        if (Index == len(FileIn) - 1):
                            FileIn[Index] = '\r\n'
                        else:
                            FileIn[Index] = FileIn[Index + 1]
                    continue
            CommIndex = GetCharIndexOutStr(u'/', Line)
            if CommIndex > -1:
                if (len(Line) - 1) > CommIndex:
                    if Line[CommIndex + 1] == u'/':
                        Line = Line[:CommIndex].strip()
                    else:
                        EdkLogger.Error("Unicode File Parser",
                                        ToolError.FORMAT_INVALID,
                                        ExtraData=File.Path)
                else:
                    EdkLogger.Error("Unicode File Parser",
                                    ToolError.FORMAT_INVALID,
                                    ExtraData=File.Path)

            Line = Line.replace(UNICODE_WIDE_CHAR, WIDE_CHAR)
            Line = Line.replace(UNICODE_NARROW_CHAR, NARROW_CHAR)
            Line = Line.replace(UNICODE_NON_BREAKING_CHAR, NON_BREAKING_CHAR)

            Line = Line.replace(u'\\\\', u'\u0006')
            Line = Line.replace(u'\\r\\n', CR + LF)
            Line = Line.replace(u'\\n', CR + LF)
            Line = Line.replace(u'\\r', CR)
            Line = Line.replace(u'\\t', u'\t')
            Line = Line.replace(u'''\"''', u'''"''')
            Line = Line.replace(u'\t', u' ')
            Line = Line.replace(u'\u0006', u'\\')

            # IncList = gINCLUDE_PATTERN.findall(Line)
            IncList = []
            if len(IncList) == 1:
                for Dir in [File.Dir] + self.IncludePathList:
                    IncFile = PathClass(str(IncList[0]), Dir)
                    self.IncFileList.append(IncFile)
                    if os.path.isfile(IncFile.Path):
                        Lines.extend(self.PreProcess(IncFile, True))
                        break
                else:
                    EdkLogger.Error("Unicode File Parser",
                                    ToolError.FILE_NOT_FOUND,
                                    Message="Cannot find include file",
                                    ExtraData=str(IncList[0]))
                continue

            #
            # Between Name entry and Language entry can not contain line feed
            #
            if Line.startswith(u'#string') and Line.find(u'#language') == -1:
                MultiLineFeedExits = True

            if Line.startswith(u'#string') and Line.find(
                    u'#language') > 0 and Line.find(u'"') < 0:
                MultiLineFeedExits = True

            #
            # Between Language entry and String entry can not contain line feed
            #
            if Line.startswith(u'#language') and len(Line.split()) == 2:
                MultiLineFeedExits = True

            #
            # Between two String entry, can not contain line feed
            #
            if Line.startswith(u'"'):
                if StringEntryExistsFlag == 2:
                    EdkLogger.Error("Unicode File Parser",
                                    ToolError.FORMAT_INVALID,
                                    Message=ST.ERR_UNIPARSE_LINEFEED_UP_EXIST %
                                    Line,
                                    ExtraData=File.Path)

                StringEntryExistsFlag = 1
                if not Line.endswith('"'):
                    EdkLogger.Error(
                        "Unicode File Parser",
                        ToolError.FORMAT_INVALID,
                        ExtraData=
                        '''The line %s misses '"' at the end of it in file %s'''
                        % (LineCount, File.Path))
            elif Line.startswith(u'#language'):
                if StringEntryExistsFlag == 2:
                    EdkLogger.Error("Unicode File Parser",
                                    ToolError.FORMAT_INVALID,
                                    Message=ST.ERR_UNI_MISS_STRING_ENTRY %
                                    Line,
                                    ExtraData=File.Path)
                StringEntryExistsFlag = 0
            else:
                StringEntryExistsFlag = 0

            Lines.append(Line)

        #
        # Convert string def format as below
        #
        #     #string MY_STRING_1
        #     #language eng
        #     "My first English string line 1"
        #     "My first English string line 2"
        #     #string MY_STRING_1
        #     #language spa
        #     "Mi segunda secuencia 1"
        #     "Mi segunda secuencia 2"
        #

        if not IsIncludeFile and not Lines:
            EdkLogger.Error("Unicode File Parser", ToolError.FORMAT_INVALID, \
                Message=ST.ERR_UNIPARSE_NO_SECTION_EXIST, \
                ExtraData=File.Path)

        NewLines = []
        StrName = u''
        ExistStrNameList = []
        for Line in Lines:
            if StrName and not StrName.split()[1].startswith(
                    DT.TAB_STR_TOKENCNAME + DT.TAB_UNDERLINE_SPLIT):
                EdkLogger.Error("Unicode File Parser", ToolError.FORMAT_INVALID, \
                                Message=ST.ERR_UNIPARSE_STRNAME_FORMAT_ERROR % StrName.split()[1], \
                                ExtraData=File.Path)

            if StrName and len(StrName.split()[1].split(
                    DT.TAB_UNDERLINE_SPLIT)) == 4:
                StringTokenList = StrName.split()[1].split(
                    DT.TAB_UNDERLINE_SPLIT)
                if (StringTokenList[3].upper() in [DT.TAB_STR_TOKENPROMPT, DT.TAB_STR_TOKENHELP] and \
                    StringTokenList[3] not in [DT.TAB_STR_TOKENPROMPT, DT.TAB_STR_TOKENHELP]) or \
                    (StringTokenList[2].upper() == DT.TAB_STR_TOKENERR and StringTokenList[2] != DT.TAB_STR_TOKENERR):
                    EdkLogger.Error("Unicode File Parser", ToolError.FORMAT_INVALID, \
                                Message=ST.ERR_UNIPARSE_STRTOKEN_FORMAT_ERROR % StrName.split()[1], \
                                ExtraData=File.Path)

            if Line.count(u'#language') > 1:
                EdkLogger.Error("Unicode File Parser", ToolError.FORMAT_INVALID, \
                                Message=ST.ERR_UNIPARSE_SEP_LANGENTRY_LINE % Line, \
                                ExtraData=File.Path)

            if Line.startswith(u'//'):
                continue
            elif Line.startswith(u'#langdef'):
                if len(Line.split()) == 2:
                    NewLines.append(Line)
                    continue
                elif len(Line.split()) > 2 and Line.find(u'"') > 0:
                    NewLines.append(Line[:Line.find(u'"')].strip())
                    NewLines.append(Line[Line.find(u'"'):])
                else:
                    EdkLogger.Error("Unicode File Parser",
                                    ToolError.FORMAT_INVALID,
                                    ExtraData=File.Path)
            elif Line.startswith(u'#string'):
                if len(Line.split()) == 2:
                    StrName = Line
                    if StrName:
                        if StrName.split()[1] not in ExistStrNameList:
                            ExistStrNameList.append(StrName.split()[1].strip())
                        elif StrName.split()[1] in [DT.TAB_INF_ABSTRACT, DT.TAB_INF_DESCRIPTION, \
                                                    DT.TAB_INF_BINARY_ABSTRACT, DT.TAB_INF_BINARY_DESCRIPTION, \
                                                    DT.TAB_DEC_PACKAGE_ABSTRACT, DT.TAB_DEC_PACKAGE_DESCRIPTION, \
                                                    DT.TAB_DEC_BINARY_ABSTRACT, DT.TAB_DEC_BINARY_DESCRIPTION]:
                            EdkLogger.Error("Unicode File Parser", ToolError.FORMAT_INVALID, \
                                            Message=ST.ERR_UNIPARSE_MULTI_ENTRY_EXIST % StrName.split()[1], \
                                            ExtraData=File.Path)
                    continue
                elif len(Line.split()) == 4 and Line.find(u'#language') > 0:
                    if Line[Line.find(u'#language')-1] != ' ' or \
                       Line[Line.find(u'#language')+len(u'#language')] != u' ':
                        EdkLogger.Error("Unicode File Parser",
                                        ToolError.FORMAT_INVALID,
                                        ExtraData=File.Path)

                    if Line.find(u'"') > 0:
                        EdkLogger.Error("Unicode File Parser",
                                        ToolError.FORMAT_INVALID,
                                        ExtraData=File.Path)

                    StrName = Line.split()[0] + u' ' + Line.split()[1]
                    if StrName:
                        if StrName.split()[1] not in ExistStrNameList:
                            ExistStrNameList.append(StrName.split()[1].strip())
                        elif StrName.split()[1] in [DT.TAB_INF_ABSTRACT, DT.TAB_INF_DESCRIPTION, \
                                                    DT.TAB_INF_BINARY_ABSTRACT, DT.TAB_INF_BINARY_DESCRIPTION, \
                                                    DT.TAB_DEC_PACKAGE_ABSTRACT, DT.TAB_DEC_PACKAGE_DESCRIPTION, \
                                                    DT.TAB_DEC_BINARY_ABSTRACT, DT.TAB_DEC_BINARY_DESCRIPTION]:
                            EdkLogger.Error("Unicode File Parser", ToolError.FORMAT_INVALID, \
                                            Message=ST.ERR_UNIPARSE_MULTI_ENTRY_EXIST % StrName.split()[1], \
                                            ExtraData=File.Path)
                    if IsIncludeFile:
                        if StrName not in NewLines:
                            NewLines.append(
                                (Line[:Line.find(u'#language')]).strip())
                    else:
                        NewLines.append(
                            (Line[:Line.find(u'#language')]).strip())
                    NewLines.append((Line[Line.find(u'#language'):]).strip())
                elif len(Line.split()) > 4 and Line.find(
                        u'#language') > 0 and Line.find(u'"') > 0:
                    if Line[Line.find(u'#language')-1] != u' ' or \
                       Line[Line.find(u'#language')+len(u'#language')] != u' ':
                        EdkLogger.Error("Unicode File Parser",
                                        ToolError.FORMAT_INVALID,
                                        ExtraData=File.Path)

                    if Line[Line.find(u'"') - 1] != u' ':
                        EdkLogger.Error("Unicode File Parser",
                                        ToolError.FORMAT_INVALID,
                                        ExtraData=File.Path)

                    StrName = Line.split()[0] + u' ' + Line.split()[1]
                    if StrName:
                        if StrName.split()[1] not in ExistStrNameList:
                            ExistStrNameList.append(StrName.split()[1].strip())
                        elif StrName.split()[1] in [DT.TAB_INF_ABSTRACT, DT.TAB_INF_DESCRIPTION, \
                                                    DT.TAB_INF_BINARY_ABSTRACT, DT.TAB_INF_BINARY_DESCRIPTION, \
                                                    DT.TAB_DEC_PACKAGE_ABSTRACT, DT.TAB_DEC_PACKAGE_DESCRIPTION, \
                                                    DT.TAB_DEC_BINARY_ABSTRACT, DT.TAB_DEC_BINARY_DESCRIPTION]:
                            EdkLogger.Error("Unicode File Parser", ToolError.FORMAT_INVALID, \
                                            Message=ST.ERR_UNIPARSE_MULTI_ENTRY_EXIST % StrName.split()[1], \
                                            ExtraData=File.Path)
                    if IsIncludeFile:
                        if StrName not in NewLines:
                            NewLines.append(
                                (Line[:Line.find(u'#language')]).strip())
                    else:
                        NewLines.append(
                            (Line[:Line.find(u'#language')]).strip())
                    NewLines.append((
                        Line[Line.find(u'#language'):Line.find(u'"')]).strip())
                    NewLines.append((Line[Line.find(u'"'):]).strip())
                else:
                    EdkLogger.Error("Unicode File Parser",
                                    ToolError.FORMAT_INVALID,
                                    ExtraData=File.Path)
            elif Line.startswith(u'#language'):
                if len(Line.split()) == 2:
                    if IsIncludeFile:
                        if StrName not in NewLines:
                            NewLines.append(StrName)
                    else:
                        NewLines.append(StrName)
                    NewLines.append(Line)
                elif len(Line.split()) > 2 and Line.find(u'"') > 0:
                    if IsIncludeFile:
                        if StrName not in NewLines:
                            NewLines.append(StrName)
                    else:
                        NewLines.append(StrName)
                    NewLines.append((Line[:Line.find(u'"')]).strip())
                    NewLines.append((Line[Line.find(u'"'):]).strip())
                else:
                    EdkLogger.Error("Unicode File Parser",
                                    ToolError.FORMAT_INVALID,
                                    ExtraData=File.Path)
            elif Line.startswith(u'"'):
                if u'#string' in Line or u'#language' in Line:
                    EdkLogger.Error("Unicode File Parser",
                                    ToolError.FORMAT_INVALID,
                                    ExtraData=File.Path)
                NewLines.append(Line)
            else:
                print Line
                EdkLogger.Error("Unicode File Parser",
                                ToolError.FORMAT_INVALID,
                                ExtraData=File.Path)

        if StrName and not StrName.split()[1].startswith(u'STR_'):
            EdkLogger.Error("Unicode File Parser", ToolError.FORMAT_INVALID, \
                                Message=ST.ERR_UNIPARSE_STRNAME_FORMAT_ERROR % StrName.split()[1], \
                                ExtraData=File.Path)

        if StrName and not NewLines:
            EdkLogger.Error("Unicode File Parser", ToolError.FORMAT_INVALID, \
                            Message=ST.ERR_UNI_MISS_LANGENTRY % StrName, \
                            ExtraData=File.Path)

        #
        # Check Abstract, Description, BinaryAbstract and BinaryDescription order,
        # should be Abstract, Description, BinaryAbstract, BinaryDesctiption
        AbstractPosition = -1
        DescriptionPosition = -1
        BinaryAbstractPosition = -1
        BinaryDescriptionPosition = -1
        for StrName in ExistStrNameList:
            if DT.TAB_HEADER_ABSTRACT.upper() in StrName:
                if 'BINARY' in StrName:
                    BinaryAbstractPosition = ExistStrNameList.index(StrName)
                else:
                    AbstractPosition = ExistStrNameList.index(StrName)
            if DT.TAB_HEADER_DESCRIPTION.upper() in StrName:
                if 'BINARY' in StrName:
                    BinaryDescriptionPosition = ExistStrNameList.index(StrName)
                else:
                    DescriptionPosition = ExistStrNameList.index(StrName)

        OrderList = sorted([AbstractPosition, DescriptionPosition])
        BinaryOrderList = sorted(
            [BinaryAbstractPosition, BinaryDescriptionPosition])
        Min = OrderList[0]
        Max = OrderList[1]
        BinaryMin = BinaryOrderList[0]
        BinaryMax = BinaryOrderList[1]
        if BinaryDescriptionPosition > -1:
            if not(BinaryDescriptionPosition == BinaryMax and BinaryAbstractPosition == BinaryMin and \
                   BinaryMax > Max):
                EdkLogger.Error("Unicode File Parser", ToolError.FORMAT_INVALID, \
                                Message=ST.ERR_UNIPARSE_ENTRY_ORDER_WRONG, \
                                ExtraData=File.Path)
        elif BinaryAbstractPosition > -1:
            if not (BinaryAbstractPosition > Max):
                EdkLogger.Error("Unicode File Parser", ToolError.FORMAT_INVALID, \
                                Message=ST.ERR_UNIPARSE_ENTRY_ORDER_WRONG, \
                                ExtraData=File.Path)

        if DescriptionPosition > -1:
            if not(DescriptionPosition == Max and AbstractPosition == Min and \
                   DescriptionPosition > AbstractPosition):
                EdkLogger.Error("Unicode File Parser", ToolError.FORMAT_INVALID, \
                                Message=ST.ERR_UNIPARSE_ENTRY_ORDER_WRONG, \
                                ExtraData=File.Path)

        if not self.UniFileHeader:
            EdkLogger.Error("Unicode File Parser",
                            ToolError.FORMAT_INVALID,
                            Message=ST.ERR_NO_SOURCE_HEADER,
                            ExtraData=File.Path)

        return NewLines