1## @file 2# process rule section generation 3# 4# Copyright (c) 2007 - 2014, Intel Corporation. All rights reserved.<BR> 5# 6# This program and the accompanying materials 7# are licensed and made available under the terms and conditions of the BSD License 8# which accompanies this distribution. The full text of the license may be found at 9# http://opensource.org/licenses/bsd-license.php 10# 11# THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS, 12# WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED. 13# 14 15## 16# Import Modules 17# 18from struct import * 19import Section 20from GenFdsGlobalVariable import GenFdsGlobalVariable 21import subprocess 22from Ffs import Ffs 23import Common.LongFilePathOs as os 24from CommonDataClass.FdfClass import EfiSectionClassObject 25from Common import EdkLogger 26from Common.BuildToolError import * 27from Common.Misc import PeImageClass 28from Common.LongFilePathSupport import OpenLongFilePath as open 29from Common.LongFilePathSupport import CopyLongFilePath 30 31## generate rule section 32# 33# 34class EfiSection (EfiSectionClassObject): 35 36 ## The constructor 37 # 38 # @param self The object pointer 39 # 40 def __init__(self): 41 EfiSectionClassObject.__init__(self) 42 43 ## GenSection() method 44 # 45 # Generate rule section 46 # 47 # @param self The object pointer 48 # @param OutputPath Where to place output file 49 # @param ModuleName Which module this section belongs to 50 # @param SecNum Index of section 51 # @param KeyStringList Filter for inputs of section generation 52 # @param FfsInf FfsInfStatement object that contains this section data 53 # @param Dict dictionary contains macro and its value 54 # @retval tuple (Generated file name list, section alignment) 55 # 56 def GenSection(self, OutputPath, ModuleName, SecNum, KeyStringList, FfsInf = None, Dict = {}) : 57 58 if self.FileName != None and self.FileName.startswith('PCD('): 59 self.FileName = GenFdsGlobalVariable.GetPcdValue(self.FileName) 60 """Prepare the parameter of GenSection""" 61 if FfsInf != None : 62 InfFileName = FfsInf.InfFileName 63 SectionType = FfsInf.__ExtendMacro__(self.SectionType) 64 Filename = FfsInf.__ExtendMacro__(self.FileName) 65 BuildNum = FfsInf.__ExtendMacro__(self.BuildNum) 66 StringData = FfsInf.__ExtendMacro__(self.StringData) 67 NoStrip = True 68 if FfsInf.ModuleType in ('SEC', 'PEI_CORE', 'PEIM') and SectionType in ('TE', 'PE32'): 69 if FfsInf.KeepReloc != None: 70 NoStrip = FfsInf.KeepReloc 71 elif FfsInf.KeepRelocFromRule != None: 72 NoStrip = FfsInf.KeepRelocFromRule 73 elif self.KeepReloc != None: 74 NoStrip = self.KeepReloc 75 elif FfsInf.ShadowFromInfFile != None: 76 NoStrip = FfsInf.ShadowFromInfFile 77 else: 78 EdkLogger.error("GenFds", GENFDS_ERROR, "Module %s apply rule for None!" %ModuleName) 79 80 """If the file name was pointed out, add it in FileList""" 81 FileList = [] 82 if Filename != None: 83 Filename = GenFdsGlobalVariable.MacroExtend(Filename, Dict) 84 # check if the path is absolute or relative 85 if os.path.isabs(Filename): 86 Filename = os.path.normpath(Filename) 87 else: 88 Filename = os.path.normpath(os.path.join(FfsInf.EfiOutputPath, Filename)) 89 90 if not self.Optional: 91 FileList.append(Filename) 92 elif os.path.exists(Filename): 93 FileList.append(Filename) 94 else: 95 FileList, IsSect = Section.Section.GetFileList(FfsInf, self.FileType, self.FileExtension, Dict) 96 if IsSect : 97 return FileList, self.Alignment 98 99 Index = 0 100 Align = self.Alignment 101 102 """ If Section type is 'VERSION'""" 103 OutputFileList = [] 104 if SectionType == 'VERSION': 105 106 InfOverrideVerString = False 107 if FfsInf.Version != None: 108 #StringData = FfsInf.Version 109 BuildNum = FfsInf.Version 110 InfOverrideVerString = True 111 112 if InfOverrideVerString: 113 #VerTuple = ('-n', '"' + StringData + '"') 114 if BuildNum != None and BuildNum != '': 115 BuildNumTuple = ('-j', BuildNum) 116 else: 117 BuildNumTuple = tuple() 118 119 Num = SecNum 120 OutputFile = os.path.join( OutputPath, ModuleName + 'SEC' + str(Num) + Ffs.SectionSuffix.get(SectionType)) 121 GenFdsGlobalVariable.GenerateSection(OutputFile, [], 'EFI_SECTION_VERSION', 122 #Ui=StringData, 123 Ver=BuildNum) 124 OutputFileList.append(OutputFile) 125 126 elif FileList != []: 127 for File in FileList: 128 Index = Index + 1 129 Num = '%s.%d' %(SecNum , Index) 130 OutputFile = os.path.join(OutputPath, ModuleName + 'SEC' + Num + Ffs.SectionSuffix.get(SectionType)) 131 f = open(File, 'r') 132 VerString = f.read() 133 f.close() 134 BuildNum = VerString 135 if BuildNum != None and BuildNum != '': 136 BuildNumTuple = ('-j', BuildNum) 137 GenFdsGlobalVariable.GenerateSection(OutputFile, [], 'EFI_SECTION_VERSION', 138 #Ui=VerString, 139 Ver=BuildNum) 140 OutputFileList.append(OutputFile) 141 142 else: 143 BuildNum = StringData 144 if BuildNum != None and BuildNum != '': 145 BuildNumTuple = ('-j', BuildNum) 146 else: 147 BuildNumTuple = tuple() 148 BuildNumString = ' ' + ' '.join(BuildNumTuple) 149 150 #if VerString == '' and 151 if BuildNumString == '': 152 if self.Optional == True : 153 GenFdsGlobalVariable.VerboseLogger( "Optional Section don't exist!") 154 return [], None 155 else: 156 EdkLogger.error("GenFds", GENFDS_ERROR, "File: %s miss Version Section value" %InfFileName) 157 Num = SecNum 158 OutputFile = os.path.join( OutputPath, ModuleName + 'SEC' + str(Num) + Ffs.SectionSuffix.get(SectionType)) 159 GenFdsGlobalVariable.GenerateSection(OutputFile, [], 'EFI_SECTION_VERSION', 160 #Ui=VerString, 161 Ver=BuildNum) 162 OutputFileList.append(OutputFile) 163 164 # 165 # If Section Type is 'UI' 166 # 167 elif SectionType == 'UI': 168 169 InfOverrideUiString = False 170 if FfsInf.Ui != None: 171 StringData = FfsInf.Ui 172 InfOverrideUiString = True 173 174 if InfOverrideUiString: 175 Num = SecNum 176 OutputFile = os.path.join( OutputPath, ModuleName + 'SEC' + str(Num) + Ffs.SectionSuffix.get(SectionType)) 177 GenFdsGlobalVariable.GenerateSection(OutputFile, [], 'EFI_SECTION_USER_INTERFACE', 178 Ui=StringData) 179 OutputFileList.append(OutputFile) 180 181 elif FileList != []: 182 for File in FileList: 183 Index = Index + 1 184 Num = '%s.%d' %(SecNum , Index) 185 OutputFile = os.path.join(OutputPath, ModuleName + 'SEC' + Num + Ffs.SectionSuffix.get(SectionType)) 186 f = open(File, 'r') 187 UiString = f.read() 188 f.close() 189 GenFdsGlobalVariable.GenerateSection(OutputFile, [], 'EFI_SECTION_USER_INTERFACE', 190 Ui=UiString) 191 OutputFileList.append(OutputFile) 192 else: 193 if StringData != None and len(StringData) > 0: 194 UiTuple = ('-n', '"' + StringData + '"') 195 else: 196 UiTuple = tuple() 197 198 if self.Optional == True : 199 GenFdsGlobalVariable.VerboseLogger( "Optional Section don't exist!") 200 return '', None 201 else: 202 EdkLogger.error("GenFds", GENFDS_ERROR, "File: %s miss UI Section value" %InfFileName) 203 204 Num = SecNum 205 OutputFile = os.path.join( OutputPath, ModuleName + 'SEC' + str(Num) + Ffs.SectionSuffix.get(SectionType)) 206 GenFdsGlobalVariable.GenerateSection(OutputFile, [], 'EFI_SECTION_USER_INTERFACE', 207 Ui=StringData) 208 OutputFileList.append(OutputFile) 209 210 211 else: 212 """If File List is empty""" 213 if FileList == [] : 214 if self.Optional == True: 215 GenFdsGlobalVariable.VerboseLogger("Optional Section don't exist!") 216 return [], None 217 else: 218 EdkLogger.error("GenFds", GENFDS_ERROR, "Output file for %s section could not be found for %s" % (SectionType, InfFileName)) 219 220 else: 221 """Convert the File to Section file one by one """ 222 for File in FileList: 223 """ Copy Map file to FFS output path """ 224 Index = Index + 1 225 Num = '%s.%d' %(SecNum , Index) 226 OutputFile = os.path.join( OutputPath, ModuleName + 'SEC' + Num + Ffs.SectionSuffix.get(SectionType)) 227 File = GenFdsGlobalVariable.MacroExtend(File, Dict) 228 229 #Get PE Section alignment when align is set to AUTO 230 if self.Alignment == 'Auto' and (SectionType == 'PE32' or SectionType == 'TE'): 231 ImageObj = PeImageClass (File) 232 if ImageObj.SectionAlignment < 0x400: 233 Align = str (ImageObj.SectionAlignment) 234 else: 235 Align = str (ImageObj.SectionAlignment / 0x400) + 'K' 236 237 if File[(len(File)-4):] == '.efi': 238 MapFile = File.replace('.efi', '.map') 239 if os.path.exists(MapFile): 240 CopyMapFile = os.path.join(OutputPath, ModuleName + '.map') 241 if not os.path.exists(CopyMapFile) or \ 242 (os.path.getmtime(MapFile) > os.path.getmtime(CopyMapFile)): 243 CopyLongFilePath(MapFile, CopyMapFile) 244 245 if not NoStrip: 246 FileBeforeStrip = os.path.join(OutputPath, ModuleName + '.efi') 247 if not os.path.exists(FileBeforeStrip) or \ 248 (os.path.getmtime(File) > os.path.getmtime(FileBeforeStrip)): 249 CopyLongFilePath(File, FileBeforeStrip) 250 StrippedFile = os.path.join(OutputPath, ModuleName + '.stripped') 251 GenFdsGlobalVariable.GenerateFirmwareImage( 252 StrippedFile, 253 [File], 254 Strip=True 255 ) 256 File = StrippedFile 257 258 """For TE Section call GenFw to generate TE image""" 259 260 if SectionType == 'TE': 261 TeFile = os.path.join( OutputPath, ModuleName + 'Te.raw') 262 GenFdsGlobalVariable.GenerateFirmwareImage( 263 TeFile, 264 [File], 265 Type='te' 266 ) 267 File = TeFile 268 269 """Call GenSection""" 270 GenFdsGlobalVariable.GenerateSection(OutputFile, 271 [File], 272 Section.Section.SectionType.get (SectionType) 273 ) 274 OutputFileList.append(OutputFile) 275 276 return OutputFileList, Align 277