mirror of
				https://github.com/acidanthera/audk.git
				synced 2025-10-31 03:03:46 +01:00 
			
		
		
		
	BaseTool Branch: https://edk2-buildtools.svn.sourceforge.net/svnroot/edk2-buildtools/branches/Releases/BaseTools_r2100 Signed-off-by: lgao4 Reviewed-by: hchen30 git-svn-id: https://edk2.svn.sourceforge.net/svnroot/edk2/trunk/edk2@12214 6f19259b-4bc3-4df7-8a09-765794883524
		
			
				
	
	
		
			640 lines
		
	
	
		
			26 KiB
		
	
	
	
		
			Python
		
	
	
	
	
	
			
		
		
	
	
			640 lines
		
	
	
		
			26 KiB
		
	
	
	
		
			Python
		
	
	
	
	
	
| ## @file
 | |
| # This file is used to define class objects of INF file [Pcds] section. 
 | |
| # It will consumed by InfParser. 
 | |
| #
 | |
| # Copyright (c) 2011, Intel Corporation. All rights reserved.<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.
 | |
| 
 | |
| '''
 | |
| InfPcdObject
 | |
| '''
 | |
| import os
 | |
| import re
 | |
| 
 | |
| from Logger import StringTable as ST
 | |
| from Logger import ToolError
 | |
| import Logger.Log as Logger
 | |
| from Library import GlobalData 
 | |
| from Library import DataType as DT
 | |
| 
 | |
| from Library.Misc import Sdict
 | |
| from Library.Misc import GetHelpStringByRemoveHashKey
 | |
| from Library.ParserValidate import IsValidPcdType 
 | |
| from Library.ParserValidate import IsValidCVariableName
 | |
| from Library.ParserValidate import IsValidPcdValue
 | |
| from Library.ParserValidate import IsValidArch
 | |
| from Library.CommentParsing import ParseComment
 | |
| from Library.String import GetSplitValueList
 | |
| from Library.String import IsHexDigitUINT32
 | |
| from Library.ExpressionValidate import IsValidFeatureFlagExp
 | |
| from Parser.InfAsBuiltProcess import GetPackageListInfo
 | |
| from Parser.DecParser import Dec
 | |
| 
 | |
| from Object.Parser.InfPackagesObject import InfPackageItem
 | |
| 
 | |
| def ValidateArch(ArchItem, PcdTypeItem1, LineNo, SupArchDict, SupArchList):
 | |
|     #
 | |
|     # Validate Arch
 | |
|     #            
 | |
|     if (ArchItem == '' or ArchItem == None):
 | |
|         ArchItem = 'COMMON'
 | |
|     
 | |
|     if PcdTypeItem1.upper != DT.TAB_INF_FEATURE_PCD.upper():
 | |
|         ArchList = GetSplitValueList(ArchItem, ' ')
 | |
|         for ArchItemNew in ArchList:
 | |
|             if not IsValidArch(ArchItemNew):
 | |
|                 Logger.Error("InfParser", 
 | |
|                              ToolError.FORMAT_INVALID,
 | |
|                              ST.ERR_INF_PARSER_DEFINE_FROMAT_INVALID%(ArchItemNew), 
 | |
|                              File=GlobalData.gINF_MODULE_NAME,
 | |
|                              Line=LineNo, 
 | |
|                              ExtraData=ArchItemNew)
 | |
|         SupArchDict[PcdTypeItem1] = ArchList            
 | |
|     else:
 | |
|         SupArchList.append(ArchItem)
 | |
|         
 | |
|     return SupArchList, SupArchDict
 | |
| 
 | |
| def ParsePcdComment(CommentList, PcdTypeItem, PcdItemObj):
 | |
|     CommentInsList = []
 | |
|     PreUsage = None
 | |
|     PreHelpText = ''
 | |
|     BlockFlag = -1
 | |
|     FFEHelpText = ''
 | |
|     CommentItemHelpText = '' 
 | |
|     Count = 0   
 | |
|     for CommentItem in CommentList:
 | |
|         Count = Count + 1
 | |
|         CommentItemUsage, CommentType, CommentString, CommentItemHelpText =  ParseComment(CommentItem, 
 | |
|                                                                              DT.ALL_USAGE_TOKENS, 
 | |
|                                                                              {}, 
 | |
|                                                                              [],
 | |
|                                                                              False)
 | |
|         if CommentType and CommentString:
 | |
|             pass                      
 | |
|                      
 | |
|         if PcdTypeItem == 'FeaturePcd':
 | |
|             CommentItemUsage = DT.USAGE_ITEM_CONSUMES
 | |
|             if CommentItemHelpText == None:
 | |
|                 CommentItemHelpText = ''
 | |
|             
 | |
|             if Count == 1:
 | |
|                 FFEHelpText = CommentItemHelpText
 | |
|             else:
 | |
|                 FFEHelpText = FFEHelpText + DT.END_OF_LINE + CommentItemHelpText
 | |
|             
 | |
|             if Count == len(CommentList):
 | |
|                 CommentItemHelpText = FFEHelpText
 | |
|                 BlockFlag = 4
 | |
|             else:
 | |
|                 continue
 | |
|                             
 | |
|         if CommentItemHelpText == None:
 | |
|             CommentItemHelpText = ''
 | |
|             if Count == len(CommentList) and CommentItemUsage == DT.ITEM_UNDEFINED:
 | |
|                 CommentItemHelpText = DT.END_OF_LINE
 | |
|                 
 | |
|         if Count == len(CommentList) and (BlockFlag == 1 or BlockFlag == 2):
 | |
|             if CommentItemUsage == DT.ITEM_UNDEFINED:
 | |
|                 BlockFlag = 4
 | |
|             else:
 | |
|                 BlockFlag = 3
 | |
|         elif BlockFlag == -1 and Count == len(CommentList):
 | |
|             BlockFlag = 4  
 | |
|             
 | |
|         if BlockFlag == -1 or BlockFlag == 1 or BlockFlag == 2:
 | |
|             if CommentItemUsage == DT.ITEM_UNDEFINED:
 | |
|                 if BlockFlag == -1:
 | |
|                     BlockFlag = 1
 | |
|                 elif BlockFlag == 1:
 | |
|                     BlockFlag = 2
 | |
|             else:
 | |
|                 if BlockFlag == 1 or BlockFlag == 2:
 | |
|                     BlockFlag = 3
 | |
|                 elif BlockFlag == -1:
 | |
|                     BlockFlag = 4
 | |
|         #
 | |
|         # Combine two comment line if they are generic comment
 | |
|         #   
 | |
|         if CommentItemUsage == PreUsage == DT.ITEM_UNDEFINED:
 | |
|             CommentItemHelpText = PreHelpText + DT.END_OF_LINE + CommentItemHelpText
 | |
|             
 | |
|             PreHelpText = CommentItemHelpText
 | |
|             
 | |
|         if BlockFlag == 4:     
 | |
|             CommentItemIns = InfPcdItemCommentContent()
 | |
|             CommentItemIns.SetUsageItem(CommentItemUsage)
 | |
|             CommentItemIns.SetHelpStringItem(CommentItemHelpText)
 | |
|             CommentInsList.append(CommentItemIns)
 | |
|             
 | |
|             BlockFlag = -1
 | |
|             PreUsage = None
 | |
|             PreHelpText = ''
 | |
|             
 | |
|         elif BlockFlag == 3:
 | |
|             #
 | |
|             # Add previous help string
 | |
|             # 
 | |
|             CommentItemIns = InfPcdItemCommentContent()
 | |
|             CommentItemIns.SetUsageItem(DT.ITEM_UNDEFINED)
 | |
|             if PreHelpText == '' or PreHelpText.endswith(DT.END_OF_LINE):
 | |
|                 PreHelpText += DT.END_OF_LINE            
 | |
|             CommentItemIns.SetHelpStringItem(PreHelpText)
 | |
|             CommentInsList.append(CommentItemIns)
 | |
|             #
 | |
|             # Add Current help string
 | |
|             #
 | |
|             CommentItemIns = InfPcdItemCommentContent()
 | |
|             CommentItemIns.SetUsageItem(CommentItemUsage)
 | |
|             CommentItemIns.SetHelpStringItem(CommentItemHelpText)
 | |
|             CommentInsList.append(CommentItemIns)
 | |
|             
 | |
|             BlockFlag = -1
 | |
|             PreUsage = None
 | |
|             PreHelpText = ''    
 | |
|                                                                             
 | |
|         else:
 | |
|             PreUsage = CommentItemUsage
 | |
|             PreHelpText = CommentItemHelpText
 | |
|            
 | |
|     PcdItemObj.SetHelpStringList(CommentInsList)
 | |
|     
 | |
|     return PcdItemObj               
 | |
| 
 | |
| class InfPcdItemCommentContent():
 | |
|     def __init__(self):
 | |
|         #
 | |
|         # ## SOMETIMES_CONSUMES ## HelpString 
 | |
|         #
 | |
|         self.UsageItem = ''
 | |
|         #
 | |
|         # Help String
 | |
|         #
 | |
|         self.HelpStringItem = ''
 | |
|         
 | |
|     def SetUsageItem(self, UsageItem):
 | |
|         self.UsageItem = UsageItem
 | |
|     def GetUsageItem(self):
 | |
|         return self.UsageItem
 | |
|       
 | |
|     def SetHelpStringItem(self, HelpStringItem):
 | |
|         self.HelpStringItem = HelpStringItem
 | |
|     def GetHelpStringItem(self):
 | |
|         return self.HelpStringItem
 | |
|     
 | |
| ## InfPcdItem
 | |
| #
 | |
| # This class defined Pcd item used in Module files
 | |
| #
 | |
| # @param CName:                Input value for CName, default is ''
 | |
| # @param Token:                Input value for Token, default is ''
 | |
| # @param TokenSpaceGuidCName:  Input value for TokenSpaceGuidCName, default 
 | |
| #                              is ''
 | |
| # @param DatumType:            Input value for DatumType, default is ''
 | |
| # @param MaxDatumSize:         Input value for MaxDatumSize, default is ''
 | |
| # @param DefaultValue:         Input value for DefaultValue, default is ''
 | |
| # @param ItemType:             Input value for ItemType, default is ''
 | |
| # @param ValidUsage:           Input value for ValidUsage, default is []
 | |
| # @param SkuInfoList:          Input value for SkuInfoList, default is {}
 | |
| # @param SupModuleList:        Input value for SupModuleList, default is []
 | |
| #
 | |
| class InfPcdItem():
 | |
|     def __init__(self):
 | |
|         self.CName = ''
 | |
|         self.Token = ''
 | |
|         self.TokenSpaceGuidCName = ''
 | |
|         self.TokenSpaceGuidValue = ''
 | |
|         self.DatumType      = ''
 | |
|         self.MaxDatumSize   = ''
 | |
|         self.DefaultValue   = ''
 | |
|         self.Offset         = ''
 | |
|         self.ValidUsage     = ''
 | |
|         self.ItemType       = '' 
 | |
|         self.SupModuleList  = []
 | |
|         self.HelpStringList = []
 | |
|         self.FeatureFlagExp = ''
 | |
|         self.SupArchList    = []
 | |
|         self.PcdErrorsList = []
 | |
|         
 | |
|     def SetCName(self, CName):
 | |
|         self.CName = CName    
 | |
|     def GetCName(self):
 | |
|         return self.CName
 | |
|     
 | |
|     def SetToken(self, Token):
 | |
|         self.Token = Token    
 | |
|     def GetToken(self):
 | |
|         return self.Token
 | |
|     
 | |
|     def SetTokenSpaceGuidCName(self, TokenSpaceGuidCName):
 | |
|         self.TokenSpaceGuidCName = TokenSpaceGuidCName    
 | |
|     def GetTokenSpaceGuidCName(self):
 | |
|         return self.TokenSpaceGuidCName
 | |
|     
 | |
|     def SetTokenSpaceGuidValue(self, TokenSpaceGuidValue):
 | |
|         self.TokenSpaceGuidValue = TokenSpaceGuidValue    
 | |
|     def GetTokenSpaceGuidValue(self):
 | |
|         return self.TokenSpaceGuidValue
 | |
|     
 | |
|     def SetDatumType(self, DatumType):
 | |
|         self.DatumType = DatumType        
 | |
|     def GetDatumType(self):
 | |
|         return self.DatumType
 | |
|     
 | |
|     def SetMaxDatumSize(self, MaxDatumSize):
 | |
|         self.MaxDatumSize = MaxDatumSize    
 | |
|     def GetMaxDatumSize(self):
 | |
|         return self.MaxDatumSize
 | |
| 
 | |
|     def SetDefaultValue(self, DefaultValue):
 | |
|         self.DefaultValue = DefaultValue        
 | |
|     def GetDefaultValue(self):
 | |
|         return self.DefaultValue
 | |
|     
 | |
|     def SetPcdErrorsList(self, PcdErrorsList):
 | |
|         self.PcdErrorsList = PcdErrorsList    
 | |
|     def GetPcdErrorsList(self):
 | |
|         return self.PcdErrorsList
 | |
| 
 | |
|     def SetItemType(self, ItemType):
 | |
|         self.ItemType = ItemType        
 | |
|     def GetItemType(self):
 | |
|         return self.ItemType
 | |
| 
 | |
|     def SetSupModuleList(self, SupModuleList):
 | |
|         self.SupModuleList = SupModuleList      
 | |
|     def GetSupModuleList(self):
 | |
|         return self.SupModuleList
 | |
|     
 | |
|     def SetHelpStringList(self, HelpStringList):
 | |
|         self.HelpStringList = HelpStringList
 | |
|     def GetHelpStringList(self):
 | |
|         return self.HelpStringList
 | |
|     
 | |
|     def SetFeatureFlagExp(self, FeatureFlagExp):
 | |
|         self.FeatureFlagExp = FeatureFlagExp
 | |
|     def GetFeatureFlagExp(self):
 | |
|         return self.FeatureFlagExp
 | |
|     
 | |
|     def SetSupportArchList(self, ArchList):
 | |
|         self.SupArchList = ArchList
 | |
|     def GetSupportArchList(self):
 | |
|         return self.SupArchList
 | |
|     
 | |
|     def SetOffset(self, Offset):
 | |
|         self.Offset = Offset
 | |
|     def GetOffset(self):
 | |
|         return self.Offset
 | |
| 
 | |
| ##
 | |
| #
 | |
| #
 | |
| #
 | |
| class InfPcdObject():
 | |
|     def __init__(self, FileName):
 | |
|         self.Pcds = Sdict()
 | |
|         self.FileName = FileName
 | |
|         
 | |
|     def SetPcds(self, PcdContent, KeysList = None, PackageInfo = None):
 | |
|         
 | |
|         if GlobalData.gIS_BINARY_INF:
 | |
|             self.SetAsBuildPcds(PcdContent, KeysList, PackageInfo)
 | |
|             return True
 | |
|         
 | |
|         #
 | |
|         # Validate Arch
 | |
|         #
 | |
|         SupArchList = []
 | |
|         SupArchDict = {}
 | |
|         PcdTypeItem = ''
 | |
|         for (PcdTypeItem1, ArchItem, LineNo) in KeysList:
 | |
|             SupArchList, SupArchDict = ValidateArch(ArchItem, PcdTypeItem1, LineNo, SupArchDict, SupArchList)
 | |
|              
 | |
|             #
 | |
|             # Validate PcdType
 | |
|             #
 | |
|             if (PcdTypeItem1 == '' or PcdTypeItem1 == None):
 | |
|                 return False
 | |
|             else:
 | |
|                 if not IsValidPcdType(PcdTypeItem1):
 | |
|                     Logger.Error("InfParser", 
 | |
|                                  ToolError.FORMAT_INVALID, 
 | |
|                                  ST.ERR_INF_PARSER_PCD_SECTION_TYPE_ERROR%(DT.PCD_USAGE_TYPE_LIST_OF_MODULE),
 | |
|                                  File=GlobalData.gINF_MODULE_NAME, 
 | |
|                                  Line=LineNo, 
 | |
|                                  ExtraData=PcdTypeItem1)
 | |
|                     return False
 | |
|             
 | |
|             PcdTypeItem = PcdTypeItem1
 | |
|             
 | |
|             for PcdItem in PcdContent:
 | |
|                 PcdItemObj = InfPcdItem()
 | |
|                 CommentList = PcdItem[1]
 | |
|                 CurrentLineOfPcdItem = PcdItem[2]
 | |
|                 PcdItem = PcdItem[0]
 | |
|                 
 | |
|                 if CommentList != None and len(CommentList) != 0:
 | |
|                     PcdItemObj = ParsePcdComment(CommentList, PcdTypeItem, PcdItemObj)
 | |
|                 else:
 | |
|                     CommentItemIns = InfPcdItemCommentContent()
 | |
|                     CommentItemIns.SetUsageItem(DT.ITEM_UNDEFINED)
 | |
|                     PcdItemObj.SetHelpStringList([CommentItemIns])
 | |
|                 
 | |
|                 if len(PcdItem) >= 1 and len(PcdItem) <= 3:
 | |
|                     PcdItemObj = SetPcdName(PcdItem, CurrentLineOfPcdItem, PcdItemObj)
 | |
|                     
 | |
|                 if len(PcdItem) >= 2 and len(PcdItem) <= 3:
 | |
|                     #
 | |
|                     # Contain PcdName and Value, validate value.
 | |
|                     #
 | |
|                     if IsValidPcdValue(PcdItem[1]) or PcdItem[1].strip() == "":
 | |
|                         PcdItemObj.SetDefaultValue(PcdItem[1])
 | |
|                     else:
 | |
|                         Logger.Error("InfParser", 
 | |
|                                      ToolError.FORMAT_INVALID, 
 | |
|                                      ST.ERR_INF_PARSER_PCD_VALUE_INVALID,
 | |
|                                      File=CurrentLineOfPcdItem[2], 
 | |
|                                      Line=CurrentLineOfPcdItem[1], 
 | |
|                                      ExtraData=PcdItem[1])
 | |
|                 
 | |
|                 if len(PcdItem) == 3:
 | |
|                     #
 | |
|                     # Contain PcdName, value, and FeatureFlag express
 | |
|                     #
 | |
|                     #
 | |
|                     # Validate Feature Flag Express
 | |
|                     #
 | |
|                     if PcdItem[2].strip() == '':
 | |
|                         Logger.Error("InfParser", 
 | |
|                                      ToolError.FORMAT_INVALID, 
 | |
|                                      ST.ERR_INF_PARSER_FEATURE_FLAG_EXP_MISSING,
 | |
|                                      File=CurrentLineOfPcdItem[2], 
 | |
|                                      Line=CurrentLineOfPcdItem[1], 
 | |
|                                      ExtraData=CurrentLineOfPcdItem[0])
 | |
|                     #
 | |
|                     # Validate FFE    
 | |
|                     #
 | |
|                     FeatureFlagRtv = IsValidFeatureFlagExp(PcdItem[2].strip())
 | |
|                     if not FeatureFlagRtv[0]:
 | |
|                         Logger.Error("InfParser", 
 | |
|                                      ToolError.FORMAT_INVALID, 
 | |
|                                      ST.ERR_INF_PARSER_FEATURE_FLAG_EXP_SYNTAX_INVLID%(FeatureFlagRtv[1]),
 | |
|                                      File=CurrentLineOfPcdItem[2], 
 | |
|                                      Line=CurrentLineOfPcdItem[1], 
 | |
|                                      ExtraData=CurrentLineOfPcdItem[0])
 | |
|                     PcdItemObj.SetFeatureFlagExp(PcdItem[2])
 | |
|                 
 | |
|                 if len(PcdItem) < 1 or len(PcdItem) > 3:
 | |
|                     Logger.Error("InfParser", 
 | |
|                                  ToolError.FORMAT_INVALID, 
 | |
|                                  ST.ERR_INF_PARSER_PCD_SECTION_CONTENT_ERROR,
 | |
|                                  File=CurrentLineOfPcdItem[2], 
 | |
|                                  Line=CurrentLineOfPcdItem[1], 
 | |
|                                  ExtraData=CurrentLineOfPcdItem[0])
 | |
|                     return False       
 | |
|                 
 | |
|                 if PcdTypeItem.upper != DT.TAB_INF_FEATURE_PCD.upper():
 | |
|                     PcdItemObj.SetSupportArchList(SupArchDict[PcdTypeItem])
 | |
|                 else:
 | |
|                     PcdItemObj.SetSupportArchList(SupArchList)
 | |
|                 
 | |
|                 if self.Pcds.has_key((PcdTypeItem, PcdItemObj)):           
 | |
|                     PcdsList = self.Pcds[PcdTypeItem, PcdItemObj]
 | |
|                     PcdsList.append(PcdItemObj)
 | |
|                     self.Pcds[PcdTypeItem, PcdItemObj] = PcdsList
 | |
|                 else:
 | |
|                     PcdsList = []
 | |
|                     PcdsList.append(PcdItemObj)
 | |
|                     self.Pcds[PcdTypeItem, PcdItemObj] = PcdsList
 | |
|             
 | |
|         return True
 | |
|     
 | |
|     def SetAsBuildPcds(self, PcdContent, KeysList = None, PackageInfo = None):
 | |
|         for PcdItem in PcdContent:
 | |
|             PcdItemObj = InfPcdItem()
 | |
|             CommentList = PcdItem[1]
 | |
|             CurrentLineOfPcdItem = PcdItem[2]
 | |
|             PcdItem = PcdItem[0]
 | |
|             CommentString = ''
 | |
|             for CommmentLine in CommentList:
 | |
|                 CommentString += GetHelpStringByRemoveHashKey(CommmentLine)
 | |
|             
 | |
|             PcdItemObj.SetHelpStringList(CommentString)
 | |
|             PcdItemObj.SetItemType(KeysList[0][0])
 | |
|             #
 | |
|             # Set PcdTokenSpaceCName and CName
 | |
|             #
 | |
|             PcdItemObj = SetPcdName(PcdItem, CurrentLineOfPcdItem, PcdItemObj)           
 | |
|             #
 | |
|             # Set Value/DatumType/MaxDatumSize/Token
 | |
|             #
 | |
|             PcdItemObj = SetValueDatumTypeMaxSizeToken(PcdItem, 
 | |
|                                                       CurrentLineOfPcdItem, 
 | |
|                                                       PcdItemObj,
 | |
|                                                       KeysList[0][1],
 | |
|                                                       PackageInfo)
 | |
|         
 | |
|             PcdTypeItem = KeysList[0][0]
 | |
|             if self.Pcds.has_key((PcdTypeItem, PcdItemObj)):           
 | |
|                 PcdsList = self.Pcds[PcdTypeItem, PcdItemObj]
 | |
|                 PcdsList.append(PcdItemObj)
 | |
|                 self.Pcds[PcdTypeItem, PcdItemObj] = PcdsList
 | |
|             else:
 | |
|                 PcdsList = []
 | |
|                 PcdsList.append(PcdItemObj)
 | |
|                 self.Pcds[PcdTypeItem, PcdItemObj] = PcdsList            
 | |
|   
 | |
|     def GetPcds(self):
 | |
|         return self.Pcds
 | |
| 
 | |
| def ParserPcdInfoInDec(String):
 | |
|     ValueList = GetSplitValueList(String, DT.TAB_VALUE_SPLIT, 3)
 | |
|     
 | |
|     #
 | |
|     # DatumType, Token
 | |
|     #
 | |
|     return ValueList[2], ValueList[3]
 | |
| 
 | |
| def SetValueDatumTypeMaxSizeToken(PcdItem, CurrentLineOfPcdItem, PcdItemObj, Arch, PackageInfo = None):
 | |
|     #
 | |
|     # Package information not been generated currently, we need to parser INF file to get information. 
 | |
|     #
 | |
|     if not PackageInfo:
 | |
|         PackageInfo = []
 | |
|         InfFileName = CurrentLineOfPcdItem[2]
 | |
|         PackageInfoList = GetPackageListInfo(InfFileName, GlobalData.gWORKSPACE, -1)
 | |
|         for PackageInfoListItem in PackageInfoList:
 | |
|             PackageInfoIns = InfPackageItem()
 | |
|             PackageInfoIns.SetPackageName(PackageInfoListItem)
 | |
|             PackageInfo.append(PackageInfoIns)
 | |
| 
 | |
|     PcdInfoInDecHasFound = False
 | |
|     for PackageItem in PackageInfo:
 | |
|         if PcdInfoInDecHasFound:
 | |
|             break
 | |
|         PackageName = PackageItem.PackageName
 | |
|         #
 | |
|         # Open DEC file to get information
 | |
|         #
 | |
|         FullFileName = os.path.normpath(os.path.realpath(os.path.join(GlobalData.gWORKSPACE, PackageName)))
 | |
|         
 | |
|         DecParser = Dec(FullFileName)
 | |
|         #
 | |
|         # Find PCD information.               
 | |
|         #
 | |
|         DecPcdsDict = DecParser.GetPcdSectionObject().ValueDict
 | |
|         for Key in DecPcdsDict.keys():
 | |
|             if (Key[0] == 'PCDSDYNAMICEX' and PcdItemObj.GetItemType() == 'PcdEx') and \
 | |
|                 (Key[1] == 'COMMON' or Key[1] == Arch):
 | |
|                 for PcdInDec in DecPcdsDict[Key]:
 | |
|                     if PcdInDec.TokenCName == PcdItemObj.CName and \
 | |
|                        PcdInDec.TokenSpaceGuidCName == PcdItemObj.TokenSpaceGuidCName:
 | |
|                         PcdItemObj.SetToken(PcdInDec.TokenValue)
 | |
|                         PcdItemObj.SetDatumType(PcdInDec.DatumType)
 | |
|                         PcdItemObj.SetSupportArchList([Arch])
 | |
|                         
 | |
|             if (Key[0] == 'PCDSPATCHABLEINMODULE' and PcdItemObj.GetItemType() == 'PatchPcd') and \
 | |
|            (Key[1] == 'COMMON' or Key[1] == Arch):
 | |
|                 for PcdInDec in DecPcdsDict[Key]:
 | |
|                     if PcdInDec.TokenCName == PcdItemObj.CName and \
 | |
|                        PcdInDec.TokenSpaceGuidCName == PcdItemObj.TokenSpaceGuidCName:
 | |
|                         PcdItemObj.SetToken(PcdInDec.TokenValue)
 | |
|                         PcdItemObj.SetDatumType(PcdInDec.DatumType)
 | |
|                         PcdItemObj.SetSupportArchList([Arch]) 
 | |
|         
 | |
|         if PcdItemObj.GetDatumType() == 'VOID*':
 | |
|             PcdItemObj.SetMaxDatumSize('%s'%(len(GetSplitValueList(PcdItem[1], DT.TAB_COMMA_SPLIT))))
 | |
|                                                                      
 | |
|         DecGuidsDict = DecParser.GetGuidSectionObject().ValueDict
 | |
|         for Key in DecGuidsDict.keys():
 | |
|             if Key == 'COMMON' or Key == Arch:
 | |
|                 for GuidInDec in DecGuidsDict[Key]:
 | |
|                     if GuidInDec.GuidCName == PcdItemObj.TokenSpaceGuidCName:
 | |
|                         PcdItemObj.SetTokenSpaceGuidValue(GuidInDec.GuidString)
 | |
| 
 | |
|     #
 | |
|     # Validate Value.
 | |
|     #
 | |
|     if ValidatePcdValueOnDatumType(PcdItem[1], PcdItemObj.GetDatumType()):         
 | |
|         PcdItemObj.SetDefaultValue(PcdItem[1])
 | |
|     else:
 | |
|         Logger.Error("InfParser", 
 | |
|                      ToolError.FORMAT_INVALID, 
 | |
|                      ST.ERR_ASBUILD_PCD_VALUE_INVALID%("\"" + PcdItem[1] + "\"", "\"" + 
 | |
|                                                        PcdItemObj.GetDatumType() + "\""),
 | |
|                      File=CurrentLineOfPcdItem[2], 
 | |
|                      Line=CurrentLineOfPcdItem[1], 
 | |
|                      ExtraData=CurrentLineOfPcdItem[0])                
 | |
|     #
 | |
|     # validate offset
 | |
|     #
 | |
|     if PcdItemObj.GetItemType().upper() == DT.TAB_INF_PATCH_PCD.upper():
 | |
|         if not IsHexDigitUINT32(PcdItem[2]):
 | |
|             Logger.Error("InfParser", 
 | |
|                          ToolError.FORMAT_INVALID, 
 | |
|                          ST.ERR_ASBUILD_PCD_OFFSET_FORMAT_INVALID%("\"" + PcdItem[2] + "\""),
 | |
|                          File=CurrentLineOfPcdItem[2], 
 | |
|                          Line=CurrentLineOfPcdItem[1], 
 | |
|                          ExtraData=CurrentLineOfPcdItem[0])            
 | |
|         PcdItemObj.SetOffset(PcdItem[2])
 | |
|         
 | |
|     if PcdItemObj.GetToken() == '' or PcdItemObj.GetDatumType() == '':
 | |
|         Logger.Error("InfParser", 
 | |
|                      ToolError.FORMAT_INVALID, 
 | |
|                      ST.ERR_ASBUILD_PCD_DECLARITION_MISS%("\"" + PcdItem[0] + "\""),
 | |
|                      File=CurrentLineOfPcdItem[2], 
 | |
|                      Line=CurrentLineOfPcdItem[1], 
 | |
|                      ExtraData=CurrentLineOfPcdItem[0])
 | |
|         
 | |
|     return PcdItemObj
 | |
| 
 | |
| def ValidatePcdValueOnDatumType(Value, Type):
 | |
|     
 | |
|     Value = Value.strip()
 | |
|     #
 | |
|     # Boolean type only allow 0x00 or 0x01 as value per INF spec
 | |
|     #
 | |
|     if Type == 'BOOLEAN':
 | |
|         if not (Value == '0x00' or Value == '0x01'):
 | |
|             return False    
 | |
|     elif Type == 'VOID*':
 | |
|         if not Value.startswith("{"):
 | |
|             return False
 | |
|         if not Value.endswith("}"):
 | |
|             return False
 | |
|         #
 | |
|         # Strip "{" at head and "}" at tail.
 | |
|         #
 | |
|         Value = Value[1:-1] 
 | |
|         ValueList = GetSplitValueList(Value, DT.TAB_COMMA_SPLIT)
 | |
|         
 | |
|         ReIsValidHexByte = re.compile("^0x[0-9a-f]{1,2}$", re.IGNORECASE)
 | |
|         for ValueItem in ValueList:
 | |
|             if not ReIsValidHexByte.match(ValueItem):
 | |
|                 return False
 | |
|         
 | |
|     elif Type == 'UINT8' or Type == 'UINT16' or Type == 'UINT32' or Type == 'UINT64':
 | |
|         
 | |
|         ReIsValidUint8z = re.compile('^0[x|X][a-fA-F0-9]{2}$')
 | |
|         ReIsValidUint16z = re.compile('^0[x|X][a-fA-F0-9]{4}$')
 | |
|         ReIsValidUint32z = re.compile('^0[x|X][a-fA-F0-9]{8}$')
 | |
|         ReIsValidUint64z = re.compile('^0[x|X][a-fA-F0-9]{16}$')
 | |
|         
 | |
|         if not ReIsValidUint8z.match(Value) and Type == 'UINT8':
 | |
|             return False  
 | |
|         elif not ReIsValidUint16z.match(Value) and  Type == 'UINT16':
 | |
|             return False
 | |
|         elif not ReIsValidUint32z.match(Value) and  Type == 'UINT32':
 | |
|             return False
 | |
|         elif not ReIsValidUint64z.match(Value) and  Type == 'UINT64':
 | |
|             return False
 | |
|     else:
 | |
|         #
 | |
|         # Since we assume the DEC file always correct, should never go to here.
 | |
|         #
 | |
|         pass
 | |
|     
 | |
|     return True    
 | |
|  
 | |
| def SetPcdName(PcdItem, CurrentLineOfPcdItem, PcdItemObj):
 | |
|     #
 | |
|     # Only PCD Name specified 
 | |
|     # <PcdName> ::= <TokenSpaceGuidCName> "." <TokenCName>
 | |
|     #
 | |
|     PcdId = GetSplitValueList(PcdItem[0], DT.TAB_SPLIT)
 | |
|     if len(PcdId) != 2:                       
 | |
|         Logger.Error("InfParser", 
 | |
|                      ToolError.FORMAT_INVALID, 
 | |
|                      ST.ERR_INF_PARSER_PCD_NAME_FORMAT_ERROR,
 | |
|                      File=CurrentLineOfPcdItem[2], 
 | |
|                      Line=CurrentLineOfPcdItem[1], 
 | |
|                      ExtraData=CurrentLineOfPcdItem[0])
 | |
|     else:
 | |
|         #
 | |
|         # Validate PcdTokenSpaceGuidCName
 | |
|         #
 | |
|         if not IsValidCVariableName(PcdId[0]):
 | |
|             Logger.Error("InfParser", 
 | |
|                          ToolError.FORMAT_INVALID, 
 | |
|                          ST.ERR_INF_PARSER_PCD_CVAR_GUID,
 | |
|                          File=CurrentLineOfPcdItem[2], 
 | |
|                          Line=CurrentLineOfPcdItem[1], 
 | |
|                          ExtraData=PcdId[0])
 | |
|         if not IsValidCVariableName(PcdId[1]):
 | |
|             Logger.Error("InfParser", 
 | |
|                          ToolError.FORMAT_INVALID, 
 | |
|                          ST.ERR_INF_PARSER_PCD_CVAR_PCDCNAME,
 | |
|                          File=CurrentLineOfPcdItem[2], 
 | |
|                          Line=CurrentLineOfPcdItem[1], 
 | |
|                          ExtraData=PcdId[1])
 | |
|         PcdItemObj.SetTokenSpaceGuidCName(PcdId[0])
 | |
|         PcdItemObj.SetCName(PcdId[1])
 | |
|     
 | |
|     return PcdItemObj       |