1 #include "scd_chan_wrapper.h"
6 #include "scd_logging.h"
9 scd_chan_wrapper::scd_chan_wrapper(scd_simulator& sim, const std::string& name,
10 sc_prim_channel& chan):
11 _sim(sim), _name(name), _is_initialized(false),
12 _is_writing(false), _is_reading(false)
16 _chan_in = &dynamic_cast<scd_rem_chan_in_if&>(chan);
17 } catch (std::bad_cast e)
24 _chan_out = &dynamic_cast<scd_rem_chan_out_if&>(chan);
25 } catch (std::bad_cast e)
30 if (_chan_in == NULL && _chan_out == NULL)
31 scd_warn("channel \"" + _name + "\" is not a remote channel");
35 scd_chan_wrapper::~scd_chan_wrapper()
37 if ( _is_initialized )
39 _sim.get_poller().remove_handler(*this);
46 bool scd_chan_wrapper::is_initialized() const { return _is_initialized; }
49 const std::string& scd_chan_wrapper::get_name() const { return _name; }
52 void scd_chan_wrapper::connect(scd_socket* sock)
54 assert(!_is_initialized);
57 _is_initialized = true;
59 sock_ev flags = SOCK_EV_CLOSE;
62 flags |= SOCK_EV_READ;
65 _sim.get_poller().register_handler(*this, flags);
70 void scd_chan_wrapper::process()
72 // check if channel has data to send
73 if (_chan_out != NULL && _is_initialized )
75 if (!_is_writing && _socket->is_valid() && _chan_out->available() > 0 )
77 // register write event
79 _sim.get_poller().get_ev(*this, events);
80 events |= SOCK_EV_WRITE;
81 _sim.get_poller().set_ev( *this, events );
86 // check if channel has data to read
87 if (_chan_in != NULL && _is_initialized )
89 if (!_is_reading && _socket->is_valid() && _chan_in->free() > 0 )
91 // register read event
93 _sim.get_poller().get_ev(*this, events);
94 events |= SOCK_EV_READ;
95 _sim.get_poller().set_ev( *this, events );
103 void scd_chan_wrapper::close()
111 void scd_chan_wrapper::handle_sock_ev(sock_ev events)
113 if (events & SOCK_EV_CLOSE)
115 scd_debug("channel \"" + _name + "\" closed connection");
116 _sim.get_poller().set_ev(*this, 0);
117 _sim.get_cont_man().set_fail();
122 if (events & SOCK_EV_READ)
127 if (events & SOCK_EV_WRITE)
132 } // handle_sock_ev()
135 const scd_socket& scd_chan_wrapper::get_sock() { return *_socket; }
138 void scd_chan_wrapper::_read_event()
140 size_t free = _chan_in->free();
142 /* receive portions as long as they can be received */
143 size_t recv = 0xFF; //dummy
144 while ( free != 0 && recv != 0)
146 free = ( free < SCD_CHAN_BUFLEN ) ? free : SCD_CHAN_BUFLEN ;
147 recv = _socket->recv(_buf, free);
149 _chan_in->receive(_buf, recv);
150 free = _chan_in->free();
156 _sim.get_poller().get_ev(*this, events);
157 events &= ~SOCK_EV_READ;
158 _sim.get_poller().set_ev(*this, events );
163 if (!_socket->is_valid())
165 scd_debug("channel \"" + _name + "\" closed connection");
166 _sim.get_poller().set_ev(*this, 0);
167 _sim.get_cont_man().set_fail();
171 } // end _read_event()
174 void scd_chan_wrapper::_write_event()
176 /* send portions as long as they can be sent */
177 size_t sent = 0xFF; //dummy
180 sent = _socket->send( _chan_out->send(), _chan_out->available() );
182 _chan_out->remove(sent);
185 if (_chan_out->available() == 0)
188 _sim.get_poller().get_ev(*this, events);
189 events &= ~SOCK_EV_WRITE;
190 _sim.get_poller().set_ev(*this, events );
195 if (!_socket->is_valid())
197 scd_debug("channel \"" + _name + "\" closed connection");
198 _sim.get_poller().set_ev(*this, 0);
199 _sim.get_cont_man().set_fail();