From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received-SPF: Pass (sender SPF authorized) identity=mailfrom; client-ip=134.134.136.65; helo=mga03.intel.com; envelope-from=bob.c.feng@intel.com; receiver=edk2-devel@lists.01.org Received: from mga03.intel.com (mga03.intel.com [134.134.136.65]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by ml01.01.org (Postfix) with ESMTPS id 05F31203B8CE9 for ; Mon, 25 Jun 2018 02:43:53 -0700 (PDT) X-Amp-Result: SKIPPED(no attachment in message) X-Amp-File-Uploaded: False Received: from fmsmga007.fm.intel.com ([10.253.24.52]) by orsmga103.jf.intel.com with ESMTP/TLS/DHE-RSA-AES256-GCM-SHA384; 25 Jun 2018 02:43:53 -0700 X-ExtLoop1: 1 X-IronPort-AV: E=Sophos;i="5.51,269,1526367600"; d="scan'208";a="49681580" Received: from shwdeopenpsi105.ccr.corp.intel.com ([10.239.9.110]) by fmsmga007.fm.intel.com with ESMTP; 25 Jun 2018 02:43:51 -0700 From: BobCF To: edk2-devel@lists.01.org Cc: Bob Feng , Liming Gao Date: Mon, 25 Jun 2018 17:43:48 +0800 Message-Id: <20180625094348.203720-1-bob.c.feng@intel.com> X-Mailer: git-send-email 2.16.2.windows.1 Subject: [Patch] BaseTools: Enable structure pcd in FDF file X-BeenThere: edk2-devel@lists.01.org X-Mailman-Version: 2.1.26 Precedence: list List-Id: EDK II Development List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , X-List-Received-Date: Mon, 25 Jun 2018 09:43:54 -0000 Contributed-under: TianoCore Contribution Agreement 1.1 Signed-off-by: Bob Feng Cc: Liming Gao --- BaseTools/Source/Python/AutoGen/AutoGen.py | 3 +- BaseTools/Source/Python/AutoGen/GenC.py | 4 + BaseTools/Source/Python/GenFds/FdfParser.py | 81 ++++++++-- .../Source/Python/Workspace/BuildClassObject.py | 14 ++ BaseTools/Source/Python/Workspace/DscBuildData.py | 171 ++++++++++++++++++++- BaseTools/Source/Python/build/BuildReport.py | 3 + 6 files changed, 256 insertions(+), 20 deletions(-) diff --git a/BaseTools/Source/Python/AutoGen/AutoGen.py b/BaseTools/Source/Python/AutoGen/AutoGen.py index ed0be3bc74..e3f404bd6b 100644 --- a/BaseTools/Source/Python/AutoGen/AutoGen.py +++ b/BaseTools/Source/Python/AutoGen/AutoGen.py @@ -565,11 +565,11 @@ class WorkspaceAutoGen(AutoGen): for Pcd in Pkg.Pcds: DecPcds.add((Pcd[0], Pcd[1])) DecPcdsKey.add((Pcd[0], Pcd[1], Pcd[2])) Platform.SkuName = self.SkuId - for Name, Guid in PcdSet: + for Name, Guid,Fileds in PcdSet: if (Name, Guid) not in DecPcds: EdkLogger.error( 'build', PARSER_ERROR, "PCD (%s.%s) used in FDF is not declared in DEC files." % (Guid, Name), @@ -579,11 +579,10 @@ class WorkspaceAutoGen(AutoGen): else: # Check whether Dynamic or DynamicEx PCD used in FDF file. If used, build break and give a error message. if (Name, Guid, TAB_PCDS_FIXED_AT_BUILD) in DecPcdsKey \ or (Name, Guid, TAB_PCDS_PATCHABLE_IN_MODULE) in DecPcdsKey \ or (Name, Guid, TAB_PCDS_FEATURE_FLAG) in DecPcdsKey: - Platform.AddPcd(Name, Guid, PcdSet[Name, Guid]) continue elif (Name, Guid, TAB_PCDS_DYNAMIC) in DecPcdsKey or (Name, Guid, TAB_PCDS_DYNAMIC_EX) in DecPcdsKey: EdkLogger.error( 'build', PARSER_ERROR, diff --git a/BaseTools/Source/Python/AutoGen/GenC.py b/BaseTools/Source/Python/AutoGen/GenC.py index ae3af085a1..d186f399ba 100644 --- a/BaseTools/Source/Python/AutoGen/GenC.py +++ b/BaseTools/Source/Python/AutoGen/GenC.py @@ -888,10 +888,12 @@ def CreateModulePcdCode(Info, AutoGenC, AutoGenH, Pcd): FixPcdSizeTokenName = '_PCD_SIZE_' + TokenCName FixedPcdSizeVariableName = '_gPcd_FixedAtBuild_Size_' + TokenCName if Pcd.PcdValueFromComm: Pcd.DefaultValue = Pcd.PcdValueFromComm + elif Pcd.PcdValueFromFdf: + Pcd.DefaultValue = Pcd.PcdValueFromFdf if Pcd.Type in PCD_DYNAMIC_EX_TYPE_SET: TokenNumber = int(Pcd.TokenValue, 0) # Add TokenSpaceGuidValue value to PcdTokenName to discriminate the DynamicEx PCDs with # different Guids but same TokenCName @@ -1181,10 +1183,12 @@ def CreateLibraryPcdCode(Info, AutoGenC, AutoGenH, Pcd): PatchPcdMaxSizeVariable = '_gPcd_BinaryPatch_MaxSize_' + TokenCName FixedPcdSizeVariableName = '_gPcd_FixedAtBuild_Size_' + TokenCName if Pcd.PcdValueFromComm: Pcd.DefaultValue = Pcd.PcdValueFromComm + elif Pcd.PcdValueFromFdf: + Pcd.DefaultValue = Pcd.PcdValueFromFdf # # Write PCDs # if Pcd.Type in PCD_DYNAMIC_EX_TYPE_SET: TokenNumber = int(Pcd.TokenValue, 0) diff --git a/BaseTools/Source/Python/GenFds/FdfParser.py b/BaseTools/Source/Python/GenFds/FdfParser.py index 78cb049c61..a8a2e7d70e 100644 --- a/BaseTools/Source/Python/GenFds/FdfParser.py +++ b/BaseTools/Source/Python/GenFds/FdfParser.py @@ -80,17 +80,16 @@ T_CHAR_BACKSLASH, T_CHAR_DOUBLE_QUOTE, T_CHAR_SINGLE_QUOTE, T_CHAR_STAR, T_CHAR_ (' ', '\0', '\r', '\t', '\n', '/', '\\', '\"', '\'', '*', '#') SEPERATOR_TUPLE = ('=', '|', ',', '{', '}') RegionSizePattern = re.compile("\s*(?P(?:0x|0X)?[a-fA-F0-9]+)\s*\|\s*(?P(?:0x|0X)?[a-fA-F0-9]+)\s*") -RegionSizeGuidPattern = re.compile("\s*(?P\w+\.\w+)\s*\|\s*(?P\w+\.\w+)\s*") -RegionOffsetPcdPattern = re.compile("\s*(?P\w+\.\w+)\s*$") +RegionSizeGuidPattern = re.compile("\s*(?P\w+\.\w+[\.\w\[\]]*)\s*\|\s*(?P\w+\.\w+[\.\w\[\]]*)\s*") +RegionOffsetPcdPattern = re.compile("\s*(?P\w+\.\w+[\.\w\[\]]*)\s*$") ShortcutPcdPattern = re.compile("\s*\w+\s*=\s*(?P(?:0x|0X)?[a-fA-F0-9]+)\s*\|\s*(?P\w+\.\w+)\s*") BaseAddrValuePattern = re.compile('^0[xX][0-9a-fA-F]+') FileExtensionPattern = re.compile(r'([a-zA-Z][a-zA-Z0-9]*)') TokenFindPattern = re.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: @@ -223,12 +222,13 @@ class FileProfile : fsock.close() except: EdkLogger.error("FdfParser", FILE_OPEN_FAILURE, ExtraData=FileName) - + self.FileName = FileName self.PcdDict = {} + self.PcdLocalDict = {} self.InfList = [] self.InfDict = {'ArchTBD':[]} # ECC will use this Dict and List information self.PcdFileLineDict = {} self.InfFileLineList = [] @@ -784,21 +784,22 @@ class FdfParser: elif self.__Token == 'SET': if not self.__GetIfListCurrentItemStat(IfList): continue SetLine = self.CurrentLineNumber - 1 SetOffset = self.CurrentOffsetWithinLine - len('SET') - PcdPair = self.__GetNextPcdName() + PcdPair = self.__GetNextPcdSettings() PcdName = "%s.%s" % (PcdPair[1], PcdPair[0]) if not self.__IsToken( "="): raise Warning("expected '='", 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 ('!ifdef', '!ifndef', '!if'): @@ -1046,10 +1047,33 @@ class FdfParser: 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 == '[' 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 == '-' or TempChar == '[' or TempChar == ']': + self.__GetOneChar() + + else: + break + + self.__Token = self.__CurrentLine()[StartPos : self.CurrentOffsetWithinLine] + return True + + return False + ## __GetNextToken() method # # Get next token unit before a seperator # If found, the string value is put into self.__Token # @@ -1237,10 +1261,30 @@ class FdfParser: raise Warning("expected format of .", self.FileName, self.CurrentLineNumber) pcdCName = self.__Token return (pcdCName, pcdTokenSpaceCName) + def __GetNextPcdSettings(self): + if not self.__GetNextWord(): + raise Warning("expected format of .", self.FileName, self.CurrentLineNumber) + pcdTokenSpaceCName = self.__Token + + if not self.__IsToken( "."): + raise Warning("expected format of .", self.FileName, self.CurrentLineNumber) + + if not self.__GetNextWord(): + raise Warning("expected format of .", self.FileName, self.CurrentLineNumber) + pcdCName = self.__Token + + Fields = [] + while self.__IsToken("."): + if not self.__GetNextPcdWord(): + raise Warning("expected format of .", self.FileName, self.CurrentLineNumber) + Fields.append(self.__Token) + + return (pcdCName, pcdTokenSpaceCName,".".join(Fields)) + ## __GetStringData() method # # Get string contents quoted in "" # If found, the decimal data is put into self.__Token # @@ -1552,10 +1596,13 @@ class FdfParser: 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 @@ -1570,13 +1617,14 @@ class FdfParser: raise Warning("expected Hex base address", self.FileName, self.CurrentLineNumber) Obj.BaseAddress = self.__Token if self.__IsToken( "|"): - pcdPair = self.__GetNextPcdName() + 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"): @@ -1586,13 +1634,14 @@ class FdfParser: if not self.__GetNextHexNumber(): raise Warning("expected Hex size", self.FileName, self.CurrentLineNumber) Size = self.__Token if self.__IsToken( "|"): - pcdPair = self.__GetNextPcdName() + 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 = long(Size, 0) return True @@ -1679,13 +1728,14 @@ class FdfParser: raise Warning("expected Hex or Integer block size", self.FileName, self.CurrentLineNumber) BlockSize = self.__Token BlockSizePcd = None if self.__IsToken( "|"): - PcdPair = self.__GetNextPcdName() + 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 = long(BlockSize, 0) BlockNumber = None @@ -1762,21 +1812,22 @@ class FdfParser: # @retval True Successfully find # @retval False Not able to find # def __GetSetStatement(self, Obj): if self.__IsKeyword("SET"): - PcdPair = self.__GetNextPcdName() + PcdPair = self.__GetNextPcdSettings() if not self.__IsToken( "="): raise Warning("expected '='", 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 @@ -1849,18 +1900,20 @@ class FdfParser: # self.__UndoToken() IsRegionPcd = (RegionSizeGuidPattern.match(self.__CurrentLine()[self.CurrentOffsetWithinLine:]) or RegionOffsetPcdPattern.match(self.__CurrentLine()[self.CurrentOffsetWithinLine:])) if IsRegionPcd: - RegionObj.PcdOffset = self.__GetNextPcdName() + RegionObj.PcdOffset = self.__GetNextPcdSettings() self.Profile.PcdDict[RegionObj.PcdOffset] = "0x%08X" % (RegionObj.Offset + long(Fd.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( "|"): - RegionObj.PcdSize = self.__GetNextPcdName() + 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(): @@ -2594,11 +2647,11 @@ class FdfParser: 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.__GetNextPcdName() + PcdPair = self.__GetNextPcdSettings() if not self.__IsToken( ")"): raise Warning("expected ')'", self.FileName, self.CurrentLineNumber) self.__Token = 'PCD('+PcdPair[1]+'.'+PcdPair[0]+')' FfsFileObj.NameGuid = self.__Token @@ -3682,11 +3735,11 @@ class FdfParser: 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.__GetNextPcdName() + PcdPair = self.__GetNextPcdSettings() if not self.__IsToken( ")"): raise Warning("expected ')'", self.FileName, self.CurrentLineNumber) self.__Token = 'PCD('+PcdPair[1]+'.'+PcdPair[0]+')' NameGuid = self.__Token @@ -3956,11 +4009,11 @@ class FdfParser: self.__GetNextWord() if self.__Token == 'PCD': if not self.__IsToken( "("): raise Warning("expected '('", self.FileName, self.CurrentLineNumber) - PcdPair = self.__GetNextPcdName() + PcdPair = self.__GetNextPcdSettings() if not self.__IsToken( ")"): raise Warning("expected ')'", self.FileName, self.CurrentLineNumber) self.__Token = 'PCD('+PcdPair[1]+'.'+PcdPair[0]+')' EfiSectionObj.FileName = self.__Token diff --git a/BaseTools/Source/Python/Workspace/BuildClassObject.py b/BaseTools/Source/Python/Workspace/BuildClassObject.py index 209315d901..59b7f5fe20 100644 --- a/BaseTools/Source/Python/Workspace/BuildClassObject.py +++ b/BaseTools/Source/Python/Workspace/BuildClassObject.py @@ -68,18 +68,29 @@ class PcdClassObject(object): self.DscDefaultValue = None self.DscRawValue = None if IsDsc: self.DscDefaultValue = Value self.PcdValueFromComm = "" + self.PcdValueFromFdf = "" self.DefinitionPosition = ("","") ## Get the maximum number of bytes def GetPcdMaxSize(self): if self.DatumType in TAB_PCD_NUMERIC_TYPES: return MAX_SIZE_TYPE[self.DatumType] MaxSize = int(self.MaxDatumSize,10) if self.MaxDatumSize else 0 + if self.PcdValueFromFdf: + if self.PcdValueFromFdf.startswith("{") and self.PcdValueFromFdf.endswith("}"): + MaxSize = max([len(self.PcdValueFromFdf.split(",")),MaxSize]) + elif self.PcdValueFromFdf.startswith("\"") or self.PcdValueFromFdf.startswith("\'"): + MaxSize = max([len(self.PcdValueFromFdf)-2+1,MaxSize]) + elif self.PcdValueFromFdf.startswith("L\""): + MaxSize = max([2*(len(self.PcdValueFromFdf)-3+1),MaxSize]) + else: + MaxSize = max([len(self.PcdValueFromFdf),MaxSize]) + if self.PcdValueFromComm: if self.PcdValueFromComm.startswith("{") and self.PcdValueFromComm.endswith("}"): return max([len(self.PcdValueFromComm.split(",")),MaxSize]) elif self.PcdValueFromComm.startswith("\"") or self.PcdValueFromComm.startswith("\'"): return max([len(self.PcdValueFromComm)-2+1,MaxSize]) @@ -167,10 +178,11 @@ class StructurePcd(PcdClassObject): self.PcdDefineLineNo = 0 self.PkgPath = "" self.DefaultValueFromDec = "" self.ValueChain = set() self.PcdFieldValueFromComm = collections.OrderedDict() + self.PcdFieldValueFromFdf = collections.OrderedDict() def __repr__(self): return self.TypeName def AddDefaultValue (self, FieldName, Value, FileName="", LineNo=0): if FieldName in self.DefaultValues: @@ -214,10 +226,11 @@ class StructurePcd(PcdClassObject): self.validateranges = PcdObject.validateranges if PcdObject.validateranges else self.validateranges self.validlists = PcdObject.validlists if PcdObject.validlists else self.validlists self.expressions = PcdObject.expressions if PcdObject.expressions else self.expressions self.DscRawValue = PcdObject.DscRawValue if PcdObject.DscRawValue else self.DscRawValue self.PcdValueFromComm = PcdObject.PcdValueFromComm if PcdObject.PcdValueFromComm else self.PcdValueFromComm + self.PcdValueFromFdf = PcdObject.PcdValueFromFdf if PcdObject.PcdValueFromFdf else self.PcdValueFromFdf self.DefinitionPosition = PcdObject.DefinitionPosition if PcdObject.DefinitionPosition else self.DefinitionPosition if type(PcdObject) is StructurePcd: self.StructuredPcdIncludeFile = PcdObject.StructuredPcdIncludeFile if PcdObject.StructuredPcdIncludeFile else self.StructuredPcdIncludeFile self.PackageDecs = PcdObject.PackageDecs if PcdObject.PackageDecs else self.PackageDecs self.DefaultValues = PcdObject.DefaultValues if PcdObject.DefaultValues else self.DefaultValues @@ -229,10 +242,11 @@ class StructurePcd(PcdClassObject): self.StructName = PcdObject.DatumType if PcdObject.DatumType else self.StructName self.PcdDefineLineNo = PcdObject.PcdDefineLineNo if PcdObject.PcdDefineLineNo else self.PcdDefineLineNo self.PkgPath = PcdObject.PkgPath if PcdObject.PkgPath else self.PkgPath self.ValueChain = PcdObject.ValueChain if PcdObject.ValueChain else self.ValueChain self.PcdFieldValueFromComm = PcdObject.PcdFieldValueFromComm if PcdObject.PcdFieldValueFromComm else self.PcdFieldValueFromComm + self.PcdFieldValueFromFdf = PcdObject.PcdFieldValueFromFdf if PcdObject.PcdFieldValueFromFdf else self.PcdFieldValueFromFdf ## LibraryClassObject # # This Class defines LibraryClassObject used in BuildDatabase # diff --git a/BaseTools/Source/Python/Workspace/DscBuildData.py b/BaseTools/Source/Python/Workspace/DscBuildData.py index 1ed7eb1c2c..c3d40f7daf 100644 --- a/BaseTools/Source/Python/Workspace/DscBuildData.py +++ b/BaseTools/Source/Python/Workspace/DscBuildData.py @@ -1128,11 +1128,12 @@ class DscBuildData(PlatformBuildClassObject): self._Pcds.update(self._GetDynamicPcd(MODEL_PCD_DYNAMIC_EX_DEFAULT)) self._Pcds.update(self._GetDynamicHiiPcd(MODEL_PCD_DYNAMIC_EX_HII)) self._Pcds.update(self._GetDynamicVpdPcd(MODEL_PCD_DYNAMIC_EX_VPD)) self._Pcds = self.CompletePcdValues(self._Pcds) - self._Pcds = self.OverrideByFdfCommOverAll(self._Pcds) + self._Pcds = self.OverrideByFdfOverAll(self._Pcds) + self._Pcds = self.OverrideByCommOverAll(self._Pcds) self._Pcds = self.UpdateStructuredPcds(MODEL_PCD_TYPE_LIST, self._Pcds) self._Pcds = self.CompleteHiiPcdsDefaultStores(self._Pcds) self._Pcds = self._FilterPcdBySkuUsage(self._Pcds) self.RecoverCommandLinePcd() @@ -1188,11 +1189,38 @@ class DscBuildData(PlatformBuildClassObject): structure_pcd_data[(item[0],item[1])].append(item) return structure_pcd_data @staticmethod - def OverrideByFdfComm(StruPcds): + def OverrideByFdf(StruPcds,workspace): + if GlobalData.gFdfParser is None: + return StruPcds + StructurePcdInFdf = OrderedDict() + fdfpcd = GlobalData.gFdfParser.Profile.PcdDict + fdfpcdlocation = GlobalData.gFdfParser.Profile.PcdLocalDict + for item in fdfpcd : + if len(item[2]) and (item[0],item[1]) in StruPcds: + StructurePcdInFdf[(item[1],item[0],item[2] )] = fdfpcd[item] + GlobalPcds = {(item[0],item[1]) for item in StructurePcdInFdf} + for Pcd in StruPcds.values(): + if (Pcd.TokenSpaceGuidCName,Pcd.TokenCName) not in GlobalPcds: + continue + FieldValues = OrderedDict() + for item in StructurePcdInFdf: + if (Pcd.TokenSpaceGuidCName,Pcd.TokenCName) == (item[0],item[1]) and item[2]: + FieldValues[item[2]] = StructurePcdInFdf[item] + for field in FieldValues: + if field not in Pcd.PcdFieldValueFromFdf: + Pcd.PcdFieldValueFromFdf[field] = ["","",""] + Pcd.PcdFieldValueFromFdf[field][0] = FieldValues[field] + Pcd.PcdFieldValueFromFdf[field][1] = os.path.relpath(fdfpcdlocation[(Pcd.TokenCName,Pcd.TokenSpaceGuidCName,field)][0],workspace) + Pcd.PcdFieldValueFromFdf[field][2] = fdfpcdlocation[(Pcd.TokenCName,Pcd.TokenSpaceGuidCName,field)][1] + + return StruPcds + + @staticmethod + def OverrideByComm(StruPcds): StructurePcdInCom = OrderedDict() for item in GlobalData.BuildOptionPcd: if len(item) == 5 and (item[1],item[0]) in StruPcds: StructurePcdInCom[(item[0],item[1],item[2] )] = (item[3],item[4]) GlobalPcds = {(item[0],item[1]) for item in StructurePcdInCom} @@ -1209,11 +1237,11 @@ class DscBuildData(PlatformBuildClassObject): Pcd.PcdFieldValueFromComm[field][0] = FieldValues[field][0] Pcd.PcdFieldValueFromComm[field][1] = FieldValues[field][1][0] Pcd.PcdFieldValueFromComm[field][2] = FieldValues[field][1][1] return StruPcds - def OverrideByFdfCommOverAll(self,AllPcds): + def OverrideByCommOverAll(self,AllPcds): def CheckStructureInComm(commpcds): if not commpcds: return False if len(commpcds[0]) == 5: return True @@ -1256,10 +1284,54 @@ class DscBuildData(PlatformBuildClassObject): self._PCD_TYPE_STRING_[MODEL_PCD_PATCHABLE_IN_MODULE], self._PCD_TYPE_STRING_[MODEL_PCD_FEATURE_FLAG]]: self.Pcds[Name, Guid] = copy.deepcopy(PcdInDec) self.Pcds[Name, Guid].DefaultValue = NoFiledValues[( Guid,Name)][0] return AllPcds + + def OverrideByFdfOverAll(self,AllPcds): + + if GlobalData.gFdfParser is None: + return + NoFiledValues = GlobalData.gFdfParser.Profile.PcdDict + for Guid,Name,Field in NoFiledValues: + if len(Field): + continue + Value = NoFiledValues[(Guid,Name,Field)] + if (Name,Guid) in AllPcds: + Pcd = AllPcds.get((Name,Guid)) + if isinstance(self._DecPcds.get((Pcd.TokenCName,Pcd.TokenSpaceGuidCName), None),StructurePcd): + self._DecPcds.get((Pcd.TokenCName,Pcd.TokenSpaceGuidCName)).PcdValueFromComm = Value + else: + Pcd.PcdValueFromComm = Value + Pcd.DefaultValue = Value + for sku in Pcd.SkuInfoList: + SkuInfo = Pcd.SkuInfoList[sku] + if SkuInfo.DefaultValue: + SkuInfo.DefaultValue = Value + else: + SkuInfo.HiiDefaultValue = Value + for defaultstore in SkuInfo.DefaultStoreDict: + SkuInfo.DefaultStoreDict[defaultstore] = Value + if Pcd.Type in [self._PCD_TYPE_STRING_[MODEL_PCD_DYNAMIC_EX_HII], self._PCD_TYPE_STRING_[MODEL_PCD_DYNAMIC_HII]]: + if Pcd.DatumType == TAB_VOID: + if not Pcd.MaxDatumSize: + Pcd.MaxDatumSize = '0' + CurrentSize = int(Pcd.MaxDatumSize,16) if Pcd.MaxDatumSize.upper().startswith("0X") else int(Pcd.MaxDatumSize) + OptionSize = len((StringToArray(Pcd.PcdValueFromComm)).split(",")) + MaxSize = max(CurrentSize, OptionSize) + Pcd.MaxDatumSize = str(MaxSize) + else: + PcdInDec = self.DecPcds.get((Name,Guid)) + if PcdInDec: + PcdInDec.PcdValueFromComm = Value + if PcdInDec.Type in [self._PCD_TYPE_STRING_[MODEL_PCD_FIXED_AT_BUILD], + self._PCD_TYPE_STRING_[MODEL_PCD_PATCHABLE_IN_MODULE], + self._PCD_TYPE_STRING_[MODEL_PCD_FEATURE_FLAG]]: + self.Pcds[Name, Guid] = copy.deepcopy(PcdInDec) + self.Pcds[Name, Guid].DefaultValue = Value + return AllPcds + def UpdateStructuredPcds(self, TypeList, AllPcds): DynamicPcdType = [self._PCD_TYPE_STRING_[MODEL_PCD_DYNAMIC_DEFAULT], self._PCD_TYPE_STRING_[MODEL_PCD_DYNAMIC_HII], self._PCD_TYPE_STRING_[MODEL_PCD_DYNAMIC_VPD], @@ -1365,11 +1437,12 @@ class DscBuildData(PlatformBuildClassObject): for defaultstoreid in DefaultStores: if defaultstoreid not in stru_pcd.SkuOverrideValues[skuid]: stru_pcd.SkuOverrideValues[skuid][defaultstoreid] = copy.deepcopy(stru_pcd.SkuOverrideValues[nextskuid][mindefaultstorename]) stru_pcd.ValueChain.add((skuid,defaultstoreid)) - S_pcd_set = DscBuildData.OverrideByFdfComm(S_pcd_set) + S_pcd_set = DscBuildData.OverrideByFdf(S_pcd_set,self.WorkspaceDir) + S_pcd_set = DscBuildData.OverrideByComm(S_pcd_set) Str_Pcd_Values = self.GenerateByteArrayValue(S_pcd_set) if Str_Pcd_Values: for (skuname,StoreName,PcdGuid,PcdName,PcdValue) in Str_Pcd_Values: str_pcd_obj = S_pcd_set.get((PcdName, PcdGuid)) if str_pcd_obj is None: @@ -1591,10 +1664,34 @@ class DscBuildData(PlatformBuildClassObject): FieldName = FieldName.split(']', 1)[1] FieldName = NewFieldName + FieldName while '[' in FieldName: FieldName = FieldName.rsplit('[', 1)[0] CApp = CApp + ' __FLEXIBLE_SIZE(*Size, %s, %s, %d); // From %s Line %d Value %s \n' % (Pcd.DatumType, FieldName.strip("."), ArrayIndex + 1, FieldList[FieldName_ori][1], FieldList[FieldName_ori][2], FieldList[FieldName_ori][0]) + if Pcd.PcdFieldValueFromFdf: + CApp = CApp + "// From fdf \n" + for FieldName in Pcd.PcdFieldValueFromFdf: + FieldName = "." + FieldName + IsArray = IsFieldValueAnArray(Pcd.PcdFieldValueFromFdf[FieldName.strip(".")][0]) + if IsArray and not (Pcd.PcdFieldValueFromFdf[FieldName.strip(".")][0].startswith('{GUID') and Pcd.PcdFieldValueFromFdf[FieldName.strip(".")][0].endswith('}')): + try: + Value = ValueExpressionEx(Pcd.PcdFieldValueFromFdf[FieldName.strip(".")][0], TAB_VOID, self._GuidDict)(True) + except BadExpression: + EdkLogger.error('Build', FORMAT_INVALID, "Invalid value format for %s. From %s Line %d " % + (".".join((Pcd.TokenSpaceGuidCName, Pcd.TokenCName, FieldName.strip('.'))), Pcd.PcdFieldValueFromFdf[FieldName.strip(".")][1], Pcd.PcdFieldValueFromFdf[FieldName.strip(".")][2])) + Value, ValueSize = ParseFieldValue(Value) + CApp = CApp + ' __FLEXIBLE_SIZE(*Size, %s, %s, %d / __ARRAY_ELEMENT_SIZE(%s, %s) + ((%d %% __ARRAY_ELEMENT_SIZE(%s, %s)) ? 1 : 0)); // From %s Line %d Value %s\n' % (Pcd.DatumType, FieldName.strip("."), ValueSize, Pcd.DatumType, FieldName.strip("."), ValueSize, Pcd.DatumType, FieldName.strip("."), Pcd.PcdFieldValueFromFdf[FieldName.strip(".")][1], Pcd.PcdFieldValueFromFdf[FieldName.strip(".")][2], Pcd.PcdFieldValueFromFdf[FieldName.strip(".")][0]); + else: + NewFieldName = '' + FieldName_ori = FieldName.strip('.') + while '[' in FieldName: + NewFieldName = NewFieldName + FieldName.split('[', 1)[0] + '[0]' + ArrayIndex = int(FieldName.split('[', 1)[1].split(']', 1)[0]) + FieldName = FieldName.split(']', 1)[1] + FieldName = NewFieldName + FieldName + while '[' in FieldName: + FieldName = FieldName.rsplit('[', 1)[0] + CApp = CApp + ' __FLEXIBLE_SIZE(*Size, %s, %s, %d); // From %s Line %s Value %s \n' % (Pcd.DatumType, FieldName.strip("."), ArrayIndex + 1, Pcd.PcdFieldValueFromFdf[FieldName_ori][1], Pcd.PcdFieldValueFromFdf[FieldName_ori][2], Pcd.PcdFieldValueFromFdf[FieldName_ori][0]) if Pcd.PcdFieldValueFromComm: CApp = CApp + "// From Command Line \n" for FieldName in Pcd.PcdFieldValueFromComm: FieldName = "." + FieldName IsArray = IsFieldValueAnArray(Pcd.PcdFieldValueFromComm[FieldName.strip(".")][0]) @@ -1832,10 +1929,74 @@ class DscBuildData(PlatformBuildClassObject): @staticmethod def GenerateCommandLineValueStatement(Pcd): CApp = ' Assign_%s_%s_CommandLine_Value(Pcd);\n' % (Pcd.TokenSpaceGuidCName, Pcd.TokenCName) return CApp + def GenerateFdfValue(self,Pcd): + CApp = "// Value in Fdf\n" + CApp = CApp + "void Assign_%s_%s_Fdf_Value(%s *Pcd){\n" % (Pcd.TokenSpaceGuidCName, Pcd.TokenCName,Pcd.DatumType) + CApp = CApp + ' UINT32 FieldSize;\n' + CApp = CApp + ' CHAR8 *Value;\n' + + pcddefaultvalue = Pcd.PcdValueFromFdf + for FieldList in [pcddefaultvalue,Pcd.PcdFieldValueFromFdf]: + if not FieldList: + continue + if pcddefaultvalue and FieldList == pcddefaultvalue: + IsArray = IsFieldValueAnArray(FieldList) + if IsArray: + try: + FieldList = ValueExpressionEx(FieldList, TAB_VOID)(True) + except BadExpression: + EdkLogger.error("Build", FORMAT_INVALID, "Invalid value format for %s.%s, from Fdf: %s" % + (Pcd.TokenSpaceGuidCName, Pcd.TokenCName, FieldList)) + Value, ValueSize = ParseFieldValue (FieldList) + + if isinstance(Value, str): + CApp = CApp + ' Pcd = %s; // From Fdf \n' % (Value) + elif IsArray: + # + # Use memcpy() to copy value into field + # + CApp = CApp + ' Value = %s; // From Fdf .\n' % (DscBuildData.IntToCString(Value, ValueSize)) + CApp = CApp + ' memcpy (Pcd, Value, %d);\n' % (ValueSize) + continue + for FieldName in FieldList: + IsArray = IsFieldValueAnArray(FieldList[FieldName][0]) + if IsArray: + try: + FieldList[FieldName][0] = ValueExpressionEx(FieldList[FieldName][0], TAB_VOID, self._GuidDict)(True) + except BadExpression: + EdkLogger.error('Build', FORMAT_INVALID, "Invalid value format for %s. From %s Line %d " % + (".".join((Pcd.TokenSpaceGuidCName, Pcd.TokenCName, FieldName)), FieldList[FieldName][1], FieldList[FieldName][2])) + except: + print "error" + try: + Value, ValueSize = ParseFieldValue (FieldList[FieldName][0]) + except Exception: + EdkLogger.error('Build', FORMAT_INVALID, "Invalid value format for %s. From %s Line %d " % (".".join((Pcd.TokenSpaceGuidCName,Pcd.TokenCName,FieldName)),FieldList[FieldName][1], FieldList[FieldName][2])) + if isinstance(Value, str): + CApp = CApp + ' Pcd->%s = %s; // From %s Line %d Value %s\n' % (FieldName, Value, FieldList[FieldName][1], FieldList[FieldName][2], FieldList[FieldName][0]) + elif IsArray: + # + # Use memcpy() to copy value into field + # + CApp = CApp + ' FieldSize = __FIELD_SIZE(%s, %s);\n' % (Pcd.DatumType, FieldName) + CApp = CApp + ' Value = %s; // From %s Line %d Value %s\n' % (DscBuildData.IntToCString(Value, ValueSize), FieldList[FieldName][1], FieldList[FieldName][2], FieldList[FieldName][0]) + CApp = CApp + ' memcpy (&Pcd->%s, Value, (FieldSize > 0 && FieldSize < %d) ? FieldSize : %d);\n' % (FieldName, ValueSize, ValueSize) + else: + if ValueSize > 4: + CApp = CApp + ' Pcd->%s = %dULL; // From %s Line %d Value %s\n' % (FieldName, Value, FieldList[FieldName][1], FieldList[FieldName][2], FieldList[FieldName][0]) + else: + CApp = CApp + ' Pcd->%s = %d; // From %s Line %s Value %s\n' % (FieldName, Value, FieldList[FieldName][1], FieldList[FieldName][2], FieldList[FieldName][0]) + CApp = CApp + "}\n" + return CApp + + @staticmethod + def GenerateFdfValueStatement(Pcd): + CApp = ' Assign_%s_%s_Fdf_Value(Pcd);\n' % (Pcd.TokenSpaceGuidCName, Pcd.TokenCName) + return CApp def GenerateInitializeFunc(self, SkuName, DefaultStore, Pcd, InitByteValue, CApp): OverrideValues = {DefaultStore:""} if Pcd.SkuOverrideValues: OverrideValues = Pcd.SkuOverrideValues[SkuName] @@ -1904,10 +2065,11 @@ class DscBuildData(PlatformBuildClassObject): if skuname == SkuName: break else: CApp = CApp + "// SkuName: %s, DefaultStoreName: STANDARD \n" % self.SkuIdMgr.SystemSkuId CApp = CApp + DscBuildData.GenerateInitValueStatement(Pcd,self.SkuIdMgr.SystemSkuId,TAB_DEFAULT_STORES_DEFAULT) + CApp = CApp + DscBuildData.GenerateFdfValueStatement(Pcd) CApp = CApp + DscBuildData.GenerateCommandLineValueStatement(Pcd) # # Set new PCD value and size # CApp = CApp + ' PcdSetPtr (%s, %s, %s, %s, Size, (UINT8 *)Pcd);\n' % (SkuName, DefaultStoreName, Pcd.TokenSpaceGuidCName, Pcd.TokenCName) @@ -1940,10 +2102,11 @@ class DscBuildData(PlatformBuildClassObject): CApp = CApp + '\n' for PcdName in StructuredPcds: Pcd = StructuredPcds[PcdName] CApp = CApp + self.GenerateSizeFunction(Pcd) CApp = CApp + self.GenerateDefaultValueAssignFunction(Pcd) + CApp = CApp + self.GenerateFdfValue(Pcd) CApp = CApp + self.GenerateCommandLineValue(Pcd) if not Pcd.SkuOverrideValues or Pcd.Type in [self._PCD_TYPE_STRING_[MODEL_PCD_FIXED_AT_BUILD], self._PCD_TYPE_STRING_[MODEL_PCD_PATCHABLE_IN_MODULE]]: CApp = CApp + self.GenerateInitValueFunction(Pcd,self.SkuIdMgr.SystemSkuId, TAB_DEFAULT_STORES_DEFAULT) else: diff --git a/BaseTools/Source/Python/build/BuildReport.py b/BaseTools/Source/Python/build/BuildReport.py index 324b6ff6aa..bc0b6e5d68 100644 --- a/BaseTools/Source/Python/build/BuildReport.py +++ b/BaseTools/Source/Python/build/BuildReport.py @@ -1329,10 +1329,13 @@ class PcdReport(object): OverrideFieldStruct = collections.OrderedDict() if OverrideStruct: for Key, Values in OverrideStruct.items(): if Values[1] and Values[1].endswith('.dsc'): OverrideFieldStruct[Key] = Values + if Pcd.PcdFieldValueFromFdf: + for Key, Values in Pcd.PcdFieldValueFromFdf.items(): + OverrideFieldStruct[Key] = Values if Pcd.PcdFieldValueFromComm: for Key, Values in Pcd.PcdFieldValueFromComm.items(): OverrideFieldStruct[Key] = Values return OverrideFieldStruct -- 2.16.2.windows.1