2 # This file is used to create a database used by build tool
4 # Copyright (c) 2008 - 2009, Intel Corporation
5 # All rights reserved. This program and the accompanying materials
6 # are licensed and made available under the terms and conditions of the BSD License
7 # which accompanies this distribution. The full text of the license may be found at
8 # http://opensource.org/licenses/bsd-license.php
10 # THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
11 # WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
21 import Common
.EdkLogger
as EdkLogger
22 import Common
.GlobalData
as GlobalData
24 from Common
.String
import *
25 from Common
.DataType
import *
26 from Common
.Misc
import *
28 from CommonDataClass
.CommonClass
import SkuInfoClass
30 from MetaDataTable
import *
31 from MetaFileTable
import *
32 from MetaFileParser
import *
33 from BuildClassObject
import *
35 ## Platform build information from DSC file
37 # This class is used to retrieve information stored in database and convert them
38 # into PlatformBuildClassObject form for easier use for AutoGen.
40 class DscBuildData(PlatformBuildClassObject
):
41 # dict used to convert PCD type in database to string used by build tool
43 MODEL_PCD_FIXED_AT_BUILD
: "FixedAtBuild",
44 MODEL_PCD_PATCHABLE_IN_MODULE
: "PatchableInModule",
45 MODEL_PCD_FEATURE_FLAG
: "FeatureFlag",
46 MODEL_PCD_DYNAMIC
: "Dynamic",
47 MODEL_PCD_DYNAMIC_DEFAULT
: "Dynamic",
48 MODEL_PCD_DYNAMIC_HII
: "DynamicHii",
49 MODEL_PCD_DYNAMIC_VPD
: "DynamicVpd",
50 MODEL_PCD_DYNAMIC_EX
: "DynamicEx",
51 MODEL_PCD_DYNAMIC_EX_DEFAULT
: "DynamicEx",
52 MODEL_PCD_DYNAMIC_EX_HII
: "DynamicExHii",
53 MODEL_PCD_DYNAMIC_EX_VPD
: "DynamicExVpd",
56 # dict used to convert part of [Defines] to members of DscBuildData directly
61 TAB_DSC_DEFINES_PLATFORM_NAME
: "_PlatformName",
62 TAB_DSC_DEFINES_PLATFORM_GUID
: "_Guid",
63 TAB_DSC_DEFINES_PLATFORM_VERSION
: "_Version",
64 TAB_DSC_DEFINES_DSC_SPECIFICATION
: "_DscSpecification",
65 #TAB_DSC_DEFINES_OUTPUT_DIRECTORY : "_OutputDirectory",
66 #TAB_DSC_DEFINES_SUPPORTED_ARCHITECTURES : "_SupArchList",
67 #TAB_DSC_DEFINES_BUILD_TARGETS : "_BuildTargets",
68 #TAB_DSC_DEFINES_SKUID_IDENTIFIER : "_SkuName",
69 #TAB_DSC_DEFINES_FLASH_DEFINITION : "_FlashDefinition",
70 TAB_DSC_DEFINES_BUILD_NUMBER
: "_BuildNumber",
71 TAB_DSC_DEFINES_MAKEFILE_NAME
: "_MakefileName",
72 TAB_DSC_DEFINES_BS_BASE_ADDRESS
: "_BsBaseAddress",
73 TAB_DSC_DEFINES_RT_BASE_ADDRESS
: "_RtBaseAddress",
76 # used to compose dummy library class name for those forced library instances
77 _NullLibraryNumber
= 0
79 ## Constructor of DscBuildData
81 # Initialize object of DscBuildData
83 # @param FilePath The path of platform description file
84 # @param RawData The raw data of DSC file
85 # @param BuildDataBase Database used to retrieve module/package information
86 # @param Arch The target architecture
87 # @param Platform (not used for DscBuildData)
88 # @param Macros Macros used for replacement in DSC file
90 def __init__(self
, FilePath
, RawData
, BuildDataBase
, Arch
='COMMON', Platform
='DUMMY', Macros
={}):
91 self
.MetaFile
= FilePath
92 self
._RawData
= RawData
93 self
._Bdb
= BuildDataBase
97 RecordList
= self
._RawData
[MODEL_META_DATA_DEFINE
, self
._Arch
]
98 for Record
in RecordList
:
99 GlobalData
.gEdkGlobal
[Record
[0]] = Record
[1]
102 def __setitem__(self
, key
, value
):
103 self
.__dict
__[self
._PROPERTY
_[key
]] = value
106 def __getitem__(self
, key
):
107 return self
.__dict
__[self
._PROPERTY
_[key
]]
110 def __contains__(self
, key
):
111 return key
in self
._PROPERTY
_
113 ## Set all internal used members of DscBuildData to None
116 self
._PlatformName
= None
119 self
._DscSpecification
= None
120 self
._OutputDirectory
= None
121 self
._SupArchList
= None
122 self
._BuildTargets
= None
124 self
._FlashDefinition
= None
125 self
._BuildNumber
= None
126 self
._MakefileName
= None
127 self
._BsBaseAddress
= None
128 self
._RtBaseAddress
= None
131 self
._LibraryInstances
= None
132 self
._LibraryClasses
= None
134 self
._BuildOptions
= None
142 # Changing the default ARCH to another may affect all other information
143 # because all information in a platform may be ARCH-related. That's
144 # why we need to clear all internal used members, in order to cause all
145 # information to be re-retrieved.
147 # @param Value The value of ARCH
149 def _SetArch(self
, Value
):
150 if self
._Arch
== Value
:
155 ## Retrieve all information in [Defines] section
157 # (Retriving all [Defines] information in one-shot is just to save time.)
159 def _GetHeaderInfo(self
):
160 RecordList
= self
._RawData
[MODEL_META_DATA_HEADER
, self
._Arch
]
161 for Record
in RecordList
:
163 # items defined _PROPERTY_ don't need additional processing
165 self
[Name
] = Record
[1]
166 # some special items in [Defines] section need special treatment
167 elif Name
== TAB_DSC_DEFINES_OUTPUT_DIRECTORY
:
168 self
._OutputDirectory
= NormPath(Record
[1], self
._Macros
)
169 if ' ' in self
._OutputDirectory
:
170 EdkLogger
.error("build", FORMAT_NOT_SUPPORTED
, "No space is allowed in OUTPUT_DIRECTORY",
171 File
=self
.MetaFile
, Line
=Record
[-1],
172 ExtraData
=self
._OutputDirectory
)
173 elif Name
== TAB_DSC_DEFINES_FLASH_DEFINITION
:
174 self
._FlashDefinition
= PathClass(NormPath(Record
[1], self
._Macros
), GlobalData
.gWorkspace
)
175 ErrorCode
, ErrorInfo
= self
._FlashDefinition
.Validate('.fdf')
177 EdkLogger
.error('build', ErrorCode
, File
=self
.MetaFile
, Line
=Record
[-1],
179 elif Name
== TAB_DSC_DEFINES_SUPPORTED_ARCHITECTURES
:
180 self
._SupArchList
= GetSplitValueList(Record
[1], TAB_VALUE_SPLIT
)
181 elif Name
== TAB_DSC_DEFINES_BUILD_TARGETS
:
182 self
._BuildTargets
= GetSplitValueList(Record
[1])
183 elif Name
== TAB_DSC_DEFINES_SKUID_IDENTIFIER
:
184 if self
._SkuName
== None:
185 self
._SkuName
= Record
[1]
186 # set _Header to non-None in order to avoid database re-querying
187 self
._Header
= 'DUMMY'
189 ## Retrieve platform name
190 def _GetPlatformName(self
):
191 if self
._PlatformName
== None:
192 if self
._Header
== None:
193 self
._GetHeaderInfo
()
194 if self
._PlatformName
== None:
195 EdkLogger
.error('build', ATTRIBUTE_NOT_AVAILABLE
, "No PLATFORM_NAME", File
=self
.MetaFile
)
196 return self
._PlatformName
198 ## Retrieve file guid
199 def _GetFileGuid(self
):
200 if self
._Guid
== None:
201 if self
._Header
== None:
202 self
._GetHeaderInfo
()
203 if self
._Guid
== None:
204 EdkLogger
.error('build', ATTRIBUTE_NOT_AVAILABLE
, "No FILE_GUID", File
=self
.MetaFile
)
207 ## Retrieve platform version
208 def _GetVersion(self
):
209 if self
._Version
== None:
210 if self
._Header
== None:
211 self
._GetHeaderInfo
()
212 if self
._Version
== None:
216 ## Retrieve platform description file version
217 def _GetDscSpec(self
):
218 if self
._DscSpecification
== None:
219 if self
._Header
== None:
220 self
._GetHeaderInfo
()
221 if self
._DscSpecification
== None:
222 self
._DscSpecification
= ''
223 return self
._DscSpecification
225 ## Retrieve OUTPUT_DIRECTORY
226 def _GetOutpuDir(self
):
227 if self
._OutputDirectory
== None:
228 if self
._Header
== None:
229 self
._GetHeaderInfo
()
230 if self
._OutputDirectory
== None:
231 self
._OutputDirectory
= os
.path
.join("Build", self
._PlatformName
)
232 return self
._OutputDirectory
234 ## Retrieve SUPPORTED_ARCHITECTURES
235 def _GetSupArch(self
):
236 if self
._SupArchList
== None:
237 if self
._Header
== None:
238 self
._GetHeaderInfo
()
239 if self
._SupArchList
== None:
240 self
._SupArchList
= ARCH_LIST
241 return self
._SupArchList
243 ## Retrieve BUILD_TARGETS
244 def _GetBuildTarget(self
):
245 if self
._BuildTargets
== None:
246 if self
._Header
== None:
247 self
._GetHeaderInfo
()
248 if self
._BuildTargets
== None:
249 self
._BuildTargets
= ['DEBUG', 'RELEASE']
250 return self
._BuildTargets
252 ## Retrieve SKUID_IDENTIFIER
253 def _GetSkuName(self
):
254 if self
._SkuName
== None:
255 if self
._Header
== None:
256 self
._GetHeaderInfo
()
257 if self
._SkuName
== None or self
._SkuName
not in self
.SkuIds
:
258 self
._SkuName
= 'DEFAULT'
261 ## Override SKUID_IDENTIFIER
262 def _SetSkuName(self
, Value
):
263 if Value
in self
.SkuIds
:
264 self
._SkuName
= Value
266 def _GetFdfFile(self
):
267 if self
._FlashDefinition
== None:
268 if self
._Header
== None:
269 self
._GetHeaderInfo
()
270 if self
._FlashDefinition
== None:
271 self
._FlashDefinition
= ''
272 return self
._FlashDefinition
274 ## Retrieve FLASH_DEFINITION
275 def _GetBuildNumber(self
):
276 if self
._BuildNumber
== None:
277 if self
._Header
== None:
278 self
._GetHeaderInfo
()
279 if self
._BuildNumber
== None:
280 self
._BuildNumber
= ''
281 return self
._BuildNumber
283 ## Retrieve MAKEFILE_NAME
284 def _GetMakefileName(self
):
285 if self
._MakefileName
== None:
286 if self
._Header
== None:
287 self
._GetHeaderInfo
()
288 if self
._MakefileName
== None:
289 self
._MakefileName
= ''
290 return self
._MakefileName
292 ## Retrieve BsBaseAddress
293 def _GetBsBaseAddress(self
):
294 if self
._BsBaseAddress
== None:
295 if self
._Header
== None:
296 self
._GetHeaderInfo
()
297 if self
._BsBaseAddress
== None:
298 self
._BsBaseAddress
= ''
299 return self
._BsBaseAddress
301 ## Retrieve RtBaseAddress
302 def _GetRtBaseAddress(self
):
303 if self
._RtBaseAddress
== None:
304 if self
._Header
== None:
305 self
._GetHeaderInfo
()
306 if self
._RtBaseAddress
== None:
307 self
._RtBaseAddress
= ''
308 return self
._RtBaseAddress
310 ## Retrieve [SkuIds] section information
311 def _GetSkuIds(self
):
312 if self
._SkuIds
== None:
314 RecordList
= self
._RawData
[MODEL_EFI_SKU_ID
]
315 for Record
in RecordList
:
316 if Record
[0] in [None, '']:
317 EdkLogger
.error('build', FORMAT_INVALID
, 'No Sku ID number',
318 File
=self
.MetaFile
, Line
=Record
[-1])
319 if Record
[1] in [None, '']:
320 EdkLogger
.error('build', FORMAT_INVALID
, 'No Sku ID name',
321 File
=self
.MetaFile
, Line
=Record
[-1])
322 self
._SkuIds
[Record
[1]] = Record
[0]
323 if 'DEFAULT' not in self
._SkuIds
:
324 self
._SkuIds
['DEFAULT'] = 0
327 ## Retrieve [Components] section information
328 def _GetModules(self
):
329 if self
._Modules
!= None:
332 self
._Modules
= sdict()
333 RecordList
= self
._RawData
[MODEL_META_DATA_COMPONENT
, self
._Arch
]
334 Macros
= {"EDK_SOURCE":GlobalData
.gEcpSource
, "EFI_SOURCE":GlobalData
.gEfiSource
}
335 Macros
.update(self
._Macros
)
336 for Record
in RecordList
:
337 ModuleFile
= PathClass(NormPath(Record
[0], Macros
), GlobalData
.gWorkspace
, Arch
=self
._Arch
)
341 # check the file validation
342 ErrorCode
, ErrorInfo
= ModuleFile
.Validate('.inf')
344 EdkLogger
.error('build', ErrorCode
, File
=self
.MetaFile
, Line
=LineNo
,
347 if ModuleFile
in self
._Modules
:
348 EdkLogger
.error('build', FILE_DUPLICATED
, File
=self
.MetaFile
, ExtraData
=str(ModuleFile
), Line
=LineNo
)
350 Module
= ModuleBuildClassObject()
351 Module
.MetaFile
= ModuleFile
353 # get module override path
354 RecordList
= self
._RawData
[MODEL_META_DATA_COMPONENT_SOURCE_OVERRIDE_PATH
, self
._Arch
, None, ModuleId
]
356 Module
.SourceOverridePath
= os
.path
.join(GlobalData
.gWorkspace
, NormPath(RecordList
[0][0], Macros
))
358 # Check if the source override path exists
359 if not os
.path
.isdir(Module
.SourceOverridePath
):
360 EdkLogger
.error('build', FILE_NOT_FOUND
, Message
= 'Source override path does not exist:', File
=self
.MetaFile
, ExtraData
=Module
.SourceOverridePath
, Line
=LineNo
)
362 #Add to GlobalData Variables
363 GlobalData
.gOverrideDir
[ModuleFile
.Key
] = Module
.SourceOverridePath
365 # get module private library instance
366 RecordList
= self
._RawData
[MODEL_EFI_LIBRARY_CLASS
, self
._Arch
, None, ModuleId
]
367 for Record
in RecordList
:
368 LibraryClass
= Record
[0]
369 LibraryPath
= PathClass(NormPath(Record
[1], Macros
), GlobalData
.gWorkspace
, Arch
=self
._Arch
)
372 # check the file validation
373 ErrorCode
, ErrorInfo
= LibraryPath
.Validate('.inf')
375 EdkLogger
.error('build', ErrorCode
, File
=self
.MetaFile
, Line
=LineNo
,
378 if LibraryClass
== '' or LibraryClass
== 'NULL':
379 self
._NullLibraryNumber
+= 1
380 LibraryClass
= 'NULL%d' % self
._NullLibraryNumber
381 EdkLogger
.verbose("Found forced library for %s\n\t%s [%s]" % (ModuleFile
, LibraryPath
, LibraryClass
))
382 Module
.LibraryClasses
[LibraryClass
] = LibraryPath
383 if LibraryPath
not in self
.LibraryInstances
:
384 self
.LibraryInstances
.append(LibraryPath
)
386 # get module private PCD setting
387 for Type
in [MODEL_PCD_FIXED_AT_BUILD
, MODEL_PCD_PATCHABLE_IN_MODULE
, \
388 MODEL_PCD_FEATURE_FLAG
, MODEL_PCD_DYNAMIC
, MODEL_PCD_DYNAMIC_EX
]:
389 RecordList
= self
._RawData
[Type
, self
._Arch
, None, ModuleId
]
390 for TokenSpaceGuid
, PcdCName
, Setting
, Dummy1
, Dummy2
, Dummy3
, Dummy4
in RecordList
:
391 TokenList
= GetSplitValueList(Setting
)
392 DefaultValue
= TokenList
[0]
393 if len(TokenList
) > 1:
394 MaxDatumSize
= TokenList
[1]
397 TypeString
= self
._PCD
_TYPE
_STRING
_[Type
]
398 Pcd
= PcdClassObject(
409 Module
.Pcds
[PcdCName
, TokenSpaceGuid
] = Pcd
411 # get module private build options
412 RecordList
= self
._RawData
[MODEL_META_DATA_BUILD_OPTION
, self
._Arch
, None, ModuleId
]
413 for ToolChainFamily
, ToolChain
, Option
, Dummy1
, Dummy2
, Dummy3
, Dummy4
in RecordList
:
414 if (ToolChainFamily
, ToolChain
) not in Module
.BuildOptions
:
415 Module
.BuildOptions
[ToolChainFamily
, ToolChain
] = Option
417 OptionString
= Module
.BuildOptions
[ToolChainFamily
, ToolChain
]
418 Module
.BuildOptions
[ToolChainFamily
, ToolChain
] = OptionString
+ " " + Option
420 self
._Modules
[ModuleFile
] = Module
423 ## Retrieve all possible library instances used in this platform
424 def _GetLibraryInstances(self
):
425 if self
._LibraryInstances
== None:
426 self
._GetLibraryClasses
()
427 return self
._LibraryInstances
429 ## Retrieve [LibraryClasses] information
430 def _GetLibraryClasses(self
):
431 if self
._LibraryClasses
== None:
432 self
._LibraryInstances
= []
434 # tdict is a special dict kind of type, used for selecting correct
435 # library instance for given library class and module type
437 LibraryClassDict
= tdict(True, 3)
438 # track all library class names
439 LibraryClassSet
= set()
440 RecordList
= self
._RawData
[MODEL_EFI_LIBRARY_CLASS
, self
._Arch
]
441 Macros
= {"EDK_SOURCE":GlobalData
.gEcpSource
, "EFI_SOURCE":GlobalData
.gEfiSource
}
442 Macros
.update(self
._Macros
)
443 for Record
in RecordList
:
444 LibraryClass
, LibraryInstance
, Dummy
, Arch
, ModuleType
, Dummy
, LineNo
= Record
445 LibraryClassSet
.add(LibraryClass
)
446 LibraryInstance
= PathClass(NormPath(LibraryInstance
, Macros
), GlobalData
.gWorkspace
, Arch
=self
._Arch
)
447 # check the file validation
448 ErrorCode
, ErrorInfo
= LibraryInstance
.Validate('.inf')
450 EdkLogger
.error('build', ErrorCode
, File
=self
.MetaFile
, Line
=LineNo
,
453 if ModuleType
!= 'COMMON' and ModuleType
not in SUP_MODULE_LIST
:
454 EdkLogger
.error('build', OPTION_UNKNOWN
, "Unknown module type [%s]" % ModuleType
,
455 File
=self
.MetaFile
, ExtraData
=LibraryInstance
, Line
=LineNo
)
456 LibraryClassDict
[Arch
, ModuleType
, LibraryClass
] = LibraryInstance
457 if LibraryInstance
not in self
._LibraryInstances
:
458 self
._LibraryInstances
.append(LibraryInstance
)
460 # resolve the specific library instance for each class and each module type
461 self
._LibraryClasses
= tdict(True)
462 for LibraryClass
in LibraryClassSet
:
463 # try all possible module types
464 for ModuleType
in SUP_MODULE_LIST
:
465 LibraryInstance
= LibraryClassDict
[self
._Arch
, ModuleType
, LibraryClass
]
466 if LibraryInstance
== None:
468 self
._LibraryClasses
[LibraryClass
, ModuleType
] = LibraryInstance
470 # for R8 style library instances, which are listed in different section
471 RecordList
= self
._RawData
[MODEL_EFI_LIBRARY_INSTANCE
, self
._Arch
]
472 for Record
in RecordList
:
473 File
= PathClass(NormPath(Record
[0], Macros
), GlobalData
.gWorkspace
, Arch
=self
._Arch
)
475 # check the file validation
476 ErrorCode
, ErrorInfo
= File
.Validate('.inf')
478 EdkLogger
.error('build', ErrorCode
, File
=self
.MetaFile
, Line
=LineNo
,
480 if File
not in self
._LibraryInstances
:
481 self
._LibraryInstances
.append(File
)
483 # we need the module name as the library class name, so we have
484 # to parse it here. (self._Bdb[] will trigger a file parse if it
485 # hasn't been parsed)
487 Library
= self
._Bdb
[File
, self
._Arch
]
488 self
._LibraryClasses
[Library
.BaseName
, ':dummy:'] = Library
489 return self
._LibraryClasses
491 ## Retrieve all PCD settings in platform
493 if self
._Pcds
== None:
495 self
._Pcds
.update(self
._GetPcd
(MODEL_PCD_FIXED_AT_BUILD
))
496 self
._Pcds
.update(self
._GetPcd
(MODEL_PCD_PATCHABLE_IN_MODULE
))
497 self
._Pcds
.update(self
._GetPcd
(MODEL_PCD_FEATURE_FLAG
))
498 self
._Pcds
.update(self
._GetDynamicPcd
(MODEL_PCD_DYNAMIC_DEFAULT
))
499 self
._Pcds
.update(self
._GetDynamicHiiPcd
(MODEL_PCD_DYNAMIC_HII
))
500 self
._Pcds
.update(self
._GetDynamicVpdPcd
(MODEL_PCD_DYNAMIC_VPD
))
501 self
._Pcds
.update(self
._GetDynamicPcd
(MODEL_PCD_DYNAMIC_EX_DEFAULT
))
502 self
._Pcds
.update(self
._GetDynamicHiiPcd
(MODEL_PCD_DYNAMIC_EX_HII
))
503 self
._Pcds
.update(self
._GetDynamicVpdPcd
(MODEL_PCD_DYNAMIC_EX_VPD
))
506 ## Retrieve [BuildOptions]
507 def _GetBuildOptions(self
):
508 if self
._BuildOptions
== None:
509 self
._BuildOptions
= {}
510 RecordList
= self
._RawData
[MODEL_META_DATA_BUILD_OPTION
]
511 for ToolChainFamily
, ToolChain
, Option
, Dummy1
, Dummy2
, Dummy3
, Dummy4
in RecordList
:
512 self
._BuildOptions
[ToolChainFamily
, ToolChain
] = Option
513 return self
._BuildOptions
515 ## Retrieve non-dynamic PCD settings
517 # @param Type PCD type
519 # @retval a dict object contains settings of given PCD type
521 def _GetPcd(self
, Type
):
524 # tdict is a special dict kind of type, used for selecting correct
525 # PCD settings for certain ARCH
527 PcdDict
= tdict(True, 3)
529 # Find out all possible PCD candidates for self._Arch
530 RecordList
= self
._RawData
[Type
, self
._Arch
]
531 for TokenSpaceGuid
, PcdCName
, Setting
, Arch
, SkuName
, Dummy3
, Dummy4
in RecordList
:
532 PcdSet
.add((PcdCName
, TokenSpaceGuid
))
533 PcdDict
[Arch
, PcdCName
, TokenSpaceGuid
] = Setting
534 # Remove redundant PCD candidates
535 for PcdCName
, TokenSpaceGuid
in PcdSet
:
536 ValueList
= ['', '', '']
537 Setting
= PcdDict
[self
._Arch
, PcdCName
, TokenSpaceGuid
]
540 TokenList
= Setting
.split(TAB_VALUE_SPLIT
)
541 ValueList
[0:len(TokenList
)] = TokenList
542 PcdValue
, DatumType
, MaxDatumSize
= ValueList
543 Pcds
[PcdCName
, TokenSpaceGuid
] = PcdClassObject(
546 self
._PCD
_TYPE
_STRING
_[Type
],
556 ## Retrieve dynamic PCD settings
558 # @param Type PCD type
560 # @retval a dict object contains settings of given PCD type
562 def _GetDynamicPcd(self
, Type
):
565 # tdict is a special dict kind of type, used for selecting correct
566 # PCD settings for certain ARCH and SKU
568 PcdDict
= tdict(True, 4)
570 # Find out all possible PCD candidates for self._Arch
571 RecordList
= self
._RawData
[Type
, self
._Arch
]
572 for TokenSpaceGuid
, PcdCName
, Setting
, Arch
, SkuName
, Dummy3
, Dummy4
in RecordList
:
573 PcdSet
.add((PcdCName
, TokenSpaceGuid
))
574 PcdDict
[Arch
, SkuName
, PcdCName
, TokenSpaceGuid
] = Setting
575 # Remove redundant PCD candidates, per the ARCH and SKU
576 for PcdCName
, TokenSpaceGuid
in PcdSet
:
577 ValueList
= ['', '', '']
578 Setting
= PcdDict
[self
._Arch
, self
.SkuName
, PcdCName
, TokenSpaceGuid
]
581 TokenList
= Setting
.split(TAB_VALUE_SPLIT
)
582 ValueList
[0:len(TokenList
)] = TokenList
583 PcdValue
, DatumType
, MaxDatumSize
= ValueList
585 SkuInfo
= SkuInfoClass(self
.SkuName
, self
.SkuIds
[self
.SkuName
], '', '', '', '', '', PcdValue
)
586 Pcds
[PcdCName
, TokenSpaceGuid
] = PcdClassObject(
589 self
._PCD
_TYPE
_STRING
_[Type
],
594 {self
.SkuName
: SkuInfo
},
599 ## Retrieve dynamic HII PCD settings
601 # @param Type PCD type
603 # @retval a dict object contains settings of given PCD type
605 def _GetDynamicHiiPcd(self
, Type
):
608 # tdict is a special dict kind of type, used for selecting correct
609 # PCD settings for certain ARCH and SKU
611 PcdDict
= tdict(True, 4)
613 RecordList
= self
._RawData
[Type
, self
._Arch
]
614 # Find out all possible PCD candidates for self._Arch
615 for TokenSpaceGuid
, PcdCName
, Setting
, Arch
, SkuName
, Dummy3
, Dummy4
in RecordList
:
616 PcdSet
.add((PcdCName
, TokenSpaceGuid
))
617 PcdDict
[Arch
, SkuName
, PcdCName
, TokenSpaceGuid
] = Setting
618 # Remove redundant PCD candidates, per the ARCH and SKU
619 for PcdCName
, TokenSpaceGuid
in PcdSet
:
620 ValueList
= ['', '', '', '']
621 Setting
= PcdDict
[self
._Arch
, self
.SkuName
, PcdCName
, TokenSpaceGuid
]
624 TokenList
= Setting
.split(TAB_VALUE_SPLIT
)
625 ValueList
[0:len(TokenList
)] = TokenList
626 VariableName
, VariableGuid
, VariableOffset
, DefaultValue
= ValueList
627 SkuInfo
= SkuInfoClass(self
.SkuName
, self
.SkuIds
[self
.SkuName
], VariableName
, VariableGuid
, VariableOffset
, DefaultValue
)
628 Pcds
[PcdCName
, TokenSpaceGuid
] = PcdClassObject(
631 self
._PCD
_TYPE
_STRING
_[Type
],
636 {self
.SkuName
: SkuInfo
},
641 ## Retrieve dynamic VPD PCD settings
643 # @param Type PCD type
645 # @retval a dict object contains settings of given PCD type
647 def _GetDynamicVpdPcd(self
, Type
):
650 # tdict is a special dict kind of type, used for selecting correct
651 # PCD settings for certain ARCH and SKU
653 PcdDict
= tdict(True, 4)
655 # Find out all possible PCD candidates for self._Arch
656 RecordList
= self
._RawData
[Type
, self
._Arch
]
657 for TokenSpaceGuid
, PcdCName
, Setting
, Arch
, SkuName
, Dummy3
, Dummy4
in RecordList
:
658 PcdSet
.add((PcdCName
, TokenSpaceGuid
))
659 PcdDict
[Arch
, SkuName
, PcdCName
, TokenSpaceGuid
] = Setting
660 # Remove redundant PCD candidates, per the ARCH and SKU
661 for PcdCName
, TokenSpaceGuid
in PcdSet
:
663 Setting
= PcdDict
[self
._Arch
, self
.SkuName
, PcdCName
, TokenSpaceGuid
]
666 TokenList
= Setting
.split(TAB_VALUE_SPLIT
)
667 ValueList
[0:len(TokenList
)] = TokenList
668 VpdOffset
, MaxDatumSize
= ValueList
670 SkuInfo
= SkuInfoClass(self
.SkuName
, self
.SkuIds
[self
.SkuName
], '', '', '', '', VpdOffset
)
671 Pcds
[PcdCName
, TokenSpaceGuid
] = PcdClassObject(
674 self
._PCD
_TYPE
_STRING
_[Type
],
679 {self
.SkuName
: SkuInfo
},
684 ## Add external modules
686 # The external modules are mostly those listed in FDF file, which don't
689 # @param FilePath The path of module description file
691 def AddModule(self
, FilePath
):
692 FilePath
= NormPath(FilePath
)
693 if FilePath
not in self
.Modules
:
694 Module
= ModuleBuildClassObject()
695 Module
.MetaFile
= FilePath
696 self
.Modules
.append(Module
)
700 # The external PCDs are mostly those listed in FDF file to specify address
701 # or offset information.
703 # @param Name Name of the PCD
704 # @param Guid Token space guid of the PCD
705 # @param Value Value of the PCD
707 def AddPcd(self
, Name
, Guid
, Value
):
708 if (Name
, Guid
) not in self
.Pcds
:
709 self
.Pcds
[Name
, Guid
] = PcdClassObject(Name
, Guid
, '', '', '', '', '', {}, None)
710 self
.Pcds
[Name
, Guid
].DefaultValue
= Value
712 Arch
= property(_GetArch
, _SetArch
)
713 Platform
= property(_GetPlatformName
)
714 PlatformName
= property(_GetPlatformName
)
715 Guid
= property(_GetFileGuid
)
716 Version
= property(_GetVersion
)
717 DscSpecification
= property(_GetDscSpec
)
718 OutputDirectory
= property(_GetOutpuDir
)
719 SupArchList
= property(_GetSupArch
)
720 BuildTargets
= property(_GetBuildTarget
)
721 SkuName
= property(_GetSkuName
, _SetSkuName
)
722 FlashDefinition
= property(_GetFdfFile
)
723 BuildNumber
= property(_GetBuildNumber
)
724 MakefileName
= property(_GetMakefileName
)
725 BsBaseAddress
= property(_GetBsBaseAddress
)
726 RtBaseAddress
= property(_GetRtBaseAddress
)
728 SkuIds
= property(_GetSkuIds
)
729 Modules
= property(_GetModules
)
730 LibraryInstances
= property(_GetLibraryInstances
)
731 LibraryClasses
= property(_GetLibraryClasses
)
732 Pcds
= property(_GetPcds
)
733 BuildOptions
= property(_GetBuildOptions
)
735 ## Platform build information from DSC file
737 # This class is used to retrieve information stored in database and convert them
738 # into PackageBuildClassObject form for easier use for AutoGen.
740 class DecBuildData(PackageBuildClassObject
):
741 # dict used to convert PCD type in database to string used by build tool
742 _PCD_TYPE_STRING_
= {
743 MODEL_PCD_FIXED_AT_BUILD
: "FixedAtBuild",
744 MODEL_PCD_PATCHABLE_IN_MODULE
: "PatchableInModule",
745 MODEL_PCD_FEATURE_FLAG
: "FeatureFlag",
746 MODEL_PCD_DYNAMIC
: "Dynamic",
747 MODEL_PCD_DYNAMIC_DEFAULT
: "Dynamic",
748 MODEL_PCD_DYNAMIC_HII
: "DynamicHii",
749 MODEL_PCD_DYNAMIC_VPD
: "DynamicVpd",
750 MODEL_PCD_DYNAMIC_EX
: "DynamicEx",
751 MODEL_PCD_DYNAMIC_EX_DEFAULT
: "DynamicEx",
752 MODEL_PCD_DYNAMIC_EX_HII
: "DynamicExHii",
753 MODEL_PCD_DYNAMIC_EX_VPD
: "DynamicExVpd",
756 # dict used to convert part of [Defines] to members of DecBuildData directly
761 TAB_DEC_DEFINES_PACKAGE_NAME
: "_PackageName",
762 TAB_DEC_DEFINES_PACKAGE_GUID
: "_Guid",
763 TAB_DEC_DEFINES_PACKAGE_VERSION
: "_Version",
767 ## Constructor of DecBuildData
769 # Initialize object of DecBuildData
771 # @param FilePath The path of package description file
772 # @param RawData The raw data of DEC file
773 # @param BuildDataBase Database used to retrieve module information
774 # @param Arch The target architecture
775 # @param Platform (not used for DecBuildData)
776 # @param Macros Macros used for replacement in DSC file
778 def __init__(self
, File
, RawData
, BuildDataBase
, Arch
='COMMON', Platform
='DUMMY', Macros
={}):
780 self
._PackageDir
= File
.Dir
781 self
._RawData
= RawData
782 self
._Bdb
= BuildDataBase
784 self
._Macros
= Macros
788 def __setitem__(self
, key
, value
):
789 self
.__dict
__[self
._PROPERTY
_[key
]] = value
792 def __getitem__(self
, key
):
793 return self
.__dict
__[self
._PROPERTY
_[key
]]
796 def __contains__(self
, key
):
797 return key
in self
._PROPERTY
_
799 ## Set all internal used members of DecBuildData to None
802 self
._PackageName
= None
805 self
._Protocols
= None
808 self
._Includes
= None
809 self
._LibraryClasses
= None
818 # Changing the default ARCH to another may affect all other information
819 # because all information in a platform may be ARCH-related. That's
820 # why we need to clear all internal used members, in order to cause all
821 # information to be re-retrieved.
823 # @param Value The value of ARCH
825 def _SetArch(self
, Value
):
826 if self
._Arch
== Value
:
831 ## Retrieve all information in [Defines] section
833 # (Retriving all [Defines] information in one-shot is just to save time.)
835 def _GetHeaderInfo(self
):
836 RecordList
= self
._RawData
[MODEL_META_DATA_HEADER
]
837 for Record
in RecordList
:
840 self
[Name
] = Record
[1]
841 self
._Header
= 'DUMMY'
843 ## Retrieve package name
844 def _GetPackageName(self
):
845 if self
._PackageName
== None:
846 if self
._Header
== None:
847 self
._GetHeaderInfo
()
848 if self
._PackageName
== None:
849 EdkLogger
.error("build", ATTRIBUTE_NOT_AVAILABLE
, "No PACKAGE_NAME", File
=self
.MetaFile
)
850 return self
._PackageName
852 ## Retrieve file guid
853 def _GetFileGuid(self
):
854 if self
._Guid
== None:
855 if self
._Header
== None:
856 self
._GetHeaderInfo
()
857 if self
._Guid
== None:
858 EdkLogger
.error("build", ATTRIBUTE_NOT_AVAILABLE
, "No PACKAGE_GUID", File
=self
.MetaFile
)
861 ## Retrieve package version
862 def _GetVersion(self
):
863 if self
._Version
== None:
864 if self
._Header
== None:
865 self
._GetHeaderInfo
()
866 if self
._Version
== None:
870 ## Retrieve protocol definitions (name/value pairs)
871 def _GetProtocol(self
):
872 if self
._Protocols
== None:
874 # tdict is a special kind of dict, used for selecting correct
875 # protocol defition for given ARCH
877 ProtocolDict
= tdict(True)
879 # find out all protocol definitions for specific and 'common' arch
880 RecordList
= self
._RawData
[MODEL_EFI_PROTOCOL
, self
._Arch
]
881 for Name
, Guid
, Dummy
, Arch
, ID
, LineNo
in RecordList
:
882 if Name
not in NameList
:
883 NameList
.append(Name
)
884 ProtocolDict
[Arch
, Name
] = Guid
885 # use sdict to keep the order
886 self
._Protocols
= sdict()
887 for Name
in NameList
:
889 # limit the ARCH to self._Arch, if no self._Arch found, tdict
890 # will automatically turn to 'common' ARCH for trying
892 self
._Protocols
[Name
] = ProtocolDict
[self
._Arch
, Name
]
893 return self
._Protocols
895 ## Retrieve PPI definitions (name/value pairs)
897 if self
._Ppis
== None:
899 # tdict is a special kind of dict, used for selecting correct
900 # PPI defition for given ARCH
902 PpiDict
= tdict(True)
904 # find out all PPI definitions for specific arch and 'common' arch
905 RecordList
= self
._RawData
[MODEL_EFI_PPI
, self
._Arch
]
906 for Name
, Guid
, Dummy
, Arch
, ID
, LineNo
in RecordList
:
907 if Name
not in NameList
:
908 NameList
.append(Name
)
909 PpiDict
[Arch
, Name
] = Guid
910 # use sdict to keep the order
912 for Name
in NameList
:
914 # limit the ARCH to self._Arch, if no self._Arch found, tdict
915 # will automatically turn to 'common' ARCH for trying
917 self
._Ppis
[Name
] = PpiDict
[self
._Arch
, Name
]
920 ## Retrieve GUID definitions (name/value pairs)
922 if self
._Guids
== None:
924 # tdict is a special kind of dict, used for selecting correct
925 # GUID defition for given ARCH
927 GuidDict
= tdict(True)
929 # find out all protocol definitions for specific and 'common' arch
930 RecordList
= self
._RawData
[MODEL_EFI_GUID
, self
._Arch
]
931 for Name
, Guid
, Dummy
, Arch
, ID
, LineNo
in RecordList
:
932 if Name
not in NameList
:
933 NameList
.append(Name
)
934 GuidDict
[Arch
, Name
] = Guid
935 # use sdict to keep the order
936 self
._Guids
= sdict()
937 for Name
in NameList
:
939 # limit the ARCH to self._Arch, if no self._Arch found, tdict
940 # will automatically turn to 'common' ARCH for trying
942 self
._Guids
[Name
] = GuidDict
[self
._Arch
, Name
]
945 ## Retrieve public include paths declared in this package
946 def _GetInclude(self
):
947 if self
._Includes
== None:
949 RecordList
= self
._RawData
[MODEL_EFI_INCLUDE
, self
._Arch
]
950 Macros
= {"EDK_SOURCE":GlobalData
.gEcpSource
, "EFI_SOURCE":GlobalData
.gEfiSource
}
951 Macros
.update(self
._Macros
)
952 for Record
in RecordList
:
953 File
= PathClass(NormPath(Record
[0], Macros
), self
._PackageDir
, Arch
=self
._Arch
)
956 ErrorCode
, ErrorInfo
= File
.Validate()
958 EdkLogger
.error('build', ErrorCode
, ExtraData
=ErrorInfo
, File
=self
.MetaFile
, Line
=LineNo
)
960 # avoid duplicate include path
961 if File
not in self
._Includes
:
962 self
._Includes
.append(File
)
963 return self
._Includes
965 ## Retrieve library class declarations (not used in build at present)
966 def _GetLibraryClass(self
):
967 if self
._LibraryClasses
== None:
969 # tdict is a special kind of dict, used for selecting correct
970 # library class declaration for given ARCH
972 LibraryClassDict
= tdict(True)
973 LibraryClassSet
= set()
974 RecordList
= self
._RawData
[MODEL_EFI_LIBRARY_CLASS
, self
._Arch
]
975 Macros
= {"EDK_SOURCE":GlobalData
.gEcpSource
, "EFI_SOURCE":GlobalData
.gEfiSource
}
976 Macros
.update(self
._Macros
)
977 for LibraryClass
, File
, Dummy
, Arch
, ID
, LineNo
in RecordList
:
978 File
= PathClass(NormPath(File
, Macros
), self
._PackageDir
, Arch
=self
._Arch
)
979 # check the file validation
980 ErrorCode
, ErrorInfo
= File
.Validate()
982 EdkLogger
.error('build', ErrorCode
, ExtraData
=ErrorInfo
, File
=self
.MetaFile
, Line
=LineNo
)
983 LibraryClassSet
.add(LibraryClass
)
984 LibraryClassDict
[Arch
, LibraryClass
] = File
985 self
._LibraryClasses
= sdict()
986 for LibraryClass
in LibraryClassSet
:
987 self
._LibraryClasses
[LibraryClass
] = LibraryClassDict
[self
._Arch
, LibraryClass
]
988 return self
._LibraryClasses
990 ## Retrieve PCD declarations
992 if self
._Pcds
== None:
994 self
._Pcds
.update(self
._GetPcd
(MODEL_PCD_FIXED_AT_BUILD
))
995 self
._Pcds
.update(self
._GetPcd
(MODEL_PCD_PATCHABLE_IN_MODULE
))
996 self
._Pcds
.update(self
._GetPcd
(MODEL_PCD_FEATURE_FLAG
))
997 self
._Pcds
.update(self
._GetPcd
(MODEL_PCD_DYNAMIC
))
998 self
._Pcds
.update(self
._GetPcd
(MODEL_PCD_DYNAMIC_EX
))
1001 ## Retrieve PCD declarations for given type
1002 def _GetPcd(self
, Type
):
1005 # tdict is a special kind of dict, used for selecting correct
1006 # PCD declaration for given ARCH
1008 PcdDict
= tdict(True, 3)
1009 # for summarizing PCD
1011 # find out all PCDs of the 'type'
1012 RecordList
= self
._RawData
[Type
, self
._Arch
]
1013 for TokenSpaceGuid
, PcdCName
, Setting
, Arch
, Dummy1
, Dummy2
in RecordList
:
1014 PcdDict
[Arch
, PcdCName
, TokenSpaceGuid
] = Setting
1015 PcdSet
.add((PcdCName
, TokenSpaceGuid
))
1017 for PcdCName
, TokenSpaceGuid
in PcdSet
:
1018 ValueList
= ['', '', '']
1020 # limit the ARCH to self._Arch, if no self._Arch found, tdict
1021 # will automatically turn to 'common' ARCH and try again
1023 Setting
= PcdDict
[self
._Arch
, PcdCName
, TokenSpaceGuid
]
1026 TokenList
= Setting
.split(TAB_VALUE_SPLIT
)
1027 ValueList
[0:len(TokenList
)] = TokenList
1028 DefaultValue
, DatumType
, TokenNumber
= ValueList
1029 Pcds
[PcdCName
, TokenSpaceGuid
, self
._PCD
_TYPE
_STRING
_[Type
]] = PcdClassObject(
1032 self
._PCD
_TYPE
_STRING
_[Type
],
1043 Arch
= property(_GetArch
, _SetArch
)
1044 PackageName
= property(_GetPackageName
)
1045 Guid
= property(_GetFileGuid
)
1046 Version
= property(_GetVersion
)
1048 Protocols
= property(_GetProtocol
)
1049 Ppis
= property(_GetPpi
)
1050 Guids
= property(_GetGuid
)
1051 Includes
= property(_GetInclude
)
1052 LibraryClasses
= property(_GetLibraryClass
)
1053 Pcds
= property(_GetPcds
)
1055 ## Module build information from INF file
1057 # This class is used to retrieve information stored in database and convert them
1058 # into ModuleBuildClassObject form for easier use for AutoGen.
1060 class InfBuildData(ModuleBuildClassObject
):
1061 # dict used to convert PCD type in database to string used by build tool
1062 _PCD_TYPE_STRING_
= {
1063 MODEL_PCD_FIXED_AT_BUILD
: "FixedAtBuild",
1064 MODEL_PCD_PATCHABLE_IN_MODULE
: "PatchableInModule",
1065 MODEL_PCD_FEATURE_FLAG
: "FeatureFlag",
1066 MODEL_PCD_DYNAMIC
: "Dynamic",
1067 MODEL_PCD_DYNAMIC_DEFAULT
: "Dynamic",
1068 MODEL_PCD_DYNAMIC_HII
: "DynamicHii",
1069 MODEL_PCD_DYNAMIC_VPD
: "DynamicVpd",
1070 MODEL_PCD_DYNAMIC_EX
: "DynamicEx",
1071 MODEL_PCD_DYNAMIC_EX_DEFAULT
: "DynamicEx",
1072 MODEL_PCD_DYNAMIC_EX_HII
: "DynamicExHii",
1073 MODEL_PCD_DYNAMIC_EX_VPD
: "DynamicExVpd",
1076 # dict used to convert part of [Defines] to members of InfBuildData directly
1081 TAB_INF_DEFINES_BASE_NAME
: "_BaseName",
1082 TAB_INF_DEFINES_FILE_GUID
: "_Guid",
1083 TAB_INF_DEFINES_MODULE_TYPE
: "_ModuleType",
1087 TAB_INF_DEFINES_INF_VERSION
: "_AutoGenVersion",
1088 TAB_INF_DEFINES_COMPONENT_TYPE
: "_ComponentType",
1089 TAB_INF_DEFINES_MAKEFILE_NAME
: "_MakefileName",
1090 #TAB_INF_DEFINES_CUSTOM_MAKEFILE : "_CustomMakefile",
1091 TAB_INF_DEFINES_VERSION_NUMBER
: "_Version",
1092 TAB_INF_DEFINES_VERSION_STRING
: "_Version",
1093 TAB_INF_DEFINES_VERSION
: "_Version",
1094 TAB_INF_DEFINES_PCD_IS_DRIVER
: "_PcdIsDriver",
1095 TAB_INF_DEFINES_SHADOW
: "_Shadow",
1097 TAB_COMPONENTS_SOURCE_OVERRIDE_PATH
: "_SourceOverridePath",
1100 # dict used to convert Component type to Module type
1103 "SECURITY_CORE" : "SEC",
1104 "PEI_CORE" : "PEI_CORE",
1105 "COMBINED_PEIM_DRIVER" : "PEIM",
1106 "PIC_PEIM" : "PEIM",
1107 "RELOCATABLE_PEIM" : "PEIM",
1108 "PE32_PEIM" : "PEIM",
1109 "BS_DRIVER" : "DXE_DRIVER",
1110 "RT_DRIVER" : "DXE_RUNTIME_DRIVER",
1111 "SAL_RT_DRIVER" : "DXE_SAL_DRIVER",
1112 # "BS_DRIVER" : "DXE_SMM_DRIVER",
1113 # "BS_DRIVER" : "UEFI_DRIVER",
1114 "APPLICATION" : "UEFI_APPLICATION",
1118 # regular expression for converting XXX_FLAGS in [nmake] section to new type
1119 _NMAKE_FLAG_PATTERN_
= re
.compile("(?:EBC_)?([A-Z]+)_(?:STD_|PROJ_|ARCH_)?FLAGS(?:_DLL|_ASL|_EXE)?", re
.UNICODE
)
1120 # dict used to convert old tool name used in [nmake] section to new ones
1128 ## Constructor of DscBuildData
1130 # Initialize object of DscBuildData
1132 # @param FilePath The path of platform description file
1133 # @param RawData The raw data of DSC file
1134 # @param BuildDataBase Database used to retrieve module/package information
1135 # @param Arch The target architecture
1136 # @param Platform The name of platform employing this module
1137 # @param Macros Macros used for replacement in DSC file
1139 def __init__(self
, FilePath
, RawData
, BuildDatabase
, Arch
='COMMON', Platform
='COMMON', Macros
={}):
1140 self
.MetaFile
= FilePath
1141 self
._ModuleDir
= FilePath
.Dir
1142 self
._RawData
= RawData
1143 self
._Bdb
= BuildDatabase
1145 self
._Platform
= 'COMMON'
1146 self
._Macros
= Macros
1147 self
._SourceOverridePath
= None
1148 if FilePath
.Key
in GlobalData
.gOverrideDir
:
1149 self
._SourceOverridePath
= GlobalData
.gOverrideDir
[FilePath
.Key
]
1153 def __setitem__(self
, key
, value
):
1154 self
.__dict
__[self
._PROPERTY
_[key
]] = value
1157 def __getitem__(self
, key
):
1158 return self
.__dict
__[self
._PROPERTY
_[key
]]
1160 ## "in" test support
1161 def __contains__(self
, key
):
1162 return key
in self
._PROPERTY
_
1164 ## Set all internal used members of InfBuildData to None
1166 self
._Header
_ = None
1167 self
._AutoGenVersion
= None
1168 self
._BaseName
= None
1169 self
._ModuleType
= None
1170 self
._ComponentType
= None
1171 self
._BuildType
= None
1173 self
._Version
= None
1174 self
._PcdIsDriver
= None
1175 self
._BinaryModule
= None
1177 self
._MakefileName
= None
1178 self
._CustomMakefile
= None
1179 self
._Specification
= None
1180 self
._LibraryClass
= None
1181 self
._ModuleEntryPointList
= None
1182 self
._ModuleUnloadImageList
= None
1183 self
._ConstructorList
= None
1184 self
._DestructorList
= None
1186 self
._Binaries
= None
1187 self
._Sources
= None
1188 self
._LibraryClasses
= None
1189 self
._Libraries
= None
1190 self
._Protocols
= None
1193 self
._Includes
= None
1194 self
._Packages
= None
1196 self
._BuildOptions
= None
1198 #self._SourceOverridePath = None
1206 # Changing the default ARCH to another may affect all other information
1207 # because all information in a platform may be ARCH-related. That's
1208 # why we need to clear all internal used members, in order to cause all
1209 # information to be re-retrieved.
1211 # @param Value The value of ARCH
1213 def _SetArch(self
, Value
):
1214 if self
._Arch
== Value
:
1219 ## Return the name of platform employing this module
1220 def _GetPlatform(self
):
1221 return self
._Platform
1223 ## Change the name of platform employing this module
1225 # Changing the default name of platform to another may affect some information
1226 # because they may be PLATFORM-related. That's why we need to clear all internal
1227 # used members, in order to cause all information to be re-retrieved.
1229 def _SetPlatform(self
, Value
):
1230 if self
._Platform
== Value
:
1232 self
._Platform
= Value
1235 ## Retrieve all information in [Defines] section
1237 # (Retriving all [Defines] information in one-shot is just to save time.)
1239 def _GetHeaderInfo(self
):
1240 RecordList
= self
._RawData
[MODEL_META_DATA_HEADER
, self
._Arch
, self
._Platform
]
1241 for Record
in RecordList
:
1242 Record
= ReplaceMacros(Record
, GlobalData
.gEdkGlobal
, False)
1244 # items defined _PROPERTY_ don't need additional processing
1246 self
[Name
] = Record
[1]
1247 # some special items in [Defines] section need special treatment
1248 elif Name
== 'EFI_SPECIFICATION_VERSION':
1249 if self
._Specification
== None:
1250 self
._Specification
= sdict()
1251 self
._Specification
[Name
] = Record
[1]
1252 elif Name
== 'EDK_RELEASE_VERSION':
1253 if self
._Specification
== None:
1254 self
._Specification
= sdict()
1255 self
._Specification
[Name
] = Record
[1]
1256 elif Name
== 'PI_SPECIFICATION_VERSION':
1257 if self
._Specification
== None:
1258 self
._Specification
= sdict()
1259 self
._Specification
[Name
] = Record
[1]
1260 elif Name
== 'LIBRARY_CLASS':
1261 if self
._LibraryClass
== None:
1262 self
._LibraryClass
= []
1263 ValueList
= GetSplitValueList(Record
[1])
1264 LibraryClass
= ValueList
[0]
1265 if len(ValueList
) > 1:
1266 SupModuleList
= GetSplitValueList(ValueList
[1], ' ')
1268 SupModuleList
= SUP_MODULE_LIST
1269 self
._LibraryClass
.append(LibraryClassObject(LibraryClass
, SupModuleList
))
1270 elif Name
== 'ENTRY_POINT':
1271 if self
._ModuleEntryPointList
== None:
1272 self
._ModuleEntryPointList
= []
1273 self
._ModuleEntryPointList
.append(Record
[1])
1274 elif Name
== 'UNLOAD_IMAGE':
1275 if self
._ModuleUnloadImageList
== None:
1276 self
._ModuleUnloadImageList
= []
1279 self
._ModuleUnloadImageList
.append(Record
[1])
1280 elif Name
== 'CONSTRUCTOR':
1281 if self
._ConstructorList
== None:
1282 self
._ConstructorList
= []
1285 self
._ConstructorList
.append(Record
[1])
1286 elif Name
== 'DESTRUCTOR':
1287 if self
._DestructorList
== None:
1288 self
._DestructorList
= []
1291 self
._DestructorList
.append(Record
[1])
1292 elif Name
== TAB_INF_DEFINES_CUSTOM_MAKEFILE
:
1293 TokenList
= GetSplitValueList(Record
[1])
1294 if self
._CustomMakefile
== None:
1295 self
._CustomMakefile
= {}
1296 if len(TokenList
) < 2:
1297 self
._CustomMakefile
['MSFT'] = TokenList
[0]
1298 self
._CustomMakefile
['GCC'] = TokenList
[0]
1300 if TokenList
[0] not in ['MSFT', 'GCC']:
1301 EdkLogger
.error("build", FORMAT_NOT_SUPPORTED
,
1302 "No supported family [%s]" % TokenList
[0],
1303 File
=self
.MetaFile
, Line
=Record
[-1])
1304 self
._CustomMakefile
[TokenList
[0]] = TokenList
[1]
1306 if self
._Defs
== None:
1307 self
._Defs
= sdict()
1308 self
._Defs
[Name
] = Record
[1]
1311 # Retrieve information in sections specific to R8.x modules
1313 if self
._AutoGenVersion
>= 0x00010005: # _AutoGenVersion may be None, which is less than anything
1314 if not self
._ModuleType
:
1315 EdkLogger
.error("build", ATTRIBUTE_NOT_AVAILABLE
,
1316 "MODULE_TYPE is not given", File
=self
.MetaFile
)
1317 if self
._Defs
and 'PCI_DEVICE_ID' in self
._Defs
and 'PCI_VENDOR_ID' in self
._Defs \
1318 and 'PCI_CLASS_CODE' in self
._Defs
:
1319 self
._BuildType
= 'UEFI_OPTIONROM'
1321 self
._BuildType
= self
._ModuleType
.upper()
1323 self
._BuildType
= self
._ComponentType
.upper()
1324 if not self
._ComponentType
:
1325 EdkLogger
.error("build", ATTRIBUTE_NOT_AVAILABLE
,
1326 "COMPONENT_TYPE is not given", File
=self
.MetaFile
)
1327 if self
._ComponentType
in self
._MODULE
_TYPE
_:
1328 self
._ModuleType
= self
._MODULE
_TYPE
_[self
._ComponentType
]
1329 if self
._ComponentType
== 'LIBRARY':
1330 self
._LibraryClass
= [LibraryClassObject(self
._BaseName
, SUP_MODULE_LIST
)]
1331 # make use some [nmake] section macros
1332 RecordList
= self
._RawData
[MODEL_META_DATA_NMAKE
, self
._Arch
, self
._Platform
]
1333 for Name
,Value
,Dummy
,Arch
,Platform
,ID
,LineNo
in RecordList
:
1334 Value
= Value
.replace('$(PROCESSOR)', self
._Arch
)
1335 Name
= Name
.replace('$(PROCESSOR)', self
._Arch
)
1336 Name
, Value
= ReplaceMacros((Name
, Value
), GlobalData
.gEdkGlobal
, True)
1337 if Name
== "IMAGE_ENTRY_POINT":
1338 if self
._ModuleEntryPointList
== None:
1339 self
._ModuleEntryPointList
= []
1340 self
._ModuleEntryPointList
.append(Value
)
1341 elif Name
== "DPX_SOURCE":
1342 Macros
= {"EDK_SOURCE":GlobalData
.gEcpSource
, "EFI_SOURCE":GlobalData
.gEfiSource
}
1343 Macros
.update(self
._Macros
)
1344 File
= PathClass(NormPath(Value
, Macros
), self
._ModuleDir
, Arch
=self
._Arch
)
1345 # check the file validation
1346 ErrorCode
, ErrorInfo
= File
.Validate(".dxs", CaseSensitive
=False)
1348 EdkLogger
.error('build', ErrorCode
, ExtraData
=ErrorInfo
,
1349 File
=self
.MetaFile
, Line
=LineNo
)
1350 if self
.Sources
== None:
1352 self
._Sources
.append(File
)
1354 ToolList
= self
._NMAKE
_FLAG
_PATTERN
_.findall(Name
)
1355 if len(ToolList
) == 0 or len(ToolList
) != 1:
1357 # EdkLogger.warn("build", "Don't know how to do with macro [%s]" % Name,
1358 # File=self.MetaFile, Line=LineNo)
1360 if self
._BuildOptions
== None:
1361 self
._BuildOptions
= sdict()
1363 if ToolList
[0] in self
._TOOL
_CODE
_:
1364 Tool
= self
._TOOL
_CODE
_[ToolList
[0]]
1367 ToolChain
= "*_*_*_%s_FLAGS" % Tool
1368 ToolChainFamily
= 'MSFT' # R8.x only support MSFT tool chain
1369 #ignore not replaced macros in value
1370 ValueList
= GetSplitValueList(' ' + Value
, '/D')
1371 Dummy
= ValueList
[0]
1372 for Index
in range(1, len(ValueList
)):
1373 if ValueList
[Index
][-1] == '=' or ValueList
[Index
] == '':
1375 Dummy
= Dummy
+ ' /D ' + ValueList
[Index
]
1376 Value
= Dummy
.strip()
1377 if (ToolChainFamily
, ToolChain
) not in self
._BuildOptions
:
1378 self
._BuildOptions
[ToolChainFamily
, ToolChain
] = Value
1380 OptionString
= self
._BuildOptions
[ToolChainFamily
, ToolChain
]
1381 self
._BuildOptions
[ToolChainFamily
, ToolChain
] = OptionString
+ " " + Value
1382 # set _Header to non-None in order to avoid database re-querying
1383 self
._Header
_ = 'DUMMY'
1385 ## Retrieve file version
1386 def _GetInfVersion(self
):
1387 if self
._AutoGenVersion
== None:
1388 if self
._Header
_ == None:
1389 self
._GetHeaderInfo
()
1390 if self
._AutoGenVersion
== None:
1391 self
._AutoGenVersion
= 0x00010000
1392 return self
._AutoGenVersion
1394 ## Retrieve BASE_NAME
1395 def _GetBaseName(self
):
1396 if self
._BaseName
== None:
1397 if self
._Header
_ == None:
1398 self
._GetHeaderInfo
()
1399 if self
._BaseName
== None:
1400 EdkLogger
.error('build', ATTRIBUTE_NOT_AVAILABLE
, "No BASE_NAME name", File
=self
.MetaFile
)
1401 return self
._BaseName
1403 ## Retrieve MODULE_TYPE
1404 def _GetModuleType(self
):
1405 if self
._ModuleType
== None:
1406 if self
._Header
_ == None:
1407 self
._GetHeaderInfo
()
1408 if self
._ModuleType
== None:
1409 self
._ModuleType
= 'BASE'
1410 if self
._ModuleType
not in SUP_MODULE_LIST
:
1411 self
._ModuleType
= "USER_DEFINED"
1412 return self
._ModuleType
1414 ## Retrieve COMPONENT_TYPE
1415 def _GetComponentType(self
):
1416 if self
._ComponentType
== None:
1417 if self
._Header
_ == None:
1418 self
._GetHeaderInfo
()
1419 if self
._ComponentType
== None:
1420 self
._ComponentType
= 'USER_DEFINED'
1421 return self
._ComponentType
1423 ## Retrieve "BUILD_TYPE"
1424 def _GetBuildType(self
):
1425 if self
._BuildType
== None:
1426 if self
._Header
_ == None:
1427 self
._GetHeaderInfo
()
1428 if not self
._BuildType
:
1429 self
._BuildType
= "BASE"
1430 return self
._BuildType
1432 ## Retrieve file guid
1433 def _GetFileGuid(self
):
1434 if self
._Guid
== None:
1435 if self
._Header
_ == None:
1436 self
._GetHeaderInfo
()
1437 if self
._Guid
== None:
1438 self
._Guid
= '00000000-0000-0000-000000000000'
1441 ## Retrieve module version
1442 def _GetVersion(self
):
1443 if self
._Version
== None:
1444 if self
._Header
_ == None:
1445 self
._GetHeaderInfo
()
1446 if self
._Version
== None:
1447 self
._Version
= '0.0'
1448 return self
._Version
1450 ## Retrieve PCD_IS_DRIVER
1451 def _GetPcdIsDriver(self
):
1452 if self
._PcdIsDriver
== None:
1453 if self
._Header
_ == None:
1454 self
._GetHeaderInfo
()
1455 if self
._PcdIsDriver
== None:
1456 self
._PcdIsDriver
= ''
1457 return self
._PcdIsDriver
1460 def _GetShadow(self
):
1461 if self
._Shadow
== None:
1462 if self
._Header
_ == None:
1463 self
._GetHeaderInfo
()
1464 if self
._Shadow
!= None and self
._Shadow
.upper() == 'TRUE':
1467 self
._Shadow
= False
1470 ## Retrieve CUSTOM_MAKEFILE
1471 def _GetMakefile(self
):
1472 if self
._CustomMakefile
== None:
1473 if self
._Header
_ == None:
1474 self
._GetHeaderInfo
()
1475 if self
._CustomMakefile
== None:
1476 self
._CustomMakefile
= {}
1477 return self
._CustomMakefile
1479 ## Retrieve EFI_SPECIFICATION_VERSION
1481 if self
._Specification
== None:
1482 if self
._Header
_ == None:
1483 self
._GetHeaderInfo
()
1484 if self
._Specification
== None:
1485 self
._Specification
= {}
1486 return self
._Specification
1488 ## Retrieve LIBRARY_CLASS
1489 def _GetLibraryClass(self
):
1490 if self
._LibraryClass
== None:
1491 if self
._Header
_ == None:
1492 self
._GetHeaderInfo
()
1493 if self
._LibraryClass
== None:
1494 self
._LibraryClass
= []
1495 return self
._LibraryClass
1497 ## Retrieve ENTRY_POINT
1498 def _GetEntryPoint(self
):
1499 if self
._ModuleEntryPointList
== None:
1500 if self
._Header
_ == None:
1501 self
._GetHeaderInfo
()
1502 if self
._ModuleEntryPointList
== None:
1503 self
._ModuleEntryPointList
= []
1504 return self
._ModuleEntryPointList
1506 ## Retrieve UNLOAD_IMAGE
1507 def _GetUnloadImage(self
):
1508 if self
._ModuleUnloadImageList
== None:
1509 if self
._Header
_ == None:
1510 self
._GetHeaderInfo
()
1511 if self
._ModuleUnloadImageList
== None:
1512 self
._ModuleUnloadImageList
= []
1513 return self
._ModuleUnloadImageList
1515 ## Retrieve CONSTRUCTOR
1516 def _GetConstructor(self
):
1517 if self
._ConstructorList
== None:
1518 if self
._Header
_ == None:
1519 self
._GetHeaderInfo
()
1520 if self
._ConstructorList
== None:
1521 self
._ConstructorList
= []
1522 return self
._ConstructorList
1524 ## Retrieve DESTRUCTOR
1525 def _GetDestructor(self
):
1526 if self
._DestructorList
== None:
1527 if self
._Header
_ == None:
1528 self
._GetHeaderInfo
()
1529 if self
._DestructorList
== None:
1530 self
._DestructorList
= []
1531 return self
._DestructorList
1533 ## Retrieve definies other than above ones
1534 def _GetDefines(self
):
1535 if self
._Defs
== None:
1536 if self
._Header
_ == None:
1537 self
._GetHeaderInfo
()
1538 if self
._Defs
== None:
1539 self
._Defs
= sdict()
1542 ## Retrieve binary files
1543 def _GetBinaryFiles(self
):
1544 if self
._Binaries
== None:
1546 RecordList
= self
._RawData
[MODEL_EFI_BINARY_FILE
, self
._Arch
, self
._Platform
]
1547 Macros
= {"EDK_SOURCE":GlobalData
.gEcpSource
, "EFI_SOURCE":GlobalData
.gEfiSource
, 'PROCESSOR':self
._Arch
}
1548 Macros
.update(self
._Macros
)
1549 for Record
in RecordList
:
1550 Record
= ReplaceMacros(Record
, GlobalData
.gEdkGlobal
, False)
1551 FileType
= Record
[0]
1556 TokenList
= GetSplitValueList(Record
[2], TAB_VALUE_SPLIT
)
1558 Target
= TokenList
[0]
1559 if len(TokenList
) > 1:
1560 FeatureFlag
= Record
[1:]
1562 File
= PathClass(NormPath(Record
[1], Macros
), self
._ModuleDir
, '', FileType
, True, self
._Arch
, '', Target
)
1563 # check the file validation
1564 ErrorCode
, ErrorInfo
= File
.Validate()
1566 EdkLogger
.error('build', ErrorCode
, ExtraData
=ErrorInfo
, File
=self
.MetaFile
, Line
=LineNo
)
1567 self
._Binaries
.append(File
)
1568 return self
._Binaries
1570 ## Retrieve source files
1571 def _GetSourceFiles(self
):
1572 if self
._Sources
== None:
1574 RecordList
= self
._RawData
[MODEL_EFI_SOURCE_FILE
, self
._Arch
, self
._Platform
]
1575 Macros
= {"EDK_SOURCE":GlobalData
.gEcpSource
, "EFI_SOURCE":GlobalData
.gEfiSource
, 'PROCESSOR':self
._Arch
}
1576 Macros
.update(self
._Macros
)
1577 for Record
in RecordList
:
1578 Record
= ReplaceMacros(Record
, GlobalData
.gEdkGlobal
, False)
1580 ToolChainFamily
= Record
[1]
1582 ToolCode
= Record
[3]
1583 FeatureFlag
= Record
[4]
1584 if self
._AutoGenVersion
< 0x00010005:
1585 # old module source files (R8)
1586 File
= PathClass(NormPath(Record
[0], Macros
), self
._ModuleDir
, self
._SourceOverridePath
,
1587 '', False, self
._Arch
, ToolChainFamily
, '', TagName
, ToolCode
)
1588 # check the file validation
1589 ErrorCode
, ErrorInfo
= File
.Validate(CaseSensitive
=False)
1591 if File
.Ext
.lower() == '.h':
1592 EdkLogger
.warn('build', 'Include file not found', ExtraData
=ErrorInfo
,
1593 File
=self
.MetaFile
, Line
=LineNo
)
1596 EdkLogger
.error('build', ErrorCode
, ExtraData
=File
, File
=self
.MetaFile
, Line
=LineNo
)
1598 File
= PathClass(NormPath(Record
[0], Macros
), self
._ModuleDir
, '',
1599 '', False, self
._Arch
, ToolChainFamily
, '', TagName
, ToolCode
)
1600 # check the file validation
1601 ErrorCode
, ErrorInfo
= File
.Validate()
1603 EdkLogger
.error('build', ErrorCode
, ExtraData
=ErrorInfo
, File
=self
.MetaFile
, Line
=LineNo
)
1605 self
._Sources
.append(File
)
1606 return self
._Sources
1608 ## Retrieve library classes employed by this module
1609 def _GetLibraryClassUses(self
):
1610 if self
._LibraryClasses
== None:
1611 self
._LibraryClasses
= sdict()
1612 RecordList
= self
._RawData
[MODEL_EFI_LIBRARY_CLASS
, self
._Arch
, self
._Platform
]
1613 for Record
in RecordList
:
1614 Record
= ReplaceMacros(Record
, GlobalData
.gEdkGlobal
, False)
1616 Instance
= Record
[1]
1617 if Instance
!= None and Instance
!= '':
1618 Instance
= NormPath(Instance
, self
._Macros
)
1619 self
._LibraryClasses
[Lib
] = Instance
1620 return self
._LibraryClasses
1622 ## Retrieve library names (for R8.x style of modules)
1623 def _GetLibraryNames(self
):
1624 if self
._Libraries
== None:
1625 self
._Libraries
= []
1626 RecordList
= self
._RawData
[MODEL_EFI_LIBRARY_INSTANCE
, self
._Arch
, self
._Platform
]
1627 for Record
in RecordList
:
1628 # in case of name with '.lib' extension, which is unusual in R8.x inf
1629 Record
= ReplaceMacros(Record
, GlobalData
.gEdkGlobal
, False)
1630 LibraryName
= os
.path
.splitext(Record
[0])[0]
1631 if LibraryName
not in self
._Libraries
:
1632 self
._Libraries
.append(LibraryName
)
1633 return self
._Libraries
1635 ## Retrieve protocols consumed/produced by this module
1636 def _GetProtocols(self
):
1637 if self
._Protocols
== None:
1638 self
._Protocols
= sdict()
1639 RecordList
= self
._RawData
[MODEL_EFI_PROTOCOL
, self
._Arch
, self
._Platform
]
1640 for Record
in RecordList
:
1642 Value
= ProtocolValue(CName
, self
.Packages
)
1644 PackageList
= "\n\t".join([str(P
) for P
in self
.Packages
])
1645 EdkLogger
.error('build', RESOURCE_NOT_AVAILABLE
,
1646 "Value of Protocol [%s] is not found under [Protocols] section in" % CName
,
1647 ExtraData
=PackageList
, File
=self
.MetaFile
, Line
=Record
[-1])
1648 self
._Protocols
[CName
] = Value
1649 return self
._Protocols
1651 ## Retrieve PPIs consumed/produced by this module
1653 if self
._Ppis
== None:
1654 self
._Ppis
= sdict()
1655 RecordList
= self
._RawData
[MODEL_EFI_PPI
, self
._Arch
, self
._Platform
]
1656 for Record
in RecordList
:
1658 Value
= PpiValue(CName
, self
.Packages
)
1660 PackageList
= "\n\t".join([str(P
) for P
in self
.Packages
])
1661 EdkLogger
.error('build', RESOURCE_NOT_AVAILABLE
,
1662 "Value of PPI [%s] is not found under [Ppis] section in " % CName
,
1663 ExtraData
=PackageList
, File
=self
.MetaFile
, Line
=Record
[-1])
1664 self
._Ppis
[CName
] = Value
1667 ## Retrieve GUIDs consumed/produced by this module
1668 def _GetGuids(self
):
1669 if self
._Guids
== None:
1670 self
._Guids
= sdict()
1671 RecordList
= self
._RawData
[MODEL_EFI_GUID
, self
._Arch
, self
._Platform
]
1672 for Record
in RecordList
:
1674 Value
= GuidValue(CName
, self
.Packages
)
1676 PackageList
= "\n\t".join([str(P
) for P
in self
.Packages
])
1677 EdkLogger
.error('build', RESOURCE_NOT_AVAILABLE
,
1678 "Value of Guid [%s] is not found under [Guids] section in" % CName
,
1679 ExtraData
=PackageList
, File
=self
.MetaFile
, Line
=Record
[-1])
1680 self
._Guids
[CName
] = Value
1683 ## Retrieve include paths necessary for this module (for R8.x style of modules)
1684 def _GetIncludes(self
):
1685 if self
._Includes
== None:
1687 if self
._SourceOverridePath
:
1688 self
._Includes
.append(self
._SourceOverridePath
)
1689 RecordList
= self
._RawData
[MODEL_EFI_INCLUDE
, self
._Arch
, self
._Platform
]
1690 # [includes] section must be used only in old (R8.x) inf file
1691 if self
.AutoGenVersion
>= 0x00010005 and len(RecordList
) > 0:
1692 EdkLogger
.error('build', FORMAT_NOT_SUPPORTED
, "No [include] section allowed",
1693 File
=self
.MetaFile
, Line
=RecordList
[0][-1]-1)
1694 for Record
in RecordList
:
1695 Record
= ReplaceMacros(Record
, GlobalData
.gEdkGlobal
, False)
1696 Record
[0] = Record
[0].replace('$(PROCESSOR)', self
._Arch
)
1697 Record
[0] = ReplaceMacro(Record
[0], {'EFI_SOURCE' : GlobalData
.gEfiSource
}, False)
1698 if Record
[0].find('EDK_SOURCE') > -1:
1699 File
= NormPath(ReplaceMacro(Record
[0], {'EDK_SOURCE' : GlobalData
.gEcpSource
}, False), self
._Macros
)
1701 File
= os
.path
.join(self
._ModuleDir
, File
)
1703 File
= os
.path
.join(GlobalData
.gWorkspace
, File
)
1704 File
= RealPath(os
.path
.normpath(File
))
1706 self
._Includes
.append(File
)
1708 #TRICK: let compiler to choose correct header file
1709 File
= NormPath(ReplaceMacro(Record
[0], {'EDK_SOURCE' : GlobalData
.gEdkSource
}, False), self
._Macros
)
1711 File
= os
.path
.join(self
._ModuleDir
, File
)
1713 File
= os
.path
.join(GlobalData
.gWorkspace
, File
)
1714 File
= RealPath(os
.path
.normpath(File
))
1716 self
._Includes
.append(File
)
1718 File
= NormPath(Record
[0], self
._Macros
)
1720 File
= os
.path
.join(self
._ModuleDir
, File
)
1722 File
= os
.path
.join(GlobalData
.gWorkspace
, File
)
1723 File
= RealPath(os
.path
.normpath(File
))
1725 self
._Includes
.append(File
)
1726 return self
._Includes
1728 ## Retrieve packages this module depends on
1729 def _GetPackages(self
):
1730 if self
._Packages
== None:
1732 RecordList
= self
._RawData
[MODEL_META_DATA_PACKAGE
, self
._Arch
, self
._Platform
]
1733 Macros
= {"EDK_SOURCE":GlobalData
.gEcpSource
, "EFI_SOURCE":GlobalData
.gEfiSource
}
1734 Macros
.update(self
._Macros
)
1735 for Record
in RecordList
:
1736 File
= PathClass(NormPath(Record
[0], Macros
), GlobalData
.gWorkspace
, Arch
=self
._Arch
)
1738 # check the file validation
1739 ErrorCode
, ErrorInfo
= File
.Validate('.dec')
1741 EdkLogger
.error('build', ErrorCode
, ExtraData
=ErrorInfo
, File
=self
.MetaFile
, Line
=LineNo
)
1742 # parse this package now. we need it to get protocol/ppi/guid value
1743 Package
= self
._Bdb
[File
, self
._Arch
]
1744 self
._Packages
.append(Package
)
1745 return self
._Packages
1747 ## Retrieve PCDs used in this module
1749 if self
._Pcds
== None:
1751 self
._Pcds
.update(self
._GetPcd
(MODEL_PCD_FIXED_AT_BUILD
))
1752 self
._Pcds
.update(self
._GetPcd
(MODEL_PCD_PATCHABLE_IN_MODULE
))
1753 self
._Pcds
.update(self
._GetPcd
(MODEL_PCD_FEATURE_FLAG
))
1754 self
._Pcds
.update(self
._GetPcd
(MODEL_PCD_DYNAMIC
))
1755 self
._Pcds
.update(self
._GetPcd
(MODEL_PCD_DYNAMIC_EX
))
1758 ## Retrieve build options specific to this module
1759 def _GetBuildOptions(self
):
1760 if self
._BuildOptions
== None:
1761 self
._BuildOptions
= sdict()
1762 RecordList
= self
._RawData
[MODEL_META_DATA_BUILD_OPTION
, self
._Arch
, self
._Platform
]
1763 for Record
in RecordList
:
1764 ToolChainFamily
= Record
[0]
1765 ToolChain
= Record
[1]
1767 if (ToolChainFamily
, ToolChain
) not in self
._BuildOptions
:
1768 self
._BuildOptions
[ToolChainFamily
, ToolChain
] = Option
1770 # concatenate the option string if they're for the same tool
1771 OptionString
= self
._BuildOptions
[ToolChainFamily
, ToolChain
]
1772 self
._BuildOptions
[ToolChainFamily
, ToolChain
] = OptionString
+ " " + Option
1773 return self
._BuildOptions
1775 ## Retrieve depedency expression
1776 def _GetDepex(self
):
1777 if self
._Depex
== None:
1778 self
._Depex
= tdict(False, 2)
1779 RecordList
= self
._RawData
[MODEL_EFI_DEPEX
, self
._Arch
]
1781 # PEIM and DXE drivers must have a valid [Depex] section
1782 if len(self
.LibraryClass
) == 0 and len(RecordList
) == 0:
1783 if self
.ModuleType
== 'DXE_DRIVER' or self
.ModuleType
== 'PEIM' or self
.ModuleType
== 'DXE_SMM_DRIVER' or \
1784 self
.ModuleType
== 'DXE_SAL_DRIVER' or self
.ModuleType
== 'DXE_RUNTIME_DRIVER':
1785 EdkLogger
.error('build', RESOURCE_NOT_AVAILABLE
, "No [Depex] section or no valid expression in [Depex] section for [%s] module" \
1786 % self
.ModuleType
, File
=self
.MetaFile
)
1789 for Record
in RecordList
:
1790 Record
= ReplaceMacros(Record
, GlobalData
.gEdkGlobal
, False)
1792 ModuleType
= Record
[4]
1793 TokenList
= Record
[0].split()
1794 if (Arch
, ModuleType
) not in Depex
:
1795 Depex
[Arch
, ModuleType
] = []
1796 DepexList
= Depex
[Arch
, ModuleType
]
1797 for Token
in TokenList
:
1798 if Token
in DEPEX_SUPPORTED_OPCODE
:
1799 DepexList
.append(Token
)
1800 elif Token
.endswith(".inf"): # module file name
1801 ModuleFile
= os
.path
.normpath(Token
)
1802 Module
= self
.BuildDatabase
[ModuleFile
]
1804 EdkLogger
.error('build', RESOURCE_NOT_AVAILABLE
, "Module is not found in active platform",
1805 ExtraData
=Token
, File
=self
.MetaFile
, Line
=Record
[-1])
1806 DepexList
.append(Module
.Guid
)
1808 # get the GUID value now
1809 Value
= ProtocolValue(Token
, self
.Packages
)
1811 Value
= PpiValue(Token
, self
.Packages
)
1813 Value
= GuidValue(Token
, self
.Packages
)
1815 PackageList
= "\n\t".join([str(P
) for P
in self
.Packages
])
1816 EdkLogger
.error('build', RESOURCE_NOT_AVAILABLE
,
1817 "Value of [%s] is not found in" % Token
,
1818 ExtraData
=PackageList
, File
=self
.MetaFile
, Line
=Record
[-1])
1819 DepexList
.append(Value
)
1820 for Arch
, ModuleType
in Depex
:
1821 self
._Depex
[Arch
, ModuleType
] = Depex
[Arch
, ModuleType
]
1824 ## Retrieve PCD for given type
1825 def _GetPcd(self
, Type
):
1827 PcdDict
= tdict(True, 4)
1829 RecordList
= self
._RawData
[Type
, self
._Arch
, self
._Platform
]
1830 for TokenSpaceGuid
, PcdCName
, Setting
, Arch
, Platform
, Dummy1
, LineNo
in RecordList
:
1831 PcdDict
[Arch
, Platform
, PcdCName
, TokenSpaceGuid
] = (Setting
, LineNo
)
1832 PcdSet
.add((PcdCName
, TokenSpaceGuid
))
1833 # get the guid value
1834 if TokenSpaceGuid
not in self
.Guids
:
1835 Value
= GuidValue(TokenSpaceGuid
, self
.Packages
)
1837 PackageList
= "\n\t".join([str(P
) for P
in self
.Packages
])
1838 EdkLogger
.error('build', RESOURCE_NOT_AVAILABLE
,
1839 "Value of Guid [%s] is not found under [Guids] section in" % TokenSpaceGuid
,
1840 ExtraData
=PackageList
, File
=self
.MetaFile
, Line
=LineNo
)
1841 self
.Guids
[TokenSpaceGuid
] = Value
1843 # resolve PCD type, value, datum info, etc. by getting its definition from package
1844 for PcdCName
, TokenSpaceGuid
in PcdSet
:
1845 ValueList
= ['', '']
1846 Setting
, LineNo
= PcdDict
[self
._Arch
, self
.Platform
, PcdCName
, TokenSpaceGuid
]
1849 TokenList
= Setting
.split(TAB_VALUE_SPLIT
)
1850 ValueList
[0:len(TokenList
)] = TokenList
1851 DefaultValue
= ValueList
[0]
1852 Pcd
= PcdClassObject(
1861 self
.Guids
[TokenSpaceGuid
]
1864 # get necessary info from package declaring this PCD
1865 for Package
in self
.Packages
:
1867 # 'dynamic' in INF means its type is determined by platform;
1868 # if platform doesn't give its type, use 'lowest' one in the
1869 # following order, if any
1871 # "FixedAtBuild", "PatchableInModule", "FeatureFlag", "Dynamic", "DynamicEx"
1873 PcdType
= self
._PCD
_TYPE
_STRING
_[Type
]
1874 if Type
in [MODEL_PCD_DYNAMIC
, MODEL_PCD_DYNAMIC_EX
]:
1876 for T
in ["FixedAtBuild", "PatchableInModule", "FeatureFlag", "Dynamic", "DynamicEx"]:
1877 if (PcdCName
, TokenSpaceGuid
, T
) in Package
.Pcds
:
1883 if (PcdCName
, TokenSpaceGuid
, PcdType
) in Package
.Pcds
:
1884 PcdInPackage
= Package
.Pcds
[PcdCName
, TokenSpaceGuid
, PcdType
]
1886 Pcd
.TokenValue
= PcdInPackage
.TokenValue
1887 Pcd
.DatumType
= PcdInPackage
.DatumType
1888 Pcd
.MaxDatumSize
= PcdInPackage
.MaxDatumSize
1889 if Pcd
.DefaultValue
in [None, '']:
1890 Pcd
.DefaultValue
= PcdInPackage
.DefaultValue
1896 "PCD [%s.%s] in [%s] is not found in dependent packages:" % (TokenSpaceGuid
, PcdCName
, self
.MetaFile
),
1897 File
=self
.MetaFile
, Line
=LineNo
,
1898 ExtraData
="\t%s" % '\n\t'.join([str(P
) for P
in self
.Packages
])
1900 Pcds
[PcdCName
, TokenSpaceGuid
] = Pcd
1903 Arch
= property(_GetArch
, _SetArch
)
1904 Platform
= property(_GetPlatform
, _SetPlatform
)
1906 AutoGenVersion
= property(_GetInfVersion
)
1907 BaseName
= property(_GetBaseName
)
1908 ModuleType
= property(_GetModuleType
)
1909 ComponentType
= property(_GetComponentType
)
1910 BuildType
= property(_GetBuildType
)
1911 Guid
= property(_GetFileGuid
)
1912 Version
= property(_GetVersion
)
1913 PcdIsDriver
= property(_GetPcdIsDriver
)
1914 Shadow
= property(_GetShadow
)
1915 CustomMakefile
= property(_GetMakefile
)
1916 Specification
= property(_GetSpec
)
1917 LibraryClass
= property(_GetLibraryClass
)
1918 ModuleEntryPointList
= property(_GetEntryPoint
)
1919 ModuleUnloadImageList
= property(_GetUnloadImage
)
1920 ConstructorList
= property(_GetConstructor
)
1921 DestructorList
= property(_GetDestructor
)
1922 Defines
= property(_GetDefines
)
1924 Binaries
= property(_GetBinaryFiles
)
1925 Sources
= property(_GetSourceFiles
)
1926 LibraryClasses
= property(_GetLibraryClassUses
)
1927 Libraries
= property(_GetLibraryNames
)
1928 Protocols
= property(_GetProtocols
)
1929 Ppis
= property(_GetPpis
)
1930 Guids
= property(_GetGuids
)
1931 Includes
= property(_GetIncludes
)
1932 Packages
= property(_GetPackages
)
1933 Pcds
= property(_GetPcds
)
1934 BuildOptions
= property(_GetBuildOptions
)
1935 Depex
= property(_GetDepex
)
1939 # This class defined the build databse for all modules, packages and platform.
1940 # It will call corresponding parser for the given file if it cannot find it in
1943 # @param DbPath Path of database file
1944 # @param GlobalMacros Global macros used for replacement during file parsing
1945 # @prarm RenewDb=False Create new database file if it's already there
1947 class WorkspaceDatabase(object):
1950 MODEL_FILE_INF
: InfParser
,
1951 MODEL_FILE_DEC
: DecParser
,
1952 MODEL_FILE_DSC
: DscParser
,
1953 MODEL_FILE_FDF
: None, #FdfParser,
1954 MODEL_FILE_CIF
: None
1959 MODEL_FILE_INF
: ModuleTable
,
1960 MODEL_FILE_DEC
: PackageTable
,
1961 MODEL_FILE_DSC
: PlatformTable
,
1964 # default database file path
1965 _DB_PATH_
= "Conf/.cache/build.db"
1968 # internal class used for call corresponding file parser and caching the result
1969 # to avoid unnecessary re-parsing
1971 class BuildObjectFactory(object):
1973 ".inf" : MODEL_FILE_INF
,
1974 ".dec" : MODEL_FILE_DEC
,
1975 ".dsc" : MODEL_FILE_DSC
,
1976 ".fdf" : MODEL_FILE_FDF
,
1979 # convert to xxxBuildData object
1981 MODEL_FILE_INF
: InfBuildData
,
1982 MODEL_FILE_DEC
: DecBuildData
,
1983 MODEL_FILE_DSC
: DscBuildData
,
1984 MODEL_FILE_FDF
: None #FlashDefTable,
1987 _CACHE_
= {} # (FilePath, Arch) : <object>
1990 def __init__(self
, WorkspaceDb
):
1991 self
.WorkspaceDb
= WorkspaceDb
1993 # key = (FilePath, Arch='COMMON')
1994 def __contains__(self
, Key
):
1999 return (FilePath
, Arch
) in self
._CACHE
_
2001 # key = (FilePath, Arch='COMMON')
2002 def __getitem__(self
, Key
):
2011 # if it's generated before, just return the cached one
2012 Key
= (FilePath
, Arch
)
2013 if Key
in self
._CACHE
_:
2014 return self
._CACHE
_[Key
]
2017 Ext
= FilePath
.Ext
.lower()
2018 if Ext
not in self
._FILE
_TYPE
_:
2020 FileType
= self
._FILE
_TYPE
_[Ext
]
2021 if FileType
not in self
._GENERATOR
_:
2024 # get table for current file
2025 MetaFile
= self
.WorkspaceDb
[FilePath
, FileType
, self
.WorkspaceDb
._GlobalMacros
]
2026 BuildObject
= self
._GENERATOR
_[FileType
](
2032 self
.WorkspaceDb
._GlobalMacros
,
2034 self
._CACHE
_[Key
] = BuildObject
2037 # placeholder for file format conversion
2038 class TransformObjectFactory
:
2039 def __init__(self
, WorkspaceDb
):
2040 self
.WorkspaceDb
= WorkspaceDb
2042 # key = FilePath, Arch
2043 def __getitem__(self
, Key
):
2046 ## Constructor of WorkspaceDatabase
2048 # @param DbPath Path of database file
2049 # @param GlobalMacros Global macros used for replacement during file parsing
2050 # @prarm RenewDb=False Create new database file if it's already there
2052 def __init__(self
, DbPath
, GlobalMacros
={}, RenewDb
=False):
2053 self
._GlobalMacros
= GlobalMacros
2055 if DbPath
== None or DbPath
== '':
2056 DbPath
= os
.path
.normpath(os
.path
.join(GlobalData
.gWorkspace
, self
._DB
_PATH
_))
2058 # don't create necessary path for db in memory
2059 if DbPath
!= ':memory:':
2060 DbDir
= os
.path
.split(DbPath
)[0]
2061 if not os
.path
.exists(DbDir
):
2064 # remove db file in case inconsistency between db and file in file system
2065 if self
._CheckWhetherDbNeedRenew
(RenewDb
, DbPath
):
2068 # create db with optimized parameters
2069 self
.Conn
= sqlite3
.connect(DbPath
, isolation_level
='DEFERRED')
2070 self
.Conn
.execute("PRAGMA synchronous=OFF")
2071 self
.Conn
.execute("PRAGMA temp_store=MEMORY")
2072 self
.Conn
.execute("PRAGMA count_changes=OFF")
2073 self
.Conn
.execute("PRAGMA cache_size=8192")
2074 #self.Conn.execute("PRAGMA page_size=8192")
2076 # to avoid non-ascii character conversion issue
2077 self
.Conn
.text_factory
= str
2078 self
.Cur
= self
.Conn
.cursor()
2080 # create table for internal uses
2081 self
.TblDataModel
= TableDataModel(self
.Cur
)
2082 self
.TblFile
= TableFile(self
.Cur
)
2084 # conversion object for build or file format conversion purpose
2085 self
.BuildObject
= WorkspaceDatabase
.BuildObjectFactory(self
)
2086 self
.TransformObject
= WorkspaceDatabase
.TransformObjectFactory(self
)
2088 ## Check whether workspace database need to be renew.
2089 # The renew reason maybe:
2090 # 1) If user force to renew;
2091 # 2) If user do not force renew, and
2092 # a) If the time of last modified python source is newer than database file;
2093 # b) If the time of last modified frozen executable file is newer than database file;
2095 # @param force User force renew database
2096 # @param DbPath The absolute path of workspace database file
2098 # @return Bool value for whether need renew workspace databse
2100 def _CheckWhetherDbNeedRenew (self
, force
, DbPath
):
2101 # if database does not exist, we need do nothing
2102 if not os
.path
.exists(DbPath
): return False
2104 # if user force to renew database, then not check whether database is out of date
2105 if force
: return True
2108 # Check the time of last modified source file or build.exe
2109 # if is newer than time of database, then database need to be re-created.
2111 timeOfToolModified
= 0
2112 if hasattr(sys
, "frozen"):
2113 exePath
= os
.path
.abspath(sys
.executable
)
2114 timeOfToolModified
= os
.stat(exePath
).st_mtime
2116 curPath
= os
.path
.dirname(__file__
) # curPath is the path of WorkspaceDatabase.py
2117 rootPath
= os
.path
.split(curPath
)[0] # rootPath is root path of python source, such as /BaseTools/Source/Python
2118 if rootPath
== "" or rootPath
== None:
2119 EdkLogger
.verbose("\nFail to find the root path of build.exe or python sources, so can not \
2120 determine whether database file is out of date!\n")
2122 # walk the root path of source or build's binary to get the time last modified.
2124 for root
, dirs
, files
in os
.walk (rootPath
):
2126 # bypass source control folder
2127 if dir.lower() in [".svn", "_svn", "cvs"]:
2131 ext
= os
.path
.splitext(file)[1]
2132 if ext
.lower() == ".py": # only check .py files
2133 fd
= os
.stat(os
.path
.join(root
, file))
2134 if timeOfToolModified
< fd
.st_mtime
:
2135 timeOfToolModified
= fd
.st_mtime
2136 if timeOfToolModified
> os
.stat(DbPath
).st_mtime
:
2137 EdkLogger
.verbose("\nWorkspace database is out of data!")
2142 ## Initialize build database
2143 def InitDatabase(self
):
2144 EdkLogger
.verbose("\nInitialize build database started ...")
2149 self
.TblDataModel
.Create(False)
2150 self
.TblFile
.Create(False)
2153 # Initialize table DataModel
2155 self
.TblDataModel
.InitTable()
2156 EdkLogger
.verbose("Initialize build database ... DONE!")
2160 # @param Table: The instance of the table to be queried
2162 def QueryTable(self
, Table
):
2165 ## Close entire database
2168 # Close the connection and cursor
2175 ## Get unique file ID for the gvien file
2176 def GetFileId(self
, FilePath
):
2177 return self
.TblFile
.GetFileId(FilePath
)
2179 ## Get file type value for the gvien file ID
2180 def GetFileType(self
, FileId
):
2181 return self
.TblFile
.GetFileType(FileId
)
2183 ## Get time stamp stored in file table
2184 def GetTimeStamp(self
, FileId
):
2185 return self
.TblFile
.GetFileTimeStamp(FileId
)
2187 ## Update time stamp in file table
2188 def SetTimeStamp(self
, FileId
, TimeStamp
):
2189 return self
.TblFile
.SetFileTimeStamp(FileId
, TimeStamp
)
2191 ## Check if a table integrity flag exists or not
2192 def CheckIntegrity(self
, TableName
):
2194 Result
= self
.Cur
.execute("select min(ID) from %s" % (TableName
)).fetchall()
2195 if Result
[0][0] != -1:
2201 ## Compose table name for given file type and file ID
2202 def GetTableName(self
, FileType
, FileId
):
2203 return "_%s_%s" % (FileType
, FileId
)
2205 ## Return a temp table containing all content of the given file
2207 # @param FileInfo The tuple containing path and type of a file
2209 def __getitem__(self
, FileInfo
):
2210 FilePath
, FileType
, Macros
= FileInfo
2211 if FileType
not in self
._FILE
_TABLE
_:
2214 # flag used to indicate if it's parsed or not
2215 FilePath
= str(FilePath
)
2217 FileId
= self
.GetFileId(FilePath
)
2219 TimeStamp
= os
.stat(FilePath
)[8]
2220 TableName
= self
.GetTableName(FileType
, FileId
)
2221 if TimeStamp
!= self
.GetTimeStamp(FileId
):
2222 # update the timestamp in database
2223 self
.SetTimeStamp(FileId
, TimeStamp
)
2225 # if the table exists and is integrity, don't parse it
2226 Parsed
= self
.CheckIntegrity(TableName
)
2228 FileId
= self
.TblFile
.InsertFile(FilePath
, FileType
)
2229 TableName
= self
.GetTableName(FileType
, FileId
)
2231 FileTable
= self
._FILE
_TABLE
_[FileType
](self
.Cur
, TableName
, FileId
)
2232 FileTable
.Create(not Parsed
)
2233 Parser
= self
._FILE
_PARSER
_[FileType
](FilePath
, FileType
, FileTable
, Macros
)
2234 # set the "Finished" flag in parser in order to avoid re-parsing (if parsed)
2235 Parser
.Finished
= Parsed
2238 ## Summarize all packages in the database
2239 def _GetPackageList(self
):
2241 for Module
in self
.ModuleList
:
2242 for Package
in Module
.Packages
:
2243 if Package
not in PackageList
:
2244 PackageList
.append(Package
)
2247 ## Summarize all platforms in the database
2248 def _GetPlatformList(self
):
2250 for PlatformFile
in self
.TblFile
.GetFileList(MODEL_FILE_DSC
):
2252 Platform
= self
.BuildObject
[PathClass(PlatformFile
), 'COMMON']
2255 if Platform
!= None:
2256 PlatformList
.append(Platform
)
2259 ## Summarize all modules in the database
2260 def _GetModuleList(self
):
2262 for ModuleFile
in self
.TblFile
.GetFileList(MODEL_FILE_INF
):
2264 Module
= self
.BuildObject
[PathClass(ModuleFile
), 'COMMON']
2268 ModuleList
.append(Module
)
2271 PlatformList
= property(_GetPlatformList
)
2272 PackageList
= property(_GetPackageList
)
2273 ModuleList
= property(_GetModuleList
)
2277 # This acts like the main() function for the script, unless it is 'import'ed into another
2280 if __name__
== '__main__':