]> git.proxmox.com Git - mirror_edk2.git/blame - BaseTools/Source/Python/UPT/Object/Parser/InfPcdObject.py
BaseTools: Remove the deprecated hash_key()
[mirror_edk2.git] / BaseTools / Source / Python / UPT / Object / Parser / InfPcdObject.py
CommitLineData
4234283c
LG
1## @file\r
2# This file is used to define class objects of INF file [Pcds] section. \r
3# It will consumed by InfParser. \r
4#\r
64285f15 5# Copyright (c) 2011 - 2018, Intel Corporation. All rights reserved.<BR>\r
4234283c
LG
6#\r
7# This program and the accompanying materials are licensed and made available \r
8# under the terms and conditions of the BSD License which accompanies this \r
9# distribution. The full text of the license may be found at \r
10# http://opensource.org/licenses/bsd-license.php\r
11#\r
12# THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,\r
13# WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.\r
14\r
15'''\r
16InfPcdObject\r
17'''\r
18import os\r
19import re\r
20\r
21from Logger import StringTable as ST\r
22from Logger import ToolError\r
23import Logger.Log as Logger\r
421ccda3 24from Library import GlobalData\r
4234283c
LG
25from Library import DataType as DT\r
26\r
27from Library.Misc import Sdict\r
28from Library.Misc import GetHelpStringByRemoveHashKey\r
421ccda3 29from Library.ParserValidate import IsValidPcdType\r
4234283c
LG
30from Library.ParserValidate import IsValidCVariableName\r
31from Library.ParserValidate import IsValidPcdValue\r
32from Library.ParserValidate import IsValidArch\r
33from Library.CommentParsing import ParseComment\r
64285f15
YZ
34from Library.StringUtils import GetSplitValueList\r
35from Library.StringUtils import IsHexDigitUINT32\r
4234283c
LG
36from Library.ExpressionValidate import IsValidFeatureFlagExp\r
37from Parser.InfAsBuiltProcess import GetPackageListInfo\r
38from Parser.DecParser import Dec\r
39\r
40from Object.Parser.InfPackagesObject import InfPackageItem\r
41\r
42def ValidateArch(ArchItem, PcdTypeItem1, LineNo, SupArchDict, SupArchList):\r
43 #\r
44 # Validate Arch\r
45 # \r
4231a819 46 if (ArchItem == '' or ArchItem is None):\r
4234283c 47 ArchItem = 'COMMON'\r
421ccda3 48\r
4234283c
LG
49 if PcdTypeItem1.upper != DT.TAB_INF_FEATURE_PCD.upper():\r
50 ArchList = GetSplitValueList(ArchItem, ' ')\r
51 for ArchItemNew in ArchList:\r
52 if not IsValidArch(ArchItemNew):\r
421ccda3 53 Logger.Error("InfParser",\r
4234283c 54 ToolError.FORMAT_INVALID,\r
421ccda3 55 ST.ERR_INF_PARSER_DEFINE_FROMAT_INVALID % (ArchItemNew),\r
4234283c 56 File=GlobalData.gINF_MODULE_NAME,\r
421ccda3 57 Line=LineNo,\r
4234283c 58 ExtraData=ArchItemNew)\r
421ccda3 59 SupArchDict[PcdTypeItem1] = ArchList\r
4234283c
LG
60 else:\r
61 SupArchList.append(ArchItem)\r
421ccda3 62\r
4234283c
LG
63 return SupArchList, SupArchDict\r
64\r
65def ParsePcdComment(CommentList, PcdTypeItem, PcdItemObj):\r
66 CommentInsList = []\r
67 PreUsage = None\r
68 PreHelpText = ''\r
69 BlockFlag = -1\r
70 FFEHelpText = ''\r
421ccda3
HC
71 CommentItemHelpText = ''\r
72 Count = 0\r
4234283c
LG
73 for CommentItem in CommentList:\r
74 Count = Count + 1\r
421ccda3
HC
75 CommentItemUsage, CommentType, CommentString, CommentItemHelpText = ParseComment(CommentItem,\r
76 DT.ALL_USAGE_TOKENS,\r
77 {},\r
4234283c
LG
78 [],\r
79 False)\r
80 if CommentType and CommentString:\r
421ccda3
HC
81 pass\r
82\r
4234283c
LG
83 if PcdTypeItem == 'FeaturePcd':\r
84 CommentItemUsage = DT.USAGE_ITEM_CONSUMES\r
4231a819 85 if CommentItemHelpText is None:\r
4234283c 86 CommentItemHelpText = ''\r
421ccda3 87\r
4234283c
LG
88 if Count == 1:\r
89 FFEHelpText = CommentItemHelpText\r
90 else:\r
91 FFEHelpText = FFEHelpText + DT.END_OF_LINE + CommentItemHelpText\r
421ccda3 92\r
4234283c
LG
93 if Count == len(CommentList):\r
94 CommentItemHelpText = FFEHelpText\r
95 BlockFlag = 4\r
96 else:\r
97 continue\r
421ccda3 98\r
4231a819 99 if CommentItemHelpText is None:\r
4234283c
LG
100 CommentItemHelpText = ''\r
101 if Count == len(CommentList) and CommentItemUsage == DT.ITEM_UNDEFINED:\r
102 CommentItemHelpText = DT.END_OF_LINE\r
421ccda3 103\r
4234283c
LG
104 if Count == len(CommentList) and (BlockFlag == 1 or BlockFlag == 2):\r
105 if CommentItemUsage == DT.ITEM_UNDEFINED:\r
106 BlockFlag = 4\r
107 else:\r
108 BlockFlag = 3\r
109 elif BlockFlag == -1 and Count == len(CommentList):\r
421ccda3
HC
110 BlockFlag = 4\r
111\r
4234283c
LG
112 if BlockFlag == -1 or BlockFlag == 1 or BlockFlag == 2:\r
113 if CommentItemUsage == DT.ITEM_UNDEFINED:\r
114 if BlockFlag == -1:\r
115 BlockFlag = 1\r
116 elif BlockFlag == 1:\r
117 BlockFlag = 2\r
118 else:\r
119 if BlockFlag == 1 or BlockFlag == 2:\r
120 BlockFlag = 3\r
121 elif BlockFlag == -1:\r
122 BlockFlag = 4\r
123 #\r
124 # Combine two comment line if they are generic comment\r
125 # \r
126 if CommentItemUsage == PreUsage == DT.ITEM_UNDEFINED:\r
127 CommentItemHelpText = PreHelpText + DT.END_OF_LINE + CommentItemHelpText\r
421ccda3 128\r
4234283c 129 PreHelpText = CommentItemHelpText\r
421ccda3
HC
130\r
131 if BlockFlag == 4:\r
4234283c
LG
132 CommentItemIns = InfPcdItemCommentContent()\r
133 CommentItemIns.SetUsageItem(CommentItemUsage)\r
134 CommentItemIns.SetHelpStringItem(CommentItemHelpText)\r
135 CommentInsList.append(CommentItemIns)\r
421ccda3 136\r
4234283c
LG
137 BlockFlag = -1\r
138 PreUsage = None\r
139 PreHelpText = ''\r
421ccda3 140\r
4234283c
LG
141 elif BlockFlag == 3:\r
142 #\r
143 # Add previous help string\r
144 # \r
145 CommentItemIns = InfPcdItemCommentContent()\r
146 CommentItemIns.SetUsageItem(DT.ITEM_UNDEFINED)\r
147 if PreHelpText == '' or PreHelpText.endswith(DT.END_OF_LINE):\r
421ccda3 148 PreHelpText += DT.END_OF_LINE\r
4234283c
LG
149 CommentItemIns.SetHelpStringItem(PreHelpText)\r
150 CommentInsList.append(CommentItemIns)\r
151 #\r
152 # Add Current help string\r
153 #\r
154 CommentItemIns = InfPcdItemCommentContent()\r
155 CommentItemIns.SetUsageItem(CommentItemUsage)\r
156 CommentItemIns.SetHelpStringItem(CommentItemHelpText)\r
157 CommentInsList.append(CommentItemIns)\r
421ccda3 158\r
4234283c
LG
159 BlockFlag = -1\r
160 PreUsage = None\r
421ccda3
HC
161 PreHelpText = ''\r
162\r
4234283c
LG
163 else:\r
164 PreUsage = CommentItemUsage\r
165 PreHelpText = CommentItemHelpText\r
421ccda3 166\r
4234283c 167 PcdItemObj.SetHelpStringList(CommentInsList)\r
421ccda3
HC
168\r
169 return PcdItemObj\r
4234283c
LG
170\r
171class InfPcdItemCommentContent():\r
172 def __init__(self):\r
173 #\r
174 # ## SOMETIMES_CONSUMES ## HelpString \r
175 #\r
176 self.UsageItem = ''\r
177 #\r
178 # Help String\r
179 #\r
180 self.HelpStringItem = ''\r
421ccda3 181\r
4234283c
LG
182 def SetUsageItem(self, UsageItem):\r
183 self.UsageItem = UsageItem\r
184 def GetUsageItem(self):\r
185 return self.UsageItem\r
421ccda3 186\r
4234283c
LG
187 def SetHelpStringItem(self, HelpStringItem):\r
188 self.HelpStringItem = HelpStringItem\r
189 def GetHelpStringItem(self):\r
190 return self.HelpStringItem\r
421ccda3 191\r
4234283c
LG
192## InfPcdItem\r
193#\r
194# This class defined Pcd item used in Module files\r
195#\r
196# @param CName: Input value for CName, default is ''\r
197# @param Token: Input value for Token, default is ''\r
198# @param TokenSpaceGuidCName: Input value for TokenSpaceGuidCName, default \r
199# is ''\r
200# @param DatumType: Input value for DatumType, default is ''\r
201# @param MaxDatumSize: Input value for MaxDatumSize, default is ''\r
202# @param DefaultValue: Input value for DefaultValue, default is ''\r
203# @param ItemType: Input value for ItemType, default is ''\r
204# @param ValidUsage: Input value for ValidUsage, default is []\r
205# @param SkuInfoList: Input value for SkuInfoList, default is {}\r
206# @param SupModuleList: Input value for SupModuleList, default is []\r
207#\r
208class InfPcdItem():\r
209 def __init__(self):\r
210 self.CName = ''\r
211 self.Token = ''\r
212 self.TokenSpaceGuidCName = ''\r
213 self.TokenSpaceGuidValue = ''\r
421ccda3
HC
214 self.DatumType = ''\r
215 self.MaxDatumSize = ''\r
216 self.DefaultValue = ''\r
217 self.Offset = ''\r
218 self.ValidUsage = ''\r
219 self.ItemType = ''\r
220 self.SupModuleList = []\r
4234283c
LG
221 self.HelpStringList = []\r
222 self.FeatureFlagExp = ''\r
421ccda3 223 self.SupArchList = []\r
4234283c 224 self.PcdErrorsList = []\r
421ccda3 225\r
4234283c 226 def SetCName(self, CName):\r
421ccda3 227 self.CName = CName\r
4234283c
LG
228 def GetCName(self):\r
229 return self.CName\r
421ccda3 230\r
4234283c 231 def SetToken(self, Token):\r
421ccda3 232 self.Token = Token\r
4234283c
LG
233 def GetToken(self):\r
234 return self.Token\r
421ccda3 235\r
4234283c 236 def SetTokenSpaceGuidCName(self, TokenSpaceGuidCName):\r
421ccda3 237 self.TokenSpaceGuidCName = TokenSpaceGuidCName\r
4234283c
LG
238 def GetTokenSpaceGuidCName(self):\r
239 return self.TokenSpaceGuidCName\r
421ccda3 240\r
4234283c 241 def SetTokenSpaceGuidValue(self, TokenSpaceGuidValue):\r
421ccda3 242 self.TokenSpaceGuidValue = TokenSpaceGuidValue\r
4234283c
LG
243 def GetTokenSpaceGuidValue(self):\r
244 return self.TokenSpaceGuidValue\r
421ccda3 245\r
4234283c 246 def SetDatumType(self, DatumType):\r
421ccda3 247 self.DatumType = DatumType\r
4234283c
LG
248 def GetDatumType(self):\r
249 return self.DatumType\r
421ccda3 250\r
4234283c 251 def SetMaxDatumSize(self, MaxDatumSize):\r
421ccda3 252 self.MaxDatumSize = MaxDatumSize\r
4234283c
LG
253 def GetMaxDatumSize(self):\r
254 return self.MaxDatumSize\r
255\r
256 def SetDefaultValue(self, DefaultValue):\r
421ccda3 257 self.DefaultValue = DefaultValue\r
4234283c
LG
258 def GetDefaultValue(self):\r
259 return self.DefaultValue\r
421ccda3 260\r
4234283c 261 def SetPcdErrorsList(self, PcdErrorsList):\r
421ccda3 262 self.PcdErrorsList = PcdErrorsList\r
4234283c
LG
263 def GetPcdErrorsList(self):\r
264 return self.PcdErrorsList\r
265\r
266 def SetItemType(self, ItemType):\r
421ccda3 267 self.ItemType = ItemType\r
4234283c
LG
268 def GetItemType(self):\r
269 return self.ItemType\r
270\r
271 def SetSupModuleList(self, SupModuleList):\r
421ccda3 272 self.SupModuleList = SupModuleList\r
4234283c
LG
273 def GetSupModuleList(self):\r
274 return self.SupModuleList\r
421ccda3 275\r
4234283c
LG
276 def SetHelpStringList(self, HelpStringList):\r
277 self.HelpStringList = HelpStringList\r
278 def GetHelpStringList(self):\r
279 return self.HelpStringList\r
421ccda3 280\r
4234283c
LG
281 def SetFeatureFlagExp(self, FeatureFlagExp):\r
282 self.FeatureFlagExp = FeatureFlagExp\r
283 def GetFeatureFlagExp(self):\r
284 return self.FeatureFlagExp\r
421ccda3 285\r
4234283c
LG
286 def SetSupportArchList(self, ArchList):\r
287 self.SupArchList = ArchList\r
288 def GetSupportArchList(self):\r
289 return self.SupArchList\r
421ccda3 290\r
4234283c
LG
291 def SetOffset(self, Offset):\r
292 self.Offset = Offset\r
293 def GetOffset(self):\r
294 return self.Offset\r
295\r
421ccda3
HC
296 def SetValidUsage(self, ValidUsage):\r
297 self.ValidUsage = ValidUsage\r
298\r
299 def GetValidUsage(self):\r
300 return self.ValidUsage\r
301\r
4234283c
LG
302##\r
303#\r
304#\r
305#\r
306class InfPcdObject():\r
307 def __init__(self, FileName):\r
308 self.Pcds = Sdict()\r
309 self.FileName = FileName\r
421ccda3
HC
310\r
311 def SetPcds(self, PcdContent, KeysList=None, PackageInfo=None):\r
312\r
4234283c
LG
313 if GlobalData.gIS_BINARY_INF:\r
314 self.SetAsBuildPcds(PcdContent, KeysList, PackageInfo)\r
315 return True\r
421ccda3 316\r
4234283c
LG
317 #\r
318 # Validate Arch\r
319 #\r
320 SupArchList = []\r
321 SupArchDict = {}\r
322 PcdTypeItem = ''\r
323 for (PcdTypeItem1, ArchItem, LineNo) in KeysList:\r
324 SupArchList, SupArchDict = ValidateArch(ArchItem, PcdTypeItem1, LineNo, SupArchDict, SupArchList)\r
421ccda3 325\r
4234283c
LG
326 #\r
327 # Validate PcdType\r
328 #\r
4231a819 329 if (PcdTypeItem1 == '' or PcdTypeItem1 is None):\r
4234283c
LG
330 return False\r
331 else:\r
332 if not IsValidPcdType(PcdTypeItem1):\r
421ccda3
HC
333 Logger.Error("InfParser",\r
334 ToolError.FORMAT_INVALID,\r
335 ST.ERR_INF_PARSER_PCD_SECTION_TYPE_ERROR % (DT.PCD_USAGE_TYPE_LIST_OF_MODULE),\r
336 File=GlobalData.gINF_MODULE_NAME,\r
337 Line=LineNo,\r
4234283c
LG
338 ExtraData=PcdTypeItem1)\r
339 return False\r
421ccda3 340\r
4234283c 341 PcdTypeItem = PcdTypeItem1\r
421ccda3 342\r
4234283c
LG
343 for PcdItem in PcdContent:\r
344 PcdItemObj = InfPcdItem()\r
345 CommentList = PcdItem[1]\r
346 CurrentLineOfPcdItem = PcdItem[2]\r
347 PcdItem = PcdItem[0]\r
421ccda3 348\r
4231a819 349 if CommentList is not None and len(CommentList) != 0:\r
4234283c
LG
350 PcdItemObj = ParsePcdComment(CommentList, PcdTypeItem, PcdItemObj)\r
351 else:\r
352 CommentItemIns = InfPcdItemCommentContent()\r
353 CommentItemIns.SetUsageItem(DT.ITEM_UNDEFINED)\r
354 PcdItemObj.SetHelpStringList([CommentItemIns])\r
421ccda3 355\r
4234283c
LG
356 if len(PcdItem) >= 1 and len(PcdItem) <= 3:\r
357 PcdItemObj = SetPcdName(PcdItem, CurrentLineOfPcdItem, PcdItemObj)\r
421ccda3 358\r
4234283c
LG
359 if len(PcdItem) >= 2 and len(PcdItem) <= 3:\r
360 #\r
361 # Contain PcdName and Value, validate value.\r
362 #\r
363 if IsValidPcdValue(PcdItem[1]) or PcdItem[1].strip() == "":\r
364 PcdItemObj.SetDefaultValue(PcdItem[1])\r
365 else:\r
421ccda3
HC
366 Logger.Error("InfParser",\r
367 ToolError.FORMAT_INVALID,\r
4234283c 368 ST.ERR_INF_PARSER_PCD_VALUE_INVALID,\r
421ccda3
HC
369 File=CurrentLineOfPcdItem[2],\r
370 Line=CurrentLineOfPcdItem[1],\r
4234283c 371 ExtraData=PcdItem[1])\r
421ccda3 372\r
4234283c
LG
373 if len(PcdItem) == 3:\r
374 #\r
375 # Contain PcdName, value, and FeatureFlag express\r
376 #\r
377 #\r
378 # Validate Feature Flag Express\r
379 #\r
380 if PcdItem[2].strip() == '':\r
421ccda3
HC
381 Logger.Error("InfParser",\r
382 ToolError.FORMAT_INVALID,\r
4234283c 383 ST.ERR_INF_PARSER_FEATURE_FLAG_EXP_MISSING,\r
421ccda3
HC
384 File=CurrentLineOfPcdItem[2],\r
385 Line=CurrentLineOfPcdItem[1],\r
4234283c
LG
386 ExtraData=CurrentLineOfPcdItem[0])\r
387 #\r
388 # Validate FFE \r
389 #\r
390 FeatureFlagRtv = IsValidFeatureFlagExp(PcdItem[2].strip())\r
391 if not FeatureFlagRtv[0]:\r
421ccda3
HC
392 Logger.Error("InfParser",\r
393 ToolError.FORMAT_INVALID,\r
394 ST.ERR_INF_PARSER_FEATURE_FLAG_EXP_SYNTAX_INVLID % (FeatureFlagRtv[1]),\r
395 File=CurrentLineOfPcdItem[2],\r
396 Line=CurrentLineOfPcdItem[1],\r
4234283c
LG
397 ExtraData=CurrentLineOfPcdItem[0])\r
398 PcdItemObj.SetFeatureFlagExp(PcdItem[2])\r
421ccda3 399\r
4234283c 400 if len(PcdItem) < 1 or len(PcdItem) > 3:\r
421ccda3
HC
401 Logger.Error("InfParser",\r
402 ToolError.FORMAT_INVALID,\r
4234283c 403 ST.ERR_INF_PARSER_PCD_SECTION_CONTENT_ERROR,\r
421ccda3
HC
404 File=CurrentLineOfPcdItem[2],\r
405 Line=CurrentLineOfPcdItem[1],\r
4234283c 406 ExtraData=CurrentLineOfPcdItem[0])\r
421ccda3
HC
407 return False\r
408\r
4234283c
LG
409 if PcdTypeItem.upper != DT.TAB_INF_FEATURE_PCD.upper():\r
410 PcdItemObj.SetSupportArchList(SupArchDict[PcdTypeItem])\r
411 else:\r
412 PcdItemObj.SetSupportArchList(SupArchList)\r
421ccda3 413\r
27c4ceb4 414 if (PcdTypeItem, PcdItemObj) in self.Pcds:\r
4234283c
LG
415 PcdsList = self.Pcds[PcdTypeItem, PcdItemObj]\r
416 PcdsList.append(PcdItemObj)\r
417 self.Pcds[PcdTypeItem, PcdItemObj] = PcdsList\r
418 else:\r
419 PcdsList = []\r
420 PcdsList.append(PcdItemObj)\r
421 self.Pcds[PcdTypeItem, PcdItemObj] = PcdsList\r
421ccda3 422\r
4234283c 423 return True\r
421ccda3
HC
424\r
425 def SetAsBuildPcds(self, PcdContent, KeysList=None, PackageInfo=None):\r
4234283c
LG
426 for PcdItem in PcdContent:\r
427 PcdItemObj = InfPcdItem()\r
428 CommentList = PcdItem[1]\r
429 CurrentLineOfPcdItem = PcdItem[2]\r
430 PcdItem = PcdItem[0]\r
431 CommentString = ''\r
421ccda3
HC
432\r
433 for CommentLine in CommentList:\r
434 CommentString = GetHelpStringByRemoveHashKey(CommentLine)\r
435 CommentItemIns = InfPcdItemCommentContent()\r
436 CommentItemIns.SetHelpStringItem(CommentString)\r
437 CommentItemIns.SetUsageItem(CommentString)\r
438 PcdItemObj.SetHelpStringList(PcdItemObj.GetHelpStringList() + [CommentItemIns])\r
439 if PcdItemObj.GetValidUsage():\r
440 PcdItemObj.SetValidUsage(PcdItemObj.GetValidUsage() + DT.TAB_VALUE_SPLIT + CommentString)\r
441 else:\r
442 PcdItemObj.SetValidUsage(CommentString)\r
443\r
4234283c
LG
444 PcdItemObj.SetItemType(KeysList[0][0])\r
445 #\r
446 # Set PcdTokenSpaceCName and CName\r
447 #\r
421ccda3 448 PcdItemObj = SetPcdName(PcdItem, CurrentLineOfPcdItem, PcdItemObj)\r
4234283c 449 #\r
421ccda3 450 # Set Value/DatumType/OffSet/Token\r
4234283c 451 #\r
421ccda3
HC
452 PcdItemObj = SetValueDatumTypeMaxSizeToken(PcdItem,\r
453 CurrentLineOfPcdItem,\r
4234283c
LG
454 PcdItemObj,\r
455 KeysList[0][1],\r
456 PackageInfo)\r
421ccda3 457\r
4234283c 458 PcdTypeItem = KeysList[0][0]\r
27c4ceb4 459 if (PcdTypeItem, PcdItemObj) in self.Pcds:\r
4234283c
LG
460 PcdsList = self.Pcds[PcdTypeItem, PcdItemObj]\r
461 PcdsList.append(PcdItemObj)\r
462 self.Pcds[PcdTypeItem, PcdItemObj] = PcdsList\r
463 else:\r
464 PcdsList = []\r
465 PcdsList.append(PcdItemObj)\r
421ccda3
HC
466 self.Pcds[PcdTypeItem, PcdItemObj] = PcdsList\r
467\r
4234283c
LG
468 def GetPcds(self):\r
469 return self.Pcds\r
470\r
471def ParserPcdInfoInDec(String):\r
472 ValueList = GetSplitValueList(String, DT.TAB_VALUE_SPLIT, 3)\r
421ccda3 473\r
4234283c
LG
474 #\r
475 # DatumType, Token\r
476 #\r
477 return ValueList[2], ValueList[3]\r
478\r
421ccda3 479def SetValueDatumTypeMaxSizeToken(PcdItem, CurrentLineOfPcdItem, PcdItemObj, Arch, PackageInfo=None):\r
4234283c
LG
480 #\r
481 # Package information not been generated currently, we need to parser INF file to get information. \r
482 #\r
483 if not PackageInfo:\r
484 PackageInfo = []\r
485 InfFileName = CurrentLineOfPcdItem[2]\r
486 PackageInfoList = GetPackageListInfo(InfFileName, GlobalData.gWORKSPACE, -1)\r
487 for PackageInfoListItem in PackageInfoList:\r
488 PackageInfoIns = InfPackageItem()\r
489 PackageInfoIns.SetPackageName(PackageInfoListItem)\r
490 PackageInfo.append(PackageInfoIns)\r
491\r
492 PcdInfoInDecHasFound = False\r
493 for PackageItem in PackageInfo:\r
494 if PcdInfoInDecHasFound:\r
495 break\r
496 PackageName = PackageItem.PackageName\r
497 #\r
498 # Open DEC file to get information\r
499 #\r
500 FullFileName = os.path.normpath(os.path.realpath(os.path.join(GlobalData.gWORKSPACE, PackageName)))\r
421ccda3
HC
501\r
502 DecParser = None\r
503 if FullFileName not in GlobalData.gPackageDict:\r
504 DecParser = Dec(FullFileName)\r
505 GlobalData.gPackageDict[FullFileName] = DecParser\r
506 else:\r
507 DecParser = GlobalData.gPackageDict[FullFileName]\r
508\r
4234283c
LG
509 #\r
510 # Find PCD information. \r
511 #\r
512 DecPcdsDict = DecParser.GetPcdSectionObject().ValueDict\r
513 for Key in DecPcdsDict.keys():\r
514 if (Key[0] == 'PCDSDYNAMICEX' and PcdItemObj.GetItemType() == 'PcdEx') and \\r
515 (Key[1] == 'COMMON' or Key[1] == Arch):\r
516 for PcdInDec in DecPcdsDict[Key]:\r
517 if PcdInDec.TokenCName == PcdItemObj.CName and \\r
518 PcdInDec.TokenSpaceGuidCName == PcdItemObj.TokenSpaceGuidCName:\r
519 PcdItemObj.SetToken(PcdInDec.TokenValue)\r
520 PcdItemObj.SetDatumType(PcdInDec.DatumType)\r
521 PcdItemObj.SetSupportArchList([Arch])\r
421ccda3
HC
522 PcdItemObj.SetDefaultValue(PcdInDec.DefaultValue)\r
523\r
4234283c
LG
524 if (Key[0] == 'PCDSPATCHABLEINMODULE' and PcdItemObj.GetItemType() == 'PatchPcd') and \\r
525 (Key[1] == 'COMMON' or Key[1] == Arch):\r
526 for PcdInDec in DecPcdsDict[Key]:\r
527 if PcdInDec.TokenCName == PcdItemObj.CName and \\r
528 PcdInDec.TokenSpaceGuidCName == PcdItemObj.TokenSpaceGuidCName:\r
529 PcdItemObj.SetToken(PcdInDec.TokenValue)\r
530 PcdItemObj.SetDatumType(PcdInDec.DatumType)\r
421ccda3
HC
531 PcdItemObj.SetSupportArchList([Arch])\r
532\r
4234283c 533 if PcdItemObj.GetDatumType() == 'VOID*':\r
421ccda3
HC
534 if len(PcdItem) > 1:\r
535 PcdItemObj.SetMaxDatumSize('%s' % (len(GetSplitValueList(PcdItem[1], DT.TAB_COMMA_SPLIT))))\r
536\r
4234283c
LG
537 DecGuidsDict = DecParser.GetGuidSectionObject().ValueDict\r
538 for Key in DecGuidsDict.keys():\r
539 if Key == 'COMMON' or Key == Arch:\r
540 for GuidInDec in DecGuidsDict[Key]:\r
541 if GuidInDec.GuidCName == PcdItemObj.TokenSpaceGuidCName:\r
542 PcdItemObj.SetTokenSpaceGuidValue(GuidInDec.GuidString)\r
543\r
4234283c 544 if PcdItemObj.GetItemType().upper() == DT.TAB_INF_PATCH_PCD.upper():\r
421ccda3
HC
545 #\r
546 # Validate Value.\r
547 #\r
548 # convert the value from a decimal 0 to a formatted hex value.\r
549 if PcdItem[1] == "0":\r
550 DatumType = PcdItemObj.GetDatumType()\r
551 if DatumType == "UINT8":\r
552 PcdItem[1] = "0x00"\r
553 if DatumType == "UINT16":\r
554 PcdItem[1] = "0x0000"\r
555 if DatumType == "UINT32":\r
556 PcdItem[1] = "0x00000000"\r
557 if DatumType == "UINT64":\r
558 PcdItem[1] = "0x0000000000000000"\r
559\r
560 if ValidatePcdValueOnDatumType(PcdItem[1], PcdItemObj.GetDatumType()):\r
561 PcdItemObj.SetDefaultValue(PcdItem[1])\r
562 else:\r
563 Logger.Error("InfParser",\r
564 ToolError.FORMAT_INVALID,\r
565 ST.ERR_ASBUILD_PCD_VALUE_INVALID % ("\"" + PcdItem[1] + "\"", "\"" +\r
566 PcdItemObj.GetDatumType() + "\""),\r
567 File=CurrentLineOfPcdItem[2],\r
568 Line=CurrentLineOfPcdItem[1],\r
569 ExtraData=CurrentLineOfPcdItem[0])\r
570 #\r
571 # validate offset\r
572 #\r
573 if PcdItemObj.GetItemType().upper() == DT.TAB_INF_PATCH_PCD.upper():\r
574 if not IsHexDigitUINT32(PcdItem[2]):\r
575 Logger.Error("InfParser",\r
576 ToolError.FORMAT_INVALID,\r
577 ST.ERR_ASBUILD_PCD_OFFSET_FORMAT_INVALID % ("\"" + PcdItem[2] + "\""),\r
578 File=CurrentLineOfPcdItem[2],\r
579 Line=CurrentLineOfPcdItem[1],\r
580 ExtraData=CurrentLineOfPcdItem[0])\r
581 PcdItemObj.SetOffset(PcdItem[2])\r
582\r
4234283c 583 if PcdItemObj.GetToken() == '' or PcdItemObj.GetDatumType() == '':\r
421ccda3
HC
584 Logger.Error("InfParser",\r
585 ToolError.FORMAT_INVALID,\r
586 ST.ERR_ASBUILD_PCD_DECLARITION_MISS % ("\"" + PcdItem[0] + "\""),\r
587 File=CurrentLineOfPcdItem[2],\r
588 Line=CurrentLineOfPcdItem[1],\r
4234283c 589 ExtraData=CurrentLineOfPcdItem[0])\r
421ccda3 590\r
4234283c
LG
591 return PcdItemObj\r
592\r
593def ValidatePcdValueOnDatumType(Value, Type):\r
421ccda3 594\r
4234283c
LG
595 Value = Value.strip()\r
596 #\r
597 # Boolean type only allow 0x00 or 0x01 as value per INF spec\r
598 #\r
599 if Type == 'BOOLEAN':\r
600 if not (Value == '0x00' or Value == '0x01'):\r
421ccda3 601 return False\r
4234283c
LG
602 elif Type == 'VOID*':\r
603 if not Value.startswith("{"):\r
604 return False\r
605 if not Value.endswith("}"):\r
606 return False\r
607 #\r
608 # Strip "{" at head and "}" at tail.\r
609 #\r
421ccda3 610 Value = Value[1:-1]\r
4234283c 611 ValueList = GetSplitValueList(Value, DT.TAB_COMMA_SPLIT)\r
421ccda3 612\r
4234283c
LG
613 ReIsValidHexByte = re.compile("^0x[0-9a-f]{1,2}$", re.IGNORECASE)\r
614 for ValueItem in ValueList:\r
615 if not ReIsValidHexByte.match(ValueItem):\r
616 return False\r
421ccda3 617\r
4234283c 618 elif Type == 'UINT8' or Type == 'UINT16' or Type == 'UINT32' or Type == 'UINT64':\r
421ccda3 619\r
4234283c
LG
620 ReIsValidUint8z = re.compile('^0[x|X][a-fA-F0-9]{2}$')\r
621 ReIsValidUint16z = re.compile('^0[x|X][a-fA-F0-9]{4}$')\r
622 ReIsValidUint32z = re.compile('^0[x|X][a-fA-F0-9]{8}$')\r
623 ReIsValidUint64z = re.compile('^0[x|X][a-fA-F0-9]{16}$')\r
421ccda3 624\r
4234283c 625 if not ReIsValidUint8z.match(Value) and Type == 'UINT8':\r
421ccda3 626 return False\r
4234283c
LG
627 elif not ReIsValidUint16z.match(Value) and Type == 'UINT16':\r
628 return False\r
629 elif not ReIsValidUint32z.match(Value) and Type == 'UINT32':\r
630 return False\r
631 elif not ReIsValidUint64z.match(Value) and Type == 'UINT64':\r
632 return False\r
633 else:\r
634 #\r
635 # Since we assume the DEC file always correct, should never go to here.\r
636 #\r
637 pass\r
421ccda3
HC
638\r
639 return True\r
640\r
4234283c
LG
641def SetPcdName(PcdItem, CurrentLineOfPcdItem, PcdItemObj):\r
642 #\r
643 # Only PCD Name specified \r
644 # <PcdName> ::= <TokenSpaceGuidCName> "." <TokenCName>\r
645 #\r
646 PcdId = GetSplitValueList(PcdItem[0], DT.TAB_SPLIT)\r
421ccda3
HC
647 if len(PcdId) != 2:\r
648 Logger.Error("InfParser",\r
649 ToolError.FORMAT_INVALID,\r
4234283c 650 ST.ERR_INF_PARSER_PCD_NAME_FORMAT_ERROR,\r
421ccda3
HC
651 File=CurrentLineOfPcdItem[2],\r
652 Line=CurrentLineOfPcdItem[1],\r
4234283c
LG
653 ExtraData=CurrentLineOfPcdItem[0])\r
654 else:\r
655 #\r
656 # Validate PcdTokenSpaceGuidCName\r
657 #\r
658 if not IsValidCVariableName(PcdId[0]):\r
421ccda3
HC
659 Logger.Error("InfParser",\r
660 ToolError.FORMAT_INVALID,\r
4234283c 661 ST.ERR_INF_PARSER_PCD_CVAR_GUID,\r
421ccda3
HC
662 File=CurrentLineOfPcdItem[2],\r
663 Line=CurrentLineOfPcdItem[1],\r
4234283c
LG
664 ExtraData=PcdId[0])\r
665 if not IsValidCVariableName(PcdId[1]):\r
421ccda3
HC
666 Logger.Error("InfParser",\r
667 ToolError.FORMAT_INVALID,\r
4234283c 668 ST.ERR_INF_PARSER_PCD_CVAR_PCDCNAME,\r
421ccda3
HC
669 File=CurrentLineOfPcdItem[2],\r
670 Line=CurrentLineOfPcdItem[1],\r
4234283c
LG
671 ExtraData=PcdId[1])\r
672 PcdItemObj.SetTokenSpaceGuidCName(PcdId[0])\r
673 PcdItemObj.SetCName(PcdId[1])\r
421ccda3
HC
674\r
675 return PcdItemObj\r