1## @file 2# process FFS generation from INF statement 3# 4# Copyright (c) 2007 - 2015, Intel Corporation. All rights reserved.<BR> 5# Copyright (c) 2014 Hewlett-Packard Development Company, L.P.<BR> 6# 7# This program and the accompanying materials 8# are licensed and made available under the terms and conditions of the BSD License 9# which accompanies this distribution. The full text of the license may be found at 10# http://opensource.org/licenses/bsd-license.php 11# 12# THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS, 13# WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED. 14# 15 16## 17# Import Modules 18# 19import Rule 20import Common.LongFilePathOs as os 21import StringIO 22from struct import * 23from GenFdsGlobalVariable import GenFdsGlobalVariable 24import Ffs 25import subprocess 26import sys 27import Section 28import RuleSimpleFile 29import RuleComplexFile 30from CommonDataClass.FdfClass import FfsInfStatementClassObject 31from Common.MultipleWorkspace import MultipleWorkspace as mws 32from Common.String import * 33from Common.Misc import PathClass 34from Common.Misc import GuidStructureByteArrayToGuidString 35from Common.Misc import ProcessDuplicatedInf 36from Common.Misc import GetVariableOffset 37from Common import EdkLogger 38from Common.BuildToolError import * 39from GuidSection import GuidSection 40from FvImageSection import FvImageSection 41from Common.Misc import PeImageClass 42from AutoGen.GenDepex import DependencyExpression 43from PatchPcdValue.PatchPcdValue import PatchBinaryFile 44from Common.LongFilePathSupport import CopyLongFilePath 45from Common.LongFilePathSupport import OpenLongFilePath as open 46 47## generate FFS from INF 48# 49# 50class FfsInfStatement(FfsInfStatementClassObject): 51 ## The mapping dictionary from datum type to its maximum number. 52 _MAX_SIZE_TYPE = {"BOOLEAN":0x01, "UINT8":0xFF, "UINT16":0xFFFF, "UINT32":0xFFFFFFFF, "UINT64":0xFFFFFFFFFFFFFFFF} 53 ## The constructor 54 # 55 # @param self The object pointer 56 # 57 def __init__(self): 58 FfsInfStatementClassObject.__init__(self) 59 self.TargetOverrideList = [] 60 self.ShadowFromInfFile = None 61 self.KeepRelocFromRule = None 62 self.InDsc = True 63 self.OptRomDefs = {} 64 self.PiSpecVersion = '0x00000000' 65 self.InfModule = None 66 self.FinalTargetSuffixMap = {} 67 self.CurrentLineNum = None 68 self.CurrentLineContent = None 69 self.FileName = None 70 self.InfFileName = None 71 self.OverrideGuid = None 72 self.PatchedBinFile = '' 73 self.MacroDict = {} 74 75 ## GetFinalTargetSuffixMap() method 76 # 77 # Get final build target list 78 def GetFinalTargetSuffixMap(self): 79 if not self.InfModule or not self.CurrentArch: 80 return [] 81 if not self.FinalTargetSuffixMap: 82 FinalBuildTargetList = GenFdsGlobalVariable.GetModuleCodaTargetList(self.InfModule, self.CurrentArch) 83 for File in FinalBuildTargetList: 84 self.FinalTargetSuffixMap.setdefault(os.path.splitext(File)[1], []).append(File) 85 86 # Check if current INF module has DEPEX 87 if '.depex' not in self.FinalTargetSuffixMap and self.InfModule.ModuleType != "USER_DEFINED" \ 88 and not self.InfModule.DxsFile and not self.InfModule.LibraryClass: 89 ModuleType = self.InfModule.ModuleType 90 PlatformDataBase = GenFdsGlobalVariable.WorkSpace.BuildObject[GenFdsGlobalVariable.ActivePlatform, self.CurrentArch, GenFdsGlobalVariable.TargetName, GenFdsGlobalVariable.ToolChainTag] 91 92 if ModuleType != DataType.SUP_MODULE_USER_DEFINED: 93 for LibraryClass in PlatformDataBase.LibraryClasses.GetKeys(): 94 if LibraryClass.startswith("NULL") and PlatformDataBase.LibraryClasses[LibraryClass, ModuleType]: 95 self.InfModule.LibraryClasses[LibraryClass] = PlatformDataBase.LibraryClasses[LibraryClass, ModuleType] 96 97 StrModule = str(self.InfModule) 98 PlatformModule = None 99 if StrModule in PlatformDataBase.Modules: 100 PlatformModule = PlatformDataBase.Modules[StrModule] 101 for LibraryClass in PlatformModule.LibraryClasses: 102 if LibraryClass.startswith("NULL"): 103 self.InfModule.LibraryClasses[LibraryClass] = PlatformModule.LibraryClasses[LibraryClass] 104 105 DependencyList = [self.InfModule] 106 LibraryInstance = {} 107 DepexList = [] 108 while len(DependencyList) > 0: 109 Module = DependencyList.pop(0) 110 if not Module: 111 continue 112 for Dep in Module.Depex[self.CurrentArch, ModuleType]: 113 if DepexList != []: 114 DepexList.append('AND') 115 DepexList.append('(') 116 DepexList.extend(Dep) 117 if DepexList[-1] == 'END': # no need of a END at this time 118 DepexList.pop() 119 DepexList.append(')') 120 if 'BEFORE' in DepexList or 'AFTER' in DepexList: 121 break 122 for LibName in Module.LibraryClasses: 123 if LibName in LibraryInstance: 124 continue 125 if PlatformModule and LibName in PlatformModule.LibraryClasses: 126 LibraryPath = PlatformModule.LibraryClasses[LibName] 127 else: 128 LibraryPath = PlatformDataBase.LibraryClasses[LibName, ModuleType] 129 if not LibraryPath: 130 LibraryPath = Module.LibraryClasses[LibName] 131 if not LibraryPath: 132 continue 133 LibraryModule = GenFdsGlobalVariable.WorkSpace.BuildObject[LibraryPath, self.CurrentArch, GenFdsGlobalVariable.TargetName, GenFdsGlobalVariable.ToolChainTag] 134 LibraryInstance[LibName] = LibraryModule 135 DependencyList.append(LibraryModule) 136 if DepexList: 137 Dpx = DependencyExpression(DepexList, ModuleType, True) 138 if len(Dpx.PostfixNotation) != 0: 139 # It means this module has DEPEX 140 self.FinalTargetSuffixMap['.depex'] = [os.path.join(self.EfiOutputPath, self.BaseName) + '.depex'] 141 return self.FinalTargetSuffixMap 142 143 ## __InfParse() method 144 # 145 # Parse inf file to get module information 146 # 147 # @param self The object pointer 148 # @param Dict dictionary contains macro and value pair 149 # 150 def __InfParse__(self, Dict = {}): 151 152 GenFdsGlobalVariable.VerboseLogger( " Begine parsing INf file : %s" %self.InfFileName) 153 154 self.InfFileName = self.InfFileName.replace('$(WORKSPACE)', '') 155 if len(self.InfFileName) > 1 and self.InfFileName[0] == '\\' and self.InfFileName[1] == '\\': 156 pass 157 elif self.InfFileName[0] == '\\' or self.InfFileName[0] == '/' : 158 self.InfFileName = self.InfFileName[1:] 159 160 if self.InfFileName.find('$') == -1: 161 InfPath = NormPath(self.InfFileName) 162 if not os.path.exists(InfPath): 163 InfPath = GenFdsGlobalVariable.ReplaceWorkspaceMacro(InfPath) 164 if not os.path.exists(InfPath): 165 EdkLogger.error("GenFds", GENFDS_ERROR, "Non-existant Module %s !" % (self.InfFileName)) 166 167 self.CurrentArch = self.GetCurrentArch() 168 # 169 # Get the InfClass object 170 # 171 172 PathClassObj = PathClass(self.InfFileName, GenFdsGlobalVariable.WorkSpaceDir) 173 ErrorCode, ErrorInfo = PathClassObj.Validate(".inf") 174 if ErrorCode != 0: 175 EdkLogger.error("GenFds", ErrorCode, ExtraData=ErrorInfo) 176 177 # 178 # Cache lower case version of INF path before processing FILE_GUID override 179 # 180 InfLowerPath = str(PathClassObj).lower() 181 if self.OverrideGuid: 182 PathClassObj = ProcessDuplicatedInf(PathClassObj, self.OverrideGuid, GenFdsGlobalVariable.WorkSpaceDir) 183 if self.CurrentArch != None: 184 185 Inf = GenFdsGlobalVariable.WorkSpace.BuildObject[PathClassObj, self.CurrentArch, GenFdsGlobalVariable.TargetName, GenFdsGlobalVariable.ToolChainTag] 186 # 187 # Set Ffs BaseName, MdouleGuid, ModuleType, Version, OutputPath 188 # 189 self.BaseName = Inf.BaseName 190 self.ModuleGuid = Inf.Guid 191 self.ModuleType = Inf.ModuleType 192 if Inf.Specification != None and 'PI_SPECIFICATION_VERSION' in Inf.Specification: 193 self.PiSpecVersion = Inf.Specification['PI_SPECIFICATION_VERSION'] 194 if Inf.AutoGenVersion < 0x00010005: 195 self.ModuleType = Inf.ComponentType 196 self.VersionString = Inf.Version 197 self.BinFileList = Inf.Binaries 198 self.SourceFileList = Inf.Sources 199 if self.KeepReloc == None and Inf.Shadow: 200 self.ShadowFromInfFile = Inf.Shadow 201 202 else: 203 Inf = GenFdsGlobalVariable.WorkSpace.BuildObject[PathClassObj, 'COMMON', GenFdsGlobalVariable.TargetName, GenFdsGlobalVariable.ToolChainTag] 204 self.BaseName = Inf.BaseName 205 self.ModuleGuid = Inf.Guid 206 self.ModuleType = Inf.ModuleType 207 if Inf.Specification != None and 'PI_SPECIFICATION_VERSION' in Inf.Specification: 208 self.PiSpecVersion = Inf.Specification['PI_SPECIFICATION_VERSION'] 209 self.VersionString = Inf.Version 210 self.BinFileList = Inf.Binaries 211 self.SourceFileList = Inf.Sources 212 if self.BinFileList == []: 213 EdkLogger.error("GenFds", GENFDS_ERROR, 214 "INF %s specified in FDF could not be found in build ARCH %s!" \ 215 % (self.InfFileName, GenFdsGlobalVariable.ArchList)) 216 217 if self.OverrideGuid: 218 self.ModuleGuid = self.OverrideGuid 219 220 if len(self.SourceFileList) != 0 and not self.InDsc: 221 EdkLogger.warn("GenFds", GENFDS_ERROR, "Module %s NOT found in DSC file; Is it really a binary module?" % (self.InfFileName)) 222 223 if self.ModuleType == 'SMM_CORE' and int(self.PiSpecVersion, 16) < 0x0001000A: 224 EdkLogger.error("GenFds", FORMAT_NOT_SUPPORTED, "SMM_CORE module type can't be used in the module with PI_SPECIFICATION_VERSION less than 0x0001000A", File=self.InfFileName) 225 226 if Inf._Defs != None and len(Inf._Defs) > 0: 227 self.OptRomDefs.update(Inf._Defs) 228 229 self.PatchPcds = [] 230 InfPcds = Inf.Pcds 231 Platform = GenFdsGlobalVariable.WorkSpace.BuildObject[GenFdsGlobalVariable.ActivePlatform, self.CurrentArch, GenFdsGlobalVariable.TargetName, GenFdsGlobalVariable.ToolChainTag] 232 FdfPcdDict = GenFdsGlobalVariable.FdfParser.Profile.PcdDict 233 234 # Workaround here: both build and GenFds tool convert the workspace path to lower case 235 # But INF file path in FDF and DSC file may have real case characters. 236 # Try to convert the path to lower case to see if PCDs value are override by DSC. 237 DscModules = {} 238 for DscModule in Platform.Modules: 239 DscModules[str(DscModule).lower()] = Platform.Modules[DscModule] 240 for PcdKey in InfPcds: 241 Pcd = InfPcds[PcdKey] 242 if not hasattr(Pcd, 'Offset'): 243 continue 244 if Pcd.Type != 'PatchableInModule': 245 continue 246 # Override Patchable PCD value by the value from DSC 247 PatchPcd = None 248 if InfLowerPath in DscModules and PcdKey in DscModules[InfLowerPath].Pcds: 249 PatchPcd = DscModules[InfLowerPath].Pcds[PcdKey] 250 elif PcdKey in Platform.Pcds: 251 PatchPcd = Platform.Pcds[PcdKey] 252 DscOverride = False 253 if PatchPcd and Pcd.Type == PatchPcd.Type: 254 DefaultValue = PatchPcd.DefaultValue 255 DscOverride = True 256 257 # Override Patchable PCD value by the value from FDF 258 FdfOverride = False 259 if PcdKey in FdfPcdDict: 260 DefaultValue = FdfPcdDict[PcdKey] 261 FdfOverride = True 262 263 if not DscOverride and not FdfOverride: 264 continue 265 # Check value, if value are equal, no need to patch 266 if Pcd.DatumType == "VOID*": 267 if Pcd.DefaultValue == DefaultValue or DefaultValue in [None, '']: 268 continue 269 # Get the string size from FDF or DSC 270 if DefaultValue[0] == 'L': 271 # Remove L"", but the '\0' must be appended 272 MaxDatumSize = str((len(DefaultValue) - 2) * 2) 273 elif DefaultValue[0] == '{': 274 MaxDatumSize = str(len(DefaultValue.split(','))) 275 else: 276 MaxDatumSize = str(len(DefaultValue) - 1) 277 if DscOverride: 278 Pcd.MaxDatumSize = PatchPcd.MaxDatumSize 279 # If no defined the maximum size in DSC, try to get current size from INF 280 if Pcd.MaxDatumSize in ['', None]: 281 Pcd.MaxDatumSize = str(len(Pcd.DefaultValue.split(','))) 282 else: 283 Base1 = Base2 = 10 284 if Pcd.DefaultValue.upper().startswith('0X'): 285 Base1 = 16 286 if DefaultValue.upper().startswith('0X'): 287 Base2 = 16 288 try: 289 PcdValueInImg = int(Pcd.DefaultValue, Base1) 290 PcdValueInDscOrFdf = int(DefaultValue, Base2) 291 if PcdValueInImg == PcdValueInDscOrFdf: 292 continue 293 except: 294 continue 295 # Check the Pcd size and data type 296 if Pcd.DatumType == "VOID*": 297 if int(MaxDatumSize) > int(Pcd.MaxDatumSize): 298 EdkLogger.error("GenFds", GENFDS_ERROR, "The size of VOID* type PCD '%s.%s' exceeds its maximum size %d bytes." \ 299 % (Pcd.TokenSpaceGuidCName, Pcd.TokenCName, int(MaxDatumSize) - int(Pcd.MaxDatumSize))) 300 else: 301 if PcdValueInDscOrFdf > FfsInfStatement._MAX_SIZE_TYPE[Pcd.DatumType] \ 302 or PcdValueInImg > FfsInfStatement._MAX_SIZE_TYPE[Pcd.DatumType]: 303 EdkLogger.error("GenFds", GENFDS_ERROR, "The size of %s type PCD '%s.%s' doesn't match its data type." \ 304 % (Pcd.DatumType, Pcd.TokenSpaceGuidCName, Pcd.TokenCName)) 305 self.PatchPcds.append((Pcd, DefaultValue)) 306 307 self.InfModule = Inf 308 self.PcdIsDriver = Inf.PcdIsDriver 309 self.IsBinaryModule = Inf.IsBinaryModule 310 GenFdsGlobalVariable.VerboseLogger("BaseName : %s" % self.BaseName) 311 GenFdsGlobalVariable.VerboseLogger("ModuleGuid : %s" % self.ModuleGuid) 312 GenFdsGlobalVariable.VerboseLogger("ModuleType : %s" % self.ModuleType) 313 GenFdsGlobalVariable.VerboseLogger("VersionString : %s" % self.VersionString) 314 GenFdsGlobalVariable.VerboseLogger("InfFileName :%s" % self.InfFileName) 315 316 # 317 # Set OutputPath = ${WorkSpace}\Build\Fv\Ffs\${ModuleGuid}+ ${MdouleName}\ 318 # 319 320 self.OutputPath = os.path.join(GenFdsGlobalVariable.FfsDir, \ 321 self.ModuleGuid + self.BaseName) 322 if not os.path.exists(self.OutputPath) : 323 os.makedirs(self.OutputPath) 324 325 self.EfiOutputPath = self.__GetEFIOutPutPath__() 326 GenFdsGlobalVariable.VerboseLogger( "ModuelEFIPath: " + self.EfiOutputPath) 327 328 ## PatchEfiFile 329 # 330 # Patch EFI file with patch PCD 331 # 332 # @param EfiFile: EFI file needs to be patched. 333 # @retval: Full path of patched EFI file: self.OutputPath + EfiFile base name 334 # If passed in file does not end with efi, return as is 335 # 336 def PatchEfiFile(self, EfiFile, FileType): 337 # 338 # If the module does not have any patches, then return path to input file 339 # 340 if not self.PatchPcds: 341 return EfiFile 342 343 # 344 # Only patch file if FileType is PE32 or ModuleType is USER_DEFINED 345 # 346 if FileType != 'PE32' and self.ModuleType != "USER_DEFINED": 347 return EfiFile 348 349 # 350 # Generate path to patched output file 351 # 352 Basename = os.path.basename(EfiFile) 353 Output = os.path.normpath (os.path.join(self.OutputPath, Basename)) 354 355 # 356 # If this file has already been patched, then return the path to the patched file 357 # 358 if self.PatchedBinFile == Output: 359 return Output 360 361 # 362 # If a different file from the same module has already been patched, then generate an error 363 # 364 if self.PatchedBinFile: 365 EdkLogger.error("GenFds", GENFDS_ERROR, 366 'Only one binary file can be patched:\n' 367 ' a binary file has been patched: %s\n' 368 ' current file: %s' % (self.PatchedBinFile, EfiFile), 369 File=self.InfFileName) 370 371 # 372 # Copy unpatched file contents to output file location to perform patching 373 # 374 CopyLongFilePath(EfiFile, Output) 375 376 # 377 # Apply patches to patched output file 378 # 379 for Pcd, Value in self.PatchPcds: 380 RetVal, RetStr = PatchBinaryFile(Output, int(Pcd.Offset, 0), Pcd.DatumType, Value, Pcd.MaxDatumSize) 381 if RetVal: 382 EdkLogger.error("GenFds", GENFDS_ERROR, RetStr, File=self.InfFileName) 383 384 # 385 # Save the path of the patched output file 386 # 387 self.PatchedBinFile = Output 388 389 # 390 # Return path to patched output file 391 # 392 return Output 393 394 ## GenFfs() method 395 # 396 # Generate FFS 397 # 398 # @param self The object pointer 399 # @param Dict dictionary contains macro and value pair 400 # @param FvChildAddr Array of the inside FvImage base address 401 # @param FvParentAddr Parent Fv base address 402 # @retval string Generated FFS file name 403 # 404 def GenFfs(self, Dict = {}, FvChildAddr = [], FvParentAddr=None): 405 # 406 # Parse Inf file get Module related information 407 # 408 409 self.__InfParse__(Dict) 410 SrcFile = mws.join( GenFdsGlobalVariable.WorkSpaceDir , self.InfFileName); 411 DestFile = os.path.join( self.OutputPath, self.ModuleGuid + '.ffs') 412 413 SrcFileDir = "." 414 SrcPath = os.path.dirname(SrcFile) 415 SrcFileName = os.path.basename(SrcFile) 416 SrcFileBase, SrcFileExt = os.path.splitext(SrcFileName) 417 DestPath = os.path.dirname(DestFile) 418 DestFileName = os.path.basename(DestFile) 419 DestFileBase, DestFileExt = os.path.splitext(DestFileName) 420 self.MacroDict = { 421 # source file 422 "${src}" : SrcFile, 423 "${s_path}" : SrcPath, 424 "${s_dir}" : SrcFileDir, 425 "${s_name}" : SrcFileName, 426 "${s_base}" : SrcFileBase, 427 "${s_ext}" : SrcFileExt, 428 # destination file 429 "${dst}" : DestFile, 430 "${d_path}" : DestPath, 431 "${d_name}" : DestFileName, 432 "${d_base}" : DestFileBase, 433 "${d_ext}" : DestFileExt 434 } 435 # 436 # Allow binary type module not specify override rule in FDF file. 437 # 438 if len(self.BinFileList) > 0: 439 if self.Rule == None or self.Rule == "": 440 self.Rule = "BINARY" 441 442 # 443 # Get the rule of how to generate Ffs file 444 # 445 Rule = self.__GetRule__() 446 GenFdsGlobalVariable.VerboseLogger( "Packing binaries from inf file : %s" %self.InfFileName) 447 # 448 # Convert Fv File Type for PI1.1 SMM driver. 449 # 450 if self.ModuleType == 'DXE_SMM_DRIVER' and int(self.PiSpecVersion, 16) >= 0x0001000A: 451 if Rule.FvFileType == 'DRIVER': 452 Rule.FvFileType = 'SMM' 453 # 454 # Framework SMM Driver has no SMM FV file type 455 # 456 if self.ModuleType == 'DXE_SMM_DRIVER' and int(self.PiSpecVersion, 16) < 0x0001000A: 457 if Rule.FvFileType == 'SMM' or Rule.FvFileType == 'SMM_CORE': 458 EdkLogger.error("GenFds", FORMAT_NOT_SUPPORTED, "Framework SMM module doesn't support SMM or SMM_CORE FV file type", File=self.InfFileName) 459 # 460 # For the rule only has simpleFile 461 # 462 if isinstance (Rule, RuleSimpleFile.RuleSimpleFile) : 463 SectionOutputList = self.__GenSimpleFileSection__(Rule) 464 FfsOutput = self.__GenSimpleFileFfs__(Rule, SectionOutputList) 465 return FfsOutput 466 # 467 # For Rule has ComplexFile 468 # 469 elif isinstance(Rule, RuleComplexFile.RuleComplexFile): 470 InputSectList, InputSectAlignments = self.__GenComplexFileSection__(Rule, FvChildAddr, FvParentAddr) 471 FfsOutput = self.__GenComplexFileFfs__(Rule, InputSectList, InputSectAlignments) 472 473 return FfsOutput 474 475 ## __ExtendMacro__() method 476 # 477 # Replace macro with its value 478 # 479 # @param self The object pointer 480 # @param String The string to be replaced 481 # @retval string Macro replaced string 482 # 483 def __ExtendMacro__ (self, String): 484 MacroDict = { 485 '$(INF_OUTPUT)' : self.EfiOutputPath, 486 '$(MODULE_NAME)' : self.BaseName, 487 '$(BUILD_NUMBER)': self.BuildNum, 488 '$(INF_VERSION)' : self.VersionString, 489 '$(NAMED_GUID)' : self.ModuleGuid 490 } 491 String = GenFdsGlobalVariable.MacroExtend(String, MacroDict) 492 String = GenFdsGlobalVariable.MacroExtend(String, self.MacroDict) 493 return String 494 495 ## __GetRule__() method 496 # 497 # Get correct rule for generating FFS for this INF 498 # 499 # @param self The object pointer 500 # @retval Rule Rule object 501 # 502 def __GetRule__ (self) : 503 CurrentArchList = [] 504 if self.CurrentArch == None: 505 CurrentArchList = ['common'] 506 else: 507 CurrentArchList.append(self.CurrentArch) 508 509 for CurrentArch in CurrentArchList: 510 RuleName = 'RULE' + \ 511 '.' + \ 512 CurrentArch.upper() + \ 513 '.' + \ 514 self.ModuleType.upper() 515 if self.Rule != None: 516 RuleName = RuleName + \ 517 '.' + \ 518 self.Rule.upper() 519 520 Rule = GenFdsGlobalVariable.FdfParser.Profile.RuleDict.get(RuleName) 521 if Rule != None: 522 GenFdsGlobalVariable.VerboseLogger ("Want To Find Rule Name is : " + RuleName) 523 return Rule 524 525 RuleName = 'RULE' + \ 526 '.' + \ 527 'COMMON' + \ 528 '.' + \ 529 self.ModuleType.upper() 530 531 if self.Rule != None: 532 RuleName = RuleName + \ 533 '.' + \ 534 self.Rule.upper() 535 536 GenFdsGlobalVariable.VerboseLogger ('Trying to apply common rule %s for INF %s' % (RuleName, self.InfFileName)) 537 538 Rule = GenFdsGlobalVariable.FdfParser.Profile.RuleDict.get(RuleName) 539 if Rule != None: 540 GenFdsGlobalVariable.VerboseLogger ("Want To Find Rule Name is : " + RuleName) 541 return Rule 542 543 if Rule == None : 544 EdkLogger.error("GenFds", GENFDS_ERROR, 'Don\'t Find common rule %s for INF %s' \ 545 % (RuleName, self.InfFileName)) 546 547 ## __GetPlatformArchList__() method 548 # 549 # Get Arch list this INF built under 550 # 551 # @param self The object pointer 552 # @retval list Arch list 553 # 554 def __GetPlatformArchList__(self): 555 556 InfFileKey = os.path.normpath(mws.join(GenFdsGlobalVariable.WorkSpaceDir, self.InfFileName)) 557 DscArchList = [] 558 PlatformDataBase = GenFdsGlobalVariable.WorkSpace.BuildObject[GenFdsGlobalVariable.ActivePlatform, 'IA32', GenFdsGlobalVariable.TargetName, GenFdsGlobalVariable.ToolChainTag] 559 if PlatformDataBase != None: 560 if InfFileKey in PlatformDataBase.Modules: 561 DscArchList.append ('IA32') 562 563 PlatformDataBase = GenFdsGlobalVariable.WorkSpace.BuildObject[GenFdsGlobalVariable.ActivePlatform, 'X64', GenFdsGlobalVariable.TargetName, GenFdsGlobalVariable.ToolChainTag] 564 if PlatformDataBase != None: 565 if InfFileKey in PlatformDataBase.Modules: 566 DscArchList.append ('X64') 567 568 PlatformDataBase = GenFdsGlobalVariable.WorkSpace.BuildObject[GenFdsGlobalVariable.ActivePlatform, 'IPF', GenFdsGlobalVariable.TargetName, GenFdsGlobalVariable.ToolChainTag] 569 if PlatformDataBase != None: 570 if InfFileKey in (PlatformDataBase.Modules): 571 DscArchList.append ('IPF') 572 573 PlatformDataBase = GenFdsGlobalVariable.WorkSpace.BuildObject[GenFdsGlobalVariable.ActivePlatform, 'ARM', GenFdsGlobalVariable.TargetName, GenFdsGlobalVariable.ToolChainTag] 574 if PlatformDataBase != None: 575 if InfFileKey in (PlatformDataBase.Modules): 576 DscArchList.append ('ARM') 577 578 PlatformDataBase = GenFdsGlobalVariable.WorkSpace.BuildObject[GenFdsGlobalVariable.ActivePlatform, 'EBC', GenFdsGlobalVariable.TargetName, GenFdsGlobalVariable.ToolChainTag] 579 if PlatformDataBase != None: 580 if InfFileKey in (PlatformDataBase.Modules): 581 DscArchList.append ('EBC') 582 583 PlatformDataBase = GenFdsGlobalVariable.WorkSpace.BuildObject[GenFdsGlobalVariable.ActivePlatform, 'AARCH64', GenFdsGlobalVariable.TargetName, GenFdsGlobalVariable.ToolChainTag] 584 if PlatformDataBase != None: 585 if InfFileKey in (PlatformDataBase.Modules): 586 DscArchList.append ('AARCH64') 587 588 return DscArchList 589 590 ## GetCurrentArch() method 591 # 592 # Get Arch list of the module from this INF is to be placed into flash 593 # 594 # @param self The object pointer 595 # @retval list Arch list 596 # 597 def GetCurrentArch(self) : 598 599 TargetArchList = GenFdsGlobalVariable.ArchList 600 601 PlatformArchList = self.__GetPlatformArchList__() 602 603 CurArchList = TargetArchList 604 if PlatformArchList != []: 605 CurArchList = list(set (TargetArchList) & set (PlatformArchList)) 606 GenFdsGlobalVariable.VerboseLogger ("Valid target architecture(s) is : " + " ".join(CurArchList)) 607 608 ArchList = [] 609 if self.KeyStringList != []: 610 for Key in self.KeyStringList: 611 Key = GenFdsGlobalVariable.MacroExtend(Key) 612 Target, Tag, Arch = Key.split('_') 613 if Arch in CurArchList: 614 ArchList.append(Arch) 615 if Target not in self.TargetOverrideList: 616 self.TargetOverrideList.append(Target) 617 else: 618 ArchList = CurArchList 619 620 UseArchList = TargetArchList 621 if self.UseArch != None: 622 UseArchList = [] 623 UseArchList.append(self.UseArch) 624 ArchList = list(set (UseArchList) & set (ArchList)) 625 626 self.InfFileName = NormPath(self.InfFileName) 627 if len(PlatformArchList) == 0: 628 self.InDsc = False 629 PathClassObj = PathClass(self.InfFileName, GenFdsGlobalVariable.WorkSpaceDir) 630 ErrorCode, ErrorInfo = PathClassObj.Validate(".inf") 631 if ErrorCode != 0: 632 EdkLogger.error("GenFds", ErrorCode, ExtraData=ErrorInfo) 633 if len(ArchList) == 1: 634 Arch = ArchList[0] 635 return Arch 636 elif len(ArchList) > 1: 637 if len(PlatformArchList) == 0: 638 EdkLogger.error("GenFds", GENFDS_ERROR, "GenFds command line option has multiple ARCHs %s. Not able to determine which ARCH is valid for Module %s !" % (str(ArchList), self.InfFileName)) 639 else: 640 EdkLogger.error("GenFds", GENFDS_ERROR, "Module built under multiple ARCHs %s. Not able to determine which output to put into flash for Module %s !" % (str(ArchList), self.InfFileName)) 641 else: 642 EdkLogger.error("GenFds", GENFDS_ERROR, "Module %s appears under ARCH %s in platform %s, but current deduced ARCH is %s, so NO build output could be put into flash." \ 643 % (self.InfFileName, str(PlatformArchList), GenFdsGlobalVariable.ActivePlatform, str(set (UseArchList) & set (TargetArchList)))) 644 645 ## __GetEFIOutPutPath__() method 646 # 647 # Get the output path for generated files 648 # 649 # @param self The object pointer 650 # @retval string Path that output files from this INF go to 651 # 652 def __GetEFIOutPutPath__(self): 653 Arch = '' 654 OutputPath = '' 655 (ModulePath, FileName) = os.path.split(self.InfFileName) 656 Index = FileName.rfind('.') 657 FileName = FileName[0:Index] 658 if self.OverrideGuid: 659 FileName = self.OverrideGuid 660 Arch = "NoneArch" 661 if self.CurrentArch != None: 662 Arch = self.CurrentArch 663 664 OutputPath = os.path.join(GenFdsGlobalVariable.OutputDirDict[Arch], 665 Arch , 666 ModulePath, 667 FileName, 668 'OUTPUT' 669 ) 670 OutputPath = os.path.realpath(OutputPath) 671 return OutputPath 672 673 ## __GenSimpleFileSection__() method 674 # 675 # Generate section by specified file name or a list of files with file extension 676 # 677 # @param self The object pointer 678 # @param Rule The rule object used to generate section 679 # @retval string File name of the generated section file 680 # 681 def __GenSimpleFileSection__(self, Rule): 682 # 683 # Prepare the parameter of GenSection 684 # 685 FileList = [] 686 OutputFileList = [] 687 GenSecInputFile = None 688 if Rule.FileName != None: 689 GenSecInputFile = self.__ExtendMacro__(Rule.FileName) 690 if os.path.isabs(GenSecInputFile): 691 GenSecInputFile = os.path.normpath(GenSecInputFile) 692 else: 693 GenSecInputFile = os.path.normpath(os.path.join(self.EfiOutputPath, GenSecInputFile)) 694 else: 695 FileList, IsSect = Section.Section.GetFileList(self, '', Rule.FileExtension) 696 697 Index = 1 698 SectionType = Rule.SectionType 699 # 700 # Convert Fv Section Type for PI1.1 SMM driver. 701 # 702 if self.ModuleType == 'DXE_SMM_DRIVER' and int(self.PiSpecVersion, 16) >= 0x0001000A: 703 if SectionType == 'DXE_DEPEX': 704 SectionType = 'SMM_DEPEX' 705 # 706 # Framework SMM Driver has no SMM_DEPEX section type 707 # 708 if self.ModuleType == 'DXE_SMM_DRIVER' and int(self.PiSpecVersion, 16) < 0x0001000A: 709 if SectionType == 'SMM_DEPEX': 710 EdkLogger.error("GenFds", FORMAT_NOT_SUPPORTED, "Framework SMM module doesn't support SMM_DEPEX section type", File=self.InfFileName) 711 NoStrip = True 712 if self.ModuleType in ('SEC', 'PEI_CORE', 'PEIM'): 713 if self.KeepReloc != None: 714 NoStrip = self.KeepReloc 715 elif Rule.KeepReloc != None: 716 NoStrip = Rule.KeepReloc 717 elif self.ShadowFromInfFile != None: 718 NoStrip = self.ShadowFromInfFile 719 720 if FileList != [] : 721 for File in FileList: 722 723 SecNum = '%d' %Index 724 GenSecOutputFile= self.__ExtendMacro__(Rule.NameGuid) + \ 725 Ffs.Ffs.SectionSuffix[SectionType] + 'SEC' + SecNum 726 Index = Index + 1 727 OutputFile = os.path.join(self.OutputPath, GenSecOutputFile) 728 File = GenFdsGlobalVariable.MacroExtend(File, Dict, self.CurrentArch) 729 730 #Get PE Section alignment when align is set to AUTO 731 if self.Alignment == 'Auto' and (SectionType == 'PE32' or SectionType == 'TE'): 732 ImageObj = PeImageClass (File) 733 if ImageObj.SectionAlignment < 0x400: 734 self.Alignment = str (ImageObj.SectionAlignment) 735 else: 736 self.Alignment = str (ImageObj.SectionAlignment / 0x400) + 'K' 737 738 if not NoStrip: 739 FileBeforeStrip = os.path.join(self.OutputPath, ModuleName + '.reloc') 740 if not os.path.exists(FileBeforeStrip) or \ 741 (os.path.getmtime(File) > os.path.getmtime(FileBeforeStrip)): 742 CopyLongFilePath(File, FileBeforeStrip) 743 StrippedFile = os.path.join(self.OutputPath, ModuleName + '.stipped') 744 GenFdsGlobalVariable.GenerateFirmwareImage( 745 StrippedFile, 746 [File], 747 Strip=True 748 ) 749 File = StrippedFile 750 751 if SectionType == 'TE': 752 TeFile = os.path.join( self.OutputPath, self.ModuleGuid + 'Te.raw') 753 GenFdsGlobalVariable.GenerateFirmwareImage( 754 TeFile, 755 [File], 756 Type='te' 757 ) 758 File = TeFile 759 760 GenFdsGlobalVariable.GenerateSection(OutputFile, [File], Section.Section.SectionType[SectionType]) 761 OutputFileList.append(OutputFile) 762 else: 763 SecNum = '%d' %Index 764 GenSecOutputFile= self.__ExtendMacro__(Rule.NameGuid) + \ 765 Ffs.Ffs.SectionSuffix[SectionType] + 'SEC' + SecNum 766 OutputFile = os.path.join(self.OutputPath, GenSecOutputFile) 767 GenSecInputFile = GenFdsGlobalVariable.MacroExtend(GenSecInputFile, Dict, self.CurrentArch) 768 769 #Get PE Section alignment when align is set to AUTO 770 if self.Alignment == 'Auto' and (SectionType == 'PE32' or SectionType == 'TE'): 771 ImageObj = PeImageClass (GenSecInputFile) 772 if ImageObj.SectionAlignment < 0x400: 773 self.Alignment = str (ImageObj.SectionAlignment) 774 else: 775 self.Alignment = str (ImageObj.SectionAlignment / 0x400) + 'K' 776 777 if not NoStrip: 778 FileBeforeStrip = os.path.join(self.OutputPath, ModuleName + '.reloc') 779 if not os.path.exists(FileBeforeStrip) or \ 780 (os.path.getmtime(GenSecInputFile) > os.path.getmtime(FileBeforeStrip)): 781 CopyLongFilePath(GenSecInputFile, FileBeforeStrip) 782 783 StrippedFile = os.path.join(self.OutputPath, ModuleName + '.stipped') 784 GenFdsGlobalVariable.GenerateFirmwareImage( 785 StrippedFile, 786 [GenSecInputFile], 787 Strip=True 788 ) 789 GenSecInputFile = StrippedFile 790 791 if SectionType == 'TE': 792 TeFile = os.path.join( self.OutputPath, self.ModuleGuid + 'Te.raw') 793 GenFdsGlobalVariable.GenerateFirmwareImage( 794 TeFile, 795 [GenSecInputFile], 796 Type='te' 797 ) 798 GenSecInputFile = TeFile 799 800 GenFdsGlobalVariable.GenerateSection(OutputFile, [GenSecInputFile], Section.Section.SectionType[SectionType]) 801 OutputFileList.append(OutputFile) 802 803 return OutputFileList 804 805 ## __GenSimpleFileFfs__() method 806 # 807 # Generate FFS 808 # 809 # @param self The object pointer 810 # @param Rule The rule object used to generate section 811 # @param InputFileList The output file list from GenSection 812 # @retval string Generated FFS file name 813 # 814 def __GenSimpleFileFfs__(self, Rule, InputFileList): 815 FfsOutput = self.OutputPath + \ 816 os.sep + \ 817 self.__ExtendMacro__(Rule.NameGuid) + \ 818 '.ffs' 819 820 GenFdsGlobalVariable.VerboseLogger(self.__ExtendMacro__(Rule.NameGuid)) 821 InputSection = [] 822 SectionAlignments = [] 823 for InputFile in InputFileList: 824 InputSection.append(InputFile) 825 SectionAlignments.append(Rule.SectAlignment) 826 827 if Rule.NameGuid != None and Rule.NameGuid.startswith('PCD('): 828 PcdValue = GenFdsGlobalVariable.GetPcdValue(Rule.NameGuid) 829 if len(PcdValue) == 0: 830 EdkLogger.error("GenFds", GENFDS_ERROR, '%s NOT defined.' \ 831 % (Rule.NameGuid)) 832 if PcdValue.startswith('{'): 833 PcdValue = GuidStructureByteArrayToGuidString(PcdValue) 834 RegistryGuidStr = PcdValue 835 if len(RegistryGuidStr) == 0: 836 EdkLogger.error("GenFds", GENFDS_ERROR, 'GUID value for %s in wrong format.' \ 837 % (Rule.NameGuid)) 838 self.ModuleGuid = RegistryGuidStr 839 840 GenFdsGlobalVariable.GenerateFfs(FfsOutput, InputSection, 841 Ffs.Ffs.FdfFvFileTypeToFileType[Rule.FvFileType], 842 self.ModuleGuid, Fixed=Rule.Fixed, 843 CheckSum=Rule.CheckSum, Align=Rule.Alignment, 844 SectionAlign=SectionAlignments 845 ) 846 return FfsOutput 847 848 ## __GenComplexFileSection__() method 849 # 850 # Generate section by sections in Rule 851 # 852 # @param self The object pointer 853 # @param Rule The rule object used to generate section 854 # @param FvChildAddr Array of the inside FvImage base address 855 # @param FvParentAddr Parent Fv base address 856 # @retval string File name of the generated section file 857 # 858 def __GenComplexFileSection__(self, Rule, FvChildAddr, FvParentAddr): 859 if self.ModuleType in ('SEC', 'PEI_CORE', 'PEIM'): 860 if Rule.KeepReloc != None: 861 self.KeepRelocFromRule = Rule.KeepReloc 862 SectFiles = [] 863 SectAlignments = [] 864 Index = 1 865 HasGneratedFlag = False 866 if self.PcdIsDriver == 'PEI_PCD_DRIVER': 867 if self.IsBinaryModule: 868 PcdExDbFileName = os.path.join(GenFdsGlobalVariable.FvDir, "PEIPcdDataBase.raw") 869 else: 870 PcdExDbFileName = os.path.join(self.EfiOutputPath, "PEIPcdDataBase.raw") 871 PcdExDbSecName = os.path.join(self.OutputPath, "PEIPcdDataBaseSec.raw") 872 GenFdsGlobalVariable.GenerateSection(PcdExDbSecName, 873 [PcdExDbFileName], 874 "EFI_SECTION_RAW", 875 ) 876 SectFiles.append(PcdExDbSecName) 877 SectAlignments.append(None) 878 elif self.PcdIsDriver == 'DXE_PCD_DRIVER': 879 if self.IsBinaryModule: 880 PcdExDbFileName = os.path.join(GenFdsGlobalVariable.FvDir, "DXEPcdDataBase.raw") 881 else: 882 PcdExDbFileName = os.path.join(self.EfiOutputPath, "DXEPcdDataBase.raw") 883 PcdExDbSecName = os.path.join(self.OutputPath, "DXEPcdDataBaseSec.raw") 884 GenFdsGlobalVariable.GenerateSection(PcdExDbSecName, 885 [PcdExDbFileName], 886 "EFI_SECTION_RAW", 887 ) 888 SectFiles.append(PcdExDbSecName) 889 SectAlignments.append(None) 890 for Sect in Rule.SectionList: 891 SecIndex = '%d' %Index 892 SectList = [] 893 # 894 # Convert Fv Section Type for PI1.1 SMM driver. 895 # 896 if self.ModuleType == 'DXE_SMM_DRIVER' and int(self.PiSpecVersion, 16) >= 0x0001000A: 897 if Sect.SectionType == 'DXE_DEPEX': 898 Sect.SectionType = 'SMM_DEPEX' 899 # 900 # Framework SMM Driver has no SMM_DEPEX section type 901 # 902 if self.ModuleType == 'DXE_SMM_DRIVER' and int(self.PiSpecVersion, 16) < 0x0001000A: 903 if Sect.SectionType == 'SMM_DEPEX': 904 EdkLogger.error("GenFds", FORMAT_NOT_SUPPORTED, "Framework SMM module doesn't support SMM_DEPEX section type", File=self.InfFileName) 905 # 906 # process the inside FvImage from FvSection or GuidSection 907 # 908 if FvChildAddr != []: 909 if isinstance(Sect, FvImageSection): 910 Sect.FvAddr = FvChildAddr.pop(0) 911 elif isinstance(Sect, GuidSection): 912 Sect.FvAddr = FvChildAddr 913 if FvParentAddr != None and isinstance(Sect, GuidSection): 914 Sect.FvParentAddr = FvParentAddr 915 916 if Rule.KeyStringList != []: 917 SectList, Align = Sect.GenSection(self.OutputPath , self.ModuleGuid, SecIndex, Rule.KeyStringList, self) 918 else : 919 SectList, Align = Sect.GenSection(self.OutputPath , self.ModuleGuid, SecIndex, self.KeyStringList, self) 920 921 if not HasGneratedFlag: 922 UniVfrOffsetFileSection = "" 923 ModuleFileName = mws.join(GenFdsGlobalVariable.WorkSpaceDir, self.InfFileName) 924 InfData = GenFdsGlobalVariable.WorkSpace.BuildObject[PathClass(ModuleFileName), self.CurrentArch] 925 # 926 # Search the source list in InfData to find if there are .vfr file exist. 927 # 928 VfrUniBaseName = {} 929 VfrUniOffsetList = [] 930 for SourceFile in InfData.Sources: 931 if SourceFile.Type.upper() == ".VFR" : 932 # 933 # search the .map file to find the offset of vfr binary in the PE32+/TE file. 934 # 935 VfrUniBaseName[SourceFile.BaseName] = (SourceFile.BaseName + "Bin") 936 if SourceFile.Type.upper() == ".UNI" : 937 # 938 # search the .map file to find the offset of Uni strings binary in the PE32+/TE file. 939 # 940 VfrUniBaseName["UniOffsetName"] = (self.BaseName + "Strings") 941 942 943 if len(VfrUniBaseName) > 0: 944 VfrUniOffsetList = self.__GetBuildOutputMapFileVfrUniInfo(VfrUniBaseName) 945 # 946 # Generate the Raw data of raw section 947 # 948 os.path.join( self.OutputPath, self.BaseName + '.offset') 949 UniVfrOffsetFileName = os.path.join( self.OutputPath, self.BaseName + '.offset') 950 UniVfrOffsetFileSection = os.path.join( self.OutputPath, self.BaseName + 'Offset' + '.raw') 951 952 self.__GenUniVfrOffsetFile (VfrUniOffsetList, UniVfrOffsetFileName) 953 954 UniVfrOffsetFileNameList = [] 955 UniVfrOffsetFileNameList.append(UniVfrOffsetFileName) 956 """Call GenSection""" 957 GenFdsGlobalVariable.GenerateSection(UniVfrOffsetFileSection, 958 UniVfrOffsetFileNameList, 959 "EFI_SECTION_RAW" 960 ) 961 os.remove(UniVfrOffsetFileName) 962 SectList.append(UniVfrOffsetFileSection) 963 HasGneratedFlag = True 964 965 for SecName in SectList : 966 SectFiles.append(SecName) 967 SectAlignments.append(Align) 968 Index = Index + 1 969 return SectFiles, SectAlignments 970 971 ## __GenComplexFileFfs__() method 972 # 973 # Generate FFS 974 # 975 # @param self The object pointer 976 # @param Rule The rule object used to generate section 977 # @param InputFileList The output file list from GenSection 978 # @retval string Generated FFS file name 979 # 980 def __GenComplexFileFfs__(self, Rule, InputFile, Alignments): 981 982 if Rule.NameGuid != None and Rule.NameGuid.startswith('PCD('): 983 PcdValue = GenFdsGlobalVariable.GetPcdValue(Rule.NameGuid) 984 if len(PcdValue) == 0: 985 EdkLogger.error("GenFds", GENFDS_ERROR, '%s NOT defined.' \ 986 % (Rule.NameGuid)) 987 if PcdValue.startswith('{'): 988 PcdValue = GuidStructureByteArrayToGuidString(PcdValue) 989 RegistryGuidStr = PcdValue 990 if len(RegistryGuidStr) == 0: 991 EdkLogger.error("GenFds", GENFDS_ERROR, 'GUID value for %s in wrong format.' \ 992 % (Rule.NameGuid)) 993 self.ModuleGuid = RegistryGuidStr 994 995 FfsOutput = os.path.join( self.OutputPath, self.ModuleGuid + '.ffs') 996 GenFdsGlobalVariable.GenerateFfs(FfsOutput, InputFile, 997 Ffs.Ffs.FdfFvFileTypeToFileType[Rule.FvFileType], 998 self.ModuleGuid, Fixed=Rule.Fixed, 999 CheckSum=Rule.CheckSum, Align=Rule.Alignment, 1000 SectionAlign=Alignments 1001 ) 1002 return FfsOutput 1003 1004 ## __GetGenFfsCmdParameter__() method 1005 # 1006 # Create parameter string for GenFfs 1007 # 1008 # @param self The object pointer 1009 # @param Rule The rule object used to generate section 1010 # @retval tuple (FileType, Fixed, CheckSum, Alignment) 1011 # 1012 def __GetGenFfsCmdParameter__(self, Rule): 1013 result = tuple() 1014 result += ('-t', Ffs.Ffs.FdfFvFileTypeToFileType[Rule.FvFileType]) 1015 if Rule.Fixed != False: 1016 result += ('-x',) 1017 if Rule.CheckSum != False: 1018 result += ('-s',) 1019 1020 if Rule.Alignment != None and Rule.Alignment != '': 1021 result += ('-a', Rule.Alignment) 1022 1023 return result 1024 1025 ## __GetBuildOutputMapFileVfrUniInfo() method 1026 # 1027 # Find the offset of UNI/INF object offset in the EFI image file. 1028 # 1029 # @param self The object pointer 1030 # @param VfrUniBaseName A name list contain the UNI/INF object name. 1031 # @retval RetValue A list contain offset of UNI/INF object. 1032 # 1033 def __GetBuildOutputMapFileVfrUniInfo(self, VfrUniBaseName): 1034 MapFileName = os.path.join(self.EfiOutputPath, self.BaseName + ".map") 1035 EfiFileName = os.path.join(self.EfiOutputPath, self.BaseName + ".efi") 1036 return GetVariableOffset(MapFileName, EfiFileName, VfrUniBaseName.values()) 1037 1038 ## __GenUniVfrOffsetFile() method 1039 # 1040 # Generate the offset file for the module which contain VFR or UNI file. 1041 # 1042 # @param self The object pointer 1043 # @param VfrUniOffsetList A list contain the VFR/UNI offsets in the EFI image file. 1044 # @param UniVfrOffsetFileName The output offset file name. 1045 # 1046 def __GenUniVfrOffsetFile(self, VfrUniOffsetList, UniVfrOffsetFileName): 1047 1048 try: 1049 fInputfile = open(UniVfrOffsetFileName, "wb+", 0) 1050 except: 1051 EdkLogger.error("GenFds", FILE_OPEN_FAILURE, "File open failed for %s" %UniVfrOffsetFileName,None) 1052 1053 # Use a instance of StringIO to cache data 1054 fStringIO = StringIO.StringIO('') 1055 1056 for Item in VfrUniOffsetList: 1057 if (Item[0].find("Strings") != -1): 1058 # 1059 # UNI offset in image. 1060 # GUID + Offset 1061 # { 0x8913c5e0, 0x33f6, 0x4d86, { 0x9b, 0xf1, 0x43, 0xef, 0x89, 0xfc, 0x6, 0x66 } } 1062 # 1063 UniGuid = [0xe0, 0xc5, 0x13, 0x89, 0xf6, 0x33, 0x86, 0x4d, 0x9b, 0xf1, 0x43, 0xef, 0x89, 0xfc, 0x6, 0x66] 1064 UniGuid = [chr(ItemGuid) for ItemGuid in UniGuid] 1065 fStringIO.write(''.join(UniGuid)) 1066 UniValue = pack ('Q', int (Item[1], 16)) 1067 fStringIO.write (UniValue) 1068 else: 1069 # 1070 # VFR binary offset in image. 1071 # GUID + Offset 1072 # { 0xd0bc7cb4, 0x6a47, 0x495f, { 0xaa, 0x11, 0x71, 0x7, 0x46, 0xda, 0x6, 0xa2 } }; 1073 # 1074 VfrGuid = [0xb4, 0x7c, 0xbc, 0xd0, 0x47, 0x6a, 0x5f, 0x49, 0xaa, 0x11, 0x71, 0x7, 0x46, 0xda, 0x6, 0xa2] 1075 VfrGuid = [chr(ItemGuid) for ItemGuid in VfrGuid] 1076 fStringIO.write(''.join(VfrGuid)) 1077 type (Item[1]) 1078 VfrValue = pack ('Q', int (Item[1], 16)) 1079 fStringIO.write (VfrValue) 1080 1081 # 1082 # write data into file. 1083 # 1084 try : 1085 fInputfile.write (fStringIO.getvalue()) 1086 except: 1087 EdkLogger.error("GenFds", FILE_WRITE_FAILURE, "Write data to file %s failed, please check whether the file been locked or using by other applications." %UniVfrOffsetFileName,None) 1088 1089 fStringIO.close () 1090 fInputfile.close () 1091 1092 1093 1094 1095 1096 1097 1098 1099