2 # Global variables for GenFds
4 # Copyright (c) 2007 - 2016, Intel Corporation. All rights reserved.<BR>
6 # This program and the accompanying materials
7 # are licensed and made available under the terms and conditions of the BSD License
8 # which accompanies this distribution. The full text of the license may be found at
9 # http://opensource.org/licenses/bsd-license.php
11 # THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
12 # WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
18 import Common
.LongFilePathOs
as os
24 from Common
.BuildToolError
import *
25 from Common
import EdkLogger
26 from Common
.Misc
import SaveFileOnChange
28 from Common
.TargetTxtClassObject
import TargetTxtClassObject
29 from Common
.ToolDefClassObject
import ToolDefClassObject
30 from AutoGen
.BuildEngine
import BuildRule
31 import Common
.DataType
as DataType
32 from Common
.Misc
import PathClass
33 from Common
.LongFilePathSupport
import OpenLongFilePath
as open
34 from Common
.MultipleWorkspace
import MultipleWorkspace
as mws
39 class GenFdsGlobalVariable
:
43 # will be FvDir + os.sep + 'Ffs'
51 OutputDirFromDscDict
= {}
58 FvAddressFileName
= ''
62 SharpNumberPerLine
= 40
65 FixedLoadAddress
= False
68 BuildRuleFamily
= "MSFT"
69 ToolChainFamily
= "MSFT"
70 __BuildRuleDatabase
= None
71 GuidToolDefinition
= {}
74 # The list whose element are flags to indicate if large FFS or SECTION files exist in FV.
75 # At the beginning of each generation of FV, false flag is appended to the list,
76 # after the call to GenerateSection returns, check the size of the output file,
77 # if it is greater than 0xFFFFFF, the tail flag in list is set to true,
78 # and EFI_FIRMWARE_FILE_SYSTEM3_GUID is passed to C GenFv.
79 # At the end of generation of FV, pop the flag.
80 # List is used as a stack to handle nested FV generation.
82 LargeFileInFvFlags
= []
83 EFI_FIRMWARE_FILE_SYSTEM3_GUID
= '5473C07A-3DCB-4dca-BD6F-1E9689E7349A'
84 LARGE_FILE_SIZE
= 0x1000000
86 SectionHeader
= struct
.Struct("3B 1B")
91 def __LoadBuildRule():
92 if GenFdsGlobalVariable
.__BuildRuleDatabase
:
93 return GenFdsGlobalVariable
.__BuildRuleDatabase
94 BuildConfigurationFile
= os
.path
.normpath(os
.path
.join(GenFdsGlobalVariable
.ConfDir
, "target.txt"))
95 TargetTxt
= TargetTxtClassObject()
96 if os
.path
.isfile(BuildConfigurationFile
) == True:
97 TargetTxt
.LoadTargetTxtFile(BuildConfigurationFile
)
98 if DataType
.TAB_TAT_DEFINES_BUILD_RULE_CONF
in TargetTxt
.TargetTxtDictionary
:
99 BuildRuleFile
= TargetTxt
.TargetTxtDictionary
[DataType
.TAB_TAT_DEFINES_BUILD_RULE_CONF
]
100 if BuildRuleFile
in [None, '']:
101 BuildRuleFile
= 'Conf/build_rule.txt'
102 GenFdsGlobalVariable
.__BuildRuleDatabase
= BuildRule(BuildRuleFile
)
103 ToolDefinitionFile
= TargetTxt
.TargetTxtDictionary
[DataType
.TAB_TAT_DEFINES_TOOL_CHAIN_CONF
]
104 if ToolDefinitionFile
== '':
105 ToolDefinitionFile
= "Conf/tools_def.txt"
106 if os
.path
.isfile(ToolDefinitionFile
):
107 ToolDef
= ToolDefClassObject()
108 ToolDef
.LoadToolDefFile(ToolDefinitionFile
)
109 ToolDefinition
= ToolDef
.ToolsDefTxtDatabase
110 if DataType
.TAB_TOD_DEFINES_BUILDRULEFAMILY
in ToolDefinition \
111 and GenFdsGlobalVariable
.ToolChainTag
in ToolDefinition
[DataType
.TAB_TOD_DEFINES_BUILDRULEFAMILY
] \
112 and ToolDefinition
[DataType
.TAB_TOD_DEFINES_BUILDRULEFAMILY
][GenFdsGlobalVariable
.ToolChainTag
]:
113 GenFdsGlobalVariable
.BuildRuleFamily
= ToolDefinition
[DataType
.TAB_TOD_DEFINES_BUILDRULEFAMILY
][GenFdsGlobalVariable
.ToolChainTag
]
115 if DataType
.TAB_TOD_DEFINES_FAMILY
in ToolDefinition \
116 and GenFdsGlobalVariable
.ToolChainTag
in ToolDefinition
[DataType
.TAB_TOD_DEFINES_FAMILY
] \
117 and ToolDefinition
[DataType
.TAB_TOD_DEFINES_FAMILY
][GenFdsGlobalVariable
.ToolChainTag
]:
118 GenFdsGlobalVariable
.ToolChainFamily
= ToolDefinition
[DataType
.TAB_TOD_DEFINES_FAMILY
][GenFdsGlobalVariable
.ToolChainTag
]
119 return GenFdsGlobalVariable
.__BuildRuleDatabase
122 # @param Inf: object of InfBuildData
123 # @param Arch: current arch
126 def GetBuildRules(Inf
, Arch
):
130 if not Arch
in GenFdsGlobalVariable
.OutputDirDict
:
133 BuildRuleDatabase
= GenFdsGlobalVariable
.__LoadBuildRule
()
134 if not BuildRuleDatabase
:
137 PathClassObj
= PathClass(Inf
.MetaFile
.File
,
138 GenFdsGlobalVariable
.WorkSpaceDir
)
140 Macro
["WORKSPACE" ] = GenFdsGlobalVariable
.WorkSpaceDir
141 Macro
["MODULE_NAME" ] = Inf
.BaseName
142 Macro
["MODULE_GUID" ] = Inf
.Guid
143 Macro
["MODULE_VERSION" ] = Inf
.Version
144 Macro
["MODULE_TYPE" ] = Inf
.ModuleType
145 Macro
["MODULE_FILE" ] = str(PathClassObj
)
146 Macro
["MODULE_FILE_BASE_NAME" ] = PathClassObj
.BaseName
147 Macro
["MODULE_RELATIVE_DIR" ] = PathClassObj
.SubDir
148 Macro
["MODULE_DIR" ] = PathClassObj
.SubDir
150 Macro
["BASE_NAME" ] = Inf
.BaseName
152 Macro
["ARCH" ] = Arch
153 Macro
["TOOLCHAIN" ] = GenFdsGlobalVariable
.ToolChainTag
154 Macro
["TOOLCHAIN_TAG" ] = GenFdsGlobalVariable
.ToolChainTag
155 Macro
["TOOL_CHAIN_TAG" ] = GenFdsGlobalVariable
.ToolChainTag
156 Macro
["TARGET" ] = GenFdsGlobalVariable
.TargetName
158 Macro
["BUILD_DIR" ] = GenFdsGlobalVariable
.OutputDirDict
[Arch
]
159 Macro
["BIN_DIR" ] = os
.path
.join(GenFdsGlobalVariable
.OutputDirDict
[Arch
], Arch
)
160 Macro
["LIB_DIR" ] = os
.path
.join(GenFdsGlobalVariable
.OutputDirDict
[Arch
], Arch
)
161 BuildDir
= os
.path
.join(
162 GenFdsGlobalVariable
.OutputDirDict
[Arch
],
165 PathClassObj
.BaseName
167 Macro
["MODULE_BUILD_DIR" ] = BuildDir
168 Macro
["OUTPUT_DIR" ] = os
.path
.join(BuildDir
, "OUTPUT")
169 Macro
["DEBUG_DIR" ] = os
.path
.join(BuildDir
, "DEBUG")
172 for Type
in BuildRuleDatabase
.FileTypeList
:
173 #first try getting build rule by BuildRuleFamily
174 RuleObject
= BuildRuleDatabase
[Type
, Inf
.BuildType
, Arch
, GenFdsGlobalVariable
.BuildRuleFamily
]
176 # build type is always module type, but ...
177 if Inf
.ModuleType
!= Inf
.BuildType
:
178 RuleObject
= BuildRuleDatabase
[Type
, Inf
.ModuleType
, Arch
, GenFdsGlobalVariable
.BuildRuleFamily
]
179 #second try getting build rule by ToolChainFamily
181 RuleObject
= BuildRuleDatabase
[Type
, Inf
.BuildType
, Arch
, GenFdsGlobalVariable
.ToolChainFamily
]
183 # build type is always module type, but ...
184 if Inf
.ModuleType
!= Inf
.BuildType
:
185 RuleObject
= BuildRuleDatabase
[Type
, Inf
.ModuleType
, Arch
, GenFdsGlobalVariable
.ToolChainFamily
]
188 RuleObject
= RuleObject
.Instantiate(Macro
)
189 BuildRules
[Type
] = RuleObject
190 for Ext
in RuleObject
.SourceFileExtList
:
191 BuildRules
[Ext
] = RuleObject
194 ## GetModuleCodaTargetList
196 # @param Inf: object of InfBuildData
197 # @param Arch: current arch
200 def GetModuleCodaTargetList(Inf
, Arch
):
201 BuildRules
= GenFdsGlobalVariable
.GetBuildRules(Inf
, Arch
)
208 if not Inf
.IsBinaryModule
:
209 for File
in Inf
.Sources
:
210 if File
.TagName
in ("", "*", GenFdsGlobalVariable
.ToolChainTag
) and \
211 File
.ToolChainFamily
in ("", "*", GenFdsGlobalVariable
.ToolChainFamily
):
212 FileList
.append((File
, DataType
.TAB_UNKNOWN_FILE
))
214 for File
in Inf
.Binaries
:
215 if File
.Target
in ['COMMON', '*', GenFdsGlobalVariable
.TargetName
]:
216 FileList
.append((File
, File
.Type
))
218 for File
, FileType
in FileList
:
223 while Index
< len(SourceList
):
224 Source
= SourceList
[Index
]
227 if File
.IsBinary
and File
== Source
and Inf
.Binaries
!= None and File
in Inf
.Binaries
:
228 # Skip all files that are not binary libraries
229 if not Inf
.LibraryClass
:
231 RuleObject
= BuildRules
[DataType
.TAB_DEFAULT_BINARY_FILE
]
232 elif FileType
in BuildRules
:
233 RuleObject
= BuildRules
[FileType
]
234 elif Source
.Ext
in BuildRules
:
235 RuleObject
= BuildRules
[Source
.Ext
]
237 # stop at no more rules
239 TargetList
.add(str(LastTarget
))
242 FileType
= RuleObject
.SourceFileType
244 # stop at STATIC_LIBRARY for library
245 if Inf
.LibraryClass
and FileType
== DataType
.TAB_STATIC_LIBRARY
:
247 TargetList
.add(str(LastTarget
))
250 Target
= RuleObject
.Apply(Source
)
253 TargetList
.add(str(LastTarget
))
255 elif not Target
.Outputs
:
256 # Only do build for target with outputs
257 TargetList
.add(str(Target
))
259 # to avoid cyclic rule
260 if FileType
in RuleChain
:
263 RuleChain
.append(FileType
)
264 SourceList
.extend(Target
.Outputs
)
266 FileType
= DataType
.TAB_UNKNOWN_FILE
268 return list(TargetList
)
272 # @param OutputDir Output directory
273 # @param FdfParser FDF contents parser
274 # @param Workspace The directory of workspace
275 # @param ArchList The Arch list of platform
277 def SetDir (OutputDir
, FdfParser
, WorkSpace
, ArchList
):
278 GenFdsGlobalVariable
.VerboseLogger("GenFdsGlobalVariable.OutputDir :%s" % OutputDir
)
279 # GenFdsGlobalVariable.OutputDirDict = OutputDir
280 GenFdsGlobalVariable
.FdfParser
= FdfParser
281 GenFdsGlobalVariable
.WorkSpace
= WorkSpace
282 GenFdsGlobalVariable
.FvDir
= os
.path
.join(GenFdsGlobalVariable
.OutputDirDict
[ArchList
[0]], 'FV')
283 if not os
.path
.exists(GenFdsGlobalVariable
.FvDir
) :
284 os
.makedirs(GenFdsGlobalVariable
.FvDir
)
285 GenFdsGlobalVariable
.FfsDir
= os
.path
.join(GenFdsGlobalVariable
.FvDir
, 'Ffs')
286 if not os
.path
.exists(GenFdsGlobalVariable
.FfsDir
) :
287 os
.makedirs(GenFdsGlobalVariable
.FfsDir
)
289 GenFdsGlobalVariable
.ArchList
= ArchList
293 # Create FV Address inf file
295 GenFdsGlobalVariable
.FvAddressFileName
= os
.path
.join(GenFdsGlobalVariable
.FfsDir
, 'FvAddress.inf')
296 FvAddressFile
= open(GenFdsGlobalVariable
.FvAddressFileName
, 'w')
300 FvAddressFile
.writelines("[options]" + T_CHAR_LF
)
302 for Arch
in ArchList
:
303 if GenFdsGlobalVariable
.WorkSpace
.BuildObject
[GenFdsGlobalVariable
.ActivePlatform
, Arch
, GenFdsGlobalVariable
.TargetName
, GenFdsGlobalVariable
.ToolChainTag
].BsBaseAddress
:
304 BsAddress
= GenFdsGlobalVariable
.WorkSpace
.BuildObject
[GenFdsGlobalVariable
.ActivePlatform
, Arch
, GenFdsGlobalVariable
.TargetName
, GenFdsGlobalVariable
.ToolChainTag
].BsBaseAddress
307 FvAddressFile
.writelines("EFI_BOOT_DRIVER_BASE_ADDRESS = " + \
312 for Arch
in ArchList
:
313 if GenFdsGlobalVariable
.WorkSpace
.BuildObject
[GenFdsGlobalVariable
.ActivePlatform
, Arch
, GenFdsGlobalVariable
.TargetName
, GenFdsGlobalVariable
.ToolChainTag
].RtBaseAddress
:
314 RtAddress
= GenFdsGlobalVariable
.WorkSpace
.BuildObject
[GenFdsGlobalVariable
.ActivePlatform
, Arch
, GenFdsGlobalVariable
.TargetName
, GenFdsGlobalVariable
.ToolChainTag
].RtBaseAddress
316 FvAddressFile
.writelines("EFI_RUNTIME_DRIVER_BASE_ADDRESS = " + \
320 FvAddressFile
.close()
322 ## ReplaceWorkspaceMacro()
324 # @param String String that may contain macro
326 def ReplaceWorkspaceMacro(String
):
327 String
= mws
.handleWsMacro(String
)
328 Str
= String
.replace('$(WORKSPACE)', GenFdsGlobalVariable
.WorkSpaceDir
)
329 if os
.path
.exists(Str
):
330 if not os
.path
.isabs(Str
):
331 Str
= os
.path
.abspath(Str
)
333 Str
= mws
.join(GenFdsGlobalVariable
.WorkSpaceDir
, String
)
334 return os
.path
.normpath(Str
)
336 ## Check if the input files are newer than output files
338 # @param Output Path of output file
339 # @param Input Path list of input files
341 # @retval True if Output doesn't exist, or any Input is newer
342 # @retval False if all Input is older than Output
345 def NeedsUpdate(Output
, Input
):
346 if not os
.path
.exists(Output
):
348 # always update "Output" if no "Input" given
349 if Input
== None or len(Input
) == 0:
352 # if fdf file is changed after the 'Output" is generated, update the 'Output'
353 OutputTime
= os
.path
.getmtime(Output
)
354 if GenFdsGlobalVariable
.FdfFileTimeStamp
> OutputTime
:
358 # always update "Output" if any "Input" doesn't exist
359 if not os
.path
.exists(F
):
361 # always update "Output" if any "Input" is newer than "Output"
362 if os
.path
.getmtime(F
) > OutputTime
:
367 def GenerateSection(Output
, Input
, Type
=None, CompressionType
=None, Guid
=None,
368 GuidHdrLen
=None, GuidAttr
=[], Ui
=None, Ver
=None, InputAlign
=None, BuildNumber
=None):
370 if Type
not in [None, '']:
372 if CompressionType
not in [None, '']:
373 Cmd
+= ["-c", CompressionType
]
376 if GuidHdrLen
not in [None, '']:
377 Cmd
+= ["-l", GuidHdrLen
]
378 if len(GuidAttr
) != 0:
379 #Add each guided attribute
380 for Attr
in GuidAttr
:
382 if InputAlign
!= None:
383 #Section Align is only for dummy section without section type
384 for SecAlign
in InputAlign
:
385 Cmd
+= ["--sectionalign", SecAlign
]
387 CommandFile
= Output
+ '.txt'
388 if Ui
not in [None, '']:
389 #Cmd += ["-n", '"' + Ui + '"']
390 SectionData
= array
.array('B', [0, 0, 0, 0])
391 SectionData
.fromstring(Ui
.encode("utf_16_le"))
392 SectionData
.append(0)
393 SectionData
.append(0)
394 Len
= len(SectionData
)
395 GenFdsGlobalVariable
.SectionHeader
.pack_into(SectionData
, 0, Len
& 0xff, (Len
>> 8) & 0xff, (Len
>> 16) & 0xff, 0x15)
396 SaveFileOnChange(Output
, SectionData
.tostring())
397 elif Ver
not in [None, '']:
400 Cmd
+= ["-j", BuildNumber
]
401 Cmd
+= ["-o", Output
]
403 SaveFileOnChange(CommandFile
, ' '.join(Cmd
), False)
404 if not GenFdsGlobalVariable
.NeedsUpdate(Output
, list(Input
) + [CommandFile
]):
407 GenFdsGlobalVariable
.CallExternalTool(Cmd
, "Failed to generate section")
409 Cmd
+= ["-o", Output
]
412 SaveFileOnChange(CommandFile
, ' '.join(Cmd
), False)
413 if GenFdsGlobalVariable
.NeedsUpdate(Output
, list(Input
) + [CommandFile
]):
414 GenFdsGlobalVariable
.DebugLogger(EdkLogger
.DEBUG_5
, "%s needs update because of newer %s" % (Output
, Input
))
415 GenFdsGlobalVariable
.CallExternalTool(Cmd
, "Failed to generate section")
417 if (os
.path
.getsize(Output
) >= GenFdsGlobalVariable
.LARGE_FILE_SIZE
and
418 GenFdsGlobalVariable
.LargeFileInFvFlags
):
419 GenFdsGlobalVariable
.LargeFileInFvFlags
[-1] = True
422 def GetAlignment (AlignString
):
423 if AlignString
== None:
425 if AlignString
in ("1K", "2K", "4K", "8K", "16K", "32K", "64K"):
426 return int (AlignString
.rstrip('K')) * 1024
428 return int (AlignString
)
431 def GenerateFfs(Output
, Input
, Type
, Guid
, Fixed
=False, CheckSum
=False, Align
=None,
433 Cmd
= ["GenFfs", "-t", Type
, "-g", Guid
]
438 if Align
not in [None, '']:
441 Cmd
+= ["-o", Output
]
442 for I
in range(0, len(Input
)):
443 Cmd
+= ("-i", Input
[I
])
444 if SectionAlign
not in [None, '', []] and SectionAlign
[I
] not in [None, '']:
445 Cmd
+= ("-n", SectionAlign
[I
])
447 CommandFile
= Output
+ '.txt'
448 SaveFileOnChange(CommandFile
, ' '.join(Cmd
), False)
449 if not GenFdsGlobalVariable
.NeedsUpdate(Output
, list(Input
) + [CommandFile
]):
451 GenFdsGlobalVariable
.DebugLogger(EdkLogger
.DEBUG_5
, "%s needs update because of newer %s" % (Output
, Input
))
453 GenFdsGlobalVariable
.CallExternalTool(Cmd
, "Failed to generate FFS")
456 def GenerateFirmwareVolume(Output
, Input
, BaseAddress
=None, ForceRebase
=None, Capsule
=False, Dump
=False,
457 AddressFile
=None, MapFile
=None, FfsList
=[], FileSystemGuid
=None):
458 if not GenFdsGlobalVariable
.NeedsUpdate(Output
, Input
+FfsList
):
460 GenFdsGlobalVariable
.DebugLogger(EdkLogger
.DEBUG_5
, "%s needs update because of newer %s" % (Output
, Input
))
463 if BaseAddress
not in [None, '']:
464 Cmd
+= ["-r", BaseAddress
]
466 if ForceRebase
== False:
467 Cmd
+= ["-F", "FALSE"]
468 elif ForceRebase
== True:
469 Cmd
+= ["-F", "TRUE"]
475 if AddressFile
not in [None, '']:
476 Cmd
+= ["-a", AddressFile
]
477 if MapFile
not in [None, '']:
478 Cmd
+= ["-m", MapFile
]
480 Cmd
+= ["-g", FileSystemGuid
]
481 Cmd
+= ["-o", Output
]
485 GenFdsGlobalVariable
.CallExternalTool(Cmd
, "Failed to generate FV")
488 def GenerateVtf(Output
, Input
, BaseAddress
=None, FvSize
=None):
489 if not GenFdsGlobalVariable
.NeedsUpdate(Output
, Input
):
491 GenFdsGlobalVariable
.DebugLogger(EdkLogger
.DEBUG_5
, "%s needs update because of newer %s" % (Output
, Input
))
494 if BaseAddress
not in [None, ''] and FvSize
not in [None, ''] \
495 and len(BaseAddress
) == len(FvSize
):
496 for I
in range(0, len(BaseAddress
)):
497 Cmd
+= ["-r", BaseAddress
[I
], "-s", FvSize
[I
]]
498 Cmd
+= ["-o", Output
]
502 GenFdsGlobalVariable
.CallExternalTool(Cmd
, "Failed to generate VTF")
505 def GenerateFirmwareImage(Output
, Input
, Type
="efi", SubType
=None, Zero
=False,
506 Strip
=False, Replace
=False, TimeStamp
=None, Join
=False,
507 Align
=None, Padding
=None, Convert
=False):
508 if not GenFdsGlobalVariable
.NeedsUpdate(Output
, Input
):
510 GenFdsGlobalVariable
.DebugLogger(EdkLogger
.DEBUG_5
, "%s needs update because of newer %s" % (Output
, Input
))
513 if Type
.lower() == "te":
515 if SubType
not in [None, '']:
516 Cmd
+= ["-e", SubType
]
517 if TimeStamp
not in [None, '']:
518 Cmd
+= ["-s", TimeStamp
]
519 if Align
not in [None, '']:
521 if Padding
not in [None, '']:
522 Cmd
+= ["-p", Padding
]
533 Cmd
+= ["-o", Output
]
536 GenFdsGlobalVariable
.CallExternalTool(Cmd
, "Failed to generate firmware image")
539 def GenerateOptionRom(Output
, EfiInput
, BinaryInput
, Compress
=False, ClassCode
=None,
540 Revision
=None, DeviceId
=None, VendorId
=None):
543 if len(EfiInput
) > 0:
550 for EfiFile
in EfiInput
:
552 InputList
.append (EfiFile
)
554 if len(BinaryInput
) > 0:
556 for BinFile
in BinaryInput
:
558 InputList
.append (BinFile
)
561 if not GenFdsGlobalVariable
.NeedsUpdate(Output
, InputList
):
563 GenFdsGlobalVariable
.DebugLogger(EdkLogger
.DEBUG_5
, "%s needs update because of newer %s" % (Output
, InputList
))
565 if ClassCode
!= None:
566 Cmd
+= ["-l", ClassCode
]
568 Cmd
+= ["-r", Revision
]
570 Cmd
+= ["-i", DeviceId
]
572 Cmd
+= ["-f", VendorId
]
574 Cmd
+= ["-o", Output
]
575 GenFdsGlobalVariable
.CallExternalTool(Cmd
, "Failed to generate option rom")
578 def GuidTool(Output
, Input
, ToolPath
, Options
='', returnValue
=[]):
579 if not GenFdsGlobalVariable
.NeedsUpdate(Output
, Input
):
581 GenFdsGlobalVariable
.DebugLogger(EdkLogger
.DEBUG_5
, "%s needs update because of newer %s" % (Output
, Input
))
584 Cmd
+= Options
.split(' ')
585 Cmd
+= ["-o", Output
]
588 GenFdsGlobalVariable
.CallExternalTool(Cmd
, "Failed to call " + ToolPath
, returnValue
)
590 def CallExternalTool (cmd
, errorMess
, returnValue
=[]):
592 if type(cmd
) not in (tuple, list):
593 GenFdsGlobalVariable
.ErrorLogger("ToolError! Invalid parameter type in call to CallExternalTool")
595 if GenFdsGlobalVariable
.DebugLevel
!= -1:
596 cmd
+= ('--debug', str(GenFdsGlobalVariable
.DebugLevel
))
597 GenFdsGlobalVariable
.InfLogger (cmd
)
599 if GenFdsGlobalVariable
.VerboseMode
:
601 GenFdsGlobalVariable
.InfLogger (cmd
)
603 sys
.stdout
.write ('#')
605 GenFdsGlobalVariable
.SharpCounter
= GenFdsGlobalVariable
.SharpCounter
+ 1
606 if GenFdsGlobalVariable
.SharpCounter
% GenFdsGlobalVariable
.SharpNumberPerLine
== 0:
607 sys
.stdout
.write('\n')
610 PopenObject
= subprocess
.Popen(' '.join(cmd
), stdout
=subprocess
.PIPE
, stderr
=subprocess
.PIPE
, shell
=True)
612 EdkLogger
.error("GenFds", COMMAND_FAILURE
, ExtraData
="%s: %s" % (str(X
), cmd
[0]))
613 (out
, error
) = PopenObject
.communicate()
615 while PopenObject
.returncode
== None :
617 if returnValue
!= [] and returnValue
[0] != 0:
618 #get command return value
619 returnValue
[0] = PopenObject
.returncode
621 if PopenObject
.returncode
!= 0 or GenFdsGlobalVariable
.VerboseMode
or GenFdsGlobalVariable
.DebugLevel
!= -1:
622 GenFdsGlobalVariable
.InfLogger ("Return Value = %d" % PopenObject
.returncode
)
623 GenFdsGlobalVariable
.InfLogger (out
)
624 GenFdsGlobalVariable
.InfLogger (error
)
625 if PopenObject
.returncode
!= 0:
627 EdkLogger
.error("GenFds", COMMAND_FAILURE
, errorMess
)
629 def VerboseLogger (msg
):
630 EdkLogger
.verbose(msg
)
635 def ErrorLogger (msg
, File
=None, Line
=None, ExtraData
=None):
636 EdkLogger
.error('GenFds', GENFDS_ERROR
, msg
, File
, Line
, ExtraData
)
638 def DebugLogger (Level
, msg
):
639 EdkLogger
.debug(Level
, msg
)
641 ## ReplaceWorkspaceMacro()
643 # @param Str String that may contain macro
644 # @param MacroDict Dictionary that contains macro value pair
646 def MacroExtend (Str
, MacroDict
={}, Arch
='COMMON'):
650 Dict
= {'$(WORKSPACE)' : GenFdsGlobalVariable
.WorkSpaceDir
,
651 '$(EDK_SOURCE)' : GenFdsGlobalVariable
.EdkSourceDir
,
652 # '$(OUTPUT_DIRECTORY)': GenFdsGlobalVariable.OutputDirFromDsc,
653 '$(TARGET)' : GenFdsGlobalVariable
.TargetName
,
654 '$(TOOL_CHAIN_TAG)' : GenFdsGlobalVariable
.ToolChainTag
,
657 OutputDir
= GenFdsGlobalVariable
.OutputDirFromDscDict
[GenFdsGlobalVariable
.ArchList
[0]]
658 if Arch
!= 'COMMON' and Arch
in GenFdsGlobalVariable
.ArchList
:
659 OutputDir
= GenFdsGlobalVariable
.OutputDirFromDscDict
[Arch
]
661 Dict
['$(OUTPUT_DIRECTORY)'] = OutputDir
663 if MacroDict
!= None and len (MacroDict
) != 0:
664 Dict
.update(MacroDict
)
666 for key
in Dict
.keys():
667 if Str
.find(key
) >= 0 :
668 Str
= Str
.replace (key
, Dict
[key
])
670 if Str
.find('$(ARCH)') >= 0:
671 if len(GenFdsGlobalVariable
.ArchList
) == 1:
672 Str
= Str
.replace('$(ARCH)', GenFdsGlobalVariable
.ArchList
[0])
674 EdkLogger
.error("GenFds", GENFDS_ERROR
, "No way to determine $(ARCH) for %s" % Str
)
680 # @param PcdPattern pattern that labels a PCD.
682 def GetPcdValue (PcdPattern
):
683 if PcdPattern
== None :
685 PcdPair
= PcdPattern
.lstrip('PCD(').rstrip(')').strip().split('.')
686 TokenSpace
= PcdPair
[0]
687 TokenCName
= PcdPair
[1]
690 for Arch
in GenFdsGlobalVariable
.ArchList
:
691 Platform
= GenFdsGlobalVariable
.WorkSpace
.BuildObject
[GenFdsGlobalVariable
.ActivePlatform
, Arch
, GenFdsGlobalVariable
.TargetName
, GenFdsGlobalVariable
.ToolChainTag
]
692 PcdDict
= Platform
.Pcds
694 PcdObj
= PcdDict
[Key
]
695 if (PcdObj
.TokenCName
== TokenCName
) and (PcdObj
.TokenSpaceGuidCName
== TokenSpace
):
696 if PcdObj
.Type
!= 'FixedAtBuild':
697 EdkLogger
.error("GenFds", GENFDS_ERROR
, "%s is not FixedAtBuild type." % PcdPattern
)
698 if PcdObj
.DatumType
!= 'VOID*':
699 EdkLogger
.error("GenFds", GENFDS_ERROR
, "%s is not VOID* datum type." % PcdPattern
)
701 PcdValue
= PcdObj
.DefaultValue
704 for Package
in GenFdsGlobalVariable
.WorkSpace
.GetPackageList(GenFdsGlobalVariable
.ActivePlatform
,
706 GenFdsGlobalVariable
.TargetName
,
707 GenFdsGlobalVariable
.ToolChainTag
):
708 PcdDict
= Package
.Pcds
710 PcdObj
= PcdDict
[Key
]
711 if (PcdObj
.TokenCName
== TokenCName
) and (PcdObj
.TokenSpaceGuidCName
== TokenSpace
):
712 if PcdObj
.Type
!= 'FixedAtBuild':
713 EdkLogger
.error("GenFds", GENFDS_ERROR
, "%s is not FixedAtBuild type." % PcdPattern
)
714 if PcdObj
.DatumType
!= 'VOID*':
715 EdkLogger
.error("GenFds", GENFDS_ERROR
, "%s is not VOID* datum type." % PcdPattern
)
717 PcdValue
= PcdObj
.DefaultValue
722 SetDir
= staticmethod(SetDir
)
723 ReplaceWorkspaceMacro
= staticmethod(ReplaceWorkspaceMacro
)
724 CallExternalTool
= staticmethod(CallExternalTool
)
725 VerboseLogger
= staticmethod(VerboseLogger
)
726 InfLogger
= staticmethod(InfLogger
)
727 ErrorLogger
= staticmethod(ErrorLogger
)
728 DebugLogger
= staticmethod(DebugLogger
)
729 MacroExtend
= staticmethod (MacroExtend
)
730 GetPcdValue
= staticmethod(GetPcdValue
)