1/*****************************************************************************
2
3  Licensed to Accellera Systems Initiative Inc. (Accellera) under one or
4  more contributor license agreements.  See the NOTICE file distributed
5  with this work for additional information regarding copyright ownership.
6  Accellera licenses this file to you under the Apache License, Version 2.0
7  (the "License"); you may not use this file except in compliance with the
8  License.  You may obtain a copy of the License at
9
10    http://www.apache.org/licenses/LICENSE-2.0
11
12  Unless required by applicable law or agreed to in writing, software
13  distributed under the License is distributed on an "AS IS" BASIS,
14  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
15  implied.  See the License for the specific language governing
16  permissions and limitations under the License.
17
18 *****************************************************************************/
19
20/*****************************************************************************
21
22  sc_module.cpp -- Base class of all sequential and combinational processes.
23
24  Original Author: Stan Y. Liao, Synopsys, Inc.
25
26  CHANGE LOG AT THE END OF THE FILE
27 *****************************************************************************/
28
29
30#include <cassert>
31#include <math.h>
32#include <stddef.h>
33#include <stdio.h>
34
35#include "sysc/kernel/sc_event.h"
36#include "sysc/kernel/sc_kernel_ids.h"
37#include "sysc/kernel/sc_module.h"
38#include "sysc/kernel/sc_module_registry.h"
39#include "sysc/kernel/sc_name_gen.h"
40#include "sysc/kernel/sc_object_manager.h"
41#include "sysc/kernel/sc_process.h"
42#include "sysc/kernel/sc_process_handle.h"
43#include "sysc/kernel/sc_simcontext.h"
44#include "sysc/kernel/sc_simcontext_int.h"
45#include "sysc/kernel/sc_object_int.h"
46#include "sysc/kernel/sc_reset.h"
47#include "sysc/communication/sc_communication_ids.h"
48#include "sysc/communication/sc_interface.h"
49#include "sysc/communication/sc_port.h"
50#include "sysc/communication/sc_signal.h"
51#include "sysc/communication/sc_signal_ports.h"
52#include "sysc/utils/sc_utils_ids.h"
53#include "sysc/utils/sc_iostream.h"
54
55namespace sc_core {
56
57// ----------------------------------------------------------------------------
58//  CLASS : sc_module_dynalloc_list
59//
60//  Garbage collection for modules dynamically allocated with SC_NEW.
61// ----------------------------------------------------------------------------
62
63class sc_module_dynalloc_list
64{
65public:
66
67    sc_module_dynalloc_list() : m_list()
68        {}
69
70    ~sc_module_dynalloc_list();
71
72    void add( sc_module* p )
73        { m_list.push_back( p ); }
74
75private:
76
77    sc_plist<sc_module*> m_list;
78};
79
80
81//------------------------------------------------------------------------------
82//"~sc_module_dynalloc_list"
83//
84// Note we clear the m_parent field for the module being deleted. This because
85// we process the list front to back so the parent has already been deleted,
86// and we don't want ~sc_object() to try to access the parent which may
87// contain garbage.
88//------------------------------------------------------------------------------
89sc_module_dynalloc_list::~sc_module_dynalloc_list()
90{
91    sc_plist<sc_module*>::iterator it( m_list );
92    while( ! it.empty() ) {
93        (*it)->m_parent = 0;
94        delete *it;
95        it ++;
96    }
97}
98
99
100// ----------------------------------------------------------------------------
101
102sc_module*
103sc_module_dynalloc( sc_module* module_ )
104{
105    static sc_module_dynalloc_list dynalloc_list;
106    dynalloc_list.add( module_ );
107    return module_;
108}
109
110
111// ----------------------------------------------------------------------------
112//  STRUCT : sc_bind_proxy
113//
114//  Struct for temporarily storing a pointer to an interface or port.
115//  Used for positional binding.
116// ----------------------------------------------------------------------------
117
118sc_bind_proxy::sc_bind_proxy()
119: iface( 0 ),
120  port( 0 )
121{}
122
123sc_bind_proxy::sc_bind_proxy( sc_interface& iface_ )
124: iface( &iface_ ),
125  port( 0 )
126{}
127
128sc_bind_proxy::sc_bind_proxy( sc_port_base& port_ )
129: iface( 0 ),
130  port( &port_ )
131{}
132
133
134const sc_bind_proxy SC_BIND_PROXY_NIL;
135
136
137// ----------------------------------------------------------------------------
138//  CLASS : sc_module
139//
140//  Base class for all structural entities.
141// ----------------------------------------------------------------------------
142
143void
144sc_module::sc_module_init()
145{
146    simcontext()->get_module_registry()->insert( *this );
147    simcontext()->hierarchy_push( this );
148    m_end_module_called = false;
149    m_module_name_p = 0;
150    m_port_vec = new std::vector<sc_port_base*>;
151    m_port_index = 0;
152    m_name_gen = new sc_name_gen;
153}
154
155/*
156 *  This form of the constructor assumes that the user has
157 *  used an sc_module_name parameter for his/her constructor.
158 *  That parameter object has been pushed onto the stack,
159 *  and can be looked up by calling the
160 *  top_of_module_name_stack() function of the object manager.
161 *  This technique has two advantages:
162 *
163 *  1) The user no longer has to write sc_module(name) in the
164 *     constructor initializer.
165 *  2) The user no longer has to call end_module() at the end
166 *     of the constructor -- a common negligence.
167 *
168 *  But it is important to note that sc_module_name may be used
169 *  in the user's constructor's parameter. If it is used anywhere
170 *  else, unexpected things will happen. The error-checking
171 *  mechanism builtin here cannot hope to catch all misuses.
172 *
173 */
174
175sc_module::sc_module()
176: sc_object(::sc_core::sc_get_curr_simcontext()
177                  ->get_object_manager()
178                  ->top_of_module_name_stack()
179                  ->operator const char*()),
180  sensitive(this),
181  sensitive_pos(this),
182  sensitive_neg(this),
183  m_end_module_called(false),
184  m_port_vec(),
185  m_port_index(0),
186  m_name_gen(0),
187  m_module_name_p(0)
188{
189    /* When this form is used, we better have a fresh sc_module_name
190       on the top of the stack */
191    sc_module_name* mod_name =
192        simcontext()->get_object_manager()->top_of_module_name_stack();
193    if (0 == mod_name || 0 != mod_name->m_module_p)
194        SC_REPORT_ERROR( SC_ID_SC_MODULE_NAME_REQUIRED_, 0 );
195    sc_module_init();
196    mod_name->set_module( this );
197    m_module_name_p = mod_name; // must come after sc_module_init call.
198}
199
200sc_module::sc_module( const sc_module_name& )
201: sc_object(::sc_core::sc_get_curr_simcontext()
202                  ->get_object_manager()
203                  ->top_of_module_name_stack()
204                  ->operator const char*()),
205  sensitive(this),
206  sensitive_pos(this),
207  sensitive_neg(this),
208  m_end_module_called(false),
209  m_port_vec(),
210  m_port_index(0),
211  m_name_gen(0),
212  m_module_name_p(0)
213{
214    /* For those used to the old style of passing a name to sc_module,
215       this constructor will reduce the chance of making a mistake */
216
217    /* When this form is used, we better have a fresh sc_module_name
218       on the top of the stack */
219    sc_module_name* mod_name =
220        simcontext()->get_object_manager()->top_of_module_name_stack();
221    if (0 == mod_name || 0 != mod_name->m_module_p)
222      SC_REPORT_ERROR( SC_ID_SC_MODULE_NAME_REQUIRED_, 0 );
223    sc_module_init();
224    mod_name->set_module( this );
225    m_module_name_p = mod_name; // must come after sc_module_init call.
226}
227
228/* --------------------------------------------------------------------
229 *
230 * Deprecated constructors:
231 *   sc_module( const char* )
232 *   sc_module( const std::string& )
233 */
234sc_module::sc_module( const char* nm )
235: sc_object(nm),
236  sensitive(this),
237  sensitive_pos(this),
238  sensitive_neg(this),
239  m_end_module_called(false),
240  m_port_vec(),
241  m_port_index(0),
242  m_name_gen(0),
243  m_module_name_p(0)
244{
245    SC_REPORT_WARNING( SC_ID_BAD_SC_MODULE_CONSTRUCTOR_, nm );
246    sc_module_init();
247}
248
249sc_module::sc_module( const std::string& s )
250: sc_object( s.c_str() ),
251  sensitive(this),
252  sensitive_pos(this),
253  sensitive_neg(this),
254  m_end_module_called(false),
255  m_port_vec(),
256  m_port_index(0),
257  m_name_gen(0),
258  m_module_name_p(0)
259{
260    SC_REPORT_WARNING( SC_ID_BAD_SC_MODULE_CONSTRUCTOR_, s.c_str() );
261    sc_module_init();
262}
263
264/* -------------------------------------------------------------------- */
265
266sc_module::~sc_module()
267{
268    delete m_port_vec;
269    delete m_name_gen;
270    orphan_child_objects();
271    if ( m_module_name_p )
272    {
273	m_module_name_p->clear_module( this ); // must be before end_module()
274    	end_module();
275    }
276    simcontext()->get_module_registry()->remove( *this );
277}
278
279
280const ::std::vector<sc_object*>&
281sc_module::get_child_objects() const
282{
283    return m_child_objects;
284}
285
286// set SC_THREAD asynchronous reset sensitivity
287
288void
289sc_module::async_reset_signal_is( const sc_in<bool>& port, bool level )
290{
291	sc_reset::reset_signal_is(true, port, level);
292}
293
294void
295sc_module::async_reset_signal_is( const sc_inout<bool>& port, bool level )
296{
297	sc_reset::reset_signal_is(true, port, level);
298}
299
300void
301sc_module::async_reset_signal_is( const sc_out<bool>& port, bool level )
302{
303	sc_reset::reset_signal_is(true, port, level);
304}
305
306void
307sc_module::async_reset_signal_is(const sc_signal_in_if<bool>& iface, bool level)
308{
309	sc_reset::reset_signal_is(true, iface, level);
310}
311
312void
313sc_module::end_module()
314{
315    if( ! m_end_module_called ) {
316	/* TBD: Can check here to alert the user that end_module
317                was not called for a previous module. */
318	(void)sc_get_curr_simcontext()->hierarchy_pop();
319	sc_get_curr_simcontext()->reset_curr_proc();
320	sensitive.reset();
321	sensitive_pos.reset();
322	sensitive_neg.reset();
323	m_end_module_called = true;
324	m_module_name_p = 0; // make sure we are not called in ~sc_module().
325    }
326}
327
328
329// to prevent initialization for SC_METHODs and SC_THREADs
330
331void
332sc_module::dont_initialize()
333{
334    sc_process_handle last_proc = sc_get_last_created_process_handle();
335    last_proc.dont_initialize( true );
336}
337
338// set SC_THREAD synchronous reset sensitivity
339
340void
341sc_module::reset_signal_is( const sc_in<bool>& port, bool level )
342{
343	sc_reset::reset_signal_is(false, port, level);
344}
345
346void
347sc_module::reset_signal_is( const sc_inout<bool>& port, bool level )
348{
349	sc_reset::reset_signal_is(false, port, level);
350}
351
352void
353sc_module::reset_signal_is( const sc_out<bool>& port, bool level )
354{
355	sc_reset::reset_signal_is(false, port, level);
356}
357
358void
359sc_module::reset_signal_is( const sc_signal_in_if<bool>& iface, bool level )
360{
361	sc_reset::reset_signal_is(false, iface, level);
362}
363
364// to generate unique names for objects in an MT-Safe way
365
366const char*
367sc_module::gen_unique_name( const char* basename_, bool preserve_first )
368{
369    return m_name_gen->gen_unique_name( basename_, preserve_first );
370}
371
372
373// called by construction_done
374
375void
376sc_module::before_end_of_elaboration()
377{}
378
379// We push the sc_module instance onto the stack of open objects so
380// that any objects that are created in before_end_of_elaboration have
381// the proper parent. After the call we pop the hierarchy.
382void
383sc_module::construction_done()
384{
385    hierarchy_scope scope(this);
386    before_end_of_elaboration();
387}
388
389// called by elaboration_done (does nothing by default)
390
391void
392sc_module::end_of_elaboration()
393{}
394
395
396// We push the sc_module instance onto the stack of open objects so
397// that any objects that are created in end_of_elaboration have
398// the proper parent. After the call we pop the hierarchy.
399void
400sc_module::elaboration_done( bool& error_ )
401{
402    if( ! m_end_module_called ) {
403	char msg[BUFSIZ];
404	std::sprintf( msg, "module '%s'", name() );
405	SC_REPORT_WARNING( SC_ID_END_MODULE_NOT_CALLED_, msg );
406	if( error_ ) {
407	    SC_REPORT_WARNING( SC_ID_HIER_NAME_INCORRECT_, 0 );
408	}
409	error_ = true;
410    }
411    hierarchy_scope scope(this);
412    end_of_elaboration();
413}
414
415// called by start_simulation (does nothing by default)
416
417void
418sc_module::start_of_simulation()
419{}
420
421void
422sc_module::start_simulation()
423{
424    hierarchy_scope scope(this);
425    start_of_simulation();
426}
427
428// called by simulation_done (does nothing by default)
429
430void
431sc_module::end_of_simulation()
432{}
433
434void
435sc_module::simulation_done()
436{
437    hierarchy_scope scope(this);
438    end_of_simulation();
439}
440
441void
442sc_module::set_stack_size( std::size_t size )
443{
444    sc_process_handle  proc_h(
445    	sc_is_running() ?
446	sc_get_current_process_handle() :
447	sc_get_last_created_process_handle()
448    );
449    sc_thread_handle thread_h;  // Current process as thread.
450
451
452    thread_h = (sc_thread_handle)proc_h;
453    if ( thread_h )
454    {
455	thread_h->set_stack_size( size );
456    }
457    else
458    {
459	SC_REPORT_WARNING( SC_ID_SET_STACK_SIZE_, 0 );
460    }
461}
462
463
464int
465sc_module::append_port( sc_port_base* port_ )
466{
467    int index = m_port_vec->size();
468    m_port_vec->push_back( port_ );
469    return index;
470}
471
472
473// positional binding methods
474
475static void sc_warn_arrow_arrow_bind()
476{
477    static bool warn_arrow_arrow_bind=true;
478    if ( warn_arrow_arrow_bind )
479    {
480    	warn_arrow_arrow_bind = false;
481	SC_REPORT_INFO(SC_ID_IEEE_1666_DEPRECATION_,
482	    "positional binding using << or , is deprecated, use () instead.");
483    }
484}
485
486sc_module&
487sc_module::operator << ( sc_interface& interface_ )
488{
489    sc_warn_arrow_arrow_bind();
490    positional_bind(interface_);
491    return *this;
492}
493
494sc_module&
495sc_module::operator << ( sc_port_base& port_ )
496{
497    sc_warn_arrow_arrow_bind();
498    positional_bind(port_);
499    return *this;
500}
501
502
503void
504sc_module::positional_bind( sc_interface& interface_ )
505{
506    if( m_port_index == (int)m_port_vec->size() ) {
507	char msg[BUFSIZ];
508	if( m_port_index == 0 ) {
509	    std::sprintf( msg, "module `%s' has no ports", name() );
510	} else {
511	    std::sprintf( msg, "all ports of module `%s' are bound", name() );
512	}
513	SC_REPORT_ERROR( SC_ID_BIND_IF_TO_PORT_, msg );
514    }
515    int status = (*m_port_vec)[m_port_index]->pbind( interface_ );
516    if( status != 0 ) {
517	char msg[BUFSIZ];
518	switch( status ) {
519	case 1:
520	    std::sprintf( msg, "port %d of module `%s' is already bound",
521		     m_port_index, name() );
522	    break;
523	case 2:
524	    std::sprintf( msg, "type mismatch on port %d of module `%s'",
525		     m_port_index, name() );
526	    break;
527	default:
528	    std::sprintf( msg, "unknown error" );
529	    break;
530	}
531	SC_REPORT_ERROR( SC_ID_BIND_IF_TO_PORT_, msg );
532    }
533    ++ m_port_index;
534}
535
536void
537sc_module::positional_bind( sc_port_base& port_ )
538{
539    if( m_port_index == (int)m_port_vec->size() ) {
540	char msg[BUFSIZ];
541	if( m_port_index == 0 ) {
542	    std::sprintf( msg, "module `%s' has no ports", name() );
543	} else {
544	    std::sprintf( msg, "all ports of module `%s' are bound", name() );
545	}
546	SC_REPORT_ERROR( SC_ID_BIND_PORT_TO_PORT_, msg );
547    }
548    int status = (*m_port_vec)[m_port_index]->pbind( port_ );
549    if( status != 0 ) {
550	char msg[BUFSIZ];
551	switch( status ) {
552	case 1:
553	    std::sprintf( msg, "port %d of module `%s' is already bound",
554		     m_port_index, name() );
555	    break;
556	case 2:
557	    std::sprintf( msg, "type mismatch on port %d of module `%s'",
558		     m_port_index, name() );
559	    break;
560	default:
561	    std::sprintf( msg, "unknown error" );
562	    break;
563	}
564	SC_REPORT_ERROR( SC_ID_BIND_PORT_TO_PORT_, msg );
565    }
566    ++ m_port_index;
567}
568
569
570#define TRY_BIND( p )                                                         \
571    if( (p).iface != 0 ) {                                                    \
572        positional_bind( *(p).iface );                                        \
573    } else if( (p).port != 0 ) {                                              \
574        positional_bind( *(p).port );                                         \
575    } else {                                                                  \
576        return;                                                               \
577    }
578
579
580void
581sc_module::operator () ( const sc_bind_proxy& p001,
582			 const sc_bind_proxy& p002,
583			 const sc_bind_proxy& p003,
584			 const sc_bind_proxy& p004,
585			 const sc_bind_proxy& p005,
586			 const sc_bind_proxy& p006,
587			 const sc_bind_proxy& p007,
588			 const sc_bind_proxy& p008,
589			 const sc_bind_proxy& p009,
590			 const sc_bind_proxy& p010,
591			 const sc_bind_proxy& p011,
592			 const sc_bind_proxy& p012,
593			 const sc_bind_proxy& p013,
594			 const sc_bind_proxy& p014,
595			 const sc_bind_proxy& p015,
596			 const sc_bind_proxy& p016,
597			 const sc_bind_proxy& p017,
598			 const sc_bind_proxy& p018,
599			 const sc_bind_proxy& p019,
600			 const sc_bind_proxy& p020,
601			 const sc_bind_proxy& p021,
602			 const sc_bind_proxy& p022,
603			 const sc_bind_proxy& p023,
604			 const sc_bind_proxy& p024,
605			 const sc_bind_proxy& p025,
606			 const sc_bind_proxy& p026,
607			 const sc_bind_proxy& p027,
608			 const sc_bind_proxy& p028,
609			 const sc_bind_proxy& p029,
610			 const sc_bind_proxy& p030,
611			 const sc_bind_proxy& p031,
612			 const sc_bind_proxy& p032,
613			 const sc_bind_proxy& p033,
614			 const sc_bind_proxy& p034,
615			 const sc_bind_proxy& p035,
616			 const sc_bind_proxy& p036,
617			 const sc_bind_proxy& p037,
618			 const sc_bind_proxy& p038,
619			 const sc_bind_proxy& p039,
620			 const sc_bind_proxy& p040,
621			 const sc_bind_proxy& p041,
622			 const sc_bind_proxy& p042,
623			 const sc_bind_proxy& p043,
624			 const sc_bind_proxy& p044,
625			 const sc_bind_proxy& p045,
626			 const sc_bind_proxy& p046,
627			 const sc_bind_proxy& p047,
628			 const sc_bind_proxy& p048,
629			 const sc_bind_proxy& p049,
630			 const sc_bind_proxy& p050,
631			 const sc_bind_proxy& p051,
632			 const sc_bind_proxy& p052,
633			 const sc_bind_proxy& p053,
634			 const sc_bind_proxy& p054,
635			 const sc_bind_proxy& p055,
636			 const sc_bind_proxy& p056,
637			 const sc_bind_proxy& p057,
638			 const sc_bind_proxy& p058,
639			 const sc_bind_proxy& p059,
640			 const sc_bind_proxy& p060,
641			 const sc_bind_proxy& p061,
642			 const sc_bind_proxy& p062,
643			 const sc_bind_proxy& p063,
644			 const sc_bind_proxy& p064 )
645{
646    static bool warn_only_once=true;
647    if ( m_port_index > 0 && warn_only_once )
648    {
649        warn_only_once = false;
650	SC_REPORT_INFO(SC_ID_IEEE_1666_DEPRECATION_,
651	 "multiple () binding deprecated, use explicit port binding instead." );
652    }
653
654    TRY_BIND( p001 );
655    TRY_BIND( p002 );
656    TRY_BIND( p003 );
657    TRY_BIND( p004 );
658    TRY_BIND( p005 );
659    TRY_BIND( p006 );
660    TRY_BIND( p007 );
661    TRY_BIND( p008 );
662    TRY_BIND( p009 );
663    TRY_BIND( p010 );
664    TRY_BIND( p011 );
665    TRY_BIND( p012 );
666    TRY_BIND( p013 );
667    TRY_BIND( p014 );
668    TRY_BIND( p015 );
669    TRY_BIND( p016 );
670    TRY_BIND( p017 );
671    TRY_BIND( p018 );
672    TRY_BIND( p019 );
673    TRY_BIND( p020 );
674    TRY_BIND( p021 );
675    TRY_BIND( p022 );
676    TRY_BIND( p023 );
677    TRY_BIND( p024 );
678    TRY_BIND( p025 );
679    TRY_BIND( p026 );
680    TRY_BIND( p027 );
681    TRY_BIND( p028 );
682    TRY_BIND( p029 );
683    TRY_BIND( p030 );
684    TRY_BIND( p031 );
685    TRY_BIND( p032 );
686    TRY_BIND( p033 );
687    TRY_BIND( p034 );
688    TRY_BIND( p035 );
689    TRY_BIND( p036 );
690    TRY_BIND( p037 );
691    TRY_BIND( p038 );
692    TRY_BIND( p039 );
693    TRY_BIND( p040 );
694    TRY_BIND( p041 );
695    TRY_BIND( p042 );
696    TRY_BIND( p043 );
697    TRY_BIND( p044 );
698    TRY_BIND( p045 );
699    TRY_BIND( p046 );
700    TRY_BIND( p047 );
701    TRY_BIND( p048 );
702    TRY_BIND( p049 );
703    TRY_BIND( p050 );
704    TRY_BIND( p051 );
705    TRY_BIND( p052 );
706    TRY_BIND( p053 );
707    TRY_BIND( p054 );
708    TRY_BIND( p055 );
709    TRY_BIND( p056 );
710    TRY_BIND( p057 );
711    TRY_BIND( p058 );
712    TRY_BIND( p059 );
713    TRY_BIND( p060 );
714    TRY_BIND( p061 );
715    TRY_BIND( p062 );
716    TRY_BIND( p063 );
717    TRY_BIND( p064 );
718}
719
720} // namespace sc_core
721
722/*****************************************************************************
723
724  MODIFICATION LOG - modifiers, enter your name, affiliation, date and
725  changes you are making here.
726
727      Name, Affiliation, Date: Ali Dasdan, Synopsys, Inc.
728  Description of Modification: - Implementation of operator() and operator,
729                                 positional connection method.
730                               - Implementation of error checking in
731                                 operator<<'s.
732                               - Implementation of the function test_module_prm.
733                               - Implementation of set_stack_size().
734
735      Name, Affiliation, Date: Andy Goodrich, Forte Design Systems 20 May 2003
736  Description of Modification: Inherit from sc_process_host
737
738      Name, Affiliation, Date: Bishnupriya Bhattacharya, Cadence Design Systems,
739                               25 August, 2003
740  Description of Modification: dont_initialize() uses
741                               sc_get_last_created_process_handle() instead of
742                               sc_get_current_process_b()
743
744      Name, Affiliation, Date: Andy Goodrich, Forte Design Systems 25 Mar 2003
745  Description of Modification: Fixed bug in SC_NEW, see comments on
746                               ~sc_module_dynalloc_list below.
747
748
749 *****************************************************************************/
750
751
752// $Log: sc_module.cpp,v $
753// Revision 1.14  2011/08/29 18:04:32  acg
754//  Philipp A. Hartmann: miscellaneous clean ups.
755//
756// Revision 1.13  2011/08/26 20:46:10  acg
757//  Andy Goodrich: moved the modification log to the end of the file to
758//  eliminate source line number skew when check-ins are done.
759//
760// Revision 1.12  2011/08/24 22:05:51  acg
761//  Torsten Maehne: initialization changes to remove warnings.
762//
763// Revision 1.11  2011/03/05 19:44:20  acg
764//  Andy Goodrich: changes for object and event naming and structures.
765//
766// Revision 1.10  2011/02/18 20:27:14  acg
767//  Andy Goodrich: Updated Copyrights.
768//
769// Revision 1.9  2011/02/16 22:37:30  acg
770//  Andy Goodrich: clean up to remove need for ps_disable_pending.
771//
772// Revision 1.8  2011/02/14 17:51:40  acg
773//  Andy Goodrich: proper pushing an poppping of the module hierarchy for
774//  start_of_simulation() and end_of_simulation.
775//
776// Revision 1.7  2011/02/13 21:47:37  acg
777//  Andy Goodrich: update copyright notice.
778//
779// Revision 1.6  2011/01/25 20:50:37  acg
780//  Andy Goodrich: changes for IEEE 1666 2011.
781//
782// Revision 1.5  2009/05/22 16:06:29  acg
783//  Andy Goodrich: process control updates.
784//
785// Revision 1.4  2008/11/17 15:57:15  acg
786//  Andy Goodrich: added deprecation message for sc_module(const char*)
787//
788// Revision 1.3  2008/05/22 17:06:25  acg
789//  Andy Goodrich: updated copyright notice to include 2008.
790//
791// Revision 1.2  2007/05/17 20:16:33  acg
792//  Andy Goodrich: changes for beta release to LWG.
793//
794// Revision 1.1.1.1  2006/12/15 20:20:05  acg
795// SystemC 2.3
796//
797// Revision 1.9  2006/12/02 20:58:18  acg
798//  Andy Goodrich: updates from 2.2 for IEEE 1666 support.
799//
800// Revision 1.8  2006/03/21 00:00:34  acg
801//   Andy Goodrich: changed name of sc_get_current_process_base() to be
802//   sc_get_current_process_b() since its returning an sc_process_b instance.
803//
804// Revision 1.7  2006/03/14 23:56:58  acg
805//   Andy Goodrich: This fixes a bug when an exception is thrown in
806//   sc_module::sc_module() for a dynamically allocated sc_module
807//   object. We are calling sc_module::end_module() on a module that has
808//   already been deleted. The scenario runs like this:
809//
810//   a) the sc_module constructor is entered
811//   b) the exception is thrown
812//   c) the exception processor deletes the storage for the sc_module
813//   d) the stack is unrolled causing the sc_module_name instance to be deleted
814//   e) ~sc_module_name() calls end_module() with its pointer to the sc_module
815//   f) because the sc_module has been deleted its storage is corrupted,
816//      either by linking it to a free space chain, or by reuse of some sort
817//   g) the m_simc field is garbage
818//   h) the m_object_manager field is also garbage
819//   i) an exception occurs
820//
821//   This does not happen for automatic sc_module instances since the
822//   storage for the module is not reclaimed its just part of the stack.
823//
824//   I am fixing this by having the destructor for sc_module clear the
825//   module pointer in its sc_module_name instance. That cuts things at
826//   step (e) above, since the pointer will be null if the module has
827//   already been deleted. To make sure the module stack is okay, I call
828//   end-module() in ~sc_module in the case where there is an
829//   sc_module_name pointer lying around.
830//
831// Revision 1.6  2006/01/26 21:04:54  acg
832//  Andy Goodrich: deprecation message changes and additional messages.
833//
834// Revision 1.5  2006/01/25 00:31:19  acg
835//  Andy Goodrich: Changed over to use a standard message id of
836//  SC_ID_IEEE_1666_DEPRECATION for all deprecation messages.
837//
838// Revision 1.4  2006/01/24 20:49:05  acg
839// Andy Goodrich: changes to remove the use of deprecated features within the
840// simulator, and to issue warning messages when deprecated features are used.
841//
842// Revision 1.3  2006/01/13 18:44:29  acg
843// Added $Log to record CVS changes into the source.
844//
845
846// Taf!
847