BaseTools: Correct PCD generation logic to make sure DB is use
[mirror_edk2.git] / BaseTools / Source / Python / Workspace / DscBuildData.py
CommitLineData
ae7b6df8
LG
1## @file\r
2# This file is used to create a database used by build tool\r
3#\r
4# Copyright (c) 2017, Intel Corporation. All rights reserved.<BR>\r
5# (C) Copyright 2016 Hewlett Packard Enterprise Development LP<BR>\r
6# This program and the accompanying materials\r
7# are licensed and made available under the terms and conditions of the BSD License\r
8# which accompanies this distribution. The full text of the license may be found at\r
9# http://opensource.org/licenses/bsd-license.php\r
10#\r
11# THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,\r
12# WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.\r
13#\r
14\r
15## Platform build information from DSC file\r
16#\r
17# This class is used to retrieve information stored in database and convert them\r
18# into PlatformBuildClassObject form for easier use for AutoGen.\r
19#\r
20from Common.String import *\r
21from Common.DataType import *\r
22from Common.Misc import *\r
23from types import *\r
24\r
25from CommonDataClass.CommonClass import SkuInfoClass\r
26\r
27from MetaDataTable import *\r
28from MetaFileTable import *\r
29from MetaFileParser import *\r
30\r
31from WorkspaceCommon import GetDeclaredPcd\r
32from Common.Misc import AnalyzeDscPcd\r
33from Common.Misc import ProcessDuplicatedInf\r
34import re\r
35from Common.Parsing import IsValidWord\r
36from Common.VariableAttributes import VariableAttributes\r
37import Common.GlobalData as GlobalData\r
38import subprocess\r
39from Workspace.BuildClassObject import PlatformBuildClassObject, StructurePcd, PcdClassObject, ModuleBuildClassObject\r
40\r
41#\r
42# Treat CHAR16 as a synonym for UINT16. CHAR16 support is required for VFR C structs\r
43#\r
44PcdValueInitName = 'PcdValueInit'\r
45PcdSupportedBaseTypes = ['BOOLEAN', 'UINT8', 'UINT16', 'UINT32', 'UINT64', 'CHAR16']\r
46PcdSupportedBaseTypeWidth = {'BOOLEAN':8, 'UINT8':8, 'UINT16':16, 'UINT32':32, 'UINT64':64}\r
47PcdUnsupportedBaseTypes = ['INT8', 'INT16', 'INT32', 'INT64', 'CHAR8', 'UINTN', 'INTN', 'VOID']\r
48\r
49PcdMainCHeader = '''\r
50/**\r
51 DO NOT EDIT\r
52 FILE auto-generated\r
53**/\r
54\r
55#include <stdio.h>\r
56#include <stdlib.h>\r
57#include <string.h>\r
58#include <PcdValueCommon.h>\r
59'''\r
60\r
61PcdMainCEntry = '''\r
62int\r
63main (\r
64 int argc,\r
65 char *argv[]\r
66 )\r
67{\r
68 return PcdValueMain (argc, argv);\r
69}\r
70'''\r
71\r
72PcdMakefileHeader = '''\r
73#\r
74# DO NOT EDIT\r
75# This file is auto-generated by build utility\r
76#\r
77\r
78'''\r
79\r
80PcdMakefileEnd = '''\r
81!INCLUDE $(BASE_TOOLS_PATH)\Source\C\Makefiles\ms.common\r
82\r
83CFLAGS = $(CFLAGS) /wd4200 /wd4034 /wd4101\r
84\r
85LIBS = $(LIB_PATH)\Common.lib\r
86\r
87!INCLUDE $(BASE_TOOLS_PATH)\Source\C\Makefiles\ms.app\r
88'''\r
89\r
90PcdGccMakefile = '''\r
91ARCH ?= IA32\r
92MAKEROOT ?= $(EDK_TOOLS_PATH)/Source/C\r
93LIBS = -lCommon\r
94'''\r
95\r
96class DscBuildData(PlatformBuildClassObject):\r
97 # dict used to convert PCD type in database to string used by build tool\r
98 _PCD_TYPE_STRING_ = {\r
99 MODEL_PCD_FIXED_AT_BUILD : "FixedAtBuild",\r
100 MODEL_PCD_PATCHABLE_IN_MODULE : "PatchableInModule",\r
101 MODEL_PCD_FEATURE_FLAG : "FeatureFlag",\r
102 MODEL_PCD_DYNAMIC : "Dynamic",\r
103 MODEL_PCD_DYNAMIC_DEFAULT : "Dynamic",\r
104 MODEL_PCD_DYNAMIC_HII : "DynamicHii",\r
105 MODEL_PCD_DYNAMIC_VPD : "DynamicVpd",\r
106 MODEL_PCD_DYNAMIC_EX : "DynamicEx",\r
107 MODEL_PCD_DYNAMIC_EX_DEFAULT : "DynamicEx",\r
108 MODEL_PCD_DYNAMIC_EX_HII : "DynamicExHii",\r
109 MODEL_PCD_DYNAMIC_EX_VPD : "DynamicExVpd",\r
110 }\r
111\r
112 # dict used to convert part of [Defines] to members of DscBuildData directly\r
113 _PROPERTY_ = {\r
114 #\r
115 # Required Fields\r
116 #\r
117 TAB_DSC_DEFINES_PLATFORM_NAME : "_PlatformName",\r
118 TAB_DSC_DEFINES_PLATFORM_GUID : "_Guid",\r
119 TAB_DSC_DEFINES_PLATFORM_VERSION : "_Version",\r
120 TAB_DSC_DEFINES_DSC_SPECIFICATION : "_DscSpecification",\r
121 # TAB_DSC_DEFINES_OUTPUT_DIRECTORY : "_OutputDirectory",\r
122 # TAB_DSC_DEFINES_SUPPORTED_ARCHITECTURES : "_SupArchList",\r
123 # TAB_DSC_DEFINES_BUILD_TARGETS : "_BuildTargets",\r
124 TAB_DSC_DEFINES_SKUID_IDENTIFIER : "_SkuName",\r
125 # TAB_DSC_DEFINES_FLASH_DEFINITION : "_FlashDefinition",\r
126 TAB_DSC_DEFINES_BUILD_NUMBER : "_BuildNumber",\r
127 TAB_DSC_DEFINES_MAKEFILE_NAME : "_MakefileName",\r
128 TAB_DSC_DEFINES_BS_BASE_ADDRESS : "_BsBaseAddress",\r
129 TAB_DSC_DEFINES_RT_BASE_ADDRESS : "_RtBaseAddress",\r
130 # TAB_DSC_DEFINES_RFC_LANGUAGES : "_RFCLanguages",\r
131 # TAB_DSC_DEFINES_ISO_LANGUAGES : "_ISOLanguages",\r
132 }\r
133\r
134 # used to compose dummy library class name for those forced library instances\r
135 _NullLibraryNumber = 0\r
136\r
137 ## Constructor of DscBuildData\r
138 #\r
139 # Initialize object of DscBuildData\r
140 #\r
141 # @param FilePath The path of platform description file\r
142 # @param RawData The raw data of DSC file\r
143 # @param BuildDataBase Database used to retrieve module/package information\r
144 # @param Arch The target architecture\r
145 # @param Platform (not used for DscBuildData)\r
146 # @param Macros Macros used for replacement in DSC file\r
147 #\r
148 def __init__(self, FilePath, RawData, BuildDataBase, Arch='COMMON', Target=None, Toolchain=None):\r
149 self.MetaFile = FilePath\r
150 self._RawData = RawData\r
151 self._Bdb = BuildDataBase\r
152 self._Arch = Arch\r
153 self._Target = Target\r
154 self._Toolchain = Toolchain\r
155 self._Clear()\r
156 self._HandleOverridePath()\r
157 if os.getenv("WORKSPACE"):\r
158 self.OutputPath = os.path.join(os.getenv("WORKSPACE"), 'Build', PcdValueInitName)\r
159 else:\r
160 self.OutputPath = os.path.dirname(self.DscFile)\r
8518bf0b 161 self.DefaultStores = None\r
e651d06c 162 self.SkuIdMgr = SkuClass(self.SkuName, self.SkuIds)\r
8518bf0b 163 arraystr = self.SkuIdMgr.DumpSkuIdArrary()\r
ae7b6df8
LG
164\r
165 ## XXX[key] = value\r
166 def __setitem__(self, key, value):\r
167 self.__dict__[self._PROPERTY_[key]] = value\r
168\r
169 ## value = XXX[key]\r
170 def __getitem__(self, key):\r
171 return self.__dict__[self._PROPERTY_[key]]\r
172\r
173 ## "in" test support\r
174 def __contains__(self, key):\r
175 return key in self._PROPERTY_\r
176\r
177 ## Set all internal used members of DscBuildData to None\r
178 def _Clear(self):\r
179 self._Header = None\r
180 self._PlatformName = None\r
181 self._Guid = None\r
182 self._Version = None\r
183 self._DscSpecification = None\r
184 self._OutputDirectory = None\r
185 self._SupArchList = None\r
186 self._BuildTargets = None\r
187 self._SkuName = None\r
ae7b6df8
LG
188 self._PcdInfoFlag = None\r
189 self._VarCheckFlag = None\r
190 self._FlashDefinition = None\r
191 self._Prebuild = None\r
192 self._Postbuild = None\r
193 self._BuildNumber = None\r
194 self._MakefileName = None\r
195 self._BsBaseAddress = None\r
196 self._RtBaseAddress = None\r
197 self._SkuIds = None\r
198 self._Modules = None\r
199 self._LibraryInstances = None\r
200 self._LibraryClasses = None\r
201 self._Pcds = None\r
202 self._DecPcds = None\r
203 self._BuildOptions = None\r
204 self._ModuleTypeOptions = None\r
205 self._LoadFixAddress = None\r
206 self._RFCLanguages = None\r
207 self._ISOLanguages = None\r
208 self._VpdToolGuid = None\r
209 self.__Macros = None\r
8518bf0b 210 self.DefaultStores = None\r
ae7b6df8
LG
211\r
212\r
213 ## handle Override Path of Module\r
214 def _HandleOverridePath(self):\r
215 RecordList = self._RawData[MODEL_META_DATA_COMPONENT, self._Arch]\r
216 Macros = self._Macros\r
217 Macros["EDK_SOURCE"] = GlobalData.gEcpSource\r
218 for Record in RecordList:\r
8518bf0b
LG
219 ModuleId = Record[6]\r
220 LineNo = Record[7]\r
ae7b6df8
LG
221 ModuleFile = PathClass(NormPath(Record[0]), GlobalData.gWorkspace, Arch=self._Arch)\r
222 RecordList = self._RawData[MODEL_META_DATA_COMPONENT_SOURCE_OVERRIDE_PATH, self._Arch, None, ModuleId]\r
223 if RecordList != []:\r
224 SourceOverridePath = mws.join(GlobalData.gWorkspace, NormPath(RecordList[0][0]))\r
225\r
226 # Check if the source override path exists\r
227 if not os.path.isdir(SourceOverridePath):\r
228 EdkLogger.error('build', FILE_NOT_FOUND, Message='Source override path does not exist:', File=self.MetaFile, ExtraData=SourceOverridePath, Line=LineNo)\r
229\r
230 # Add to GlobalData Variables\r
231 GlobalData.gOverrideDir[ModuleFile.Key] = SourceOverridePath\r
232\r
233 ## Get current effective macros\r
234 def _GetMacros(self):\r
235 if self.__Macros == None:\r
236 self.__Macros = {}\r
237 self.__Macros.update(GlobalData.gPlatformDefines)\r
238 self.__Macros.update(GlobalData.gGlobalDefines)\r
239 self.__Macros.update(GlobalData.gCommandLineDefines)\r
240 return self.__Macros\r
241\r
242 ## Get architecture\r
243 def _GetArch(self):\r
244 return self._Arch\r
245\r
246 ## Set architecture\r
247 #\r
248 # Changing the default ARCH to another may affect all other information\r
249 # because all information in a platform may be ARCH-related. That's\r
250 # why we need to clear all internal used members, in order to cause all\r
251 # information to be re-retrieved.\r
252 #\r
253 # @param Value The value of ARCH\r
254 #\r
255 def _SetArch(self, Value):\r
256 if self._Arch == Value:\r
257 return\r
258 self._Arch = Value\r
259 self._Clear()\r
260\r
261 ## Retrieve all information in [Defines] section\r
262 #\r
263 # (Retriving all [Defines] information in one-shot is just to save time.)\r
264 #\r
265 def _GetHeaderInfo(self):\r
266 RecordList = self._RawData[MODEL_META_DATA_HEADER, self._Arch]\r
267 for Record in RecordList:\r
268 Name = Record[1]\r
269 # items defined _PROPERTY_ don't need additional processing\r
270\r
271 # some special items in [Defines] section need special treatment\r
272 if Name == TAB_DSC_DEFINES_OUTPUT_DIRECTORY:\r
273 self._OutputDirectory = NormPath(Record[2], self._Macros)\r
274 if ' ' in self._OutputDirectory:\r
275 EdkLogger.error("build", FORMAT_NOT_SUPPORTED, "No space is allowed in OUTPUT_DIRECTORY",\r
276 File=self.MetaFile, Line=Record[-1],\r
277 ExtraData=self._OutputDirectory)\r
278 elif Name == TAB_DSC_DEFINES_FLASH_DEFINITION:\r
279 self._FlashDefinition = PathClass(NormPath(Record[2], self._Macros), GlobalData.gWorkspace)\r
280 ErrorCode, ErrorInfo = self._FlashDefinition.Validate('.fdf')\r
281 if ErrorCode != 0:\r
282 EdkLogger.error('build', ErrorCode, File=self.MetaFile, Line=Record[-1],\r
283 ExtraData=ErrorInfo)\r
284 elif Name == TAB_DSC_PREBUILD:\r
285 PrebuildValue = Record[2]\r
286 if Record[2][0] == '"':\r
287 if Record[2][-1] != '"':\r
288 EdkLogger.error('build', FORMAT_INVALID, 'Missing double quotes in the end of %s statement.' % TAB_DSC_PREBUILD,\r
289 File=self.MetaFile, Line=Record[-1])\r
290 PrebuildValue = Record[2][1:-1]\r
291 self._Prebuild = PrebuildValue\r
292 elif Name == TAB_DSC_POSTBUILD:\r
293 PostbuildValue = Record[2]\r
294 if Record[2][0] == '"':\r
295 if Record[2][-1] != '"':\r
296 EdkLogger.error('build', FORMAT_INVALID, 'Missing double quotes in the end of %s statement.' % TAB_DSC_POSTBUILD,\r
297 File=self.MetaFile, Line=Record[-1])\r
298 PostbuildValue = Record[2][1:-1]\r
299 self._Postbuild = PostbuildValue\r
300 elif Name == TAB_DSC_DEFINES_SUPPORTED_ARCHITECTURES:\r
301 self._SupArchList = GetSplitValueList(Record[2], TAB_VALUE_SPLIT)\r
302 elif Name == TAB_DSC_DEFINES_BUILD_TARGETS:\r
303 self._BuildTargets = GetSplitValueList(Record[2])\r
304 elif Name == TAB_DSC_DEFINES_SKUID_IDENTIFIER:\r
305 if self._SkuName == None:\r
306 self._SkuName = Record[2]\r
e651d06c
LG
307 if GlobalData.gSKUID_CMD:\r
308 self._SkuName = GlobalData.gSKUID_CMD\r
ae7b6df8
LG
309 elif Name == TAB_DSC_DEFINES_PCD_INFO_GENERATION:\r
310 self._PcdInfoFlag = Record[2]\r
311 elif Name == TAB_DSC_DEFINES_PCD_VAR_CHECK_GENERATION:\r
312 self._VarCheckFlag = Record[2]\r
313 elif Name == TAB_FIX_LOAD_TOP_MEMORY_ADDRESS:\r
314 try:\r
315 self._LoadFixAddress = int (Record[2], 0)\r
316 except:\r
317 EdkLogger.error("build", PARAMETER_INVALID, "FIX_LOAD_TOP_MEMORY_ADDRESS %s is not valid dec or hex string" % (Record[2]))\r
318 elif Name == TAB_DSC_DEFINES_RFC_LANGUAGES:\r
319 if not Record[2] or Record[2][0] != '"' or Record[2][-1] != '"' or len(Record[2]) == 1:\r
320 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"',\r
321 File=self.MetaFile, Line=Record[-1])\r
322 LanguageCodes = Record[2][1:-1]\r
323 if not LanguageCodes:\r
324 EdkLogger.error('build', FORMAT_NOT_SUPPORTED, 'one or more RFC4646 format language code must be provided for RFC_LANGUAGES statement',\r
325 File=self.MetaFile, Line=Record[-1])\r
326 LanguageList = GetSplitValueList(LanguageCodes, TAB_SEMI_COLON_SPLIT)\r
327 # check whether there is empty entries in the list\r
328 if None in LanguageList:\r
329 EdkLogger.error('build', FORMAT_NOT_SUPPORTED, 'one or more empty language code is in RFC_LANGUAGES statement',\r
330 File=self.MetaFile, Line=Record[-1])\r
331 self._RFCLanguages = LanguageList\r
332 elif Name == TAB_DSC_DEFINES_ISO_LANGUAGES:\r
333 if not Record[2] or Record[2][0] != '"' or Record[2][-1] != '"' or len(Record[2]) == 1:\r
334 EdkLogger.error('build', FORMAT_NOT_SUPPORTED, 'language code for ISO_LANGUAGES must have double quotes around it, for example: ISO_LANGUAGES = "engchn"',\r
335 File=self.MetaFile, Line=Record[-1])\r
336 LanguageCodes = Record[2][1:-1]\r
337 if not LanguageCodes:\r
338 EdkLogger.error('build', FORMAT_NOT_SUPPORTED, 'one or more ISO639-2 format language code must be provided for ISO_LANGUAGES statement',\r
339 File=self.MetaFile, Line=Record[-1])\r
340 if len(LanguageCodes) % 3:\r
341 EdkLogger.error('build', FORMAT_NOT_SUPPORTED, 'bad ISO639-2 format for ISO_LANGUAGES',\r
342 File=self.MetaFile, Line=Record[-1])\r
343 LanguageList = []\r
344 for i in range(0, len(LanguageCodes), 3):\r
345 LanguageList.append(LanguageCodes[i:i + 3])\r
346 self._ISOLanguages = LanguageList\r
347 elif Name == TAB_DSC_DEFINES_VPD_TOOL_GUID:\r
348 #\r
349 # try to convert GUID to a real UUID value to see whether the GUID is format\r
350 # for VPD_TOOL_GUID is correct.\r
351 #\r
352 try:\r
353 uuid.UUID(Record[2])\r
354 except:\r
355 EdkLogger.error("build", FORMAT_INVALID, "Invalid GUID format for VPD_TOOL_GUID", File=self.MetaFile)\r
356 self._VpdToolGuid = Record[2]\r
357 elif Name in self:\r
358 self[Name] = Record[2]\r
359 # set _Header to non-None in order to avoid database re-querying\r
360 self._Header = 'DUMMY'\r
361\r
362 ## Retrieve platform name\r
363 def _GetPlatformName(self):\r
364 if self._PlatformName == None:\r
365 if self._Header == None:\r
366 self._GetHeaderInfo()\r
367 if self._PlatformName == None:\r
368 EdkLogger.error('build', ATTRIBUTE_NOT_AVAILABLE, "No PLATFORM_NAME", File=self.MetaFile)\r
369 return self._PlatformName\r
370\r
371 ## Retrieve file guid\r
372 def _GetFileGuid(self):\r
373 if self._Guid == None:\r
374 if self._Header == None:\r
375 self._GetHeaderInfo()\r
376 if self._Guid == None:\r
377 EdkLogger.error('build', ATTRIBUTE_NOT_AVAILABLE, "No PLATFORM_GUID", File=self.MetaFile)\r
378 return self._Guid\r
379\r
380 ## Retrieve platform version\r
381 def _GetVersion(self):\r
382 if self._Version == None:\r
383 if self._Header == None:\r
384 self._GetHeaderInfo()\r
385 if self._Version == None:\r
386 EdkLogger.error('build', ATTRIBUTE_NOT_AVAILABLE, "No PLATFORM_VERSION", File=self.MetaFile)\r
387 return self._Version\r
388\r
389 ## Retrieve platform description file version\r
390 def _GetDscSpec(self):\r
391 if self._DscSpecification == None:\r
392 if self._Header == None:\r
393 self._GetHeaderInfo()\r
394 if self._DscSpecification == None:\r
395 EdkLogger.error('build', ATTRIBUTE_NOT_AVAILABLE, "No DSC_SPECIFICATION", File=self.MetaFile)\r
396 return self._DscSpecification\r
397\r
398 ## Retrieve OUTPUT_DIRECTORY\r
399 def _GetOutpuDir(self):\r
400 if self._OutputDirectory == None:\r
401 if self._Header == None:\r
402 self._GetHeaderInfo()\r
403 if self._OutputDirectory == None:\r
404 self._OutputDirectory = os.path.join("Build", self._PlatformName)\r
405 return self._OutputDirectory\r
406\r
407 ## Retrieve SUPPORTED_ARCHITECTURES\r
408 def _GetSupArch(self):\r
409 if self._SupArchList == None:\r
410 if self._Header == None:\r
411 self._GetHeaderInfo()\r
412 if self._SupArchList == None:\r
413 EdkLogger.error('build', ATTRIBUTE_NOT_AVAILABLE, "No SUPPORTED_ARCHITECTURES", File=self.MetaFile)\r
414 return self._SupArchList\r
415\r
416 ## Retrieve BUILD_TARGETS\r
417 def _GetBuildTarget(self):\r
418 if self._BuildTargets == None:\r
419 if self._Header == None:\r
420 self._GetHeaderInfo()\r
421 if self._BuildTargets == None:\r
422 EdkLogger.error('build', ATTRIBUTE_NOT_AVAILABLE, "No BUILD_TARGETS", File=self.MetaFile)\r
423 return self._BuildTargets\r
424\r
425 def _GetPcdInfoFlag(self):\r
426 if self._PcdInfoFlag == None or self._PcdInfoFlag.upper() == 'FALSE':\r
427 return False\r
428 elif self._PcdInfoFlag.upper() == 'TRUE':\r
429 return True\r
430 else:\r
431 return False\r
432 def _GetVarCheckFlag(self):\r
433 if self._VarCheckFlag == None or self._VarCheckFlag.upper() == 'FALSE':\r
434 return False\r
435 elif self._VarCheckFlag.upper() == 'TRUE':\r
436 return True\r
437 else:\r
438 return False\r
e651d06c
LG
439\r
440 # # Retrieve SKUID_IDENTIFIER\r
ae7b6df8
LG
441 def _GetSkuName(self):\r
442 if self._SkuName == None:\r
443 if self._Header == None:\r
444 self._GetHeaderInfo()\r
e651d06c 445 if self._SkuName == None:\r
ae7b6df8
LG
446 self._SkuName = 'DEFAULT'\r
447 return self._SkuName\r
448\r
449 ## Override SKUID_IDENTIFIER\r
450 def _SetSkuName(self, Value):\r
451 self._SkuName = Value\r
452 self._Pcds = None\r
453\r
454 def _GetFdfFile(self):\r
455 if self._FlashDefinition == None:\r
456 if self._Header == None:\r
457 self._GetHeaderInfo()\r
458 if self._FlashDefinition == None:\r
459 self._FlashDefinition = ''\r
460 return self._FlashDefinition\r
461\r
462 def _GetPrebuild(self):\r
463 if self._Prebuild == None:\r
464 if self._Header == None:\r
465 self._GetHeaderInfo()\r
466 if self._Prebuild == None:\r
467 self._Prebuild = ''\r
468 return self._Prebuild\r
469\r
470 def _GetPostbuild(self):\r
471 if self._Postbuild == None:\r
472 if self._Header == None:\r
473 self._GetHeaderInfo()\r
474 if self._Postbuild == None:\r
475 self._Postbuild = ''\r
476 return self._Postbuild\r
477\r
478 ## Retrieve FLASH_DEFINITION\r
479 def _GetBuildNumber(self):\r
480 if self._BuildNumber == None:\r
481 if self._Header == None:\r
482 self._GetHeaderInfo()\r
483 if self._BuildNumber == None:\r
484 self._BuildNumber = ''\r
485 return self._BuildNumber\r
486\r
487 ## Retrieve MAKEFILE_NAME\r
488 def _GetMakefileName(self):\r
489 if self._MakefileName == None:\r
490 if self._Header == None:\r
491 self._GetHeaderInfo()\r
492 if self._MakefileName == None:\r
493 self._MakefileName = ''\r
494 return self._MakefileName\r
495\r
496 ## Retrieve BsBaseAddress\r
497 def _GetBsBaseAddress(self):\r
498 if self._BsBaseAddress == None:\r
499 if self._Header == None:\r
500 self._GetHeaderInfo()\r
501 if self._BsBaseAddress == None:\r
502 self._BsBaseAddress = ''\r
503 return self._BsBaseAddress\r
504\r
505 ## Retrieve RtBaseAddress\r
506 def _GetRtBaseAddress(self):\r
507 if self._RtBaseAddress == None:\r
508 if self._Header == None:\r
509 self._GetHeaderInfo()\r
510 if self._RtBaseAddress == None:\r
511 self._RtBaseAddress = ''\r
512 return self._RtBaseAddress\r
513\r
514 ## Retrieve the top address for the load fix address\r
515 def _GetLoadFixAddress(self):\r
516 if self._LoadFixAddress == None:\r
517 if self._Header == None:\r
518 self._GetHeaderInfo()\r
519\r
520 if self._LoadFixAddress == None:\r
521 self._LoadFixAddress = self._Macros.get(TAB_FIX_LOAD_TOP_MEMORY_ADDRESS, '0')\r
522\r
523 try:\r
524 self._LoadFixAddress = int (self._LoadFixAddress, 0)\r
525 except:\r
526 EdkLogger.error("build", PARAMETER_INVALID, "FIX_LOAD_TOP_MEMORY_ADDRESS %s is not valid dec or hex string" % (self._LoadFixAddress))\r
527\r
528 #\r
529 # If command line defined, should override the value in DSC file.\r
530 #\r
531 if 'FIX_LOAD_TOP_MEMORY_ADDRESS' in GlobalData.gCommandLineDefines.keys():\r
532 try:\r
533 self._LoadFixAddress = int(GlobalData.gCommandLineDefines['FIX_LOAD_TOP_MEMORY_ADDRESS'], 0)\r
534 except:\r
535 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']))\r
536\r
537 if self._LoadFixAddress < 0:\r
538 EdkLogger.error("build", PARAMETER_INVALID, "FIX_LOAD_TOP_MEMORY_ADDRESS is set to the invalid negative value 0x%x" % (self._LoadFixAddress))\r
539 if self._LoadFixAddress != 0xFFFFFFFFFFFFFFFF and self._LoadFixAddress % 0x1000 != 0:\r
540 EdkLogger.error("build", PARAMETER_INVALID, "FIX_LOAD_TOP_MEMORY_ADDRESS is set to the invalid unaligned 4K value 0x%x" % (self._LoadFixAddress))\r
541\r
542 return self._LoadFixAddress\r
543\r
544 ## Retrieve RFCLanguage filter\r
545 def _GetRFCLanguages(self):\r
546 if self._RFCLanguages == None:\r
547 if self._Header == None:\r
548 self._GetHeaderInfo()\r
549 if self._RFCLanguages == None:\r
550 self._RFCLanguages = []\r
551 return self._RFCLanguages\r
552\r
553 ## Retrieve ISOLanguage filter\r
554 def _GetISOLanguages(self):\r
555 if self._ISOLanguages == None:\r
556 if self._Header == None:\r
557 self._GetHeaderInfo()\r
558 if self._ISOLanguages == None:\r
559 self._ISOLanguages = []\r
560 return self._ISOLanguages\r
561 ## Retrieve the GUID string for VPD tool\r
562 def _GetVpdToolGuid(self):\r
563 if self._VpdToolGuid == None:\r
564 if self._Header == None:\r
565 self._GetHeaderInfo()\r
566 if self._VpdToolGuid == None:\r
567 self._VpdToolGuid = ''\r
568 return self._VpdToolGuid\r
569\r
570 ## Retrieve [SkuIds] section information\r
571 def _GetSkuIds(self):\r
572 if self._SkuIds == None:\r
573 self._SkuIds = sdict()\r
574 RecordList = self._RawData[MODEL_EFI_SKU_ID, self._Arch]\r
575 for Record in RecordList:\r
576 if Record[0] in [None, '']:\r
577 EdkLogger.error('build', FORMAT_INVALID, 'No Sku ID number',\r
578 File=self.MetaFile, Line=Record[-1])\r
579 if Record[1] in [None, '']:\r
580 EdkLogger.error('build', FORMAT_INVALID, 'No Sku ID name',\r
581 File=self.MetaFile, Line=Record[-1])\r
8518bf0b
LG
582 Pattern = re.compile('^[1-9]\d*|0$')\r
583 if Pattern.match(Record[0]) == None:\r
584 EdkLogger.error('build', FORMAT_INVALID, "The format of the Sku ID number is invalid. The correct format is '{(0-9)} {(1-9)(0-9)+}'",\r
585 File=self.MetaFile, Line=Record[-1])\r
586 if not IsValidWord(Record[1]):\r
587 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_-.)*'",\r
588 File=self.MetaFile, Line=Record[-1])\r
2b8a6c44 589 self._SkuIds[Record[1].upper()] = (Record[0], Record[1].upper(), Record[2].upper())\r
ae7b6df8 590 if 'DEFAULT' not in self._SkuIds:\r
8518bf0b 591 self._SkuIds['DEFAULT'] = ("0","DEFAULT","DEFAULT")\r
ae7b6df8 592 if 'COMMON' not in self._SkuIds:\r
8518bf0b 593 self._SkuIds['COMMON'] = ("0","DEFAULT","DEFAULT")\r
ae7b6df8 594 return self._SkuIds\r
8518bf0b
LG
595 def ToInt(self,intstr):\r
596 return int(intstr,16) if intstr.upper().startswith("0X") else int(intstr)\r
597 def _GetDefaultStores(self):\r
598 if self.DefaultStores == None:\r
599 self.DefaultStores = sdict()\r
600 RecordList = self._RawData[MODEL_EFI_DEFAULT_STORES, self._Arch]\r
601 for Record in RecordList:\r
602 if Record[0] in [None, '']:\r
603 EdkLogger.error('build', FORMAT_INVALID, 'No DefaultStores ID number',\r
604 File=self.MetaFile, Line=Record[-1])\r
605 if Record[1] in [None, '']:\r
606 EdkLogger.error('build', FORMAT_INVALID, 'No DefaultStores ID name',\r
607 File=self.MetaFile, Line=Record[-1])\r
2b8a6c44 608 self.DefaultStores[Record[1].upper()] = (self.ToInt(Record[0]),Record[1].upper())\r
8518bf0b
LG
609 if TAB_DEFAULT_STORES_DEFAULT not in self.DefaultStores:\r
610 self.DefaultStores[TAB_DEFAULT_STORES_DEFAULT] = (0,TAB_DEFAULT_STORES_DEFAULT)\r
e651d06c
LG
611 GlobalData.gDefaultStores = self.DefaultStores.keys()\r
612 if GlobalData.gDefaultStores:\r
613 GlobalData.gDefaultStores.sort()\r
8518bf0b 614 return self.DefaultStores\r
ae7b6df8
LG
615\r
616 ## Retrieve [Components] section information\r
617 def _GetModules(self):\r
618 if self._Modules != None:\r
619 return self._Modules\r
620\r
621 self._Modules = sdict()\r
622 RecordList = self._RawData[MODEL_META_DATA_COMPONENT, self._Arch]\r
623 Macros = self._Macros\r
624 Macros["EDK_SOURCE"] = GlobalData.gEcpSource\r
625 for Record in RecordList:\r
626 DuplicatedFile = False\r
627\r
628 ModuleFile = PathClass(NormPath(Record[0], Macros), GlobalData.gWorkspace, Arch=self._Arch)\r
8518bf0b
LG
629 ModuleId = Record[6]\r
630 LineNo = Record[7]\r
ae7b6df8
LG
631\r
632 # check the file validation\r
633 ErrorCode, ErrorInfo = ModuleFile.Validate('.inf')\r
634 if ErrorCode != 0:\r
635 EdkLogger.error('build', ErrorCode, File=self.MetaFile, Line=LineNo,\r
636 ExtraData=ErrorInfo)\r
637 # Check duplication\r
638 # If arch is COMMON, no duplicate module is checked since all modules in all component sections are selected\r
639 if self._Arch != 'COMMON' and ModuleFile in self._Modules:\r
640 DuplicatedFile = True\r
641\r
642 Module = ModuleBuildClassObject()\r
643 Module.MetaFile = ModuleFile\r
644\r
645 # get module private library instance\r
646 RecordList = self._RawData[MODEL_EFI_LIBRARY_CLASS, self._Arch, None, ModuleId]\r
647 for Record in RecordList:\r
648 LibraryClass = Record[0]\r
649 LibraryPath = PathClass(NormPath(Record[1], Macros), GlobalData.gWorkspace, Arch=self._Arch)\r
650 LineNo = Record[-1]\r
651\r
652 # check the file validation\r
653 ErrorCode, ErrorInfo = LibraryPath.Validate('.inf')\r
654 if ErrorCode != 0:\r
655 EdkLogger.error('build', ErrorCode, File=self.MetaFile, Line=LineNo,\r
656 ExtraData=ErrorInfo)\r
657\r
658 if LibraryClass == '' or LibraryClass == 'NULL':\r
659 self._NullLibraryNumber += 1\r
660 LibraryClass = 'NULL%d' % self._NullLibraryNumber\r
661 EdkLogger.verbose("Found forced library for %s\n\t%s [%s]" % (ModuleFile, LibraryPath, LibraryClass))\r
662 Module.LibraryClasses[LibraryClass] = LibraryPath\r
663 if LibraryPath not in self.LibraryInstances:\r
664 self.LibraryInstances.append(LibraryPath)\r
665\r
666 # get module private PCD setting\r
667 for Type in [MODEL_PCD_FIXED_AT_BUILD, MODEL_PCD_PATCHABLE_IN_MODULE, \\r
668 MODEL_PCD_FEATURE_FLAG, MODEL_PCD_DYNAMIC, MODEL_PCD_DYNAMIC_EX]:\r
669 RecordList = self._RawData[Type, self._Arch, None, ModuleId]\r
8518bf0b 670 for TokenSpaceGuid, PcdCName, Setting, Dummy1, Dummy2, Dummy3, Dummy4,Dummy5 in RecordList:\r
ae7b6df8
LG
671 TokenList = GetSplitValueList(Setting)\r
672 DefaultValue = TokenList[0]\r
673 if len(TokenList) > 1:\r
674 MaxDatumSize = TokenList[1]\r
675 else:\r
676 MaxDatumSize = ''\r
677 TypeString = self._PCD_TYPE_STRING_[Type]\r
678 Pcd = PcdClassObject(\r
679 PcdCName,\r
680 TokenSpaceGuid,\r
681 TypeString,\r
682 '',\r
683 DefaultValue,\r
684 '',\r
685 MaxDatumSize,\r
686 {},\r
687 False,\r
688 None\r
689 )\r
690 Module.Pcds[PcdCName, TokenSpaceGuid] = Pcd\r
691\r
692 # get module private build options\r
693 RecordList = self._RawData[MODEL_META_DATA_BUILD_OPTION, self._Arch, None, ModuleId]\r
8518bf0b 694 for ToolChainFamily, ToolChain, Option, Dummy1, Dummy2, Dummy3, Dummy4,Dummy5 in RecordList:\r
ae7b6df8
LG
695 if (ToolChainFamily, ToolChain) not in Module.BuildOptions:\r
696 Module.BuildOptions[ToolChainFamily, ToolChain] = Option\r
697 else:\r
698 OptionString = Module.BuildOptions[ToolChainFamily, ToolChain]\r
699 Module.BuildOptions[ToolChainFamily, ToolChain] = OptionString + " " + Option\r
700\r
701 RecordList = self._RawData[MODEL_META_DATA_HEADER, self._Arch, None, ModuleId]\r
702 if DuplicatedFile and not RecordList:\r
703 EdkLogger.error('build', FILE_DUPLICATED, File=self.MetaFile, ExtraData=str(ModuleFile), Line=LineNo)\r
704 if RecordList:\r
705 if len(RecordList) != 1:\r
706 EdkLogger.error('build', OPTION_UNKNOWN, 'Only FILE_GUID can be listed in <Defines> section.',\r
707 File=self.MetaFile, ExtraData=str(ModuleFile), Line=LineNo)\r
708 ModuleFile = ProcessDuplicatedInf(ModuleFile, RecordList[0][2], GlobalData.gWorkspace)\r
709 ModuleFile.Arch = self._Arch\r
710\r
711 self._Modules[ModuleFile] = Module\r
712 return self._Modules\r
713\r
714 ## Retrieve all possible library instances used in this platform\r
715 def _GetLibraryInstances(self):\r
716 if self._LibraryInstances == None:\r
717 self._GetLibraryClasses()\r
718 return self._LibraryInstances\r
719\r
720 ## Retrieve [LibraryClasses] information\r
721 def _GetLibraryClasses(self):\r
722 if self._LibraryClasses == None:\r
723 self._LibraryInstances = []\r
724 #\r
725 # tdict is a special dict kind of type, used for selecting correct\r
726 # library instance for given library class and module type\r
727 #\r
728 LibraryClassDict = tdict(True, 3)\r
729 # track all library class names\r
730 LibraryClassSet = set()\r
731 RecordList = self._RawData[MODEL_EFI_LIBRARY_CLASS, self._Arch, None, -1]\r
732 Macros = self._Macros\r
733 for Record in RecordList:\r
8518bf0b 734 LibraryClass, LibraryInstance, Dummy, Arch, ModuleType, Dummy,Dummy, LineNo = Record\r
ae7b6df8
LG
735 if LibraryClass == '' or LibraryClass == 'NULL':\r
736 self._NullLibraryNumber += 1\r
737 LibraryClass = 'NULL%d' % self._NullLibraryNumber\r
738 EdkLogger.verbose("Found forced library for arch=%s\n\t%s [%s]" % (Arch, LibraryInstance, LibraryClass))\r
739 LibraryClassSet.add(LibraryClass)\r
740 LibraryInstance = PathClass(NormPath(LibraryInstance, Macros), GlobalData.gWorkspace, Arch=self._Arch)\r
741 # check the file validation\r
742 ErrorCode, ErrorInfo = LibraryInstance.Validate('.inf')\r
743 if ErrorCode != 0:\r
744 EdkLogger.error('build', ErrorCode, File=self.MetaFile, Line=LineNo,\r
745 ExtraData=ErrorInfo)\r
746\r
747 if ModuleType != 'COMMON' and ModuleType not in SUP_MODULE_LIST:\r
748 EdkLogger.error('build', OPTION_UNKNOWN, "Unknown module type [%s]" % ModuleType,\r
749 File=self.MetaFile, ExtraData=LibraryInstance, Line=LineNo)\r
750 LibraryClassDict[Arch, ModuleType, LibraryClass] = LibraryInstance\r
751 if LibraryInstance not in self._LibraryInstances:\r
752 self._LibraryInstances.append(LibraryInstance)\r
753\r
754 # resolve the specific library instance for each class and each module type\r
755 self._LibraryClasses = tdict(True)\r
756 for LibraryClass in LibraryClassSet:\r
757 # try all possible module types\r
758 for ModuleType in SUP_MODULE_LIST:\r
759 LibraryInstance = LibraryClassDict[self._Arch, ModuleType, LibraryClass]\r
760 if LibraryInstance == None:\r
761 continue\r
762 self._LibraryClasses[LibraryClass, ModuleType] = LibraryInstance\r
763\r
764 # for Edk style library instances, which are listed in different section\r
765 Macros["EDK_SOURCE"] = GlobalData.gEcpSource\r
766 RecordList = self._RawData[MODEL_EFI_LIBRARY_INSTANCE, self._Arch]\r
767 for Record in RecordList:\r
768 File = PathClass(NormPath(Record[0], Macros), GlobalData.gWorkspace, Arch=self._Arch)\r
769 LineNo = Record[-1]\r
770 # check the file validation\r
771 ErrorCode, ErrorInfo = File.Validate('.inf')\r
772 if ErrorCode != 0:\r
773 EdkLogger.error('build', ErrorCode, File=self.MetaFile, Line=LineNo,\r
774 ExtraData=ErrorInfo)\r
775 if File not in self._LibraryInstances:\r
776 self._LibraryInstances.append(File)\r
777 #\r
778 # we need the module name as the library class name, so we have\r
779 # to parse it here. (self._Bdb[] will trigger a file parse if it\r
780 # hasn't been parsed)\r
781 #\r
782 Library = self._Bdb[File, self._Arch, self._Target, self._Toolchain]\r
783 self._LibraryClasses[Library.BaseName, ':dummy:'] = Library\r
784 return self._LibraryClasses\r
785\r
786 def _ValidatePcd(self, PcdCName, TokenSpaceGuid, Setting, PcdType, LineNo):\r
787 if self._DecPcds == None:\r
2b8a6c44 788\r
ae7b6df8
LG
789 FdfInfList = []\r
790 if GlobalData.gFdfParser:\r
791 FdfInfList = GlobalData.gFdfParser.Profile.InfList\r
792\r
793 PkgSet = set()\r
794 for Inf in FdfInfList:\r
795 ModuleFile = PathClass(NormPath(Inf), GlobalData.gWorkspace, Arch=self._Arch)\r
796 if ModuleFile in self._Modules:\r
797 continue\r
798 ModuleData = self._Bdb[ModuleFile, self._Arch, self._Target, self._Toolchain]\r
799 PkgSet.update(ModuleData.Packages)\r
ae7b6df8 800\r
2b8a6c44
LG
801 self._DecPcds = GetDeclaredPcd(self, self._Bdb, self._Arch, self._Target, self._Toolchain,PkgSet)\r
802\r
803\r
804 if (PcdCName, TokenSpaceGuid) not in self._DecPcds:\r
ae7b6df8
LG
805 EdkLogger.error('build', PARSER_ERROR,\r
806 "Pcd (%s.%s) defined in DSC is not declared in DEC files. Arch: ['%s']" % (TokenSpaceGuid, PcdCName, self._Arch),\r
807 File=self.MetaFile, Line=LineNo)\r
808 ValueList, IsValid, Index = AnalyzeDscPcd(Setting, PcdType, self._DecPcds[PcdCName, TokenSpaceGuid].DatumType)\r
809 if not IsValid and PcdType not in [MODEL_PCD_FEATURE_FLAG, MODEL_PCD_FIXED_AT_BUILD]:\r
810 EdkLogger.error('build', FORMAT_INVALID, "Pcd format incorrect.", File=self.MetaFile, Line=LineNo,\r
811 ExtraData="%s.%s|%s" % (TokenSpaceGuid, PcdCName, Setting))\r
812 if ValueList[Index] and PcdType not in [MODEL_PCD_FEATURE_FLAG, MODEL_PCD_FIXED_AT_BUILD]:\r
813 try:\r
814 ValueList[Index] = ValueExpression(ValueList[Index], GlobalData.gPlatformPcds)(True)\r
815 except WrnExpression, Value:\r
816 ValueList[Index] = Value.result\r
817 except EvaluationException, Excpt:\r
818 if hasattr(Excpt, 'Pcd'):\r
819 if Excpt.Pcd in GlobalData.gPlatformOtherPcds:\r
820 EdkLogger.error('Parser', FORMAT_INVALID, "Cannot use this PCD (%s) in an expression as"\r
821 " it must be defined in a [PcdsFixedAtBuild] or [PcdsFeatureFlag] section"\r
822 " of the DSC file" % Excpt.Pcd,\r
823 File=self.MetaFile, Line=LineNo)\r
824 else:\r
825 EdkLogger.error('Parser', FORMAT_INVALID, "PCD (%s) is not defined in DSC file" % Excpt.Pcd,\r
826 File=self.MetaFile, Line=LineNo)\r
827 else:\r
828 EdkLogger.error('Parser', FORMAT_INVALID, "Invalid expression: %s" % str(Excpt),\r
829 File=self.MetaFile, Line=LineNo)\r
830 if ValueList[Index] == 'True':\r
831 ValueList[Index] = '1'\r
832 elif ValueList[Index] == 'False':\r
833 ValueList[Index] = '0'\r
834 if ValueList[Index]:\r
835 Valid, ErrStr = CheckPcdDatum(self._DecPcds[PcdCName, TokenSpaceGuid].DatumType, ValueList[Index])\r
836 if not Valid:\r
837 EdkLogger.error('build', FORMAT_INVALID, ErrStr, File=self.MetaFile, Line=LineNo,\r
838 ExtraData="%s.%s" % (TokenSpaceGuid, PcdCName))\r
839 return ValueList\r
840\r
8518bf0b
LG
841 def _FilterPcdBySkuUsage(self,Pcds):\r
842 available_sku = self.SkuIdMgr.AvailableSkuIdSet\r
843 sku_usage = self.SkuIdMgr.SkuUsageType\r
844 if sku_usage == SkuClass.SINGLE:\r
845 for pcdname in Pcds:\r
846 pcd = Pcds[pcdname]\r
847 Pcds[pcdname].SkuInfoList = {"DEFAULT":pcd.SkuInfoList[skuid] for skuid in pcd.SkuInfoList if skuid in available_sku}\r
65eff519
LG
848 if type(pcd) is StructurePcd and pcd.SkuOverrideValues:\r
849 Pcds[pcdname].SkuOverrideValues = {"DEFAULT":pcd.SkuOverrideValues[skuid] for skuid in pcd.SkuOverrideValues if skuid in available_sku}\r
8518bf0b
LG
850 else:\r
851 for pcdname in Pcds:\r
852 pcd = Pcds[pcdname]\r
853 Pcds[pcdname].SkuInfoList = {skuid:pcd.SkuInfoList[skuid] for skuid in pcd.SkuInfoList if skuid in available_sku}\r
65eff519
LG
854 if type(pcd) is StructurePcd and pcd.SkuOverrideValues:\r
855 Pcds[pcdname].SkuOverrideValues = {skuid:pcd.SkuOverrideValues[skuid] for skuid in pcd.SkuOverrideValues if skuid in available_sku}\r
8518bf0b 856 return Pcds\r
2b8a6c44
LG
857 def CompleteHiiPcdsDefaultStores(self,Pcds):\r
858 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]]]\r
859 DefaultStoreMgr = DefaultStore(self.DefaultStores)\r
860 for pcd in HiiPcd:\r
861 for skuid in pcd.SkuInfoList:\r
862 skuobj = pcd.SkuInfoList.get(skuid)\r
863 if "STANDARD" not in skuobj.DefaultStoreDict:\r
864 PcdDefaultStoreSet = set([defaultstorename for defaultstorename in skuobj.DefaultStoreDict])\r
865 mindefaultstorename = DefaultStoreMgr.GetMin(PcdDefaultStoreSet)\r
866 skuobj.DefaultStoreDict['STANDARD'] = copy.deepcopy(skuobj.DefaultStoreDict[mindefaultstorename])\r
867 return Pcds\r
868\r
ae7b6df8
LG
869 ## Retrieve all PCD settings in platform\r
870 def _GetPcds(self):\r
871 if self._Pcds == None:\r
872 self._Pcds = sdict()\r
873 self._Pcds.update(self._GetPcd(MODEL_PCD_FIXED_AT_BUILD))\r
874 self._Pcds.update(self._GetPcd(MODEL_PCD_PATCHABLE_IN_MODULE))\r
875 self._Pcds.update(self._GetPcd(MODEL_PCD_FEATURE_FLAG))\r
876 self._Pcds.update(self._GetDynamicPcd(MODEL_PCD_DYNAMIC_DEFAULT))\r
877 self._Pcds.update(self._GetDynamicHiiPcd(MODEL_PCD_DYNAMIC_HII))\r
878 self._Pcds.update(self._GetDynamicVpdPcd(MODEL_PCD_DYNAMIC_VPD))\r
879 self._Pcds.update(self._GetDynamicPcd(MODEL_PCD_DYNAMIC_EX_DEFAULT))\r
880 self._Pcds.update(self._GetDynamicHiiPcd(MODEL_PCD_DYNAMIC_EX_HII))\r
881 self._Pcds.update(self._GetDynamicVpdPcd(MODEL_PCD_DYNAMIC_EX_VPD))\r
882\r
8518bf0b 883 self._Pcds = self.CompletePcdValues(self._Pcds)\r
ae7b6df8 884 self._Pcds = self.UpdateStructuredPcds(MODEL_PCD_TYPE_LIST, self._Pcds)\r
2b8a6c44 885 self._Pcds = self.CompleteHiiPcdsDefaultStores(self._Pcds)\r
8518bf0b 886 self._Pcds = self._FilterPcdBySkuUsage(self._Pcds)\r
ae7b6df8
LG
887 return self._Pcds\r
888\r
8518bf0b
LG
889 def _dumpPcdInfo(self,Pcds):\r
890 for pcd in Pcds:\r
891 pcdobj = Pcds[pcd]\r
892 if not pcdobj.TokenCName.startswith("Test"):\r
893 continue\r
894 for skuid in pcdobj.SkuInfoList:\r
895 if pcdobj.Type in (self._PCD_TYPE_STRING_[MODEL_PCD_DYNAMIC_HII],self._PCD_TYPE_STRING_[MODEL_PCD_DYNAMIC_EX_HII]):\r
896 for storename in pcdobj.SkuInfoList[skuid].DefaultStoreDict:\r
897 print "PcdCName: %s, SkuName: %s, StoreName: %s, Value: %s" % (".".join((pcdobj.TokenSpaceGuidCName, pcdobj.TokenCName)), skuid,storename,str(pcdobj.SkuInfoList[skuid].DefaultStoreDict[storename]))\r
898 else:\r
899 print "PcdCName: %s, SkuName: %s, Value: %s" % (".".join((pcdobj.TokenSpaceGuidCName, pcdobj.TokenCName)), skuid,str(pcdobj.SkuInfoList[skuid].DefaultValue))\r
ae7b6df8
LG
900 ## Retrieve [BuildOptions]\r
901 def _GetBuildOptions(self):\r
902 if self._BuildOptions == None:\r
903 self._BuildOptions = sdict()\r
904 #\r
905 # Retrieve build option for EDKII and EDK style module\r
906 #\r
907 for CodeBase in (EDKII_NAME, EDK_NAME):\r
908 RecordList = self._RawData[MODEL_META_DATA_BUILD_OPTION, self._Arch, CodeBase]\r
8518bf0b 909 for ToolChainFamily, ToolChain, Option, Dummy1, Dummy2, Dummy3, Dummy4,Dummy5 in RecordList:\r
ae7b6df8
LG
910 CurKey = (ToolChainFamily, ToolChain, CodeBase)\r
911 #\r
912 # Only flags can be appended\r
913 #\r
914 if CurKey not in self._BuildOptions or not ToolChain.endswith('_FLAGS') or Option.startswith('='):\r
915 self._BuildOptions[CurKey] = Option\r
916 else:\r
917 self._BuildOptions[CurKey] += ' ' + Option\r
918 return self._BuildOptions\r
919\r
920 def GetBuildOptionsByModuleType(self, Edk, ModuleType):\r
921 if self._ModuleTypeOptions == None:\r
922 self._ModuleTypeOptions = sdict()\r
923 if (Edk, ModuleType) not in self._ModuleTypeOptions:\r
924 options = sdict()\r
925 self._ModuleTypeOptions[Edk, ModuleType] = options\r
926 DriverType = '%s.%s' % (Edk, ModuleType)\r
927 CommonDriverType = '%s.%s' % ('COMMON', ModuleType)\r
928 RecordList = self._RawData[MODEL_META_DATA_BUILD_OPTION, self._Arch, DriverType]\r
8518bf0b 929 for ToolChainFamily, ToolChain, Option, Arch, Type, Dummy3, Dummy4,Dummy5 in RecordList:\r
ae7b6df8
LG
930 if Type == DriverType or Type == CommonDriverType:\r
931 Key = (ToolChainFamily, ToolChain, Edk)\r
932 if Key not in options or not ToolChain.endswith('_FLAGS') or Option.startswith('='):\r
933 options[Key] = Option\r
934 else:\r
935 options[Key] += ' ' + Option\r
936 return self._ModuleTypeOptions[Edk, ModuleType]\r
937\r
938 def GetStructurePcdInfo(self, PcdSet):\r
939 structure_pcd_data = {}\r
940 for item in PcdSet:\r
8518bf0b
LG
941 if (item[0],item[1]) not in structure_pcd_data:\r
942 structure_pcd_data[(item[0],item[1])] = []\r
943 structure_pcd_data[(item[0],item[1])].append(item)\r
ae7b6df8
LG
944\r
945 return structure_pcd_data\r
946\r
947 def UpdateStructuredPcds(self, TypeList, AllPcds):\r
65eff519
LG
948\r
949 DynamicPcdType = [self._PCD_TYPE_STRING_[MODEL_PCD_DYNAMIC_DEFAULT],\r
950 self._PCD_TYPE_STRING_[MODEL_PCD_DYNAMIC_HII],\r
951 self._PCD_TYPE_STRING_[MODEL_PCD_DYNAMIC_VPD],\r
952 self._PCD_TYPE_STRING_[MODEL_PCD_DYNAMIC_EX_DEFAULT],\r
953 self._PCD_TYPE_STRING_[MODEL_PCD_DYNAMIC_EX_HII],\r
954 self._PCD_TYPE_STRING_[MODEL_PCD_DYNAMIC_EX_VPD]]\r
955\r
ae7b6df8 956 Pcds = AllPcds\r
8518bf0b 957 DefaultStoreMgr = DefaultStore(self.DefaultStores)\r
65eff519
LG
958 SkuIds = self.SkuIdMgr.AvailableSkuIdSet\r
959 SkuIds.update({'DEFAULT':0})\r
8518bf0b 960 DefaultStores = set([storename for pcdobj in AllPcds.values() for skuobj in pcdobj.SkuInfoList.values() for storename in skuobj.DefaultStoreDict.keys()])\r
ae7b6df8
LG
961\r
962 S_PcdSet = []\r
963 # Find out all possible PCD candidates for self._Arch\r
964 RecordList = []\r
2b8a6c44 965\r
ae7b6df8
LG
966 for Type in TypeList:\r
967 RecordList.extend(self._RawData[Type, self._Arch])\r
968\r
8518bf0b 969 for TokenSpaceGuid, PcdCName, Setting, Arch, SkuName, default_store, Dummy4,Dummy5 in RecordList:\r
2b8a6c44
LG
970 SkuName = SkuName.upper()\r
971 default_store = default_store.upper()\r
972 SkuName = 'DEFAULT' if SkuName == 'COMMON' else SkuName\r
8518bf0b
LG
973 if SkuName not in SkuIds:\r
974 continue\r
2b8a6c44 975\r
8518bf0b
LG
976 if SkuName in SkuIds and "." in TokenSpaceGuid:\r
977 S_PcdSet.append(( TokenSpaceGuid.split(".")[0],TokenSpaceGuid.split(".")[1], PcdCName,SkuName, default_store,Dummy5, AnalyzePcdExpression(Setting)[0]))\r
ae7b6df8
LG
978\r
979 # handle pcd value override\r
980 StrPcdSet = self.GetStructurePcdInfo(S_PcdSet)\r
981 S_pcd_set = {}\r
982 for str_pcd in StrPcdSet:\r
8518bf0b
LG
983 str_pcd_obj = Pcds.get((str_pcd[1], str_pcd[0]), None)\r
984 str_pcd_dec = self._DecPcds.get((str_pcd[1], str_pcd[0]), None)\r
ae7b6df8
LG
985 if str_pcd_dec:\r
986 str_pcd_obj_str = StructurePcd()\r
987 str_pcd_obj_str.copy(str_pcd_dec)\r
988 if str_pcd_obj:\r
989 str_pcd_obj_str.copy(str_pcd_obj)\r
990 if str_pcd_obj.DefaultValue:\r
991 str_pcd_obj_str.DefaultFromDSC = str_pcd_obj.DefaultValue\r
992 for str_pcd_data in StrPcdSet[str_pcd]:\r
8518bf0b
LG
993 if str_pcd_data[3] in SkuIds:\r
994 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,LineNo=str_pcd_data[5])\r
995 S_pcd_set[str_pcd[1], str_pcd[0]] = str_pcd_obj_str\r
2b8a6c44
LG
996 else:\r
997 EdkLogger.error('build', PARSER_ERROR,\r
998 "Pcd (%s.%s) defined in DSC is not declared in DEC files. Arch: ['%s']" % (str_pcd[0], str_pcd[1], self._Arch),\r
999 File=self.MetaFile,Line = StrPcdSet[str_pcd][0][5])\r
ae7b6df8
LG
1000 # Add the Structure PCD that only defined in DEC, don't have override in DSC file\r
1001 for Pcd in self._DecPcds:\r
1002 if type (self._DecPcds[Pcd]) is StructurePcd:\r
1003 if Pcd not in S_pcd_set:\r
1004 str_pcd_obj_str = StructurePcd()\r
1005 str_pcd_obj_str.copy(self._DecPcds[Pcd])\r
1006 str_pcd_obj = Pcds.get(Pcd, None)\r
1007 if str_pcd_obj:\r
1008 str_pcd_obj_str.copy(str_pcd_obj)\r
1009 if str_pcd_obj.DefaultValue:\r
1010 str_pcd_obj_str.DefaultFromDSC = str_pcd_obj.DefaultValue\r
1011 S_pcd_set[Pcd] = str_pcd_obj_str\r
1012 if S_pcd_set:\r
1013 GlobalData.gStructurePcd[self.Arch] = S_pcd_set\r
8518bf0b 1014 for stru_pcd in S_pcd_set.values():\r
65eff519 1015 if stru_pcd.Type not in DynamicPcdType:\r
8518bf0b 1016 continue\r
67e63e9a
LG
1017 for skuid in SkuIds:\r
1018 if skuid in stru_pcd.SkuOverrideValues:\r
1019 continue\r
1020 nextskuid = self.SkuIdMgr.GetNextSkuId(skuid)\r
1021 NoDefault = False\r
1022 while nextskuid not in stru_pcd.SkuOverrideValues:\r
1023 if nextskuid == "DEFAULT":\r
1024 NoDefault = True\r
1025 break\r
1026 nextskuid = self.SkuIdMgr.GetNextSkuId(nextskuid)\r
1027 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})\r
8518bf0b
LG
1028 if stru_pcd.Type in [self._PCD_TYPE_STRING_[MODEL_PCD_DYNAMIC_HII], self._PCD_TYPE_STRING_[MODEL_PCD_DYNAMIC_EX_HII]]:\r
1029 for skuid in SkuIds:\r
1030 nextskuid = skuid\r
2b8a6c44 1031 NoDefault = False\r
8518bf0b
LG
1032 if skuid not in stru_pcd.SkuOverrideValues:\r
1033 while nextskuid not in stru_pcd.SkuOverrideValues:\r
2b8a6c44
LG
1034 if nextskuid == "DEFAULT":\r
1035 NoDefault = True\r
1036 break\r
8518bf0b 1037 nextskuid = self.SkuIdMgr.GetNextSkuId(nextskuid)\r
2b8a6c44
LG
1038 if NoDefault:\r
1039 continue\r
1040 PcdDefaultStoreSet = set([defaultstorename for defaultstorename in stru_pcd.SkuOverrideValues[nextskuid]])\r
8518bf0b 1041 mindefaultstorename = DefaultStoreMgr.GetMin(PcdDefaultStoreSet)\r
2b8a6c44 1042\r
8518bf0b
LG
1043 for defaultstoreid in DefaultStores:\r
1044 if defaultstoreid not in stru_pcd.SkuOverrideValues[skuid]:\r
2b8a6c44 1045 stru_pcd.SkuOverrideValues[skuid][defaultstoreid] = copy.deepcopy(stru_pcd.SkuOverrideValues[nextskuid][mindefaultstorename])\r
65eff519 1046\r
ae7b6df8
LG
1047 Str_Pcd_Values = self.GenerateByteArrayValue(S_pcd_set)\r
1048 if Str_Pcd_Values:\r
8518bf0b
LG
1049 for (skuname,StoreName,PcdGuid,PcdName,PcdValue) in Str_Pcd_Values:\r
1050 str_pcd_obj = S_pcd_set.get((PcdName, PcdGuid))\r
ae7b6df8 1051 if str_pcd_obj is None:\r
67e63e9a 1052 print PcdName, PcdGuid\r
ae7b6df8
LG
1053 raise\r
1054 if str_pcd_obj.Type in [self._PCD_TYPE_STRING_[MODEL_PCD_DYNAMIC_HII],\r
1055 self._PCD_TYPE_STRING_[MODEL_PCD_DYNAMIC_EX_HII]]:\r
8518bf0b
LG
1056 if skuname not in str_pcd_obj.SkuInfoList:\r
1057 str_pcd_obj.SkuInfoList[skuname] = SkuInfoClass(SkuIdName=skuname, SkuId=self.SkuIds[skuname][0], HiiDefaultValue=PcdValue, DefaultStore = {StoreName:PcdValue})\r
ae7b6df8 1058 else:\r
8518bf0b
LG
1059 str_pcd_obj.SkuInfoList[skuname].HiiDefaultValue = PcdValue\r
1060 str_pcd_obj.SkuInfoList[skuname].DefaultStoreDict.update({StoreName:PcdValue})\r
ae7b6df8
LG
1061 elif str_pcd_obj.Type in [self._PCD_TYPE_STRING_[MODEL_PCD_FIXED_AT_BUILD],\r
1062 self._PCD_TYPE_STRING_[MODEL_PCD_PATCHABLE_IN_MODULE]]:\r
8518bf0b
LG
1063 if skuname in (self.SkuIdMgr.SystemSkuId, 'DEFAULT', 'COMMON'):\r
1064 str_pcd_obj.DefaultValue = PcdValue\r
ae7b6df8 1065 else:\r
8518bf0b 1066 if skuname not in str_pcd_obj.SkuInfoList:\r
65eff519
LG
1067 nextskuid = self.SkuIdMgr.GetNextSkuId(skuname)\r
1068 NoDefault = False\r
1069 while nextskuid not in str_pcd_obj.SkuInfoList:\r
1070 if nextskuid == "DEFAULT":\r
1071 NoDefault = True\r
1072 break\r
1073 nextskuid = self.SkuIdMgr.GetNextSkuId(nextskuid)\r
1074 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)\r
1075 str_pcd_obj.SkuInfoList[skuname].SkuId = self.SkuIds[skuname][0]\r
1076 str_pcd_obj.SkuInfoList[skuname].SkuIdName = skuname\r
ae7b6df8 1077 else:\r
8518bf0b
LG
1078 str_pcd_obj.SkuInfoList[skuname].DefaultValue = PcdValue\r
1079 for str_pcd_obj in S_pcd_set.values():\r
1080 if str_pcd_obj.Type not in [self._PCD_TYPE_STRING_[MODEL_PCD_DYNAMIC_HII],\r
1081 self._PCD_TYPE_STRING_[MODEL_PCD_DYNAMIC_EX_HII]]:\r
1082 continue\r
1083 PcdDefaultStoreSet = set([defaultstorename for skuobj in str_pcd_obj.SkuInfoList.values() for defaultstorename in skuobj.DefaultStoreDict])\r
1084 DefaultStoreObj = DefaultStore(self._GetDefaultStores())\r
1085 mindefaultstorename = DefaultStoreObj.GetMin(PcdDefaultStoreSet)\r
1086 str_pcd_obj.SkuInfoList[self.SkuIdMgr.SystemSkuId].HiiDefaultValue = str_pcd_obj.SkuInfoList[self.SkuIdMgr.SystemSkuId].DefaultStoreDict[mindefaultstorename]\r
ae7b6df8
LG
1087\r
1088 for str_pcd_obj in S_pcd_set.values():\r
2b8a6c44 1089\r
ae7b6df8
LG
1090 str_pcd_obj.MaxDatumSize = self.GetStructurePcdMaxSize(str_pcd_obj)\r
1091 Pcds[str_pcd_obj.TokenCName, str_pcd_obj.TokenSpaceGuidCName] = str_pcd_obj\r
1092\r
65eff519
LG
1093 for pcdkey in Pcds:\r
1094 pcd = Pcds[pcdkey]\r
1095 if 'DEFAULT' not in pcd.SkuInfoList.keys() and 'COMMON' in pcd.SkuInfoList.keys():\r
1096 pcd.SkuInfoList['DEFAULT'] = pcd.SkuInfoList['COMMON']\r
1097 del(pcd.SkuInfoList['COMMON'])\r
1098 elif 'DEFAULT' in pcd.SkuInfoList.keys() and 'COMMON' in pcd.SkuInfoList.keys():\r
1099 del(pcd.SkuInfoList['COMMON'])\r
1100\r
1101 map(self.FilterSkuSettings,[Pcds[pcdkey] for pcdkey in Pcds if Pcds[pcdkey].Type in DynamicPcdType])\r
ae7b6df8
LG
1102 return Pcds\r
1103\r
1104 ## Retrieve non-dynamic PCD settings\r
1105 #\r
1106 # @param Type PCD type\r
1107 #\r
1108 # @retval a dict object contains settings of given PCD type\r
1109 #\r
1110 def _GetPcd(self, Type):\r
1111 Pcds = sdict()\r
1112 #\r
1113 # tdict is a special dict kind of type, used for selecting correct\r
1114 # PCD settings for certain ARCH\r
1115 #\r
2b8a6c44 1116 AvailableSkuIdSet = copy.copy(self.SkuIds)\r
ae7b6df8
LG
1117\r
1118 PcdDict = tdict(True, 3)\r
1119 PcdSet = set()\r
1120 # Find out all possible PCD candidates for self._Arch\r
1121 RecordList = self._RawData[Type, self._Arch]\r
ae7b6df8 1122 PcdValueDict = sdict()\r
8518bf0b 1123 for TokenSpaceGuid, PcdCName, Setting, Arch, SkuName, Dummy3, Dummy4,Dummy5 in RecordList:\r
2b8a6c44
LG
1124 SkuName = SkuName.upper()\r
1125 SkuName = 'DEFAULT' if SkuName == 'COMMON' else SkuName\r
1126 if SkuName not in AvailableSkuIdSet:\r
1127 EdkLogger.error('build ', PARAMETER_INVALID, 'Sku %s is not defined in [SkuIds] section' % SkuName,\r
1128 File=self.MetaFile, Line=Dummy5)\r
8518bf0b
LG
1129 if SkuName in (self.SkuIdMgr.SystemSkuId, 'DEFAULT', 'COMMON'):\r
1130 if "." not in TokenSpaceGuid:\r
1131 PcdSet.add((PcdCName, TokenSpaceGuid, SkuName, Dummy4))\r
ae7b6df8 1132 PcdDict[Arch, PcdCName, TokenSpaceGuid, SkuName] = Setting\r
ae7b6df8
LG
1133\r
1134 for PcdCName, TokenSpaceGuid, SkuName, Dummy4 in PcdSet:\r
1135 Setting = PcdDict[self._Arch, PcdCName, TokenSpaceGuid, SkuName]\r
1136 if Setting == None:\r
1137 continue\r
1138 PcdValue, DatumType, MaxDatumSize = self._ValidatePcd(PcdCName, TokenSpaceGuid, Setting, Type, Dummy4)\r
1139 if (PcdCName, TokenSpaceGuid) in PcdValueDict:\r
1140 PcdValueDict[PcdCName, TokenSpaceGuid][SkuName] = (PcdValue, DatumType, MaxDatumSize)\r
1141 else:\r
1142 PcdValueDict[PcdCName, TokenSpaceGuid] = {SkuName:(PcdValue, DatumType, MaxDatumSize)}\r
1143\r
1144 PcdsKeys = PcdValueDict.keys()\r
1145 for PcdCName, TokenSpaceGuid in PcdsKeys:\r
1146\r
1147 PcdSetting = PcdValueDict[PcdCName, TokenSpaceGuid]\r
1148 PcdValue = None\r
1149 DatumType = None\r
1150 MaxDatumSize = None\r
1151 if 'COMMON' in PcdSetting:\r
1152 PcdValue, DatumType, MaxDatumSize = PcdSetting['COMMON']\r
1153 if 'DEFAULT' in PcdSetting:\r
1154 PcdValue, DatumType, MaxDatumSize = PcdSetting['DEFAULT']\r
8518bf0b
LG
1155 if self.SkuIdMgr.SystemSkuId in PcdSetting:\r
1156 PcdValue, DatumType, MaxDatumSize = PcdSetting[self.SkuIdMgr.SystemSkuId]\r
ae7b6df8
LG
1157\r
1158 Pcds[PcdCName, TokenSpaceGuid] = PcdClassObject(\r
1159 PcdCName,\r
1160 TokenSpaceGuid,\r
1161 self._PCD_TYPE_STRING_[Type],\r
1162 DatumType,\r
1163 PcdValue,\r
1164 '',\r
1165 MaxDatumSize,\r
1166 {},\r
1167 False,\r
1168 None,\r
1169 IsDsc=True)\r
1170\r
1171\r
1172 return Pcds\r
1173\r
8518bf0b
LG
1174 def __UNICODE2OCTList(self,Value):\r
1175 Value = Value.strip()\r
1176 Value = Value[2:-1]\r
1177 List = []\r
1178 for Item in Value:\r
1179 Temp = '%04X' % ord(Item)\r
1180 List.append('0x' + Temp[2:4])\r
1181 List.append('0x' + Temp[0:2])\r
1182 List.append('0x00')\r
1183 List.append('0x00')\r
1184 return List\r
1185 def __STRING2OCTList(self,Value):\r
1186 OCTList = []\r
1187 Value = Value.strip('"')\r
1188 for char in Value:\r
1189 Temp = '%02X' % ord(char)\r
1190 OCTList.append('0x' + Temp)\r
1191 OCTList.append('0x00')\r
1192 return OCTList\r
1193\r
ae7b6df8
LG
1194 def GetStructurePcdMaxSize(self, str_pcd):\r
1195 pcd_default_value = str_pcd.DefaultValue\r
1196 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()]\r
1197 sku_values.append(pcd_default_value)\r
1198\r
1199 def get_length(value):\r
1200 Value = value.strip()\r
1201 if Value.startswith('GUID') and Value.endswith(')'):\r
1202 return 16\r
1203 if Value.startswith('L"') and Value.endswith('"'):\r
1204 return len(Value[2:-1])\r
1205 if Value[0] == '"' and Value[-1] == '"':\r
1206 return len(Value) - 2\r
1207 if Value[0] == '{' and Value[-1] == '}':\r
1208 return len(Value.split(","))\r
1209 if Value.startswith("L'") and Value.endswith("'") and len(list(Value[2:-1])) > 1:\r
1210 return len(list(Value[2:-1]))\r
1211 if Value[0] == "'" and Value[-1] == "'" and len(list(Value[1:-1])) > 1:\r
1212 return len(Value) - 2\r
1213 return len(Value)\r
1214\r
1215 return str(max([pcd_size for pcd_size in [get_length(item) for item in sku_values]]))\r
1216\r
1217 def IsFieldValueAnArray (self, Value):\r
1218 Value = Value.strip()\r
1219 if Value.startswith('GUID') and Value.endswith(')'):\r
1220 return True\r
1221 if Value.startswith('L"') and Value.endswith('"') and len(list(Value[2:-1])) > 1:\r
1222 return True\r
1223 if Value[0] == '"' and Value[-1] == '"' and len(list(Value[1:-1])) > 1:\r
1224 return True\r
1225 if Value[0] == '{' and Value[-1] == '}':\r
1226 return True\r
1227 if Value.startswith("L'") and Value.endswith("'") and len(list(Value[2:-1])) > 1:\r
1228 print 'foo = ', list(Value[2:-1])\r
1229 return True\r
1230 if Value[0] == "'" and Value[-1] == "'" and len(list(Value[1:-1])) > 1:\r
1231 print 'bar = ', list(Value[1:-1])\r
1232 return True\r
1233 return False\r
1234\r
1235 def ExecuteCommand (self, Command):\r
1236 try:\r
1237 Process = subprocess.Popen(Command, stdout=subprocess.PIPE, stderr=subprocess.PIPE, shell=True)\r
1238 except:\r
1239 print 'ERROR: Can not execute command:', Command\r
1240 sys.exit(1)\r
1241 Result = Process.communicate()\r
1242 if Process.returncode <> 0:\r
1243 print 'ERROR: Can not collect output from command:', Command\r
1244 return Result[0], Result[1]\r
1245\r
1246 def IntToCString(self, Value, ValueSize):\r
1247 Result = '"'\r
1248 if not isinstance (Value, str):\r
1249 for Index in range(0, ValueSize):\r
1250 Result = Result + '\\x%02x' % (Value & 0xff)\r
1251 Value = Value >> 8\r
1252 Result = Result + '"'\r
1253 return Result\r
1254\r
1255 def GenerateInitializeFunc(self, SkuName, DefaultStoreName, Pcd, InitByteValue, CApp):\r
8518bf0b 1256 OverrideValues = {DefaultStoreName:""}\r
ae7b6df8
LG
1257 if Pcd.SkuOverrideValues:\r
1258 OverrideValues = Pcd.SkuOverrideValues[SkuName]\r
8518bf0b
LG
1259 for DefaultStoreName in OverrideValues.keys():\r
1260 CApp = CApp + 'void\n'\r
1261 CApp = CApp + 'Initialize_%s_%s_%s_%s(\n' % (SkuName, DefaultStoreName, Pcd.TokenSpaceGuidCName, Pcd.TokenCName)\r
1262 CApp = CApp + ' void\n'\r
1263 CApp = CApp + ' )\n'\r
1264 CApp = CApp + '{\n'\r
1265 CApp = CApp + ' UINT32 Size;\n'\r
1266 CApp = CApp + ' UINT32 FieldSize;\n'\r
b2395724 1267 CApp = CApp + ' CHAR8 *Value;\n'\r
8518bf0b
LG
1268 CApp = CApp + ' UINT32 OriginalSize;\n'\r
1269 CApp = CApp + ' VOID *OriginalPcd;\n'\r
1270 CApp = CApp + ' %s *Pcd;\n' % (Pcd.DatumType)\r
1271 CApp = CApp + '\n'\r
47854fd5 1272\r
8518bf0b 1273 Pcd.DefaultValue = Pcd.DefaultValue.strip()\r
47854fd5
LG
1274 PcdDefaultValue = StringToArray(Pcd.DefaultValue)\r
1275\r
8518bf0b 1276 InitByteValue += '%s.%s.%s.%s|%s|%s\n' % (SkuName, DefaultStoreName, Pcd.TokenSpaceGuidCName, Pcd.TokenCName, Pcd.DatumType, PcdDefaultValue)\r
ae7b6df8 1277\r
8518bf0b
LG
1278 #\r
1279 # Get current PCD value and size\r
1280 #\r
1281 CApp = CApp + ' OriginalPcd = PcdGetPtr (%s, %s, %s, %s, &OriginalSize);\n' % (SkuName, DefaultStoreName, Pcd.TokenSpaceGuidCName, Pcd.TokenCName)\r
ae7b6df8 1282\r
8518bf0b
LG
1283 #\r
1284 # Determine the size of the PCD. For simple structures, sizeof(TYPE) provides\r
1285 # the correct value. For structures with a flexible array member, the flexible\r
1286 # array member is detected, and the size is based on the highest index used with\r
1287 # the flexible array member. The flexible array member must be the last field\r
1288 # in a structure. The size formula for this case is:\r
1289 # OFFSET_OF(FlexbleArrayField) + sizeof(FlexibleArray[0]) * (HighestIndex + 1)\r
1290 #\r
1291 CApp = CApp + ' Size = sizeof(%s);\n' % (Pcd.DatumType)\r
1292 for FieldList in [Pcd.DefaultValues, OverrideValues.get(DefaultStoreName)]:\r
1293 if not FieldList:\r
1294 continue\r
1295 for FieldName in FieldList:\r
1296 FieldName = "." + FieldName\r
1297 IsArray = self.IsFieldValueAnArray(FieldList[FieldName.strip(".")][0])\r
1298 if IsArray:\r
1299 Value, ValueSize = ParseFieldValue (FieldList[FieldName.strip(".")][0])\r
1300 CApp = CApp + ' __FLEXIBLE_SIZE(Size, %s, %s, %d / __ARRAY_ELEMENT_SIZE(%s, %s));\n' % (Pcd.DatumType, FieldName.strip("."), ValueSize, Pcd.DatumType, FieldName.strip("."));\r
1301 else:\r
1302 NewFieldName = ''\r
1303 while '[' in FieldName:\r
1304 NewFieldName = NewFieldName + FieldName.split('[', 1)[0] + '[0]'\r
1305 ArrayIndex = int(FieldName.split('[', 1)[1].split(']', 1)[0])\r
1306 FieldName = FieldName.split(']', 1)[1]\r
1307 FieldName = NewFieldName + FieldName\r
1308 while '[' in FieldName:\r
1309 FieldName = FieldName.rsplit('[', 1)[0]\r
1310 CApp = CApp + ' __FLEXIBLE_SIZE(Size, %s, %s, %d);\n' % (Pcd.DatumType, FieldName.strip("."), ArrayIndex + 1)\r
ae7b6df8 1311\r
8518bf0b
LG
1312 #\r
1313 # Allocate and zero buffer for the PCD\r
1314 # Must handle cases where current value is smaller, larger, or same size\r
1315 # Always keep that larger one as the current size\r
1316 #\r
1317 CApp = CApp + ' Size = (OriginalSize > Size ? OriginalSize : Size);\n'\r
1318 CApp = CApp + ' Pcd = (%s *)malloc (Size);\n' % (Pcd.DatumType)\r
1319 CApp = CApp + ' memset (Pcd, 0, Size);\n'\r
ae7b6df8 1320\r
8518bf0b
LG
1321 #\r
1322 # Copy current PCD value into allocated buffer.\r
1323 #\r
1324 CApp = CApp + ' memcpy (Pcd, OriginalPcd, OriginalSize);\n'\r
ae7b6df8 1325\r
8518bf0b
LG
1326 #\r
1327 # Assign field values in PCD\r
1328 #\r
1329 for FieldList in [Pcd.DefaultValues, Pcd.DefaultFromDSC,OverrideValues.get(DefaultStoreName)]:\r
1330 if not FieldList:\r
1331 continue\r
1332 if Pcd.DefaultFromDSC and FieldList == Pcd.DefaultFromDSC:\r
1333 IsArray = self.IsFieldValueAnArray(FieldList)\r
1334 Value, ValueSize = ParseFieldValue (FieldList)\r
1335 if isinstance(Value, str):\r
1336 CApp = CApp + ' Pcd = %s; // From DSC Default Value %s\n' % (Value, Pcd.DefaultFromDSC)\r
1337 elif IsArray:\r
1338 #\r
1339 # Use memcpy() to copy value into field\r
1340 #\r
1341 CApp = CApp + ' Value = %s; // From DSC Default Value %s\n' % (self.IntToCString(Value, ValueSize), Pcd.DefaultFromDSC)\r
1342 CApp = CApp + ' memcpy (Pcd, Value, %d);\n' % (ValueSize)\r
1343 continue\r
ae7b6df8 1344\r
8518bf0b
LG
1345 for FieldName in FieldList:\r
1346 IsArray = self.IsFieldValueAnArray(FieldList[FieldName][0])\r
1347 try:\r
1348 Value, ValueSize = ParseFieldValue (FieldList[FieldName][0])\r
1349 except Exception:\r
1350 print FieldList[FieldName][0]\r
1351 if isinstance(Value, str):\r
1352 CApp = CApp + ' Pcd->%s = %s; // From %s Line %d Value %s\n' % (FieldName, Value, FieldList[FieldName][1], FieldList[FieldName][2], FieldList[FieldName][0])\r
1353 elif IsArray:\r
1354 #\r
1355 # Use memcpy() to copy value into field\r
1356 #\r
1357 CApp = CApp + ' FieldSize = __FIELD_SIZE(%s, %s);\n' % (Pcd.DatumType, FieldName)\r
1358 CApp = CApp + ' Value = %s; // From %s Line %d Value %s\n' % (self.IntToCString(Value, ValueSize), FieldList[FieldName][1], FieldList[FieldName][2], FieldList[FieldName][0])\r
1359 CApp = CApp + ' memcpy (&Pcd->%s[0], Value, (FieldSize > 0 && FieldSize < %d) ? FieldSize : %d);\n' % (FieldName, ValueSize, ValueSize)\r
ae7b6df8 1360 else:\r
8518bf0b
LG
1361 if ValueSize > 4:\r
1362 CApp = CApp + ' Pcd->%s = %dULL; // From %s Line %d Value %s\n' % (FieldName, Value, FieldList[FieldName][1], FieldList[FieldName][2], FieldList[FieldName][0])\r
1363 else:\r
1364 CApp = CApp + ' Pcd->%s = %d; // From %s Line %d Value %s\n' % (FieldName, Value, FieldList[FieldName][1], FieldList[FieldName][2], FieldList[FieldName][0])\r
ae7b6df8 1365\r
8518bf0b
LG
1366 #\r
1367 # Set new PCD value and size\r
1368 #\r
1369 CApp = CApp + ' PcdSetPtr (%s, %s, %s, %s, Size, (UINT8 *)Pcd);\n' % (SkuName, DefaultStoreName, Pcd.TokenSpaceGuidCName, Pcd.TokenCName)\r
ae7b6df8 1370\r
8518bf0b
LG
1371 #\r
1372 # Free PCD\r
1373 #\r
1374 CApp = CApp + ' free (Pcd);\n'\r
1375 CApp = CApp + '}\n'\r
1376 CApp = CApp + '\n'\r
ae7b6df8
LG
1377 return InitByteValue, CApp\r
1378\r
1379 def GenerateByteArrayValue (self, StructuredPcds):\r
1380 #\r
1381 # Generate/Compile/Run C application to determine if there are any flexible array members\r
1382 #\r
1383 if not StructuredPcds:\r
1384 return\r
1385\r
1386 InitByteValue = ""\r
1387 CApp = PcdMainCHeader\r
1388\r
1389 Includes = {}\r
1390 for PcdName in StructuredPcds:\r
1391 Pcd = StructuredPcds[PcdName]\r
1392 IncludeFile = Pcd.StructuredPcdIncludeFile\r
1393 if IncludeFile not in Includes:\r
1394 Includes[IncludeFile] = True\r
1395 CApp = CApp + '#include <%s>\n' % (IncludeFile)\r
1396 CApp = CApp + '\n'\r
1397\r
1398 for PcdName in StructuredPcds:\r
1399 Pcd = StructuredPcds[PcdName]\r
1400 if not Pcd.SkuOverrideValues:\r
8518bf0b 1401 InitByteValue, CApp = self.GenerateInitializeFunc(self.SkuIdMgr.SystemSkuId, 'STANDARD', Pcd, InitByteValue, CApp)\r
ae7b6df8
LG
1402 else:\r
1403 for SkuName in Pcd.SkuOverrideValues:\r
1404 for DefaultStoreName in Pcd.DefaultStoreName:\r
1405 Pcd = StructuredPcds[PcdName]\r
1406 InitByteValue, CApp = self.GenerateInitializeFunc(SkuName, DefaultStoreName, Pcd, InitByteValue, CApp)\r
1407\r
1408 CApp = CApp + 'VOID\n'\r
1409 CApp = CApp + 'PcdEntryPoint(\n'\r
1410 CApp = CApp + ' VOID\n'\r
1411 CApp = CApp + ' )\n'\r
1412 CApp = CApp + '{\n'\r
1413 for Pcd in StructuredPcds.values():\r
1414 if not Pcd.SkuOverrideValues:\r
8518bf0b 1415 CApp = CApp + ' Initialize_%s_%s_%s_%s();\n' % (self.SkuIdMgr.SystemSkuId, 'STANDARD', Pcd.TokenSpaceGuidCName, Pcd.TokenCName)\r
ae7b6df8
LG
1416 else:\r
1417 for SkuName in Pcd.SkuOverrideValues:\r
8518bf0b 1418 for DefaultStoreName in Pcd.SkuOverrideValues[SkuName]:\r
ae7b6df8
LG
1419 CApp = CApp + ' Initialize_%s_%s_%s_%s();\n' % (SkuName, DefaultStoreName, Pcd.TokenSpaceGuidCName, Pcd.TokenCName)\r
1420 CApp = CApp + '}\n'\r
1421\r
1422 CApp = CApp + PcdMainCEntry + '\n'\r
1423\r
1424 if not os.path.exists(self.OutputPath):\r
1425 os.makedirs(self.OutputPath)\r
1426 CAppBaseFileName = os.path.join(self.OutputPath, PcdValueInitName)\r
1427 File = open (CAppBaseFileName + '.c', 'w')\r
1428 File.write(CApp)\r
1429 File.close()\r
1430\r
1431 MakeApp = PcdMakefileHeader\r
1432 if sys.platform == "win32":\r
1433 MakeApp = MakeApp + 'ARCH = IA32\nAPPNAME = %s\n' % (PcdValueInitName) + 'OBJECTS = %s\%s.obj\n' % (self.OutputPath, PcdValueInitName) + 'INC = '\r
1434 else:\r
1435 MakeApp = MakeApp + PcdGccMakefile\r
1436 MakeApp = MakeApp + 'APPNAME = %s\n' % (PcdValueInitName) + 'OBJECTS = %s/%s.o\n' % (self.OutputPath, PcdValueInitName) + \\r
b2395724 1437 'include $(MAKEROOT)/Makefiles/app.makefile\n' + 'BUILD_CFLAGS += -Wno-pointer-to-int-cast -Wno-unused-variable\n' + 'INCLUDE +='\r
ae7b6df8
LG
1438\r
1439 PlatformInc = {}\r
1440 for Cache in self._Bdb._CACHE_.values():\r
1441 if Cache.MetaFile.Ext.lower() != '.dec':\r
1442 continue\r
1443 if Cache.Includes:\r
1444 if str(Cache.MetaFile.Path) not in PlatformInc:\r
1445 PlatformInc[str(Cache.MetaFile.Path)] = Cache.Includes\r
1446\r
1447 PcdDependDEC = []\r
1448 for Pcd in StructuredPcds.values():\r
1449 for PackageDec in Pcd.PackageDecs:\r
1450 Package = os.path.normpath(mws.join(GlobalData.gWorkspace, PackageDec))\r
1451 if not os.path.exists(Package):\r
1452 EdkLogger.error('Build', RESOURCE_NOT_AVAILABLE, "The dependent Package %s of PCD %s.%s is not exist." % (PackageDec, Pcd.TokenSpaceGuidCName, Pcd.TokenCName))\r
1453 if Package not in PcdDependDEC:\r
1454 PcdDependDEC.append(Package)\r
1455\r
1456 if PlatformInc and PcdDependDEC:\r
1457 for pkg in PcdDependDEC:\r
1458 if pkg in PlatformInc:\r
1459 for inc in PlatformInc[pkg]:\r
1460 MakeApp += '-I' + str(inc) + ' '\r
1461 MakeApp = MakeApp + '\n'\r
1462 if sys.platform == "win32":\r
1463 MakeApp = MakeApp + PcdMakefileEnd\r
1464 MakeFileName = os.path.join(self.OutputPath, 'Makefile')\r
1465 File = open (MakeFileName, 'w')\r
1466 File.write(MakeApp)\r
1467 File.close()\r
1468\r
1469 InputValueFile = os.path.join(self.OutputPath, 'Input.txt')\r
1470 OutputValueFile = os.path.join(self.OutputPath, 'Output.txt')\r
1471 File = open (InputValueFile, 'w')\r
1472 File.write(InitByteValue)\r
1473 File.close()\r
1474\r
b2395724 1475 Messages = ''\r
ae7b6df8
LG
1476 if sys.platform == "win32":\r
1477 StdOut, StdErr = self.ExecuteCommand ('nmake clean & nmake -f %s' % (MakeFileName))\r
b2395724 1478 Messages = StdOut\r
ae7b6df8
LG
1479 else:\r
1480 StdOut, StdErr = self.ExecuteCommand ('make clean & make -f %s' % (MakeFileName))\r
b2395724
LG
1481 Messages = StdErr\r
1482 Messages = Messages.split('\n')\r
1483 for Message in Messages:\r
1484 if " error" in Message:\r
1485 FileInfo = Message.strip().split('(')\r
1486 if len (FileInfo) > 1:\r
1487 FileName = FileInfo [0]\r
1488 FileLine = FileInfo [1].split (')')[0]\r
1489 else:\r
1490 FileInfo = Message.strip().split(':')\r
1491 FileName = FileInfo [0]\r
1492 FileLine = FileInfo [1]\r
1493\r
1494 File = open (FileName, 'r')\r
1495 FileData = File.readlines()\r
1496 File.close()\r
1497 error_line = FileData[int (FileLine) - 1]\r
1498 if r"//" in error_line:\r
1499 c_line,dsc_line = error_line.split(r"//")\r
1500 else:\r
1501 dsc_line = error_line\r
1502\r
1503 message_itmes = Message.split(":")\r
1504 Index = 0\r
1505 for item in message_itmes:\r
1506 if "PcdValueInit.c" in item:\r
1507 Index = message_itmes.index(item)\r
1508 message_itmes[Index] = dsc_line.strip()\r
1509 break\r
1510\r
1511 EdkLogger.error("build", PCD_STRUCTURE_PCD_ERROR, ":".join(message_itmes[Index:]))\r
ae7b6df8
LG
1512\r
1513 PcdValueInitExe = PcdValueInitName\r
1514 if not sys.platform == "win32":\r
1515 PcdValueInitExe = os.path.join(os.getenv("EDK_TOOLS_PATH"), 'Source', 'C', 'bin', PcdValueInitName)\r
1516\r
1517 StdOut, StdErr = self.ExecuteCommand (PcdValueInitExe + ' -i %s -o %s' % (InputValueFile, OutputValueFile))\r
1518 File = open (OutputValueFile, 'r')\r
1519 FileBuffer = File.readlines()\r
1520 File.close()\r
1521\r
1522 StructurePcdSet = []\r
1523 for Pcd in FileBuffer:\r
1524 PcdValue = Pcd.split ('|')\r
1525 PcdInfo = PcdValue[0].split ('.')\r
8518bf0b 1526 StructurePcdSet.append((PcdInfo[0],PcdInfo[1], PcdInfo[2], PcdInfo[3], PcdValue[2].strip()))\r
ae7b6df8
LG
1527 return StructurePcdSet\r
1528\r
1529 ## Retrieve dynamic PCD settings\r
1530 #\r
1531 # @param Type PCD type\r
1532 #\r
1533 # @retval a dict object contains settings of given PCD type\r
1534 #\r
1535 def _GetDynamicPcd(self, Type):\r
1536\r
ae7b6df8
LG
1537\r
1538 Pcds = sdict()\r
1539 #\r
1540 # tdict is a special dict kind of type, used for selecting correct\r
1541 # PCD settings for certain ARCH and SKU\r
1542 #\r
1543 PcdDict = tdict(True, 4)\r
1544 PcdList = []\r
1545 # Find out all possible PCD candidates for self._Arch\r
1546 RecordList = self._RawData[Type, self._Arch]\r
8518bf0b 1547 AvailableSkuIdSet = copy.copy(self.SkuIds)\r
ae7b6df8 1548\r
ae7b6df8 1549\r
8518bf0b 1550 for TokenSpaceGuid, PcdCName, Setting, Arch, SkuName, Dummy3, Dummy4,Dummy5 in RecordList:\r
2b8a6c44
LG
1551 SkuName = SkuName.upper()\r
1552 SkuName = 'DEFAULT' if SkuName == 'COMMON' else SkuName\r
ae7b6df8 1553 if SkuName not in AvailableSkuIdSet:\r
2b8a6c44
LG
1554 EdkLogger.error('build', PARAMETER_INVALID, 'Sku %s is not defined in [SkuIds] section' % SkuName,\r
1555 File=self.MetaFile, Line=Dummy5)\r
ae7b6df8
LG
1556 if "." not in TokenSpaceGuid:\r
1557 PcdList.append((PcdCName, TokenSpaceGuid, SkuName, Dummy4))\r
1558 PcdDict[Arch, SkuName, PcdCName, TokenSpaceGuid] = Setting\r
1559\r
1560 # Remove redundant PCD candidates, per the ARCH and SKU\r
1561 for PcdCName, TokenSpaceGuid, SkuName, Dummy4 in PcdList:\r
1562\r
1563 Setting = PcdDict[self._Arch, SkuName, PcdCName, TokenSpaceGuid]\r
1564 if Setting == None:\r
1565 continue\r
1566\r
1567 PcdValue, DatumType, MaxDatumSize = self._ValidatePcd(PcdCName, TokenSpaceGuid, Setting, Type, Dummy4)\r
8518bf0b 1568 SkuInfo = SkuInfoClass(SkuName, self.SkuIds[SkuName][0], '', '', '', '', '', PcdValue)\r
ae7b6df8
LG
1569 if (PcdCName, TokenSpaceGuid) in Pcds.keys():\r
1570 pcdObject = Pcds[PcdCName, TokenSpaceGuid]\r
1571 pcdObject.SkuInfoList[SkuName] = SkuInfo\r
1572 if MaxDatumSize.strip():\r
1573 CurrentMaxSize = int(MaxDatumSize.strip(), 0)\r
1574 else:\r
1575 CurrentMaxSize = 0\r
1576 if pcdObject.MaxDatumSize:\r
1577 PcdMaxSize = int(pcdObject.MaxDatumSize, 0)\r
1578 else:\r
1579 PcdMaxSize = 0\r
1580 if CurrentMaxSize > PcdMaxSize:\r
1581 pcdObject.MaxDatumSize = str(CurrentMaxSize)\r
1582 else:\r
1583 Pcds[PcdCName, TokenSpaceGuid] = PcdClassObject(\r
1584 PcdCName,\r
1585 TokenSpaceGuid,\r
1586 self._PCD_TYPE_STRING_[Type],\r
1587 DatumType,\r
1588 PcdValue,\r
1589 '',\r
1590 MaxDatumSize,\r
1591 {SkuName : SkuInfo},\r
1592 False,\r
1593 None,\r
1594 IsDsc=True)\r
1595\r
1596 for pcd in Pcds.values():\r
1597 pcdDecObject = self._DecPcds[pcd.TokenCName, pcd.TokenSpaceGuidCName]\r
e651d06c
LG
1598 # Only fix the value while no value provided in DSC file.\r
1599 for sku in pcd.SkuInfoList.values():\r
1600 if (sku.DefaultValue == "" or sku.DefaultValue==None):\r
1601 sku.DefaultValue = pcdDecObject.DefaultValue\r
ae7b6df8
LG
1602 if 'DEFAULT' not in pcd.SkuInfoList.keys() and 'COMMON' not in pcd.SkuInfoList.keys():\r
1603 valuefromDec = pcdDecObject.DefaultValue\r
1604 SkuInfo = SkuInfoClass('DEFAULT', '0', '', '', '', '', '', valuefromDec)\r
1605 pcd.SkuInfoList['DEFAULT'] = SkuInfo\r
1606 elif 'DEFAULT' not in pcd.SkuInfoList.keys() and 'COMMON' in pcd.SkuInfoList.keys():\r
1607 pcd.SkuInfoList['DEFAULT'] = pcd.SkuInfoList['COMMON']\r
1608 del(pcd.SkuInfoList['COMMON'])\r
1609 elif 'DEFAULT' in pcd.SkuInfoList.keys() and 'COMMON' in pcd.SkuInfoList.keys():\r
1610 del(pcd.SkuInfoList['COMMON'])\r
65eff519
LG
1611\r
1612 map(self.FilterSkuSettings,Pcds.values())\r
ae7b6df8
LG
1613\r
1614 return Pcds\r
1615\r
65eff519
LG
1616 def FilterSkuSettings(self, PcdObj):\r
1617\r
1618 if self.SkuIdMgr.SkuUsageType == self.SkuIdMgr.SINGLE:\r
1619 if 'DEFAULT' in PcdObj.SkuInfoList.keys() and self.SkuIdMgr.SystemSkuId not in PcdObj.SkuInfoList.keys():\r
1620 PcdObj.SkuInfoList[self.SkuIdMgr.SystemSkuId] = PcdObj.SkuInfoList['DEFAULT']\r
1621 PcdObj.SkuInfoList = {'DEFAULT':PcdObj.SkuInfoList[self.SkuIdMgr.SystemSkuId]}\r
1622 PcdObj.SkuInfoList['DEFAULT'].SkuIdName = 'DEFAULT'\r
1623 PcdObj.SkuInfoList['DEFAULT'].SkuId = '0'\r
1624\r
1625 elif self.SkuIdMgr.SkuUsageType == self.SkuIdMgr.DEFAULT:\r
1626 PcdObj.SkuInfoList = {'DEFAULT':PcdObj.SkuInfoList['DEFAULT']}\r
1627\r
1628 return PcdObj\r
1629\r
1630\r
ae7b6df8
LG
1631 def CompareVarAttr(self, Attr1, Attr2):\r
1632 if not Attr1 or not Attr2: # for empty string\r
1633 return True\r
1634 Attr1s = [attr.strip() for attr in Attr1.split(",")]\r
1635 Attr1Set = set(Attr1s)\r
1636 Attr2s = [attr.strip() for attr in Attr2.split(",")]\r
1637 Attr2Set = set(Attr2s)\r
1638 if Attr2Set == Attr1Set:\r
1639 return True\r
1640 else:\r
1641 return False\r
8518bf0b
LG
1642 def CompletePcdValues(self,PcdSet):\r
1643 Pcds = {}\r
1644 DefaultStoreObj = DefaultStore(self._GetDefaultStores())\r
2b8a6c44 1645 SkuIds = set([(skuid,skuobj.SkuId) for pcdobj in PcdSet.values() for skuid,skuobj in pcdobj.SkuInfoList.items()])\r
8518bf0b
LG
1646 DefaultStores = set([storename for pcdobj in PcdSet.values() for skuobj in pcdobj.SkuInfoList.values() for storename in skuobj.DefaultStoreDict.keys()])\r
1647 for PcdCName, TokenSpaceGuid in PcdSet:\r
1648 PcdObj = PcdSet[(PcdCName, TokenSpaceGuid)]\r
1649 if PcdObj.Type not in [self._PCD_TYPE_STRING_[MODEL_PCD_DYNAMIC_DEFAULT],\r
1650 self._PCD_TYPE_STRING_[MODEL_PCD_DYNAMIC_HII],\r
1651 self._PCD_TYPE_STRING_[MODEL_PCD_DYNAMIC_VPD],\r
1652 self._PCD_TYPE_STRING_[MODEL_PCD_DYNAMIC_EX_DEFAULT],\r
1653 self._PCD_TYPE_STRING_[MODEL_PCD_DYNAMIC_EX_HII],\r
1654 self._PCD_TYPE_STRING_[MODEL_PCD_DYNAMIC_EX_VPD]]:\r
1655 Pcds[PcdCName, TokenSpaceGuid]= PcdObj\r
1656 continue\r
1657 PcdType = PcdObj.Type\r
1658 if PcdType in [self._PCD_TYPE_STRING_[MODEL_PCD_DYNAMIC_HII], self._PCD_TYPE_STRING_[MODEL_PCD_DYNAMIC_EX_HII]]:\r
1659 for skuid in PcdObj.SkuInfoList:\r
1660 skuobj = PcdObj.SkuInfoList[skuid]\r
1661 mindefaultstorename = DefaultStoreObj.GetMin(set([defaultstorename for defaultstorename in skuobj.DefaultStoreDict]))\r
1662 for defaultstorename in DefaultStores:\r
1663 if defaultstorename not in skuobj.DefaultStoreDict:\r
2b8a6c44 1664 skuobj.DefaultStoreDict[defaultstorename] = copy.deepcopy(skuobj.DefaultStoreDict[mindefaultstorename])\r
8518bf0b 1665 skuobj.HiiDefaultValue = skuobj.DefaultStoreDict[mindefaultstorename]\r
2b8a6c44
LG
1666 for skuname,skuid in SkuIds:\r
1667 if skuname not in PcdObj.SkuInfoList:\r
1668 nextskuid = self.SkuIdMgr.GetNextSkuId(skuname)\r
8518bf0b
LG
1669 while nextskuid not in PcdObj.SkuInfoList:\r
1670 nextskuid = self.SkuIdMgr.GetNextSkuId(nextskuid)\r
2b8a6c44
LG
1671 PcdObj.SkuInfoList[skuname] = copy.deepcopy(PcdObj.SkuInfoList[nextskuid])\r
1672 PcdObj.SkuInfoList[skuname].SkuId = skuid\r
1673 PcdObj.SkuInfoList[skuname].SkuIdName = skuname\r
8518bf0b
LG
1674 if PcdType in [self._PCD_TYPE_STRING_[MODEL_PCD_DYNAMIC_HII], self._PCD_TYPE_STRING_[MODEL_PCD_DYNAMIC_EX_HII]]:\r
1675 PcdObj.DefaultValue = PcdObj.SkuInfoList.values()[0].HiiDefaultValue if self.SkuIdMgr.SkuUsageType == self.SkuIdMgr.SINGLE else PcdObj.SkuInfoList["DEFAULT"].HiiDefaultValue\r
1676 Pcds[PcdCName, TokenSpaceGuid]= PcdObj\r
1677 return Pcds\r
ae7b6df8
LG
1678 ## Retrieve dynamic HII PCD settings\r
1679 #\r
1680 # @param Type PCD type\r
1681 #\r
1682 # @retval a dict object contains settings of given PCD type\r
1683 #\r
1684 def _GetDynamicHiiPcd(self, Type):\r
1685\r
ae7b6df8
LG
1686 VariableAttrs = {}\r
1687\r
1688 Pcds = sdict()\r
1689 #\r
1690 # tdict is a special dict kind of type, used for selecting correct\r
1691 # PCD settings for certain ARCH and SKU\r
1692 #\r
8518bf0b 1693 PcdDict = tdict(True, 5)\r
ae7b6df8
LG
1694 PcdSet = set()\r
1695 RecordList = self._RawData[Type, self._Arch]\r
1696 # Find out all possible PCD candidates for self._Arch\r
8518bf0b 1697 AvailableSkuIdSet = copy.copy(self.SkuIds)\r
2b8a6c44 1698 DefaultStoresDefine = self._GetDefaultStores()\r
ae7b6df8 1699\r
8518bf0b 1700 for TokenSpaceGuid, PcdCName, Setting, Arch, SkuName, DefaultStore, Dummy4,Dummy5 in RecordList:\r
2b8a6c44
LG
1701 SkuName = SkuName.upper()\r
1702 SkuName = 'DEFAULT' if SkuName == 'COMMON' else SkuName\r
1703 DefaultStore = DefaultStore.upper()\r
8518bf0b
LG
1704 if DefaultStore == "COMMON":\r
1705 DefaultStore = "STANDARD"\r
ae7b6df8 1706 if SkuName not in AvailableSkuIdSet:\r
2b8a6c44
LG
1707 EdkLogger.error('build', PARAMETER_INVALID, 'Sku %s is not defined in [SkuIds] section' % SkuName,\r
1708 File=self.MetaFile, Line=Dummy5)\r
1709 if DefaultStore not in DefaultStoresDefine:\r
1710 EdkLogger.error('build', PARAMETER_INVALID, 'DefaultStores %s is not defined in [DefaultStores] section' % DefaultStore,\r
1711 File=self.MetaFile, Line=Dummy5)\r
ae7b6df8 1712 if "." not in TokenSpaceGuid:\r
8518bf0b
LG
1713 PcdSet.add((PcdCName, TokenSpaceGuid, SkuName,DefaultStore, Dummy4))\r
1714 PcdDict[Arch, SkuName, PcdCName, TokenSpaceGuid,DefaultStore] = Setting\r
ae7b6df8
LG
1715\r
1716\r
1717 # Remove redundant PCD candidates, per the ARCH and SKU\r
8518bf0b 1718 for PcdCName, TokenSpaceGuid, SkuName,DefaultStore, Dummy4 in PcdSet:\r
ae7b6df8 1719\r
8518bf0b 1720 Setting = PcdDict[self._Arch, SkuName, PcdCName, TokenSpaceGuid,DefaultStore]\r
ae7b6df8
LG
1721 if Setting == None:\r
1722 continue\r
1723 VariableName, VariableGuid, VariableOffset, DefaultValue, VarAttribute = self._ValidatePcd(PcdCName, TokenSpaceGuid, Setting, Type, Dummy4)\r
1724\r
1725 rt, Msg = VariableAttributes.ValidateVarAttributes(VarAttribute)\r
1726 if not rt:\r
1727 EdkLogger.error("build", PCD_VARIABLE_ATTRIBUTES_ERROR, "Variable attributes settings for %s is incorrect.\n %s" % (".".join((TokenSpaceGuid, PcdCName)), Msg),\r
1728 ExtraData="[%s]" % VarAttribute)\r
1729 ExceedMax = False\r
1730 FormatCorrect = True\r
1731 if VariableOffset.isdigit():\r
1732 if int(VariableOffset, 10) > 0xFFFF:\r
1733 ExceedMax = True\r
1734 elif re.match(r'[\t\s]*0[xX][a-fA-F0-9]+$', VariableOffset):\r
1735 if int(VariableOffset, 16) > 0xFFFF:\r
1736 ExceedMax = True\r
1737 # For Offset written in "A.B"\r
1738 elif VariableOffset.find('.') > -1:\r
1739 VariableOffsetList = VariableOffset.split(".")\r
1740 if not (len(VariableOffsetList) == 2\r
1741 and IsValidWord(VariableOffsetList[0])\r
1742 and IsValidWord(VariableOffsetList[1])):\r
1743 FormatCorrect = False\r
1744 else:\r
1745 FormatCorrect = False\r
1746 if not FormatCorrect:\r
1747 EdkLogger.error('Build', FORMAT_INVALID, "Invalid syntax or format of the variable offset value is incorrect for %s." % ".".join((TokenSpaceGuid, PcdCName)))\r
1748\r
1749 if ExceedMax:\r
1750 EdkLogger.error('Build', OPTION_VALUE_INVALID, "The variable offset value must not exceed the maximum value of 0xFFFF (UINT16) for %s." % ".".join((TokenSpaceGuid, PcdCName)))\r
1751 if (VariableName, VariableGuid) not in VariableAttrs:\r
1752 VariableAttrs[(VariableName, VariableGuid)] = VarAttribute\r
1753 else:\r
1754 if not self.CompareVarAttr(VariableAttrs[(VariableName, VariableGuid)], VarAttribute):\r
1755 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)]))\r
1756\r
ae7b6df8
LG
1757 pcdDecObject = self._DecPcds[PcdCName, TokenSpaceGuid]\r
1758 if (PcdCName, TokenSpaceGuid) in Pcds.keys():\r
1759 pcdObject = Pcds[PcdCName, TokenSpaceGuid]\r
8518bf0b
LG
1760 if SkuName in pcdObject.SkuInfoList:\r
1761 Skuitem = pcdObject.SkuInfoList[SkuName]\r
1762 Skuitem.DefaultStoreDict.update({DefaultStore:DefaultValue})\r
1763 else:\r
1764 SkuInfo = SkuInfoClass(SkuName, self.SkuIds[SkuName][0], VariableName, VariableGuid, VariableOffset, DefaultValue, VariableAttribute=VarAttribute,DefaultStore={DefaultStore:DefaultValue})\r
1765 pcdObject.SkuInfoList[SkuName] = SkuInfo\r
ae7b6df8 1766 else:\r
8518bf0b 1767 SkuInfo = SkuInfoClass(SkuName, self.SkuIds[SkuName][0], VariableName, VariableGuid, VariableOffset, DefaultValue, VariableAttribute=VarAttribute,DefaultStore={DefaultStore:DefaultValue})\r
ae7b6df8
LG
1768 Pcds[PcdCName, TokenSpaceGuid] = PcdClassObject(\r
1769 PcdCName,\r
1770 TokenSpaceGuid,\r
1771 self._PCD_TYPE_STRING_[Type],\r
1772 '',\r
1773 DefaultValue,\r
1774 '',\r
1775 '',\r
1776 {SkuName : SkuInfo},\r
1777 False,\r
1778 None,\r
1779 pcdDecObject.validateranges,\r
1780 pcdDecObject.validlists,\r
1781 pcdDecObject.expressions,\r
1782 IsDsc=True)\r
1783\r
1784\r
1785 for pcd in Pcds.values():\r
1786 SkuInfoObj = pcd.SkuInfoList.values()[0]\r
1787 pcdDecObject = self._DecPcds[pcd.TokenCName, pcd.TokenSpaceGuidCName]\r
1788 # Only fix the value while no value provided in DSC file.\r
1789 for sku in pcd.SkuInfoList.values():\r
1790 if (sku.HiiDefaultValue == "" or sku.HiiDefaultValue == None):\r
1791 sku.HiiDefaultValue = pcdDecObject.DefaultValue\r
1792 if 'DEFAULT' not in pcd.SkuInfoList.keys() and 'COMMON' not in pcd.SkuInfoList.keys():\r
1793 valuefromDec = pcdDecObject.DefaultValue\r
2b8a6c44 1794 SkuInfo = SkuInfoClass('DEFAULT', '0', SkuInfoObj.VariableName, SkuInfoObj.VariableGuid, SkuInfoObj.VariableOffset, valuefromDec,VariableAttribute=SkuInfoObj.VariableAttribute,DefaultStore={DefaultStore:valuefromDec})\r
ae7b6df8
LG
1795 pcd.SkuInfoList['DEFAULT'] = SkuInfo\r
1796 elif 'DEFAULT' not in pcd.SkuInfoList.keys() and 'COMMON' in pcd.SkuInfoList.keys():\r
1797 pcd.SkuInfoList['DEFAULT'] = pcd.SkuInfoList['COMMON']\r
1798 del(pcd.SkuInfoList['COMMON'])\r
1799 elif 'DEFAULT' in pcd.SkuInfoList.keys() and 'COMMON' in pcd.SkuInfoList.keys():\r
1800 del(pcd.SkuInfoList['COMMON'])\r
1801\r
ae7b6df8
LG
1802 if pcd.MaxDatumSize.strip():\r
1803 MaxSize = int(pcd.MaxDatumSize, 0)\r
1804 else:\r
1805 MaxSize = 0\r
1806 if pcdDecObject.DatumType == 'VOID*':\r
2b8a6c44 1807 for (_, skuobj) in pcd.SkuInfoList.items():\r
ae7b6df8 1808 datalen = 0\r
47854fd5
LG
1809 skuobj.HiiDefaultValue = StringToArray(skuobj.HiiDefaultValue)\r
1810 datalen = len(skuobj.HiiDefaultValue.split(","))\r
ae7b6df8
LG
1811 if datalen > MaxSize:\r
1812 MaxSize = datalen\r
47854fd5
LG
1813 for defaultst in skuobj.DefaultStoreDict:\r
1814 skuobj.DefaultStoreDict[defaultst] = StringToArray(skuobj.DefaultStoreDict[defaultst])\r
1815 pcd.DefaultValue = StringToArray(pcd.DefaultValue)\r
ae7b6df8 1816 pcd.MaxDatumSize = str(MaxSize)\r
2b8a6c44
LG
1817 rt, invalidhii = self.CheckVariableNameAssignment(Pcds)\r
1818 if not rt:\r
1819 invalidpcd = ",".join(invalidhii)\r
1820 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)\r
65eff519
LG
1821\r
1822 map(self.FilterSkuSettings,Pcds.values())\r
1823\r
ae7b6df8
LG
1824 return Pcds\r
1825\r
2b8a6c44
LG
1826 def CheckVariableNameAssignment(self,Pcds):\r
1827 invalidhii = []\r
1828 for pcdname in Pcds:\r
1829 pcd = Pcds[pcdname]\r
1830 varnameset = set([sku.VariableName for (skuid,sku) in pcd.SkuInfoList.items()])\r
1831 if len(varnameset) > 1:\r
1832 invalidhii.append(".".join((pcdname[1],pcdname[0])))\r
1833 if len(invalidhii):\r
1834 return False,invalidhii\r
1835 else:\r
1836 return True, []\r
ae7b6df8
LG
1837 ## Retrieve dynamic VPD PCD settings\r
1838 #\r
1839 # @param Type PCD type\r
1840 #\r
1841 # @retval a dict object contains settings of given PCD type\r
1842 #\r
1843 def _GetDynamicVpdPcd(self, Type):\r
1844\r
ae7b6df8
LG
1845\r
1846 Pcds = sdict()\r
1847 #\r
1848 # tdict is a special dict kind of type, used for selecting correct\r
1849 # PCD settings for certain ARCH and SKU\r
1850 #\r
1851 PcdDict = tdict(True, 4)\r
1852 PcdList = []\r
1853\r
1854 # Find out all possible PCD candidates for self._Arch\r
1855 RecordList = self._RawData[Type, self._Arch]\r
8518bf0b 1856 AvailableSkuIdSet = copy.copy(self.SkuIds)\r
ae7b6df8 1857\r
8518bf0b 1858 for TokenSpaceGuid, PcdCName, Setting, Arch, SkuName, Dummy3, Dummy4,Dummy5 in RecordList:\r
2b8a6c44
LG
1859 SkuName = SkuName.upper()\r
1860 SkuName = 'DEFAULT' if SkuName == 'COMMON' else SkuName\r
ae7b6df8 1861 if SkuName not in AvailableSkuIdSet:\r
2b8a6c44
LG
1862 EdkLogger.error('build', PARAMETER_INVALID, 'Sku %s is not defined in [SkuIds] section' % SkuName,\r
1863 File=self.MetaFile, Line=Dummy5)\r
ae7b6df8
LG
1864 if "." not in TokenSpaceGuid:\r
1865 PcdList.append((PcdCName, TokenSpaceGuid, SkuName, Dummy4))\r
1866 PcdDict[Arch, SkuName, PcdCName, TokenSpaceGuid] = Setting\r
1867\r
1868 # Remove redundant PCD candidates, per the ARCH and SKU\r
1869 for PcdCName, TokenSpaceGuid, SkuName, Dummy4 in PcdList:\r
1870 Setting = PcdDict[self._Arch, SkuName, PcdCName, TokenSpaceGuid]\r
1871 if Setting == None:\r
1872 continue\r
1873 #\r
1874 # For the VOID* type, it can have optional data of MaxDatumSize and InitialValue\r
1875 # For the Integer & Boolean type, the optional data can only be InitialValue.\r
1876 # At this point, we put all the data into the PcdClssObject for we don't know the PCD's datumtype\r
1877 # until the DEC parser has been called.\r
1878 #\r
1879 VpdOffset, MaxDatumSize, InitialValue = self._ValidatePcd(PcdCName, TokenSpaceGuid, Setting, Type, Dummy4)\r
8518bf0b 1880 SkuInfo = SkuInfoClass(SkuName, self.SkuIds[SkuName][0], '', '', '', '', VpdOffset, InitialValue)\r
ae7b6df8
LG
1881 if (PcdCName, TokenSpaceGuid) in Pcds.keys():\r
1882 pcdObject = Pcds[PcdCName, TokenSpaceGuid]\r
1883 pcdObject.SkuInfoList[SkuName] = SkuInfo\r
1884 if MaxDatumSize.strip():\r
1885 CurrentMaxSize = int(MaxDatumSize.strip(), 0)\r
1886 else:\r
1887 CurrentMaxSize = 0\r
1888 if pcdObject.MaxDatumSize:\r
1889 PcdMaxSize = int(pcdObject.MaxDatumSize, 0)\r
1890 else:\r
1891 PcdMaxSize = 0\r
1892 if CurrentMaxSize > PcdMaxSize:\r
1893 pcdObject.MaxDatumSize = str(CurrentMaxSize)\r
1894 else:\r
1895 Pcds[PcdCName, TokenSpaceGuid] = PcdClassObject(\r
1896 PcdCName,\r
1897 TokenSpaceGuid,\r
1898 self._PCD_TYPE_STRING_[Type],\r
1899 '',\r
1900 InitialValue,\r
1901 '',\r
1902 MaxDatumSize,\r
1903 {SkuName : SkuInfo},\r
1904 False,\r
1905 None,\r
1906 IsDsc=True)\r
1907 for pcd in Pcds.values():\r
1908 SkuInfoObj = pcd.SkuInfoList.values()[0]\r
1909 pcdDecObject = self._DecPcds[pcd.TokenCName, pcd.TokenSpaceGuidCName]\r
e651d06c
LG
1910 # Only fix the value while no value provided in DSC file.\r
1911 for sku in pcd.SkuInfoList.values():\r
1912 if (sku.DefaultValue == "" or sku.DefaultValue==None):\r
1913 sku.DefaultValue = pcdDecObject.DefaultValue\r
ae7b6df8
LG
1914 if 'DEFAULT' not in pcd.SkuInfoList.keys() and 'COMMON' not in pcd.SkuInfoList.keys():\r
1915 valuefromDec = pcdDecObject.DefaultValue\r
1916 SkuInfo = SkuInfoClass('DEFAULT', '0', '', '', '', '', SkuInfoObj.VpdOffset, valuefromDec)\r
1917 pcd.SkuInfoList['DEFAULT'] = SkuInfo\r
1918 elif 'DEFAULT' not in pcd.SkuInfoList.keys() and 'COMMON' in pcd.SkuInfoList.keys():\r
1919 pcd.SkuInfoList['DEFAULT'] = pcd.SkuInfoList['COMMON']\r
1920 del(pcd.SkuInfoList['COMMON'])\r
1921 elif 'DEFAULT' in pcd.SkuInfoList.keys() and 'COMMON' in pcd.SkuInfoList.keys():\r
1922 del(pcd.SkuInfoList['COMMON'])\r
ae7b6df8 1923\r
65eff519
LG
1924\r
1925 map(self.FilterSkuSettings,Pcds.values())\r
ae7b6df8
LG
1926 return Pcds\r
1927\r
1928 ## Add external modules\r
1929 #\r
1930 # The external modules are mostly those listed in FDF file, which don't\r
1931 # need "build".\r
1932 #\r
1933 # @param FilePath The path of module description file\r
1934 #\r
1935 def AddModule(self, FilePath):\r
1936 FilePath = NormPath(FilePath)\r
1937 if FilePath not in self.Modules:\r
1938 Module = ModuleBuildClassObject()\r
1939 Module.MetaFile = FilePath\r
1940 self.Modules.append(Module)\r
1941\r
1942 ## Add external PCDs\r
1943 #\r
1944 # The external PCDs are mostly those listed in FDF file to specify address\r
1945 # or offset information.\r
1946 #\r
1947 # @param Name Name of the PCD\r
1948 # @param Guid Token space guid of the PCD\r
1949 # @param Value Value of the PCD\r
1950 #\r
1951 def AddPcd(self, Name, Guid, Value):\r
1952 if (Name, Guid) not in self.Pcds:\r
1953 self.Pcds[Name, Guid] = PcdClassObject(Name, Guid, '', '', '', '', '', {}, False, None)\r
1954 self.Pcds[Name, Guid].DefaultValue = Value\r
1955\r
1956 _Macros = property(_GetMacros)\r
1957 Arch = property(_GetArch, _SetArch)\r
1958 Platform = property(_GetPlatformName)\r
1959 PlatformName = property(_GetPlatformName)\r
1960 Guid = property(_GetFileGuid)\r
1961 Version = property(_GetVersion)\r
1962 DscSpecification = property(_GetDscSpec)\r
1963 OutputDirectory = property(_GetOutpuDir)\r
1964 SupArchList = property(_GetSupArch)\r
1965 BuildTargets = property(_GetBuildTarget)\r
1966 SkuName = property(_GetSkuName, _SetSkuName)\r
ae7b6df8
LG
1967 PcdInfoFlag = property(_GetPcdInfoFlag)\r
1968 VarCheckFlag = property(_GetVarCheckFlag)\r
1969 FlashDefinition = property(_GetFdfFile)\r
1970 Prebuild = property(_GetPrebuild)\r
1971 Postbuild = property(_GetPostbuild)\r
1972 BuildNumber = property(_GetBuildNumber)\r
1973 MakefileName = property(_GetMakefileName)\r
1974 BsBaseAddress = property(_GetBsBaseAddress)\r
1975 RtBaseAddress = property(_GetRtBaseAddress)\r
1976 LoadFixAddress = property(_GetLoadFixAddress)\r
1977 RFCLanguages = property(_GetRFCLanguages)\r
1978 ISOLanguages = property(_GetISOLanguages)\r
1979 VpdToolGuid = property(_GetVpdToolGuid)\r
1980 SkuIds = property(_GetSkuIds)\r
1981 Modules = property(_GetModules)\r
1982 LibraryInstances = property(_GetLibraryInstances)\r
1983 LibraryClasses = property(_GetLibraryClasses)\r
1984 Pcds = property(_GetPcds)\r
1985 BuildOptions = property(_GetBuildOptions)\r