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