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