]> git.proxmox.com Git - mirror_edk2.git/blob - BaseTools/Source/Python/UPT/Object/Parser/InfGuidObject.py
BaseTools: Replace BSD License with BSD+Patent License
[mirror_edk2.git] / BaseTools / Source / Python / UPT / Object / Parser / InfGuidObject.py
1 ## @file
2 # This file is used to define class objects of INF file [Guids] section.
3 # It will consumed by InfParser.
4 #
5 # Copyright (c) 2011 - 2018, Intel Corporation. All rights reserved.<BR>
6 #
7 # SPDX-License-Identifier: BSD-2-Clause-Patent
8
9 '''
10 InfGuidObject
11 '''
12
13 from Library.ParserValidate import IsValidCVariableName
14 from Library.CommentParsing import ParseComment
15 from Library.ExpressionValidate import IsValidFeatureFlagExp
16
17 from Library.Misc import Sdict
18 from Library import DataType as DT
19 import Logger.Log as Logger
20 from Logger import ToolError
21 from Logger import StringTable as ST
22
23 class InfGuidItemCommentContent():
24 def __init__(self):
25 #
26 # ## SOMETIMES_CONSUMES ## Variable:L"MemoryTypeInformation"
27 # TailString.
28 #
29 #
30 # SOMETIMES_CONSUMES
31 #
32 self.UsageItem = ''
33 #
34 # Variable
35 #
36 self.GuidTypeItem = ''
37 #
38 # MemoryTypeInformation
39 #
40 self.VariableNameItem = ''
41 #
42 # TailString
43 #
44 self.HelpStringItem = ''
45
46 def SetUsageItem(self, UsageItem):
47 self.UsageItem = UsageItem
48 def GetUsageItem(self):
49 return self.UsageItem
50
51 def SetGuidTypeItem(self, GuidTypeItem):
52 self.GuidTypeItem = GuidTypeItem
53 def GetGuidTypeItem(self):
54 return self.GuidTypeItem
55
56 def SetVariableNameItem(self, VariableNameItem):
57 self.VariableNameItem = VariableNameItem
58 def GetVariableNameItem(self):
59 return self.VariableNameItem
60
61 def SetHelpStringItem(self, HelpStringItem):
62 self.HelpStringItem = HelpStringItem
63 def GetHelpStringItem(self):
64 return self.HelpStringItem
65
66 class InfGuidItem():
67 def __init__(self):
68 self.Name = ''
69 self.FeatureFlagExp = ''
70 #
71 # A list contain instance of InfGuidItemCommentContent
72 #
73 self.CommentList = []
74 self.SupArchList = []
75
76 def SetName(self, Name):
77 self.Name = Name
78 def GetName(self):
79 return self.Name
80
81 def SetFeatureFlagExp(self, FeatureFlagExp):
82 self.FeatureFlagExp = FeatureFlagExp
83 def GetFeatureFlagExp(self):
84 return self.FeatureFlagExp
85
86 def SetCommentList(self, CommentList):
87 self.CommentList = CommentList
88 def GetCommentList(self):
89 return self.CommentList
90
91 def SetSupArchList(self, SupArchList):
92 self.SupArchList = SupArchList
93 def GetSupArchList(self):
94 return self.SupArchList
95
96 ## ParseComment
97 #
98 # ParseComment
99 #
100 def ParseGuidComment(CommentsList, InfGuidItemObj):
101 #
102 # Get/Set Usage and HelpString
103 #
104 if CommentsList is not None and len(CommentsList) != 0 :
105 CommentInsList = []
106 PreUsage = None
107 PreGuidType = None
108 PreHelpText = ''
109 BlockFlag = -1
110 Count = 0
111 for CommentItem in CommentsList:
112 Count = Count + 1
113 CommentItemUsage, \
114 CommentItemGuidType, \
115 CommentItemVarString, \
116 CommentItemHelpText = \
117 ParseComment(CommentItem,
118 DT.ALL_USAGE_TOKENS,
119 DT.GUID_TYPE_TOKENS,
120 [],
121 True)
122
123 if CommentItemHelpText is None:
124 CommentItemHelpText = ''
125 if Count == len(CommentsList) and CommentItemUsage == CommentItemGuidType == DT.ITEM_UNDEFINED:
126 CommentItemHelpText = DT.END_OF_LINE
127
128 if Count == len(CommentsList):
129 if BlockFlag == 1 or BlockFlag == 2:
130 if CommentItemUsage == CommentItemGuidType == DT.ITEM_UNDEFINED:
131 BlockFlag = 4
132 else:
133 BlockFlag = 3
134 if BlockFlag == -1:
135 BlockFlag = 4
136 if BlockFlag == -1 or BlockFlag == 1 or BlockFlag == 2:
137 if CommentItemUsage == CommentItemGuidType == DT.ITEM_UNDEFINED:
138 if BlockFlag == -1:
139 BlockFlag = 1
140 elif BlockFlag == 1:
141 BlockFlag = 2
142 else:
143 if BlockFlag == 1 or BlockFlag == 2:
144 BlockFlag = 3
145 elif BlockFlag == -1:
146 BlockFlag = 4
147
148 #
149 # Combine two comment line if they are generic comment
150 #
151 if CommentItemUsage == CommentItemGuidType == PreUsage == PreGuidType == DT.ITEM_UNDEFINED:
152 CommentItemHelpText = PreHelpText + DT.END_OF_LINE + CommentItemHelpText
153 PreHelpText = CommentItemHelpText
154
155 if BlockFlag == 4:
156 CommentItemIns = InfGuidItemCommentContent()
157 CommentItemIns.SetUsageItem(CommentItemUsage)
158 CommentItemIns.SetGuidTypeItem(CommentItemGuidType)
159 CommentItemIns.SetVariableNameItem(CommentItemVarString)
160 if CommentItemHelpText == '' or CommentItemHelpText.endswith(DT.END_OF_LINE):
161 CommentItemHelpText = CommentItemHelpText.strip(DT.END_OF_LINE)
162 CommentItemIns.SetHelpStringItem(CommentItemHelpText)
163 CommentInsList.append(CommentItemIns)
164
165 BlockFlag = -1
166 PreUsage = None
167 PreGuidType = None
168 PreHelpText = ''
169
170 elif BlockFlag == 3:
171 #
172 # Add previous help string
173 #
174 CommentItemIns = InfGuidItemCommentContent()
175 CommentItemIns.SetUsageItem(DT.ITEM_UNDEFINED)
176 CommentItemIns.SetGuidTypeItem(DT.ITEM_UNDEFINED)
177 if PreHelpText == '' or PreHelpText.endswith(DT.END_OF_LINE):
178 PreHelpText = PreHelpText.strip(DT.END_OF_LINE)
179 CommentItemIns.SetHelpStringItem(PreHelpText)
180 CommentInsList.append(CommentItemIns)
181 #
182 # Add Current help string
183 #
184 CommentItemIns = InfGuidItemCommentContent()
185 CommentItemIns.SetUsageItem(CommentItemUsage)
186 CommentItemIns.SetGuidTypeItem(CommentItemGuidType)
187 CommentItemIns.SetVariableNameItem(CommentItemVarString)
188 if CommentItemHelpText == '' or CommentItemHelpText.endswith(DT.END_OF_LINE):
189 CommentItemHelpText = CommentItemHelpText.strip(DT.END_OF_LINE)
190 CommentItemIns.SetHelpStringItem(CommentItemHelpText)
191 CommentInsList.append(CommentItemIns)
192
193 BlockFlag = -1
194 PreUsage = None
195 PreGuidType = None
196 PreHelpText = ''
197
198 else:
199 PreUsage = CommentItemUsage
200 PreGuidType = CommentItemGuidType
201 PreHelpText = CommentItemHelpText
202
203 InfGuidItemObj.SetCommentList(CommentInsList)
204 else:
205 #
206 # Still need to set the USAGE/GUIDTYPE to undefined.
207 #
208 CommentItemIns = InfGuidItemCommentContent()
209 CommentItemIns.SetUsageItem(DT.ITEM_UNDEFINED)
210 CommentItemIns.SetGuidTypeItem(DT.ITEM_UNDEFINED)
211 InfGuidItemObj.SetCommentList([CommentItemIns])
212
213 return InfGuidItemObj
214
215 ## InfGuidObject
216 #
217 # InfGuidObject
218 #
219 class InfGuidObject():
220 def __init__(self):
221 self.Guids = Sdict()
222 #
223 # Macro defined in this section should be only used in this section.
224 #
225 self.Macros = {}
226
227 def SetGuid(self, GuidList, Arch = None):
228 __SupportArchList = []
229 for ArchItem in Arch:
230 #
231 # Validate Arch
232 #
233 if (ArchItem == '' or ArchItem is None):
234 ArchItem = 'COMMON'
235
236 __SupportArchList.append(ArchItem)
237
238 for Item in GuidList:
239 #
240 # Get Comment content of this protocol
241 #
242 CommentsList = None
243 if len(Item) == 3:
244 CommentsList = Item[1]
245 CurrentLineOfItem = Item[2]
246 Item = Item[0]
247 InfGuidItemObj = InfGuidItem()
248 if len(Item) >= 1 and len(Item) <= 2:
249 #
250 # Only GuildName contained
251 #
252 if not IsValidCVariableName(Item[0]):
253 Logger.Error("InfParser",
254 ToolError.FORMAT_INVALID,
255 ST.ERR_INF_PARSER_INVALID_CNAME%(Item[0]),
256 File=CurrentLineOfItem[2],
257 Line=CurrentLineOfItem[1],
258 ExtraData=CurrentLineOfItem[0])
259 if (Item[0] != ''):
260 InfGuidItemObj.SetName(Item[0])
261 else:
262 Logger.Error("InfParser",
263 ToolError.FORMAT_INVALID,
264 ST.ERR_INF_PARSER_CNAME_MISSING,
265 File=CurrentLineOfItem[2],
266 Line=CurrentLineOfItem[1],
267 ExtraData=CurrentLineOfItem[0])
268 if len(Item) == 2:
269 #
270 # Contained CName and Feature Flag Express
271 # <statements> ::= <CName> ["|" <FeatureFlagExpress>]
272 # For GUID entry.
273 #
274 if Item[1].strip() == '':
275 Logger.Error("InfParser",
276 ToolError.FORMAT_INVALID,
277 ST.ERR_INF_PARSER_FEATURE_FLAG_EXP_MISSING,
278 File=CurrentLineOfItem[2],
279 Line=CurrentLineOfItem[1],
280 ExtraData=CurrentLineOfItem[0])
281 #
282 # Validate Feature Flag Express
283 #
284 FeatureFlagRtv = IsValidFeatureFlagExp(Item[1].strip())
285 if not FeatureFlagRtv[0]:
286 Logger.Error("InfParser",
287 ToolError.FORMAT_INVALID,
288 ST.ERR_INF_PARSER_FEATURE_FLAG_EXP_SYNTAX_INVLID%(FeatureFlagRtv[1]),
289 File=CurrentLineOfItem[2],
290 Line=CurrentLineOfItem[1],
291 ExtraData=CurrentLineOfItem[0])
292 InfGuidItemObj.SetFeatureFlagExp(Item[1])
293 if len(Item) != 1 and len(Item) != 2:
294 #
295 # Invalid format of GUID statement
296 #
297 Logger.Error("InfParser",
298 ToolError.FORMAT_INVALID,
299 ST.ERR_INF_PARSER_GUID_PPI_PROTOCOL_SECTION_CONTENT_ERROR,
300 File=CurrentLineOfItem[2],
301 Line=CurrentLineOfItem[1],
302 ExtraData=CurrentLineOfItem[0])
303
304 InfGuidItemObj = ParseGuidComment(CommentsList, InfGuidItemObj)
305 InfGuidItemObj.SetSupArchList(__SupportArchList)
306
307 #
308 # Determine GUID name duplicate. Follow below rule:
309 #
310 # A GUID must not be duplicated within a [Guids] section.
311 # A GUID may appear in multiple architectural [Guids]
312 # sections. A GUID listed in an architectural [Guids]
313 # section must not be listed in the common architectural
314 # [Guids] section.
315 #
316 # NOTE: This check will not report error now.
317 #
318 for Item in self.Guids:
319 if Item.GetName() == InfGuidItemObj.GetName():
320 ItemSupArchList = Item.GetSupArchList()
321 for ItemArch in ItemSupArchList:
322 for GuidItemObjArch in __SupportArchList:
323 if ItemArch == GuidItemObjArch:
324 #
325 # ST.ERR_INF_PARSER_ITEM_DUPLICATE
326 #
327 pass
328
329 if ItemArch.upper() == 'COMMON' or GuidItemObjArch.upper() == 'COMMON':
330 #
331 # ST.ERR_INF_PARSER_ITEM_DUPLICATE_COMMON
332 #
333 pass
334
335 if (InfGuidItemObj) in self.Guids:
336 GuidList = self.Guids[InfGuidItemObj]
337 GuidList.append(InfGuidItemObj)
338 self.Guids[InfGuidItemObj] = GuidList
339 else:
340 GuidList = []
341 GuidList.append(InfGuidItemObj)
342 self.Guids[InfGuidItemObj] = GuidList
343
344 return True
345
346 def GetGuid(self):
347 return self.Guids