diff options
Diffstat (limited to 'src/systemc/tests/systemc/kernel/phase_callbacks')
10 files changed, 950 insertions, 0 deletions
diff --git a/src/systemc/tests/systemc/kernel/phase_callbacks/test01/golden/test01.log b/src/systemc/tests/systemc/kernel/phase_callbacks/test01/golden/test01.log new file mode 100644 index 000000000..9e42301d0 --- /dev/null +++ b/src/systemc/tests/systemc/kernel/phase_callbacks/test01/golden/test01.log @@ -0,0 +1,7 @@ +SystemC Simulation +prim_channel: before end of elaboration +prim_channel: start of simulation + +Info: /OSCI/SystemC: Simulation stopped by user. +prim_channel: end of simulation +Program completed diff --git a/src/systemc/tests/systemc/kernel/phase_callbacks/test01/test01.cpp b/src/systemc/tests/systemc/kernel/phase_callbacks/test01/test01.cpp new file mode 100644 index 000000000..c4095aae3 --- /dev/null +++ b/src/systemc/tests/systemc/kernel/phase_callbacks/test01/test01.cpp @@ -0,0 +1,57 @@ +#include "systemc.h" + +class Sig : public sc_prim_channel { + public: + virtual void before_end_of_elaboration() + { + cout << "prim_channel: before end of elaboration" << endl; + } + virtual void end_of_simulation() + { + cout << "prim_channel: end of simulation" << endl; + } + virtual void start_of_simulation() + { + cout << "prim_channel: start of simulation" << endl; + } +}; + +SC_MODULE(X) +{ + SC_CTOR(X) + { + SC_CTHREAD(y, clk.pos()); + } + void y() + { + wait(); + sc_stop(); + } + sc_in_clk clk; +}; + +int sc_main(int argc, char* argv[]) +{ + sc_clock clock; + Sig signal; + X x("x"); + + x.clk(clock); + + if ( sc_start_of_simulation_invoked() ) + cout << __FILE__ << "(" << __LINE__ << "): bad start flag should be false" << endl; + if ( sc_end_of_simulation_invoked() ) + cout << __FILE__ << "(" << __LINE__ << "): bad end flag should be false" << endl; + + sc_start(2, SC_NS); + if ( !sc_start_of_simulation_invoked() ) + cout << __FILE__ << "(" << __LINE__ << "): bad start flag should be true" << endl; + + if ( !sc_end_of_simulation_invoked() ) + cout << __FILE__ << "(" << __LINE__ << "): bad end flag should be true" << endl; + + cerr << "Program completed" << endl; + + return 0; +} + diff --git a/src/systemc/tests/systemc/kernel/phase_callbacks/test02/golden/test02.log b/src/systemc/tests/systemc/kernel/phase_callbacks/test02/golden/test02.log new file mode 100644 index 000000000..9e42301d0 --- /dev/null +++ b/src/systemc/tests/systemc/kernel/phase_callbacks/test02/golden/test02.log @@ -0,0 +1,7 @@ +SystemC Simulation +prim_channel: before end of elaboration +prim_channel: start of simulation + +Info: /OSCI/SystemC: Simulation stopped by user. +prim_channel: end of simulation +Program completed diff --git a/src/systemc/tests/systemc/kernel/phase_callbacks/test02/test02.cpp b/src/systemc/tests/systemc/kernel/phase_callbacks/test02/test02.cpp new file mode 100644 index 000000000..2f4f3c285 --- /dev/null +++ b/src/systemc/tests/systemc/kernel/phase_callbacks/test02/test02.cpp @@ -0,0 +1,57 @@ +#include "systemc.h" + +class Sig : public sc_prim_channel { + public: + virtual void before_end_of_elaboration() + { + cout << "prim_channel: before end of elaboration" << endl; + } + virtual void end_of_simulation() + { + cout << "prim_channel: end of simulation" << endl; + } + virtual void start_of_simulation() + { + cout << "prim_channel: start of simulation" << endl; + } +}; + +SC_MODULE(X) +{ + SC_CTOR(X) + { + SC_CTHREAD(y, clk.pos()); + } + void y() + { + wait(); + } + sc_in_clk clk; +}; + +int sc_main(int argc, char* argv[]) +{ + sc_clock clock; + Sig signal; + X x("x"); + + x.clk(clock); + + if ( sc_start_of_simulation_invoked() ) + cout << __FILE__ << "(" << __LINE__ << "): bad start flag should be false" << endl; + if ( sc_end_of_simulation_invoked() ) + cout << __FILE__ << "(" << __LINE__ << "): bad end flag should be false" << endl; + + sc_start(2, SC_NS); + if ( !sc_start_of_simulation_invoked() ) + cout << __FILE__ << "(" << __LINE__ << "): bad start flag should be true" << endl; + + sc_stop(); + if ( !sc_end_of_simulation_invoked() ) + cout << __FILE__ << "(" << __LINE__ << "): bad end flag should be true" << endl; + + cerr << "Program completed" << endl; + + return 0; +} + diff --git a/src/systemc/tests/systemc/kernel/phase_callbacks/test03/golden/test03.log b/src/systemc/tests/systemc/kernel/phase_callbacks/test03/golden/test03.log new file mode 100644 index 000000000..29f67481e --- /dev/null +++ b/src/systemc/tests/systemc/kernel/phase_callbacks/test03/golden/test03.log @@ -0,0 +1,22 @@ +SystemC Simulation +top.delayed_mod.delayed_port->before_end_of_elaboration() called +top.direct_mod.delayed_port->before_end_of_elaboration() called +top.delayed_mod.direct_port->before_end_of_elaboration() called +top.delayed_port->before_end_of_elaboration() called +top.direct_port->before_end_of_elaboration() called +top.direct_mod.direct_port->before_end_of_elaboration() called +top->before_end_of_elaboration() called +top.direct_mod->before_end_of_elaboration() called +top.direct_mod.direct_port_direct_mod->before_end_of_elaboration() called +top.direct_port_direct_mod->before_end_of_elaboration() called +top.direct_port_delayed_mod->before_end_of_elaboration() called +top.direct_mod.direct_port_delayed_mod->before_end_of_elaboration() called +top.delayed_port_direct_mod->before_end_of_elaboration() called +top.delayed_mod->before_end_of_elaboration() called +top.delayed_mod.direct_port_direct_mod->before_end_of_elaboration() called +top.direct_mod.delayed_port_direct_mod->before_end_of_elaboration() called +top.delayed_mod.delayed_port_direct_mod->before_end_of_elaboration() called +top.delayed_mod.delayed_port_delayed_mod->before_end_of_elaboration() called +top.direct_mod.delayed_port_delayed_mod->before_end_of_elaboration() called +top.delayed_mod.direct_port_delayed_mod->before_end_of_elaboration() called +top.delayed_port_delayed_mod->before_end_of_elaboration() called diff --git a/src/systemc/tests/systemc/kernel/phase_callbacks/test03/test03.cpp b/src/systemc/tests/systemc/kernel/phase_callbacks/test03/test03.cpp new file mode 100644 index 000000000..d34109cb7 --- /dev/null +++ b/src/systemc/tests/systemc/kernel/phase_callbacks/test03/test03.cpp @@ -0,0 +1,148 @@ +/***************************************************************************** + + Licensed to Accellera Systems Initiative Inc. (Accellera) under one or + more contributor license agreements. See the NOTICE file distributed + with this work for additional information regarding copyright ownership. + Accellera licenses this file to you under the Apache License, Version 2.0 + (the "License"); you may not use this file except in compliance with the + License. You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + + Unless required by applicable law or agreed to in writing, software + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or + implied. See the License for the specific language governing + permissions and limitations under the License. + + *****************************************************************************/ + +// test03.cpp -- test for delayed before end of elaboration. +// +// Original Author: Philipp A. Hartmann, OFFIS Institute for Information +// Technology +// +// MODIFICATION LOG - modifiers, enter your name, affiliation, date and +// +// $Log: test03.cpp,v $ +// Revision 1.2 2011/07/24 13:05:30 acg +// Alan Fitch: added return 0 to sc_main that was missing. +// +// Revision 1.1 2011/05/08 17:55:36 acg +// Philipp A. Hartmann: first check in of test. +// + +#include <systemc> + +using namespace sc_core; + +#define PRINT_CALL( CallBack, Condition ) \ + std::cout << this->name() \ + << "->" #CallBack "()" \ + << ( ( Condition ) ? " " : " NOT " ) \ + << "called" \ + << std::endl + +SC_MODULE(in_port_module) +{ + SC_CTOR(in_port_module) : beoe_called(false) {} + + void before_end_of_elaboration() + { beoe_called = true; } + + void end_of_elaboration() + { PRINT_CALL(before_end_of_elaboration,beoe_called); } + + bool beoe_called; +}; + +struct my_port : sc_in<bool> +{ + typedef sc_in<bool> base_type; + + explicit my_port( const char* nm ) + : base_type(nm) + , direct_mod( (std::string(nm)+"_direct_mod").c_str() ) + , beoe_called(false) {} + + void before_end_of_elaboration() + { + beoe_called = true; + std::string nm = std::string(basename()) + "_delayed_mod"; + delayed_mod = new in_port_module( nm.c_str() ); + } + + void end_of_elaboration() + { PRINT_CALL(before_end_of_elaboration,beoe_called); } + + in_port_module direct_mod; + in_port_module* delayed_mod; + bool beoe_called; +}; + +SC_MODULE(sub_module) +{ + my_port direct_port; + my_port* delayed_port; + + SC_CTOR(sub_module) + : direct_port("direct_port") + , delayed_port(0) + , beoe_called(false) + {} + + void before_end_of_elaboration() + { + delayed_port = new my_port( "delayed_port" ); + (*delayed_port)( direct_port ); + beoe_called = true; + } + + void end_of_elaboration() + { PRINT_CALL(before_end_of_elaboration,beoe_called); } + + bool beoe_called; +}; + +SC_MODULE(module) +{ + sub_module direct_mod; + my_port direct_port; + sub_module* delayed_mod; + my_port* delayed_port; + + SC_CTOR(module) + : direct_mod("direct_mod") + , direct_port("direct_port") + , delayed_mod(0) + , delayed_port(0) + , beoe_called(false) + { + direct_mod.direct_port( direct_port ); + } + + void before_end_of_elaboration() + { + delayed_port = new my_port( "delayed_port" ); + (*delayed_port)( direct_port ); + + delayed_mod = new sub_module( "delayed_mod" ); + delayed_mod->direct_port( *delayed_port ); + beoe_called = true; + } + + void end_of_elaboration() + { PRINT_CALL(before_end_of_elaboration,beoe_called); } + + bool beoe_called; +}; + +int sc_main( int, char*[] ) +{ + module mod("top"); + sc_signal<bool> sig("sig"); + mod.direct_port( sig ); + + sc_start(); + return 0; +} diff --git a/src/systemc/tests/systemc/kernel/phase_callbacks/test04/golden/register_phase_callbacks.log b/src/systemc/tests/systemc/kernel/phase_callbacks/test04/golden/register_phase_callbacks.log new file mode 100644 index 000000000..5915a8821 --- /dev/null +++ b/src/systemc/tests/systemc/kernel/phase_callbacks/test04/golden/register_phase_callbacks.log @@ -0,0 +1,80 @@ +SystemC Simulation + +Warning: (W552) register simulation phase callback: phase_tracer_0: SC_ELABORATION: + substituted by (SC_BEFORE_END_OF_ELABORATION|SC_END_OF_ELABORATION) +In file: <removed by verify.pl> + +Warning: (W552) register simulation phase callback: phase_tracer_0: SC_RUNNING: + substituted by (SC_END_OF_INITIALIZATION|SC_END_OF_UPDATE|SC_BEFORE_TIMESTEP) +In file: <removed by verify.pl> + +Warning: (W552) register simulation phase callback: phase_tracer_0: SC_RUNNING: + substituted by (SC_END_OF_INITIALIZATION|SC_END_OF_UPDATE|SC_BEFORE_TIMESTEP) +In file: <removed by verify.pl> + +Warning: (W552) register simulation phase callback: phase_tracer_0: SC_ELABORATION: + substituted by (SC_BEFORE_END_OF_ELABORATION|SC_END_OF_ELABORATION) +In file: <removed by verify.pl> + +Warning: (W552) register simulation phase callback: phase_tracer_0: SC_RUNNING: + substituted by (SC_END_OF_INITIALIZATION|SC_END_OF_UPDATE|SC_BEFORE_TIMESTEP) +In file: <removed by verify.pl> +phase_tracer_0: before_end_of_elaboration: 0 callbacks called. +phase_tracer_0: phase callback SC_BEFORE_END_OF_ELABORATION: 0 s -> pending activity: MAX +phase_tracer_0: end_of_elaboration: 1 callbacks called. +phase_tracer_0: phase callback SC_END_OF_ELABORATION: 0 s -> pending activity: MAX +phase_tracer_0: start_of_simulation: 2 callbacks called. + +Warning: (W552) register simulation phase callback: phase_tracer_0: elaboration done + SC_ELABORATION callback(s) ignored +In file: <removed by verify.pl> +phase_tracer_0: phase callback SC_START_OF_SIMULATION: 0 s -> pending activity: MAX +phase_tracer_0: phase callback SC_END_OF_INITIALIZATION: 0 s -> pending activity: 0 s +phase_tracer_0.timed: 0 s: 0 +phase_tracer_0.delta: 0 s: 0 +phase_tracer_0: phase callback SC_END_OF_UPDATE: 0 s -> pending activity: 0 s +phase_tracer_0.delta: 0 s: 1 +phase_tracer_0: phase callback SC_END_OF_UPDATE: 0 s -> pending activity: 100 ns + +Warning: (W553) forbidden action in simulation phase callback: SC_END_OF_UPDATE: + delta notification of `phase_tracer_0.event_0' ignored +In file: <removed by verify.pl> +phase_tracer_0: phase callback SC_BEFORE_TIMESTEP: 0 s -> pending activity: 100 ns + +Warning: (W553) forbidden action in simulation phase callback: SC_BEFORE_TIMESTEP: + delta notification of `phase_tracer_0.event_0' ignored +In file: <removed by verify.pl> +phase_tracer_0.timed: 100 ns: 1 +phase_tracer_0: phase callback SC_END_OF_UPDATE: 100 ns -> pending activity: 0 s +phase_tracer_0.delta: 100 ns: 2 +phase_tracer_0: phase callback SC_END_OF_UPDATE: 100 ns -> pending activity: 100 ns + +Warning: (W553) forbidden action in simulation phase callback: SC_END_OF_UPDATE: + timed notification of `phase_tracer_0.event_0' ignored +In file: <removed by verify.pl> +phase_tracer_0: phase callback SC_BEFORE_TIMESTEP: 100 ns -> pending activity: 100 ns + +Warning: (W553) forbidden action in simulation phase callback: SC_BEFORE_TIMESTEP: + timed notification of `phase_tracer_0.event_0' ignored +In file: <removed by verify.pl> +phase_tracer_0.timed: 200 ns: 2 +phase_tracer_0: phase callback SC_END_OF_UPDATE: 200 ns -> pending activity: 0 s +phase_tracer_0: phase callback SC_BEFORE_TIMESTEP: 200 ns -> pending activity: 100 ns +phase_tracer_0.timed: 300 ns: 3 +phase_tracer_0: phase callback SC_END_OF_UPDATE: 300 ns -> pending activity: 0 s +phase_tracer_0.delta: 300 ns: 3 +phase_tracer_0: phase callback SC_END_OF_UPDATE: 300 ns -> pending activity: 100 ns +phase_tracer_0: phase callback SC_BEFORE_TIMESTEP: 300 ns -> pending activity: 100 ns +phase_tracer_0.timed: 400 ns: 4 +phase_tracer_0: phase callback SC_END_OF_UPDATE: 400 ns -> pending activity: 0 s +phase_tracer_0.delta: 400 ns: 4 +phase_tracer_0: phase callback SC_END_OF_UPDATE: 400 ns -> pending activity: 100 ns +phase_tracer_0: phase callback SC_BEFORE_TIMESTEP: 400 ns -> pending activity: 100 ns +phase_tracer_0.timed: 500 ns: 5 +phase_tracer_0: phase callback SC_END_OF_UPDATE: 500 ns -> pending activity: MAX + +Info: /OSCI/SystemC: Simulation stopped by user. +phase_tracer_0: end_of_simulation: 19 callbacks called. +phase_tracer_0: phase callback SC_END_OF_SIMULATION: 500 ns -> pending activity: MAX +phase_tracer_0: phase callback SC_STOPPED: 500 ns -> pending activity: MAX +phase_tracer_0: [destructor]: 21 callbacks called. diff --git a/src/systemc/tests/systemc/kernel/phase_callbacks/test04/register_phase_callbacks.cpp b/src/systemc/tests/systemc/kernel/phase_callbacks/test04/register_phase_callbacks.cpp new file mode 100644 index 000000000..5ed6dd4f9 --- /dev/null +++ b/src/systemc/tests/systemc/kernel/phase_callbacks/test04/register_phase_callbacks.cpp @@ -0,0 +1,221 @@ +/***************************************************************************** + + Licensed to Accellera Systems Initiative Inc. (Accellera) under one or + more contributor license agreements. See the NOTICE file distributed + with this work for additional information regarding copyright ownership. + Accellera licenses this file to you under the Apache License, Version 2.0 + (the "License"); you may not use this file except in compliance with the + License. You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + + Unless required by applicable law or agreed to in writing, software + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or + implied. See the License for the specific language governing + permissions and limitations under the License. + + *****************************************************************************/ + +/***************************************************************************** + + register_phase_callbacks.cpp -- Test for (un)registering dynamic callbacks + + Note: requires simulation phase callback support enabled in the kernel + SC_ENABLE_SIMULATION_PHASE_CALLBACKS / --enable-phase-callbacks + + Original Author: Philipp A. Hartmann, OFFIS, 2013-05-17 + + *****************************************************************************/ + +/***************************************************************************** + + MODIFICATION LOG - modifiers, enter your name, affiliation, date and + changes you are making here. + + Name, Affiliation, Date: + Description of Modification: + + *****************************************************************************/ + +#include <systemc.h> + +#define VERBOSE 1 + +SC_MODULE(phase_tracer) +{ + SC_HAS_PROCESS(phase_tracer); + phase_tracer( sc_module_name nm + = sc_core::sc_gen_unique_name("phase_tracer") ) + : cb_count(0), timed_count(), delta_count() + { + SC_METHOD(timed); + SC_METHOD(delta); + sensitive << ev; + + old_mask = SC_STATUS_ANY; + cb_mask = register_simulation_phase_callback( SC_STATUS_ANY ); + sc_assert( cb_mask == (old_mask & ~SC_ELABORATION & ~SC_RUNNING) ); + old_mask = cb_mask; + + cb_mask = unregister_simulation_phase_callback(SC_STOPPED); + sc_assert( cb_mask == (old_mask & ~SC_STOPPED) ); + old_mask = cb_mask; + + cb_mask = register_simulation_phase_callback( SC_UNITIALIZED ); + sc_assert( cb_mask == old_mask ); + + cb_mask = unregister_simulation_phase_callback(SC_UNITIALIZED); + sc_assert( cb_mask == old_mask ); + + cb_mask = unregister_simulation_phase_callback(SC_RUNNING); + sc_assert( cb_mask == (old_mask & ~SC_END_OF_INITIALIZATION +// & ~SC_END_OF_EVALUATION + & ~SC_END_OF_UPDATE + & ~SC_BEFORE_TIMESTEP) ); + old_mask = cb_mask; + + cb_mask = unregister_simulation_phase_callback(SC_ELABORATION); + sc_assert( cb_mask == (old_mask & ~SC_BEFORE_END_OF_ELABORATION + & ~SC_END_OF_ELABORATION ) ); + old_mask = cb_mask; + + cb_mask = unregister_simulation_phase_callback( SC_STATUS_ANY ); + sc_assert( cb_mask == SC_UNITIALIZED ); + old_mask = cb_mask; + + cb_mask = register_simulation_phase_callback( SC_RUNNING ); + sc_assert( cb_mask == ( SC_END_OF_INITIALIZATION +// | SC_END_OF_EVALUATION + | SC_END_OF_UPDATE | SC_BEFORE_TIMESTEP ) ); + + cb_mask = register_simulation_phase_callback( SC_STATUS_ANY ); + sc_assert( cb_mask == (SC_STATUS_ANY & ~SC_ELABORATION & ~SC_RUNNING) ); + } + + void timed() + { + std::cout + << sc_get_current_process_handle().name() + << ": " << sc_time_stamp() + << ": " << timed_count + << std::endl; + if( timed_count++ < 5 ) { + next_trigger( 100, SC_NS ); + } + if( delta_count < 5 ) + ev.notify( SC_ZERO_TIME ); + + if( timed_count>=6 ) + sc_stop(); + } + void delta() + { + std::cout + << sc_get_current_process_handle().name() + << ": " << sc_time_stamp() + << ": " << delta_count + << std::endl; + delta_count++; + } + + virtual void simulation_phase_callback() + { + cb_count++; + +# if VERBOSE + { + std::string ttp; + if( !sc_pending_activity() ) { + ttp = "MAX"; + } else { + ttp = sc_time_to_pending_activity().to_string(); + } + std::cout << name() + << ": phase callback " + << sc_get_status() + << ": " << sc_time_stamp() + << " -> pending activity: " << ttp + << std::endl; + } +# endif + sc_assert( cb_mask & sc_get_status() ); + + switch( sc_get_status() ) + { + case SC_END_OF_UPDATE: + case SC_BEFORE_TIMESTEP: + if( timed_count == 3 ) + ev.cancel(); + if( delta_count == 2 ) + ev.notify(SC_ZERO_TIME); + if( timed_count == 2 ) + ev.notify( 1, SC_NS ); + break; + default: + // do nothing + break; + } + } + + ~phase_tracer() + { print_static_phase_stats( "[destructor]" ); } + + void print_static_phase_stats( const char* phase ) + { +#if VERBOSE + std::cout << name() + << ": " << phase << ": " + << cb_count << " callbacks called." + << std::endl; +#endif + } + +private: + + virtual void before_end_of_elaboration() + { + sc_assert( sc_get_status() == SC_BEFORE_END_OF_ELABORATION ); + print_static_phase_stats( "before_end_of_elaboration" ); + } + + virtual void end_of_elaboration() + { + sc_assert( sc_get_status() == SC_END_OF_ELABORATION ); + print_static_phase_stats( "end_of_elaboration" ); + } + + virtual void start_of_simulation() + { + sc_assert( sc_get_status() == SC_START_OF_SIMULATION ); + print_static_phase_stats( "start_of_simulation" ); + + // ignored - issues warning + register_simulation_phase_callback( SC_ELABORATION ); + } + + virtual void end_of_simulation() + { + sc_assert( sc_get_status() == SC_END_OF_SIMULATION ); + print_static_phase_stats( "end_of_simulation" ); + } + + + +private: + phase_cb_mask cb_mask, old_mask; + sc_dt::uint64 cb_count, timed_count, delta_count; + sc_event ev; +}; + + +int sc_main(int, char*[]) +{ + // don't run without callbacks enabled + sc_report_handler::set_actions( SC_ID_PHASE_CALLBACKS_UNSUPPORTED_ + , SC_DEFAULT_ERROR_ACTIONS ); + + phase_tracer pt; + sc_start(); + return 0; +} diff --git a/src/systemc/tests/systemc/kernel/phase_callbacks/test05/golden/simulation_callbacks.log b/src/systemc/tests/systemc/kernel/phase_callbacks/test05/golden/simulation_callbacks.log new file mode 100644 index 000000000..85fefc217 --- /dev/null +++ b/src/systemc/tests/systemc/kernel/phase_callbacks/test05/golden/simulation_callbacks.log @@ -0,0 +1,109 @@ +SystemC Simulation +top.phase_tracer_0: phase callback SC_END_OF_UPDATE: 0 s -> pending activity: MAX +top.phase_tracer_0: phase callback SC_END_OF_UPDATE: 0 s -> pending activity: 0 s +top.timed: 0 s: 0/0 +top.phase_tracer_0: phase callback SC_END_OF_UPDATE: 0 s -> pending activity: 0 s +top.delta: 0 s: 1/1 +top.phase_tracer_0: phase callback SC_END_OF_UPDATE: 0 s -> pending activity: 1 ns +top.phase_tracer_0: phase callback SC_BEFORE_TIMESTEP: 0 s -> pending activity: 1 ns +top.timed: 1 ns: 1/0 +top.phase_tracer_0: phase callback SC_END_OF_UPDATE: 1 ns -> pending activity: 0 s +top.delta: 1 ns: 2/1 +top.phase_tracer_0: phase callback SC_END_OF_UPDATE: 1 ns -> pending activity: 1 ns +top.phase_tracer_0: phase callback SC_BEFORE_TIMESTEP: 1 ns -> pending activity: 1 ns +top.timed: 2 ns: 2/0 +top.phase_tracer_0: phase callback SC_END_OF_UPDATE: 2 ns -> pending activity: 0 s +top.delta: 2 ns: 3/1 +top.phase_tracer_0: phase callback SC_END_OF_UPDATE: 2 ns -> pending activity: 1 ns +top.phase_tracer_0: phase callback SC_BEFORE_TIMESTEP: 2 ns -> pending activity: 1 ns +top.timed: 3 ns: 3/0 +top.phase_tracer_0: phase callback SC_END_OF_UPDATE: 3 ns -> pending activity: 0 s +top.delta: 3 ns: 4/1 +top.phase_tracer_0: phase callback SC_END_OF_UPDATE: 3 ns -> pending activity: 1 ns +top.phase_tracer_0: phase callback SC_BEFORE_TIMESTEP: 3 ns -> pending activity: 1 ns +top.timed: 4 ns: 4/0 +top.phase_tracer_0: phase callback SC_END_OF_UPDATE: 4 ns -> pending activity: 0 s +top.delta: 4 ns: 5/1 +top.phase_tracer_0: phase callback SC_END_OF_UPDATE: 4 ns -> pending activity: 1 ns +top.phase_tracer_0: phase callback SC_BEFORE_TIMESTEP: 4 ns -> pending activity: 1 ns +top.timed: 5 ns: 5/0 +top.phase_tracer_0: phase callback SC_END_OF_UPDATE: 5 ns -> pending activity: 0 s +top.delta: 5 ns: 6/1 +top.phase_tracer_0: phase callback SC_END_OF_UPDATE: 5 ns -> pending activity: 1 ns +top.phase_tracer_0: phase callback SC_BEFORE_TIMESTEP: 5 ns -> pending activity: 1 ns +top.timed: 6 ns: 6/0 +top.phase_tracer_0: phase callback SC_END_OF_UPDATE: 6 ns -> pending activity: 0 s +top.delta: 6 ns: 7/1 +top.phase_tracer_0: phase callback SC_END_OF_UPDATE: 6 ns -> pending activity: 1 ns +top.phase_tracer_0: phase callback SC_BEFORE_TIMESTEP: 6 ns -> pending activity: 1 ns +top.timed: 7 ns: 7/0 +top.phase_tracer_0: phase callback SC_END_OF_UPDATE: 7 ns -> pending activity: 0 s +top.delta: 7 ns: 8/1 +top.phase_tracer_0: phase callback SC_END_OF_UPDATE: 7 ns -> pending activity: 1 ns +top.phase_tracer_0: phase callback SC_BEFORE_TIMESTEP: 7 ns -> pending activity: 1 ns +top.timed: 8 ns: 8/0 +top.phase_tracer_0: phase callback SC_END_OF_UPDATE: 8 ns -> pending activity: 0 s +top.delta: 8 ns: 9/1 +top.phase_tracer_0: phase callback SC_END_OF_UPDATE: 8 ns -> pending activity: 1 ns +top.phase_tracer_0: phase callback SC_BEFORE_TIMESTEP: 8 ns -> pending activity: 1 ns +top.timed: 9 ns: 9/0 +top.phase_tracer_0: phase callback SC_END_OF_UPDATE: 9 ns -> pending activity: 0 s +top.delta: 9 ns: 10/1 +top.phase_tracer_0: phase callback SC_END_OF_UPDATE: 9 ns -> pending activity: 1 ns +top.phase_tracer_0: phase callback SC_BEFORE_TIMESTEP: 9 ns -> pending activity: 1 ns +top.phase_tracer_0: phase callback SC_END_OF_UPDATE: 10 ns -> pending activity: MAX +top.phase_tracer_0: phase callback SC_END_OF_UPDATE: 10 ns -> pending activity: 0 s +top.timed: 10 ns: 0/0 +top.phase_tracer_0: phase callback SC_END_OF_UPDATE: 10 ns -> pending activity: 0 s +top.delta: 10 ns: 1/1 +top.phase_tracer_0: phase callback SC_END_OF_UPDATE: 10 ns -> pending activity: 1 ns +top.phase_tracer_0: phase callback SC_BEFORE_TIMESTEP: 10 ns -> pending activity: 1 ns +top.timed: 11 ns: 1/0 +top.phase_tracer_0: phase callback SC_END_OF_UPDATE: 11 ns -> pending activity: 0 s +top.delta: 11 ns: 2/1 +top.phase_tracer_0: phase callback SC_END_OF_UPDATE: 11 ns -> pending activity: 1 ns +top.phase_tracer_0: phase callback SC_BEFORE_TIMESTEP: 11 ns -> pending activity: 1 ns +top.timed: 12 ns: 2/0 +top.phase_tracer_0: phase callback SC_END_OF_UPDATE: 12 ns -> pending activity: 0 s +top.delta: 12 ns: 3/1 +top.phase_tracer_0: phase callback SC_END_OF_UPDATE: 12 ns -> pending activity: 1 ns +top.phase_tracer_0: phase callback SC_BEFORE_TIMESTEP: 12 ns -> pending activity: 1 ns +top.timed: 13 ns: 3/0 +top.phase_tracer_0: phase callback SC_END_OF_UPDATE: 13 ns -> pending activity: 0 s +top.delta: 13 ns: 4/1 +top.phase_tracer_0: phase callback SC_END_OF_UPDATE: 13 ns -> pending activity: 1 ns +top.phase_tracer_0: phase callback SC_BEFORE_TIMESTEP: 13 ns -> pending activity: 1 ns +top.timed: 14 ns: 4/0 +top.phase_tracer_0: phase callback SC_END_OF_UPDATE: 14 ns -> pending activity: 0 s +top.delta: 14 ns: 5/1 +top.phase_tracer_0: phase callback SC_END_OF_UPDATE: 14 ns -> pending activity: 1 ns +top.phase_tracer_0: phase callback SC_BEFORE_TIMESTEP: 14 ns -> pending activity: 1 ns +top.timed: 15 ns: 5/0 +top.phase_tracer_0: phase callback SC_END_OF_UPDATE: 15 ns -> pending activity: 0 s +top.delta: 15 ns: 6/1 +top.phase_tracer_0: phase callback SC_END_OF_UPDATE: 15 ns -> pending activity: 1 ns +top.phase_tracer_0: phase callback SC_BEFORE_TIMESTEP: 15 ns -> pending activity: 1 ns +top.timed: 16 ns: 6/0 +top.phase_tracer_0: phase callback SC_END_OF_UPDATE: 16 ns -> pending activity: 0 s +top.delta: 16 ns: 7/1 +top.phase_tracer_0: phase callback SC_END_OF_UPDATE: 16 ns -> pending activity: 1 ns +top.phase_tracer_0: phase callback SC_BEFORE_TIMESTEP: 16 ns -> pending activity: 1 ns +top.timed: 17 ns: 7/0 +top.phase_tracer_0: phase callback SC_END_OF_UPDATE: 17 ns -> pending activity: 0 s +top.delta: 17 ns: 8/1 +top.phase_tracer_0: phase callback SC_END_OF_UPDATE: 17 ns -> pending activity: 1 ns +top.phase_tracer_0: phase callback SC_BEFORE_TIMESTEP: 17 ns -> pending activity: 1 ns +top.timed: 18 ns: 8/0 +top.phase_tracer_0: phase callback SC_END_OF_UPDATE: 18 ns -> pending activity: 0 s +top.delta: 18 ns: 9/1 +top.phase_tracer_0: phase callback SC_END_OF_UPDATE: 18 ns -> pending activity: 1 ns +top.phase_tracer_0: phase callback SC_BEFORE_TIMESTEP: 18 ns -> pending activity: 1 ns +top.timed: 19 ns: 9/0 +top.phase_tracer_0: phase callback SC_END_OF_UPDATE: 19 ns -> pending activity: 0 s +top.delta: 19 ns: 10/1 +top.phase_tracer_0: phase callback SC_END_OF_UPDATE: 19 ns -> pending activity: 1 ns +top.phase_tracer_0: phase callback SC_BEFORE_TIMESTEP: 19 ns -> pending activity: 1 ns +top.phase_tracer_0: phase callback SC_END_OF_UPDATE: 20 ns -> pending activity: MAX + +Info: /OSCI/SystemC: Simulation stopped by user. +top.phase_tracer_0: [destructor]: 65 callbacks called. diff --git a/src/systemc/tests/systemc/kernel/phase_callbacks/test05/simulation_callbacks.cpp b/src/systemc/tests/systemc/kernel/phase_callbacks/test05/simulation_callbacks.cpp new file mode 100644 index 000000000..03dde6ccc --- /dev/null +++ b/src/systemc/tests/systemc/kernel/phase_callbacks/test05/simulation_callbacks.cpp @@ -0,0 +1,242 @@ +/***************************************************************************** + + Licensed to Accellera Systems Initiative Inc. (Accellera) under one or + more contributor license agreements. See the NOTICE file distributed + with this work for additional information regarding copyright ownership. + Accellera licenses this file to you under the Apache License, Version 2.0 + (the "License"); you may not use this file except in compliance with the + License. You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + + Unless required by applicable law or agreed to in writing, software + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or + implied. See the License for the specific language governing + permissions and limitations under the License. + + *****************************************************************************/ + +/***************************************************************************** + + simulation_callbacks.cpp -- Test of simulation phase callbacks + + Note: requires simulation phase callback support enabled in the kernel + SC_ENABLE_SIMULATION_PHASE_CALLBACKS / --enable-phase-callbacks + + Original Author: Philipp A. Hartmann, OFFIS, 2013-05-17 + + *****************************************************************************/ + +/***************************************************************************** + + MODIFICATION LOG - modifiers, enter your name, affiliation, date and + changes you are making here. + + Name, Affiliation, Date: + Description of Modification: + + *****************************************************************************/ + +#include <systemc.h> + +#ifdef BENCHMARK +# include "rusage_timer.h" +# define ROUNDS 20 +# define NUM_TIMED_TRIGGERS 2000000 +# define NUM_DELTA_TRIGGERS 50 +# define VERBOSE 0 +#else +# define ROUNDS 2 +# define NUM_TIMED_TRIGGERS 10 +# define NUM_DELTA_TRIGGERS 1 +# define VERBOSE 1 +#endif + +#ifndef REGISTER_CALLBACKS +# define REGISTER_CALLBACKS 1 +#endif +#ifndef EXTRA_METHOD +# define EXTRA_METHOD 0 +#endif + +#define TIMED_THREAD 1 + +#if TIMED_THREAD +# define TIMED_WAIT wait +# define TIMED_PROCESS SC_THREAD +#else +# define TIMED_WAIT next_trigger +# define TIMED_PROCESS SC_METHOD +#endif + +#if REGISTER_CALLBACKS +//# define CALLBACK_MASK ( SC_END_OF_EVALUATION ) +//# define CALLBACK_MASK ( SC_END_OF_UPDATE ) +//# define CALLBACK_MASK ( SC_BEFORE_TIMESTEP ) +# define CALLBACK_MASK ( SC_END_OF_UPDATE | SC_BEFORE_TIMESTEP ) +#else +// SC_RUNNING (for EXTRA_METHOD) +# define CALLBACK_MASK ( SC_RUNNING ) +#endif + +static const sc_dt::uint64 max_rounds = ROUNDS; +static const sc_dt::uint64 max_timed_triggers = NUM_TIMED_TRIGGERS; +static const sc_dt::uint64 max_delta_triggers = NUM_DELTA_TRIGGERS; +static const sc_time delay(1, SC_NS); + +SC_MODULE(phase_tracer) +{ + SC_HAS_PROCESS(phase_tracer); + phase_tracer( sc_module_name = sc_core::sc_gen_unique_name("phase_tracer") ) + : cb_mask(CALLBACK_MASK), cb_count(0) + { +#if REGISTER_CALLBACKS + cb_mask = register_simulation_phase_callback( CALLBACK_MASK ); +#endif + } + + virtual void simulation_phase_callback() + { + cb_count++; + +# if VERBOSE + { + std::string ttp; + if( !sc_pending_activity() ) { + ttp = "MAX"; + } else { + ttp = sc_time_to_pending_activity().to_string(); + } + std::cout << name() + << ": phase callback " + << sc_get_status() + << ": " << sc_time_stamp() + << " -> pending activity: " << ttp + << std::endl; + } +# endif + sc_assert( cb_mask & sc_get_status() ); + } + + ~phase_tracer() + { print_static_phase_stats( "[destructor]" ); } + + void print_static_phase_stats( const char* phase ) + { +#if VERBOSE + std::cout << name() + << ": " << phase << ": " + << cb_count << " callbacks called." + << std::endl; +#endif + } + +private: + unsigned cb_mask; + sc_dt::uint64 cb_count; +}; + +SC_MODULE(activities) +{ + SC_CTOR(activities) + : timed_count(), delta_count() + { + TIMED_PROCESS(timed); + sensitive << timed_ev; + dont_initialize(); + SC_METHOD(delta); + sensitive << delta_ev; + dont_initialize(); +#if EXTRA_METHOD + SC_METHOD(extra); + sensitive << timed_ev; + dont_initialize(); +#endif + } + + void notify_round() + { timed_ev.notify(SC_ZERO_TIME); } + +private: + void timed() + { +# if TIMED_THREAD + while(1) +# endif + { + if( timed_count >= max_timed_triggers ) { + timed_count = 0; + TIMED_WAIT(); + } else { + verbose(); + ++timed_count; + if( max_delta_triggers ) + delta_ev.notify(SC_ZERO_TIME); + timed_ev.notify(delay); + TIMED_WAIT(); + } + } + } + + void delta() + { + ++delta_count; + verbose(); + if( delta_count >= max_delta_triggers ) { + delta_count = 0; + } else { + delta_ev.notify(SC_ZERO_TIME); + } + } + + void extra() + { + if( sc_pending_activity_at_current_time() ) { + pt.simulation_phase_callback(); + next_trigger(SC_ZERO_TIME); + } else if (sc_time_to_pending_activity()== sc_max_time()-sc_time_stamp() ) { + next_trigger(); + } else { + pt.simulation_phase_callback(); + next_trigger(sc_time_to_pending_activity()); + } + } + + void verbose() + { +#if VERBOSE + std::cout + << sc_get_current_process_handle().name() + << ": " << sc_time_stamp() + << ": " << timed_count << "/" << delta_count + << std::endl; +#endif + } + +private: + phase_tracer pt; + sc_dt::uint64 timed_count, delta_count; + sc_event timed_ev, delta_ev; +}; + + +int sc_main(int, char*[]) +{ + activities top("top"); + + sc_start(SC_ZERO_TIME); + for(unsigned i=0; i<max_rounds; ++i) + { +#ifdef BENCHMARK + rusage_timer timer; +#endif + top.notify_round(); + sc_start(); +#ifdef BENCHMARK + std::cout << timer.to_seconds() << std::endl; +#endif + } + sc_stop(); + return 0; +} |