2 # This file is used to define common parsing related functions used in parsing
3 # Inf/Dsc/Makefile process
5 # Copyright (c) 2008 - 2018, Intel Corporation. All rights reserved.<BR>
6 # SPDX-License-Identifier: BSD-2-Clause-Patent
12 from __future__
import absolute_import
13 import Common
.LongFilePathOs
as os
, re
14 import Common
.EdkLogger
as EdkLogger
15 from Common
.DataType
import *
16 from CommonDataClass
.DataClass
import *
17 from Common
.StringUtils
import CleanString
, GetSplitValueList
, ReplaceMacro
18 from . import EotGlobalData
19 from Common
.StringUtils
import GetSplitList
20 from Common
.LongFilePathSupport
import OpenLongFilePath
as open
26 # Call external decompress tool to decompress the fv section
28 def DeCompress(Method
, Input
):
29 # Write the input to a temp file
30 open('_Temp.bin', 'wb').write(Input
)
33 cmd
= r
'LzmaCompress -o _New.bin -d _Temp.bin'
35 cmd
= r
'TianoCompress -d --uefi -o _New.bin _Temp.bin'
36 if Method
== 'Framework':
37 cmd
= r
'TianoCompress -d -o _New.bin _Temp.bin'
39 # Call tool to create the decompressed output file
40 Process
= subprocess
.Popen(cmd
, stdout
=subprocess
.PIPE
, stderr
=subprocess
.STDOUT
)
41 Process
.communicate()[0]
43 # Return the beffer of New.bin
44 if os
.path
.exists('_New.bin'):
45 return open('_New.bin', 'rb').read()
48 ## PreProcess() method
52 # 1. Remove all comments
53 # 2. Merge multiple lines code to one line
55 # @param Filename: Name of the file to be parsed
56 # @param MergeMultipleLines: Switch for if merge multiple lines
57 # @param LineNo: Default line no
59 # @return Lines: The file contents after removing comments
61 def PreProcess(Filename
, MergeMultipleLines
= True, LineNo
= -1):
63 Filename
= os
.path
.normpath(Filename
)
64 if not os
.path
.isfile(Filename
):
65 EdkLogger
.error("Eot", EdkLogger
.FILE_NOT_FOUND
, ExtraData
=Filename
)
67 IsFindBlockComment
= False
68 IsFindBlockCode
= False
70 ReservedLineLength
= 0
71 for Line
in open(Filename
, 'r'):
73 # Remove comment block
74 if Line
.find(TAB_COMMENT_EDK_START
) > -1:
75 ReservedLine
= GetSplitList(Line
, TAB_COMMENT_EDK_START
, 1)[0]
76 IsFindBlockComment
= True
77 if Line
.find(TAB_COMMENT_EDK_END
) > -1:
78 Line
= ReservedLine
+ GetSplitList(Line
, TAB_COMMENT_EDK_END
, 1)[1]
80 IsFindBlockComment
= False
81 if IsFindBlockComment
:
85 # Remove comments at tail and remove spaces again
86 Line
= CleanString(Line
)
91 if MergeMultipleLines
:
92 # Add multiple lines to one line
93 if IsFindBlockCode
and Line
[-1] != TAB_SLASH
:
94 ReservedLine
= (ReservedLine
+ TAB_SPACE_SPLIT
+ Line
).strip()
95 Lines
.append(ReservedLine
)
96 for Index
in (0, ReservedLineLength
):
99 ReservedLineLength
= 0
100 IsFindBlockCode
= False
102 if Line
[-1] == TAB_SLASH
:
103 ReservedLine
= ReservedLine
+ TAB_SPACE_SPLIT
+ Line
[0:-1].strip()
104 ReservedLineLength
= ReservedLineLength
+ 1
105 IsFindBlockCode
= True
112 ## AddToGlobalMacro() method
114 # Add a macro to EotGlobalData.gMACRO
116 # @param Name: Name of the macro
117 # @param Value: Value of the macro
119 def AddToGlobalMacro(Name
, Value
):
120 Value
= ReplaceMacro(Value
, EotGlobalData
.gMACRO
, True)
121 EotGlobalData
.gMACRO
[Name
] = Value
123 ## AddToSelfMacro() method
125 # Parse a line of macro definition and add it to a macro set
127 # @param SelfMacro: The self macro set
128 # @param Line: The line of a macro definition
130 # @return Name: Name of macro
131 # @return Value: Value of macro
133 def AddToSelfMacro(SelfMacro
, Line
):
135 List
= GetSplitValueList(Line
, TAB_EQUAL_SPLIT
, 1)
139 Value
= ReplaceMacro(Value
, EotGlobalData
.gMACRO
, True)
140 Value
= ReplaceMacro(Value
, SelfMacro
, True)
141 SelfMacro
[Name
] = Value
145 ## GetIncludeListOfFile() method
147 # Get the include path list for a source file
149 # 1. Find the source file belongs to which INF file
150 # 2. Find the inf's package
151 # 3. Return the include path list of the package
153 # @param WorkSpace: WORKSPACE path
154 # @param Filepath: File path
155 # @param Db: Eot database
157 # @return IncludeList: A list of include directories
159 def GetIncludeListOfFile(WorkSpace
, Filepath
, Db
):
161 Filepath
= os
.path
.normpath(Filepath
)
163 select Value1 from Inf where Model = %s and BelongsToFile in(
164 select distinct B.BelongsToFile from File as A left join Inf as B
165 where A.ID = B.BelongsToFile and B.Model = %s and (A.Path || '%s' || B.Value1) = '%s')""" \
166 % (MODEL_META_DATA_PACKAGE
, MODEL_EFI_SOURCE_FILE
, '\\', Filepath
)
167 RecordSet
= Db
.TblFile
.Exec(SqlCommand
)
168 for Record
in RecordSet
:
169 DecFullPath
= os
.path
.normpath(os
.path
.join(WorkSpace
, Record
[0]))
170 (DecPath
, DecName
) = os
.path
.split(DecFullPath
)
171 SqlCommand
= """select Value1 from Dec where BelongsToFile =
172 (select ID from File where FullPath = '%s') and Model = %s""" \
173 % (DecFullPath
, MODEL_EFI_INCLUDE
)
174 NewRecordSet
= Db
.TblDec
.Exec(SqlCommand
)
175 for NewRecord
in NewRecordSet
:
176 IncludePath
= os
.path
.normpath(os
.path
.join(DecPath
, NewRecord
[0]))
177 if IncludePath
not in IncludeList
:
178 IncludeList
.append(IncludePath
)
182 ## GetTableList() method
184 # Search table file and find all small tables
186 # @param FileModelList: Model code for the file list
187 # @param Table: Table to insert records
188 # @param Db: Eot database
190 # @return TableList: A list of tables
192 def GetTableList(FileModelList
, Table
, Db
):
194 SqlCommand
= """select ID, FullPath from File where Model in %s""" % str(FileModelList
)
195 RecordSet
= Db
.TblFile
.Exec(SqlCommand
)
196 for Record
in RecordSet
:
197 TableName
= Table
+ str(Record
[0])
198 TableList
.append([TableName
, Record
[1]])
202 ## GetAllIncludeDir() method
204 # Find all Include directories
206 # @param Db: Eot database
208 # @return IncludeList: A list of include directories
210 def GetAllIncludeDirs(Db
):
212 SqlCommand
= """select distinct Value1 from Inf where Model = %s order by Value1""" % MODEL_EFI_INCLUDE
213 RecordSet
= Db
.TblInf
.Exec(SqlCommand
)
215 for Record
in RecordSet
:
216 IncludeList
.append(Record
[0])
220 ## GetAllIncludeFiles() method
222 # Find all Include files
224 # @param Db: Eot database
226 # @return IncludeFileList: A list of include files
228 def GetAllIncludeFiles(Db
):
229 IncludeList
= GetAllIncludeDirs(Db
)
232 for Dir
in IncludeList
:
233 if os
.path
.isdir(Dir
):
234 SubDir
= os
.listdir(Dir
)
236 if os
.path
.isfile(Item
):
237 IncludeFileList
.append(Item
)
239 return IncludeFileList
241 ## GetAllSourceFiles() method
243 # Find all source files
245 # @param Db: Eot database
247 # @return SourceFileList: A list of source files
249 def GetAllSourceFiles(Db
):
251 SqlCommand
= """select distinct Value1 from Inf where Model = %s order by Value1""" % MODEL_EFI_SOURCE_FILE
252 RecordSet
= Db
.TblInf
.Exec(SqlCommand
)
254 for Record
in RecordSet
:
255 SourceFileList
.append(Record
[0])
257 return SourceFileList
259 ## GetAllFiles() method
261 # Find all files, both source files and include files
263 # @param Db: Eot database
265 # @return FileList: A list of files
269 IncludeFileList
= GetAllIncludeFiles(Db
)
270 SourceFileList
= GetAllSourceFiles(Db
)
271 for Item
in IncludeFileList
:
272 if os
.path
.isfile(Item
) and Item
not in FileList
:
273 FileList
.append(Item
)
274 for Item
in SourceFileList
:
275 if os
.path
.isfile(Item
) and Item
not in FileList
:
276 FileList
.append(Item
)
280 ## ParseConditionalStatement() method
282 # Parse conditional statement
284 # @param Line: One line to be parsed
285 # @param Macros: A set of all macro
286 # @param StatusSet: A set of all status
288 # @retval True: Find keyword of conditional statement
289 # @retval False: Not find keyword of conditional statement
291 def ParseConditionalStatement(Line
, Macros
, StatusSet
):
292 NewLine
= Line
.upper()
293 if NewLine
.find(TAB_IF_EXIST
.upper()) > -1:
294 IfLine
= Line
[NewLine
.find(TAB_IF_EXIST
) + len(TAB_IF_EXIST
) + 1:].strip()
295 IfLine
= ReplaceMacro(IfLine
, EotGlobalData
.gMACRO
, True)
296 IfLine
= ReplaceMacro(IfLine
, Macros
, True)
297 IfLine
= IfLine
.replace("\"", '')
298 IfLine
= IfLine
.replace("(", '')
299 IfLine
= IfLine
.replace(")", '')
300 Status
= os
.path
.exists(os
.path
.normpath(IfLine
))
301 StatusSet
.append([Status
])
303 if NewLine
.find(TAB_IF_DEF
.upper()) > -1:
304 IfLine
= Line
[NewLine
.find(TAB_IF_DEF
) + len(TAB_IF_DEF
) + 1:].strip()
306 if IfLine
in Macros
or IfLine
in EotGlobalData
.gMACRO
:
308 StatusSet
.append([Status
])
310 if NewLine
.find(TAB_IF_N_DEF
.upper()) > -1:
311 IfLine
= Line
[NewLine
.find(TAB_IF_N_DEF
) + len(TAB_IF_N_DEF
) + 1:].strip()
313 if IfLine
not in Macros
and IfLine
not in EotGlobalData
.gMACRO
:
315 StatusSet
.append([Status
])
317 if NewLine
.find(TAB_IF
.upper()) > -1:
318 IfLine
= Line
[NewLine
.find(TAB_IF
) + len(TAB_IF
) + 1:].strip()
319 Status
= ParseConditionalStatementMacros(IfLine
, Macros
)
320 StatusSet
.append([Status
])
322 if NewLine
.find(TAB_ELSE_IF
.upper()) > -1:
323 IfLine
= Line
[NewLine
.find(TAB_ELSE_IF
) + len(TAB_ELSE_IF
) + 1:].strip()
324 Status
= ParseConditionalStatementMacros(IfLine
, Macros
)
325 StatusSet
[-1].append(Status
)
327 if NewLine
.find(TAB_ELSE
.upper()) > -1:
329 for Item
in StatusSet
[-1]:
330 Status
= Status
or Item
331 StatusSet
[-1].append(not Status
)
333 if NewLine
.find(TAB_END_IF
.upper()) > -1:
339 ## ParseConditionalStatement() method
341 # Parse conditional statement with Macros
343 # @param Line: One line to be parsed
344 # @param Macros: A set of macros
346 # @return Line: New line after replacing macros
348 def ParseConditionalStatementMacros(Line
, Macros
):
349 if Line
.upper().find('DEFINED(') > -1 or Line
.upper().find('EXIST') > -1:
351 Line
= ReplaceMacro(Line
, EotGlobalData
.gMACRO
, True)
352 Line
= ReplaceMacro(Line
, Macros
, True)
353 Line
= Line
.replace("&&", "and")
354 Line
= Line
.replace("||", "or")
357 ## GetConditionalStatementStatus() method
359 # 1. Assume the latest status as True
360 # 2. Pop the top status of status set, previous status
361 # 3. Compare the latest one and the previous one and get new status
363 # @param StatusSet: A set of all status
365 # @return Status: The final status
367 def GetConditionalStatementStatus(StatusSet
):
369 for Item
in StatusSet
:
370 Status
= Status
and Item
[-1]
374 ## SearchBelongsToFunction() method
376 # Search all functions belong to the file
378 # @param BelongsToFile: File id
379 # @param StartLine: Start line of search scope
380 # @param EndLine: End line of search scope
382 # @return: The found function
384 def SearchBelongsToFunction(BelongsToFile
, StartLine
, EndLine
):
385 SqlCommand
= """select ID, Name from Function where BelongsToFile = %s and StartLine <= %s and EndLine >= %s""" %(BelongsToFile
, StartLine
, EndLine
)
386 RecordSet
= EotGlobalData
.gDb
.TblFunction
.Exec(SqlCommand
)
388 return RecordSet
[0][0], RecordSet
[0][1]
392 ## SearchPpiCallFunction() method
394 # Search all used PPI calling function 'PeiServicesReInstallPpi' and 'PeiServicesInstallPpi'
395 # Store the result to database
397 # @param Identifier: Table id
398 # @param SourceFileID: Source file id
399 # @param SourceFileFullPath: Source file full path
400 # @param ItemMode: Mode of the item
402 def SearchPpiCallFunction(Identifier
, SourceFileID
, SourceFileFullPath
, ItemMode
):
403 ItemName
, ItemType
, GuidName
, GuidMacro
, GuidValue
= '', 'Ppi', '', '', ''
404 SqlCommand
= """select Value, Name, BelongsToFile, StartLine, EndLine from %s
405 where (Name like '%%%s%%' and Model = %s)""" \
406 % (Identifier
, 'PeiServicesReInstallPpi', MODEL_IDENTIFIER_FUNCTION_CALLING
)
407 BelongsToFunctionID
, BelongsToFunction
= -1, ''
408 Db
= EotGlobalData
.gDb
.TblReport
409 RecordSet
= Db
.Exec(SqlCommand
)
410 for Record
in RecordSet
:
412 BelongsToFile
, StartLine
, EndLine
= Record
[2], Record
[3], Record
[4]
413 BelongsToFunctionID
, BelongsToFunction
= SearchBelongsToFunction(BelongsToFile
, StartLine
, EndLine
)
414 VariableList
= Record
[0].split(',')
415 for Variable
in VariableList
:
416 Variable
= Variable
.strip()
417 # Get index of the variable
418 if Variable
.find('[') > -1:
419 Index
= int(Variable
[Variable
.find('[') + 1 : Variable
.find(']')])
420 Variable
= Variable
[:Variable
.find('[')]
422 if Variable
.startswith('&'):
423 Variable
= Variable
[1:]
425 SqlCommand
= """select Value from %s where (Name like '%%%s%%') and Model = %s""" \
426 % (Identifier
, Variable
, MODEL_IDENTIFIER_VARIABLE
)
427 NewRecordSet
= Db
.Exec(SqlCommand
)
429 NewRecord
= NewRecordSet
[0][0]
430 VariableValueList
= NewRecord
.split('},')
431 if len(VariableValueList
) > Index
:
432 VariableValue
= VariableValueList
[Index
]
433 NewVariableValueList
= VariableValue
.split(',')
434 if len(NewVariableValueList
) > 1:
435 NewVariableValue
= NewVariableValueList
[1].strip()
436 if NewVariableValue
.startswith('&'):
437 Db
.Insert(-1, '', '', SourceFileID
, SourceFileFullPath
, ItemName
, ItemType
, ItemMode
, NewVariableValue
[1:], GuidMacro
, GuidValue
, BelongsToFunction
, 0)
440 EotGlobalData
.gOP_UN_MATCHED
.write('%s, %s, %s, %s, %s, %s\n' % (ItemType
, ItemMode
, SourceFileID
, SourceFileFullPath
, StartLine
, NewParameter
))
442 ItemName
, ItemType
, GuidName
, GuidMacro
, GuidValue
= '', 'Ppi', '', '', ''
443 SqlCommand
= """select Value, Name, BelongsToFile, StartLine, EndLine from %s
444 where (Value like '%%%s%%' and Model = %s)""" \
445 % (Identifier
, 'PeiServicesInstallPpi', MODEL_IDENTIFIER_ASSIGNMENT_EXPRESSION
)
446 BelongsToFunctionID
, BelongsToFunction
= -1, ''
447 Db
= EotGlobalData
.gDb
.TblReport
448 RecordSet
= Db
.Exec(SqlCommand
)
450 SqlCommand
= """select Value, Name, BelongsToFile, StartLine, EndLine from %s
451 where (Name like '%%%s%%' and Model = %s)""" \
452 % (Identifier
, 'PeiServicesInstallPpi', MODEL_IDENTIFIER_FUNCTION_CALLING
)
453 Db
= EotGlobalData
.gDb
.TblReport
454 RecordSet2
= Db
.Exec(SqlCommand
)
456 for Record
in RecordSet
+ RecordSet2
:
460 BelongsToFile
, StartLine
, EndLine
= Record
[2], Record
[3], Record
[4]
461 BelongsToFunctionID
, BelongsToFunction
= SearchBelongsToFunction(BelongsToFile
, StartLine
, EndLine
)
462 Variable
= Record
[0].replace('PeiServicesInstallPpi', '').replace('(', '').replace(')', '').replace('&', '').strip()
463 Variable
= Variable
[Variable
.find(',') + 1:].strip()
464 # Get index of the variable
465 if Variable
.find('[') > -1:
466 Index
= int(Variable
[Variable
.find('[') + 1 : Variable
.find(']')])
467 Variable
= Variable
[:Variable
.find('[')]
469 if Variable
.startswith('&'):
470 Variable
= Variable
[1:]
472 SqlCommand
= """select Value from %s where (Name like '%%%s%%') and Model = %s""" \
473 % (Identifier
, Variable
, MODEL_IDENTIFIER_VARIABLE
)
474 NewRecordSet
= Db
.Exec(SqlCommand
)
476 NewRecord
= NewRecordSet
[0][0]
477 VariableValueList
= NewRecord
.split('},')
478 for VariableValue
in VariableValueList
[Index
:]:
479 NewVariableValueList
= VariableValue
.split(',')
480 if len(NewVariableValueList
) > 1:
481 NewVariableValue
= NewVariableValueList
[1].strip()
482 if NewVariableValue
.startswith('&'):
483 Db
.Insert(-1, '', '', SourceFileID
, SourceFileFullPath
, ItemName
, ItemType
, ItemMode
, NewVariableValue
[1:], GuidMacro
, GuidValue
, BelongsToFunction
, 0)
486 EotGlobalData
.gOP_UN_MATCHED
.write('%s, %s, %s, %s, %s, %s\n' % (ItemType
, ItemMode
, SourceFileID
, SourceFileFullPath
, StartLine
, NewParameter
))
488 ## SearchPpis() method
490 # Search all used PPI calling function
491 # Store the result to database
493 # @param SqlCommand: SQL command statement
494 # @param Table: Table id
495 # @param SourceFileID: Source file id
496 # @param SourceFileFullPath: Source file full path
497 # @param ItemMode: Mode of the item
498 # @param PpiMode: Mode of PPI
500 def SearchPpi(SqlCommand
, Table
, SourceFileID
, SourceFileFullPath
, ItemMode
, PpiMode
= 1):
501 ItemName
, ItemType
, GuidName
, GuidMacro
, GuidValue
= '', 'Ppi', '', '', ''
502 BelongsToFunctionID
, BelongsToFunction
= -1, ''
503 Db
= EotGlobalData
.gDb
.TblReport
504 RecordSet
= Db
.Exec(SqlCommand
)
505 for Record
in RecordSet
:
506 Parameter
= GetPpiParameter(Record
[0], PpiMode
)
507 BelongsToFile
, StartLine
, EndLine
= Record
[2], Record
[3], Record
[4]
508 # Get BelongsToFunction
509 BelongsToFunctionID
, BelongsToFunction
= SearchBelongsToFunction(BelongsToFile
, StartLine
, EndLine
)
511 # Default is Not Found
515 if ItemMode
== 'Consumed':
516 if Parameter
.startswith('g'):
517 Db
.Insert(-1, '', '', SourceFileID
, SourceFileFullPath
, ItemName
, ItemType
, ItemMode
, Parameter
, GuidMacro
, GuidValue
, BelongsToFunction
, 0)
519 EotGlobalData
.gOP_UN_MATCHED
.write('%s, %s, %s, %s, %s, %s\n' % (ItemType
, ItemMode
, SourceFileID
, SourceFileFullPath
, StartLine
, Parameter
))
522 # Direct Parameter.Guid
523 SqlCommand
= """select Value from %s where (Name like '%%%s.Guid%%' or Name like '%%%s->Guid%%') and Model = %s""" % (Table
, Parameter
, Parameter
, MODEL_IDENTIFIER_ASSIGNMENT_EXPRESSION
)
524 NewRecordSet
= Db
.Exec(SqlCommand
)
525 for NewRecord
in NewRecordSet
:
526 GuidName
= GetParameterName(NewRecord
[0])
527 Db
.Insert(-1, '', '', SourceFileID
, SourceFileFullPath
, ItemName
, ItemType
, ItemMode
, GuidName
, GuidMacro
, GuidValue
, BelongsToFunction
, 0)
533 if Key
.rfind(' ') > -1:
534 Key
= Key
[Key
.rfind(' ') : ].strip().replace('&', '')
535 Value
= FindKeyValue(EotGlobalData
.gDb
.TblFile
, Table
, Key
)
536 List
= GetSplitValueList(Value
.replace('\n', ''), TAB_COMMA_SPLIT
)
538 GuidName
= GetParameterName(List
[1])
539 Db
.Insert(-1, '', '', SourceFileID
, SourceFileFullPath
, ItemName
, ItemType
, ItemMode
, GuidName
, GuidMacro
, GuidValue
, BelongsToFunction
, 0)
544 Start
= Parameter
.find('[')
545 End
= Parameter
.find(']')
546 if Start
> -1 and End
> -1 and Start
< End
:
548 Index
= int(Parameter
[Start
+ 1 : End
])
549 Parameter
= Parameter
[0 : Start
]
550 SqlCommand
= """select Value from %s where Name = '%s' and Model = %s""" % (Table
, Parameter
, MODEL_IDENTIFIER_VARIABLE
)
551 NewRecordSet
= Db
.Exec(SqlCommand
)
552 for NewRecord
in NewRecordSet
:
553 NewParameter
= GetSplitValueList(NewRecord
[0], '}')[Index
]
554 GuidName
= GetPpiParameter(NewParameter
[NewParameter
.find('{') : ])
555 Db
.Insert(-1, '', '', SourceFileID
, SourceFileFullPath
, ItemName
, ItemType
, ItemMode
, GuidName
, GuidMacro
, GuidValue
, BelongsToFunction
, 0)
560 # A External Parameter
562 SqlCommand
= """select File.ID from Inf, File
563 where BelongsToFile = (select BelongsToFile from Inf where Value1 = '%s')
564 and Inf.Model = %s and Inf.Value1 = File.FullPath and File.Model = %s""" % (SourceFileFullPath
, MODEL_EFI_SOURCE_FILE
, MODEL_FILE_C
)
565 NewRecordSet
= Db
.Exec(SqlCommand
)
566 for NewRecord
in NewRecordSet
:
567 Table
= 'Identifier' + str(NewRecord
[0])
568 SqlCommand
= """select Value from %s where Name = '%s' and Modifier = 'EFI_PEI_PPI_DESCRIPTOR' and Model = %s""" % (Table
, Parameter
, MODEL_IDENTIFIER_VARIABLE
)
569 PpiSet
= Db
.Exec(SqlCommand
)
571 GuidName
= GetPpiParameter(PpiSet
[0][0])
573 Db
.Insert(-1, '', '', SourceFileID
, SourceFileFullPath
, ItemName
, ItemType
, ItemMode
, GuidName
, GuidMacro
, GuidValue
, BelongsToFunction
, 0)
578 EotGlobalData
.gOP_UN_MATCHED
.write('%s, %s, %s, %s, %s, %s\n' % (ItemType
, ItemMode
, SourceFileID
, SourceFileFullPath
, StartLine
, Parameter
))
580 ## SearchProtocols() method
582 # Search all used PROTOCOL calling function
583 # Store the result to database
585 # @param SqlCommand: SQL command statement
586 # @param Table: Table id
587 # @param SourceFileID: Source file id
588 # @param SourceFileFullPath: Source file full path
589 # @param ItemMode: Mode of the item
590 # @param ProtocolMode: Mode of PROTOCOL
592 def SearchProtocols(SqlCommand
, Table
, SourceFileID
, SourceFileFullPath
, ItemMode
, ProtocolMode
):
593 ItemName
, ItemType
, GuidName
, GuidMacro
, GuidValue
= '', 'Protocol', '', '', ''
594 BelongsToFunctionID
, BelongsToFunction
= -1, ''
595 Db
= EotGlobalData
.gDb
.TblReport
596 RecordSet
= Db
.Exec(SqlCommand
)
597 for Record
in RecordSet
:
599 BelongsToFile
, StartLine
, EndLine
= Record
[2], Record
[3], Record
[4]
600 # Get BelongsToFunction
601 BelongsToFunctionID
, BelongsToFunction
= SearchBelongsToFunction(BelongsToFile
, StartLine
, EndLine
)
603 # Default is Not Found
606 if ProtocolMode
== 0 or ProtocolMode
== 1:
607 Parameter
= GetProtocolParameter(Record
[0], ProtocolMode
)
608 if Parameter
.startswith('g') or Parameter
.endswith('Guid') or Parameter
== 'ShellEnvProtocol' or Parameter
== 'ShellInterfaceProtocol':
609 GuidName
= GetParameterName(Parameter
)
610 Db
.Insert(-1, '', '', SourceFileID
, SourceFileFullPath
, ItemName
, ItemType
, ItemMode
, GuidName
, GuidMacro
, GuidValue
, BelongsToFunction
, 0)
613 if ProtocolMode
== 2:
614 Protocols
= GetSplitValueList(Record
[0], TAB_COMMA_SPLIT
)
615 for Protocol
in Protocols
:
616 if Protocol
.startswith('&') and Protocol
.endswith('Guid'):
617 GuidName
= GetParameterName(Protocol
)
618 Db
.Insert(-1, '', '', SourceFileID
, SourceFileFullPath
, ItemName
, ItemType
, ItemMode
, GuidName
, GuidMacro
, GuidValue
, BelongsToFunction
, 0)
621 NewValue
= FindKeyValue(EotGlobalData
.gDb
.TblFile
, Table
, Protocol
)
622 if Protocol
!= NewValue
and NewValue
.endswith('Guid'):
623 GuidName
= GetParameterName(NewValue
)
624 Db
.Insert(-1, '', '', SourceFileID
, SourceFileFullPath
, ItemName
, ItemType
, ItemMode
, GuidName
, GuidMacro
, GuidValue
, BelongsToFunction
, 0)
628 if BelongsToFunction
in EotGlobalData
.gProducedProtocolLibrary
or BelongsToFunction
in EotGlobalData
.gConsumedProtocolLibrary
:
629 EotGlobalData
.gOP_UN_MATCHED_IN_LIBRARY_CALLING
.write('%s, %s, %s, %s, %s, %s, %s\n' % (ItemType
, ItemMode
, SourceFileID
, SourceFileFullPath
, StartLine
, Parameter
, BelongsToFunction
))
631 EotGlobalData
.gOP_UN_MATCHED
.write('%s, %s, %s, %s, %s, %s\n' % (ItemType
, ItemMode
, SourceFileID
, SourceFileFullPath
, StartLine
, Parameter
))
633 ## SearchFunctionCalling() method
635 # Search all used PPI/PROTOCOL calling function by library
636 # Store the result to database
638 # @param SqlCommand: SQL command statement
639 # @param Table: Table id
640 # @param SourceFileID: Source file id
641 # @param SourceFileFullPath: Source file full path
642 # @param ItemType: Type of the item, PPI or PROTOCOL
643 # @param ItemMode: Mode of item
645 def SearchFunctionCalling(Table
, SourceFileID
, SourceFileFullPath
, ItemType
, ItemMode
):
647 Db
= EotGlobalData
.gDb
.TblReport
648 Parameters
, ItemName
, GuidName
, GuidMacro
, GuidValue
, BelongsToFunction
= [], '', '', '', '', ''
649 if ItemType
== 'Protocol' and ItemMode
== 'Produced':
650 LibraryList
= EotGlobalData
.gProducedProtocolLibrary
651 elif ItemType
== 'Protocol' and ItemMode
== 'Consumed':
652 LibraryList
= EotGlobalData
.gConsumedProtocolLibrary
653 elif ItemType
== 'Protocol' and ItemMode
== 'Callback':
654 LibraryList
= EotGlobalData
.gCallbackProtocolLibrary
655 elif ItemType
== 'Ppi' and ItemMode
== 'Produced':
656 LibraryList
= EotGlobalData
.gProducedPpiLibrary
657 elif ItemType
== 'Ppi' and ItemMode
== 'Consumed':
658 LibraryList
= EotGlobalData
.gConsumedPpiLibrary
660 for Library
in LibraryList
:
661 Index
= LibraryList
[Library
]
662 SqlCommand
= """select Value, StartLine from %s
663 where Name like '%%%s%%' and Model = %s""" \
664 % (Table
, Library
, MODEL_IDENTIFIER_FUNCTION_CALLING
)
665 RecordSet
= Db
.Exec(SqlCommand
)
666 for Record
in RecordSet
:
669 ParameterList
= GetSplitValueList(Record
[0], TAB_COMMA_SPLIT
)
670 for Parameter
in ParameterList
:
671 Parameters
.append(GetParameterName(Parameter
))
673 Parameters
= [GetProtocolParameter(Record
[0], Index
)]
674 StartLine
= Record
[1]
675 for Parameter
in Parameters
:
676 if Parameter
.startswith('g') or Parameter
.endswith('Guid') or Parameter
== 'ShellEnvProtocol' or Parameter
== 'ShellInterfaceProtocol':
677 GuidName
= GetParameterName(Parameter
)
678 Db
.Insert(-1, '', '', SourceFileID
, SourceFileFullPath
, ItemName
, ItemType
, ItemMode
, GuidName
, GuidMacro
, GuidValue
, BelongsToFunction
, 0)
682 EotGlobalData
.gOP_UN_MATCHED
.write('%s, %s, %s, %s, %s, %s\n' % (ItemType
, ItemMode
, SourceFileID
, SourceFileFullPath
, StartLine
, Parameter
))
684 ## FindProtocols() method
686 # Find defined protocols
688 # @param SqlCommand: SQL command statement
689 # @param Table: Table id
690 # @param SourceFileID: Source file id
691 # @param SourceFileFullPath: Source file full path
692 # @param ItemName: String of protocol definition
693 # @param ItemType: Type of the item, PPI or PROTOCOL
694 # @param ItemMode: Mode of item
696 #def FindProtocols(Db, SqlCommand, Table, SourceFileID, SourceFileFullPath, ItemName, ItemType, ItemMode, GuidName, GuidMacro, GuidValue):
697 # BelongsToFunction = ''
698 # RecordSet = Db.Exec(SqlCommand)
699 # for Record in RecordSet:
701 # Parameter = GetProtocolParameter(Record[0])
703 ## GetProtocolParameter() method
705 # Parse string of protocol and find parameters
707 # @param Parameter: Parameter to be parsed
708 # @param Index: The index of the parameter
710 # @return: call common GetParameter
712 def GetProtocolParameter(Parameter
, Index
= 1):
713 return GetParameter(Parameter
, Index
)
715 ## GetPpiParameter() method
717 # Parse string of ppi and find parameters
719 # @param Parameter: Parameter to be parsed
720 # @param Index: The index of the parameter
722 # @return: call common GetParameter
724 def GetPpiParameter(Parameter
, Index
= 1):
725 return GetParameter(Parameter
, Index
)
727 ## GetParameter() method
729 # Get a parameter by index
731 # @param Parameter: Parameter to be parsed
732 # @param Index: The index of the parameter
734 # @return Parameter: The found parameter
736 def GetParameter(Parameter
, Index
= 1):
737 ParameterList
= GetSplitValueList(Parameter
, TAB_COMMA_SPLIT
)
738 if len(ParameterList
) > Index
:
739 Parameter
= GetParameterName(ParameterList
[Index
])
745 ## GetParameterName() method
747 # Get a parameter name
749 # @param Parameter: Parameter to be parsed
751 # @return: The name of parameter
753 def GetParameterName(Parameter
):
754 if isinstance(Parameter
, type('')) and Parameter
.startswith('&'):
755 return Parameter
[1:].replace('{', '').replace('}', '').replace('\r', '').replace('\n', '').strip()
757 return Parameter
.strip()
759 ## FindKeyValue() method
761 # Find key value of a variable
763 # @param Db: Database to be searched
764 # @param Table: Table to be searched
765 # @param Key: The keyword
767 # @return Value: The value of the keyword
769 def FindKeyValue(Db
, Table
, Key
):
770 SqlCommand
= """select Value from %s where Name = '%s' and (Model = %s or Model = %s)""" % (Table
, Key
, MODEL_IDENTIFIER_VARIABLE
, MODEL_IDENTIFIER_ASSIGNMENT_EXPRESSION
)
771 RecordSet
= Db
.Exec(SqlCommand
)
773 for Record
in RecordSet
:
774 if Record
[0] != 'NULL':
775 Value
= FindKeyValue(Db
, Table
, GetParameterName(Record
[0]))
782 ## ParseMapFile() method
784 # Parse map files to get a dict of 'ModuleName' : {FunName : FunAddress}
786 # @param Files: A list of map files
788 # @return AllMaps: An object of all map files
790 def ParseMapFile(Files
):
795 Content
= open(File
, 'r').readlines()
797 Line
= CleanString(Line
)
802 if Line
.find('(') > -1 and Line
.find(')') > -1:
803 if CurrentModule
!= '' and CurrentMaps
!= {}:
804 AllMaps
[CurrentModule
] = CurrentMaps
805 CurrentModule
= Line
[:Line
.find('(')]
813 if List
[1] == 'F' or List
[1] == 'FS':
817 CurrentMaps
[Name
] = Address
824 # Convert a GUID to a GUID with all upper letters
826 # @param guid: The GUID to be converted
828 # @param newGuid: The GUID with all upper letters.
830 def ConvertGuid(guid
):
831 numList
= ['0', '1', '2', '3', '4', '5', '6', '7', '8', '9']
833 if guid
.startswith('g'):
836 if i
.upper() == i
and i
not in numList
:
837 newGuid
= newGuid
+ ('_' + i
)
839 newGuid
= newGuid
+ i
.upper()
840 if newGuid
.startswith('_'):
841 newGuid
= newGuid
[1:]
842 if newGuid
.endswith('_'):
843 newGuid
= newGuid
[:-1]
847 ## ConvertGuid2() method
849 # Convert a GUID to a GUID with new string instead of old string
851 # @param guid: The GUID to be converted
852 # @param old: Old string to be replaced
853 # @param new: New string to replace the old one
855 # @param newGuid: The GUID after replacement
857 def ConvertGuid2(guid
, old
, new
):
858 newGuid
= ConvertGuid(guid
)
859 newGuid
= newGuid
.replace(old
, new
)
865 # This acts like the main() function for the script, unless it is 'import'ed into another
868 if __name__
== '__main__':