2 # This file is used to create a database used by ECC tool
4 # Copyright (c) 2007 - 2014, Intel Corporation. All rights reserved.<BR>
5 # This program and the accompanying materials
6 # are licensed and made available under the terms and conditions of the BSD License
7 # which accompanies this distribution. The full text of the license may be found at
8 # http://opensource.org/licenses/bsd-license.php
10 # THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
11 # WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
18 import Common
.LongFilePathOs
as os
, time
20 import Common
.EdkLogger
as EdkLogger
21 import CommonDataClass
.DataClass
as DataClass
23 from Table
.TableDataModel
import TableDataModel
24 from Table
.TableFile
import TableFile
25 from Table
.TableFunction
import TableFunction
26 from Table
.TablePcd
import TablePcd
27 from Table
.TableIdentifier
import TableIdentifier
28 from Table
.TableReport
import TableReport
29 from MetaFileWorkspace
.MetaFileTable
import ModuleTable
30 from MetaFileWorkspace
.MetaFileTable
import PackageTable
31 from MetaFileWorkspace
.MetaFileTable
import PlatformTable
32 from Table
.TableFdf
import TableFdf
37 DATABASE_PATH
= "Ecc.db"
41 # This class defined the ECC databse
42 # During the phase of initialization, the database will create all tables and
43 # insert all records of table DataModel
45 # @param object: Inherited from object class
46 # @param DbPath: A string for the path of the ECC database
48 # @var Conn: Connection of the ECC database
49 # @var Cur: Cursor of the connection
50 # @var TblDataModel: Local instance for TableDataModel
52 class Database(object):
53 def __init__(self
, DbPath
):
57 self
.TblDataModel
= None
59 self
.TblFunction
= None
60 self
.TblIdentifier
= None
68 ## Initialize ECC database
70 # 1. Delete all old existing tables
71 # 2. Create new tables
72 # 3. Initialize table DataModel
74 def InitDatabase(self
, NewDatabase
= True):
75 EdkLogger
.verbose("\nInitialize ECC database started ...")
77 # Drop all old existing tables
80 if os
.path
.exists(self
.DbPath
):
81 os
.remove(self
.DbPath
)
82 self
.Conn
= sqlite3
.connect(self
.DbPath
, isolation_level
= 'DEFERRED')
83 self
.Conn
.execute("PRAGMA page_size=4096")
84 self
.Conn
.execute("PRAGMA synchronous=OFF")
85 # to avoid non-ascii charater conversion error
86 self
.Conn
.text_factory
= str
87 self
.Cur
= self
.Conn
.cursor()
89 self
.TblDataModel
= TableDataModel(self
.Cur
)
90 self
.TblFile
= TableFile(self
.Cur
)
91 self
.TblFunction
= TableFunction(self
.Cur
)
92 self
.TblIdentifier
= TableIdentifier(self
.Cur
)
93 self
.TblPcd
= TablePcd(self
.Cur
)
94 self
.TblReport
= TableReport(self
.Cur
)
95 self
.TblInf
= ModuleTable(self
.Cur
)
96 self
.TblDec
= PackageTable(self
.Cur
)
97 self
.TblDsc
= PlatformTable(self
.Cur
)
98 self
.TblFdf
= TableFdf(self
.Cur
)
104 self
.TblDataModel
.Create()
105 self
.TblFile
.Create()
106 self
.TblFunction
.Create()
108 self
.TblReport
.Create()
115 # Init each table's ID
117 self
.TblDataModel
.InitID()
118 self
.TblFile
.InitID()
119 self
.TblFunction
.InitID()
121 self
.TblReport
.InitID()
128 # Initialize table DataModel
131 self
.TblDataModel
.InitTable()
133 EdkLogger
.verbose("Initialize ECC database ... DONE!")
137 # @param Table: The instance of the table to be queried
139 def QueryTable(self
, Table
):
142 ## Close entire database
145 # Close the connection and cursor
154 # Close connection and cursor
159 ## Insert one file information
161 # Insert one file's information to the database
162 # 1. Create a record in TableFile
163 # 2. Create functions one by one
164 # 2.1 Create variables of function one by one
165 # 2.2 Create pcds of function one by one
166 # 3. Create variables one by one
167 # 4. Create pcds one by one
169 def InsertOneFile(self
, File
):
171 # Insert a record for file
173 FileID
= self
.TblFile
.Insert(File
.Name
, File
.ExtName
, File
.Path
, File
.FullPath
, Model
= File
.Model
, TimeStamp
= File
.TimeStamp
)
175 if File
.Model
== DataClass
.MODEL_FILE_C
or File
.Model
== DataClass
.MODEL_FILE_H
:
176 IdTable
= TableIdentifier(self
.Cur
)
177 IdTable
.Table
= "Identifier%s" % FileID
180 # Insert function of file
182 for Function
in File
.FunctionList
:
183 FunctionID
= self
.TblFunction
.Insert(Function
.Header
, Function
.Modifier
, Function
.Name
, Function
.ReturnStatement
, \
184 Function
.StartLine
, Function
.StartColumn
, Function
.EndLine
, Function
.EndColumn
, \
185 Function
.BodyStartLine
, Function
.BodyStartColumn
, FileID
, \
186 Function
.FunNameStartLine
, Function
.FunNameStartColumn
)
188 # Insert Identifier of function
190 for Identifier
in Function
.IdentifierList
:
191 IdentifierID
= IdTable
.Insert(Identifier
.Modifier
, Identifier
.Type
, Identifier
.Name
, Identifier
.Value
, Identifier
.Model
, \
192 FileID
, FunctionID
, Identifier
.StartLine
, Identifier
.StartColumn
, Identifier
.EndLine
, Identifier
.EndColumn
)
194 # Insert Pcd of function
196 for Pcd
in Function
.PcdList
:
197 PcdID
= self
.TblPcd
.Insert(Pcd
.CName
, Pcd
.TokenSpaceGuidCName
, Pcd
.Token
, Pcd
.DatumType
, Pcd
.Model
, \
198 FileID
, FunctionID
, Pcd
.StartLine
, Pcd
.StartColumn
, Pcd
.EndLine
, Pcd
.EndColumn
)
200 # Insert Identifier of file
202 for Identifier
in File
.IdentifierList
:
203 IdentifierID
= IdTable
.Insert(Identifier
.Modifier
, Identifier
.Type
, Identifier
.Name
, Identifier
.Value
, Identifier
.Model
, \
204 FileID
, -1, Identifier
.StartLine
, Identifier
.StartColumn
, Identifier
.EndLine
, Identifier
.EndColumn
)
208 for Pcd
in File
.PcdList
:
209 PcdID
= self
.TblPcd
.Insert(Pcd
.CName
, Pcd
.TokenSpaceGuidCName
, Pcd
.Token
, Pcd
.DatumType
, Pcd
.Model
, \
210 FileID
, -1, Pcd
.StartLine
, Pcd
.StartColumn
, Pcd
.EndLine
, Pcd
.EndColumn
)
212 EdkLogger
.verbose("Insert information from file %s ... DONE!" % File
.FullPath
)
214 ## UpdateIdentifierBelongsToFunction
216 # Update the field "BelongsToFunction" for each Indentifier
219 def UpdateIdentifierBelongsToFunction_disabled(self
):
220 EdkLogger
.verbose("Update 'BelongsToFunction' for Identifiers started ...")
222 SqlCommand
= """select ID, BelongsToFile, StartLine, EndLine, Model from Identifier"""
223 EdkLogger
.debug(4, "SqlCommand: %s" %SqlCommand
)
224 self
.Cur
.execute(SqlCommand
)
225 Records
= self
.Cur
.fetchall()
226 for Record
in Records
:
227 IdentifierID
= Record
[0]
228 BelongsToFile
= Record
[1]
229 StartLine
= Record
[2]
234 # Check whether an identifier belongs to a function
236 EdkLogger
.debug(4, "For common identifiers ... ")
237 SqlCommand
= """select ID from Function
238 where StartLine < %s and EndLine > %s
239 and BelongsToFile = %s""" % (StartLine
, EndLine
, BelongsToFile
)
240 EdkLogger
.debug(4, "SqlCommand: %s" %SqlCommand
)
241 self
.Cur
.execute(SqlCommand
)
242 IDs
= self
.Cur
.fetchall()
244 SqlCommand
= """Update Identifier set BelongsToFunction = %s where ID = %s""" % (ID
[0], IdentifierID
)
245 EdkLogger
.debug(4, "SqlCommand: %s" %SqlCommand
)
246 self
.Cur
.execute(SqlCommand
)
249 # Check whether the identifier is a function header
251 EdkLogger
.debug(4, "For function headers ... ")
252 if Model
== DataClass
.MODEL_IDENTIFIER_COMMENT
:
253 SqlCommand
= """select ID from Function
254 where StartLine = %s + 1
255 and BelongsToFile = %s""" % (EndLine
, BelongsToFile
)
256 EdkLogger
.debug(4, "SqlCommand: %s" %SqlCommand
)
257 self
.Cur
.execute(SqlCommand
)
258 IDs
= self
.Cur
.fetchall()
260 SqlCommand
= """Update Identifier set BelongsToFunction = %s, Model = %s where ID = %s""" % (ID
[0], DataClass
.MODEL_IDENTIFIER_FUNCTION_HEADER
, IdentifierID
)
261 EdkLogger
.debug(4, "SqlCommand: %s" %SqlCommand
)
262 self
.Cur
.execute(SqlCommand
)
264 EdkLogger
.verbose("Update 'BelongsToFunction' for Identifiers ... DONE")
267 ## UpdateIdentifierBelongsToFunction
269 # Update the field "BelongsToFunction" for each Indentifier
272 def UpdateIdentifierBelongsToFunction(self
):
273 EdkLogger
.verbose("Update 'BelongsToFunction' for Identifiers started ...")
275 SqlCommand
= """select ID, BelongsToFile, StartLine, EndLine from Function"""
276 Records
= self
.TblFunction
.Exec(SqlCommand
)
279 for Record
in Records
:
280 FunctionID
= Record
[0]
281 BelongsToFile
= Record
[1]
282 StartLine
= Record
[2]
284 #Data1.append(("'file%s'" % BelongsToFile, FunctionID, BelongsToFile, StartLine, EndLine))
285 #Data2.append(("'file%s'" % BelongsToFile, FunctionID, DataClass.MODEL_IDENTIFIER_FUNCTION_HEADER, BelongsToFile, DataClass.MODEL_IDENTIFIER_COMMENT, StartLine - 1))
287 SqlCommand
= """Update Identifier%s set BelongsToFunction = %s where BelongsToFile = %s and StartLine > %s and EndLine < %s""" % \
288 (BelongsToFile
, FunctionID
, BelongsToFile
, StartLine
, EndLine
)
289 self
.TblIdentifier
.Exec(SqlCommand
)
291 SqlCommand
= """Update Identifier%s set BelongsToFunction = %s, Model = %s where BelongsToFile = %s and Model = %s and EndLine = %s""" % \
292 (BelongsToFile
, FunctionID
, DataClass
.MODEL_IDENTIFIER_FUNCTION_HEADER
, BelongsToFile
, DataClass
.MODEL_IDENTIFIER_COMMENT
, StartLine
- 1)
293 self
.TblIdentifier
.Exec(SqlCommand
)
295 # # Check whether an identifier belongs to a function
298 # SqlCommand = """Update ? set BelongsToFunction = ? where BelongsToFile = ? and StartLine > ? and EndLine < ?"""
300 # EdkLogger.debug(4, "SqlCommand: %s" %SqlCommand)
301 # self.Cur.executemany(SqlCommand, Data1)
304 # # Check whether the identifier is a function header
306 # EdkLogger.debug(4, "For function headers ... ")
307 # SqlCommand = """Update ? set BelongsToFunction = ?, Model = ? where BelongsToFile = ? and Model = ? and EndLine = ?"""
308 # EdkLogger.debug(4, "SqlCommand: %s" %SqlCommand)
309 # self.Cur.executemany(SqlCommand, Data2)
311 # EdkLogger.verbose("Update 'BelongsToFunction' for Identifiers ... DONE")
316 # This acts like the main() function for the script, unless it is 'import'ed into another
319 if __name__
== '__main__':
320 EdkLogger
.Initialize()
321 #EdkLogger.SetLevel(EdkLogger.VERBOSE)
322 EdkLogger
.SetLevel(EdkLogger
.DEBUG_0
)
323 EdkLogger
.verbose("Start at " + time
.strftime('%H:%M:%S', time
.localtime()))
325 Db
= Database(DATABASE_PATH
)
327 Db
.QueryTable(Db
.TblDataModel
)
329 identifier1
= DataClass
.IdentifierClass(-1, '', '', "i''1", 'aaa', DataClass
.MODEL_IDENTIFIER_COMMENT
, 1, -1, 32, 43, 54, 43)
330 identifier2
= DataClass
.IdentifierClass(-1, '', '', 'i1', 'aaa', DataClass
.MODEL_IDENTIFIER_COMMENT
, 1, -1, 15, 43, 20, 43)
331 identifier3
= DataClass
.IdentifierClass(-1, '', '', 'i1', 'aaa', DataClass
.MODEL_IDENTIFIER_COMMENT
, 1, -1, 55, 43, 58, 43)
332 identifier4
= DataClass
.IdentifierClass(-1, '', '', "i1'", 'aaa', DataClass
.MODEL_IDENTIFIER_COMMENT
, 1, -1, 77, 43, 88, 43)
333 fun1
= DataClass
.FunctionClass(-1, '', '', 'fun1', '', 21, 2, 60, 45, 1, 23, 0, [], [])
334 file = DataClass
.FileClass(-1, 'F1', 'c', 'C:\\', 'C:\\F1.exe', DataClass
.MODEL_FILE_C
, '2007-12-28', [fun1
], [identifier1
, identifier2
, identifier3
, identifier4
], [])
335 Db
.InsertOneFile(file)
336 Db
.UpdateIdentifierBelongsToFunction()
338 Db
.QueryTable(Db
.TblFile
)
339 Db
.QueryTable(Db
.TblFunction
)
340 Db
.QueryTable(Db
.TblPcd
)
341 Db
.QueryTable(Db
.TblIdentifier
)
344 EdkLogger
.verbose("End at " + time
.strftime('%H:%M:%S', time
.localtime()))