]> git.proxmox.com Git - mirror_edk2.git/blob - BaseTools/Source/Python/GenFds/Fd.py
BaseTools: Replace StringIO.StringIO with io.BytesIO
[mirror_edk2.git] / BaseTools / Source / Python / GenFds / Fd.py
1 ## @file
2 # process FD generation
3 #
4 # Copyright (c) 2007 - 2018, 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 #
18 import Region
19 import Fv
20 import Common.LongFilePathOs as os
21 from io import BytesIO
22 import sys
23 from struct import *
24 from GenFdsGlobalVariable import GenFdsGlobalVariable
25 from CommonDataClass.FdfClass import FDClassObject
26 from Common import EdkLogger
27 from Common.BuildToolError import *
28 from Common.Misc import SaveFileOnChange
29 from GenFds import GenFds
30 from Common.DataType import BINARY_FILE_TYPE_FV
31
32 ## generate FD
33 #
34 #
35 class FD(FDClassObject):
36 ## The constructor
37 #
38 # @param self The object pointer
39 #
40 def __init__(self):
41 FDClassObject.__init__(self)
42
43 ## GenFd() method
44 #
45 # Generate FD
46 #
47 # @retval string Generated FD file name
48 #
49 def GenFd (self, Flag = False):
50 if self.FdUiName.upper() + 'fd' in GenFds.ImageBinDict:
51 return GenFds.ImageBinDict[self.FdUiName.upper() + 'fd']
52
53 #
54 # Print Information
55 #
56 FdFileName = os.path.join(GenFdsGlobalVariable.FvDir, self.FdUiName + '.fd')
57 if not Flag:
58 GenFdsGlobalVariable.InfLogger("\nFd File Name:%s (%s)" %(self.FdUiName, FdFileName))
59
60 Offset = 0x00
61 for item in self.BlockSizeList:
62 Offset = Offset + item[0] * item[1]
63 if Offset != self.Size:
64 EdkLogger.error("GenFds", GENFDS_ERROR, 'FD %s Size not consistent with block array' % self.FdUiName)
65 GenFdsGlobalVariable.VerboseLogger('Following Fv will be add to Fd !!!')
66 for FvObj in GenFdsGlobalVariable.FdfParser.Profile.FvDict:
67 GenFdsGlobalVariable.VerboseLogger(FvObj)
68
69 GenFdsGlobalVariable.VerboseLogger('################### Gen VTF ####################')
70 self.GenVtfFile()
71
72 HasCapsuleRegion = False
73 for RegionObj in self.RegionList:
74 if RegionObj.RegionType == 'CAPSULE':
75 HasCapsuleRegion = True
76 break
77 if HasCapsuleRegion:
78 TempFdBuffer = BytesIO('')
79 PreviousRegionStart = -1
80 PreviousRegionSize = 1
81
82 for RegionObj in self.RegionList :
83 if RegionObj.RegionType == 'CAPSULE':
84 continue
85 if RegionObj.Offset + RegionObj.Size <= PreviousRegionStart:
86 pass
87 elif RegionObj.Offset <= PreviousRegionStart or (RegionObj.Offset >=PreviousRegionStart and RegionObj.Offset < PreviousRegionStart + PreviousRegionSize):
88 pass
89 elif RegionObj.Offset > PreviousRegionStart + PreviousRegionSize:
90 if not Flag:
91 GenFdsGlobalVariable.InfLogger('Padding region starting from offset 0x%X, with size 0x%X' %(PreviousRegionStart + PreviousRegionSize, RegionObj.Offset - (PreviousRegionStart + PreviousRegionSize)))
92 PadRegion = Region.Region()
93 PadRegion.Offset = PreviousRegionStart + PreviousRegionSize
94 PadRegion.Size = RegionObj.Offset - PadRegion.Offset
95 if not Flag:
96 PadRegion.AddToBuffer(TempFdBuffer, self.BaseAddress, self.BlockSizeList, self.ErasePolarity, GenFds.ImageBinDict, self.vtfRawDict, self.DefineVarDict)
97 PreviousRegionStart = RegionObj.Offset
98 PreviousRegionSize = RegionObj.Size
99 #
100 # Call each region's AddToBuffer function
101 #
102 if PreviousRegionSize > self.Size:
103 pass
104 GenFdsGlobalVariable.VerboseLogger('Call each region\'s AddToBuffer function')
105 RegionObj.AddToBuffer (TempFdBuffer, self.BaseAddress, self.BlockSizeList, self.ErasePolarity, GenFds.ImageBinDict, self.vtfRawDict, self.DefineVarDict)
106
107 FdBuffer = BytesIO('')
108 PreviousRegionStart = -1
109 PreviousRegionSize = 1
110 for RegionObj in self.RegionList :
111 if RegionObj.Offset + RegionObj.Size <= PreviousRegionStart:
112 EdkLogger.error("GenFds", GENFDS_ERROR,
113 'Region offset 0x%X in wrong order with Region starting from 0x%X, size 0x%X\nRegions in FDF must have offsets appear in ascending order.'\
114 % (RegionObj.Offset, PreviousRegionStart, PreviousRegionSize))
115 elif RegionObj.Offset <= PreviousRegionStart or (RegionObj.Offset >=PreviousRegionStart and RegionObj.Offset < PreviousRegionStart + PreviousRegionSize):
116 EdkLogger.error("GenFds", GENFDS_ERROR,
117 'Region offset 0x%X overlaps with Region starting from 0x%X, size 0x%X' \
118 % (RegionObj.Offset, PreviousRegionStart, PreviousRegionSize))
119 elif RegionObj.Offset > PreviousRegionStart + PreviousRegionSize:
120 if not Flag:
121 GenFdsGlobalVariable.InfLogger('Padding region starting from offset 0x%X, with size 0x%X' %(PreviousRegionStart + PreviousRegionSize, RegionObj.Offset - (PreviousRegionStart + PreviousRegionSize)))
122 PadRegion = Region.Region()
123 PadRegion.Offset = PreviousRegionStart + PreviousRegionSize
124 PadRegion.Size = RegionObj.Offset - PadRegion.Offset
125 if not Flag:
126 PadRegion.AddToBuffer(FdBuffer, self.BaseAddress, self.BlockSizeList, self.ErasePolarity, GenFds.ImageBinDict, self.vtfRawDict, self.DefineVarDict)
127 PreviousRegionStart = RegionObj.Offset
128 PreviousRegionSize = RegionObj.Size
129 #
130 # Verify current region fits within allocated FD section Size
131 #
132 if PreviousRegionStart + PreviousRegionSize > self.Size:
133 EdkLogger.error("GenFds", GENFDS_ERROR,
134 'FD %s size too small to fit region with offset 0x%X and size 0x%X'
135 % (self.FdUiName, PreviousRegionStart, PreviousRegionSize))
136 #
137 # Call each region's AddToBuffer function
138 #
139 GenFdsGlobalVariable.VerboseLogger('Call each region\'s AddToBuffer function')
140 RegionObj.AddToBuffer (FdBuffer, self.BaseAddress, self.BlockSizeList, self.ErasePolarity, GenFds.ImageBinDict, self.vtfRawDict, self.DefineVarDict, Flag=Flag)
141 #
142 # Write the buffer contents to Fd file
143 #
144 GenFdsGlobalVariable.VerboseLogger('Write the buffer contents to Fd file')
145 if not Flag:
146 SaveFileOnChange(FdFileName, FdBuffer.getvalue())
147 FdBuffer.close()
148 GenFds.ImageBinDict[self.FdUiName.upper() + 'fd'] = FdFileName
149 return FdFileName
150
151 ## generate VTF
152 #
153 # @param self The object pointer
154 #
155 def GenVtfFile (self) :
156 #
157 # Get this Fd's all Fv name
158 #
159 FvAddDict ={}
160 FvList = []
161 for RegionObj in self.RegionList:
162 if RegionObj.RegionType == BINARY_FILE_TYPE_FV:
163 if len(RegionObj.RegionDataList) == 1:
164 RegionData = RegionObj.RegionDataList[0]
165 FvList.append(RegionData.upper())
166 FvAddDict[RegionData.upper()] = (int(self.BaseAddress, 16) + \
167 RegionObj.Offset, RegionObj.Size)
168 else:
169 Offset = RegionObj.Offset
170 for RegionData in RegionObj.RegionDataList:
171 FvList.append(RegionData.upper())
172 FvObj = GenFdsGlobalVariable.FdfParser.Profile.FvDict.get(RegionData.upper())
173 if len(FvObj.BlockSizeList) < 1:
174 EdkLogger.error("GenFds", GENFDS_ERROR,
175 'FV.%s must point out FVs blocksize and Fv BlockNum' \
176 % FvObj.UiFvName)
177 else:
178 Size = 0
179 for blockStatement in FvObj.BlockSizeList:
180 Size = Size + blockStatement[0] * blockStatement[1]
181 FvAddDict[RegionData.upper()] = (int(self.BaseAddress, 16) + \
182 Offset, Size)
183 Offset = Offset + Size
184 #
185 # Check whether this Fd need VTF
186 #
187 Flag = False
188 for VtfObj in GenFdsGlobalVariable.FdfParser.Profile.VtfList:
189 compLocList = VtfObj.GetFvList()
190 if set(compLocList).issubset(FvList):
191 Flag = True
192 break
193 if Flag == True:
194 self.vtfRawDict = VtfObj.GenVtf(FvAddDict)
195
196 ## generate flash map file
197 #
198 # @param self The object pointer
199 #
200 def GenFlashMap (self):
201 pass
202
203
204
205
206
207
208
209