00001 // $Id: ovm__component_8sv-source.html,v 1.1 2008/10/07 21:54:55 alex.marin Exp $ 00002 //------------------------------------------------------------------------------ 00003 // Copyright 2007-2008 Mentor Graphics Corporation 00004 // Copyright 2007-2008 Cadence Design Systems, Inc. 00005 // All Rights Reserved Worldwide 00006 // 00007 // Licensed under the Apache License, Version 2.0 (the 00008 // "License"); you may not use this file except in 00009 // compliance with the License. You may obtain a copy of 00010 // the License at 00011 // 00012 // http://www.apache.org/licenses/LICENSE-2.0 00013 // 00014 // Unless required by applicable law or agreed to in 00015 // writing, software distributed under the License is 00016 // distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR 00017 // CONDITIONS OF ANY KIND, either express or implied. See 00018 // the License for the specific language governing 00019 // permissions and limitations under the License. 00020 //------------------------------------------------------------------------------ 00021 00022 `include "base/ovm_component.svh" 00023 00024 //------------------------------------------------------------------------------ 00025 // 00026 // Class: ovm_*_phase (predefined phases) 00027 // 00028 //------------------------------------------------------------------------------ 00029 00030 `ovm_phase_func_decl(build,1) 00031 `ovm_phase_func_decl(connect,0) 00032 `ovm_phase_func_decl(end_of_elaboration,0) 00033 `ovm_phase_func_decl(start_of_simulation,0) 00034 `ovm_phase_func_decl(extract,0) 00035 `ovm_phase_func_decl(check,0) 00036 `ovm_phase_func_decl(report,0) 00037 00038 build_phase #(ovm_component) build_ph = new(); 00039 connect_phase #(ovm_component) connect_ph = new(); 00040 end_of_elaboration_phase #(ovm_component) end_of_elaboration_ph = new(); 00041 start_of_simulation_phase #(ovm_component) start_of_simulation_ph = new(); 00042 extract_phase #(ovm_component) extract_ph = new(); 00043 check_phase #(ovm_component) check_ph = new(); 00044 report_phase #(ovm_component) report_ph = new(); 00045 00046 00047 // DEPRECATED - DO NOT USE IN NEW CODE 00048 00049 `ovm_phase_func_decl(post_new,0) 00050 `ovm_phase_func_decl(export_connections,0) 00051 `ovm_phase_func_decl(import_connections,1) 00052 `ovm_phase_func_decl(pre_run,0) 00053 `ovm_phase_func_decl(configure,0) 00054 post_new_phase #(ovm_component) post_new_ph = new(); 00055 export_connections_phase #(ovm_component) export_connections_ph = new(); 00056 import_connections_phase #(ovm_component) import_connections_ph = new(); 00057 pre_run_phase #(ovm_component) pre_run_ph = new(); 00058 configure_phase #(ovm_component) configure_ph = new(); 00059 ovm_component ovm_top_levels[$]; // don't use 00060 00061 `include "base/ovm_root.svh" 00062 00063 //------------------------------------------------------------------------------ 00064 // 00065 // CLASS: ovm_component 00066 // 00067 //------------------------------------------------------------------------------ 00068 00069 // new 00070 // --- 00071 00072 function ovm_component::new (string name, ovm_component parent); 00073 string error_str; 00074 00075 super.new(name); 00076 00077 // If ovm_top, reset name to "" so it doesn't show in full paths then return 00078 if (parent==null && name == "__top__") begin 00079 set_name(""); 00080 return; 00081 end 00082 00083 // Check that we're not in or past end_of_elaboration 00084 if (end_of_elaboration_ph.is_in_progress() || 00085 end_of_elaboration_ph.is_done() ) begin 00086 ovm_phase curr_phase; 00087 curr_phase = ovm_top.get_current_phase(); 00088 ovm_report_fatal("ILLCRT", {"It is illegal to create a component once", 00089 " phasing reaches end_of_elaboration. The current phase is ", 00090 curr_phase.get_name()}); 00091 end 00092 00093 if (name == "") begin 00094 name.itoa(m_inst_count); 00095 name = {"COMP_", name}; 00096 end 00097 00098 if (parent == null) 00099 parent = ovm_top; 00100 00101 ovm_report_message("NEWCOMP",$psprintf("this=%0s, parent=%0s, name=%s", 00102 this.get_full_name(),parent.get_full_name(),name),10001); 00103 00104 if (parent.has_child(name) && this != parent.get_child(name)) begin 00105 if (parent == ovm_top) begin 00106 error_str = {"Name '",name,"' is not unique to other top-level ", 00107 "instances. If parent is a module, build a unique name by combining the ", 00108 "the module name and component name: $psprintf(\"\%m.\%s\",\"",name,"\")."}; 00109 ovm_report_fatal("CLDEXT",error_str); 00110 end 00111 else 00112 ovm_report_fatal("CLDEXT", 00113 $psprintf("Cannot set '%s' as a child of '%s', %s", 00114 name, parent.get_full_name(), 00115 "which already has a child by that name.")); 00116 return; 00117 end 00118 00119 m_parent = parent; 00120 00121 set_name(name); 00122 00123 if (!m_parent.m_add_child(this)) 00124 m_parent = null; 00125 00126 event_pool = new("event_pool"); 00127 00128 // Register ovm_component phases with ovm_top; only need do once 00129 if (ovm_component::m_phases_loaded==0) begin 00130 ovm_component::m_phases_loaded = 1; 00131 ovm_top.insert_phase(build_ph, null); 00132 ovm_top.insert_phase(post_new_ph, build_ph); 00133 ovm_top.insert_phase(export_connections_ph, post_new_ph); 00134 ovm_top.insert_phase(connect_ph, export_connections_ph); 00135 ovm_top.insert_phase(import_connections_ph, connect_ph); 00136 ovm_top.insert_phase(configure_ph, import_connections_ph); 00137 ovm_top.insert_phase(end_of_elaboration_ph, configure_ph); 00138 ovm_top.insert_phase(start_of_simulation_ph,end_of_elaboration_ph); 00139 ovm_top.insert_phase(pre_run_ph, start_of_simulation_ph); 00140 ovm_top.insert_phase(extract_ph, pre_run_ph); 00141 ovm_top.insert_phase(check_ph, extract_ph); 00142 ovm_top.insert_phase(report_ph, check_ph); 00143 end 00144 00145 // Now that inst name is established, reseed (if use_ovm_seeding is set) 00146 reseed(); 00147 00148 // Do local configuration settings (URM backward compatibility) 00149 void'(get_config_int("recording_detail", recording_detail)); 00150 00151 // Deprecated container of top-levels (replaced by ovm_top) 00152 if (parent == ovm_top) 00153 ovm_top_levels.push_back(this); 00154 00155 endfunction 00156 00157 00158 // m_add_child 00159 // ----------- 00160 00161 function bit ovm_component::m_add_child(ovm_component child); 00162 00163 if (m_children.exists(child.get_name()) && 00164 m_children[child.get_name()] != child) begin 00165 ovm_report_warning("BDCLD", 00166 $psprintf("A child with the name '%0s' (type=%0s) already exists.", 00167 child.get_name(), m_children[child.get_name()].get_type_name())); 00168 return 0; 00169 end 00170 00171 foreach (m_children[c]) 00172 if (child == m_children[c]) begin 00173 ovm_report_warning("BDCHLD", 00174 $psprintf("A child with the name '%0s' %0s %0s'", 00175 child.get_name(), 00176 "already exists in parent under name '", 00177 m_children[c].get_name())); 00178 return 0; 00179 end 00180 00181 m_children[child.get_name()] = child; 00182 return 1; 00183 endfunction 00184 00185 00186 //------------------------------------------------------------------------------ 00187 // 00188 // Hierarchy Methods 00189 // 00190 //------------------------------------------------------------------------------ 00191 00192 00193 // get_first_child 00194 // --------------- 00195 00196 function int ovm_component::get_first_child(`ref string name); 00197 return m_children.first(name); 00198 endfunction 00199 00200 00201 // get_next_child 00202 // -------------- 00203 00204 function int ovm_component::get_next_child(`ref string name); 00205 return m_children.next(name); 00206 endfunction 00207 00208 00209 // get_child 00210 // --------- 00211 00212 function ovm_component ovm_component::get_child(string name); 00213 return m_children[name]; 00214 endfunction 00215 00216 00217 // has_child 00218 // --------- 00219 00220 function int ovm_component::has_child(string name); 00221 return m_children.exists(name); 00222 endfunction 00223 00224 00225 // get_num_children 00226 // ---------------- 00227 00228 function int ovm_component::get_num_children(); 00229 return m_children.num(); 00230 endfunction 00231 00232 00233 // get_type_name 00234 // ------------- 00235 00236 function string ovm_component::get_type_name(); 00237 return "ovm_component"; 00238 endfunction 00239 00240 00241 // get_full_name 00242 // ------------- 00243 00244 function string ovm_component::get_full_name (); 00245 // Note: Implementation choice to construct full name once since the 00246 // full name may be used often for lookups. 00247 if(m_name == "") 00248 return get_name(); 00249 else 00250 return m_name; 00251 endfunction 00252 00253 00254 // get_parent 00255 // ---------- 00256 00257 function ovm_component ovm_component::get_parent (); 00258 return m_parent; 00259 endfunction 00260 00261 00262 // set_name 00263 // -------- 00264 00265 function void ovm_component::set_name (string name); 00266 00267 super.set_name(name); 00268 m_set_full_name(); 00269 00270 endfunction 00271 00272 00273 00274 // m_set_full_name 00275 // --------------- 00276 00277 function void ovm_component::m_set_full_name(); 00278 if (m_parent == ovm_top || m_parent==null) 00279 m_name = get_name(); 00280 else 00281 m_name = {m_parent.get_full_name(), ".", get_name()}; 00282 00283 foreach (m_children[c]) begin 00284 ovm_component tmp; 00285 tmp = m_children[c]; 00286 tmp.m_set_full_name(); 00287 end 00288 00289 endfunction 00290 00291 00292 // lookup 00293 // ------ 00294 00295 function ovm_component ovm_component::lookup( string name ); 00296 00297 string leaf , remainder; 00298 ovm_component comp; 00299 00300 comp = this; 00301 00302 m_extract_name(name, leaf, remainder); 00303 00304 if (leaf == "") begin 00305 comp = ovm_top; // absolute lookup 00306 m_extract_name(remainder, leaf, remainder); 00307 end 00308 00309 if (!comp.has_child(leaf)) begin 00310 ovm_report_warning("Lookup Error", 00311 $psprintf("Cannot find child %0s",leaf)); 00312 return null; 00313 end 00314 00315 if( remainder != "" ) 00316 return comp.m_children[leaf].lookup(remainder); 00317 00318 return comp.m_children[leaf]; 00319 00320 endfunction 00321 00322 00323 // m_extract_name 00324 // -------------- 00325 00326 function void ovm_component::m_extract_name(input string name , 00327 output string leaf , 00328 output string remainder ); 00329 int i , len; 00330 string extract_str; 00331 len = name.len(); 00332 00333 for( i = 0; i < name.len(); i++ ) begin 00334 if( name[i] == "." ) begin 00335 break; 00336 end 00337 end 00338 00339 if( i == len ) begin 00340 leaf = name; 00341 remainder = ""; 00342 return; 00343 end 00344 00345 leaf = name.substr( 0 , i - 1 ); 00346 remainder = name.substr( i + 1 , len - 1 ); 00347 00348 return; 00349 endfunction 00350 00351 00352 // flush 00353 // ----- 00354 00355 function void ovm_component::flush(); 00356 return; 00357 endfunction 00358 00359 00360 // do_flush (flush_hier?) 00361 // -------- 00362 00363 function void ovm_component::do_flush(); 00364 foreach( m_children[s] ) 00365 m_children[s].do_flush(); 00366 flush(); 00367 endfunction 00368 00369 00370 //------------------------------------------------------------------------------ 00371 // 00372 // Factory Methods 00373 // 00374 //------------------------------------------------------------------------------ 00375 00376 // create 00377 // ------ 00378 00379 function ovm_object ovm_component::create (string name =""); 00380 ovm_report_error("ILLCRT", 00381 "create cannot be called on a ovm_component. Use create_component instead."); 00382 return null; 00383 endfunction 00384 00385 00386 // clone 00387 // ------ 00388 00389 function ovm_object ovm_component::clone (); 00390 ovm_report_error("ILLCLN","clone cannot be called on a ovm_component. "); 00391 return null; 00392 endfunction 00393 00394 00395 // print_override_info 00396 // ------------------- 00397 00398 function void ovm_component::print_override_info (string type_name, 00399 string inst_name=""); 00400 ovm_factory::print_override_info(type_name, get_full_name(), inst_name); 00401 endfunction 00402 00403 00404 // create_component 00405 // ---------------- 00406 00407 function ovm_component ovm_component::create_component (string type_name, 00408 string inst_name); 00409 return ovm_factory::create_component(type_name, get_full_name(), 00410 inst_name, this); 00411 endfunction 00412 00413 00414 // create_object 00415 // ------------- 00416 00417 function ovm_object ovm_component::create_object (string type_name, 00418 string name=""); 00419 return ovm_factory::create_object(type_name, get_full_name(), name); 00420 endfunction 00421 00422 00423 // set_type_override (static) 00424 // ----------------- 00425 00426 function void ovm_component::set_type_override (string override_type, 00427 string type_name, 00428 bit replace=1); 00429 ovm_factory::set_type_override(override_type, type_name, replace); 00430 endfunction 00431 00432 00433 // set_inst_override 00434 // ----------------- 00435 00436 function void ovm_component::set_inst_override (string inst_path, 00437 string override_type, 00438 string type_name); 00439 if(inst_path == "") 00440 inst_path = get_full_name(); 00441 else 00442 inst_path = {get_full_name(), ".", inst_path}; 00443 ovm_factory::set_inst_override(inst_path, override_type, type_name); 00444 endfunction 00445 00446 00447 //------------------------------------------------------------------------------ 00448 // 00449 // Hierarchical report configuration interface 00450 // 00451 //------------------------------------------------------------------------------ 00452 00453 // set_report_severity_action_hier 00454 // ------------------------------- 00455 00456 function void ovm_component::set_report_severity_action_hier( ovm_severity s, 00457 ovm_action a); 00458 set_report_severity_action(s, a); 00459 foreach( m_children[c] ) 00460 m_children[c].set_report_severity_action_hier(s, a); 00461 endfunction 00462 00463 00464 // set_report_id_action_hier 00465 // ------------------------- 00466 00467 function void ovm_component::set_report_id_action_hier( string id, ovm_action a); 00468 set_report_id_action(id, a); 00469 foreach( m_children[c] ) 00470 m_children[c].set_report_id_action_hier(id, a); 00471 endfunction 00472 00473 00474 // set_report_severity_id_action_hier 00475 // ---------------------------------- 00476 00477 function void ovm_component::set_report_severity_id_action_hier( ovm_severity s, 00478 string id, 00479 ovm_action a); 00480 set_report_severity_id_action(s, id, a); 00481 foreach( m_children[c] ) 00482 m_children[c].set_report_severity_id_action_hier(s, id, a); 00483 endfunction 00484 00485 00486 // set_report_severity_file_hier 00487 // ----------------------------- 00488 00489 function void ovm_component::set_report_severity_file_hier( ovm_severity s, 00490 OVM_FILE f); 00491 set_report_severity_file(s, f); 00492 foreach( m_children[c] ) 00493 m_children[c].set_report_severity_file_hier(s, f); 00494 endfunction 00495 00496 00497 // set_report_default_file_hier 00498 // ---------------------------- 00499 00500 function void ovm_component::set_report_default_file_hier( OVM_FILE f); 00501 set_report_default_file(f); 00502 foreach( m_children[c] ) 00503 m_children[c].set_report_default_file_hier(f); 00504 endfunction 00505 00506 00507 // set_report_id_file_hier 00508 // ----------------------- 00509 00510 function void ovm_component::set_report_id_file_hier( string id, OVM_FILE f); 00511 set_report_id_file(id, f); 00512 foreach( m_children[c] ) 00513 m_children[c].set_report_id_file_hier(id, f); 00514 endfunction 00515 00516 00517 // set_report_severity_id_file_hier 00518 // -------------------------------- 00519 00520 function void ovm_component::set_report_severity_id_file_hier ( ovm_severity s, 00521 string id, 00522 OVM_FILE f); 00523 set_report_severity_id_file(s, id, f); 00524 foreach( m_children[c] ) 00525 m_children[c].set_report_severity_id_file_hier(s, id, f); 00526 endfunction 00527 00528 00529 // set_report_verbosity_level_hier 00530 // ------------------------------- 00531 00532 function void ovm_component::set_report_verbosity_level_hier(int v); 00533 set_report_verbosity_level(v); 00534 foreach( m_children[c] ) 00535 m_children[c].set_report_verbosity_level_hier(v); 00536 endfunction 00537 00538 00539 //------------------------------------------------------------------------------ 00540 // 00541 // Phase interface 00542 // 00543 //------------------------------------------------------------------------------ 00544 00545 00546 // do_func_phase 00547 // ------------- 00548 00549 function void ovm_component::do_func_phase (ovm_phase phase); 00550 // If in build_ph, don't build if already done 00551 m_curr_phase = phase; 00552 if (!(phase == build_ph && m_build_done)) 00553 phase.call_func(this); 00554 endfunction 00555 00556 00557 // do_kill_all 00558 // ----------- 00559 00560 function void ovm_component::do_kill_all(); 00561 foreach(m_children[c]) 00562 m_children[c].do_kill_all(); 00563 endfunction 00564 00565 00566 // build 00567 // ----- 00568 00569 function void ovm_component::build(); 00570 m_build_done = 1; 00571 apply_config_settings(); 00572 endfunction 00573 00574 00575 // connect 00576 // ------- 00577 00578 function void ovm_component::connect(); 00579 return; 00580 endfunction 00581 00582 00583 // configure 00584 // --------- 00585 00586 function void ovm_component::configure(); 00587 return; 00588 endfunction 00589 00590 00591 // start_of_simulation 00592 // ------------------- 00593 00594 function void ovm_component::start_of_simulation(); 00595 return; 00596 endfunction 00597 00598 00599 // end_of_elaboration 00600 // ------------------ 00601 00602 function void ovm_component::end_of_elaboration(); 00603 return; 00604 endfunction 00605 00606 00607 // extract 00608 // ------- 00609 00610 function void ovm_component::extract(); 00611 return; 00612 endfunction 00613 00614 00615 // check 00616 // ----- 00617 00618 function void ovm_component::check(); 00619 return; 00620 endfunction 00621 00622 00623 // report 00624 // ------ 00625 00626 function void ovm_component::report(); 00627 return; 00628 endfunction 00629 00630 00631 // stop 00632 // ---- 00633 00634 task ovm_component::stop(string ph_name); 00635 return; 00636 endtask 00637 00638 00639 // resolve_bindings 00640 // ---------------- 00641 00642 function void ovm_component::resolve_bindings(); 00643 return; 00644 endfunction 00645 00646 00647 // do_resolve_bindings 00648 // ------------------- 00649 00650 function void ovm_component::do_resolve_bindings(); 00651 foreach( m_children[s] ) 00652 m_children[s].do_resolve_bindings(); 00653 resolve_bindings(); 00654 endfunction 00655 00656 00657 00658 //------------------------------------------------------------------------------ 00659 // 00660 // Recording interface 00661 // 00662 //------------------------------------------------------------------------------ 00663 00664 // accept_tr 00665 // --------- 00666 00667 function void ovm_component::accept_tr (ovm_transaction tr, 00668 time accept_time=0); 00669 ovm_event e; 00670 tr.accept_tr(accept_time); 00671 do_accept_tr(tr); 00672 e = event_pool.get("accept_tr"); 00673 if(e!=null) 00674 e.trigger(); 00675 endfunction 00676 00677 // begin_tr 00678 // -------- 00679 00680 function integer ovm_component::begin_tr (ovm_transaction tr, 00681 string stream_name ="main", 00682 string label="", 00683 string desc="", 00684 time begin_time=0); 00685 return m_begin_tr(tr, 0, 0, stream_name, label, desc, begin_time); 00686 endfunction 00687 00688 // begin_child_tr 00689 // -------------- 00690 00691 function integer ovm_component::begin_child_tr (ovm_transaction tr, 00692 integer parent_handle=0, 00693 string stream_name="main", 00694 string label="", 00695 string desc="", 00696 time begin_time=0); 00697 return m_begin_tr(tr, parent_handle, 1, stream_name, label, desc, begin_time); 00698 endfunction 00699 00700 // m_begin_tr 00701 // ---------- 00702 00703 function integer ovm_component::m_begin_tr (ovm_transaction tr, 00704 integer parent_handle=0, 00705 bit has_parent=0, 00706 string stream_name="main", 00707 string label="", 00708 string desc="", 00709 time begin_time=0); 00710 ovm_event e; 00711 integer stream_h; 00712 integer tr_h; 00713 integer link_tr_h; 00714 string name; 00715 00716 tr_h = 0; 00717 if(has_parent) 00718 link_tr_h = tr.begin_child_tr(begin_time, parent_handle); 00719 else 00720 link_tr_h = tr.begin_tr(begin_time); 00721 00722 if (tr.get_name() != "") 00723 name = tr.get_name(); 00724 else 00725 name = tr.get_type_name(); 00726 00727 if(stream_name == "") stream_name="main"; 00728 00729 if (recording_detail != OVM_NONE) begin 00730 00731 if(m_stream_handle.exists(stream_name)) 00732 stream_h = m_stream_handle[stream_name]; 00733 00734 if (ovm_check_handle_kind("Fiber", stream_h) != 1) 00735 begin 00736 stream_h = ovm_create_fiber(stream_name, "TVM", get_full_name()); 00737 m_stream_handle[stream_name] = stream_h; 00738 end 00739 00740 if(has_parent == 0) 00741 tr_h = ovm_begin_transaction("Begin_No_Parent, Link", 00742 stream_h, 00743 name, 00744 label, 00745 desc, 00746 begin_time); 00747 else begin 00748 tr_h = ovm_begin_transaction("Begin_End, Link", 00749 stream_h, 00750 name, 00751 label, 00752 desc, 00753 begin_time); 00754 if(parent_handle!=0) 00755 ovm_link_transaction(parent_handle, tr_h, "child"); 00756 end 00757 00758 m_tr_h[tr] = tr_h; 00759 00760 if (ovm_check_handle_kind("Transaction", link_tr_h) == 1) 00761 ovm_link_transaction(tr_h,link_tr_h); 00762 00763 do_begin_tr(tr,stream_name,tr_h); 00764 00765 e = event_pool.get("begin_tr"); 00766 if (e!=null) 00767 e.trigger(tr); 00768 00769 end 00770 00771 return tr_h; 00772 00773 endfunction 00774 00775 00776 // end_tr 00777 // ------ 00778 00779 function void ovm_component::end_tr (ovm_transaction tr, 00780 time end_time=0, 00781 bit free_handle=1); 00782 ovm_event e; 00783 integer tr_h; 00784 tr_h = 0; 00785 00786 tr.end_tr(end_time,free_handle); 00787 00788 if (recording_detail != OVM_NONE) begin 00789 00790 if (m_tr_h.exists(tr)) begin 00791 00792 tr_h = m_tr_h[tr]; 00793 00794 do_end_tr(tr, tr_h); // callback 00795 00796 m_tr_h.delete(tr); 00797 00798 if (ovm_check_handle_kind("Transaction", tr_h) == 1) begin 00799 00800 ovm_default_recorder.tr_handle = tr_h; 00801 tr.record(ovm_default_recorder); 00802 00803 ovm_end_transaction(tr_h,end_time); 00804 00805 if (free_handle) 00806 ovm_free_transaction_handle(tr_h); 00807 00808 end 00809 end 00810 else begin 00811 do_end_tr(tr, tr_h); // callback 00812 end 00813 00814 00815 e = event_pool.get("end_tr"); 00816 if(e!=null) 00817 e.trigger(); 00818 end 00819 00820 endfunction 00821 00822 // record_error_tr 00823 // --------------- 00824 00825 function integer ovm_component::record_error_tr (string stream_name="main", 00826 ovm_object info=null, 00827 string label="error_tr", 00828 string desc="", 00829 time error_time=0, 00830 bit keep_active=0); 00831 string etype; 00832 integer stream_h; 00833 00834 if(keep_active) etype = "Error, Link"; 00835 else etype = "Error"; 00836 00837 if(error_time == 0) error_time = $time; 00838 00839 stream_h = m_stream_handle[stream_name]; 00840 if (ovm_check_handle_kind("Fiber", stream_h) != 1) begin 00841 stream_h = ovm_create_fiber(stream_name, "TVM", get_full_name()); 00842 m_stream_handle[stream_name] = stream_h; 00843 end 00844 00845 record_error_tr = ovm_begin_transaction(etype, stream_h, label, 00846 label, desc, error_time); 00847 if(info!=null) begin 00848 ovm_default_recorder.tr_handle = record_error_tr; 00849 info.record(ovm_default_recorder); 00850 end 00851 00852 ovm_end_transaction(record_error_tr,error_time); 00853 endfunction 00854 00855 00856 // record_event_tr 00857 // --------------- 00858 00859 function integer ovm_component::record_event_tr (string stream_name="main", 00860 ovm_object info=null, 00861 string label="event_tr", 00862 string desc="", 00863 time event_time=0, 00864 bit keep_active=0); 00865 string etype; 00866 integer stream_h; 00867 00868 if(keep_active) etype = "Event, Link"; 00869 else etype = "Event"; 00870 00871 if(event_time == 0) event_time = $time; 00872 00873 stream_h = m_stream_handle[stream_name]; 00874 if (ovm_check_handle_kind("Fiber", stream_h) != 1) begin 00875 stream_h = ovm_create_fiber(stream_name, "TVM", get_full_name()); 00876 m_stream_handle[stream_name] = stream_h; 00877 end 00878 00879 record_event_tr = ovm_begin_transaction(etype, stream_h, label, 00880 label, desc, event_time); 00881 if(info!=null) begin 00882 ovm_default_recorder.tr_handle = record_event_tr; 00883 info.record(ovm_default_recorder); 00884 end 00885 00886 ovm_end_transaction(record_event_tr,event_time); 00887 endfunction 00888 00889 // do_accept_tr 00890 // ------------ 00891 00892 function void ovm_component::do_accept_tr (ovm_transaction tr); 00893 return; 00894 endfunction 00895 00896 00897 // do_begin_tr 00898 // ----------- 00899 00900 function void ovm_component::do_begin_tr (ovm_transaction tr, 00901 string stream_name, 00902 integer tr_handle); 00903 return; 00904 endfunction 00905 00906 00907 // do_end_tr 00908 // --------- 00909 00910 function void ovm_component::do_end_tr (ovm_transaction tr, 00911 integer tr_handle); 00912 return; 00913 endfunction 00914 00915 00916 //------------------------------------------------------------------------------ 00917 // 00918 // Configuration interface 00919 // 00920 //------------------------------------------------------------------------------ 00921 00922 00923 // set_config_int 00924 // -------------- 00925 00926 function void ovm_component::set_config_int (string inst_name, 00927 string field_name, 00928 ovm_bitstream_t value); 00929 ovm_int_config_setting cfg; 00930 cfg = new({get_full_name(), ".", inst_name}, field_name, 00931 value, get_full_name()); 00932 m_configuration_table.push_front(cfg); 00933 endfunction 00934 00935 00936 // set_config_string 00937 // ----------------- 00938 00939 function void ovm_component::set_config_string (string inst_name, 00940 string field_name, 00941 string value); 00942 ovm_string_config_setting cfg; 00943 cfg = new({get_full_name(), ".", inst_name}, field_name, 00944 value, get_full_name()); 00945 m_configuration_table.push_front(cfg); 00946 endfunction 00947 00948 00949 // set_config_object 00950 // ----------------- 00951 00952 function void ovm_component::set_config_object (string inst_name, 00953 string field_name, 00954 ovm_object value, 00955 bit clone=1); 00956 ovm_object_config_setting cfg; 00957 if(clone && (value != null)) begin 00958 ovm_object tmp; 00959 tmp = value.clone(); 00960 00961 // If create not implemented, or clone is attempted on objects that 00962 // do not t allow cloning (e.g. components) clone will return null. 00963 if(tmp == null) begin 00964 ovm_report_warning("INVCLN", {"Clone failed during set_config_object, ", 00965 "the original reference will be used for configuration. Check that ", 00966 "the create method for the object type is defined properly."}); 00967 `ifdef INCA 00968 $stacktrace; 00969 `endif 00970 end 00971 else 00972 value = tmp; 00973 end 00974 00975 cfg = new({get_full_name(), ".", inst_name}, field_name, 00976 value, get_full_name(), clone); 00977 m_configuration_table.push_front(cfg); 00978 00979 endfunction 00980 00981 00982 // MACROS: (used in get_config_* method implementations) 00983 // ------- 00984 00985 `define OVM_LOCAL_SCOPE_STACK(STACK, START) \ 00986 begin \ 00987 ovm_component oc; \ 00988 oc = START; \ 00989 if(oc!=null) begin \ 00990 do begin \ 00991 STACK.push_front(oc.m_parent); \ 00992 oc = oc.m_parent; \ 00993 end while(oc); \ 00994 end \ 00995 else \ 00996 STACK.push_front(null); \ 00997 end 00998 00999 `define OVM_APPLY_CONFIG_SETTING(STACK, CFG) \ 01000 foreach(STACK[s]) begin \ 01001 comp = STACK[s]; \ 01002 if(rtn) break; \ 01003 if(comp==null) begin \ 01004 for(int i=0; i<global_configuration_table.size(); ++i) begin \ 01005 if(global_configuration_table[i].component_match(this) && \ 01006 global_configuration_table[i].field_match(field_name)) \ 01007 begin \ 01008 if($cast(CFG, global_configuration_table[i])) begin \ 01009 if(print_config_matches) \ 01010 global_configuration_table[i].print_match(this,null,field_name);\ 01011 value = CFG.value; \ 01012 rtn = 1; \ 01013 break; \ 01014 end \ 01015 end \ 01016 end \ 01017 end \ 01018 else begin \ 01019 for(int i = 0; i<comp.m_configuration_table.size(); ++i) begin \ 01020 if(comp.m_configuration_table[i].component_match(this) && \ 01021 comp.m_configuration_table[i].field_match(field_name)) \ 01022 begin \ 01023 if($cast(CFG, comp.m_configuration_table[i])) begin \ 01024 if(print_config_matches) \ 01025 comp.m_configuration_table[i].print_match(this,comp,field_name);\ 01026 value = CFG.value; \ 01027 rtn = 1; \ 01028 break; \ 01029 end \ 01030 end \ 01031 end \ 01032 end \ 01033 end 01034 01035 01036 // get_config_int 01037 // -------------- 01038 01039 function bit ovm_component::get_config_int (string field_name, 01040 inout ovm_bitstream_t value); 01041 ovm_component stack[$]; 01042 ovm_component comp; 01043 ovm_int_config_setting cfg; 01044 bit rtn; rtn = 0; 01045 `OVM_LOCAL_SCOPE_STACK(stack, this) 01046 `OVM_APPLY_CONFIG_SETTING(stack, cfg) 01047 return rtn; 01048 endfunction 01049 01050 01051 // get_config_string 01052 // ----------------- 01053 01054 function bit ovm_component::get_config_string (string field_name, 01055 inout string value); 01056 ovm_component stack[$]; 01057 ovm_component comp; 01058 ovm_string_config_setting cfg; 01059 bit rtn; rtn = 0; 01060 `OVM_LOCAL_SCOPE_STACK(stack, this) 01061 `OVM_APPLY_CONFIG_SETTING(stack, cfg) 01062 return rtn; 01063 endfunction 01064 01065 01066 // get_config_object 01067 // ----------------- 01068 01069 function bit ovm_component::get_config_object (string field_name, 01070 inout ovm_object value, 01071 input bit clone=1); 01072 ovm_component stack[$]; 01073 ovm_component comp; 01074 ovm_object_config_setting cfg; 01075 bit rtn; rtn = 0; 01076 `OVM_LOCAL_SCOPE_STACK(stack, this) 01077 `OVM_APPLY_CONFIG_SETTING(stack, cfg) 01078 if(rtn && clone && (value != null)) begin 01079 ovm_object tmp; 01080 tmp = value.clone(); 01081 if(tmp != null) 01082 tmp = value; 01083 end 01084 return rtn; 01085 endfunction 01086 01087 01088 // apply_config_settings 01089 // --------------------- 01090 01091 function void ovm_component::apply_config_settings (bit verbose=0); 01092 ovm_component stack[$]; 01093 ovm_config_setting cfg; 01094 ovm_int_config_setting cfg_int; 01095 ovm_string_config_setting cfg_str; 01096 ovm_object_config_setting cfg_obj; 01097 ovm_component comp; 01098 `OVM_LOCAL_SCOPE_STACK(stack, this) 01099 //apply any override that matches this component. Go bottom up and then back 01100 //to front so the last override in the global scope has precedence to the 01101 //first override in the parent scope. 01102 for(int i=stack.size()-1; i>=0; --i) begin 01103 if(stack[i]!=null) begin 01104 for(int j=stack[i].m_configuration_table.size()-1; j>=0; --j) begin 01105 cfg = stack[i].m_configuration_table[j]; 01106 if(ovm_is_match(cfg.inst, get_full_name())) begin 01107 if($cast(cfg_int, cfg)) begin 01108 set_int_local(cfg_int.field, cfg_int.value); 01109 end 01110 else if($cast(cfg_str, cfg)) begin 01111 set_string_local(cfg_str.field, cfg_str.value); 01112 end 01113 else if($cast(cfg_obj, cfg)) begin 01114 set_object_local(cfg_obj.field, cfg_obj.value, cfg_obj.clone); 01115 end 01116 end 01117 end 01118 end 01119 else begin 01120 for(int j=global_configuration_table.size()-1; j>=0; --j) begin 01121 //not sure why I need this cast. Seems like a bug 01122 $cast(cfg, global_configuration_table[j]); 01123 if(ovm_is_match(cfg.inst, get_full_name())) begin 01124 if($cast(cfg_int, cfg)) begin 01125 set_int_local(cfg_int.field, cfg_int.value); 01126 end 01127 else if($cast(cfg_str, cfg)) begin 01128 set_string_local(cfg_str.field, cfg_str.value); 01129 end 01130 else if($cast(cfg_obj, cfg)) begin 01131 set_object_local(cfg_obj.field, cfg_obj.value, cfg_obj.clone); 01132 end 01133 end 01134 end 01135 end 01136 end 01137 endfunction 01138 01139 01140 // print_config_settings 01141 // --------------------- 01142 01143 function void ovm_component::print_config_settings (string field="", 01144 ovm_component comp=null, 01145 bit recurse=0); 01146 static int depth; 01147 ovm_component stack[$]; 01148 ovm_component cc; 01149 string all_matches; 01150 string v,r; 01151 all_matches = ""; 01152 01153 if(comp==null) 01154 comp = this; 01155 01156 `OVM_LOCAL_SCOPE_STACK(stack, comp) 01157 cc = comp; 01158 01159 $swrite(v, "%s", cc.get_full_name()); 01160 while(v.len()<17) v = {v," "}; 01161 foreach(stack[s]) begin 01162 comp = stack[s]; 01163 if(comp==null) begin 01164 for(int i=0; i<global_configuration_table.size(); ++i) begin 01165 r = global_configuration_table[i].matches_string(cc, null); 01166 if(r != "") 01167 all_matches = {all_matches, v, r, "\n"}; 01168 end 01169 end 01170 else begin 01171 for(int i=0; i<comp.m_configuration_table.size(); ++i) begin 01172 r = comp.m_configuration_table[i].matches_string(cc, comp); 01173 if(r != "") 01174 all_matches = {all_matches, v, r, "\n"}; 01175 end 01176 end 01177 end 01178 01179 // Note: should use ovm_printer for formatting 01180 if(((all_matches != "") || (recurse == 1)) && depth == 0) begin 01181 $display("Configuration settings for component %s (recurse = %0d)", 01182 cc.get_full_name(), recurse); 01183 $display("Set to Set from Component match Field name Type Value"); 01184 $display("-------------------------------------------------------------------------------"); 01185 end 01186 if(all_matches == "") 01187 $display("%s NONE", v); 01188 else 01189 $write("%s", all_matches); 01190 01191 if(recurse) begin 01192 depth++; 01193 if(cc.m_children.first(v)) 01194 do this.print_config_settings(field, cc.m_children[v], recurse); 01195 while(cc.m_children.next(v)); 01196 depth--; 01197 end 01198 endfunction 01199 01200 01201 01202 01203 //------------------------------------------------------------------------------ 01204 // 01205 // DEPRECATED - DO NOT USE 01206 // 01207 //------------------------------------------------------------------------------ 01208 01209 // do_display (deprecated) 01210 // ---------- 01211 01212 function void ovm_component::do_display( int max_level = -1 , 01213 int level = 0 , 01214 bit display_connectors = 0 ); 01215 if( level == max_level ) 01216 return; 01217 01218 foreach( m_children[s] ) 01219 m_children[s].do_display( max_level , level + 1 , 01220 display_connectors ); 01221 endfunction 01222 01223 01224 // check_connection_size (deprecated) 01225 // --------------------- 01226 01227 function void ovm_component::check_connection_size(); 01228 foreach( m_children[s] ) 01229 m_children[s].check_connection_size(); 01230 endfunction 01231 01232 01233 // global_stop_request (static, deprecated) 01234 // ------------------- 01235 01236 function void ovm_component::global_stop_request(); 01237 ovm_root top; 01238 top = get_top(); 01239 top.stop_request(); 01240 endfunction 01241 01242 01243 // post_new (deprecated) 01244 // -------- 01245 01246 function void ovm_component::post_new(); 01247 return; 01248 endfunction 01249 01250 01251 // export_connections (deprecated) 01252 // ------------------ 01253 01254 function void ovm_component::export_connections(); 01255 return; 01256 endfunction 01257 01258 01259 // import_connections (deprecated) 01260 // ------------------ 01261 01262 function void ovm_component::import_connections(); 01263 return; 01264 endfunction 01265 01266 01267 // pre_run (deprecated) 01268 // ------- 01269 01270 function void ovm_component::pre_run(); 01271 return; 01272 endfunction 01273 01274 01275 // absolute_lookup (deprecated) 01276 // --------------- 01277 01278 function ovm_component ovm_component::absolute_lookup( string name ); 01279 name = {".",name}; 01280 return lookup(name); 01281 endfunction 01282 01283 01284 // relative_lookup (deprecated) 01285 // --------------- 01286 01287 function ovm_component ovm_component::relative_lookup( string name ); 01288 return lookup(name); 01289 endfunction 01290 01291 01292 // build_debug_lists (deprecated) 01293 // ----------------- 01294 01295 function void ovm_component::build_debug_lists(); 01296 foreach(m_children[s]) 01297 m_children[s].add_to_debug_list(); 01298 endfunction 01299 01300 01301 // add_to_debug_list (deprecated) 01302 // ----------------- 01303 01304 function void ovm_component::add_to_debug_list(); 01305 m_parent.m_components[get_name()] = this; 01306 endfunction 01307 01308 01309 // find_component (deprecated) 01310 // -------------- 01311 01312 function ovm_component ovm_component::find_component (string comp_match); 01313 return ovm_top.find(comp_match); 01314 endfunction 01315 01316 01317 01318 // find_components (deprecated) 01319 // --------------- 01320 01321 function void ovm_component::find_components (string comp_match, 01322 ref ovm_component comps[$]); 01323 ovm_top.find_all(comp_match,comps); 01324 endfunction 01325 01326 01327 // get_component (deprecated) 01328 // ------------- 01329 01330 ovm_component m__comps[$]; // deprecated, do not use 01331 01332 function ovm_component ovm_component::get_component (int ele); 01333 if (m__comps.size()==0) 01334 ovm_top.find_all("*",m__comps); 01335 if (ele < m__comps.size()) 01336 return m__comps[ele]; 01337 return null; 01338 endfunction 01339 01340 01341 // get_num_components (deprecated) 01342 // ------------------ 01343 01344 function int ovm_component::get_num_components (); 01345 while (m__comps.size()!=0) 01346 m__comps.delete(0); 01347 ovm_top.find_all("*",m__comps); 01348 get_num_components = m__comps.size(); 01349 endfunction 01350 01351 01352 /* 01353 // get_child_old 01354 // ------------- 01355 01356 function ovm_component ovm_component::get_child_old(int index); 01357 int curr; 01358 string c; 01359 int num; 01360 01361 if (index < 0 || index >= this.m_children.num()) begin 01362 num = this.m_children.num(); 01363 ovm_report_error("BDINDX", 01364 $psprintf("index %0d out of range. Valid range is [0:%0d]", 01365 index, num)); 01366 return null; 01367 end 01368 01369 curr = 0; 01370 01371 if(!m_children.first(c)) 01372 return null; 01373 01374 while (curr != index) begin 01375 void'(m_children.next(c)); 01376 curr++; 01377 end 01378 01379 return m_children[c]; 01380 01381 endfunction 01382 */ 01383
![]() Intelligent Design Verification Project: OVM, Revision: 1.1.0 |
Copyright (c) 2008 Intelligent Design Verification. Permission is granted to copy, distribute and/or modify this document under the terms of the GNU Free Documentation License, Version 1.2 or any later version published by the Free Software Foundation; with no Invariant Sections, no Front-Cover Texts, and no Back-Cover Texts. A copy of the license is included here: http://www.intelligentdv.com/licenses/fdl.txt |
![]() Doxygen Version: 1.4.6 Mon Sep 29 14:20:12 2008 |