1 ## @file DecPomAlignment.py
2 # This file contained the adapter for convert INF parser object to POM Object
4 # Copyright (c) 2011 - 2018, Intel Corporation. All rights reserved.<BR>
6 # SPDX-License-Identifier: BSD-2-Clause-Patent
12 from __future__
import print_function
22 import Logger
.Log
as Logger
23 from Logger
import StringTable
as ST
24 from Logger
.ToolError
import UPT_MUL_DEC_ERROR
25 from Logger
.ToolError
import FORMAT_INVALID
27 from Library
.Parsing
import NormPath
28 from Library
.DataType
import ARCH_LIST
29 from Library
.DataType
import TAB_GUIDS
30 from Library
.DataType
import TAB_PROTOCOLS
31 from Library
.DataType
import TAB_PPIS
32 from Library
.DataType
import TAB_DEC_DEFINES_PACKAGE_NAME
33 from Library
.DataType
import TAB_DEC_DEFINES_PACKAGE_GUID
34 from Library
.DataType
import TAB_DEC_DEFINES_PACKAGE_VERSION
35 from Library
.DataType
import TAB_DEC_DEFINES_DEC_SPECIFICATION
36 from Library
.DataType
import TAB_DEC_DEFINES_PKG_UNI_FILE
37 from Library
.DataType
import TAB_ARCH_COMMON
38 from Library
.DataType
import TAB_INCLUDES
39 from Library
.DataType
import TAB_LIBRARY_CLASSES
40 from Library
.DataType
import TAB_PCDS
41 from Library
.DataType
import TAB_PCDS_FIXED_AT_BUILD_NULL
42 from Library
.DataType
import TAB_PCDS_PATCHABLE_IN_MODULE_NULL
43 from Library
.DataType
import TAB_PCDS_FEATURE_FLAG_NULL
44 from Library
.DataType
import TAB_PCDS_DYNAMIC_EX_NULL
45 from Library
.DataType
import TAB_PCDS_DYNAMIC_NULL
46 from Library
.DataType
import TAB_PTR_TYPE_PCD
47 from Library
.DataType
import ITEM_UNDEFINED
48 from Library
.DataType
import TAB_DEC_BINARY_ABSTRACT
49 from Library
.DataType
import TAB_DEC_BINARY_DESCRIPTION
50 from Library
.DataType
import TAB_LANGUAGE_EN_US
51 from Library
.DataType
import TAB_BINARY_HEADER_IDENTIFIER
52 from Library
.DataType
import TAB_BINARY_HEADER_USERID
53 from Library
.DataType
import TAB_LANGUAGE_EN_X
54 from Library
.DataType
import TAB_LANGUAGE_EN
55 from Library
.DataType
import TAB_STR_TOKENCNAME
56 from Library
.DataType
import TAB_STR_TOKENPROMPT
57 from Library
.DataType
import TAB_STR_TOKENHELP
58 from Library
.DataType
import TAB_STR_TOKENERR
59 from Library
.DataType
import TAB_HEX_START
60 from Library
.DataType
import TAB_SPLIT
61 import Library
.DataType
as DT
62 from Library
.CommentParsing
import ParseHeaderCommentSection
63 from Library
.CommentParsing
import ParseGenericComment
64 from Library
.CommentParsing
import ParseDecPcdGenericComment
65 from Library
.CommentParsing
import ParseDecPcdTailComment
66 from Library
.Misc
import GetFiles
67 from Library
.Misc
import Sdict
68 from Library
.Misc
import GetRelativePath
69 from Library
.Misc
import PathClass
70 from Library
.Misc
import ValidateUNIFilePath
71 from Library
.UniClassObject
import UniFileClassObject
72 from Library
.UniClassObject
import ConvertSpecialUnicodes
73 from Library
.UniClassObject
import GetLanguageCode1766
74 from Library
.ParserValidate
import IsValidPath
75 from Parser
.DecParser
import Dec
76 from Object
.POM
.PackageObject
import PackageObject
77 from Object
.POM
.CommonObject
import UserExtensionObject
78 from Object
.POM
.CommonObject
import IncludeObject
79 from Object
.POM
.CommonObject
import GuidObject
80 from Object
.POM
.CommonObject
import ProtocolObject
81 from Object
.POM
.CommonObject
import PpiObject
82 from Object
.POM
.CommonObject
import LibraryClassObject
83 from Object
.POM
.CommonObject
import PcdObject
84 from Object
.POM
.CommonObject
import TextObject
85 from Object
.POM
.CommonObject
import MiscFileObject
86 from Object
.POM
.CommonObject
import FileObject
91 # Inherited from PackageObject
93 class DecPomAlignment(PackageObject
):
94 def __init__(self
, Filename
, WorkspaceDir
= None, CheckMulDec
= False):
95 PackageObject
.__init
__(self
)
96 self
.UserExtensions
= ''
97 self
.WorkspaceDir
= WorkspaceDir
98 self
.SupArchList
= ARCH_LIST
99 self
.CheckMulDec
= CheckMulDec
100 self
.DecParser
= None
101 self
.UniFileClassObject
= None
102 self
.PcdDefaultValueDict
= {}
107 self
.LoadDecFile(Filename
)
110 # Transfer to Package Object if IsToPackage is True
116 # Load the file if it exists
118 # @param Filename: Input value for filename of Dec file
120 def LoadDecFile(self
, Filename
):
122 # Insert a record for file
124 Filename
= NormPath(Filename
)
125 (Path
, Name
) = os
.path
.split(Filename
)
126 self
.SetFullPath(Filename
)
127 self
.SetRelaPath(Path
)
128 self
.SetFileName(Name
)
129 self
.SetPackagePath(GetRelativePath(Path
, self
.WorkspaceDir
))
130 self
.SetCombinePath(GetRelativePath(Filename
, self
.WorkspaceDir
))
132 self
.DecParser
= Dec(Filename
)
134 ## Transfer to Package Object
136 # Transfer all contents of a Dec file to a standard Package Object
138 def DecToPackage(self
):
140 # Init global information for the file
142 ContainerFile
= self
.GetFullPath()
145 # Generate Package Header
147 self
.GenPackageHeader(ContainerFile
)
152 self
.GenIncludes(ContainerFile
)
157 self
.GenGuidProtocolPpis(TAB_GUIDS
, ContainerFile
)
162 self
.GenGuidProtocolPpis(TAB_PROTOCOLS
, ContainerFile
)
167 self
.GenGuidProtocolPpis(TAB_PPIS
, ContainerFile
)
170 # Generate LibraryClasses
172 self
.GenLibraryClasses(ContainerFile
)
177 self
.GenPcds(ContainerFile
)
180 # Generate Module File list, will be used later on to generate
183 self
.GenModuleFileList(ContainerFile
)
186 # Generate user extensions
188 self
.GenUserExtensions()
190 ## Generate user extension
193 def GenUserExtensions(self
):
194 UEObj
= self
.DecParser
.GetUserExtensionSectionObject()
195 UEList
= UEObj
.GetAllUserExtensions()
197 if not Item
.UserString
:
199 UserExtension
= UserExtensionObject()
201 if UserId
.startswith('"') and UserId
.endswith('"'):
202 UserId
= UserId
[1:-1]
203 UserExtension
.SetUserID(UserId
)
204 Identifier
= Item
.IdString
205 if Identifier
.startswith('"') and Identifier
.endswith('"'):
206 Identifier
= Identifier
[1:-1]
208 # Generate miscellaneous files of DEC file
210 if UserId
== 'TianoCore' and Identifier
== 'ExtraFiles':
211 self
.GenMiscFiles(Item
.UserString
)
212 UserExtension
.SetIdentifier(Identifier
)
213 UserExtension
.SetStatement(Item
.UserString
)
214 UserExtension
.SetSupArchList(
215 Item
.ArchAndModuleType
217 self
.SetUserExtensionList(
218 self
.GetUserExtensionList() + [UserExtension
]
221 # Add Private sections to UserExtension
222 if self
.DecParser
.GetPrivateSections():
223 PrivateUserExtension
= UserExtensionObject()
224 PrivateUserExtension
.SetStatement(self
.DecParser
.GetPrivateSections())
225 PrivateUserExtension
.SetIdentifier(DT
.TAB_PRIVATE
)
226 PrivateUserExtension
.SetUserID(DT
.TAB_INTEL
)
227 self
.SetUserExtensionList(self
.GetUserExtensionList() + [PrivateUserExtension
])
229 ## Generate miscellaneous files on DEC file
232 def GenMiscFiles(self
, Content
):
233 MiscFileObj
= MiscFileObject()
234 for Line
in Content
.splitlines():
237 FileName
= Line
[:Line
.find('#')]
241 if IsValidPath(FileName
, self
.GetRelaPath()):
242 FileObj
= FileObject()
243 FileObj
.SetURI(FileName
)
244 MiscFileObj
.SetFileList(MiscFileObj
.GetFileList()+[FileObj
])
246 Logger
.Error("InfParser",
248 ST
.ERR_INF_PARSER_FILE_NOT_EXIST_OR_NAME_INVALID
%(Line),
249 File
=self
.GetFileName(),
251 self
.SetMiscFileList(self
.GetMiscFileList()+[MiscFileObj
])
253 ## Generate Package Header
255 # Gen Package Header of Dec as <Key> = <Value>
257 # @param ContainerFile: The Dec file full path
259 def GenPackageHeader(self
, ContainerFile
):
260 Logger
.Debug(2, "Generate PackageHeader ...")
264 # Update all defines item in database
266 DefObj
= self
.DecParser
.GetDefineSectionObject()
267 for Item
in DefObj
.GetDefines():
269 # put items into Dict except for PackageName, Guid, Version, DEC_SPECIFICATION
271 SkipItemList
= [TAB_DEC_DEFINES_PACKAGE_NAME
, \
272 TAB_DEC_DEFINES_PACKAGE_GUID
, TAB_DEC_DEFINES_PACKAGE_VERSION
, \
273 TAB_DEC_DEFINES_DEC_SPECIFICATION
, TAB_DEC_DEFINES_PKG_UNI_FILE
]
274 if Item
.Key
in SkipItemList
:
276 DefinesDict
['%s = %s' % (Item
.Key
, Item
.Value
)] = TAB_ARCH_COMMON
278 self
.SetBaseName(DefObj
.GetPackageName())
279 self
.SetVersion(DefObj
.GetPackageVersion())
280 # self.SetName(DefObj.GetPackageName() + ' Version ' + \
281 # DefObj.GetPackageVersion())
282 self
.SetName(os
.path
.splitext(self
.GetFileName())[0])
283 self
.SetGuid(DefObj
.GetPackageGuid())
284 if DefObj
.GetPackageUniFile():
285 ValidateUNIFilePath(DefObj
.GetPackageUniFile())
286 self
.UniFileClassObject
= \
287 UniFileClassObject([PathClass(os
.path
.join(DefObj
.GetPackagePath(), DefObj
.GetPackageUniFile()))])
289 self
.UniFileClassObject
= None
292 UserExtension
= UserExtensionObject()
293 UserExtension
.SetDefinesDict(DefinesDict
)
294 UserExtension
.SetIdentifier('DefineModifiers')
295 UserExtension
.SetUserID('EDK2')
296 self
.SetUserExtensionList(
297 self
.GetUserExtensionList() + [UserExtension
]
301 # Get File header information
303 if self
.UniFileClassObject
:
304 Lang
= TAB_LANGUAGE_EN_X
306 Lang
= TAB_LANGUAGE_EN_US
307 Abstract
, Description
, Copyright
, License
= \
308 ParseHeaderCommentSection(self
.DecParser
.GetHeadComment(),
311 self
.SetAbstract((Lang
, Abstract
))
313 self
.SetDescription((Lang
, Description
))
315 self
.SetCopyright(('', Copyright
))
317 self
.SetLicense(('', License
))
320 # Get Binary header information
322 if self
.DecParser
.BinaryHeadComment
:
323 Abstract
, Description
, Copyright
, License
= \
324 ParseHeaderCommentSection(self
.DecParser
.BinaryHeadComment
,
327 if not Abstract
or not Description
or not Copyright
or not License
:
328 Logger
.Error('MkPkg',
330 ST
.ERR_INVALID_BINARYHEADER_FORMAT
,
333 self
.SetBinaryHeaderAbstract((Lang
, Abstract
))
334 self
.SetBinaryHeaderDescription((Lang
, Description
))
335 self
.SetBinaryHeaderCopyright(('', Copyright
))
336 self
.SetBinaryHeaderLicense(('', License
))
338 BinaryAbstractList
= []
339 BinaryDescriptionList
= []
341 #Get Binary header from UNI file
342 # Initialize the UniStrDict dictionary, top keys are language codes
344 if self
.UniFileClassObject
:
345 UniStrDict
= self
.UniFileClassObject
.OrderedStringList
346 for Lang
in UniStrDict
:
347 for StringDefClassObject
in UniStrDict
[Lang
]:
348 Lang
= GetLanguageCode1766(Lang
)
349 if StringDefClassObject
.StringName
== TAB_DEC_BINARY_ABSTRACT
:
350 if (Lang
, ConvertSpecialUnicodes(StringDefClassObject
.StringValue
)) \
351 not in self
.GetBinaryHeaderAbstract():
352 BinaryAbstractList
.append((Lang
, ConvertSpecialUnicodes(StringDefClassObject
.StringValue
)))
353 if StringDefClassObject
.StringName
== TAB_DEC_BINARY_DESCRIPTION
:
354 if (Lang
, ConvertSpecialUnicodes(StringDefClassObject
.StringValue
)) \
355 not in self
.GetBinaryHeaderDescription():
356 BinaryDescriptionList
.append((Lang
,
357 ConvertSpecialUnicodes(StringDefClassObject
.StringValue
)))
358 #Combine Binary header from DEC file and UNI file
359 BinaryAbstractList
= self
.GetBinaryHeaderAbstract() + BinaryAbstractList
360 BinaryDescriptionList
= self
.GetBinaryHeaderDescription() + BinaryDescriptionList
361 BinaryCopyrightList
= self
.GetBinaryHeaderCopyright()
362 BinaryLicenseList
= self
.GetBinaryHeaderLicense()
363 #Generate the UserExtensionObject for TianoCore."BinaryHeader"
364 if BinaryAbstractList
or BinaryDescriptionList
or BinaryCopyrightList
or BinaryLicenseList
:
365 BinaryUserExtension
= UserExtensionObject()
366 BinaryUserExtension
.SetBinaryAbstract(BinaryAbstractList
)
367 BinaryUserExtension
.SetBinaryDescription(BinaryDescriptionList
)
368 BinaryUserExtension
.SetBinaryCopyright(BinaryCopyrightList
)
369 BinaryUserExtension
.SetBinaryLicense(BinaryLicenseList
)
370 BinaryUserExtension
.SetIdentifier(TAB_BINARY_HEADER_IDENTIFIER
)
371 BinaryUserExtension
.SetUserID(TAB_BINARY_HEADER_USERID
)
372 self
.SetUserExtensionList(self
.GetUserExtensionList() + [BinaryUserExtension
])
377 # Gen Includes of Dec
379 # @param ContainerFile: The Dec file full path
381 def GenIncludes(self
, ContainerFile
):
384 Logger
.Debug(2, "Generate %s ..." % TAB_INCLUDES
)
385 IncludesDict
= Sdict()
387 IncObj
= self
.DecParser
.GetIncludeSectionObject()
388 for Item
in IncObj
.GetAllIncludes():
389 IncludePath
= os
.path
.normpath(Item
.File
)
390 if platform
.system() != 'Windows' and platform
.system() != 'Microsoft':
391 IncludePath
= IncludePath
.replace('\\', '/')
392 if IncludePath
in IncludesDict
:
393 if Item
.GetArchList() == [TAB_ARCH_COMMON
] or IncludesDict
[IncludePath
] == [TAB_ARCH_COMMON
]:
394 IncludesDict
[IncludePath
] = [TAB_ARCH_COMMON
]
396 IncludesDict
[IncludePath
] = IncludesDict
[IncludePath
] + Item
.GetArchList()
398 IncludesDict
[IncludePath
] = Item
.GetArchList()
401 # get the standardIncludeFileList(industry), packageIncludeFileList
402 # (others) for PackageObject
404 PackagePath
= os
.path
.split(self
.GetFullPath())[0]
406 sorted([os
.path
.normpath(Path
) + sep
for Path
in IncludesDict
.keys()])
409 # get a non-overlap set of include path, IncludePathList should be
410 # sorted, and path should be end with path separator '\'
413 for Path1
in IncludePathList
:
414 for Path2
in NonOverLapList
:
415 if Path1
.startswith(Path2
):
418 NonOverLapList
.append(Path1
)
420 # revert the list so the longest path shown first in list, also need
421 # to remove the extra path separator '\'
422 # as this list is used to search the supported Arch info
424 for IndexN
in range (0, len(IncludePathList
)):
425 IncludePathList
[IndexN
] = os
.path
.normpath(IncludePathList
[IndexN
])
426 IncludePathList
.sort()
427 IncludePathList
.reverse()
429 # save the include path list for later usage
431 self
.SetIncludePathList(IncludePathList
)
432 StandardIncludeFileList
= []
433 PackageIncludeFileList
= []
436 for Path
in NonOverLapList
:
437 FileList
= GetFiles(os
.path
.join(PackagePath
, Path
), ['CVS', '.svn'], False)
438 IncludeFileList
+= [os
.path
.normpath(os
.path
.join(Path
, File
)) for File
in FileList
]
439 for Includefile
in IncludeFileList
:
440 ExtName
= os
.path
.splitext(Includefile
)[1]
441 if ExtName
.upper() == '.DEC' and self
.CheckMulDec
:
442 Logger
.Error('MkPkg',
444 ST
.ERR_MUL_DEC_ERROR
%(os
.path
.dirname(ContainerFile
),
445 os
.path
.basename(ContainerFile
),
448 FileCombinePath
= os
.path
.dirname(Includefile
)
449 Include
= IncludeObject()
450 for Path
in IncludePathList
:
451 if FileCombinePath
.startswith(Path
):
452 SupArchList
= IncludesDict
[Path
]
454 Include
.SetFilePath(Includefile
)
455 Include
.SetSupArchList(SupArchList
)
456 if Includefile
.find('IndustryStandard') != -1:
457 StandardIncludeFileList
.append(Include
)
459 PackageIncludeFileList
.append(Include
)
461 self
.SetStandardIncludeFileList(StandardIncludeFileList
)
464 # put include path into the PackageIncludeFileList
467 IncObj
= self
.DecParser
.GetIncludeSectionObject()
468 for Item
in IncObj
.GetAllIncludes():
469 IncludePath
= Item
.File
470 Include
= IncludeObject()
471 Include
.SetFilePath(IncludePath
)
472 Include
.SetSupArchList(Item
.GetArchList())
473 PackagePathList
.append(Include
)
474 self
.SetPackageIncludeFileList(PackagePathList
+ PackageIncludeFileList
)
479 # <CName>=<GuidValue>
481 # @param ContainerFile: The Dec file full path
483 def GenGuidProtocolPpis(self
, Type
, ContainerFile
):
486 Logger
.Debug(2, "Generate %s ..." % Type
)
490 if Type
== TAB_GUIDS
:
491 Obj
= self
.DecParser
.GetGuidSectionObject()
492 def CreateGuidObject():
493 Object
= GuidObject()
494 Object
.SetGuidTypeList([])
495 Object
.SetUsage(None)
498 Factory
= CreateGuidObject
499 elif Type
== TAB_PROTOCOLS
:
500 Obj
= self
.DecParser
.GetProtocolSectionObject()
502 def CreateProtocolObject():
503 return ProtocolObject()
504 Factory
= CreateProtocolObject
505 elif Type
== TAB_PPIS
:
506 Obj
= self
.DecParser
.GetPpiSectionObject()
508 def CreatePpiObject():
510 Factory
= CreatePpiObject
517 DeclarationsList
= []
520 # Go through each arch
522 for Item
in Obj
.GetGuidStyleAllItems():
523 Name
= Item
.GuidCName
524 Value
= Item
.GuidString
525 HelpTxt
= ParseGenericComment(Item
.GetHeadComment() + \
526 Item
.GetTailComment())
528 ListObject
= Factory()
529 ListObject
.SetCName(Name
)
530 ListObject
.SetGuid(Value
)
531 ListObject
.SetSupArchList(Item
.GetArchList())
533 if self
.UniFileClassObject
:
534 HelpTxt
.SetLang(TAB_LANGUAGE_EN_X
)
535 ListObject
.SetHelpTextList([HelpTxt
])
537 DeclarationsList
.append(ListObject
)
540 #GuidTypeList is abstracted from help
542 if Type
== TAB_GUIDS
:
543 self
.SetGuidList(self
.GetGuidList() + DeclarationsList
)
544 elif Type
== TAB_PROTOCOLS
:
545 self
.SetProtocolList(self
.GetProtocolList() + DeclarationsList
)
546 elif Type
== TAB_PPIS
:
547 self
.SetPpiList(self
.GetPpiList() + DeclarationsList
)
551 # Gen LibraryClasses of Dec
552 # <CName>=<GuidValue>
554 # @param ContainerFile: The Dec file full path
556 def GenLibraryClasses(self
, ContainerFile
):
559 Logger
.Debug(2, "Generate %s ..." % TAB_LIBRARY_CLASSES
)
560 LibraryClassDeclarations
= []
562 LibObj
= self
.DecParser
.GetLibraryClassSectionObject()
563 for Item
in LibObj
.GetAllLibraryclasses():
564 LibraryClass
= LibraryClassObject()
565 LibraryClass
.SetLibraryClass(Item
.Libraryclass
)
566 LibraryClass
.SetSupArchList(Item
.GetArchList())
567 LibraryClass
.SetIncludeHeader(Item
.File
)
568 HelpTxt
= ParseGenericComment(Item
.GetHeadComment() + \
569 Item
.GetTailComment(), None, '@libraryclass')
571 if self
.UniFileClassObject
:
572 HelpTxt
.SetLang(TAB_LANGUAGE_EN_X
)
573 LibraryClass
.SetHelpTextList([HelpTxt
])
574 LibraryClassDeclarations
.append(LibraryClass
)
576 self
.SetLibraryClassList(self
.GetLibraryClassList() + \
577 LibraryClassDeclarations
)
582 # <TokenSpcCName>.<TokenCName>|<Value>|<DatumType>|<Token>
584 # @param ContainerFile: The Dec file full path
586 def GenPcds(self
, ContainerFile
):
587 Logger
.Debug(2, "Generate %s ..." % TAB_PCDS
)
588 PcdObj
= self
.DecParser
.GetPcdSectionObject()
594 (TAB_PCDS_FIXED_AT_BUILD_NULL
, 'FixedPcd'),
595 (TAB_PCDS_PATCHABLE_IN_MODULE_NULL
, 'PatchPcd'),
596 (TAB_PCDS_FEATURE_FLAG_NULL
, 'FeaturePcd'),
597 (TAB_PCDS_DYNAMIC_EX_NULL
, 'PcdEx'),
598 (TAB_PCDS_DYNAMIC_NULL
, 'Pcd')]
603 # Initialize UniStrDict dictionary, top keys are language codes
608 if self
.UniFileClassObject
:
609 Language
= TAB_LANGUAGE_EN_X
611 Language
= TAB_LANGUAGE_EN_US
613 if self
.UniFileClassObject
:
614 UniStrDict
= self
.UniFileClassObject
.OrderedStringList
615 for Lang
in UniStrDict
:
616 for StringDefClassObject
in UniStrDict
[Lang
]:
617 StrList
= StringDefClassObject
.StringName
.split('_')
618 # StringName format is STR_<TOKENSPACECNAME>_<PCDCNAME>_PROMPT
619 if len(StrList
) == 4 and StrList
[0] == TAB_STR_TOKENCNAME
and StrList
[3] == TAB_STR_TOKENPROMPT
:
620 PromptStrList
.append((GetLanguageCode1766(Lang
), StringDefClassObject
.StringName
, \
621 StringDefClassObject
.StringValue
))
622 # StringName format is STR_<TOKENSPACECNAME>_<PCDCNAME>_HELP
623 if len(StrList
) == 4 and StrList
[0] == TAB_STR_TOKENCNAME
and StrList
[3] == TAB_STR_TOKENHELP
:
624 HelpStrList
.append((GetLanguageCode1766(Lang
), StringDefClassObject
.StringName
, \
625 StringDefClassObject
.StringValue
))
626 # StringName format is STR_<TOKENSPACECNAME>_ERR_##
627 if len(StrList
) == 4 and StrList
[0] == TAB_STR_TOKENCNAME
and StrList
[2] == TAB_STR_TOKENERR
:
628 PcdErrStrList
.append((GetLanguageCode1766(Lang
), StringDefClassObject
.StringName
, \
629 StringDefClassObject
.StringValue
))
633 for PcdType
, Type
in IterList
:
635 # Go through all archs
637 # for Arch in self.SupArchList + [TAB_ARCH_COMMON]:
639 for Item
in PcdObj
.GetPcdsByType(PcdType
.upper()):
640 PcdDeclaration
= GenPcdDeclaration(
642 (Item
.TokenSpaceGuidCName
, Item
.TokenCName
,
643 Item
.DefaultValue
, Item
.DatumType
, Item
.TokenValue
,
644 Type
, Item
.GetHeadComment(), Item
.GetTailComment(), ''),
646 self
.DecParser
.GetDefineSectionMacro()
648 PcdDeclaration
.SetSupArchList(Item
.GetArchListOfType(PcdType
))
651 # Get PCD error message from PCD error comment section in DEC file
653 for PcdErr
in PcdDeclaration
.GetPcdErrorsList():
654 if (PcdDeclaration
.GetTokenSpaceGuidCName(), PcdErr
.GetErrorNumber()) \
655 in self
.DecParser
.PcdErrorCommentDict
:
656 Key
= (PcdDeclaration
.GetTokenSpaceGuidCName(), PcdErr
.GetErrorNumber())
657 PcdErr
.SetErrorMessageList(PcdErr
.GetErrorMessageList() + \
658 [(Language
, self
.DecParser
.PcdErrorCommentDict
[Key
])])
660 for Index
in range(0, len(PromptStrList
)):
661 StrNameList
= PromptStrList
[Index
][1].split('_')
662 if StrNameList
[1].lower() == Item
.TokenSpaceGuidCName
.lower() and \
663 StrNameList
[2].lower() == Item
.TokenCName
.lower():
664 TxtObj
= TextObject()
665 TxtObj
.SetLang(PromptStrList
[Index
][0])
666 TxtObj
.SetString(PromptStrList
[Index
][2])
667 for Prompt
in PcdDeclaration
.GetPromptList():
668 if Prompt
.GetLang() == TxtObj
.GetLang() and \
669 Prompt
.GetString() == TxtObj
.GetString():
672 PcdDeclaration
.SetPromptList(PcdDeclaration
.GetPromptList() + [TxtObj
])
674 for Index
in range(0, len(HelpStrList
)):
675 StrNameList
= HelpStrList
[Index
][1].split('_')
676 if StrNameList
[1].lower() == Item
.TokenSpaceGuidCName
.lower() and \
677 StrNameList
[2].lower() == Item
.TokenCName
.lower():
678 TxtObj
= TextObject()
679 TxtObj
.SetLang(HelpStrList
[Index
][0])
680 TxtObj
.SetString(HelpStrList
[Index
][2])
681 for HelpStrObj
in PcdDeclaration
.GetHelpTextList():
682 if HelpStrObj
.GetLang() == TxtObj
.GetLang() and \
683 HelpStrObj
.GetString() == TxtObj
.GetString():
686 PcdDeclaration
.SetHelpTextList(PcdDeclaration
.GetHelpTextList() + [TxtObj
])
689 # Get PCD error message from UNI file
691 for Index
in range(0, len(PcdErrStrList
)):
692 StrNameList
= PcdErrStrList
[Index
][1].split('_')
693 if StrNameList
[1].lower() == Item
.TokenSpaceGuidCName
.lower() and \
694 StrNameList
[2].lower() == TAB_STR_TOKENERR
.lower():
695 for PcdErr
in PcdDeclaration
.GetPcdErrorsList():
696 if PcdErr
.GetErrorNumber().lower() == (TAB_HEX_START
+ StrNameList
[3]).lower() and \
697 (PcdErrStrList
[Index
][0], PcdErrStrList
[Index
][2]) not in PcdErr
.GetErrorMessageList():
698 PcdErr
.SetErrorMessageList(PcdErr
.GetErrorMessageList() + \
699 [(PcdErrStrList
[Index
][0], PcdErrStrList
[Index
][2])])
702 # Check to prevent missing error message if a Pcd has the error code.
704 for PcdErr
in PcdDeclaration
.GetPcdErrorsList():
705 if PcdErr
.GetErrorNumber().strip():
706 if not PcdErr
.GetErrorMessageList():
709 ST
.ERR_DECPARSE_PCD_UNMATCHED_ERRORCODE
% PcdErr
.GetErrorNumber(),
712 PcdErr
.GetFileLine())
714 PcdDeclarations
.append(PcdDeclaration
)
715 self
.SetPcdList(self
.GetPcdList() + PcdDeclarations
)
719 # Get error message via language
720 # @param ErrorMessageList: Error message tuple list the language and its message
721 # @param Lang: the language of setting
722 # @return: the error message described in the related UNI file
723 def GetEnErrorMessage(self
, ErrorMessageList
):
726 Lang
= TAB_LANGUAGE_EN_US
727 for (Language
, Message
) in ErrorMessageList
:
730 for (Language
, Message
) in ErrorMessageList
:
731 if Language
.find(TAB_LANGUAGE_EN
) >= 0:
735 return ErrorMessageList
[0][1]
741 # Replace the strings for Python eval function.
742 # @param ReplaceValue: The string that needs to be replaced.
743 # @return: The string was replaced, then eval function is always making out it.
744 def ReplaceForEval(self
, ReplaceValue
, IsRange
=False, IsExpr
=False):
748 # deal with "NOT EQ", "NOT LT", "NOT GT", "NOT LE", "NOT GE", "NOT NOT"
750 NOTNOT_Pattern
= '[\t\s]*NOT[\t\s]+NOT[\t\s]*'
751 NOTGE_Pattern
= '[\t\s]*NOT[\t\s]+GE[\t\s]*'
752 NOTLE_Pattern
= '[\t\s]*NOT[\t\s]+LE[\t\s]*'
753 NOTGT_Pattern
= '[\t\s]*NOT[\t\s]+GT[\t\s]*'
754 NOTLT_Pattern
= '[\t\s]*NOT[\t\s]+LT[\t\s]*'
755 NOTEQ_Pattern
= '[\t\s]*NOT[\t\s]+EQ[\t\s]*'
756 ReplaceValue
= re
.compile(NOTNOT_Pattern
).sub('', ReplaceValue
)
757 ReplaceValue
= re
.compile(NOTLT_Pattern
).sub('x >= ', ReplaceValue
)
758 ReplaceValue
= re
.compile(NOTGT_Pattern
).sub('x <= ', ReplaceValue
)
759 ReplaceValue
= re
.compile(NOTLE_Pattern
).sub('x > ', ReplaceValue
)
760 ReplaceValue
= re
.compile(NOTGE_Pattern
).sub('x < ', ReplaceValue
)
761 ReplaceValue
= re
.compile(NOTEQ_Pattern
).sub('x != ', ReplaceValue
)
764 ReplaceValue
= ReplaceValue
.replace('EQ', 'x ==')
765 ReplaceValue
= ReplaceValue
.replace('LT', 'x <')
766 ReplaceValue
= ReplaceValue
.replace('LE', 'x <=')
767 ReplaceValue
= ReplaceValue
.replace('GT', 'x >')
768 ReplaceValue
= ReplaceValue
.replace('GE', 'x >=')
769 ReplaceValue
= ReplaceValue
.replace('XOR', 'x ^')
771 ReplaceValue
= ReplaceValue
.replace('EQ', '==')
772 ReplaceValue
= ReplaceValue
.replace('NE', '!=')
773 ReplaceValue
= ReplaceValue
.replace('LT', '<')
774 ReplaceValue
= ReplaceValue
.replace('LE', '<=')
775 ReplaceValue
= ReplaceValue
.replace('GT', '>')
776 ReplaceValue
= ReplaceValue
.replace('GE', '>=')
777 ReplaceValue
= ReplaceValue
.replace('XOR', '^')
779 ReplaceValue
= ReplaceValue
.replace('AND', 'and')
780 ReplaceValue
= ReplaceValue
.replace('&&', ' and ')
781 ReplaceValue
= ReplaceValue
.replace('xor', '^')
782 ReplaceValue
= ReplaceValue
.replace('OR', 'or')
783 ReplaceValue
= ReplaceValue
.replace('||', ' or ')
784 ReplaceValue
= ReplaceValue
.replace('NOT', 'not')
785 if ReplaceValue
.find('!') >= 0 and ReplaceValue
[ReplaceValue
.index('!') + 1] != '=':
786 ReplaceValue
= ReplaceValue
.replace('!', ' not ')
787 if '.' in ReplaceValue
:
788 Pattern
= '[a-zA-Z0-9]{1,}\.[a-zA-Z0-9]{1,}'
789 MatchedList
= re
.findall(Pattern
, ReplaceValue
)
790 for MatchedItem
in MatchedList
:
791 if MatchedItem
not in self
.PcdDefaultValueDict
:
792 Logger
.Error("Dec File Parser", FORMAT_INVALID
, Message
=ST
.ERR_DECPARSE_PCD_NODEFINED
% MatchedItem
,
795 ReplaceValue
= ReplaceValue
.replace(MatchedItem
, self
.PcdDefaultValueDict
[MatchedItem
])
800 # Check pcd's default value according to the pcd's description
802 def CheckPcdValue(self
):
803 for Pcd
in self
.GetPcdList():
804 self
.PcdDefaultValueDict
[TAB_SPLIT
.join((Pcd
.GetTokenSpaceGuidCName(), Pcd
.GetCName())).strip()] = \
805 Pcd
.GetDefaultValue()
807 for Pcd
in self
.GetPcdList():
808 ValidationExpressions
= []
809 PcdGuidName
= TAB_SPLIT
.join((Pcd
.GetTokenSpaceGuidCName(), Pcd
.GetCName()))
810 Valids
= Pcd
.GetPcdErrorsList()
812 Expression
= Valid
.GetExpression()
815 # Delete the 'L' prefix of a quoted string, this operation is for eval()
817 QUOTED_PATTERN
= '[\t\s]*L?"[^"]*"'
818 QuotedMatchedObj
= re
.search(QUOTED_PATTERN
, Expression
)
820 MatchedStr
= QuotedMatchedObj
.group().strip()
821 if MatchedStr
.startswith('L'):
822 Expression
= Expression
.replace(MatchedStr
, MatchedStr
[1:].strip())
824 Expression
= self
.ReplaceForEval(Expression
, IsExpr
=True)
825 Expression
= Expression
.replace(PcdGuidName
, 'x')
826 Message
= self
.GetEnErrorMessage(Valid
.GetErrorMessageList())
827 ValidationExpressions
.append((Expression
, Message
))
829 ValidList
= Valid
.GetValidValue()
831 ValidValue
= 'x in %s' % [eval(v
) for v
in ValidList
.split(' ') if v
]
832 Message
= self
.GetEnErrorMessage(Valid
.GetErrorMessageList())
833 ValidationExpressions
.append((ValidValue
, Message
))
835 ValidValueRange
= Valid
.GetValidValueRange()
837 ValidValueRange
= self
.ReplaceForEval(ValidValueRange
, IsRange
=True)
838 if ValidValueRange
.find('-') >= 0:
839 ValidValueRange
= ValidValueRange
.replace('-', '<= x <=')
840 elif not ValidValueRange
.startswith('x ') and not ValidValueRange
.startswith('not ') \
841 and not ValidValueRange
.startswith('not(') and not ValidValueRange
.startswith('('):
842 ValidValueRange
= 'x %s' % ValidValueRange
843 Message
= self
.GetEnErrorMessage(Valid
.GetErrorMessageList())
844 ValidationExpressions
.append((ValidValueRange
, Message
))
846 DefaultValue
= self
.PcdDefaultValueDict
[PcdGuidName
.strip()]
848 # Delete the 'L' prefix of a quoted string, this operation is for eval()
850 QUOTED_PATTERN
= '[\t\s]*L?"[^"]*"'
851 QuotedMatchedObj
= re
.search(QUOTED_PATTERN
, DefaultValue
)
853 MatchedStr
= QuotedMatchedObj
.group().strip()
854 if MatchedStr
.startswith('L'):
855 DefaultValue
= DefaultValue
.replace(MatchedStr
, MatchedStr
[1:].strip())
858 DefaultValue
= eval(DefaultValue
.replace('TRUE', 'True').replace('true', 'True')
859 .replace('FALSE', 'False').replace('false', 'False'))
860 except BaseException
:
863 for (Expression
, Msg
) in ValidationExpressions
:
865 if not eval(Expression
, {'x':DefaultValue
}):
866 Logger
.Error("Dec File Parser", FORMAT_INVALID
, ExtraData
='%s, value = %s' %\
867 (PcdGuidName
, DefaultValue
), Message
=Msg
, File
=self
.FullPath
)
869 Logger
.Error("Dec File Parser", FORMAT_INVALID
, ExtraData
=PcdGuidName
, \
870 Message
=Msg
, File
=self
.FullPath
)
874 def GenModuleFileList(self
, ContainerFile
):
876 ContainerFileName
= os
.path
.basename(ContainerFile
)
877 ContainerFilePath
= os
.path
.dirname(ContainerFile
)
878 for Item
in GetFiles(ContainerFilePath
,
879 ['CVS', '.svn'] + self
.GetIncludePathList(), False):
880 ExtName
= os
.path
.splitext(Item
)[1]
881 if ExtName
.lower() == '.inf':
882 ModuleFileList
.append(Item
)
883 elif ExtName
.upper() == '.DEC' and self
.CheckMulDec
:
884 if Item
== ContainerFileName
:
886 Logger
.Error('MkPkg',
888 ST
.ERR_MUL_DEC_ERROR
%(ContainerFilePath
,
892 self
.SetModuleFileList(ModuleFileList
)
894 ## Show detailed information of Package
896 # Print all members and their values of Package class
898 def ShowPackage(self
):
899 print('\nName =', self
.GetName())
900 print('\nBaseName =', self
.GetBaseName())
901 print('\nVersion =', self
.GetVersion())
902 print('\nGuid =', self
.GetGuid())
904 print('\nStandardIncludes = %d ' \
905 % len(self
.GetStandardIncludeFileList()), end
=' ')
906 for Item
in self
.GetStandardIncludeFileList():
907 print(Item
.GetFilePath(), ' ', Item
.GetSupArchList())
908 print('\nPackageIncludes = %d \n' \
909 % len(self
.GetPackageIncludeFileList()), end
=' ')
910 for Item
in self
.GetPackageIncludeFileList():
911 print(Item
.GetFilePath(), ' ', Item
.GetSupArchList())
913 print('\nGuids =', self
.GetGuidList())
914 for Item
in self
.GetGuidList():
915 print(Item
.GetCName(), Item
.GetGuid(), Item
.GetSupArchList())
916 print('\nProtocols =', self
.GetProtocolList())
917 for Item
in self
.GetProtocolList():
918 print(Item
.GetCName(), Item
.GetGuid(), Item
.GetSupArchList())
919 print('\nPpis =', self
.GetPpiList())
920 for Item
in self
.GetPpiList():
921 print(Item
.GetCName(), Item
.GetGuid(), Item
.GetSupArchList())
922 print('\nLibraryClasses =', self
.GetLibraryClassList())
923 for Item
in self
.GetLibraryClassList():
924 print(Item
.GetLibraryClass(), Item
.GetRecommendedInstance(), \
925 Item
.GetSupArchList())
926 print('\nPcds =', self
.GetPcdList())
927 for Item
in self
.GetPcdList():
928 print('CName=', Item
.GetCName(), 'TokenSpaceGuidCName=', \
929 Item
.GetTokenSpaceGuidCName(), \
930 'DefaultValue=', Item
.GetDefaultValue(), \
931 'ValidUsage=', Item
.GetValidUsage(), \
932 'SupArchList', Item
.GetSupArchList(), \
933 'Token=', Item
.GetToken(), 'DatumType=', Item
.GetDatumType())
935 for Item
in self
.GetMiscFileList():
936 print(Item
.GetName())
937 for FileObjectItem
in Item
.GetFileList():
938 print(FileObjectItem
.GetURI())
939 print('****************\n')
943 # @param ContainerFile: File name of the DEC file
944 # @param PcdInfo: Pcd information, of format (TokenGuidCName,
945 # TokenName, Value, DatumType, Token, Type,
946 # GenericComment, TailComment, Arch)
947 # @param Language: The language of HelpText, Prompt
949 def GenPcdDeclaration(ContainerFile
, PcdInfo
, Language
, MacroReplaceDict
):
953 TokenGuidCName
, TokenName
, Value
, DatumType
, Token
, Type
, \
954 GenericComment
, TailComment
, Arch
= PcdInfo
956 Pcd
.SetCName(TokenName
)
958 Pcd
.SetTokenSpaceGuidCName(TokenGuidCName
)
959 Pcd
.SetDatumType(DatumType
)
960 Pcd
.SetDefaultValue(Value
)
961 Pcd
.SetValidUsage(Type
)
963 # MaxDatumSize is required field for 'VOID*' PCD
965 if DatumType
== TAB_PTR_TYPE_PCD
:
966 Pcd
.SetMaxDatumSize(ITEM_UNDEFINED
)
969 Pcd
.SetSupArchList(SupArchList
)
972 HelpStr
, PcdErrList
, PromptStr
= ParseDecPcdGenericComment(GenericComment
,
978 Pcd
.SetPcdErrorsList(PcdErrList
)
981 SupModuleList
, TailHelpStr
= ParseDecPcdTailComment(TailComment
,
984 Pcd
.SetSupModuleList(SupModuleList
)
986 if HelpStr
and (not HelpStr
.endswith('\n')) and TailHelpStr
:
988 HelpStr
+= TailHelpStr
990 HelpTxtObj
= TextObject()
991 HelpTxtObj
.SetLang(Language
)
992 HelpTxtObj
.SetString(HelpStr
)
993 Pcd
.SetHelpTextList([HelpTxtObj
])
995 TxtObj
= TextObject()
996 TxtObj
.SetLang(Language
)
997 TxtObj
.SetString(PromptStr
)
998 Pcd
.SetPromptList([TxtObj
])