17 #ifndef _SCC_OBSERVER_H_
18 #define _SCC_OBSERVER_H_
22 #include <sysc/communication/sc_signal_ifs.h>
23 #include <sysc/datatypes/int/sc_nbdefs.h>
24 #include <sysc/kernel/sc_dynamic_processes.h>
25 #include <sysc/kernel/sc_process.h>
26 #include <sysc/kernel/sc_process_handle.h>
27 #include <sysc/kernel/sc_ver.h>
58 virtual bool notify() = 0;
78 virtual notification_handle* observe(sc_dt::sc_int_base
const& o, std::string
const& nm) = 0;
79 virtual notification_handle* observe(sc_dt::sc_uint_base
const& o, std::string
const& nm) = 0;
81 virtual notification_handle* observe(sc_dt::sc_unsigned
const& o, std::string
const& nm) = 0;
84 virtual notification_handle* observe(sc_dt::sc_fxval_fast
const& o, std::string
const& nm) = 0;
86 virtual notification_handle* observe(sc_dt::sc_fxnum_fast
const& o, std::string
const& nm) = 0;
88 virtual notification_handle* observe(sc_dt::sc_bv_base
const& o, std::string
const& nm) = 0;
89 virtual notification_handle* observe(sc_dt::sc_lv_base
const& o, std::string
const& nm) = 0;
90 #if(SYSTEMC_VERSION >= 20171012)
92 virtual notification_handle* observe(sc_core::sc_event
const& o, std::string
const& nm) = 0;
97 #define DECL_REGISTER_METHOD_A(tp) \
98 inline observer::notification_handle* observe(observer* obs, tp const& o, std::string const& nm) { return obs->observe(o, nm); }
99 #if(SYSTEMC_VERSION >= 20171012)
100 DECL_REGISTER_METHOD_A(sc_core::sc_event)
101 DECL_REGISTER_METHOD_A(sc_core::sc_time)
103 DECL_REGISTER_METHOD_A(
bool)
104 DECL_REGISTER_METHOD_A(sc_dt::sc_bit)
105 DECL_REGISTER_METHOD_A(sc_dt::sc_logic)
107 DECL_REGISTER_METHOD_A(
unsigned char)
108 DECL_REGISTER_METHOD_A(
unsigned short)
109 DECL_REGISTER_METHOD_A(
unsigned int)
110 DECL_REGISTER_METHOD_A(
unsigned long)
111 DECL_REGISTER_METHOD_A(
char)
112 DECL_REGISTER_METHOD_A(
short)
113 DECL_REGISTER_METHOD_A(
int)
114 DECL_REGISTER_METHOD_A(
long)
115 DECL_REGISTER_METHOD_A(sc_dt::int64)
116 DECL_REGISTER_METHOD_A(sc_dt::uint64)
118 DECL_REGISTER_METHOD_A(
float)
119 DECL_REGISTER_METHOD_A(
double)
120 DECL_REGISTER_METHOD_A(sc_dt::sc_int_base)
121 DECL_REGISTER_METHOD_A(sc_dt::sc_uint_base)
122 DECL_REGISTER_METHOD_A(sc_dt::sc_signed)
123 DECL_REGISTER_METHOD_A(sc_dt::sc_unsigned)
125 DECL_REGISTER_METHOD_A(sc_dt::sc_fxval)
126 DECL_REGISTER_METHOD_A(sc_dt::sc_fxval_fast)
127 DECL_REGISTER_METHOD_A(sc_dt::sc_fxnum)
128 DECL_REGISTER_METHOD_A(sc_dt::sc_fxnum_fast)
130 DECL_REGISTER_METHOD_A(sc_dt::sc_bv_base)
131 DECL_REGISTER_METHOD_A(sc_dt::sc_lv_base)
133 #undef DECL_REGISTER_METHOD_A
135 template <
class T>
inline void sc_trace(sc_core::sc_trace_file* tf,
const sc_core::sc_signal_in_if<T>&
object,
const char* name) {
136 if(
auto* obs =
dynamic_cast<observer*
>(tf)) {
137 if(
auto* handle = obs->observe(
object.read(), std::string(name))) {
138 sc_core::sc_spawn_options scopts;
139 scopts.spawn_method();
140 scopts.set_sensitivity(&
object.default_event());
143 if(!handle->notify())
144 sc_core::sc_get_current_process_handle().disable();
149 sc_core::sc_trace(tf,
object.read(), name);
152 template <
class T>
inline void sc_trace(sc_core::sc_trace_file* tf,
const sc_core::sc_signal_in_if<T>&
object,
const std::string& name) {
153 sc_trace(tf,
object, name.c_str());
156 template <
class T>
inline void sc_trace(sc_core::sc_trace_file* tf,
const sc_core::sc_in<T>& port,
char const* name) {
157 const sc_core::sc_signal_in_if<T>* iface = 0;
158 if(sc_core::sc_get_curr_simcontext()->elaboration_done())
159 iface =
dynamic_cast<const sc_core::sc_signal_in_if<T>*
>(port.get_interface());
161 if(
auto* obs =
dynamic_cast<observer*
>(tf)) {
162 if(
auto* handle = obs->observe(port.read(), name)) {
163 sc_core::sc_spawn_options scopts;
164 scopts.spawn_method();
165 scopts.set_sensitivity(&port.default_event());
168 if(!handle->notify())
169 sc_core::sc_get_current_process_handle().disable();
174 sc_trace(tf, iface->read(), name);
176 port.add_trace_internal(tf, name);
179 template <
class T>
inline void sc_trace(sc_core::sc_trace_file* tf,
const sc_core::sc_in<T>& port,
const std::string& name) {
180 sc_trace(tf, port, name.c_str());
183 template <
class T>
inline void sc_trace(sc_core::sc_trace_file* tf,
const sc_core::sc_inout<T>& port,
char const* name) {
184 const sc_core::sc_signal_in_if<T>* iface = 0;
185 if(sc_core::sc_get_curr_simcontext()->elaboration_done())
186 iface =
dynamic_cast<const sc_core::sc_signal_in_if<T>*
>(port.get_interface());
188 if(
auto* obs =
dynamic_cast<observer*
>(tf)) {
189 if(
auto* handle = obs->observe(port.read(), name)) {
190 sc_core::sc_spawn_options scopts;
191 scopts.spawn_method();
192 scopts.set_sensitivity(&port.default_event());
195 if(!handle->notify())
196 sc_core::sc_get_current_process_handle().disable();
201 sc_trace(tf, iface->read(), name);
203 port.add_trace_internal(tf, name);
206 template <
class T>
inline void sc_trace(sc_core::sc_trace_file* tf,
const sc_core::sc_inout<T>& port,
const std::string& name) {
207 sc_trace(tf, port, name.c_str());
210 #define DEFN_TRACE_FUNC_REF_A(tp) \
211 inline void sc_trace(sc_core::sc_trace_file* tf, const tp& object, const std::string& name) { sc_core::sc_trace(tf, object, name); }
213 #define DEFN_TRACE_FUNC_PTR_A(tp) \
214 inline void sc_trace(sc_core::sc_trace_file* tf, const tp* object, const std::string& name) { sc_core::sc_trace(tf, object, name); }
216 #define DEFN_TRACE_FUNC_A(tp) \
217 DEFN_TRACE_FUNC_REF_A(tp) \
218 DEFN_TRACE_FUNC_PTR_A(tp)
220 #define DEFN_TRACE_FUNC_REF_B(tp) \
221 inline void sc_trace(sc_core::sc_trace_file* tf, const tp& object, const std::string& name, int width) { \
222 sc_core::sc_trace(tf, object, name, width); \
224 inline void sc_trace(sc_core::sc_trace_file* tf, const tp& object, const std::string& name) { \
225 sc_core::sc_trace(tf, object, name, sizeof(tp) * 8); \
228 #define DEFN_TRACE_FUNC_PTR_B(tp) \
229 inline void sc_trace(sc_core::sc_trace_file* tf, const tp* object, const std::string& name, int width) { \
230 sc_core::sc_trace(tf, object, name, width); \
232 inline void sc_trace(sc_core::sc_trace_file* tf, const tp* object, const std::string& name) { \
233 sc_core::sc_trace(tf, object, name, sizeof(tp) * 8); \
236 #define DEFN_TRACE_FUNC_B(tp) \
237 DEFN_TRACE_FUNC_REF_B(tp) \
238 DEFN_TRACE_FUNC_PTR_B(tp)
241 DEFN_TRACE_FUNC_A(sc_core::sc_event)
242 DEFN_TRACE_FUNC_A(sc_core::sc_time)
245 DEFN_TRACE_FUNC_A(
bool)
246 DEFN_TRACE_FUNC_A(
float)
247 DEFN_TRACE_FUNC_A(
double)
249 DEFN_TRACE_FUNC_B(
unsigned char)
250 DEFN_TRACE_FUNC_B(
unsigned short)
251 DEFN_TRACE_FUNC_B(
unsigned int)
252 DEFN_TRACE_FUNC_B(
unsigned long)
253 #ifdef SYSTEMC_64BIT_PATCHES
254 DEFN_TRACE_FUNC_B(
unsigned long long)
256 DEFN_TRACE_FUNC_B(
char)
257 DEFN_TRACE_FUNC_B(
short)
258 DEFN_TRACE_FUNC_B(
int)
259 DEFN_TRACE_FUNC_B(
long)
260 #ifdef SYSTEMC_64BIT_PATCHES
261 DEFN_TRACE_FUNC_B(
long long)
263 DEFN_TRACE_FUNC_B(sc_dt::int64)
264 DEFN_TRACE_FUNC_B(sc_dt::uint64)
266 DEFN_TRACE_FUNC_A(sc_dt::sc_bit)
267 DEFN_TRACE_FUNC_A(sc_dt::sc_logic)
269 DEFN_TRACE_FUNC_A(sc_dt::sc_int_base)
270 DEFN_TRACE_FUNC_A(sc_dt::sc_uint_base)
271 DEFN_TRACE_FUNC_A(sc_dt::sc_signed)
272 DEFN_TRACE_FUNC_A(sc_dt::sc_unsigned)
274 DEFN_TRACE_FUNC_A(sc_dt::sc_bv_base)
275 DEFN_TRACE_FUNC_A(sc_dt::sc_lv_base)
279 DEFN_TRACE_FUNC_A(sc_dt::sc_fxval)
280 DEFN_TRACE_FUNC_A(sc_dt::sc_fxval_fast)
281 DEFN_TRACE_FUNC_A(sc_dt::sc_fxnum)
282 DEFN_TRACE_FUNC_A(sc_dt::sc_fxnum_fast)
286 #undef DEFN_TRACE_FUNC_REF_A
287 #undef DEFN_TRACE_FUNC_PTR_A
288 #undef DEFN_TRACE_FUNC_A
290 #undef DEFN_TRACE_FUNC_REF_B
291 #undef DEFN_TRACE_FUNC_PTR_B
292 #undef DEFN_TRACE_FUNC_B
A handle to be used be the observed object to notify the observer about a change.
The interface defining an observer.