]> git.proxmox.com Git - mirror_edk2.git/blob - BaseTools/Source/Python/Workspace/DscBuildData.py
BaseTools: Remove unused logic for EDKI
[mirror_edk2.git] / BaseTools / Source / Python / Workspace / DscBuildData.py
1 ## @file
2 # This file is used to create a database used by build tool
3 #
4 # Copyright (c) 2008 - 2018, Intel Corporation. All rights reserved.<BR>
5 # (C) Copyright 2016 Hewlett Packard Enterprise Development LP<BR>
6 # This program and the accompanying materials
7 # are licensed and made available under the terms and conditions of the BSD License
8 # which accompanies this distribution. The full text of the license may be found at
9 # http://opensource.org/licenses/bsd-license.php
10 #
11 # THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
12 # WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
13 #
14
15 ## Platform build information from DSC file
16 #
17 # This class is used to retrieve information stored in database and convert them
18 # into PlatformBuildClassObject form for easier use for AutoGen.
19 #
20 from __future__ import print_function
21 from __future__ import absolute_import
22 from Common.StringUtils import *
23 from Common.DataType import *
24 from Common.Misc import *
25 from types import *
26 from Common.Expression import *
27 from CommonDataClass.CommonClass import SkuInfoClass
28 from Common.TargetTxtClassObject import TargetTxtClassObject
29 from Common.ToolDefClassObject import ToolDefClassObject
30 from .MetaDataTable import *
31 from .MetaFileTable import *
32 from .MetaFileParser import *
33
34 from .WorkspaceCommon import GetDeclaredPcd
35 from Common.Misc import AnalyzeDscPcd
36 from Common.Misc import ProcessDuplicatedInf,RemoveCComments
37 import re
38 from Common.Parsing import IsValidWord
39 from Common.VariableAttributes import VariableAttributes
40 import Common.GlobalData as GlobalData
41 import subprocess
42 from Common.Misc import SaveFileOnChange
43 from Workspace.BuildClassObject import PlatformBuildClassObject, StructurePcd, PcdClassObject, ModuleBuildClassObject
44 from collections import OrderedDict, defaultdict
45 from .BuildClassObject import ArrayIndex
46
47 PcdValueInitName = 'PcdValueInit'
48
49 PcdMainCHeader = '''
50 /**
51 DO NOT EDIT
52 FILE auto-generated
53 **/
54
55 #include <stdio.h>
56 #include <stdlib.h>
57 #include <string.h>
58 #include <PcdValueCommon.h>
59 '''
60
61 PcdMainCEntry = '''
62 int
63 main (
64 int argc,
65 char *argv[]
66 )
67 {
68 return PcdValueMain (argc, argv);
69 }
70 '''
71
72 PcdMakefileHeader = '''
73 #
74 # DO NOT EDIT
75 # This file is auto-generated by build utility
76 #
77
78 '''
79
80 WindowsCFLAGS = 'CFLAGS = $(CFLAGS) /wd4200 /wd4034 /wd4101 '
81 LinuxCFLAGS = 'BUILD_CFLAGS += -Wno-pointer-to-int-cast -Wno-unused-variable '
82 PcdMakefileEnd = '''
83 !INCLUDE $(BASE_TOOLS_PATH)\Source\C\Makefiles\ms.common
84
85 LIBS = $(LIB_PATH)\Common.lib
86
87 !INCLUDE $(BASE_TOOLS_PATH)\Source\C\Makefiles\ms.app
88 '''
89
90 AppTarget = '''
91 all: $(APPFILE)
92 $(APPFILE): $(OBJECTS)
93 %s
94 '''
95
96 PcdGccMakefile = '''
97 MAKEROOT ?= $(EDK_TOOLS_PATH)/Source/C
98 LIBS = -lCommon
99 '''
100
101 variablePattern = re.compile(r'[\t\s]*0[xX][a-fA-F0-9]+$')
102 SkuIdPattern = re.compile(r'^[a-zA-Z_][a-zA-Z0-9_]*$')
103 ## regular expressions for finding decimal and hex numbers
104 Pattern = re.compile('^[1-9]\d*|0$')
105 HexPattern = re.compile(r'0[xX][0-9a-fA-F]+$')
106 ## Regular expression for finding header file inclusions
107 from AutoGen.GenMake import gIncludePattern
108
109 ## Find dependencies for one source file
110 #
111 # By searching recursively "#include" directive in file, find out all the
112 # files needed by given source file. The dependecies will be only searched
113 # in given search path list.
114 #
115 # @param SearchPathList The list of search path
116 #
117 # @retval list The list of files the given source file depends on
118 #
119 def GetDependencyList(FileStack, SearchPathList):
120 DepDb = dict()
121 DependencySet = set(FileStack)
122 while len(FileStack) > 0:
123 F = FileStack.pop()
124 FullPathDependList = []
125 CurrentFileDependencyList = []
126 if F in DepDb:
127 CurrentFileDependencyList = DepDb[F]
128 else:
129 try:
130 Fd = open(F, 'r')
131 FileContent = Fd.read()
132 except BaseException as X:
133 EdkLogger.error("build", FILE_OPEN_FAILURE, ExtraData=F + "\n\t" + str(X))
134 finally:
135 if "Fd" in dir(locals()):
136 Fd.close()
137
138 if len(FileContent) == 0:
139 continue
140
141 if FileContent[0] == 0xff or FileContent[0] == 0xfe:
142 FileContent = unicode(FileContent, "utf-16")
143 IncludedFileList = gIncludePattern.findall(FileContent)
144
145 for Inc in IncludedFileList:
146 Inc = Inc.strip()
147 Inc = os.path.normpath(Inc)
148 CurrentFileDependencyList.append(Inc)
149 DepDb[F] = CurrentFileDependencyList
150
151 CurrentFilePath = os.path.dirname(F)
152 PathList = [CurrentFilePath] + SearchPathList
153 for Inc in CurrentFileDependencyList:
154 for SearchPath in PathList:
155 FilePath = os.path.join(SearchPath, Inc)
156 if not os.path.exists(FilePath):
157 continue
158 if FilePath not in DependencySet:
159 FileStack.append(FilePath)
160 FullPathDependList.append(FilePath)
161 break
162 DependencySet.update(FullPathDependList)
163 DependencyList = list(DependencySet) # remove duplicate ones
164
165 return DependencyList
166
167 class DscBuildData(PlatformBuildClassObject):
168 # dict used to convert PCD type in database to string used by build tool
169 _PCD_TYPE_STRING_ = {
170 MODEL_PCD_FIXED_AT_BUILD : TAB_PCDS_FIXED_AT_BUILD,
171 MODEL_PCD_PATCHABLE_IN_MODULE : TAB_PCDS_PATCHABLE_IN_MODULE,
172 MODEL_PCD_FEATURE_FLAG : TAB_PCDS_FEATURE_FLAG,
173 MODEL_PCD_DYNAMIC : TAB_PCDS_DYNAMIC,
174 MODEL_PCD_DYNAMIC_DEFAULT : TAB_PCDS_DYNAMIC,
175 MODEL_PCD_DYNAMIC_HII : TAB_PCDS_DYNAMIC_HII,
176 MODEL_PCD_DYNAMIC_VPD : TAB_PCDS_DYNAMIC_VPD,
177 MODEL_PCD_DYNAMIC_EX : TAB_PCDS_DYNAMIC_EX,
178 MODEL_PCD_DYNAMIC_EX_DEFAULT : TAB_PCDS_DYNAMIC_EX,
179 MODEL_PCD_DYNAMIC_EX_HII : TAB_PCDS_DYNAMIC_EX_HII,
180 MODEL_PCD_DYNAMIC_EX_VPD : TAB_PCDS_DYNAMIC_EX_VPD,
181 }
182
183 # dict used to convert part of [Defines] to members of DscBuildData directly
184 _PROPERTY_ = {
185 #
186 # Required Fields
187 #
188 TAB_DSC_DEFINES_PLATFORM_NAME : "_PlatformName",
189 TAB_DSC_DEFINES_PLATFORM_GUID : "_Guid",
190 TAB_DSC_DEFINES_PLATFORM_VERSION : "_Version",
191 TAB_DSC_DEFINES_DSC_SPECIFICATION : "_DscSpecification",
192 # TAB_DSC_DEFINES_OUTPUT_DIRECTORY : "_OutputDirectory",
193 # TAB_DSC_DEFINES_SUPPORTED_ARCHITECTURES : "_SupArchList",
194 # TAB_DSC_DEFINES_BUILD_TARGETS : "_BuildTargets",
195 TAB_DSC_DEFINES_SKUID_IDENTIFIER : "_SkuName",
196 # TAB_DSC_DEFINES_FLASH_DEFINITION : "_FlashDefinition",
197 TAB_DSC_DEFINES_BUILD_NUMBER : "_BuildNumber",
198 TAB_DSC_DEFINES_MAKEFILE_NAME : "_MakefileName",
199 TAB_DSC_DEFINES_BS_BASE_ADDRESS : "_BsBaseAddress",
200 TAB_DSC_DEFINES_RT_BASE_ADDRESS : "_RtBaseAddress",
201 # TAB_DSC_DEFINES_RFC_LANGUAGES : "_RFCLanguages",
202 # TAB_DSC_DEFINES_ISO_LANGUAGES : "_ISOLanguages",
203 }
204
205 # used to compose dummy library class name for those forced library instances
206 _NullLibraryNumber = 0
207
208 ## Constructor of DscBuildData
209 #
210 # Initialize object of DscBuildData
211 #
212 # @param FilePath The path of platform description file
213 # @param RawData The raw data of DSC file
214 # @param BuildDataBase Database used to retrieve module/package information
215 # @param Arch The target architecture
216 # @param Platform (not used for DscBuildData)
217 # @param Macros Macros used for replacement in DSC file
218 #
219 def __init__(self, FilePath, RawData, BuildDataBase, Arch=TAB_ARCH_COMMON, Target=None, Toolchain=None):
220 self.MetaFile = FilePath
221 self._RawData = RawData
222 self._Bdb = BuildDataBase
223 self._Arch = Arch
224 self._Target = Target
225 self._Toolchain = Toolchain
226 self._ToolChainFamily = None
227 self._Clear()
228 self._HandleOverridePath()
229 self.WorkspaceDir = os.getenv("WORKSPACE") if os.getenv("WORKSPACE") else ""
230 self.DefaultStores = None
231 self.SkuIdMgr = SkuClass(self.SkuName, self.SkuIds)
232
233 @property
234 def OutputPath(self):
235 if os.getenv("WORKSPACE"):
236 return os.path.join(os.getenv("WORKSPACE"), self.OutputDirectory, self._Target + "_" + self._Toolchain, PcdValueInitName)
237 else:
238 return os.path.dirname(self.DscFile)
239
240 ## XXX[key] = value
241 def __setitem__(self, key, value):
242 self.__dict__[self._PROPERTY_[key]] = value
243
244 ## value = XXX[key]
245 def __getitem__(self, key):
246 return self.__dict__[self._PROPERTY_[key]]
247
248 ## "in" test support
249 def __contains__(self, key):
250 return key in self._PROPERTY_
251
252 ## Set all internal used members of DscBuildData to None
253 def _Clear(self):
254 self._Header = None
255 self._PlatformName = None
256 self._Guid = None
257 self._Version = None
258 self._DscSpecification = None
259 self._OutputDirectory = None
260 self._SupArchList = None
261 self._BuildTargets = None
262 self._SkuName = None
263 self._PcdInfoFlag = None
264 self._VarCheckFlag = None
265 self._FlashDefinition = None
266 self._Prebuild = None
267 self._Postbuild = None
268 self._BuildNumber = None
269 self._MakefileName = None
270 self._BsBaseAddress = None
271 self._RtBaseAddress = None
272 self._SkuIds = None
273 self._Modules = None
274 self._LibraryInstances = None
275 self._LibraryClasses = None
276 self._Pcds = None
277 self._DecPcds = None
278 self._BuildOptions = None
279 self._ModuleTypeOptions = None
280 self._LoadFixAddress = None
281 self._RFCLanguages = None
282 self._ISOLanguages = None
283 self._VpdToolGuid = None
284 self._MacroDict = None
285 self.DefaultStores = None
286
287 ## handle Override Path of Module
288 def _HandleOverridePath(self):
289 RecordList = self._RawData[MODEL_META_DATA_COMPONENT, self._Arch]
290 for Record in RecordList:
291 ModuleId = Record[6]
292 LineNo = Record[7]
293 ModuleFile = PathClass(NormPath(Record[0]), GlobalData.gWorkspace, Arch=self._Arch)
294 RecordList = self._RawData[MODEL_META_DATA_COMPONENT_SOURCE_OVERRIDE_PATH, self._Arch, None, ModuleId]
295 if RecordList != []:
296 SourceOverridePath = mws.join(GlobalData.gWorkspace, NormPath(RecordList[0][0]))
297
298 # Check if the source override path exists
299 if not os.path.isdir(SourceOverridePath):
300 EdkLogger.error('build', FILE_NOT_FOUND, Message='Source override path does not exist:', File=self.MetaFile, ExtraData=SourceOverridePath, Line=LineNo)
301
302 # Add to GlobalData Variables
303 GlobalData.gOverrideDir[ModuleFile.Key] = SourceOverridePath
304
305 ## Get current effective macros
306 @property
307 def _Macros(self):
308 if self._MacroDict is None:
309 self._MacroDict = {}
310 self._MacroDict.update(GlobalData.gPlatformDefines)
311 self._MacroDict.update(GlobalData.gGlobalDefines)
312 self._MacroDict.update(GlobalData.gCommandLineDefines)
313 return self._MacroDict
314
315 ## Get architecture
316 @property
317 def Arch(self):
318 return self._Arch
319
320 ## Retrieve all information in [Defines] section
321 #
322 # (Retriving all [Defines] information in one-shot is just to save time.)
323 #
324 def _GetHeaderInfo(self):
325 RecordList = self._RawData[MODEL_META_DATA_HEADER, self._Arch]
326 for Record in RecordList:
327 Name = Record[1]
328 # items defined _PROPERTY_ don't need additional processing
329
330 # some special items in [Defines] section need special treatment
331 if Name == TAB_DSC_DEFINES_OUTPUT_DIRECTORY:
332 self._OutputDirectory = NormPath(Record[2], self._Macros)
333 if ' ' in self._OutputDirectory:
334 EdkLogger.error("build", FORMAT_NOT_SUPPORTED, "No space is allowed in OUTPUT_DIRECTORY",
335 File=self.MetaFile, Line=Record[-1],
336 ExtraData=self._OutputDirectory)
337 elif Name == TAB_DSC_DEFINES_FLASH_DEFINITION:
338 self._FlashDefinition = PathClass(NormPath(Record[2], self._Macros), GlobalData.gWorkspace)
339 ErrorCode, ErrorInfo = self._FlashDefinition.Validate('.fdf')
340 if ErrorCode != 0:
341 EdkLogger.error('build', ErrorCode, File=self.MetaFile, Line=Record[-1],
342 ExtraData=ErrorInfo)
343 elif Name == TAB_DSC_PREBUILD:
344 PrebuildValue = Record[2]
345 if Record[2][0] == '"':
346 if Record[2][-1] != '"':
347 EdkLogger.error('build', FORMAT_INVALID, 'Missing double quotes in the end of %s statement.' % TAB_DSC_PREBUILD,
348 File=self.MetaFile, Line=Record[-1])
349 PrebuildValue = Record[2][1:-1]
350 self._Prebuild = PrebuildValue
351 elif Name == TAB_DSC_POSTBUILD:
352 PostbuildValue = Record[2]
353 if Record[2][0] == '"':
354 if Record[2][-1] != '"':
355 EdkLogger.error('build', FORMAT_INVALID, 'Missing double quotes in the end of %s statement.' % TAB_DSC_POSTBUILD,
356 File=self.MetaFile, Line=Record[-1])
357 PostbuildValue = Record[2][1:-1]
358 self._Postbuild = PostbuildValue
359 elif Name == TAB_DSC_DEFINES_SUPPORTED_ARCHITECTURES:
360 self._SupArchList = GetSplitValueList(Record[2], TAB_VALUE_SPLIT)
361 elif Name == TAB_DSC_DEFINES_BUILD_TARGETS:
362 self._BuildTargets = GetSplitValueList(Record[2])
363 elif Name == TAB_DSC_DEFINES_SKUID_IDENTIFIER:
364 if self._SkuName is None:
365 self._SkuName = Record[2]
366 if GlobalData.gSKUID_CMD:
367 self._SkuName = GlobalData.gSKUID_CMD
368 elif Name == TAB_DSC_DEFINES_PCD_INFO_GENERATION:
369 self._PcdInfoFlag = Record[2]
370 elif Name == TAB_DSC_DEFINES_PCD_VAR_CHECK_GENERATION:
371 self._VarCheckFlag = Record[2]
372 elif Name == TAB_FIX_LOAD_TOP_MEMORY_ADDRESS:
373 try:
374 self._LoadFixAddress = int (Record[2], 0)
375 except:
376 EdkLogger.error("build", PARAMETER_INVALID, "FIX_LOAD_TOP_MEMORY_ADDRESS %s is not valid dec or hex string" % (Record[2]))
377 elif Name == TAB_DSC_DEFINES_RFC_LANGUAGES:
378 if not Record[2] or Record[2][0] != '"' or Record[2][-1] != '"' or len(Record[2]) == 1:
379 EdkLogger.error('build', FORMAT_NOT_SUPPORTED, 'language code for RFC_LANGUAGES must have double quotes around it, for example: RFC_LANGUAGES = "en-us;zh-hans"',
380 File=self.MetaFile, Line=Record[-1])
381 LanguageCodes = Record[2][1:-1]
382 if not LanguageCodes:
383 EdkLogger.error('build', FORMAT_NOT_SUPPORTED, 'one or more RFC4646 format language code must be provided for RFC_LANGUAGES statement',
384 File=self.MetaFile, Line=Record[-1])
385 LanguageList = GetSplitValueList(LanguageCodes, TAB_SEMI_COLON_SPLIT)
386 # check whether there is empty entries in the list
387 if None in LanguageList:
388 EdkLogger.error('build', FORMAT_NOT_SUPPORTED, 'one or more empty language code is in RFC_LANGUAGES statement',
389 File=self.MetaFile, Line=Record[-1])
390 self._RFCLanguages = LanguageList
391 elif Name == TAB_DSC_DEFINES_ISO_LANGUAGES:
392 if not Record[2] or Record[2][0] != '"' or Record[2][-1] != '"' or len(Record[2]) == 1:
393 EdkLogger.error('build', FORMAT_NOT_SUPPORTED, 'language code for ISO_LANGUAGES must have double quotes around it, for example: ISO_LANGUAGES = "engchn"',
394 File=self.MetaFile, Line=Record[-1])
395 LanguageCodes = Record[2][1:-1]
396 if not LanguageCodes:
397 EdkLogger.error('build', FORMAT_NOT_SUPPORTED, 'one or more ISO639-2 format language code must be provided for ISO_LANGUAGES statement',
398 File=self.MetaFile, Line=Record[-1])
399 if len(LanguageCodes) % 3:
400 EdkLogger.error('build', FORMAT_NOT_SUPPORTED, 'bad ISO639-2 format for ISO_LANGUAGES',
401 File=self.MetaFile, Line=Record[-1])
402 LanguageList = []
403 for i in range(0, len(LanguageCodes), 3):
404 LanguageList.append(LanguageCodes[i:i + 3])
405 self._ISOLanguages = LanguageList
406 elif Name == TAB_DSC_DEFINES_VPD_TOOL_GUID:
407 #
408 # try to convert GUID to a real UUID value to see whether the GUID is format
409 # for VPD_TOOL_GUID is correct.
410 #
411 try:
412 uuid.UUID(Record[2])
413 except:
414 EdkLogger.error("build", FORMAT_INVALID, "Invalid GUID format for VPD_TOOL_GUID", File=self.MetaFile)
415 self._VpdToolGuid = Record[2]
416 elif Name in self:
417 self[Name] = Record[2]
418 # set _Header to non-None in order to avoid database re-querying
419 self._Header = 'DUMMY'
420
421 ## Retrieve platform name
422 @property
423 def PlatformName(self):
424 if self._PlatformName is None:
425 if self._Header is None:
426 self._GetHeaderInfo()
427 if self._PlatformName is None:
428 EdkLogger.error('build', ATTRIBUTE_NOT_AVAILABLE, "No PLATFORM_NAME", File=self.MetaFile)
429 return self._PlatformName
430
431 @property
432 def Platform(self):
433 return self.PlatformName
434
435 ## Retrieve file guid
436 @property
437 def Guid(self):
438 if self._Guid is None:
439 if self._Header is None:
440 self._GetHeaderInfo()
441 if self._Guid is None:
442 EdkLogger.error('build', ATTRIBUTE_NOT_AVAILABLE, "No PLATFORM_GUID", File=self.MetaFile)
443 return self._Guid
444
445 ## Retrieve platform version
446 @property
447 def Version(self):
448 if self._Version is None:
449 if self._Header is None:
450 self._GetHeaderInfo()
451 if self._Version is None:
452 EdkLogger.error('build', ATTRIBUTE_NOT_AVAILABLE, "No PLATFORM_VERSION", File=self.MetaFile)
453 return self._Version
454
455 ## Retrieve platform description file version
456 @property
457 def DscSpecification(self):
458 if self._DscSpecification is None:
459 if self._Header is None:
460 self._GetHeaderInfo()
461 if self._DscSpecification is None:
462 EdkLogger.error('build', ATTRIBUTE_NOT_AVAILABLE, "No DSC_SPECIFICATION", File=self.MetaFile)
463 return self._DscSpecification
464
465 ## Retrieve OUTPUT_DIRECTORY
466 @property
467 def OutputDirectory(self):
468 if self._OutputDirectory is None:
469 if self._Header is None:
470 self._GetHeaderInfo()
471 if self._OutputDirectory is None:
472 self._OutputDirectory = os.path.join("Build", self._PlatformName)
473 return self._OutputDirectory
474
475 ## Retrieve SUPPORTED_ARCHITECTURES
476 @property
477 def SupArchList(self):
478 if self._SupArchList is None:
479 if self._Header is None:
480 self._GetHeaderInfo()
481 if self._SupArchList is None:
482 EdkLogger.error('build', ATTRIBUTE_NOT_AVAILABLE, "No SUPPORTED_ARCHITECTURES", File=self.MetaFile)
483 return self._SupArchList
484
485 ## Retrieve BUILD_TARGETS
486 @property
487 def BuildTargets(self):
488 if self._BuildTargets is None:
489 if self._Header is None:
490 self._GetHeaderInfo()
491 if self._BuildTargets is None:
492 EdkLogger.error('build', ATTRIBUTE_NOT_AVAILABLE, "No BUILD_TARGETS", File=self.MetaFile)
493 return self._BuildTargets
494
495 @property
496 def PcdInfoFlag(self):
497 if self._PcdInfoFlag is None or self._PcdInfoFlag.upper() == 'FALSE':
498 return False
499 elif self._PcdInfoFlag.upper() == 'TRUE':
500 return True
501 else:
502 return False
503
504 @property
505 def VarCheckFlag(self):
506 if self._VarCheckFlag is None or self._VarCheckFlag.upper() == 'FALSE':
507 return False
508 elif self._VarCheckFlag.upper() == 'TRUE':
509 return True
510 else:
511 return False
512
513 # # Retrieve SKUID_IDENTIFIER
514 @property
515 def SkuName(self):
516 if self._SkuName is None:
517 if self._Header is None:
518 self._GetHeaderInfo()
519 if self._SkuName is None:
520 self._SkuName = TAB_DEFAULT
521 return self._SkuName
522
523 ## Override SKUID_IDENTIFIER
524 @SkuName.setter
525 def SkuName(self, Value):
526 self._SkuName = Value
527
528 @property
529 def FlashDefinition(self):
530 if self._FlashDefinition is None:
531 if self._Header is None:
532 self._GetHeaderInfo()
533 if self._FlashDefinition is None:
534 self._FlashDefinition = ''
535 return self._FlashDefinition
536
537 @property
538 def Prebuild(self):
539 if self._Prebuild is None:
540 if self._Header is None:
541 self._GetHeaderInfo()
542 if self._Prebuild is None:
543 self._Prebuild = ''
544 return self._Prebuild
545
546 @property
547 def Postbuild(self):
548 if self._Postbuild is None:
549 if self._Header is None:
550 self._GetHeaderInfo()
551 if self._Postbuild is None:
552 self._Postbuild = ''
553 return self._Postbuild
554
555 ## Retrieve FLASH_DEFINITION
556 @property
557 def BuildNumber(self):
558 if self._BuildNumber is None:
559 if self._Header is None:
560 self._GetHeaderInfo()
561 if self._BuildNumber is None:
562 self._BuildNumber = ''
563 return self._BuildNumber
564
565 ## Retrieve MAKEFILE_NAME
566 @property
567 def MakefileName(self):
568 if self._MakefileName is None:
569 if self._Header is None:
570 self._GetHeaderInfo()
571 if self._MakefileName is None:
572 self._MakefileName = ''
573 return self._MakefileName
574
575 ## Retrieve BsBaseAddress
576 @property
577 def BsBaseAddress(self):
578 if self._BsBaseAddress is None:
579 if self._Header is None:
580 self._GetHeaderInfo()
581 if self._BsBaseAddress is None:
582 self._BsBaseAddress = ''
583 return self._BsBaseAddress
584
585 ## Retrieve RtBaseAddress
586 @property
587 def RtBaseAddress(self):
588 if self._RtBaseAddress is None:
589 if self._Header is None:
590 self._GetHeaderInfo()
591 if self._RtBaseAddress is None:
592 self._RtBaseAddress = ''
593 return self._RtBaseAddress
594
595 ## Retrieve the top address for the load fix address
596 @property
597 def LoadFixAddress(self):
598 if self._LoadFixAddress is None:
599 if self._Header is None:
600 self._GetHeaderInfo()
601
602 if self._LoadFixAddress is None:
603 self._LoadFixAddress = self._Macros.get(TAB_FIX_LOAD_TOP_MEMORY_ADDRESS, '0')
604
605 try:
606 self._LoadFixAddress = int (self._LoadFixAddress, 0)
607 except:
608 EdkLogger.error("build", PARAMETER_INVALID, "FIX_LOAD_TOP_MEMORY_ADDRESS %s is not valid dec or hex string" % (self._LoadFixAddress))
609
610 #
611 # If command line defined, should override the value in DSC file.
612 #
613 if 'FIX_LOAD_TOP_MEMORY_ADDRESS' in GlobalData.gCommandLineDefines:
614 try:
615 self._LoadFixAddress = int(GlobalData.gCommandLineDefines['FIX_LOAD_TOP_MEMORY_ADDRESS'], 0)
616 except:
617 EdkLogger.error("build", PARAMETER_INVALID, "FIX_LOAD_TOP_MEMORY_ADDRESS %s is not valid dec or hex string" % (GlobalData.gCommandLineDefines['FIX_LOAD_TOP_MEMORY_ADDRESS']))
618
619 if self._LoadFixAddress < 0:
620 EdkLogger.error("build", PARAMETER_INVALID, "FIX_LOAD_TOP_MEMORY_ADDRESS is set to the invalid negative value 0x%x" % (self._LoadFixAddress))
621 if self._LoadFixAddress != 0xFFFFFFFFFFFFFFFF and self._LoadFixAddress % 0x1000 != 0:
622 EdkLogger.error("build", PARAMETER_INVALID, "FIX_LOAD_TOP_MEMORY_ADDRESS is set to the invalid unaligned 4K value 0x%x" % (self._LoadFixAddress))
623
624 return self._LoadFixAddress
625
626 ## Retrieve RFCLanguage filter
627 @property
628 def RFCLanguages(self):
629 if self._RFCLanguages is None:
630 if self._Header is None:
631 self._GetHeaderInfo()
632 if self._RFCLanguages is None:
633 self._RFCLanguages = []
634 return self._RFCLanguages
635
636 ## Retrieve ISOLanguage filter
637 @property
638 def ISOLanguages(self):
639 if self._ISOLanguages is None:
640 if self._Header is None:
641 self._GetHeaderInfo()
642 if self._ISOLanguages is None:
643 self._ISOLanguages = []
644 return self._ISOLanguages
645
646 ## Retrieve the GUID string for VPD tool
647 @property
648 def VpdToolGuid(self):
649 if self._VpdToolGuid is None:
650 if self._Header is None:
651 self._GetHeaderInfo()
652 if self._VpdToolGuid is None:
653 self._VpdToolGuid = ''
654 return self._VpdToolGuid
655
656 ## Retrieve [SkuIds] section information
657 @property
658 def SkuIds(self):
659 if self._SkuIds is None:
660 self._SkuIds = OrderedDict()
661 RecordList = self._RawData[MODEL_EFI_SKU_ID, self._Arch]
662 for Record in RecordList:
663 if not Record[0]:
664 EdkLogger.error('build', FORMAT_INVALID, 'No Sku ID number',
665 File=self.MetaFile, Line=Record[-1])
666 if not Record[1]:
667 EdkLogger.error('build', FORMAT_INVALID, 'No Sku ID name',
668 File=self.MetaFile, Line=Record[-1])
669 if not Pattern.match(Record[0]) and not HexPattern.match(Record[0]):
670 EdkLogger.error('build', FORMAT_INVALID, "The format of the Sku ID number is invalid. It only support Integer and HexNumber",
671 File=self.MetaFile, Line=Record[-1])
672 if not SkuIdPattern.match(Record[1]) or (Record[2] and not SkuIdPattern.match(Record[2])):
673 EdkLogger.error('build', FORMAT_INVALID, "The format of the Sku ID name is invalid. The correct format is '(a-zA-Z_)(a-zA-Z0-9_)*'",
674 File=self.MetaFile, Line=Record[-1])
675 self._SkuIds[Record[1].upper()] = (str(DscBuildData.ToInt(Record[0])), Record[1].upper(), Record[2].upper())
676 if TAB_DEFAULT not in self._SkuIds:
677 self._SkuIds[TAB_DEFAULT] = ("0", TAB_DEFAULT, TAB_DEFAULT)
678 if TAB_COMMON not in self._SkuIds:
679 self._SkuIds[TAB_COMMON] = ("0", TAB_DEFAULT, TAB_DEFAULT)
680 return self._SkuIds
681
682 @staticmethod
683 def ToInt(intstr):
684 return int(intstr, 16) if intstr.upper().startswith("0X") else int(intstr)
685
686 def _GetDefaultStores(self):
687 if self.DefaultStores is None:
688 self.DefaultStores = OrderedDict()
689 RecordList = self._RawData[MODEL_EFI_DEFAULT_STORES, self._Arch]
690 for Record in RecordList:
691 if not Record[0]:
692 EdkLogger.error('build', FORMAT_INVALID, 'No DefaultStores ID number',
693 File=self.MetaFile, Line=Record[-1])
694 if not Record[1]:
695 EdkLogger.error('build', FORMAT_INVALID, 'No DefaultStores ID name',
696 File=self.MetaFile, Line=Record[-1])
697 if not Pattern.match(Record[0]) and not HexPattern.match(Record[0]):
698 EdkLogger.error('build', FORMAT_INVALID, "The format of the DefaultStores ID number is invalid. It only support Integer and HexNumber",
699 File=self.MetaFile, Line=Record[-1])
700 if not IsValidWord(Record[1]):
701 EdkLogger.error('build', FORMAT_INVALID, "The format of the DefaultStores ID name is invalid. The correct format is '(a-zA-Z0-9_)(a-zA-Z0-9_-.)*'",
702 File=self.MetaFile, Line=Record[-1])
703 self.DefaultStores[Record[1].upper()] = (DscBuildData.ToInt(Record[0]), Record[1].upper())
704 if TAB_DEFAULT_STORES_DEFAULT not in self.DefaultStores:
705 self.DefaultStores[TAB_DEFAULT_STORES_DEFAULT] = (0, TAB_DEFAULT_STORES_DEFAULT)
706 GlobalData.gDefaultStores = sorted(self.DefaultStores.keys())
707 return self.DefaultStores
708
709 def OverrideDuplicateModule(self):
710 RecordList = self._RawData[MODEL_META_DATA_COMPONENT, self._Arch]
711 Macros = self._Macros
712 Components = {}
713 for Record in RecordList:
714 ModuleId = Record[6]
715 file_guid = self._RawData[MODEL_META_DATA_HEADER, self._Arch, None, ModuleId]
716 file_guid_str = file_guid[0][2] if file_guid else "NULL"
717 ModuleFile = PathClass(NormPath(Record[0], Macros), GlobalData.gWorkspace, Arch=self._Arch)
718 if self._Arch != TAB_ARCH_COMMON and (file_guid_str,str(ModuleFile)) in Components:
719 self._RawData.DisableOverrideComponent(Components[(file_guid_str,str(ModuleFile))])
720 Components[(file_guid_str,str(ModuleFile))] = ModuleId
721 self._RawData._PostProcessed = False
722 ## Retrieve [Components] section information
723 @property
724 def Modules(self):
725 if self._Modules is not None:
726 return self._Modules
727 self.OverrideDuplicateModule()
728 self._Modules = OrderedDict()
729 RecordList = self._RawData[MODEL_META_DATA_COMPONENT, self._Arch]
730 Macros = self._Macros
731 for Record in RecordList:
732 ModuleFile = PathClass(NormPath(Record[0], Macros), GlobalData.gWorkspace, Arch=self._Arch)
733 ModuleId = Record[6]
734 LineNo = Record[7]
735
736 # check the file validation
737 ErrorCode, ErrorInfo = ModuleFile.Validate('.inf')
738 if ErrorCode != 0:
739 EdkLogger.error('build', ErrorCode, File=self.MetaFile, Line=LineNo,
740 ExtraData=ErrorInfo)
741
742 Module = ModuleBuildClassObject()
743 Module.MetaFile = ModuleFile
744
745 # get module private library instance
746 RecordList = self._RawData[MODEL_EFI_LIBRARY_CLASS, self._Arch, None, ModuleId]
747 for Record in RecordList:
748 LibraryClass = Record[0]
749 LibraryPath = PathClass(NormPath(Record[1], Macros), GlobalData.gWorkspace, Arch=self._Arch)
750 LineNo = Record[-1]
751
752 # check the file validation
753 ErrorCode, ErrorInfo = LibraryPath.Validate('.inf')
754 if ErrorCode != 0:
755 EdkLogger.error('build', ErrorCode, File=self.MetaFile, Line=LineNo,
756 ExtraData=ErrorInfo)
757
758 if LibraryClass == '' or LibraryClass == 'NULL':
759 self._NullLibraryNumber += 1
760 LibraryClass = 'NULL%d' % self._NullLibraryNumber
761 EdkLogger.verbose("Found forced library for %s\n\t%s [%s]" % (ModuleFile, LibraryPath, LibraryClass))
762 Module.LibraryClasses[LibraryClass] = LibraryPath
763 if LibraryPath not in self.LibraryInstances:
764 self.LibraryInstances.append(LibraryPath)
765
766 # get module private PCD setting
767 for Type in [MODEL_PCD_FIXED_AT_BUILD, MODEL_PCD_PATCHABLE_IN_MODULE, \
768 MODEL_PCD_FEATURE_FLAG, MODEL_PCD_DYNAMIC, MODEL_PCD_DYNAMIC_EX]:
769 RecordList = self._RawData[Type, self._Arch, None, ModuleId]
770 for TokenSpaceGuid, PcdCName, Setting, Dummy1, Dummy2, Dummy3, Dummy4, Dummy5 in RecordList:
771 TokenList = GetSplitValueList(Setting)
772 DefaultValue = TokenList[0]
773 # the format is PcdName| Value | VOID* | MaxDatumSize
774 if len(TokenList) > 2:
775 MaxDatumSize = TokenList[2]
776 else:
777 MaxDatumSize = ''
778 TypeString = self._PCD_TYPE_STRING_[Type]
779 Pcd = PcdClassObject(
780 PcdCName,
781 TokenSpaceGuid,
782 TypeString,
783 '',
784 DefaultValue,
785 '',
786 MaxDatumSize,
787 {},
788 False,
789 None
790 )
791 Module.Pcds[PcdCName, TokenSpaceGuid] = Pcd
792
793 # get module private build options
794 RecordList = self._RawData[MODEL_META_DATA_BUILD_OPTION, self._Arch, None, ModuleId]
795 for ToolChainFamily, ToolChain, Option, Dummy1, Dummy2, Dummy3, Dummy4, Dummy5 in RecordList:
796 if (ToolChainFamily, ToolChain) not in Module.BuildOptions:
797 Module.BuildOptions[ToolChainFamily, ToolChain] = Option
798 else:
799 OptionString = Module.BuildOptions[ToolChainFamily, ToolChain]
800 Module.BuildOptions[ToolChainFamily, ToolChain] = OptionString + " " + Option
801
802 RecordList = self._RawData[MODEL_META_DATA_HEADER, self._Arch, None, ModuleId]
803 if RecordList:
804 if len(RecordList) != 1:
805 EdkLogger.error('build', OPTION_UNKNOWN, 'Only FILE_GUID can be listed in <Defines> section.',
806 File=self.MetaFile, ExtraData=str(ModuleFile), Line=LineNo)
807 ModuleFile = ProcessDuplicatedInf(ModuleFile, RecordList[0][2], GlobalData.gWorkspace)
808 ModuleFile.Arch = self._Arch
809
810 self._Modules[ModuleFile] = Module
811 return self._Modules
812
813 ## Retrieve all possible library instances used in this platform
814 @property
815 def LibraryInstances(self):
816 if self._LibraryInstances is None:
817 self.LibraryClasses
818 return self._LibraryInstances
819
820 ## Retrieve [LibraryClasses] information
821 @property
822 def LibraryClasses(self):
823 if self._LibraryClasses is None:
824 self._LibraryInstances = []
825 #
826 # tdict is a special dict kind of type, used for selecting correct
827 # library instance for given library class and module type
828 #
829 LibraryClassDict = tdict(True, 3)
830 # track all library class names
831 LibraryClassSet = set()
832 RecordList = self._RawData[MODEL_EFI_LIBRARY_CLASS, self._Arch, None, -1]
833 Macros = self._Macros
834 for Record in RecordList:
835 LibraryClass, LibraryInstance, Dummy, Arch, ModuleType, Dummy, Dummy, LineNo = Record
836 if LibraryClass == '' or LibraryClass == 'NULL':
837 self._NullLibraryNumber += 1
838 LibraryClass = 'NULL%d' % self._NullLibraryNumber
839 EdkLogger.verbose("Found forced library for arch=%s\n\t%s [%s]" % (Arch, LibraryInstance, LibraryClass))
840 LibraryClassSet.add(LibraryClass)
841 LibraryInstance = PathClass(NormPath(LibraryInstance, Macros), GlobalData.gWorkspace, Arch=self._Arch)
842 # check the file validation
843 ErrorCode, ErrorInfo = LibraryInstance.Validate('.inf')
844 if ErrorCode != 0:
845 EdkLogger.error('build', ErrorCode, File=self.MetaFile, Line=LineNo,
846 ExtraData=ErrorInfo)
847
848 if ModuleType != TAB_COMMON and ModuleType not in SUP_MODULE_LIST:
849 EdkLogger.error('build', OPTION_UNKNOWN, "Unknown module type [%s]" % ModuleType,
850 File=self.MetaFile, ExtraData=LibraryInstance, Line=LineNo)
851 LibraryClassDict[Arch, ModuleType, LibraryClass] = LibraryInstance
852 if LibraryInstance not in self._LibraryInstances:
853 self._LibraryInstances.append(LibraryInstance)
854
855 # resolve the specific library instance for each class and each module type
856 self._LibraryClasses = tdict(True)
857 for LibraryClass in LibraryClassSet:
858 # try all possible module types
859 for ModuleType in SUP_MODULE_LIST:
860 LibraryInstance = LibraryClassDict[self._Arch, ModuleType, LibraryClass]
861 if LibraryInstance is None:
862 continue
863 self._LibraryClasses[LibraryClass, ModuleType] = LibraryInstance
864
865 RecordList = self._RawData[MODEL_EFI_LIBRARY_INSTANCE, self._Arch]
866 for Record in RecordList:
867 File = PathClass(NormPath(Record[0], Macros), GlobalData.gWorkspace, Arch=self._Arch)
868 LineNo = Record[-1]
869 # check the file validation
870 ErrorCode, ErrorInfo = File.Validate('.inf')
871 if ErrorCode != 0:
872 EdkLogger.error('build', ErrorCode, File=self.MetaFile, Line=LineNo,
873 ExtraData=ErrorInfo)
874 if File not in self._LibraryInstances:
875 self._LibraryInstances.append(File)
876 #
877 # we need the module name as the library class name, so we have
878 # to parse it here. (self._Bdb[] will trigger a file parse if it
879 # hasn't been parsed)
880 #
881 Library = self._Bdb[File, self._Arch, self._Target, self._Toolchain]
882 self._LibraryClasses[Library.BaseName, ':dummy:'] = Library
883 return self._LibraryClasses
884
885 def _ValidatePcd(self, PcdCName, TokenSpaceGuid, Setting, PcdType, LineNo):
886 if not self._DecPcds:
887
888 FdfInfList = []
889 if GlobalData.gFdfParser:
890 FdfInfList = GlobalData.gFdfParser.Profile.InfList
891
892 PkgSet = set()
893 for Inf in FdfInfList:
894 ModuleFile = PathClass(NormPath(Inf), GlobalData.gWorkspace, Arch=self._Arch)
895 if ModuleFile in self._Modules:
896 continue
897 ModuleData = self._Bdb[ModuleFile, self._Arch, self._Target, self._Toolchain]
898 PkgSet.update(ModuleData.Packages)
899
900 self._DecPcds, self._GuidDict = GetDeclaredPcd(self, self._Bdb, self._Arch, self._Target, self._Toolchain, PkgSet)
901 self._GuidDict.update(GlobalData.gPlatformPcds)
902
903 if (PcdCName, TokenSpaceGuid) not in self._DecPcds:
904 EdkLogger.error('build', PARSER_ERROR,
905 "Pcd (%s.%s) defined in DSC is not declared in DEC files referenced in INF files in FDF. Arch: ['%s']" % (TokenSpaceGuid, PcdCName, self._Arch),
906 File=self.MetaFile, Line=LineNo)
907 ValueList, IsValid, Index = AnalyzeDscPcd(Setting, PcdType, self._DecPcds[PcdCName, TokenSpaceGuid].DatumType)
908 if not IsValid:
909 if PcdType not in [MODEL_PCD_FEATURE_FLAG, MODEL_PCD_FIXED_AT_BUILD]:
910 EdkLogger.error('build', FORMAT_INVALID, "Pcd format incorrect.", File=self.MetaFile, Line=LineNo,
911 ExtraData="%s.%s|%s" % (TokenSpaceGuid, PcdCName, Setting))
912 else:
913 if ValueList[2] == '-1':
914 EdkLogger.error('build', FORMAT_INVALID, "Pcd format incorrect.", File=self.MetaFile, Line=LineNo,
915 ExtraData="%s.%s|%s" % (TokenSpaceGuid, PcdCName, Setting))
916 if ValueList[Index]:
917 DatumType = self._DecPcds[PcdCName, TokenSpaceGuid].DatumType
918 if "{CODE(" not in ValueList[Index]:
919 try:
920 ValueList[Index] = ValueExpressionEx(ValueList[Index], DatumType, self._GuidDict)(True)
921 except BadExpression as Value:
922 EdkLogger.error('Parser', FORMAT_INVALID, Value, File=self.MetaFile, Line=LineNo,
923 ExtraData="PCD [%s.%s] Value \"%s\" " % (
924 TokenSpaceGuid, PcdCName, ValueList[Index]))
925 except EvaluationException as Excpt:
926 if hasattr(Excpt, 'Pcd'):
927 if Excpt.Pcd in GlobalData.gPlatformOtherPcds:
928 EdkLogger.error('Parser', FORMAT_INVALID, "Cannot use this PCD (%s) in an expression as"
929 " it must be defined in a [PcdsFixedAtBuild] or [PcdsFeatureFlag] section"
930 " of the DSC file" % Excpt.Pcd,
931 File=self.MetaFile, Line=LineNo)
932 else:
933 EdkLogger.error('Parser', FORMAT_INVALID, "PCD (%s) is not defined in DSC file" % Excpt.Pcd,
934 File=self.MetaFile, Line=LineNo)
935 else:
936 EdkLogger.error('Parser', FORMAT_INVALID, "Invalid expression: %s" % str(Excpt),
937 File=self.MetaFile, Line=LineNo)
938
939 if ValueList[Index]:
940 Valid, ErrStr = CheckPcdDatum(self._DecPcds[PcdCName, TokenSpaceGuid].DatumType, ValueList[Index])
941 if not Valid:
942 EdkLogger.error('build', FORMAT_INVALID, ErrStr, File=self.MetaFile, Line=LineNo,
943 ExtraData="%s.%s" % (TokenSpaceGuid, PcdCName))
944 if PcdType in (MODEL_PCD_DYNAMIC_DEFAULT, MODEL_PCD_DYNAMIC_EX_DEFAULT, MODEL_PCD_FIXED_AT_BUILD, MODEL_PCD_PATCHABLE_IN_MODULE):
945 if self._DecPcds[PcdCName, TokenSpaceGuid].DatumType.strip() != ValueList[1].strip():
946 EdkLogger.error('build', FORMAT_INVALID, "Pcd datumtype used in DSC file is not the same as its declaration in DEC file.", File=self.MetaFile, Line=LineNo,
947 ExtraData="%s.%s|%s" % (TokenSpaceGuid, PcdCName, Setting))
948 if (TokenSpaceGuid + '.' + PcdCName) in GlobalData.gPlatformPcds:
949 if GlobalData.gPlatformPcds[TokenSpaceGuid + '.' + PcdCName] != ValueList[Index]:
950 GlobalData.gPlatformPcds[TokenSpaceGuid + '.' + PcdCName] = ValueList[Index]
951 return ValueList
952
953 def _FilterPcdBySkuUsage(self, Pcds):
954 available_sku = self.SkuIdMgr.AvailableSkuIdSet
955 sku_usage = self.SkuIdMgr.SkuUsageType
956 if sku_usage == SkuClass.SINGLE:
957 for pcdname in Pcds:
958 pcd = Pcds[pcdname]
959 Pcds[pcdname].SkuInfoList = {TAB_DEFAULT:pcd.SkuInfoList[skuid] for skuid in pcd.SkuInfoList if skuid in available_sku}
960 if isinstance(pcd, StructurePcd) and pcd.SkuOverrideValues:
961 Pcds[pcdname].SkuOverrideValues = {TAB_DEFAULT:pcd.SkuOverrideValues[skuid] for skuid in pcd.SkuOverrideValues if skuid in available_sku}
962 else:
963 for pcdname in Pcds:
964 pcd = Pcds[pcdname]
965 Pcds[pcdname].SkuInfoList = {skuid:pcd.SkuInfoList[skuid] for skuid in pcd.SkuInfoList if skuid in available_sku}
966 if isinstance(pcd, StructurePcd) and pcd.SkuOverrideValues:
967 Pcds[pcdname].SkuOverrideValues = {skuid:pcd.SkuOverrideValues[skuid] for skuid in pcd.SkuOverrideValues if skuid in available_sku}
968 return Pcds
969
970 def CompleteHiiPcdsDefaultStores(self, Pcds):
971 HiiPcd = [Pcds[pcd] for pcd in Pcds if Pcds[pcd].Type in [self._PCD_TYPE_STRING_[MODEL_PCD_DYNAMIC_HII], self._PCD_TYPE_STRING_[MODEL_PCD_DYNAMIC_EX_HII]]]
972 DefaultStoreMgr = DefaultStore(self.DefaultStores)
973 for pcd in HiiPcd:
974 for skuid in pcd.SkuInfoList:
975 skuobj = pcd.SkuInfoList.get(skuid)
976 if TAB_DEFAULT_STORES_DEFAULT not in skuobj.DefaultStoreDict:
977 PcdDefaultStoreSet = set(defaultstorename for defaultstorename in skuobj.DefaultStoreDict)
978 mindefaultstorename = DefaultStoreMgr.GetMin(PcdDefaultStoreSet)
979 skuobj.DefaultStoreDict[TAB_DEFAULT_STORES_DEFAULT] = skuobj.DefaultStoreDict[mindefaultstorename]
980 return Pcds
981
982 def RecoverCommandLinePcd(self):
983 def UpdateCommandLineValue(pcd):
984 if pcd.Type in [self._PCD_TYPE_STRING_[MODEL_PCD_FIXED_AT_BUILD],
985 self._PCD_TYPE_STRING_[MODEL_PCD_PATCHABLE_IN_MODULE]]:
986 pcd.PcdValueFromComm = pcd.DefaultValue
987 elif pcd.Type in [self._PCD_TYPE_STRING_[MODEL_PCD_DYNAMIC_HII], self._PCD_TYPE_STRING_[MODEL_PCD_DYNAMIC_EX_HII]]:
988 pcd.PcdValueFromComm = pcd.SkuInfoList.get(TAB_DEFAULT).HiiDefaultValue
989 else:
990 pcd.PcdValueFromComm = pcd.SkuInfoList.get(TAB_DEFAULT).DefaultValue
991 for pcd in self._Pcds:
992 if isinstance(self._Pcds[pcd], StructurePcd) and (self._Pcds[pcd].PcdValueFromComm or self._Pcds[pcd].PcdFieldValueFromComm):
993 UpdateCommandLineValue(self._Pcds[pcd])
994
995 def __ParsePcdFromCommandLine(self):
996 if GlobalData.BuildOptionPcd:
997 for i, pcd in enumerate(GlobalData.BuildOptionPcd):
998 if isinstance(pcd, tuple):
999 continue
1000 (pcdname, pcdvalue) = pcd.split('=')
1001 if not pcdvalue:
1002 EdkLogger.error('build', AUTOGEN_ERROR, "No Value specified for the PCD %s." % (pcdname))
1003 if '.' in pcdname:
1004 (Name1, Name2) = pcdname.split('.', 1)
1005 if "." in Name2:
1006 (Name3, FieldName) = Name2.split(".", 1)
1007 if ((Name3, Name1)) in self.DecPcds:
1008 HasTokenSpace = True
1009 TokenCName = Name3
1010 TokenSpaceGuidCName = Name1
1011 else:
1012 FieldName = Name2
1013 TokenCName = Name1
1014 TokenSpaceGuidCName = ''
1015 HasTokenSpace = False
1016 else:
1017 if ((Name2, Name1)) in self.DecPcds:
1018 HasTokenSpace = True
1019 TokenCName = Name2
1020 TokenSpaceGuidCName = Name1
1021 FieldName =""
1022 else:
1023 FieldName = Name2
1024 TokenCName = Name1
1025 TokenSpaceGuidCName = ''
1026 HasTokenSpace = False
1027 else:
1028 FieldName = ""
1029 TokenCName = pcdname
1030 TokenSpaceGuidCName = ''
1031 HasTokenSpace = False
1032 TokenSpaceGuidCNameList = []
1033 FoundFlag = False
1034 PcdDatumType = ''
1035 DisplayName = TokenCName
1036 if FieldName:
1037 DisplayName = TokenCName + '.' + FieldName
1038 if not HasTokenSpace:
1039 for key in self.DecPcds:
1040 PcdItem = self.DecPcds[key]
1041 if TokenCName == PcdItem.TokenCName:
1042 if not PcdItem.TokenSpaceGuidCName in TokenSpaceGuidCNameList:
1043 if len (TokenSpaceGuidCNameList) < 1:
1044 TokenSpaceGuidCNameList.append(PcdItem.TokenSpaceGuidCName)
1045 TokenSpaceGuidCName = PcdItem.TokenSpaceGuidCName
1046 PcdDatumType = PcdItem.DatumType
1047 FoundFlag = True
1048 else:
1049 EdkLogger.error(
1050 'build',
1051 AUTOGEN_ERROR,
1052 "The Pcd %s is found under multiple different TokenSpaceGuid: %s and %s." % (DisplayName, PcdItem.TokenSpaceGuidCName, TokenSpaceGuidCNameList[0])
1053 )
1054 else:
1055 if (TokenCName, TokenSpaceGuidCName) in self.DecPcds:
1056 PcdDatumType = self.DecPcds[(TokenCName, TokenSpaceGuidCName)].DatumType
1057 FoundFlag = True
1058 if not FoundFlag:
1059 if HasTokenSpace:
1060 EdkLogger.error('build', AUTOGEN_ERROR, "The Pcd %s.%s is not found in the DEC file." % (TokenSpaceGuidCName, DisplayName))
1061 else:
1062 EdkLogger.error('build', AUTOGEN_ERROR, "The Pcd %s is not found in the DEC file." % (DisplayName))
1063 pcdvalue = pcdvalue.replace("\\\\\\'", '\\\\\\"').replace('\\\'', '\'').replace('\\\\\\"', "\\'")
1064 if FieldName:
1065 pcdvalue = DscBuildData.HandleFlexiblePcd(TokenSpaceGuidCName, TokenCName, pcdvalue, PcdDatumType, self._GuidDict, FieldName)
1066 else:
1067 pcdvalue = DscBuildData.HandleFlexiblePcd(TokenSpaceGuidCName, TokenCName, pcdvalue, PcdDatumType, self._GuidDict)
1068 IsValid, Cause = CheckPcdDatum(PcdDatumType, pcdvalue)
1069 if not IsValid:
1070 EdkLogger.error("build", FORMAT_INVALID, Cause, ExtraData="%s.%s" % (TokenSpaceGuidCName, TokenCName))
1071 GlobalData.BuildOptionPcd[i] = (TokenSpaceGuidCName, TokenCName, FieldName, pcdvalue, ("build command options", 1))
1072
1073 if GlobalData.BuildOptionPcd:
1074 for pcd in GlobalData.BuildOptionPcd:
1075 (TokenSpaceGuidCName, TokenCName, FieldName, pcdvalue, _) = pcd
1076 for BuildData in self._Bdb._CACHE_.values():
1077 if BuildData.Arch != self.Arch:
1078 continue
1079 if BuildData.MetaFile.Ext == '.dec' or BuildData.MetaFile.Ext == '.dsc':
1080 continue
1081 for key in BuildData.Pcds:
1082 PcdItem = BuildData.Pcds[key]
1083 if (TokenSpaceGuidCName, TokenCName) == (PcdItem.TokenSpaceGuidCName, PcdItem.TokenCName) and FieldName =="":
1084 PcdItem.DefaultValue = pcdvalue
1085 PcdItem.PcdValueFromComm = pcdvalue
1086 #In command line, the latter full assign value in commandLine should override the former field assign value.
1087 #For example, --pcd Token.pcd.field="" --pcd Token.pcd=H"{}"
1088 delete_assign = []
1089 field_assign = {}
1090 if GlobalData.BuildOptionPcd:
1091 for pcdTuple in GlobalData.BuildOptionPcd:
1092 TokenSpaceGuid, Token, Field = pcdTuple[0], pcdTuple[1], pcdTuple[2]
1093 if Field:
1094 if (TokenSpaceGuid, Token) not in field_assign:
1095 field_assign[TokenSpaceGuid, Token] = []
1096 field_assign[TokenSpaceGuid, Token].append(pcdTuple)
1097 else:
1098 if (TokenSpaceGuid, Token) in field_assign:
1099 delete_assign.extend(field_assign[TokenSpaceGuid, Token])
1100 field_assign[TokenSpaceGuid, Token] = []
1101 for item in delete_assign:
1102 GlobalData.BuildOptionPcd.remove(item)
1103
1104 @staticmethod
1105 def HandleFlexiblePcd(TokenSpaceGuidCName, TokenCName, PcdValue, PcdDatumType, GuidDict, FieldName=''):
1106 if FieldName:
1107 IsArray = False
1108 TokenCName += '.' + FieldName
1109 if PcdValue.startswith('H'):
1110 if FieldName and IsFieldValueAnArray(PcdValue[1:]):
1111 PcdDatumType = TAB_VOID
1112 IsArray = True
1113 if FieldName and not IsArray:
1114 return PcdValue
1115 try:
1116 PcdValue = ValueExpressionEx(PcdValue[1:], PcdDatumType, GuidDict)(True)
1117 except BadExpression as Value:
1118 EdkLogger.error('Parser', FORMAT_INVALID, 'PCD [%s.%s] Value "%s", %s' %
1119 (TokenSpaceGuidCName, TokenCName, PcdValue, Value))
1120 elif PcdValue.startswith("L'") or PcdValue.startswith("'"):
1121 if FieldName and IsFieldValueAnArray(PcdValue):
1122 PcdDatumType = TAB_VOID
1123 IsArray = True
1124 if FieldName and not IsArray:
1125 return PcdValue
1126 try:
1127 PcdValue = ValueExpressionEx(PcdValue, PcdDatumType, GuidDict)(True)
1128 except BadExpression as Value:
1129 EdkLogger.error('Parser', FORMAT_INVALID, 'PCD [%s.%s] Value "%s", %s' %
1130 (TokenSpaceGuidCName, TokenCName, PcdValue, Value))
1131 elif PcdValue.startswith('L'):
1132 PcdValue = 'L"' + PcdValue[1:] + '"'
1133 if FieldName and IsFieldValueAnArray(PcdValue):
1134 PcdDatumType = TAB_VOID
1135 IsArray = True
1136 if FieldName and not IsArray:
1137 return PcdValue
1138 try:
1139 PcdValue = ValueExpressionEx(PcdValue, PcdDatumType, GuidDict)(True)
1140 except BadExpression as Value:
1141 EdkLogger.error('Parser', FORMAT_INVALID, 'PCD [%s.%s] Value "%s", %s' %
1142 (TokenSpaceGuidCName, TokenCName, PcdValue, Value))
1143 else:
1144 if PcdValue.upper() == 'FALSE':
1145 PcdValue = str(0)
1146 if PcdValue.upper() == 'TRUE':
1147 PcdValue = str(1)
1148 if not FieldName:
1149 if PcdDatumType not in TAB_PCD_NUMERIC_TYPES:
1150 PcdValue = '"' + PcdValue + '"'
1151 elif not PcdValue.isdigit() and not PcdValue.upper().startswith('0X'):
1152 PcdValue = '"' + PcdValue + '"'
1153 else:
1154 IsArray = False
1155 Base = 10
1156 if PcdValue.upper().startswith('0X'):
1157 Base = 16
1158 try:
1159 Num = int(PcdValue, Base)
1160 except:
1161 PcdValue = '"' + PcdValue + '"'
1162 if IsFieldValueAnArray(PcdValue):
1163 PcdDatumType = TAB_VOID
1164 IsArray = True
1165 if not IsArray:
1166 return PcdValue
1167 try:
1168 PcdValue = ValueExpressionEx(PcdValue, PcdDatumType, GuidDict)(True)
1169 except BadExpression as Value:
1170 EdkLogger.error('Parser', FORMAT_INVALID, 'PCD [%s.%s] Value "%s", %s' %
1171 (TokenSpaceGuidCName, TokenCName, PcdValue, Value))
1172 return PcdValue
1173
1174 ## Retrieve all PCD settings in platform
1175 @property
1176 def Pcds(self):
1177 if self._Pcds is None:
1178 self._Pcds = OrderedDict()
1179 self.__ParsePcdFromCommandLine()
1180 self._Pcds.update(self._GetPcd(MODEL_PCD_FIXED_AT_BUILD))
1181 self._Pcds.update(self._GetPcd(MODEL_PCD_PATCHABLE_IN_MODULE))
1182 self._Pcds.update(self._GetPcd(MODEL_PCD_FEATURE_FLAG))
1183 self._Pcds.update(self._GetDynamicPcd(MODEL_PCD_DYNAMIC_DEFAULT))
1184 self._Pcds.update(self._GetDynamicHiiPcd(MODEL_PCD_DYNAMIC_HII))
1185 self._Pcds.update(self._GetDynamicVpdPcd(MODEL_PCD_DYNAMIC_VPD))
1186 self._Pcds.update(self._GetDynamicPcd(MODEL_PCD_DYNAMIC_EX_DEFAULT))
1187 self._Pcds.update(self._GetDynamicHiiPcd(MODEL_PCD_DYNAMIC_EX_HII))
1188 self._Pcds.update(self._GetDynamicVpdPcd(MODEL_PCD_DYNAMIC_EX_VPD))
1189
1190 self._Pcds = self.CompletePcdValues(self._Pcds)
1191 self._Pcds = self.OverrideByFdfOverAll(self._Pcds)
1192 self._Pcds = self.OverrideByCommOverAll(self._Pcds)
1193 self._Pcds = self.UpdateStructuredPcds(MODEL_PCD_TYPE_LIST, self._Pcds)
1194 self._Pcds = self.CompleteHiiPcdsDefaultStores(self._Pcds)
1195 self._Pcds = self._FilterPcdBySkuUsage(self._Pcds)
1196
1197 self.RecoverCommandLinePcd()
1198 return self._Pcds
1199
1200 ## Retrieve [BuildOptions]
1201 @property
1202 def BuildOptions(self):
1203 if self._BuildOptions is None:
1204 self._BuildOptions = OrderedDict()
1205 #
1206 # Retrieve build option for EDKII and EDK style module
1207 #
1208 for CodeBase in (EDKII_NAME, EDK_NAME):
1209 RecordList = self._RawData[MODEL_META_DATA_BUILD_OPTION, self._Arch, CodeBase]
1210 for ToolChainFamily, ToolChain, Option, Dummy1, Dummy2, Dummy3, Dummy4, Dummy5 in RecordList:
1211 if Dummy3.upper() != TAB_COMMON:
1212 continue
1213 CurKey = (ToolChainFamily, ToolChain, CodeBase)
1214 #
1215 # Only flags can be appended
1216 #
1217 if CurKey not in self._BuildOptions or not ToolChain.endswith('_FLAGS') or Option.startswith('='):
1218 self._BuildOptions[CurKey] = Option
1219 else:
1220 if ' ' + Option not in self._BuildOptions[CurKey]:
1221 self._BuildOptions[CurKey] += ' ' + Option
1222 return self._BuildOptions
1223
1224 def GetBuildOptionsByModuleType(self, Edk, ModuleType):
1225 if self._ModuleTypeOptions is None:
1226 self._ModuleTypeOptions = OrderedDict()
1227 if (Edk, ModuleType) not in self._ModuleTypeOptions:
1228 options = OrderedDict()
1229 self._ModuleTypeOptions[Edk, ModuleType] = options
1230 DriverType = '%s.%s' % (Edk, ModuleType)
1231 CommonDriverType = '%s.%s' % (TAB_COMMON, ModuleType)
1232 RecordList = self._RawData[MODEL_META_DATA_BUILD_OPTION, self._Arch]
1233 for ToolChainFamily, ToolChain, Option, Dummy1, Dummy2, Dummy3, Dummy4, Dummy5 in RecordList:
1234 Type = Dummy2 + '.' + Dummy3
1235 if Type.upper() == DriverType.upper() or Type.upper() == CommonDriverType.upper():
1236 Key = (ToolChainFamily, ToolChain, Edk)
1237 if Key not in options or not ToolChain.endswith('_FLAGS') or Option.startswith('='):
1238 options[Key] = Option
1239 else:
1240 if ' ' + Option not in options[Key]:
1241 options[Key] += ' ' + Option
1242 return self._ModuleTypeOptions[Edk, ModuleType]
1243
1244 @staticmethod
1245 def GetStructurePcdInfo(PcdSet):
1246 structure_pcd_data = defaultdict(list)
1247 for item in PcdSet:
1248 structure_pcd_data[(item[0], item[1])].append(item)
1249
1250 return structure_pcd_data
1251
1252 @staticmethod
1253 def OverrideByFdf(StruPcds,workspace):
1254 if GlobalData.gFdfParser is None:
1255 return StruPcds
1256 StructurePcdInFdf = OrderedDict()
1257 fdfpcd = GlobalData.gFdfParser.Profile.PcdDict
1258 fdfpcdlocation = GlobalData.gFdfParser.Profile.PcdLocalDict
1259 for item in fdfpcd :
1260 if len(item[2]) and (item[0],item[1]) in StruPcds:
1261 StructurePcdInFdf[(item[1],item[0],item[2] )] = fdfpcd[item]
1262 GlobalPcds = {(item[0],item[1]) for item in StructurePcdInFdf}
1263 for Pcd in StruPcds.values():
1264 if (Pcd.TokenSpaceGuidCName,Pcd.TokenCName) not in GlobalPcds:
1265 continue
1266 FieldValues = OrderedDict()
1267 for item in StructurePcdInFdf:
1268 if (Pcd.TokenSpaceGuidCName,Pcd.TokenCName) == (item[0],item[1]) and item[2]:
1269 FieldValues[item[2]] = StructurePcdInFdf[item]
1270 for field in FieldValues:
1271 if field not in Pcd.PcdFieldValueFromFdf:
1272 Pcd.PcdFieldValueFromFdf[field] = ["","",""]
1273 Pcd.PcdFieldValueFromFdf[field][0] = FieldValues[field]
1274 Pcd.PcdFieldValueFromFdf[field][1] = os.path.relpath(fdfpcdlocation[(Pcd.TokenCName,Pcd.TokenSpaceGuidCName,field)][0],workspace)
1275 Pcd.PcdFieldValueFromFdf[field][2] = fdfpcdlocation[(Pcd.TokenCName,Pcd.TokenSpaceGuidCName,field)][1]
1276
1277 return StruPcds
1278
1279 @staticmethod
1280 def OverrideByComm(StruPcds):
1281 StructurePcdInCom = OrderedDict()
1282 for item in GlobalData.BuildOptionPcd:
1283 if len(item) == 5 and (item[1], item[0]) in StruPcds:
1284 StructurePcdInCom[(item[0], item[1], item[2] )] = (item[3], item[4])
1285 GlobalPcds = {(item[0], item[1]) for item in StructurePcdInCom}
1286 for Pcd in StruPcds.values():
1287 if (Pcd.TokenSpaceGuidCName, Pcd.TokenCName) not in GlobalPcds:
1288 continue
1289 FieldValues = OrderedDict()
1290 for item in StructurePcdInCom:
1291 if (Pcd.TokenSpaceGuidCName, Pcd.TokenCName) == (item[0], item[1]) and item[2]:
1292 FieldValues[item[2]] = StructurePcdInCom[item]
1293 for field in FieldValues:
1294 if field not in Pcd.PcdFieldValueFromComm:
1295 Pcd.PcdFieldValueFromComm[field] = ["", "", ""]
1296 Pcd.PcdFieldValueFromComm[field][0] = FieldValues[field][0]
1297 Pcd.PcdFieldValueFromComm[field][1] = FieldValues[field][1][0]
1298 Pcd.PcdFieldValueFromComm[field][2] = FieldValues[field][1][1]
1299 return StruPcds
1300
1301 def OverrideByCommOverAll(self,AllPcds):
1302 def CheckStructureInComm(commpcds):
1303 if not commpcds:
1304 return False
1305 if len(commpcds[0]) == 5:
1306 return True
1307 return False
1308 NoFiledValues = OrderedDict()
1309 if CheckStructureInComm(GlobalData.BuildOptionPcd):
1310 StructurePcdInCom = OrderedDict()
1311 for item in GlobalData.BuildOptionPcd:
1312 StructurePcdInCom[(item[0], item[1], item[2] )] = (item[3], item[4])
1313 for item in StructurePcdInCom:
1314 if not item[2]:
1315 NoFiledValues[(item[0], item[1])] = StructurePcdInCom[item]
1316 else:
1317 for item in GlobalData.BuildOptionPcd:
1318 NoFiledValues[(item[0], item[1])] = [item[2]]
1319 for Guid, Name in NoFiledValues:
1320 if (Name, Guid) in AllPcds:
1321 Pcd = AllPcds.get((Name, Guid))
1322 if isinstance(self._DecPcds.get((Pcd.TokenCName, Pcd.TokenSpaceGuidCName), None), StructurePcd):
1323 self._DecPcds.get((Pcd.TokenCName, Pcd.TokenSpaceGuidCName)).PcdValueFromComm = NoFiledValues[(Pcd.TokenSpaceGuidCName, Pcd.TokenCName)][0]
1324 else:
1325 Pcd.PcdValueFromComm = NoFiledValues[(Pcd.TokenSpaceGuidCName, Pcd.TokenCName)][0]
1326 Pcd.DefaultValue = NoFiledValues[(Pcd.TokenSpaceGuidCName, Pcd.TokenCName)][0]
1327 for sku in Pcd.SkuInfoList:
1328 SkuInfo = Pcd.SkuInfoList[sku]
1329 if SkuInfo.DefaultValue:
1330 SkuInfo.DefaultValue = NoFiledValues[(Pcd.TokenSpaceGuidCName, Pcd.TokenCName)][0]
1331 else:
1332 SkuInfo.HiiDefaultValue = NoFiledValues[(Pcd.TokenSpaceGuidCName, Pcd.TokenCName)][0]
1333 for defaultstore in SkuInfo.DefaultStoreDict:
1334 SkuInfo.DefaultStoreDict[defaultstore] = NoFiledValues[(Pcd.TokenSpaceGuidCName, Pcd.TokenCName)][0]
1335 if Pcd.Type in [self._PCD_TYPE_STRING_[MODEL_PCD_DYNAMIC_EX_HII], self._PCD_TYPE_STRING_[MODEL_PCD_DYNAMIC_HII]]:
1336 if Pcd.DatumType == TAB_VOID:
1337 if not Pcd.MaxDatumSize:
1338 Pcd.MaxDatumSize = '0'
1339 CurrentSize = int(Pcd.MaxDatumSize, 16) if Pcd.MaxDatumSize.upper().startswith("0X") else int(Pcd.MaxDatumSize)
1340 OptionSize = len((StringToArray(Pcd.PcdValueFromComm)).split(","))
1341 MaxSize = max(CurrentSize, OptionSize)
1342 Pcd.MaxDatumSize = str(MaxSize)
1343 else:
1344 PcdInDec = self.DecPcds.get((Name, Guid))
1345 if PcdInDec:
1346 PcdInDec.PcdValueFromComm = NoFiledValues[(Guid, Name)][0]
1347 if PcdInDec.Type in [self._PCD_TYPE_STRING_[MODEL_PCD_FIXED_AT_BUILD],
1348 self._PCD_TYPE_STRING_[MODEL_PCD_PATCHABLE_IN_MODULE],
1349 self._PCD_TYPE_STRING_[MODEL_PCD_FEATURE_FLAG],
1350 self._PCD_TYPE_STRING_[MODEL_PCD_DYNAMIC],
1351 self._PCD_TYPE_STRING_[MODEL_PCD_DYNAMIC_EX]]:
1352 self.Pcds[Name, Guid] = copy.deepcopy(PcdInDec)
1353 self.Pcds[Name, Guid].DefaultValue = NoFiledValues[( Guid, Name)][0]
1354 if PcdInDec.Type in [self._PCD_TYPE_STRING_[MODEL_PCD_DYNAMIC],
1355 self._PCD_TYPE_STRING_[MODEL_PCD_DYNAMIC_EX]]:
1356 self.Pcds[Name, Guid].SkuInfoList = {TAB_DEFAULT:SkuInfoClass(TAB_DEFAULT, self.SkuIds[TAB_DEFAULT][0], '', '', '', '', '', NoFiledValues[( Guid, Name)][0])}
1357 return AllPcds
1358
1359 def OverrideByFdfOverAll(self,AllPcds):
1360
1361 if GlobalData.gFdfParser is None:
1362 return AllPcds
1363 NoFiledValues = GlobalData.gFdfParser.Profile.PcdDict
1364 for Name,Guid,Field in NoFiledValues:
1365 if len(Field):
1366 continue
1367 Value = NoFiledValues[(Name,Guid,Field)]
1368 if (Name,Guid) in AllPcds:
1369 Pcd = AllPcds.get((Name,Guid))
1370 if isinstance(self._DecPcds.get((Pcd.TokenCName,Pcd.TokenSpaceGuidCName), None),StructurePcd):
1371 self._DecPcds.get((Pcd.TokenCName,Pcd.TokenSpaceGuidCName)).PcdValueFromComm = Value
1372 else:
1373 Pcd.PcdValueFromComm = Value
1374 Pcd.DefaultValue = Value
1375 for sku in Pcd.SkuInfoList:
1376 SkuInfo = Pcd.SkuInfoList[sku]
1377 if SkuInfo.DefaultValue:
1378 SkuInfo.DefaultValue = Value
1379 else:
1380 SkuInfo.HiiDefaultValue = Value
1381 for defaultstore in SkuInfo.DefaultStoreDict:
1382 SkuInfo.DefaultStoreDict[defaultstore] = Value
1383 if Pcd.Type in [self._PCD_TYPE_STRING_[MODEL_PCD_DYNAMIC_EX_HII], self._PCD_TYPE_STRING_[MODEL_PCD_DYNAMIC_HII]]:
1384 if Pcd.DatumType == TAB_VOID:
1385 if not Pcd.MaxDatumSize:
1386 Pcd.MaxDatumSize = '0'
1387 CurrentSize = int(Pcd.MaxDatumSize,16) if Pcd.MaxDatumSize.upper().startswith("0X") else int(Pcd.MaxDatumSize)
1388 OptionSize = len((StringToArray(Pcd.PcdValueFromComm)).split(","))
1389 MaxSize = max(CurrentSize, OptionSize)
1390 Pcd.MaxDatumSize = str(MaxSize)
1391 else:
1392 PcdInDec = self.DecPcds.get((Name,Guid))
1393 if PcdInDec:
1394 PcdInDec.PcdValueFromFdf = Value
1395 if PcdInDec.Type in [self._PCD_TYPE_STRING_[MODEL_PCD_FIXED_AT_BUILD],
1396 self._PCD_TYPE_STRING_[MODEL_PCD_PATCHABLE_IN_MODULE],
1397 self._PCD_TYPE_STRING_[MODEL_PCD_FEATURE_FLAG]]:
1398 self.Pcds[Name, Guid] = copy.deepcopy(PcdInDec)
1399 self.Pcds[Name, Guid].DefaultValue = Value
1400 return AllPcds
1401
1402 def ParsePcdNameStruct(self,NamePart1,NamePart2):
1403 TokenSpaceCName = PcdCName = DimensionAttr = Field = ""
1404 if "." in NamePart1:
1405 TokenSpaceCName, TempPcdCName = NamePart1.split(".")
1406 if "[" in TempPcdCName:
1407 PcdCName = TempPcdCName[:TempPcdCName.index("[")]
1408 DimensionAttr = TempPcdCName[TempPcdCName.index("["):]
1409 else:
1410 PcdCName = TempPcdCName
1411 Field = NamePart2
1412 else:
1413 TokenSpaceCName = NamePart1
1414 if "[" in NamePart2:
1415 PcdCName = NamePart2[:NamePart2.index("[")]
1416 DimensionAttr = NamePart2[NamePart2.index("["):]
1417 else:
1418 PcdCName = NamePart2
1419
1420 return TokenSpaceCName,PcdCName,DimensionAttr,Field
1421
1422 def UpdateStructuredPcds(self, TypeList, AllPcds):
1423
1424 DynamicPcdType = [self._PCD_TYPE_STRING_[MODEL_PCD_DYNAMIC_DEFAULT],
1425 self._PCD_TYPE_STRING_[MODEL_PCD_DYNAMIC_HII],
1426 self._PCD_TYPE_STRING_[MODEL_PCD_DYNAMIC_VPD],
1427 self._PCD_TYPE_STRING_[MODEL_PCD_DYNAMIC_EX_DEFAULT],
1428 self._PCD_TYPE_STRING_[MODEL_PCD_DYNAMIC_EX_HII],
1429 self._PCD_TYPE_STRING_[MODEL_PCD_DYNAMIC_EX_VPD]]
1430
1431 Pcds = AllPcds
1432 DefaultStoreMgr = DefaultStore(self.DefaultStores)
1433 SkuIds = self.SkuIds
1434 self.SkuIdMgr.AvailableSkuIdSet.update({TAB_DEFAULT:0})
1435 DefaultStores = {storename for pcdobj in AllPcds.values() for skuobj in pcdobj.SkuInfoList.values() for storename in skuobj.DefaultStoreDict}
1436 DefaultStores.add(TAB_DEFAULT_STORES_DEFAULT)
1437
1438 S_PcdSet = []
1439 # Find out all possible PCD candidates for self._Arch
1440 RecordList = []
1441
1442 for Type in TypeList:
1443 RecordList.extend(self._RawData[Type, self._Arch])
1444
1445 for TokenSpaceGuid, PcdCName, Setting, Arch, SkuName, default_store, Dummy4, Dummy5 in RecordList:
1446 SkuName = SkuName.upper()
1447 default_store = default_store.upper()
1448 SkuName = TAB_DEFAULT if SkuName == TAB_COMMON else SkuName
1449 if SkuName not in SkuIds:
1450 continue
1451 TCName,PCName,DimensionAttr,Field = self.ParsePcdNameStruct(TokenSpaceGuid, PcdCName)
1452 pcd_in_dec = self._DecPcds.get((PCName,TCName), None)
1453 if pcd_in_dec is None:
1454 EdkLogger.error('build', PARSER_ERROR,
1455 "Pcd (%s.%s) defined in DSC is not declared in DEC files. Arch: ['%s']" % (TCName, PCName, self._Arch),
1456 File=self.MetaFile, Line = Dummy5)
1457 if SkuName in SkuIds and ("." in TokenSpaceGuid or "[" in PcdCName):
1458 if not isinstance (pcd_in_dec, StructurePcd):
1459 EdkLogger.error('build', PARSER_ERROR,
1460 "Pcd (%s.%s) is not declared as Structure PCD in DEC files. Arch: ['%s']" % (TCName, PCName, self._Arch),
1461 File=self.MetaFile, Line = Dummy5)
1462
1463 S_PcdSet.append([ TCName,PCName,DimensionAttr,Field, SkuName, default_store, Dummy5, AnalyzePcdExpression(Setting)[0]])
1464
1465 # handle pcd value override
1466 StrPcdSet = DscBuildData.GetStructurePcdInfo(S_PcdSet)
1467 S_pcd_set = OrderedDict()
1468 for str_pcd in StrPcdSet:
1469 str_pcd_obj = Pcds.get((str_pcd[1], str_pcd[0]), None)
1470 str_pcd_dec = self._DecPcds.get((str_pcd[1], str_pcd[0]), None)
1471 str_pcd_obj_str = StructurePcd()
1472 str_pcd_obj_str.copy(str_pcd_dec)
1473 if str_pcd_obj:
1474 str_pcd_obj_str.copy(str_pcd_obj)
1475 if str_pcd_obj.Type in [self._PCD_TYPE_STRING_[MODEL_PCD_DYNAMIC_HII], self._PCD_TYPE_STRING_[MODEL_PCD_DYNAMIC_EX_HII]]:
1476 str_pcd_obj_str.DefaultFromDSC = {skuname:{defaultstore: str_pcd_obj.SkuInfoList[skuname].DefaultStoreDict.get(defaultstore, str_pcd_obj.SkuInfoList[skuname].HiiDefaultValue) for defaultstore in DefaultStores} for skuname in str_pcd_obj.SkuInfoList}
1477 else:
1478 str_pcd_obj_str.DefaultFromDSC = {skuname:{defaultstore: str_pcd_obj.SkuInfoList[skuname].DefaultStoreDict.get(defaultstore, str_pcd_obj.SkuInfoList[skuname].DefaultValue) for defaultstore in DefaultStores} for skuname in str_pcd_obj.SkuInfoList}
1479 for str_pcd_data in StrPcdSet[str_pcd]:
1480 if str_pcd_data[4] in SkuIds:
1481 str_pcd_obj_str.AddOverrideValue(str_pcd_data[3], str(str_pcd_data[7]), TAB_DEFAULT if str_pcd_data[4] == TAB_COMMON else str_pcd_data[4], TAB_DEFAULT_STORES_DEFAULT if str_pcd_data[5] == TAB_COMMON else str_pcd_data[5], self.MetaFile.File if self.WorkspaceDir not in self.MetaFile.File else self.MetaFile.File[len(self.WorkspaceDir) if self.WorkspaceDir.endswith(os.path.sep) else len(self.WorkspaceDir)+1:], LineNo=str_pcd_data[6],DimensionAttr = str_pcd_data[2])
1482 S_pcd_set[str_pcd[1], str_pcd[0]] = str_pcd_obj_str
1483
1484 # Add the Structure PCD that only defined in DEC, don't have override in DSC file
1485 for Pcd in self.DecPcds:
1486 if isinstance(self._DecPcds[Pcd], StructurePcd):
1487 if Pcd not in S_pcd_set:
1488 str_pcd_obj_str = StructurePcd()
1489 str_pcd_obj_str.copy(self._DecPcds[Pcd])
1490 str_pcd_obj = Pcds.get(Pcd, None)
1491 if str_pcd_obj:
1492 str_pcd_obj_str.copy(str_pcd_obj)
1493 if str_pcd_obj.Type in [self._PCD_TYPE_STRING_[MODEL_PCD_DYNAMIC_HII], self._PCD_TYPE_STRING_[MODEL_PCD_DYNAMIC_EX_HII]]:
1494 str_pcd_obj_str.DefaultFromDSC = {skuname:{defaultstore: str_pcd_obj.SkuInfoList[skuname].DefaultStoreDict.get(defaultstore, str_pcd_obj.SkuInfoList[skuname].HiiDefaultValue) for defaultstore in DefaultStores} for skuname in str_pcd_obj.SkuInfoList}
1495 else:
1496 str_pcd_obj_str.DefaultFromDSC = {skuname:{defaultstore: str_pcd_obj.SkuInfoList[skuname].DefaultStoreDict.get(defaultstore, str_pcd_obj.SkuInfoList[skuname].DefaultValue) for defaultstore in DefaultStores} for skuname in str_pcd_obj.SkuInfoList}
1497 S_pcd_set[Pcd] = str_pcd_obj_str
1498 self.FilterStrcturePcd(S_pcd_set)
1499 if S_pcd_set:
1500 GlobalData.gStructurePcd[self.Arch] = S_pcd_set
1501 for stru_pcd in S_pcd_set.values():
1502 for skuid in SkuIds:
1503 if skuid in stru_pcd.SkuOverrideValues:
1504 continue
1505 nextskuid = self.SkuIdMgr.GetNextSkuId(skuid)
1506 NoDefault = False
1507 if skuid not in stru_pcd.SkuOverrideValues:
1508 while nextskuid not in stru_pcd.SkuOverrideValues:
1509 if nextskuid == TAB_DEFAULT:
1510 NoDefault = True
1511 break
1512 nextskuid = self.SkuIdMgr.GetNextSkuId(nextskuid)
1513 stru_pcd.SkuOverrideValues[skuid] = copy.deepcopy(stru_pcd.SkuOverrideValues[nextskuid]) if not NoDefault else copy.deepcopy({defaultstorename: stru_pcd.DefaultValues for defaultstorename in DefaultStores} if DefaultStores else {}) #{TAB_DEFAULT_STORES_DEFAULT:stru_pcd.DefaultValues})
1514 if not NoDefault:
1515 stru_pcd.ValueChain.add((skuid, ''))
1516 if stru_pcd.Type in [self._PCD_TYPE_STRING_[MODEL_PCD_DYNAMIC_HII], self._PCD_TYPE_STRING_[MODEL_PCD_DYNAMIC_EX_HII]]:
1517 for skuid in SkuIds:
1518 nextskuid = skuid
1519 NoDefault = False
1520 if skuid not in stru_pcd.SkuOverrideValues:
1521 while nextskuid not in stru_pcd.SkuOverrideValues:
1522 if nextskuid == TAB_DEFAULT:
1523 NoDefault = True
1524 break
1525 nextskuid = self.SkuIdMgr.GetNextSkuId(nextskuid)
1526 if NoDefault:
1527 continue
1528 PcdDefaultStoreSet = set(defaultstorename for defaultstorename in stru_pcd.SkuOverrideValues[nextskuid])
1529 mindefaultstorename = DefaultStoreMgr.GetMin(PcdDefaultStoreSet)
1530
1531 for defaultstoreid in DefaultStores:
1532 if defaultstoreid not in stru_pcd.SkuOverrideValues[skuid]:
1533 stru_pcd.SkuOverrideValues[skuid][defaultstoreid] = CopyDict(stru_pcd.SkuOverrideValues[nextskuid][mindefaultstorename])
1534 stru_pcd.ValueChain.add((skuid, defaultstoreid))
1535 S_pcd_set = DscBuildData.OverrideByFdf(S_pcd_set,self.WorkspaceDir)
1536 S_pcd_set = DscBuildData.OverrideByComm(S_pcd_set)
1537 Str_Pcd_Values = self.GenerateByteArrayValue(S_pcd_set)
1538 if Str_Pcd_Values:
1539 for (skuname, StoreName, PcdGuid, PcdName, PcdValue) in Str_Pcd_Values:
1540 str_pcd_obj = S_pcd_set.get((PcdName, PcdGuid))
1541 if str_pcd_obj is None:
1542 print(PcdName, PcdGuid)
1543 raise
1544 if str_pcd_obj.Type in [self._PCD_TYPE_STRING_[MODEL_PCD_DYNAMIC_HII],
1545 self._PCD_TYPE_STRING_[MODEL_PCD_DYNAMIC_EX_HII]]:
1546 if skuname not in str_pcd_obj.SkuInfoList:
1547 str_pcd_obj.SkuInfoList[skuname] = SkuInfoClass(SkuIdName=skuname, SkuId=self.SkuIds[skuname][0], HiiDefaultValue=PcdValue, DefaultStore = {StoreName:PcdValue})
1548 else:
1549 str_pcd_obj.SkuInfoList[skuname].HiiDefaultValue = PcdValue
1550 str_pcd_obj.SkuInfoList[skuname].DefaultStoreDict.update({StoreName:PcdValue})
1551 elif str_pcd_obj.Type in [self._PCD_TYPE_STRING_[MODEL_PCD_FIXED_AT_BUILD],
1552 self._PCD_TYPE_STRING_[MODEL_PCD_PATCHABLE_IN_MODULE]]:
1553 if skuname in (self.SkuIdMgr.SystemSkuId, TAB_DEFAULT, TAB_COMMON):
1554 str_pcd_obj.DefaultValue = PcdValue
1555 else:
1556 if skuname not in str_pcd_obj.SkuInfoList:
1557 nextskuid = self.SkuIdMgr.GetNextSkuId(skuname)
1558 NoDefault = False
1559 while nextskuid not in str_pcd_obj.SkuInfoList:
1560 if nextskuid == TAB_DEFAULT:
1561 NoDefault = True
1562 break
1563 nextskuid = self.SkuIdMgr.GetNextSkuId(nextskuid)
1564 str_pcd_obj.SkuInfoList[skuname] = copy.deepcopy(str_pcd_obj.SkuInfoList[nextskuid]) if not NoDefault else SkuInfoClass(SkuIdName=skuname, SkuId=self.SkuIds[skuname][0], DefaultValue=PcdValue)
1565 str_pcd_obj.SkuInfoList[skuname].SkuId = self.SkuIds[skuname][0]
1566 str_pcd_obj.SkuInfoList[skuname].SkuIdName = skuname
1567 else:
1568 str_pcd_obj.SkuInfoList[skuname].DefaultValue = PcdValue
1569 for str_pcd_obj in S_pcd_set.values():
1570 if str_pcd_obj.Type not in [self._PCD_TYPE_STRING_[MODEL_PCD_DYNAMIC_HII],
1571 self._PCD_TYPE_STRING_[MODEL_PCD_DYNAMIC_EX_HII]]:
1572 continue
1573 PcdDefaultStoreSet = set(defaultstorename for skuobj in str_pcd_obj.SkuInfoList.values() for defaultstorename in skuobj.DefaultStoreDict)
1574 DefaultStoreObj = DefaultStore(self._GetDefaultStores())
1575 mindefaultstorename = DefaultStoreObj.GetMin(PcdDefaultStoreSet)
1576 str_pcd_obj.SkuInfoList[self.SkuIdMgr.SystemSkuId].HiiDefaultValue = str_pcd_obj.SkuInfoList[self.SkuIdMgr.SystemSkuId].DefaultStoreDict[mindefaultstorename]
1577
1578 for str_pcd_obj in S_pcd_set.values():
1579
1580 str_pcd_obj.MaxDatumSize = DscBuildData.GetStructurePcdMaxSize(str_pcd_obj)
1581 Pcds[str_pcd_obj.TokenCName, str_pcd_obj.TokenSpaceGuidCName] = str_pcd_obj
1582 Pcds[str_pcd_obj.TokenCName, str_pcd_obj.TokenSpaceGuidCName].CustomAttribute['IsStru']=True
1583
1584 for pcdkey in Pcds:
1585 pcd = Pcds[pcdkey]
1586 if TAB_DEFAULT not in pcd.SkuInfoList and TAB_COMMON in pcd.SkuInfoList:
1587 pcd.SkuInfoList[TAB_DEFAULT] = pcd.SkuInfoList[TAB_COMMON]
1588 del pcd.SkuInfoList[TAB_COMMON]
1589 elif TAB_DEFAULT in pcd.SkuInfoList and TAB_COMMON in pcd.SkuInfoList:
1590 del pcd.SkuInfoList[TAB_COMMON]
1591
1592 map(self.FilterSkuSettings, [Pcds[pcdkey] for pcdkey in Pcds if Pcds[pcdkey].Type in DynamicPcdType])
1593 return Pcds
1594 @cached_property
1595 def PlatformUsedPcds(self):
1596 FdfInfList = []
1597 if GlobalData.gFdfParser:
1598 FdfInfList = GlobalData.gFdfParser.Profile.InfList
1599 FdfModuleList = [PathClass(NormPath(Inf), GlobalData.gWorkspace, Arch=self._Arch) for Inf in FdfInfList]
1600 AllModulePcds = set()
1601 ModuleSet = set(self._Modules.keys() + FdfModuleList)
1602 for ModuleFile in ModuleSet:
1603 ModuleData = self._Bdb[ModuleFile, self._Arch, self._Target, self._Toolchain]
1604 AllModulePcds = AllModulePcds | ModuleData.PcdsName
1605 for ModuleFile in self.LibraryInstances:
1606 ModuleData = self._Bdb.CreateBuildObject(ModuleFile, self._Arch, self._Target, self._Toolchain)
1607 AllModulePcds = AllModulePcds | ModuleData.PcdsName
1608 return AllModulePcds
1609
1610 #Filter the StrucutrePcd that is not used by any module in dsc file and fdf file.
1611 def FilterStrcturePcd(self, S_pcd_set):
1612 UnusedStruPcds = set(S_pcd_set.keys()) - self.PlatformUsedPcds
1613 for (Token, TokenSpaceGuid) in UnusedStruPcds:
1614 del S_pcd_set[(Token, TokenSpaceGuid)]
1615
1616 ## Retrieve non-dynamic PCD settings
1617 #
1618 # @param Type PCD type
1619 #
1620 # @retval a dict object contains settings of given PCD type
1621 #
1622 def _GetPcd(self, Type):
1623 Pcds = OrderedDict()
1624 #
1625 # tdict is a special dict kind of type, used for selecting correct
1626 # PCD settings for certain ARCH
1627 #
1628 AvailableSkuIdSet = copy.copy(self.SkuIds)
1629
1630 PcdDict = tdict(True, 4)
1631 PcdSet = set()
1632 # Find out all possible PCD candidates for self._Arch
1633 RecordList = self._RawData[Type, self._Arch]
1634 PcdValueDict = OrderedDict()
1635 for TokenSpaceGuid, PcdCName, Setting, Arch, SkuName, Dummy3, Dummy4, Dummy5 in RecordList:
1636 SkuName = SkuName.upper()
1637 SkuName = TAB_DEFAULT if SkuName == TAB_COMMON else SkuName
1638 if SkuName not in AvailableSkuIdSet:
1639 EdkLogger.error('build ', PARAMETER_INVALID, 'Sku %s is not defined in [SkuIds] section' % SkuName,
1640 File=self.MetaFile, Line=Dummy5)
1641 if SkuName in (self.SkuIdMgr.SystemSkuId, TAB_DEFAULT, TAB_COMMON):
1642 if "." not in TokenSpaceGuid and "[" not in PcdCName:
1643 PcdSet.add((PcdCName, TokenSpaceGuid, SkuName, Dummy5))
1644 PcdDict[Arch, PcdCName, TokenSpaceGuid, SkuName] = Setting
1645
1646 for PcdCName, TokenSpaceGuid, SkuName, Dummy4 in PcdSet:
1647 Setting = PcdDict[self._Arch, PcdCName, TokenSpaceGuid, SkuName]
1648 if Setting is None:
1649 continue
1650 PcdValue, DatumType, MaxDatumSize = self._ValidatePcd(PcdCName, TokenSpaceGuid, Setting, Type, Dummy4)
1651 if MaxDatumSize:
1652 if int(MaxDatumSize, 0) > 0xFFFF:
1653 EdkLogger.error('build', FORMAT_INVALID, "The size value must not exceed the maximum value of 0xFFFF (UINT16) for %s." % ".".join((TokenSpaceGuid, PcdCName)),
1654 File=self.MetaFile, Line=Dummy4)
1655 if int(MaxDatumSize, 0) < 0:
1656 EdkLogger.error('build', FORMAT_INVALID, "The size value can't be set to negative value for %s." % ".".join((TokenSpaceGuid, PcdCName)),
1657 File=self.MetaFile, Line=Dummy4)
1658 if (PcdCName, TokenSpaceGuid) in PcdValueDict:
1659 PcdValueDict[PcdCName, TokenSpaceGuid][SkuName] = (PcdValue, DatumType, MaxDatumSize)
1660 else:
1661 PcdValueDict[PcdCName, TokenSpaceGuid] = {SkuName:(PcdValue, DatumType, MaxDatumSize)}
1662
1663 for ((PcdCName, TokenSpaceGuid), PcdSetting) in PcdValueDict.iteritems():
1664 if self.SkuIdMgr.SystemSkuId in PcdSetting:
1665 PcdValue, DatumType, MaxDatumSize = PcdSetting[self.SkuIdMgr.SystemSkuId]
1666 elif TAB_DEFAULT in PcdSetting:
1667 PcdValue, DatumType, MaxDatumSize = PcdSetting[TAB_DEFAULT]
1668 elif TAB_COMMON in PcdSetting:
1669 PcdValue, DatumType, MaxDatumSize = PcdSetting[TAB_COMMON]
1670 else:
1671 PcdValue = None
1672 DatumType = None
1673 MaxDatumSize = None
1674
1675 Pcds[PcdCName, TokenSpaceGuid] = PcdClassObject(
1676 PcdCName,
1677 TokenSpaceGuid,
1678 self._PCD_TYPE_STRING_[Type],
1679 DatumType,
1680 PcdValue,
1681 '',
1682 MaxDatumSize,
1683 {},
1684 False,
1685 None,
1686 IsDsc=True)
1687 for SkuName in PcdValueDict[PcdCName, TokenSpaceGuid]:
1688 Settings = PcdValueDict[PcdCName, TokenSpaceGuid][SkuName]
1689 if SkuName not in Pcds[PcdCName, TokenSpaceGuid].DscRawValue:
1690 Pcds[PcdCName, TokenSpaceGuid].DscRawValue[SkuName] = {}
1691 Pcds[PcdCName, TokenSpaceGuid].DscRawValue[SkuName][TAB_DEFAULT_STORES_DEFAULT] = Settings[0]
1692 return Pcds
1693
1694 @staticmethod
1695 def GetStructurePcdMaxSize(str_pcd):
1696 pcd_default_value = str_pcd.DefaultValue
1697 sku_values = [skuobj.HiiDefaultValue if str_pcd.Type in [DscBuildData._PCD_TYPE_STRING_[MODEL_PCD_DYNAMIC_HII], DscBuildData._PCD_TYPE_STRING_[MODEL_PCD_DYNAMIC_EX_HII]] else skuobj.DefaultValue for skuobj in str_pcd.SkuInfoList.values()]
1698 sku_values.append(pcd_default_value)
1699
1700 def get_length(value):
1701 Value = value.strip()
1702 if len(value) > 1:
1703 if Value.startswith(TAB_GUID) and Value.endswith(')'):
1704 return 16
1705 if Value.startswith('L"') and Value.endswith('"'):
1706 return len(Value[2:-1])
1707 if Value[0] == '"' and Value[-1] == '"':
1708 return len(Value) - 2
1709 if Value.strip().startswith("{CODE("):
1710 tmpValue = RemoveCComments(Value)
1711 return len(tmpValue.split(","))
1712 if (Value[0] == '{' and Value[-1] == '}'):
1713 return len(Value.split(","))
1714 if Value.startswith("L'") and Value.endswith("'") and len(list(Value[2:-1])) > 1:
1715 return len(list(Value[2:-1]))
1716 if Value[0] == "'" and Value[-1] == "'" and len(list(Value[1:-1])) > 1:
1717 return len(Value) - 2
1718 return len(Value)
1719
1720 return str(max(get_length(item) for item in sku_values))
1721
1722 @staticmethod
1723 def ExecuteCommand (Command):
1724 try:
1725 Process = subprocess.Popen(Command, stdout=subprocess.PIPE, stderr=subprocess.PIPE, shell=True)
1726 except:
1727 EdkLogger.error('Build', COMMAND_FAILURE, 'Can not execute command: %s' % Command)
1728 Result = Process.communicate()
1729 return Process.returncode, Result[0], Result[1]
1730
1731 @staticmethod
1732 def IntToCString(Value, ValueSize):
1733 Result = '"'
1734 if not isinstance (Value, str):
1735 for Index in range(0, ValueSize):
1736 Result = Result + '\\x%02x' % (Value & 0xff)
1737 Value = Value >> 8
1738 Result = Result + '"'
1739 return Result
1740
1741 def GenerateSizeFunction(self, Pcd):
1742 CApp = "// Default Value in Dec \n"
1743 CApp = CApp + "void Cal_%s_%s_Size(UINT32 *Size){\n" % (Pcd.TokenSpaceGuidCName, Pcd.TokenCName)
1744 if Pcd.IsArray():
1745 if Pcd.Type in PCD_DYNAMIC_TYPE_SET | PCD_DYNAMIC_EX_TYPE_SET:
1746 for skuname in Pcd.SkuInfoList:
1747 skuobj = Pcd.SkuInfoList[skuname]
1748 if skuobj.VariableName:
1749 for defaultstore in skuobj.DefaultStoreDict:
1750 pcddef = self.GetPcdDscRawDefaultValue(Pcd,skuname,defaultstore)
1751 if pcddef and "{CODE(" in pcddef:
1752 CApp += " *Size = (sizeof (%s_%s_%s_%s_Value) > *Size ? sizeof (%s_%s_%s_%s_Value) : *Size);\n" % (Pcd.TokenSpaceGuidCName,Pcd.TokenCName,skuname,defaultstore,Pcd.TokenSpaceGuidCName,Pcd.TokenCName,skuname,defaultstore)
1753 else:
1754 pcddef = self.GetPcdDscRawDefaultValue(Pcd,skuname,TAB_DEFAULT_STORES_DEFAULT)
1755 if pcddef and "{CODE(" in pcddef:
1756 CApp += " *Size = (sizeof (%s_%s_%s_%s_Value) > *Size ? sizeof (%s_%s_%s_%s_Value) : *Size);\n" % (Pcd.TokenSpaceGuidCName,Pcd.TokenCName,skuname,TAB_DEFAULT_STORES_DEFAULT,Pcd.TokenSpaceGuidCName,Pcd.TokenCName,skuname,TAB_DEFAULT_STORES_DEFAULT)
1757 else:
1758 pcddef = self.GetPcdDscRawDefaultValue(Pcd,TAB_DEFAULT,TAB_DEFAULT_STORES_DEFAULT)
1759 if pcddef and "{CODE(" in pcddef:
1760 CApp += " *Size = (sizeof (%s_%s_%s_%s_Value) > *Size ? sizeof (%s_%s_%s_%s_Value) : *Size);\n" % (Pcd.TokenSpaceGuidCName,Pcd.TokenCName,TAB_DEFAULT,TAB_DEFAULT_STORES_DEFAULT,Pcd.TokenSpaceGuidCName,Pcd.TokenCName,TAB_DEFAULT,TAB_DEFAULT_STORES_DEFAULT)
1761 for index in Pcd.DefaultValues:
1762 FieldList = Pcd.DefaultValues[index]
1763 if not FieldList:
1764 continue
1765 for FieldName in FieldList:
1766 FieldName = "." + FieldName
1767 IsArray = IsFieldValueAnArray(FieldList[FieldName.strip(".")][0])
1768 if IsArray and not (FieldList[FieldName.strip(".")][0].startswith('{GUID') and FieldList[FieldName.strip(".")][0].endswith('}')):
1769 try:
1770 Value = ValueExpressionEx(FieldList[FieldName.strip(".")][0], TAB_VOID, self._GuidDict)(True)
1771 except BadExpression:
1772 EdkLogger.error('Build', FORMAT_INVALID, "Invalid value format for %s. From %s Line %d " %
1773 (".".join((Pcd.TokenSpaceGuidCName, Pcd.TokenCName, FieldName.strip('.'))), FieldList[FieldName.strip(".")][1], FieldList[FieldName.strip(".")][2]))
1774 Value, ValueSize = ParseFieldValue(Value)
1775 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("."), FieldList[FieldName.strip(".")][1], FieldList[FieldName.strip(".")][2], FieldList[FieldName.strip(".")][0]);
1776 else:
1777 NewFieldName = ''
1778 FieldName_ori = FieldName.strip('.')
1779 while '[' in FieldName:
1780 NewFieldName = NewFieldName + FieldName.split('[', 1)[0] + '[0]'
1781 ArrayIndex = int(FieldName.split('[', 1)[1].split(']', 1)[0])
1782 FieldName = FieldName.split(']', 1)[1]
1783 FieldName = NewFieldName + FieldName
1784 while '[' in FieldName:
1785 FieldName = FieldName.rsplit('[', 1)[0]
1786 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])
1787 for skuname in Pcd.SkuOverrideValues:
1788 if skuname == TAB_COMMON:
1789 continue
1790 for defaultstorenameitem in Pcd.SkuOverrideValues[skuname]:
1791 CApp = CApp + "// SkuName: %s, DefaultStoreName: %s \n" % (skuname, defaultstorenameitem)
1792 for index in Pcd.SkuOverrideValues[skuname][defaultstorenameitem]:
1793 for FieldList in [Pcd.SkuOverrideValues[skuname][defaultstorenameitem][index]]:
1794 if not FieldList:
1795 continue
1796 for FieldName in FieldList:
1797 FieldName = "." + FieldName
1798 IsArray = IsFieldValueAnArray(FieldList[FieldName.strip(".")][0])
1799 if IsArray and not (FieldList[FieldName.strip(".")][0].startswith('{GUID') and FieldList[FieldName.strip(".")][0].endswith('}')):
1800 try:
1801 Value = ValueExpressionEx(FieldList[FieldName.strip(".")][0], TAB_VOID, self._GuidDict)(True)
1802 except BadExpression:
1803 EdkLogger.error('Build', FORMAT_INVALID, "Invalid value format for %s. From %s Line %d " %
1804 (".".join((Pcd.TokenSpaceGuidCName, Pcd.TokenCName, FieldName.strip('.'))), FieldList[FieldName.strip(".")][1], FieldList[FieldName.strip(".")][2]))
1805 Value, ValueSize = ParseFieldValue(Value)
1806 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("."), FieldList[FieldName.strip(".")][1], FieldList[FieldName.strip(".")][2], FieldList[FieldName.strip(".")][0]);
1807 else:
1808 NewFieldName = ''
1809 FieldName_ori = FieldName.strip('.')
1810 while '[' in FieldName:
1811 NewFieldName = NewFieldName + FieldName.split('[', 1)[0] + '[0]'
1812 ArrayIndex = int(FieldName.split('[', 1)[1].split(']', 1)[0])
1813 FieldName = FieldName.split(']', 1)[1]
1814 FieldName = NewFieldName + FieldName
1815 while '[' in FieldName:
1816 FieldName = FieldName.rsplit('[', 1)[0]
1817 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])
1818 if Pcd.PcdFieldValueFromFdf:
1819 CApp = CApp + "// From fdf \n"
1820 for FieldName in Pcd.PcdFieldValueFromFdf:
1821 FieldName = "." + FieldName
1822 IsArray = IsFieldValueAnArray(Pcd.PcdFieldValueFromFdf[FieldName.strip(".")][0])
1823 if IsArray and not (Pcd.PcdFieldValueFromFdf[FieldName.strip(".")][0].startswith('{GUID') and Pcd.PcdFieldValueFromFdf[FieldName.strip(".")][0].endswith('}')):
1824 try:
1825 Value = ValueExpressionEx(Pcd.PcdFieldValueFromFdf[FieldName.strip(".")][0], TAB_VOID, self._GuidDict)(True)
1826 except BadExpression:
1827 EdkLogger.error('Build', FORMAT_INVALID, "Invalid value format for %s. From %s Line %d " %
1828 (".".join((Pcd.TokenSpaceGuidCName, Pcd.TokenCName, FieldName.strip('.'))), Pcd.PcdFieldValueFromFdf[FieldName.strip(".")][1], Pcd.PcdFieldValueFromFdf[FieldName.strip(".")][2]))
1829 Value, ValueSize = ParseFieldValue(Value)
1830 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]);
1831 else:
1832 NewFieldName = ''
1833 FieldName_ori = FieldName.strip('.')
1834 while '[' in FieldName:
1835 NewFieldName = NewFieldName + FieldName.split('[', 1)[0] + '[0]'
1836 ArrayIndex = int(FieldName.split('[', 1)[1].split(']', 1)[0])
1837 FieldName = FieldName.split(']', 1)[1]
1838 FieldName = NewFieldName + FieldName
1839 while '[' in FieldName:
1840 FieldName = FieldName.rsplit('[', 1)[0]
1841 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])
1842 if Pcd.PcdFieldValueFromComm:
1843 CApp = CApp + "// From Command Line \n"
1844 for FieldName in Pcd.PcdFieldValueFromComm:
1845 FieldName = "." + FieldName
1846 IsArray = IsFieldValueAnArray(Pcd.PcdFieldValueFromComm[FieldName.strip(".")][0])
1847 if IsArray and not (Pcd.PcdFieldValueFromComm[FieldName.strip(".")][0].startswith('{GUID') and Pcd.PcdFieldValueFromComm[FieldName.strip(".")][0].endswith('}')):
1848 try:
1849 Value = ValueExpressionEx(Pcd.PcdFieldValueFromComm[FieldName.strip(".")][0], TAB_VOID, self._GuidDict)(True)
1850 except BadExpression:
1851 EdkLogger.error('Build', FORMAT_INVALID, "Invalid value format for %s. From %s Line %d " %
1852 (".".join((Pcd.TokenSpaceGuidCName, Pcd.TokenCName, FieldName.strip('.'))), Pcd.PcdFieldValueFromComm[FieldName.strip(".")][1], Pcd.PcdFieldValueFromComm[FieldName.strip(".")][2]))
1853 Value, ValueSize = ParseFieldValue(Value)
1854 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.PcdFieldValueFromComm[FieldName.strip(".")][1], Pcd.PcdFieldValueFromComm[FieldName.strip(".")][2], Pcd.PcdFieldValueFromComm[FieldName.strip(".")][0]);
1855 else:
1856 NewFieldName = ''
1857 FieldName_ori = FieldName.strip('.')
1858 while '[' in FieldName:
1859 NewFieldName = NewFieldName + FieldName.split('[', 1)[0] + '[0]'
1860 ArrayIndex = int(FieldName.split('[', 1)[1].split(']', 1)[0])
1861 FieldName = FieldName.split(']', 1)[1]
1862 FieldName = NewFieldName + FieldName
1863 while '[' in FieldName:
1864 FieldName = FieldName.rsplit('[', 1)[0]
1865 CApp = CApp + ' __FLEXIBLE_SIZE(*Size, %s, %s, %d); // From %s Line %d Value %s \n' % (Pcd.DatumType, FieldName.strip("."), ArrayIndex + 1, Pcd.PcdFieldValueFromComm[FieldName_ori][1], Pcd.PcdFieldValueFromComm[FieldName_ori][2], Pcd.PcdFieldValueFromComm[FieldName_ori][0])
1866 if Pcd.GetPcdMaxSize():
1867 CApp = CApp + " *Size = (%d > *Size ? %d : *Size); // The Pcd maxsize is %d \n" % (Pcd.GetPcdMaxSize(), Pcd.GetPcdMaxSize(), Pcd.GetPcdMaxSize())
1868 CApp = CApp + "}\n"
1869 return CApp
1870
1871 @staticmethod
1872 def GenerateSizeStatments(Pcd,skuname,defaultstorename):
1873 if Pcd.IsArray():
1874 r_datatype = [Pcd.BaseDatumType]
1875 lastoneisEmpty = False
1876 for dem in Pcd.Capacity:
1877 if lastoneisEmpty:
1878 EdkLogger.error('Build', FORMAT_INVALID, "Invalid value format for %s. " %
1879 (".".join((Pcd.TokenSpaceGuidCName, Pcd.TokenCName))))
1880 if dem == '0' or dem == "-1":
1881 r_datatype.append("[1]")
1882 lastoneisEmpty = True
1883 else:
1884 r_datatype.append("[" + dem + "]")
1885
1886 if Pcd.Type in [MODEL_PCD_DYNAMIC_EX_HII, MODEL_PCD_DYNAMIC_HII]:
1887 PcdDefValue = Pcd.SkuInfoList.get(skuname).DefaultStoreDict.get(defaultstorename)
1888 elif Pcd.Type in [MODEL_PCD_DYNAMIC_EX_DEFAULT,MODEL_PCD_DYNAMIC_VPD,MODEL_PCD_DYNAMIC_DEFAULT,MODEL_PCD_DYNAMIC_EX_VPD]:
1889 PcdDefValue = Pcd.SkuInfoList.get(skuname).DefaultValue
1890 else:
1891 PcdDefValue = Pcd.DefaultValue
1892 if lastoneisEmpty:
1893 if "{CODE(" not in PcdDefValue:
1894 sizebasevalue_plus = "(%s / sizeof(%s) + 1)" % ((DscBuildData.GetStructurePcdMaxSize(Pcd), "".join(r_datatype)))
1895 sizebasevalue = "(%s / sizeof(%s))" % ((DscBuildData.GetStructurePcdMaxSize(Pcd), "".join(r_datatype)))
1896 sizeof = "sizeof(%s)" % Pcd.BaseDatumType
1897 CApp = ' Size = %s %% %s ? %s : %s ;\n' % ( (DscBuildData.GetStructurePcdMaxSize(Pcd), sizeof, sizebasevalue_plus, sizebasevalue))
1898 else:
1899 CApp = " Size = 0;\n"
1900 else:
1901 CApp = ' Size = sizeof(%s);\n' % ("".join(r_datatype) )
1902 else:
1903 CApp = ' Size = sizeof(%s);\n' % (Pcd.DatumType)
1904 CApp = CApp + ' Cal_%s_%s_Size(&Size);\n' % (Pcd.TokenSpaceGuidCName, Pcd.TokenCName)
1905 return CApp
1906
1907 def GetIndicator(self,index,FieldName,Pcd):
1908 def cleanupindex(indexstr):
1909 return indexstr.strip("[").strip("]").strip()
1910 index_elements = ArrayIndex.findall(index)
1911 pcd_capacity = Pcd.Capacity
1912 if index:
1913 indicator = "(Pcd"
1914 if len(pcd_capacity)>2:
1915 for i in xrange(0,len(index_elements)):
1916 index_ele = index_elements[i]
1917 index_num = index_ele.strip("[").strip("]").strip()
1918 if i == len(index_elements) -2:
1919 indicator += "+ %d*Size/sizeof(%s)/%d + %s)" %(int(cleanupindex(index_elements[i+1])),Pcd.BaseDatumType,reduce(lambda x,y: int(x)*int(y),pcd_capacity[:-1]), cleanupindex(index_elements[i]))
1920 break
1921 else:
1922 indicator += " + %d*%s*Size/sizeof(%s)/%d" %(int(cleanupindex(index_elements[i])),reduce(lambda x,y: int(x)*int(y),pcd_capacity[i+1:-1]),Pcd.BaseDatumType,reduce(lambda x,y: int(x)*int(y),pcd_capacity[:-1]))
1923 elif len(pcd_capacity) == 2:
1924 indicator += "+ %d*Size/sizeof(%s)/%d + %s)" %(int(cleanupindex(index_elements[0])),Pcd.BaseDatumType,int(pcd_capacity[0]), index_elements[1].strip("[").strip("]").strip())
1925 elif len(pcd_capacity) == 1:
1926 index_ele = index_elements[0]
1927 index_num = index_ele.strip("[").strip("]").strip()
1928 indicator += " + %s)" % (index_num)
1929 else:
1930 indicator = "Pcd"
1931 if FieldName:
1932 indicator += "->" + FieldName
1933 return indicator
1934
1935 def GetStarNum(self,Pcd):
1936 if not Pcd.IsArray():
1937 return 1
1938 elif Pcd.IsSimpleTypeArray():
1939 return len(Pcd.Capacity)
1940 else:
1941 return len(Pcd.Capacity) + 1
1942 def GenerateDefaultValueAssignFunction(self, Pcd):
1943 CApp = "// Default value in Dec \n"
1944 CApp = CApp + "void Assign_%s_%s_Default_Value(%s *Pcd){\n" % (Pcd.TokenSpaceGuidCName, Pcd.TokenCName, Pcd.BaseDatumType)
1945 CApp = CApp + ' UINT32 FieldSize;\n'
1946 CApp = CApp + ' CHAR8 *Value;\n'
1947 DefaultValueFromDec = Pcd.DefaultValueFromDec
1948 IsArray = IsFieldValueAnArray(Pcd.DefaultValueFromDec)
1949 if IsArray:
1950 try:
1951 DefaultValueFromDec = ValueExpressionEx(Pcd.DefaultValueFromDec, TAB_VOID)(True)
1952 except BadExpression:
1953 EdkLogger.error("Build", FORMAT_INVALID, "Invalid value format for %s.%s, from DEC: %s" %
1954 (Pcd.TokenSpaceGuidCName, Pcd.TokenCName, DefaultValueFromDec))
1955 DefaultValueFromDec = StringToArray(DefaultValueFromDec)
1956 Value, ValueSize = ParseFieldValue (DefaultValueFromDec)
1957 if isinstance(Value, str):
1958 CApp = CApp + ' Pcd = %s; // From DEC Default Value %s\n' % (Value, Pcd.DefaultValueFromDec)
1959 elif IsArray:
1960 #
1961 # Use memcpy() to copy value into field
1962 #
1963 if "{CODE(" in Pcd.DefaultValueFromDec:
1964 CApp = CApp + ' memcpy (Pcd, %s_%s_INIT_Value, sizeof(%s_%s_INIT_Value));\n' % (Pcd.TokenSpaceGuidCName, Pcd.TokenCName,Pcd.TokenSpaceGuidCName, Pcd.TokenCName)
1965 else:
1966 CApp = CApp + ' Value = %s; // From DEC Default Value %s\n' % (DscBuildData.IntToCString(Value, ValueSize), Pcd.DefaultValueFromDec)
1967 CApp = CApp + ' memcpy (Pcd, Value, %d);\n' % (ValueSize)
1968 for index in Pcd.DefaultValues:
1969 FieldList = Pcd.DefaultValues[index]
1970 if not FieldList:
1971 continue
1972 for FieldName in FieldList:
1973 IsArray = IsFieldValueAnArray(FieldList[FieldName][0])
1974 if IsArray:
1975 try:
1976 FieldList[FieldName][0] = ValueExpressionEx(FieldList[FieldName][0], TAB_VOID, self._GuidDict)(True)
1977 except BadExpression:
1978 EdkLogger.error('Build', FORMAT_INVALID, "Invalid value format for %s. From %s Line %d " %
1979 (".".join((Pcd.TokenSpaceGuidCName, Pcd.TokenCName, FieldName)), FieldList[FieldName][1], FieldList[FieldName][2]))
1980
1981 try:
1982 Value, ValueSize = ParseFieldValue (FieldList[FieldName][0])
1983 except Exception:
1984 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]))
1985
1986 indicator = self.GetIndicator(index, FieldName,Pcd)
1987 if isinstance(Value, str):
1988 CApp = CApp + ' %s = %s; // From %s Line %d Value %s\n' % (indicator, Value, FieldList[FieldName][1], FieldList[FieldName][2], FieldList[FieldName][0])
1989 elif IsArray:
1990 #
1991 # Use memcpy() to copy value into field
1992 #
1993 CApp = CApp + ' FieldSize = __FIELD_SIZE(%s, %s);\n' % (Pcd.DatumType, FieldName)
1994 CApp = CApp + ' Value = %s; // From %s Line %d Value %s\n' % (DscBuildData.IntToCString(Value, ValueSize), FieldList[FieldName][1], FieldList[FieldName][2], FieldList[FieldName][0])
1995 CApp = CApp + ' __STATIC_ASSERT((__FIELD_SIZE(%s, %s) >= %d) || (__FIELD_SIZE(%s, %s) == 0), "Input buffer exceeds the buffer array"); // From %s Line %d Value %s\n' % (Pcd.DatumType, FieldName, ValueSize, Pcd.DatumType, FieldName, FieldList[FieldName][1], FieldList[FieldName][2], FieldList[FieldName][0])
1996 CApp = CApp + ' memcpy (&Pcd->%s, Value, (FieldSize > 0 && FieldSize < %d) ? FieldSize : %d);\n' % (FieldName, ValueSize, ValueSize)
1997 CApp = CApp + ' memcpy (&%s, Value, (FieldSize > 0 && FieldSize < %d) ? FieldSize : %d);\n' % (indicator, ValueSize, ValueSize)
1998
1999 else:
2000 if '[' in FieldName and ']' in FieldName:
2001 Index = int(FieldName.split('[')[1].split(']')[0])
2002 CApp = CApp + ' __STATIC_ASSERT((%d < __ARRAY_SIZE(Pcd->%s)) || (__ARRAY_SIZE(Pcd->%s) == 0), "array index exceeds the array number"); // From %s Line %d Index of %s\n' % (Index, FieldName.split('[')[0], FieldName.split('[')[0], FieldList[FieldName][1], FieldList[FieldName][2], FieldName)
2003 if ValueSize > 4:
2004 CApp = CApp + ' %s = %dULL; // From %s Line %d Value %s\n' % (indicator, Value, FieldList[FieldName][1], FieldList[FieldName][2], FieldList[FieldName][0])
2005 else:
2006 CApp = CApp + ' %s = %d; // From %s Line %d Value %s\n' % (indicator, Value, FieldList[FieldName][1], FieldList[FieldName][2], FieldList[FieldName][0])
2007 CApp = CApp + "}\n"
2008 return CApp
2009
2010 @staticmethod
2011 def GenerateDefaultValueAssignStatement(Pcd):
2012 CApp = ' Assign_%s_%s_Default_Value(Pcd);\n' % (Pcd.TokenSpaceGuidCName, Pcd.TokenCName)
2013 return CApp
2014
2015 def GetPcdDscRawDefaultValue(self,Pcd, SkuName,DefaultStoreName):
2016 if Pcd.Type in PCD_DYNAMIC_TYPE_SET or Pcd.Type in PCD_DYNAMIC_EX_TYPE_SET:
2017 if (SkuName, DefaultStoreName) == (TAB_DEFAULT, TAB_DEFAULT_STORES_DEFAULT):
2018 pcddefaultvalue = Pcd.DefaultFromDSC.get(TAB_DEFAULT, {}).get(TAB_DEFAULT_STORES_DEFAULT) if Pcd.DefaultFromDSC else None
2019 else:
2020 pcddefaultvalue = Pcd.DscRawValue.get(SkuName, {}).get(DefaultStoreName)
2021 else:
2022 pcddefaultvalue = Pcd.DscRawValue.get(SkuName, {}).get(TAB_DEFAULT_STORES_DEFAULT)
2023
2024 return pcddefaultvalue
2025 def GenerateInitValueFunction(self, Pcd, SkuName, DefaultStoreName):
2026 CApp = "// Value in Dsc for Sku: %s, DefaultStore %s\n" % (SkuName, DefaultStoreName)
2027 CApp = CApp + "void Assign_%s_%s_%s_%s_Value(%s *Pcd){\n" % (Pcd.TokenSpaceGuidCName, Pcd.TokenCName, SkuName, DefaultStoreName, Pcd.BaseDatumType)
2028 CApp = CApp + ' UINT32 FieldSize;\n'
2029 CApp = CApp + ' CHAR8 *Value;\n'
2030
2031 CApp = CApp + "// SkuName: %s, DefaultStoreName: %s \n" % (TAB_DEFAULT, TAB_DEFAULT_STORES_DEFAULT)
2032 inherit_OverrideValues = Pcd.SkuOverrideValues[SkuName]
2033
2034 pcddefaultvalue = self.GetPcdDscRawDefaultValue(Pcd, SkuName, DefaultStoreName)
2035 if pcddefaultvalue:
2036 FieldList = pcddefaultvalue
2037 IsArray = IsFieldValueAnArray(FieldList)
2038 if IsArray:
2039 if "{CODE(" not in FieldList:
2040 try:
2041 FieldList = ValueExpressionEx(FieldList, TAB_VOID)(True)
2042 except BadExpression:
2043 EdkLogger.error("Build", FORMAT_INVALID, "Invalid value format for %s.%s, from DSC: %s" %
2044 (Pcd.TokenSpaceGuidCName, Pcd.TokenCName, FieldList))
2045 Value, ValueSize = ParseFieldValue (FieldList)
2046
2047 if (SkuName, DefaultStoreName) == (TAB_DEFAULT, TAB_DEFAULT_STORES_DEFAULT):
2048 if isinstance(Value, str):
2049 if "{CODE(" in Value:
2050 CApp = CApp + ' memcpy (Pcd, %s_%s_%s_%s_Value, sizeof(%s_%s_%s_%s_Value));\n' % (Pcd.TokenSpaceGuidCName, Pcd.TokenCName,SkuName, DefaultStoreName,Pcd.TokenSpaceGuidCName, Pcd.TokenCName,SkuName, DefaultStoreName)
2051 else:
2052 CApp = CApp + ' Pcd = %s; // From DSC Default Value %s\n' % (Value, Pcd.DefaultFromDSC.get(TAB_DEFAULT, {}).get(TAB_DEFAULT_STORES_DEFAULT, Pcd.DefaultValue) if Pcd.DefaultFromDSC else Pcd.DefaultValue)
2053 elif IsArray:
2054 #
2055 # Use memcpy() to copy value into field
2056 #
2057 if Pcd.IsArray() and "{CODE(" in pcddefaultvalue:
2058 CApp = CApp + ' memcpy (Pcd, %s_%s_%s_%s_Value, sizeof(%s_%s_%s_%s_Value));\n' % (Pcd.TokenSpaceGuidCName, Pcd.TokenCName,SkuName, DefaultStoreName,Pcd.TokenSpaceGuidCName, Pcd.TokenCName,SkuName, DefaultStoreName)
2059 else:
2060 CApp = CApp + ' Value = %s; // From DSC Default Value %s\n' % (DscBuildData.IntToCString(Value, ValueSize), Pcd.DefaultFromDSC.get(TAB_DEFAULT, {}).get(TAB_DEFAULT_STORES_DEFAULT, Pcd.DefaultValue) if Pcd.DefaultFromDSC else Pcd.DefaultValue)
2061 CApp = CApp + ' memcpy (Pcd, Value, %d);\n' % (ValueSize)
2062 else:
2063 if isinstance(Value, str):
2064 if "{CODE(" in Value:
2065 CApp = CApp + ' memcpy (Pcd, %s_%s_%s_%s_Value, sizeof(%s_%s_%s_%s_Value));\n' % (Pcd.TokenSpaceGuidCName, Pcd.TokenCName,SkuName, DefaultStoreName,Pcd.TokenSpaceGuidCName, Pcd.TokenCName,SkuName, DefaultStoreName)
2066 else:
2067 CApp = CApp + ' Pcd = %s; // From DSC Default Value %s\n' % (Value, Pcd.DscRawValue.get(SkuName, {}).get(DefaultStoreName))
2068 elif IsArray:
2069 #
2070 # Use memcpy() to copy value into field
2071 #
2072 if Pcd.IsArray() and "{CODE(" in pcddefaultvalue:
2073 CApp = CApp + ' memcpy (Pcd, %s_%s_%s_%s_Value, sizeof(%s_%s_%s_%s_Value));\n' % (Pcd.TokenSpaceGuidCName, Pcd.TokenCName,SkuName, DefaultStoreName,Pcd.TokenSpaceGuidCName, Pcd.TokenCName,SkuName, DefaultStoreName)
2074 else:
2075 CApp = CApp + ' Value = %s; // From DSC Default Value %s\n' % (DscBuildData.IntToCString(Value, ValueSize), Pcd.DscRawValue.get(SkuName, {}).get(DefaultStoreName))
2076 CApp = CApp + ' memcpy (Pcd, Value, %d);\n' % (ValueSize)
2077
2078 inheritvalue = inherit_OverrideValues.get(DefaultStoreName)
2079 if not inheritvalue:
2080 inheritvalue = []
2081 for index in inheritvalue:
2082 FieldList = inheritvalue[index]
2083 if not FieldList:
2084 continue
2085 if (SkuName, DefaultStoreName) == (TAB_DEFAULT, TAB_DEFAULT_STORES_DEFAULT) or (( (SkuName, '') not in Pcd.ValueChain) and ( (SkuName, DefaultStoreName) not in Pcd.ValueChain )):
2086 for FieldName in FieldList:
2087 indicator = self.GetIndicator(index, FieldName,Pcd)
2088 IsArray = IsFieldValueAnArray(FieldList[FieldName][0])
2089 if IsArray:
2090 try:
2091 FieldList[FieldName][0] = ValueExpressionEx(FieldList[FieldName][0], TAB_VOID, self._GuidDict)(True)
2092 except BadExpression:
2093 EdkLogger.error('Build', FORMAT_INVALID, "Invalid value format for %s. From %s Line %d " %
2094 (".".join((Pcd.TokenSpaceGuidCName, Pcd.TokenCName, FieldName)), FieldList[FieldName][1], FieldList[FieldName][2]))
2095 try:
2096 Value, ValueSize = ParseFieldValue (FieldList[FieldName][0])
2097 except Exception:
2098 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]))
2099 if isinstance(Value, str):
2100 CApp = CApp + ' Pcd->%s = %s; // From %s Line %d Value %s\n' % (FieldName, Value, FieldList[FieldName][1], FieldList[FieldName][2], FieldList[FieldName][0])
2101 elif IsArray:
2102 #
2103 # Use memcpy() to copy value into field
2104 #
2105 CApp = CApp + ' FieldSize = __FIELD_SIZE(%s, %s);\n' % (Pcd.BaseDatumType, FieldName)
2106 CApp = CApp + ' Value = %s; // From %s Line %d Value %s\n' % (DscBuildData.IntToCString(Value, ValueSize), FieldList[FieldName][1], FieldList[FieldName][2], FieldList[FieldName][0])
2107 CApp = CApp + ' __STATIC_ASSERT((__FIELD_SIZE(%s, %s) >= %d) || (__FIELD_SIZE(%s, %s) == 0), "Input buffer exceeds the buffer array"); // From %s Line %d Value %s\n' % (Pcd.DatumType, FieldName, ValueSize, Pcd.DatumType, FieldName, FieldList[FieldName][1], FieldList[FieldName][2], FieldList[FieldName][0])
2108 CApp = CApp + ' memcpy (&Pcd->%s, Value, (FieldSize > 0 && FieldSize < %d) ? FieldSize : %d);\n' % (FieldName, ValueSize, ValueSize)
2109 CApp = CApp + ' memcpy (&%s, Value, (FieldSize > 0 && FieldSize < %d) ? FieldSize : %d);\n' % (indicator, ValueSize, ValueSize)
2110 else:
2111 if '[' in FieldName and ']' in FieldName:
2112 Index = int(FieldName.split('[')[1].split(']')[0])
2113 CApp = CApp + ' __STATIC_ASSERT((%d < __ARRAY_SIZE(Pcd->%s)) || (__ARRAY_SIZE(Pcd->%s) == 0), "array index exceeds the array number"); // From %s Line %d Index of %s\n' % (Index, FieldName.split('[')[0], FieldName.split('[')[0], FieldList[FieldName][1], FieldList[FieldName][2], FieldName)
2114 if ValueSize > 4:
2115 CApp = CApp + ' %s = %dULL; // From %s Line %d Value %s\n' % (indicator, Value, FieldList[FieldName][1], FieldList[FieldName][2], FieldList[FieldName][0])
2116 else:
2117 CApp = CApp + ' %s = %d; // From %s Line %d Value %s\n' % (indicator, Value, FieldList[FieldName][1], FieldList[FieldName][2], FieldList[FieldName][0])
2118 CApp = CApp + "}\n"
2119 return CApp
2120
2121 @staticmethod
2122 def GenerateInitValueStatement(Pcd, SkuName, DefaultStoreName):
2123 CApp = ' Assign_%s_%s_%s_%s_Value(Pcd);\n' % (Pcd.TokenSpaceGuidCName, Pcd.TokenCName, SkuName, DefaultStoreName)
2124 return CApp
2125
2126 def GenerateCommandLineValue(self, Pcd):
2127 CApp = "// Value in CommandLine\n"
2128 CApp = CApp + "void Assign_%s_%s_CommandLine_Value(%s *Pcd){\n" % (Pcd.TokenSpaceGuidCName, Pcd.TokenCName, Pcd.BaseDatumType)
2129 CApp = CApp + ' UINT32 FieldSize;\n'
2130 CApp = CApp + ' CHAR8 *Value;\n'
2131
2132 pcddefaultvalue = Pcd.PcdValueFromComm
2133 for FieldList in [pcddefaultvalue, Pcd.PcdFieldValueFromComm]:
2134 if not FieldList:
2135 continue
2136 if pcddefaultvalue and FieldList == pcddefaultvalue:
2137 IsArray = IsFieldValueAnArray(FieldList)
2138 if IsArray:
2139 try:
2140 FieldList = ValueExpressionEx(FieldList, TAB_VOID)(True)
2141 except BadExpression:
2142 EdkLogger.error("Build", FORMAT_INVALID, "Invalid value format for %s.%s, from Command: %s" %
2143 (Pcd.TokenSpaceGuidCName, Pcd.TokenCName, FieldList))
2144 Value, ValueSize = ParseFieldValue (FieldList)
2145
2146 if isinstance(Value, str):
2147 CApp = CApp + ' Pcd = %s; // From Command Line \n' % (Value)
2148 elif IsArray:
2149 #
2150 # Use memcpy() to copy value into field
2151 #
2152 CApp = CApp + ' Value = %s; // From Command Line.\n' % (DscBuildData.IntToCString(Value, ValueSize))
2153 CApp = CApp + ' memcpy (Pcd, Value, %d);\n' % (ValueSize)
2154 continue
2155 for FieldName in FieldList:
2156 IsArray = IsFieldValueAnArray(FieldList[FieldName][0])
2157 if IsArray:
2158 try:
2159 FieldList[FieldName][0] = ValueExpressionEx(FieldList[FieldName][0], TAB_VOID, self._GuidDict)(True)
2160 except BadExpression:
2161 EdkLogger.error('Build', FORMAT_INVALID, "Invalid value format for %s. From %s Line %d " %
2162 (".".join((Pcd.TokenSpaceGuidCName, Pcd.TokenCName, FieldName)), FieldList[FieldName][1], FieldList[FieldName][2]))
2163 except:
2164 print("error")
2165 try:
2166 Value, ValueSize = ParseFieldValue (FieldList[FieldName][0])
2167 except Exception:
2168 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]))
2169 if isinstance(Value, str):
2170 CApp = CApp + ' Pcd->%s = %s; // From %s Line %d Value %s\n' % (FieldName, Value, FieldList[FieldName][1], FieldList[FieldName][2], FieldList[FieldName][0])
2171 elif IsArray:
2172 #
2173 # Use memcpy() to copy value into field
2174 #
2175 CApp = CApp + ' FieldSize = __FIELD_SIZE(%s, %s);\n' % (Pcd.BaseDatumType, FieldName)
2176 CApp = CApp + ' Value = %s; // From %s Line %d Value %s\n' % (DscBuildData.IntToCString(Value, ValueSize), FieldList[FieldName][1], FieldList[FieldName][2], FieldList[FieldName][0])
2177 CApp = CApp + ' __STATIC_ASSERT((__FIELD_SIZE(%s, %s) >= %d) || (__FIELD_SIZE(%s, %s) == 0), "Input buffer exceeds the buffer array"); // From %s Line %d Value %s\n' % (Pcd.DatumType, FieldName, ValueSize, Pcd.DatumType, FieldName, FieldList[FieldName][1], FieldList[FieldName][2], FieldList[FieldName][0])
2178 CApp = CApp + ' memcpy (&Pcd->%s, Value, (FieldSize > 0 && FieldSize < %d) ? FieldSize : %d);\n' % (FieldName, ValueSize, ValueSize)
2179 else:
2180 if '[' in FieldName and ']' in FieldName:
2181 Index = int(FieldName.split('[')[1].split(']')[0])
2182 CApp = CApp + ' __STATIC_ASSERT((%d < __ARRAY_SIZE(Pcd->%s)) || (__ARRAY_SIZE(Pcd->%s) == 0), "array index exceeds the array number"); // From %s Line %d Index of %s\n' % (Index, FieldName.split('[')[0], FieldName.split('[')[0], FieldList[FieldName][1], FieldList[FieldName][2], FieldName)
2183 if ValueSize > 4:
2184 CApp = CApp + ' Pcd->%s = %dULL; // From %s Line %d Value %s\n' % (FieldName, Value, FieldList[FieldName][1], FieldList[FieldName][2], FieldList[FieldName][0])
2185 else:
2186 CApp = CApp + ' Pcd->%s = %d; // From %s Line %d Value %s\n' % (FieldName, Value, FieldList[FieldName][1], FieldList[FieldName][2], FieldList[FieldName][0])
2187 CApp = CApp + "}\n"
2188 return CApp
2189
2190 @staticmethod
2191 def GenerateCommandLineValueStatement(Pcd):
2192 CApp = ' Assign_%s_%s_CommandLine_Value(Pcd);\n' % (Pcd.TokenSpaceGuidCName, Pcd.TokenCName)
2193 return CApp
2194 def GenerateFdfValue(self,Pcd):
2195 CApp = "// Value in Fdf\n"
2196 CApp = CApp + "void Assign_%s_%s_Fdf_Value(%s *Pcd){\n" % (Pcd.TokenSpaceGuidCName, Pcd.TokenCName,Pcd.BaseDatumType)
2197 CApp = CApp + ' UINT32 FieldSize;\n'
2198 CApp = CApp + ' CHAR8 *Value;\n'
2199
2200 pcddefaultvalue = Pcd.PcdValueFromFdf
2201 for FieldList in [pcddefaultvalue,Pcd.PcdFieldValueFromFdf]:
2202 if not FieldList:
2203 continue
2204 if pcddefaultvalue and FieldList == pcddefaultvalue:
2205 IsArray = IsFieldValueAnArray(FieldList)
2206 if IsArray:
2207 try:
2208 FieldList = ValueExpressionEx(FieldList, TAB_VOID)(True)
2209 except BadExpression:
2210 EdkLogger.error("Build", FORMAT_INVALID, "Invalid value format for %s.%s, from Fdf: %s" %
2211 (Pcd.TokenSpaceGuidCName, Pcd.TokenCName, FieldList))
2212 Value, ValueSize = ParseFieldValue (FieldList)
2213
2214 if isinstance(Value, str):
2215 CApp = CApp + ' Pcd = %s; // From Fdf \n' % (Value)
2216 elif IsArray:
2217 #
2218 # Use memcpy() to copy value into field
2219 #
2220 CApp = CApp + ' Value = %s; // From Fdf .\n' % (DscBuildData.IntToCString(Value, ValueSize))
2221 CApp = CApp + ' memcpy (Pcd, Value, %d);\n' % (ValueSize)
2222 continue
2223 for FieldName in FieldList:
2224 IsArray = IsFieldValueAnArray(FieldList[FieldName][0])
2225 if IsArray:
2226 try:
2227 FieldList[FieldName][0] = ValueExpressionEx(FieldList[FieldName][0], TAB_VOID, self._GuidDict)(True)
2228 except BadExpression:
2229 EdkLogger.error('Build', FORMAT_INVALID, "Invalid value format for %s. From %s Line %d " %
2230 (".".join((Pcd.TokenSpaceGuidCName, Pcd.TokenCName, FieldName)), FieldList[FieldName][1], FieldList[FieldName][2]))
2231 except:
2232 print("error")
2233 try:
2234 Value, ValueSize = ParseFieldValue (FieldList[FieldName][0])
2235 except Exception:
2236 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]))
2237 if isinstance(Value, str):
2238 CApp = CApp + ' Pcd->%s = %s; // From %s Line %d Value %s\n' % (FieldName, Value, FieldList[FieldName][1], FieldList[FieldName][2], FieldList[FieldName][0])
2239 elif IsArray:
2240 #
2241 # Use memcpy() to copy value into field
2242 #
2243 CApp = CApp + ' FieldSize = __FIELD_SIZE(%s, %s);\n' % (Pcd.BaseDatumType, FieldName)
2244 CApp = CApp + ' Value = %s; // From %s Line %d Value %s\n' % (DscBuildData.IntToCString(Value, ValueSize), FieldList[FieldName][1], FieldList[FieldName][2], FieldList[FieldName][0])
2245 CApp = CApp + ' __STATIC_ASSERT((__FIELD_SIZE(%s, %s) >= %d) || (__FIELD_SIZE(%s, %s) == 0), "Input buffer exceeds the buffer array"); // From %s Line %d Value %s\n' % (Pcd.DatumType, FieldName, ValueSize, Pcd.DatumType, FieldName, FieldList[FieldName][1], FieldList[FieldName][2], FieldList[FieldName][0])
2246 CApp = CApp + ' memcpy (&Pcd->%s, Value, (FieldSize > 0 && FieldSize < %d) ? FieldSize : %d);\n' % (FieldName, ValueSize, ValueSize)
2247 else:
2248 if '[' in FieldName and ']' in FieldName:
2249 Index = int(FieldName.split('[')[1].split(']')[0])
2250 CApp = CApp + ' __STATIC_ASSERT((%d < __ARRAY_SIZE(Pcd->%s)) || (__ARRAY_SIZE(Pcd->%s) == 0), "array index exceeds the array number"); // From %s Line %d Index of %s\n' % (Index, FieldName.split('[')[0], FieldName.split('[')[0], FieldList[FieldName][1], FieldList[FieldName][2], FieldName)
2251 if ValueSize > 4:
2252 CApp = CApp + ' Pcd->%s = %dULL; // From %s Line %d Value %s\n' % (FieldName, Value, FieldList[FieldName][1], FieldList[FieldName][2], FieldList[FieldName][0])
2253 else:
2254 CApp = CApp + ' Pcd->%s = %d; // From %s Line %s Value %s\n' % (FieldName, Value, FieldList[FieldName][1], FieldList[FieldName][2], FieldList[FieldName][0])
2255 CApp = CApp + "}\n"
2256 return CApp
2257
2258 @staticmethod
2259 def GenerateFdfValueStatement(Pcd):
2260 CApp = ' Assign_%s_%s_Fdf_Value(Pcd);\n' % (Pcd.TokenSpaceGuidCName, Pcd.TokenCName)
2261 return CApp
2262
2263 def GenerateInitializeFunc(self, SkuName, DefaultStore, Pcd, InitByteValue, CApp):
2264 OverrideValues = {DefaultStore:{}}
2265 if Pcd.SkuOverrideValues:
2266 OverrideValues = Pcd.SkuOverrideValues[SkuName]
2267 if not OverrideValues:
2268 OverrideValues = {TAB_DEFAULT_STORES_DEFAULT:Pcd.DefaultValues}
2269 for DefaultStoreName in OverrideValues:
2270 CApp = CApp + 'void\n'
2271 CApp = CApp + 'Initialize_%s_%s_%s_%s(\n' % (SkuName, DefaultStoreName, Pcd.TokenSpaceGuidCName, Pcd.TokenCName)
2272 CApp = CApp + ' void\n'
2273 CApp = CApp + ' )\n'
2274 CApp = CApp + '{\n'
2275 CApp = CApp + ' UINT32 Size;\n'
2276 CApp = CApp + ' UINT32 FieldSize;\n'
2277 CApp = CApp + ' CHAR8 *Value;\n'
2278 CApp = CApp + ' UINT32 OriginalSize;\n'
2279 CApp = CApp + ' VOID *OriginalPcd;\n'
2280
2281 CApp = CApp + ' %s *Pcd; // From %s Line %d \n' % (Pcd.BaseDatumType,Pcd.PkgPath, Pcd.PcdDefineLineNo)
2282
2283 CApp = CApp + '\n'
2284
2285 PcdDefaultValue = StringToArray(Pcd.DefaultValueFromDec.strip())
2286
2287 InitByteValue += '%s.%s.%s.%s|%s|%s\n' % (SkuName, DefaultStoreName, Pcd.TokenSpaceGuidCName, Pcd.TokenCName, Pcd.DatumType, PcdDefaultValue)
2288
2289 #
2290 # Get current PCD value and size
2291 #
2292 CApp = CApp + ' OriginalPcd = PcdGetPtr (%s, %s, %s, %s, &OriginalSize);\n' % (SkuName, DefaultStoreName, Pcd.TokenSpaceGuidCName, Pcd.TokenCName)
2293
2294 #
2295 # Determine the size of the PCD. For simple structures, sizeof(TYPE) provides
2296 # the correct value. For structures with a flexible array member, the flexible
2297 # array member is detected, and the size is based on the highest index used with
2298 # the flexible array member. The flexible array member must be the last field
2299 # in a structure. The size formula for this case is:
2300 # OFFSET_OF(FlexbleArrayField) + sizeof(FlexibleArray[0]) * (HighestIndex + 1)
2301 #
2302 CApp = CApp + DscBuildData.GenerateSizeStatments(Pcd,SkuName,DefaultStoreName)
2303
2304 #
2305 # Allocate and zero buffer for the PCD
2306 # Must handle cases where current value is smaller, larger, or same size
2307 # Always keep that larger one as the current size
2308 #
2309 CApp = CApp + ' Size = (OriginalSize > Size ? OriginalSize : Size);\n'
2310 CApp = CApp + ' Pcd = (%s *)malloc (Size);\n' % (Pcd.BaseDatumType,)
2311 CApp = CApp + ' memset (Pcd, 0, Size);\n'
2312
2313 #
2314 # Copy current PCD value into allocated buffer.
2315 #
2316 CApp = CApp + ' memcpy (Pcd, OriginalPcd, OriginalSize);\n'
2317
2318 #
2319 # Assign field values in PCD
2320 #
2321 CApp = CApp + DscBuildData.GenerateDefaultValueAssignStatement(Pcd)
2322 if Pcd.Type not in [self._PCD_TYPE_STRING_[MODEL_PCD_FIXED_AT_BUILD],
2323 self._PCD_TYPE_STRING_[MODEL_PCD_PATCHABLE_IN_MODULE]]:
2324 for skuname in self.SkuIdMgr.GetSkuChain(SkuName):
2325 storeset = [DefaultStoreName] if DefaultStoreName == TAB_DEFAULT_STORES_DEFAULT else [TAB_DEFAULT_STORES_DEFAULT, DefaultStoreName]
2326 for defaultstorenameitem in storeset:
2327 CApp = CApp + "// SkuName: %s, DefaultStoreName: %s \n" % (skuname, defaultstorenameitem)
2328 CApp = CApp + DscBuildData.GenerateInitValueStatement(Pcd, skuname, defaultstorenameitem)
2329 if skuname == SkuName:
2330 break
2331 else:
2332 CApp = CApp + "// SkuName: %s, DefaultStoreName: STANDARD \n" % self.SkuIdMgr.SystemSkuId
2333 CApp = CApp + DscBuildData.GenerateInitValueStatement(Pcd, self.SkuIdMgr.SystemSkuId, TAB_DEFAULT_STORES_DEFAULT)
2334 CApp = CApp + DscBuildData.GenerateFdfValueStatement(Pcd)
2335 CApp = CApp + DscBuildData.GenerateCommandLineValueStatement(Pcd)
2336 #
2337 # Set new PCD value and size
2338 #
2339 CApp = CApp + ' PcdSetPtr (%s, %s, %s, %s, Size, (void *)Pcd);\n' % (SkuName, DefaultStoreName, Pcd.TokenSpaceGuidCName, Pcd.TokenCName)
2340
2341 #
2342 # Free PCD
2343 #
2344 CApp = CApp + ' free (Pcd);\n'
2345 CApp = CApp + '}\n'
2346 CApp = CApp + '\n'
2347 return InitByteValue, CApp
2348
2349 def GenerateArrayAssignment(self, Pcd):
2350 CApp = ""
2351 if not Pcd:
2352 return CApp
2353 if not Pcd.IsArray():
2354 return CApp
2355 Demesion = ""
2356 for d in Pcd.Capacity:
2357 Demesion += "[]"
2358
2359 Value = Pcd.DefaultValueFromDec
2360 if "{CODE(" in Pcd.DefaultValueFromDec:
2361 realvalue = Pcd.DefaultValueFromDec.strip()[6:-2] # "{CODE(").rstrip(")}"
2362 CApp += "static %s %s_%s_INIT_Value%s = %s;\n" % (Pcd.BaseDatumType,Pcd.TokenSpaceGuidCName,Pcd.TokenCName,Demesion,realvalue)
2363
2364 if Pcd.Type in PCD_DYNAMIC_TYPE_SET | PCD_DYNAMIC_EX_TYPE_SET:
2365 for skuname in Pcd.SkuInfoList:
2366 skuinfo = Pcd.SkuInfoList[skuname]
2367 if skuinfo.VariableName:
2368 for defaultstore in skuinfo.DefaultStoreDict:
2369 pcddscrawdefaultvalue = self.GetPcdDscRawDefaultValue(Pcd, skuname, defaultstore)
2370 if pcddscrawdefaultvalue:
2371 Value = skuinfo[defaultstore]
2372 if "{CODE(" in Value:
2373 realvalue = Value.strip()[6:-2] # "{CODE(").rstrip(")}"
2374 CApp += "static %s %s_%s_%s_%s_Value%s = %s;\n" % (Pcd.BaseDatumType,Pcd.TokenSpaceGuidCName,Pcd.TokenCName,skuname,defaultstore,Demesion,realvalue)
2375 else:
2376 pcddscrawdefaultvalue = self.GetPcdDscRawDefaultValue(Pcd, skuname, TAB_DEFAULT_STORES_DEFAULT)
2377 if pcddscrawdefaultvalue:
2378 Value = skuinfo.DefaultValue
2379 if "{CODE(" in Value:
2380 realvalue = Value.strip()[6:-2] # "{CODE(").rstrip(")}"
2381 CApp += "static %s %s_%s_%s_%s_Value%s = %s;\n" % (Pcd.BaseDatumType,Pcd.TokenSpaceGuidCName,Pcd.TokenCName,skuname,TAB_DEFAULT_STORES_DEFAULT,Demesion,realvalue)
2382 else:
2383 pcddscrawdefaultvalue = self.GetPcdDscRawDefaultValue(Pcd, TAB_DEFAULT, TAB_DEFAULT_STORES_DEFAULT)
2384 if pcddscrawdefaultvalue:
2385 if "{CODE(" in Pcd.DefaultValue:
2386 realvalue = Pcd.DefaultValue.strip()[6:-2] # "{CODE(").rstrip(")}"
2387 CApp += "static %s %s_%s_DEFAULT_STANDARD_Value%s = %s;\n" % (Pcd.BaseDatumType,Pcd.TokenSpaceGuidCName,Pcd.TokenCName,Demesion,realvalue)
2388
2389 return CApp
2390
2391 def SkuOverrideValuesEmpty(self,OverrideValues):
2392 if not OverrideValues:
2393 return True
2394 for key in OverrideValues:
2395 if OverrideValues[key]:
2396 return False
2397 return True
2398
2399 def ParseCCFlags(self, ccflag):
2400 ccflags = set()
2401 ccflaglist = ccflag.split(" ")
2402 i = 0
2403 while i < len(ccflaglist):
2404 item = ccflaglist[i].strip()
2405 if item in (r"/D", r"/U","-D","-U"):
2406 ccflags.add(" ".join((ccflaglist[i],ccflaglist[i+1])))
2407 i = i+1
2408 elif item.startswith((r"/D", r"/U","-D","-U")):
2409 ccflags.add(item)
2410 i +=1
2411 return ccflags
2412 def GenerateByteArrayValue (self, StructuredPcds):
2413 #
2414 # Generate/Compile/Run C application to determine if there are any flexible array members
2415 #
2416 if not StructuredPcds:
2417 return
2418
2419 InitByteValue = ""
2420 CApp = PcdMainCHeader
2421
2422 IncludeFiles = set()
2423 for PcdName in StructuredPcds:
2424 Pcd = StructuredPcds[PcdName]
2425 for IncludeFile in Pcd.StructuredPcdIncludeFile:
2426 if IncludeFile not in IncludeFiles:
2427 IncludeFiles.add(IncludeFile)
2428 CApp = CApp + '#include <%s>\n' % (IncludeFile)
2429 CApp = CApp + '\n'
2430 for Pcd in StructuredPcds.values():
2431 CApp = CApp + self.GenerateArrayAssignment(Pcd)
2432 for PcdName in StructuredPcds:
2433 Pcd = StructuredPcds[PcdName]
2434 CApp = CApp + self.GenerateSizeFunction(Pcd)
2435 CApp = CApp + self.GenerateDefaultValueAssignFunction(Pcd)
2436 CApp = CApp + self.GenerateFdfValue(Pcd)
2437 CApp = CApp + self.GenerateCommandLineValue(Pcd)
2438 if self.SkuOverrideValuesEmpty(Pcd.SkuOverrideValues) or Pcd.Type in [self._PCD_TYPE_STRING_[MODEL_PCD_FIXED_AT_BUILD],
2439 self._PCD_TYPE_STRING_[MODEL_PCD_PATCHABLE_IN_MODULE]]:
2440 CApp = CApp + self.GenerateInitValueFunction(Pcd, self.SkuIdMgr.SystemSkuId, TAB_DEFAULT_STORES_DEFAULT)
2441 else:
2442 for SkuName in self.SkuIdMgr.SkuOverrideOrder():
2443 if SkuName not in Pcd.SkuOverrideValues:
2444 continue
2445 for DefaultStoreName in Pcd.SkuOverrideValues[SkuName]:
2446 CApp = CApp + self.GenerateInitValueFunction(Pcd, SkuName, DefaultStoreName)
2447 if self.SkuOverrideValuesEmpty(Pcd.SkuOverrideValues) or Pcd.Type in [self._PCD_TYPE_STRING_[MODEL_PCD_FIXED_AT_BUILD],
2448 self._PCD_TYPE_STRING_[MODEL_PCD_PATCHABLE_IN_MODULE]]:
2449 InitByteValue, CApp = self.GenerateInitializeFunc(self.SkuIdMgr.SystemSkuId, TAB_DEFAULT_STORES_DEFAULT, Pcd, InitByteValue, CApp)
2450 else:
2451 for SkuName in self.SkuIdMgr.SkuOverrideOrder():
2452 if SkuName not in Pcd.SkuOverrideValues:
2453 continue
2454 for DefaultStoreName in Pcd.DefaultStoreName:
2455 Pcd = StructuredPcds[PcdName]
2456 InitByteValue, CApp = self.GenerateInitializeFunc(SkuName, DefaultStoreName, Pcd, InitByteValue, CApp)
2457
2458 CApp = CApp + 'VOID\n'
2459 CApp = CApp + 'PcdEntryPoint(\n'
2460 CApp = CApp + ' VOID\n'
2461 CApp = CApp + ' )\n'
2462 CApp = CApp + '{\n'
2463 for Pcd in StructuredPcds.values():
2464 if self.SkuOverrideValuesEmpty(Pcd.SkuOverrideValues) or Pcd.Type in [self._PCD_TYPE_STRING_[MODEL_PCD_FIXED_AT_BUILD], self._PCD_TYPE_STRING_[MODEL_PCD_PATCHABLE_IN_MODULE]]:
2465 CApp = CApp + ' Initialize_%s_%s_%s_%s();\n' % (self.SkuIdMgr.SystemSkuId, TAB_DEFAULT_STORES_DEFAULT, Pcd.TokenSpaceGuidCName, Pcd.TokenCName)
2466 else:
2467 for SkuName in self.SkuIdMgr.SkuOverrideOrder():
2468 if SkuName not in self.SkuIdMgr.AvailableSkuIdSet:
2469 continue
2470 for DefaultStoreName in Pcd.SkuOverrideValues[SkuName]:
2471 CApp = CApp + ' Initialize_%s_%s_%s_%s();\n' % (SkuName, DefaultStoreName, Pcd.TokenSpaceGuidCName, Pcd.TokenCName)
2472 CApp = CApp + '}\n'
2473
2474 CApp = CApp + PcdMainCEntry + '\n'
2475
2476 if not os.path.exists(self.OutputPath):
2477 os.makedirs(self.OutputPath)
2478 CAppBaseFileName = os.path.join(self.OutputPath, PcdValueInitName)
2479 SaveFileOnChange(CAppBaseFileName + '.c', CApp, False)
2480
2481 MakeApp = PcdMakefileHeader
2482 if sys.platform == "win32":
2483 MakeApp = MakeApp + 'APPFILE = %s\%s.exe\n' % (self.OutputPath, PcdValueInitName) + 'APPNAME = %s\n' % (PcdValueInitName) + 'OBJECTS = %s\%s.obj\n' % (self.OutputPath, PcdValueInitName) + 'INC = '
2484 else:
2485 MakeApp = MakeApp + PcdGccMakefile
2486 MakeApp = MakeApp + 'APPFILE = %s/%s\n' % (self.OutputPath, PcdValueInitName) + 'APPNAME = %s\n' % (PcdValueInitName) + 'OBJECTS = %s/%s.o\n' % (self.OutputPath, PcdValueInitName) + \
2487 'include $(MAKEROOT)/Makefiles/app.makefile\n' + 'INCLUDE +='
2488
2489 IncSearchList = []
2490 PlatformInc = OrderedDict()
2491 for Cache in self._Bdb._CACHE_.values():
2492 if Cache.MetaFile.Ext.lower() != '.dec':
2493 continue
2494 if Cache.Includes:
2495 if str(Cache.MetaFile.Path) not in PlatformInc:
2496 PlatformInc[str(Cache.MetaFile.Path)] = []
2497 PlatformInc[str(Cache.MetaFile.Path)].append (os.path.dirname(Cache.MetaFile.Path))
2498 PlatformInc[str(Cache.MetaFile.Path)].extend (Cache.CommonIncludes)
2499
2500 PcdDependDEC = []
2501 for Pcd in StructuredPcds.values():
2502 for PackageDec in Pcd.PackageDecs:
2503 Package = os.path.normpath(mws.join(GlobalData.gWorkspace, PackageDec))
2504 if not os.path.exists(Package):
2505 EdkLogger.error('Build', RESOURCE_NOT_AVAILABLE, "The dependent Package %s of PCD %s.%s is not exist." % (PackageDec, Pcd.TokenSpaceGuidCName, Pcd.TokenCName))
2506 if Package not in PcdDependDEC:
2507 PcdDependDEC.append(Package)
2508
2509 if PlatformInc and PcdDependDEC:
2510 for pkg in PcdDependDEC:
2511 if pkg in PlatformInc:
2512 for inc in PlatformInc[pkg]:
2513 MakeApp += '-I' + str(inc) + ' '
2514 IncSearchList.append(inc)
2515 MakeApp = MakeApp + '\n'
2516
2517 CC_FLAGS = LinuxCFLAGS
2518 if sys.platform == "win32":
2519 CC_FLAGS = WindowsCFLAGS
2520 BuildOptions = OrderedDict()
2521 for Options in self.BuildOptions:
2522 if Options[2] != EDKII_NAME:
2523 continue
2524 Family = Options[0]
2525 if Family and Family != self.ToolChainFamily:
2526 continue
2527 Target, Tag, Arch, Tool, Attr = Options[1].split("_")
2528 if Tool != 'CC':
2529 continue
2530 if Attr != "FLAGS":
2531 continue
2532 if Target == TAB_STAR or Target == self._Target:
2533 if Tag == TAB_STAR or Tag == self._Toolchain:
2534 if 'COMMON' not in BuildOptions:
2535 BuildOptions['COMMON'] = set()
2536 if Arch == TAB_STAR:
2537 BuildOptions['COMMON']|= self.ParseCCFlags(self.BuildOptions[Options])
2538 if Arch in self.SupArchList:
2539 if Arch not in BuildOptions:
2540 BuildOptions[Arch] = set()
2541 BuildOptions[Arch] |= self.ParseCCFlags(self.BuildOptions[Options])
2542
2543 if BuildOptions:
2544 ArchBuildOptions = {arch:flags for arch,flags in BuildOptions.items() if arch != 'COMMON'}
2545 if len(ArchBuildOptions.keys()) == 1:
2546 BuildOptions['COMMON'] |= (ArchBuildOptions.values()[0])
2547 elif len(ArchBuildOptions.keys()) > 1:
2548 CommonBuildOptions = reduce(lambda x,y: x&y, ArchBuildOptions.values())
2549 BuildOptions['COMMON'] |= CommonBuildOptions
2550 ValueList = list(BuildOptions['COMMON'])
2551 CC_FLAGS += " ".join(ValueList)
2552 MakeApp += CC_FLAGS
2553
2554 if sys.platform == "win32":
2555 MakeApp = MakeApp + PcdMakefileEnd
2556 MakeApp = MakeApp + AppTarget % ("""\tcopy $(APPLICATION) $(APPFILE) /y """)
2557 else:
2558 MakeApp = MakeApp + AppTarget % ("""\tcp $(APPLICATION) $(APPFILE) """)
2559 MakeApp = MakeApp + '\n'
2560 IncludeFileFullPaths = []
2561 for includefile in IncludeFiles:
2562 for includepath in IncSearchList:
2563 includefullpath = os.path.join(str(includepath), includefile)
2564 if os.path.exists(includefullpath):
2565 IncludeFileFullPaths.append(os.path.normpath(includefullpath))
2566 break
2567 SearchPathList = []
2568 SearchPathList.append(os.path.normpath(mws.join(GlobalData.gWorkspace, "BaseTools/Source/C/Include")))
2569 SearchPathList.append(os.path.normpath(mws.join(GlobalData.gWorkspace, "BaseTools/Source/C/Common")))
2570 SearchPathList.extend(str(item) for item in IncSearchList)
2571 IncFileList = GetDependencyList(IncludeFileFullPaths, SearchPathList)
2572 for include_file in IncFileList:
2573 MakeApp += "$(OBJECTS) : %s\n" % include_file
2574 MakeFileName = os.path.join(self.OutputPath, 'Makefile')
2575 MakeApp += "$(OBJECTS) : %s\n" % MakeFileName
2576 SaveFileOnChange(MakeFileName, MakeApp, False)
2577
2578 InputValueFile = os.path.join(self.OutputPath, 'Input.txt')
2579 OutputValueFile = os.path.join(self.OutputPath, 'Output.txt')
2580 SaveFileOnChange(InputValueFile, InitByteValue, False)
2581
2582 Dest_PcdValueInitExe = PcdValueInitName
2583 if not sys.platform == "win32":
2584 Dest_PcdValueInitExe = os.path.join(self.OutputPath, PcdValueInitName)
2585 else:
2586 Dest_PcdValueInitExe = os.path.join(self.OutputPath, PcdValueInitName) +".exe"
2587 Messages = ''
2588 if sys.platform == "win32":
2589 MakeCommand = 'nmake -f %s' % (MakeFileName)
2590 returncode, StdOut, StdErr = DscBuildData.ExecuteCommand (MakeCommand)
2591 Messages = StdOut
2592 else:
2593 MakeCommand = 'make -f %s' % (MakeFileName)
2594 returncode, StdOut, StdErr = DscBuildData.ExecuteCommand (MakeCommand)
2595 Messages = StdErr
2596
2597 Messages = Messages.split('\n')
2598 MessageGroup = []
2599 if returncode != 0:
2600 CAppBaseFileName = os.path.join(self.OutputPath, PcdValueInitName)
2601 File = open (CAppBaseFileName + '.c', 'r')
2602 FileData = File.readlines()
2603 File.close()
2604 for Message in Messages:
2605 if " error" in Message or "warning" in Message:
2606 FileInfo = Message.strip().split('(')
2607 if len (FileInfo) > 1:
2608 FileName = FileInfo [0]
2609 FileLine = FileInfo [1].split (')')[0]
2610 else:
2611 FileInfo = Message.strip().split(':')
2612 if len(FileInfo) < 2:
2613 continue
2614 FileName = FileInfo [0]
2615 FileLine = FileInfo [1]
2616 if FileLine.isdigit():
2617 error_line = FileData[int (FileLine) - 1]
2618 if r"//" in error_line:
2619 c_line, dsc_line = error_line.split(r"//")
2620 else:
2621 dsc_line = error_line
2622 message_itmes = Message.split(":")
2623 Index = 0
2624 if "PcdValueInit.c" not in Message:
2625 if not MessageGroup:
2626 MessageGroup.append(Message)
2627 break
2628 else:
2629 for item in message_itmes:
2630 if "PcdValueInit.c" in item:
2631 Index = message_itmes.index(item)
2632 message_itmes[Index] = dsc_line.strip()
2633 break
2634 MessageGroup.append(":".join(message_itmes[Index:]).strip())
2635 continue
2636 else:
2637 MessageGroup.append(Message)
2638 if MessageGroup:
2639 EdkLogger.error("build", PCD_STRUCTURE_PCD_ERROR, "\n".join(MessageGroup) )
2640 else:
2641 EdkLogger.error('Build', COMMAND_FAILURE, 'Can not execute command: %s' % MakeCommand)
2642
2643 if DscBuildData.NeedUpdateOutput(OutputValueFile, Dest_PcdValueInitExe, InputValueFile):
2644 Command = Dest_PcdValueInitExe + ' -i %s -o %s' % (InputValueFile, OutputValueFile)
2645 returncode, StdOut, StdErr = DscBuildData.ExecuteCommand (Command)
2646 if returncode != 0:
2647 EdkLogger.warn('Build', COMMAND_FAILURE, 'Can not collect output from command: %s' % Command)
2648
2649 File = open (OutputValueFile, 'r')
2650 FileBuffer = File.readlines()
2651 File.close()
2652
2653 StructurePcdSet = []
2654 for Pcd in FileBuffer:
2655 PcdValue = Pcd.split ('|')
2656 PcdInfo = PcdValue[0].split ('.')
2657 StructurePcdSet.append((PcdInfo[0], PcdInfo[1], PcdInfo[2], PcdInfo[3], PcdValue[2].strip()))
2658 return StructurePcdSet
2659
2660 @staticmethod
2661 def NeedUpdateOutput(OutputFile, ValueCFile, StructureInput):
2662 if not os.path.exists(OutputFile):
2663 return True
2664 if os.stat(OutputFile).st_mtime <= os.stat(ValueCFile).st_mtime:
2665 return True
2666 if os.stat(OutputFile).st_mtime <= os.stat(StructureInput).st_mtime:
2667 return True
2668 return False
2669
2670 ## Retrieve dynamic PCD settings
2671 #
2672 # @param Type PCD type
2673 #
2674 # @retval a dict object contains settings of given PCD type
2675 #
2676 def _GetDynamicPcd(self, Type):
2677
2678
2679 Pcds = OrderedDict()
2680 #
2681 # tdict is a special dict kind of type, used for selecting correct
2682 # PCD settings for certain ARCH and SKU
2683 #
2684 PcdDict = tdict(True, 4)
2685 PcdList = []
2686 # Find out all possible PCD candidates for self._Arch
2687 RecordList = self._RawData[Type, self._Arch]
2688 AvailableSkuIdSet = copy.copy(self.SkuIds)
2689
2690
2691 for TokenSpaceGuid, PcdCName, Setting, Arch, SkuName, Dummy3, Dummy4, Dummy5 in RecordList:
2692 SkuName = SkuName.upper()
2693 SkuName = TAB_DEFAULT if SkuName == TAB_COMMON else SkuName
2694 if SkuName not in AvailableSkuIdSet:
2695 EdkLogger.error('build', PARAMETER_INVALID, 'Sku %s is not defined in [SkuIds] section' % SkuName,
2696 File=self.MetaFile, Line=Dummy5)
2697 if "." not in TokenSpaceGuid and "[" not in PcdCName:
2698 PcdList.append((PcdCName, TokenSpaceGuid, SkuName, Dummy5))
2699 PcdDict[Arch, SkuName, PcdCName, TokenSpaceGuid] = Setting
2700
2701 # Remove redundant PCD candidates, per the ARCH and SKU
2702 for PcdCName, TokenSpaceGuid, SkuName, Dummy4 in PcdList:
2703
2704 Setting = PcdDict[self._Arch, SkuName, PcdCName, TokenSpaceGuid]
2705 if Setting is None:
2706 continue
2707
2708 PcdValue, DatumType, MaxDatumSize = self._ValidatePcd(PcdCName, TokenSpaceGuid, Setting, Type, Dummy4)
2709 if MaxDatumSize:
2710 if int(MaxDatumSize, 0) > 0xFFFF:
2711 EdkLogger.error('build', FORMAT_INVALID, "The size value must not exceed the maximum value of 0xFFFF (UINT16) for %s." % ".".join((TokenSpaceGuid, PcdCName)),
2712 File=self.MetaFile, Line=Dummy4)
2713 if int(MaxDatumSize, 0) < 0:
2714 EdkLogger.error('build', FORMAT_INVALID, "The size value can't be set to negative value for %s." % ".".join((TokenSpaceGuid, PcdCName)),
2715 File=self.MetaFile, Line=Dummy4)
2716 SkuInfo = SkuInfoClass(SkuName, self.SkuIds[SkuName][0], '', '', '', '', '', PcdValue)
2717 if (PcdCName, TokenSpaceGuid) in Pcds:
2718 pcdObject = Pcds[PcdCName, TokenSpaceGuid]
2719 pcdObject.SkuInfoList[SkuName] = SkuInfo
2720 if MaxDatumSize.strip():
2721 CurrentMaxSize = int(MaxDatumSize.strip(), 0)
2722 else:
2723 CurrentMaxSize = 0
2724 if pcdObject.MaxDatumSize:
2725 PcdMaxSize = int(pcdObject.MaxDatumSize, 0)
2726 else:
2727 PcdMaxSize = 0
2728 if CurrentMaxSize > PcdMaxSize:
2729 pcdObject.MaxDatumSize = str(CurrentMaxSize)
2730 else:
2731 Pcds[PcdCName, TokenSpaceGuid] = PcdClassObject(
2732 PcdCName,
2733 TokenSpaceGuid,
2734 self._PCD_TYPE_STRING_[Type],
2735 DatumType,
2736 PcdValue,
2737 '',
2738 MaxDatumSize,
2739 OrderedDict({SkuName : SkuInfo}),
2740 False,
2741 None,
2742 IsDsc=True)
2743
2744 if SkuName not in Pcds[PcdCName, TokenSpaceGuid].DscRawValue:
2745 Pcds[PcdCName, TokenSpaceGuid].DscRawValue[SkuName] = {}
2746 Pcds[PcdCName, TokenSpaceGuid].DscRawValue[SkuName][TAB_DEFAULT_STORES_DEFAULT] = PcdValue
2747
2748 for pcd in Pcds.values():
2749 pcdDecObject = self._DecPcds[pcd.TokenCName, pcd.TokenSpaceGuidCName]
2750 # Only fix the value while no value provided in DSC file.
2751 for sku in pcd.SkuInfoList.values():
2752 if not sku.DefaultValue:
2753 sku.DefaultValue = pcdDecObject.DefaultValue
2754 if TAB_DEFAULT not in pcd.SkuInfoList and TAB_COMMON not in pcd.SkuInfoList:
2755 valuefromDec = pcdDecObject.DefaultValue
2756 SkuInfo = SkuInfoClass(TAB_DEFAULT, '0', '', '', '', '', '', valuefromDec)
2757 pcd.SkuInfoList[TAB_DEFAULT] = SkuInfo
2758 elif TAB_DEFAULT not in pcd.SkuInfoList and TAB_COMMON in pcd.SkuInfoList:
2759 pcd.SkuInfoList[TAB_DEFAULT] = pcd.SkuInfoList[TAB_COMMON]
2760 del pcd.SkuInfoList[TAB_COMMON]
2761 elif TAB_DEFAULT in pcd.SkuInfoList and TAB_COMMON in pcd.SkuInfoList:
2762 del pcd.SkuInfoList[TAB_COMMON]
2763
2764 map(self.FilterSkuSettings, Pcds.values())
2765
2766 return Pcds
2767
2768 def FilterSkuSettings(self, PcdObj):
2769
2770 if self.SkuIdMgr.SkuUsageType == self.SkuIdMgr.SINGLE:
2771 if TAB_DEFAULT in PcdObj.SkuInfoList and self.SkuIdMgr.SystemSkuId not in PcdObj.SkuInfoList:
2772 PcdObj.SkuInfoList[self.SkuIdMgr.SystemSkuId] = PcdObj.SkuInfoList[TAB_DEFAULT]
2773 PcdObj.SkuInfoList = {TAB_DEFAULT:PcdObj.SkuInfoList[self.SkuIdMgr.SystemSkuId]}
2774 PcdObj.SkuInfoList[TAB_DEFAULT].SkuIdName = TAB_DEFAULT
2775 PcdObj.SkuInfoList[TAB_DEFAULT].SkuId = '0'
2776
2777 elif self.SkuIdMgr.SkuUsageType == self.SkuIdMgr.DEFAULT:
2778 PcdObj.SkuInfoList = {TAB_DEFAULT:PcdObj.SkuInfoList[TAB_DEFAULT]}
2779
2780 return PcdObj
2781
2782 @staticmethod
2783 def CompareVarAttr(Attr1, Attr2):
2784 if not Attr1 or not Attr2: # for empty string
2785 return True
2786 Attr1s = [attr.strip() for attr in Attr1.split(",")]
2787 Attr1Set = set(Attr1s)
2788 Attr2s = [attr.strip() for attr in Attr2.split(",")]
2789 Attr2Set = set(Attr2s)
2790 if Attr2Set == Attr1Set:
2791 return True
2792 else:
2793 return False
2794
2795 def CompletePcdValues(self, PcdSet):
2796 Pcds = OrderedDict()
2797 DefaultStoreObj = DefaultStore(self._GetDefaultStores())
2798 SkuIds = {skuname:skuid for skuname, skuid in self.SkuIdMgr.AvailableSkuIdSet.items() if skuname != TAB_COMMON}
2799 DefaultStores = set(storename for pcdobj in PcdSet.values() for skuobj in pcdobj.SkuInfoList.values() for storename in skuobj.DefaultStoreDict)
2800 for PcdCName, TokenSpaceGuid in PcdSet:
2801 PcdObj = PcdSet[(PcdCName, TokenSpaceGuid)]
2802
2803 if PcdObj.Type not in [self._PCD_TYPE_STRING_[MODEL_PCD_DYNAMIC_DEFAULT],
2804 self._PCD_TYPE_STRING_[MODEL_PCD_DYNAMIC_HII],
2805 self._PCD_TYPE_STRING_[MODEL_PCD_DYNAMIC_VPD],
2806 self._PCD_TYPE_STRING_[MODEL_PCD_DYNAMIC_EX_DEFAULT],
2807 self._PCD_TYPE_STRING_[MODEL_PCD_DYNAMIC_EX_HII],
2808 self._PCD_TYPE_STRING_[MODEL_PCD_DYNAMIC_EX_VPD]]:
2809 Pcds[PcdCName, TokenSpaceGuid]= PcdObj
2810 continue
2811 PcdType = PcdObj.Type
2812 if PcdType in [self._PCD_TYPE_STRING_[MODEL_PCD_DYNAMIC_HII], self._PCD_TYPE_STRING_[MODEL_PCD_DYNAMIC_EX_HII]]:
2813 for skuid in PcdObj.SkuInfoList:
2814 skuobj = PcdObj.SkuInfoList[skuid]
2815 mindefaultstorename = DefaultStoreObj.GetMin(set(defaultstorename for defaultstorename in skuobj.DefaultStoreDict))
2816 for defaultstorename in DefaultStores:
2817 if defaultstorename not in skuobj.DefaultStoreDict:
2818 skuobj.DefaultStoreDict[defaultstorename] = skuobj.DefaultStoreDict[mindefaultstorename]
2819 skuobj.HiiDefaultValue = skuobj.DefaultStoreDict[mindefaultstorename]
2820 for skuname, skuid in SkuIds.items():
2821 if skuname not in PcdObj.SkuInfoList:
2822 nextskuid = self.SkuIdMgr.GetNextSkuId(skuname)
2823 while nextskuid not in PcdObj.SkuInfoList:
2824 nextskuid = self.SkuIdMgr.GetNextSkuId(nextskuid)
2825 PcdObj.SkuInfoList[skuname] = copy.deepcopy(PcdObj.SkuInfoList[nextskuid])
2826 PcdObj.SkuInfoList[skuname].SkuId = skuid
2827 PcdObj.SkuInfoList[skuname].SkuIdName = skuname
2828 if PcdType in [self._PCD_TYPE_STRING_[MODEL_PCD_DYNAMIC_HII], self._PCD_TYPE_STRING_[MODEL_PCD_DYNAMIC_EX_HII]]:
2829 PcdObj.DefaultValue = PcdObj.SkuInfoList.values()[0].HiiDefaultValue if self.SkuIdMgr.SkuUsageType == self.SkuIdMgr.SINGLE else PcdObj.SkuInfoList[TAB_DEFAULT].HiiDefaultValue
2830 Pcds[PcdCName, TokenSpaceGuid]= PcdObj
2831 return Pcds
2832 ## Retrieve dynamic HII PCD settings
2833 #
2834 # @param Type PCD type
2835 #
2836 # @retval a dict object contains settings of given PCD type
2837 #
2838 def _GetDynamicHiiPcd(self, Type):
2839
2840 VariableAttrs = {}
2841
2842 Pcds = OrderedDict()
2843 UserDefinedDefaultStores = []
2844 #
2845 # tdict is a special dict kind of type, used for selecting correct
2846 # PCD settings for certain ARCH and SKU
2847 #
2848 PcdDict = tdict(True, 5)
2849 PcdSet = set()
2850 RecordList = self._RawData[Type, self._Arch]
2851 # Find out all possible PCD candidates for self._Arch
2852 AvailableSkuIdSet = copy.copy(self.SkuIds)
2853 DefaultStoresDefine = self._GetDefaultStores()
2854
2855 for TokenSpaceGuid, PcdCName, Setting, Arch, SkuName, DefaultStore, Dummy4, Dummy5 in RecordList:
2856 SkuName = SkuName.upper()
2857 SkuName = TAB_DEFAULT if SkuName == TAB_COMMON else SkuName
2858 DefaultStore = DefaultStore.upper()
2859 if DefaultStore == TAB_COMMON:
2860 DefaultStore = TAB_DEFAULT_STORES_DEFAULT
2861 else:
2862 #The end user define [DefaultStores] and [SKUID_IDENTIFIER.Menufacturing] in DSC
2863 UserDefinedDefaultStores.append((PcdCName, TokenSpaceGuid))
2864 if SkuName not in AvailableSkuIdSet:
2865 EdkLogger.error('build', PARAMETER_INVALID, 'Sku %s is not defined in [SkuIds] section' % SkuName,
2866 File=self.MetaFile, Line=Dummy5)
2867 if DefaultStore not in DefaultStoresDefine:
2868 EdkLogger.error('build', PARAMETER_INVALID, 'DefaultStores %s is not defined in [DefaultStores] section' % DefaultStore,
2869 File=self.MetaFile, Line=Dummy5)
2870 if "." not in TokenSpaceGuid and "[" not in PcdCName:
2871 PcdSet.add((PcdCName, TokenSpaceGuid, SkuName, DefaultStore, Dummy5))
2872 PcdDict[Arch, SkuName, PcdCName, TokenSpaceGuid, DefaultStore] = Setting
2873
2874
2875 # Remove redundant PCD candidates, per the ARCH and SKU
2876 for PcdCName, TokenSpaceGuid, SkuName, DefaultStore, Dummy4 in PcdSet:
2877
2878 Setting = PcdDict[self._Arch, SkuName, PcdCName, TokenSpaceGuid, DefaultStore]
2879 if Setting is None:
2880 continue
2881 VariableName, VariableGuid, VariableOffset, DefaultValue, VarAttribute = self._ValidatePcd(PcdCName, TokenSpaceGuid, Setting, Type, Dummy4)
2882
2883 rt, Msg = VariableAttributes.ValidateVarAttributes(VarAttribute)
2884 if not rt:
2885 EdkLogger.error("build", PCD_VARIABLE_ATTRIBUTES_ERROR, "Variable attributes settings for %s is incorrect.\n %s" % (".".join((TokenSpaceGuid, PcdCName)), Msg),
2886 ExtraData="[%s]" % VarAttribute)
2887 ExceedMax = False
2888 FormatCorrect = True
2889 if VariableOffset.isdigit():
2890 if int(VariableOffset, 10) > 0xFFFF:
2891 ExceedMax = True
2892 elif variablePattern.match(VariableOffset):
2893 if int(VariableOffset, 16) > 0xFFFF:
2894 ExceedMax = True
2895 # For Offset written in "A.B"
2896 elif VariableOffset.find('.') > -1:
2897 VariableOffsetList = VariableOffset.split(".")
2898 if not (len(VariableOffsetList) == 2
2899 and IsValidWord(VariableOffsetList[0])
2900 and IsValidWord(VariableOffsetList[1])):
2901 FormatCorrect = False
2902 else:
2903 FormatCorrect = False
2904 if not FormatCorrect:
2905 EdkLogger.error('Build', FORMAT_INVALID, "Invalid syntax or format of the variable offset value is incorrect for %s." % ".".join((TokenSpaceGuid, PcdCName)))
2906
2907 if ExceedMax:
2908 EdkLogger.error('Build', OPTION_VALUE_INVALID, "The variable offset value must not exceed the maximum value of 0xFFFF (UINT16) for %s." % ".".join((TokenSpaceGuid, PcdCName)))
2909 if (VariableName, VariableGuid) not in VariableAttrs:
2910 VariableAttrs[(VariableName, VariableGuid)] = VarAttribute
2911 else:
2912 if not DscBuildData.CompareVarAttr(VariableAttrs[(VariableName, VariableGuid)], VarAttribute):
2913 EdkLogger.error('Build', PCD_VARIABLE_ATTRIBUTES_CONFLICT_ERROR, "The variable %s.%s for DynamicHii PCDs has conflicting attributes [%s] and [%s] " % (VariableGuid, VariableName, VarAttribute, VariableAttrs[(VariableName, VariableGuid)]))
2914
2915 pcdDecObject = self._DecPcds[PcdCName, TokenSpaceGuid]
2916 if (PcdCName, TokenSpaceGuid) in Pcds:
2917 pcdObject = Pcds[PcdCName, TokenSpaceGuid]
2918 if SkuName in pcdObject.SkuInfoList:
2919 Skuitem = pcdObject.SkuInfoList[SkuName]
2920 Skuitem.DefaultStoreDict.update({DefaultStore:DefaultValue})
2921 else:
2922 SkuInfo = SkuInfoClass(SkuName, self.SkuIds[SkuName][0], VariableName, VariableGuid, VariableOffset, DefaultValue, VariableAttribute=VarAttribute, DefaultStore={DefaultStore:DefaultValue})
2923 pcdObject.SkuInfoList[SkuName] = SkuInfo
2924 else:
2925 SkuInfo = SkuInfoClass(SkuName, self.SkuIds[SkuName][0], VariableName, VariableGuid, VariableOffset, DefaultValue, VariableAttribute=VarAttribute, DefaultStore={DefaultStore:DefaultValue})
2926 PcdClassObj = PcdClassObject(
2927 PcdCName,
2928 TokenSpaceGuid,
2929 self._PCD_TYPE_STRING_[Type],
2930 '',
2931 DefaultValue,
2932 '',
2933 '',
2934 OrderedDict({SkuName : SkuInfo}),
2935 False,
2936 None,
2937 pcdDecObject.validateranges,
2938 pcdDecObject.validlists,
2939 pcdDecObject.expressions,
2940 IsDsc=True)
2941 if (PcdCName, TokenSpaceGuid) in UserDefinedDefaultStores:
2942 PcdClassObj.UserDefinedDefaultStoresFlag = True
2943 Pcds[PcdCName, TokenSpaceGuid] = PcdClassObj
2944
2945 Pcds[PcdCName, TokenSpaceGuid].CustomAttribute['DscPosition'] = int(Dummy4)
2946 if SkuName not in Pcds[PcdCName, TokenSpaceGuid].DscRawValue:
2947 Pcds[PcdCName, TokenSpaceGuid].DscRawValue[SkuName] = {}
2948 Pcds[PcdCName, TokenSpaceGuid].DscRawValue[SkuName][DefaultStore] = DefaultValue
2949 for pcd in Pcds.values():
2950 SkuInfoObj = pcd.SkuInfoList.values()[0]
2951 pcdDecObject = self._DecPcds[pcd.TokenCName, pcd.TokenSpaceGuidCName]
2952 pcd.DatumType = pcdDecObject.DatumType
2953 # Only fix the value while no value provided in DSC file.
2954 for sku in pcd.SkuInfoList.values():
2955 if (sku.HiiDefaultValue == "" or sku.HiiDefaultValue is None):
2956 sku.HiiDefaultValue = pcdDecObject.DefaultValue
2957 for default_store in sku.DefaultStoreDict:
2958 sku.DefaultStoreDict[default_store]=pcdDecObject.DefaultValue
2959 pcd.DefaultValue = pcdDecObject.DefaultValue
2960 if TAB_DEFAULT not in pcd.SkuInfoList and TAB_COMMON not in pcd.SkuInfoList:
2961 valuefromDec = pcdDecObject.DefaultValue
2962 SkuInfo = SkuInfoClass(TAB_DEFAULT, '0', SkuInfoObj.VariableName, SkuInfoObj.VariableGuid, SkuInfoObj.VariableOffset, valuefromDec, VariableAttribute=SkuInfoObj.VariableAttribute, DefaultStore={DefaultStore:valuefromDec})
2963 pcd.SkuInfoList[TAB_DEFAULT] = SkuInfo
2964 elif TAB_DEFAULT not in pcd.SkuInfoList and TAB_COMMON in pcd.SkuInfoList:
2965 pcd.SkuInfoList[TAB_DEFAULT] = pcd.SkuInfoList[TAB_COMMON]
2966 del pcd.SkuInfoList[TAB_COMMON]
2967 elif TAB_DEFAULT in pcd.SkuInfoList and TAB_COMMON in pcd.SkuInfoList:
2968 del pcd.SkuInfoList[TAB_COMMON]
2969
2970 if pcd.MaxDatumSize.strip():
2971 MaxSize = int(pcd.MaxDatumSize, 0)
2972 else:
2973 MaxSize = 0
2974 if pcd.DatumType not in TAB_PCD_NUMERIC_TYPES:
2975 for (_, skuobj) in pcd.SkuInfoList.items():
2976 datalen = 0
2977 skuobj.HiiDefaultValue = StringToArray(skuobj.HiiDefaultValue)
2978 datalen = len(skuobj.HiiDefaultValue.split(","))
2979 if datalen > MaxSize:
2980 MaxSize = datalen
2981 for defaultst in skuobj.DefaultStoreDict:
2982 skuobj.DefaultStoreDict[defaultst] = StringToArray(skuobj.DefaultStoreDict[defaultst])
2983 pcd.DefaultValue = StringToArray(pcd.DefaultValue)
2984 pcd.MaxDatumSize = str(MaxSize)
2985 rt, invalidhii = DscBuildData.CheckVariableNameAssignment(Pcds)
2986 if not rt:
2987 invalidpcd = ",".join(invalidhii)
2988 EdkLogger.error('build', PCD_VARIABLE_INFO_ERROR, Message='The same HII PCD must map to the same EFI variable for all SKUs', File=self.MetaFile, ExtraData=invalidpcd)
2989
2990 map(self.FilterSkuSettings, Pcds.values())
2991
2992 return Pcds
2993
2994 @staticmethod
2995 def CheckVariableNameAssignment(Pcds):
2996 invalidhii = []
2997 for pcdname in Pcds:
2998 pcd = Pcds[pcdname]
2999 varnameset = set(sku.VariableName for (skuid, sku) in pcd.SkuInfoList.items())
3000 if len(varnameset) > 1:
3001 invalidhii.append(".".join((pcdname[1], pcdname[0])))
3002 if len(invalidhii):
3003 return False, invalidhii
3004 else:
3005 return True, []
3006 ## Retrieve dynamic VPD PCD settings
3007 #
3008 # @param Type PCD type
3009 #
3010 # @retval a dict object contains settings of given PCD type
3011 #
3012 def _GetDynamicVpdPcd(self, Type):
3013
3014
3015 Pcds = OrderedDict()
3016 #
3017 # tdict is a special dict kind of type, used for selecting correct
3018 # PCD settings for certain ARCH and SKU
3019 #
3020 PcdDict = tdict(True, 4)
3021 PcdList = []
3022
3023 # Find out all possible PCD candidates for self._Arch
3024 RecordList = self._RawData[Type, self._Arch]
3025 AvailableSkuIdSet = copy.copy(self.SkuIds)
3026
3027 for TokenSpaceGuid, PcdCName, Setting, Arch, SkuName, Dummy3, Dummy4, Dummy5 in RecordList:
3028 SkuName = SkuName.upper()
3029 SkuName = TAB_DEFAULT if SkuName == TAB_COMMON else SkuName
3030 if SkuName not in AvailableSkuIdSet:
3031 EdkLogger.error('build', PARAMETER_INVALID, 'Sku %s is not defined in [SkuIds] section' % SkuName,
3032 File=self.MetaFile, Line=Dummy5)
3033 if "." not in TokenSpaceGuid and "[" not in PcdCName:
3034 PcdList.append((PcdCName, TokenSpaceGuid, SkuName, Dummy5))
3035 PcdDict[Arch, SkuName, PcdCName, TokenSpaceGuid] = Setting
3036
3037 # Remove redundant PCD candidates, per the ARCH and SKU
3038 for PcdCName, TokenSpaceGuid, SkuName, Dummy4 in PcdList:
3039 Setting = PcdDict[self._Arch, SkuName, PcdCName, TokenSpaceGuid]
3040 if Setting is None:
3041 continue
3042 #
3043 # For the VOID* type, it can have optional data of MaxDatumSize and InitialValue
3044 # For the Integer & Boolean type, the optional data can only be InitialValue.
3045 # At this point, we put all the data into the PcdClssObject for we don't know the PCD's datumtype
3046 # until the DEC parser has been called.
3047 #
3048 VpdOffset, MaxDatumSize, InitialValue = self._ValidatePcd(PcdCName, TokenSpaceGuid, Setting, Type, Dummy4)
3049 if MaxDatumSize:
3050 if int(MaxDatumSize, 0) > 0xFFFF:
3051 EdkLogger.error('build', FORMAT_INVALID, "The size value must not exceed the maximum value of 0xFFFF (UINT16) for %s." % ".".join((TokenSpaceGuid, PcdCName)),
3052 File=self.MetaFile, Line=Dummy4)
3053 if int(MaxDatumSize, 0) < 0:
3054 EdkLogger.error('build', FORMAT_INVALID, "The size value can't be set to negative value for %s." % ".".join((TokenSpaceGuid, PcdCName)),
3055 File=self.MetaFile, Line=Dummy4)
3056 SkuInfo = SkuInfoClass(SkuName, self.SkuIds[SkuName][0], '', '', '', '', VpdOffset, InitialValue)
3057 if (PcdCName, TokenSpaceGuid) in Pcds:
3058 pcdObject = Pcds[PcdCName, TokenSpaceGuid]
3059 pcdObject.SkuInfoList[SkuName] = SkuInfo
3060 if MaxDatumSize.strip():
3061 CurrentMaxSize = int(MaxDatumSize.strip(), 0)
3062 else:
3063 CurrentMaxSize = 0
3064 if pcdObject.MaxDatumSize:
3065 PcdMaxSize = int(pcdObject.MaxDatumSize, 0)
3066 else:
3067 PcdMaxSize = 0
3068 if CurrentMaxSize > PcdMaxSize:
3069 pcdObject.MaxDatumSize = str(CurrentMaxSize)
3070 else:
3071 Pcds[PcdCName, TokenSpaceGuid] = PcdClassObject(
3072 PcdCName,
3073 TokenSpaceGuid,
3074 self._PCD_TYPE_STRING_[Type],
3075 '',
3076 InitialValue,
3077 '',
3078 MaxDatumSize,
3079 OrderedDict({SkuName : SkuInfo}),
3080 False,
3081 None,
3082 IsDsc=True)
3083
3084 if SkuName not in Pcds[PcdCName, TokenSpaceGuid].DscRawValue:
3085 Pcds[PcdCName, TokenSpaceGuid].DscRawValue[SkuName] = {}
3086 Pcds[PcdCName, TokenSpaceGuid].DscRawValue[SkuName][TAB_DEFAULT_STORES_DEFAULT] = InitialValue
3087 for pcd in Pcds.values():
3088 SkuInfoObj = pcd.SkuInfoList.values()[0]
3089 pcdDecObject = self._DecPcds[pcd.TokenCName, pcd.TokenSpaceGuidCName]
3090 pcd.DatumType = pcdDecObject.DatumType
3091 # Only fix the value while no value provided in DSC file.
3092 for sku in pcd.SkuInfoList.values():
3093 if not sku.DefaultValue:
3094 sku.DefaultValue = pcdDecObject.DefaultValue
3095 if TAB_DEFAULT not in pcd.SkuInfoList and TAB_COMMON not in pcd.SkuInfoList:
3096 valuefromDec = pcdDecObject.DefaultValue
3097 SkuInfo = SkuInfoClass(TAB_DEFAULT, '0', '', '', '', '', SkuInfoObj.VpdOffset, valuefromDec)
3098 pcd.SkuInfoList[TAB_DEFAULT] = SkuInfo
3099 elif TAB_DEFAULT not in pcd.SkuInfoList and TAB_COMMON in pcd.SkuInfoList:
3100 pcd.SkuInfoList[TAB_DEFAULT] = pcd.SkuInfoList[TAB_COMMON]
3101 del pcd.SkuInfoList[TAB_COMMON]
3102 elif TAB_DEFAULT in pcd.SkuInfoList and TAB_COMMON in pcd.SkuInfoList:
3103 del pcd.SkuInfoList[TAB_COMMON]
3104
3105 #For the same one VOID* pcd, if the default value type of one SKU is "Unicode string",
3106 #the other SKUs are "OtherVOID*"(ASCII string or byte array),Then convert "Unicode string" to "byte array".
3107 for pcd in Pcds.values():
3108 PcdValueTypeSet = set()
3109 for sku in pcd.SkuInfoList.values():
3110 PcdValueTypeSet.add("UnicodeString" if sku.DefaultValue.startswith(('L"',"L'")) else "OtherVOID*")
3111 if len(PcdValueTypeSet) > 1:
3112 for sku in pcd.SkuInfoList.values():
3113 sku.DefaultValue = StringToArray(sku.DefaultValue) if sku.DefaultValue.startswith(('L"',"L'")) else sku.DefaultValue
3114
3115 map(self.FilterSkuSettings, Pcds.values())
3116 return Pcds
3117
3118 ## Add external modules
3119 #
3120 # The external modules are mostly those listed in FDF file, which don't
3121 # need "build".
3122 #
3123 # @param FilePath The path of module description file
3124 #
3125 def AddModule(self, FilePath):
3126 FilePath = NormPath(FilePath)
3127 if FilePath not in self.Modules:
3128 Module = ModuleBuildClassObject()
3129 Module.MetaFile = FilePath
3130 self.Modules.append(Module)
3131
3132 @property
3133 def ToolChainFamily(self):
3134 self._ToolChainFamily = TAB_COMPILER_MSFT
3135 BuildConfigurationFile = os.path.normpath(os.path.join(GlobalData.gConfDirectory, "target.txt"))
3136 if os.path.isfile(BuildConfigurationFile) == True:
3137 TargetTxt = TargetTxtClassObject()
3138 TargetTxt.LoadTargetTxtFile(BuildConfigurationFile)
3139 ToolDefinitionFile = TargetTxt.TargetTxtDictionary[DataType.TAB_TAT_DEFINES_TOOL_CHAIN_CONF]
3140 if ToolDefinitionFile == '':
3141 ToolDefinitionFile = "tools_def.txt"
3142 ToolDefinitionFile = os.path.normpath(mws.join(self.WorkspaceDir, 'Conf', ToolDefinitionFile))
3143 if os.path.isfile(ToolDefinitionFile) == True:
3144 ToolDef = ToolDefClassObject()
3145 ToolDef.LoadToolDefFile(ToolDefinitionFile)
3146 ToolDefinition = ToolDef.ToolsDefTxtDatabase
3147 if TAB_TOD_DEFINES_FAMILY not in ToolDefinition \
3148 or self._Toolchain not in ToolDefinition[TAB_TOD_DEFINES_FAMILY] \
3149 or not ToolDefinition[TAB_TOD_DEFINES_FAMILY][self._Toolchain]:
3150 self._ToolChainFamily = TAB_COMPILER_MSFT
3151 else:
3152 self._ToolChainFamily = ToolDefinition[TAB_TOD_DEFINES_FAMILY][self._Toolchain]
3153 return self._ToolChainFamily
3154
3155 ## Add external PCDs
3156 #
3157 # The external PCDs are mostly those listed in FDF file to specify address
3158 # or offset information.
3159 #
3160 # @param Name Name of the PCD
3161 # @param Guid Token space guid of the PCD
3162 # @param Value Value of the PCD
3163 #
3164 def AddPcd(self, Name, Guid, Value):
3165 if (Name, Guid) not in self.Pcds:
3166 self.Pcds[Name, Guid] = PcdClassObject(Name, Guid, '', '', '', '', '', {}, False, None)
3167 self.Pcds[Name, Guid].DefaultValue = Value
3168
3169 @property
3170 def DecPcds(self):
3171 if self._DecPcds is None:
3172 FdfInfList = []
3173 if GlobalData.gFdfParser:
3174 FdfInfList = GlobalData.gFdfParser.Profile.InfList
3175 PkgSet = set()
3176 for Inf in FdfInfList:
3177 ModuleFile = PathClass(NormPath(Inf), GlobalData.gWorkspace, Arch=self._Arch)
3178 if ModuleFile in self._Modules:
3179 continue
3180 ModuleData = self._Bdb[ModuleFile, self._Arch, self._Target, self._Toolchain]
3181 PkgSet.update(ModuleData.Packages)
3182 self._DecPcds, self._GuidDict = GetDeclaredPcd(self, self._Bdb, self._Arch, self._Target, self._Toolchain, PkgSet)
3183 self._GuidDict.update(GlobalData.gPlatformPcds)
3184 return self._DecPcds