1. Adjust the function of "GenerateID" of each table, use a global variable to store...
[people/mcb30/basetools.git] / Source / Python / Ecc / Database.py
1 ## @file\r
2 # This file is used to create a database used by ECC tool\r
3 #\r
4 # Copyright (c) 2007, Intel Corporation\r
5 # All rights reserved. This program and the accompanying materials\r
6 # are licensed and made available under the terms and conditions of the BSD License\r
7 # which accompanies this distribution.  The full text of the license may be found at\r
8 # http://opensource.org/licenses/bsd-license.php\r
9 #\r
10 # THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,\r
11 # WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.\r
12 #\r
13 \r
14 ##\r
15 # Import Modules\r
16 #\r
17 import sqlite3\r
18 import os, time\r
19 \r
20 import Common.EdkLogger as EdkLogger\r
21 import CommonDataClass.DataClass as DataClass\r
22 \r
23 from Table.TableDataModel import TableDataModel\r
24 from Table.TableFile import TableFile\r
25 from Table.TableFunction import TableFunction\r
26 from Table.TablePcd import TablePcd\r
27 from Table.TableIdentifier import TableIdentifier\r
28 \r
29 ##\r
30 # Static definitions\r
31 #\r
32 DATABASE_PATH = "Database/Ecc.db"\r
33 \r
34 ## Database\r
35 #\r
36 # This class defined the ECC databse\r
37 # During the phase of initialization, the database will create all tables and\r
38 # insert all records of table DataModel\r
39\r
40 # @param object:    Inherited from object class\r
41 # @param DbPath:    A string for the path of the ECC database\r
42 #\r
43 # @var Conn:        Connection of the ECC database\r
44 # @var Cur:         Cursor of the connection\r
45 # @var TblDataModel:  Local instance for TableDataModel\r
46 #\r
47 class Database(object):\r
48     def __init__(self, DbPath):\r
49         self.Conn = sqlite3.connect(DbPath, isolation_level = 'DEFERRED')\r
50         self.Cur = self.Conn.cursor()\r
51         self.TblDataModel = TableDataModel(self.Cur)\r
52         self.TblFile = TableFile(self.Cur)\r
53         self.TblFunction = TableFunction(self.Cur)\r
54         self.TblIdentifier = TableIdentifier(self.Cur)\r
55         self.TblPcd = TablePcd(self.Cur)\r
56     \r
57     ## Initialize ECC database\r
58     #\r
59     # 1. Delete all old existing tables\r
60     # 2. Create new tables\r
61     # 3. Initialize table DataModel\r
62     #\r
63     def InitDatabase(self):\r
64         EdkLogger.verbose("\nInitialize ECC database started ...")\r
65         #\r
66         # Drop all old existing tables\r
67         #\r
68         self.TblDataModel.Drop()\r
69         self.TblFile.Drop()\r
70         self.TblFunction.Drop()\r
71         self.TblPcd.Drop()\r
72         self.TblIdentifier.Drop()\r
73         \r
74         #\r
75         # Create new tables\r
76         #\r
77         self.TblDataModel.Create()\r
78         self.TblFile.Create()\r
79         self.TblFunction.Create()\r
80         self.TblPcd.Create()\r
81         self.TblIdentifier.Create()\r
82         \r
83         #\r
84         # Initialize table DataModel\r
85         #\r
86         self.TblDataModel.InitTable()\r
87         EdkLogger.verbose("Initialize ECC database ... DONE!")\r
88 \r
89     ## Query a table\r
90     #\r
91     # @param Table:  The instance of the table to be queried\r
92     #\r
93     def QueryTable(self, Table):\r
94         Table.Query()\r
95     \r
96     ## Close entire database\r
97     #\r
98     # Commit all first\r
99     # Close the connection and cursor\r
100     #\r
101     def Close(self):\r
102         #\r
103         # Commit to file\r
104         #        \r
105         self.Conn.commit()\r
106         \r
107         #\r
108         # Close connection and cursor\r
109         #\r
110         self.Cur.close()\r
111         self.Conn.close()\r
112     \r
113     ## Insert one file information\r
114     #\r
115     # Insert one file's information to the database\r
116     # 1. Create a record in TableFile\r
117     # 2. Create functions one by one\r
118     #    2.1 Create variables of function one by one\r
119     #    2.2 Create pcds of function one by one\r
120     # 3. Create variables one by one\r
121     # 4. Create pcds one by one\r
122     #\r
123     def InsertOneFile(self, File):\r
124         #\r
125         # Insert a record for file\r
126         #\r
127         print self.TblFile.GetCount()\r
128         FileID = self.TblFile.Insert(File.Name, File.ExtName, File.Path, File.FullPath, Model = File.Model, TimeStamp = File.TimeStamp)\r
129 \r
130         print FileID\r
131         #\r
132         # Insert function of file\r
133         #\r
134         for Function in File.FunctionList:\r
135             FunctionID = self.TblFunction.Insert(Function.Header, Function.Modifier, Function.Name, Function.ReturnStatement, \\r
136                                     Function.StartLine, Function.StartColumn, Function.EndLine, Function.EndColumn, \\r
137                                     Function.BodyStartLine, Function.BodyStartColumn, FileID)\r
138             #\r
139             # Insert Identifier of function\r
140             #\r
141             for Identifier in Function.IdentifierList:\r
142                 IdentifierID = self.TblIdentifier.Insert(Identifier.Modifier, Identifier.Type, Identifier.Name, Identifier.Value, Identifier.Model, \\r
143                                         FileID, FunctionID, Identifier.StartLine, Identifier.StartColumn, Identifier.EndLine, Identifier.EndColumn)\r
144             #\r
145             # Insert Pcd of function\r
146             #\r
147             for Pcd in Function.PcdList:\r
148                 PcdID = self.TblPcd.Insert(Pcd.CName, Pcd.TokenSpaceGuidCName, Pcd.Token, Pcd.DatumType, Pcd.Model, \\r
149                                    FileID, FunctionID, Pcd.StartLine, Pcd.StartColumn, Pcd.EndLine, Pcd.EndColumn)\r
150         #\r
151         # Insert Identifier of file\r
152         #\r
153         for Identifier in File.IdentifierList:\r
154             IdentifierID = self.TblIdentifier.Insert(Identifier.Modifier, Identifier.Type, Identifier.Name, Identifier.Value, Identifier.Model, \\r
155                                     FileID, -1, Identifier.StartLine, Identifier.StartColumn, Identifier.EndLine, Identifier.EndColumn)\r
156         #\r
157         # Insert Pcd of file\r
158         #\r
159         for Pcd in File.PcdList:\r
160             PcdID = self.TblPcd.Insert(Pcd.CName, Pcd.TokenSpaceGuidCName, Pcd.Token, Pcd.DatumType, Pcd.Model, \\r
161                                FileID, -1, Pcd.StartLine, Pcd.StartColumn, Pcd.EndLine, Pcd.EndColumn)\r
162                 \r
163         EdkLogger.verbose("Insert information of file %s ... DONE!" % File.FullPath)\r
164 \r
165     ## UpdateIdentifierBelongsToFunction\r
166     #\r
167     # Update the field "BelongsToFunction" for each Indentifier\r
168     #\r
169     #\r
170     def UpdateIdentifierBelongsToFunction(self):\r
171         EdkLogger.verbose("Update 'BelongsToFunction' for Identifiers started ...")\r
172         \r
173         SqlCommand = """select ID, BelongsToFile, StartLine, EndLine, Model from Identifier"""\r
174         EdkLogger.debug(4, "SqlCommand: %s" %SqlCommand)\r
175         self.Cur.execute(SqlCommand)\r
176         Records = self.Cur.fetchall()\r
177         for Record in Records:\r
178             IdentifierID = Record[0]\r
179             BelongsToFile = Record[1]\r
180             StartLine = Record[2]\r
181             EndLine = Record[3]\r
182             Model = Record[4]\r
183 \r
184             #\r
185             # Check whether an identifier belongs to a function\r
186             #\r
187             EdkLogger.debug(4, "For common identifiers ... ")\r
188             SqlCommand = """select ID from Function \r
189                         where StartLine < %s and EndLine > %s\r
190                         and BelongsToFile = %s""" % (StartLine, EndLine, BelongsToFile)\r
191             EdkLogger.debug(4, "SqlCommand: %s" %SqlCommand)\r
192             self.Cur.execute(SqlCommand)\r
193             IDs = self.Cur.fetchall()\r
194             for ID in IDs:\r
195                 SqlCommand = """Update Identifier set BelongsToFunction = %s where ID = %s""" % (ID[0], IdentifierID)\r
196                 EdkLogger.debug(4, "SqlCommand: %s" %SqlCommand)\r
197                 self.Cur.execute(SqlCommand)\r
198             \r
199             #\r
200             # Check whether the identifier is a function header\r
201             #\r
202             EdkLogger.debug(4, "For function headers ... ") \r
203             if Model == DataClass.MODEL_IDENTIFIER_COMMENT:\r
204                 SqlCommand = """select ID from Function \r
205                         where StartLine = %s + 1\r
206                         and BelongsToFile = %s""" % (EndLine, BelongsToFile)\r
207                 EdkLogger.debug(4, "SqlCommand: %s" %SqlCommand)\r
208                 self.Cur.execute(SqlCommand)\r
209                 IDs = self.Cur.fetchall()\r
210                 for ID in IDs:\r
211                     SqlCommand = """Update Identifier set BelongsToFunction = %s, Model = %s where ID = %s""" % (ID[0], DataClass.MODEL_IDENTIFIER_FUNCTION_HEADER, IdentifierID)\r
212                     EdkLogger.debug(4, "SqlCommand: %s" %SqlCommand)\r
213                     self.Cur.execute(SqlCommand)\r
214         \r
215         EdkLogger.verbose("Update 'BelongsToFunction' for Identifiers ... DONE")\r
216 \r
217 ##\r
218 #\r
219 # This acts like the main() function for the script, unless it is 'import'ed into another\r
220 # script.\r
221 #\r
222 if __name__ == '__main__':\r
223     EdkLogger.Initialize()\r
224     #EdkLogger.SetLevel(EdkLogger.VERBOSE)\r
225     EdkLogger.SetLevel(EdkLogger.DEBUG_0)\r
226     EdkLogger.verbose("Start at " + time.strftime('%H:%M:%S', time.localtime()))\r
227     \r
228     Db = Database(DATABASE_PATH)\r
229     Db.InitDatabase()\r
230     Db.QueryTable(Db.TblDataModel)\r
231     \r
232     identifier1 = DataClass.IdentifierClass(-1, '', '', "i''1", 'aaa', DataClass.MODEL_IDENTIFIER_COMMENT, 1, -1, 32,  43,  54,  43)\r
233     identifier2 = DataClass.IdentifierClass(-1, '', '', 'i1', 'aaa', DataClass.MODEL_IDENTIFIER_COMMENT, 1, -1, 15,  43,  20,  43)\r
234     identifier3 = DataClass.IdentifierClass(-1, '', '', 'i1', 'aaa', DataClass.MODEL_IDENTIFIER_COMMENT, 1, -1, 55,  43,  58,  43)\r
235     identifier4 = DataClass.IdentifierClass(-1, '', '', "i1'", 'aaa', DataClass.MODEL_IDENTIFIER_COMMENT, 1, -1, 77,  43,  88,  43)\r
236     fun1 = DataClass.FunctionClass(-1, '', '', 'fun1', '', 21, 2, 60,  45, 1, 23, 0, [], [])\r
237     file = DataClass.FileClass(-1, 'F1', 'c', 'C:\\', 'C:\\F1.exe', DataClass.MODEL_FILE_C, '2007-12-28', [fun1], [identifier1, identifier2, identifier3, identifier4], [])\r
238     Db.InsertOneFile(file)\r
239     Db.UpdateIdentifierBelongsToFunction()\r
240         \r
241     Db.QueryTable(Db.TblFile)\r
242     Db.QueryTable(Db.TblFunction)\r
243     Db.QueryTable(Db.TblPcd)\r
244     Db.QueryTable(Db.TblIdentifier)\r
245     \r
246     Db.Close()\r
247     EdkLogger.verbose("End at " + time.strftime('%H:%M:%S', time.localtime()))\r
248