00001 //
00002 // -------------------------------------------------------------
00003 // Copyright 2004-2008 Synopsys, Inc.
00004 // All Rights Reserved Worldwide
00005 //
00006 // Licensed under the Apache License, Version 2.0 (the
00007 // "License"); you may not use this file except in
00008 // compliance with the License. You may obtain a copy of
00009 // the License at
00010 //
00011 // http://www.apache.org/licenses/LICENSE-2.0
00012 //
00013 // Unless required by applicable law or agreed to in
00014 // writing, software distributed under the License is
00015 // distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR
00016 // CONDITIONS OF ANY KIND, either express or implied. See
00017 // the License for the specific language governing
00018 // permissions and limitations under the License.
00019 // -------------------------------------------------------------
00020 //
00021
00022
00023 `ifndef VMM_SQL_DB__SV
00024 `define VMM_SQL_DB__SV
00025
00026 typedef class vmm_sql_db;
00027
00028 class vmm_sql_table;
00029 /*local*/ typedef enum int {PERF_TABLE=0,
00030 SYS_TABLE=1,
00031 USR_TABLE_DEFAULT=255} datakind_e;
00032 protected vmm_sql_db db;
00033 protected string schema;
00034 protected string schema_data;
00035 string name;
00036 byte datakind;
00037
00038
00039 /*local*/ extern function new(string name,
00040 string schema_data,
00041 vmm_sql_db db,
00042 byte datakind=255);
00043
00044 extern function string get_tblname();
00045 extern function vmm_sql_db get_db();
00046 extern function int insert(string data);
00047
00048 /*local*/ extern function string Xget_schemaX();
00049 /*local*/ extern function string Xget_schema_dataX();
00050 endclass: vmm_sql_table
00051
00052 virtual class vmm_sql_db;
00053
00054 protected vmm_sql_table tables[$];
00055
00056 // contents of vmm_runs table - consistent across all dbs
00057 local static string vmm_runs_table_name;
00058 local static string vmm_runs_utctime;
00059 local static string vmm_runs_hostname;
00060 local static int unsigned vmm_runs_seed;
00061 local static shortint vmm_runs_t_zone;
00062 local static int vmm_runs_t_sec;
00063
00064 // table name expansion variables
00065 local static string vmm_runs_day;
00066 local static string vmm_runs_hour;
00067 local static string vmm_runs_min;
00068 local static string vmm_runs_month;
00069 local static string vmm_runs_progname;
00070 local static string vmm_runs_sec;
00071 local static string vmm_runs_systime;
00072 local static string vmm_runs_year;
00073
00074 //singleton control for initialization of table
00075 local static bit vmm_runs_init = 0;
00076
00077 // table which contains table lists..
00078 protected vmm_sql_table tables_table;
00079
00080 vmm_log log;
00081
00082 extern function new();
00083 extern function string get_dbname();
00084 extern function string get_info(string format);
00085 extern function vmm_sql_table get_table(string tablename);
00086 extern function int get_table_names(output string tablenames[],
00087 input string regexp = ".");
00088 extern function vmm_sql_table create_table(string tablename,
00089 string scheme,
00090 byte datakind=255);
00091 extern virtual function int status();
00092 extern virtual function int statement(string sql_stmt);
00093 extern virtual function void commit();
00094 extern virtual function void close();
00095
00096 // Return an ID that is unique in the DB
00097 extern local virtual function int get_unique_id();
00098
00099 /*local*/ extern function vmm_sql_table Xcreate_table_baseX(string tablename,
00100 string scheme,
00101 byte datakind=255,
00102 bit add_to_tables=1 );
00103 /*local*/ extern function void Xcreate_system_tablesX();
00104 /*local*/ extern function string Xexpand_name_optsX(string instr,
00105 string opt);
00106 /*local*/ extern function string Xexpand_nameX(string regexp);
00107
00108 endclass: vmm_sql_db
00109
00110 //------------------------------------------------------------------
00111 //
00112 // Implementation
00113 //
00114
00115
00116 function vmm_sql_db::new();
00117 int t_sec, t_usec;
00118 shortint t_zone;
00119
00120 if (!vmm_runs_init) begin
00121 this.vmm_runs_init = 1;
00122 this.vmm_runs_hostname = vmm_sql_get_hostname_dpi();
00123 if (!($value$plusargs("ntb_random_seed=%d", this.vmm_runs_seed))) begin
00124 this.vmm_runs_seed = 1;
00125 end
00126 this.vmm_runs_utctime = vmm_sql_get_utc_dpi(this.vmm_runs_t_sec, t_usec, this.vmm_runs_t_zone);
00127 this.vmm_runs_day = vmm_sql_get_day_dpi();
00128 this.vmm_runs_hour = vmm_sql_get_hour_dpi();
00129 this.vmm_runs_min = vmm_sql_get_min_dpi();
00130 this.vmm_runs_month = vmm_sql_get_month_dpi();
00131 this.vmm_runs_progname = "NYI"; //TODO
00132 this.vmm_runs_sec = vmm_sql_get_sec_dpi();
00133 this.vmm_runs_systime = vmm_sql_get_systime_dpi();
00134 this.vmm_runs_year = vmm_sql_get_year_dpi();
00135 end
00136 endfunction: new
00137
00138
00139 function string vmm_sql_db::get_dbname();
00140 return (this.log.get_instance());
00141 endfunction: get_dbname
00142
00143 function string vmm_sql_db::get_info(string format);
00144 return this.Xexpand_nameX(format);
00145 endfunction: get_info
00146
00147
00148 function vmm_sql_table vmm_sql_db::get_table(string tablename);
00149 vmm_sql_table tbl[$];
00150 tbl = this.tables.find( x ) with ( x.name == tablename );
00151 if (tbl.size()) begin
00152 //Only one table with that name can exist (maximum)
00153 return ( tbl[0] );
00154 end else begin
00155 return (null);
00156 end
00157 endfunction: get_table
00158
00159 function string vmm_sql_db::Xexpand_name_optsX(string instr,
00160 string opt);
00161 string pre, post, outstr;
00162 outstr = instr;
00163 //incase someone uses the same option multiple times.
00164 while (`vmm_str_match(outstr, opt)) begin
00165 pre = `vmm_str_prematch(outstr);
00166 post = `vmm_str_postmatch(outstr);
00167 case(opt)
00168 "%D": begin
00169 $swrite(outstr, "%s%s%s", pre, this.vmm_runs_day, post);
00170 end
00171 "%h": begin
00172 $swrite(outstr, "%s%s%s", pre, this.vmm_runs_hostname, post);
00173 end
00174 "%H": begin
00175 $swrite(outstr, "%s%s%s", pre, this.vmm_runs_hour, post);
00176 end
00177 "%m": begin
00178 $swrite(outstr, "%s%s%s", pre, this.vmm_runs_min, post);
00179 end
00180 "%M": begin
00181 $swrite(outstr, "%s%s%s", pre, this.vmm_runs_month, post);
00182 end
00183 "%p": begin
00184 $swrite(outstr, "%s%s%s", pre, this.vmm_runs_progname, post);
00185 end
00186 "%s": begin
00187 $swrite(outstr, "%s%0d%s", pre, this.vmm_runs_seed, post);
00188 end
00189 "%S": begin
00190 $swrite(outstr, "%s%s%s", pre, this.vmm_runs_sec, post);
00191 end
00192 "%t": begin
00193 $swrite(outstr, "%s%s%s", pre, this.vmm_runs_systime, post);
00194 end
00195 "%Y": begin
00196 $swrite(outstr, "%s%s%s", pre, this.vmm_runs_year, post);
00197 end
00198 "%%": begin
00199 $swrite(outstr, "%s%%s", pre, post);
00200 end
00201 "%$": begin
00202 $swrite(outstr, "%s$%s", pre, post);
00203 end
00204 endcase
00205 end
00206
00207 return (outstr);
00208 endfunction: Xexpand_name_optsX
00209
00210 function string vmm_sql_db::Xexpand_nameX(string regexp);
00211 string dbname;
00212 string opts[$];
00213
00214 opts.push_back("%D");
00215 opts.push_back("%h");
00216 opts.push_back("%H");
00217 opts.push_back("%m");
00218 opts.push_back("%M");
00219 opts.push_back("%p");
00220 opts.push_back("%s");
00221 opts.push_back("%S");
00222 opts.push_back("%t");
00223 opts.push_back("%Y");
00224 opts.push_back("%%");
00225 opts.push_back("%$");
00226
00227 dbname = regexp;
00228 //fix up ${var[=val]}
00229 while (`vmm_str_match(dbname,"[$]{([a-zA-Z0-9.+_]*)(=[^}]+)?}")) begin
00230 string envar, enval, pre, post, default_enval;
00231 pre = `vmm_str_prematch(dbname);
00232 post = `vmm_str_postmatch(dbname);
00233 envar = `vmm_str_backref(dbname, 0);
00234 default_enval = `vmm_str_backref(dbname, 1);
00235 //remove the leading '=' in the default value
00236 if (default_enval == "") begin
00237 default_enval = default_enval.substr(1, default_enval.len() - 1);
00238 end
00239
00240 if (envar[0] == "+") begin
00241 if (!($value$plusargs({envar.substr(1,envar.len()-1),"=%s"}, enval))) begin
00242 enval = default_enval;
00243 end
00244 $swrite(dbname, "%0s%0s%0s", pre, enval, post );
00245 end else begin
00246 enval = vmm_sql_get_envar_dpi(envar);
00247 if (enval == "") begin
00248 enval = default_enval;
00249 end
00250 $swrite(dbname, "%0s%0s%0s", pre, enval, post );
00251 end
00252 end
00253
00254 //expand the other options..
00255 foreach (opts[i]) begin
00256 dbname = Xexpand_name_optsX(dbname, opts[i]);
00257 end
00258
00259 return(dbname);
00260
00261 endfunction: Xexpand_nameX
00262
00263
00264 function int vmm_sql_db::get_table_names(output string tablenames[],
00265 input string regexp);
00266 string tablename;
00267 string matched_tables[$];
00268
00269 //get the list of tables which match this name
00270 foreach (this.tables[i]) begin
00271 string tblname = this.tables[i].get_tblname();
00272 //return if not a system table and name matches...
00273 if (`vmm_str_match(tblname, regexp)) begin
00274 matched_tables.push_back(tblname);
00275 end
00276 end
00277
00278 //populate the tablenames output with the above tablenames
00279 tablenames = matched_tables;
00280
00281 return (tablenames.size());
00282 endfunction: get_table_names
00283
00284 function vmm_sql_table vmm_sql_db::Xcreate_table_baseX(string tablename,
00285 string scheme,
00286 byte datakind,
00287 bit add_to_tables);
00288 vmm_sql_table table = new(this.Xexpand_nameX(tablename), scheme,
00289 this, datakind);
00290 if (this.statement(table.Xget_schemaX())) begin
00291 table = null;
00292 end
00293 else begin
00294 this.tables.push_back(table);
00295 end
00296
00297 // Create an entry in tables_table with the correct table type
00298 // only if it is a user table
00299 if (add_to_tables && this.tables_table != null) begin
00300 this.tables_table.insert($psprintf("\"%0s\", %0d", tablename,
00301 $unsigned(datakind)));
00302 end
00303 return (table);
00304 endfunction: Xcreate_table_baseX
00305
00306 function vmm_sql_table vmm_sql_db::create_table(string tablename,
00307 string scheme,
00308 byte datakind);
00309 return(Xcreate_table_baseX(tablename, scheme, datakind));
00310 endfunction: create_table
00311
00312
00313 function void vmm_sql_db::Xcreate_system_tablesX();
00314 vmm_sql_table vmm_runs_table;
00315 string vmm_tables;
00316
00317 vmm_runs_table = this.Xcreate_table_baseX(
00318 "vmm_runs",
00319 "hostname VARCHAR(255), utime INTEGER, systime VARCHAR(30), tzone SMALLINT, seed INTEGER UNSIGNED, tables VARCHAR(255)",
00320 vmm_sql_table::SYS_TABLE,
00321 0
00322 );
00323
00324 $sformat(vmm_tables, "vmm_run_%s_%0d_%0d_%0d", this.vmm_runs_hostname,
00325 this.vmm_runs_t_sec, this.vmm_runs_seed, this.get_unique_id());
00326
00327 void'(vmm_runs_table.insert(
00328 $psprintf("\"%0s\", %0d, \"%0s\", %d, %0d, \"%0s\"",
00329 this.vmm_runs_hostname,
00330 this.vmm_runs_t_sec,
00331 this.vmm_runs_utctime,
00332 this.vmm_runs_t_zone,
00333 this.vmm_runs_seed,
00334 vmm_tables)));
00335
00336 this.tables_table = this.Xcreate_table_baseX(
00337 vmm_tables,
00338 "tblname VARCHAR(255), datakind TINYINT",
00339 vmm_sql_table::SYS_TABLE,
00340 0
00341 );
00342
00343 endfunction: Xcreate_system_tablesX
00344
00345 function vmm_sql_table::new(string name,
00346 string schema_data,
00347 vmm_sql_db db,
00348 byte datakind);
00349 this.db = db;
00350 this.name = name;
00351 this.datakind = datakind;
00352 this.schema_data = schema_data;
00353 //create the table creation string from the schema_data
00354 $swrite(this.schema, "CREATE TABLE IF NOT EXISTS %0s (%0s);",
00355 this.name,
00356 this.schema_data);
00357
00358 endfunction: new
00359
00360 function string vmm_sql_table::get_tblname();
00361 return (this.name);
00362 endfunction: get_tblname
00363
00364 function vmm_sql_db vmm_sql_table::get_db();
00365 return (this.db);
00366 endfunction: get_db
00367
00368 function int vmm_sql_table::insert(string data);
00369 string sql_stmt;
00370 $swrite(sql_stmt,
00371 "INSERT INTO %0s VALUES (%0s);",
00372 this.name,
00373 data);
00374 return (this.db.statement(sql_stmt));
00375 endfunction: insert
00376
00377 function string vmm_sql_table::Xget_schemaX();
00378 return(this.schema);
00379 endfunction: Xget_schemaX
00380
00381 function string vmm_sql_table::Xget_schema_dataX();
00382 return(this.schema_data);
00383 endfunction: Xget_schema_dataX
00384
00385 function void vmm_sql_db::commit();
00386 endfunction: commit
00387
00388 `endif