Revised OpenFlow Library  v0.6.0dev
 All Classes Files Functions Variables Friends Groups Pages
crofshim.h
1 /*
2  * crofshim.h
3  *
4  * Created on: 22.01.2014
5  * Author: andi
6  */
7 
8 #ifndef CROFSHIM_H_
9 #define CROFSHIM_H_
10 
11 #include <map>
12 
13 #include "rofl/common/croflexception.h"
14 #include "rofl/common/crofsock.h"
15 #include "rofl/common/csocket.h"
16 #include "rofl/common/caddress.h"
17 #include "rofl/common/ctspaddress.h"
18 
19 namespace rofl {
20 namespace common {
21 
22 class eRofShimBase : public RoflException {
23 public:
24  eRofShimBase(const std::string& __arg) : RoflException(__arg) {};
25 };
27 public:
28  eRofShimNotFound(const std::string& __arg) : eRofShimBase(__arg) {};
29 };
30 
31 
32 class crofshim :
33  public crofsock_env,
34  public csocket_env
35 {
36 public:
37 
41  crofshim() {};
42 
46  virtual
47  ~crofshim() {
48  clear_active_rofsockets_in4();
49  clear_active_rofsockets_in6();
50  clear_listening_sockets_in4();
51  clear_listening_sockets_in6();
52  };
53 
54 public:
55 
59  void
60  connect(enum rofl::csocket::socket_type_t socket_type, cparams const& socket_params) {
61  (new crofsock(this))->connect(socket_type, socket_params);
62  };
63 
64 public:
65 
69  void
70  clear_active_rofsockets_in4() {
71  for (std::map<rofl::common::ctspaddress_in4, crofsock*>::iterator
72  it = rofsockets_in4.begin(); it != rofsockets_in4.end(); ++it) {
73  delete it->second;
74  }
75  };
76 
80  crofsock&
81  set_active_rofsocket_in4(const rofl::common::ctspaddress_in4& addr) {
82  if (rofsockets_in4.find(addr) == rofsockets_in4.end()) {
83  throw eRofShimNotFound("crofshim::set_active_rofsocket_in4()");
84  }
85  return *(rofsockets_in4[addr]);
86  };
87 
91  const crofsock&
92  get_active_rofsocket_in4(const rofl::common::ctspaddress_in4& addr) const {
93  if (rofsockets_in4.find(addr) == rofsockets_in4.end()) {
94  throw eRofShimNotFound("crofshim::set_active_rofsocket_in4()");
95  }
96  return *(rofsockets_in4.at(addr));
97  };
98 
102  void
103  drop_active_rofsocket_in4(const rofl::common::ctspaddress_in4& addr) {
104  if (rofsockets_in4.find(addr) == rofsockets_in4.end()) {
105  return;
106  }
107  delete rofsockets_in4[addr];
108  rofsockets_in4.erase(addr);
109  };
110 
114  bool
115  has_active_rofsocket_in4(const rofl::common::ctspaddress_in4& addr) const {
116  return (not (rofsockets_in4.find(addr) == rofsockets_in4.end()));
117  };
118 
119 public:
120 
124  void
125  clear_active_rofsockets_in6() {
126  for (std::map<rofl::common::ctspaddress_in6, crofsock*>::iterator
127  it = rofsockets_in6.begin(); it != rofsockets_in6.end(); ++it) {
128  delete it->second;
129  }
130  };
131 
135  crofsock&
136  set_active_rofsocket_in6(const rofl::common::ctspaddress_in6& addr) {
137  if (rofsockets_in6.find(addr) == rofsockets_in6.end()) {
138  throw eRofShimNotFound("crofshim::set_active_rofsocket_in6()");
139  }
140  return *(rofsockets_in6[addr]);
141  };
142 
146  const crofsock&
147  get_active_rofsocket_in6(const rofl::common::ctspaddress_in6& addr) const {
148  if (rofsockets_in6.find(addr) == rofsockets_in6.end()) {
149  throw eRofShimNotFound("crofshim::set_active_rofsocket_in6()");
150  }
151  return *(rofsockets_in6.at(addr));
152  };
153 
157  void
158  drop_active_rofsocket_in6(const rofl::common::ctspaddress_in6& addr) {
159  if (rofsockets_in6.find(addr) == rofsockets_in6.end()) {
160  return;
161  }
162  delete rofsockets_in6[addr];
163  rofsockets_in6.erase(addr);
164  };
165 
169  bool
170  has_active_rofsocket_in6(const rofl::common::ctspaddress_in6& addr) const {
171  return (not (rofsockets_in6.find(addr) == rofsockets_in6.end()));
172  };
173 
174 public:
175 
179  void
180  clear_listening_sockets_in4() {
181  for (std::map<rofl::common::ctspaddress_in4, csocket*>::iterator
182  it = sockets_in4.begin(); it != sockets_in4.end(); ++it) {
183  delete it->second;
184  }
185  };
186 
191  add_listening_socket_in4(
192  enum rofl::csocket::socket_type_t socket_type,
193  const rofl::cparams& socket_params) {
194 
196  rofl::caddress_in4(socket_params.get_param(rofl::csocket::PARAM_KEY_LOCAL_HOSTNAME).get_string()),
197  atoi(socket_params.get_param(rofl::csocket::PARAM_KEY_LOCAL_PORT).get_string().c_str()));
198 
199  if (sockets_in4.find(addr) != sockets_in4.end()) {
200  delete sockets_in4[addr];
201  }
202  (sockets_in4[addr] = csocket::csocket_factory(socket_type, this))->listen(socket_params);
203  return *(sockets_in4[addr]);
204  };
205 
210  set_listening_socket_in4(
211  enum rofl::csocket::socket_type_t socket_type,
212  const rofl::cparams& socket_params) {
213 
215  rofl::caddress_in4(socket_params.get_param(rofl::csocket::PARAM_KEY_LOCAL_HOSTNAME).get_string()),
216  atoi(socket_params.get_param(rofl::csocket::PARAM_KEY_LOCAL_PORT).get_string().c_str()));
217 
218  if (sockets_in4.find(addr) == sockets_in4.end()) {
219  (sockets_in4[addr] = csocket::csocket_factory(socket_type, this))->listen(socket_params);
220  }
221  return *(sockets_in4[addr]);
222  };
223 
228  set_listening_socket_in4(
229  const rofl::common::ctspaddress_in4& addr) {
230  if (sockets_in4.find(addr) == sockets_in4.end()) {
231  throw eRofShimNotFound("crofshim::set_listening_socket_in4()");
232  }
233  return *(sockets_in4[addr]);
234  };
235 
239  const rofl::csocket&
240  get_listening_socket_in4(
241  const rofl::common::ctspaddress_in4& addr) const {
242  if (sockets_in4.find(addr) == sockets_in4.end()) {
243  throw eRofShimNotFound("crofshim::get_listening_socket_in4()");
244  }
245  return *(sockets_in4.at(addr));
246  };
247 
251  void
252  drop_listening_socket_in4(const rofl::common::ctspaddress_in4& addr) {
253  if (sockets_in4.find(addr) == sockets_in4.end()) {
254  return;
255  }
256  delete sockets_in4[addr];
257  sockets_in4.erase(addr);
258  };
259 
263  bool
264  has_listening_socket_in4(const rofl::common::ctspaddress_in4& addr) const {
265  return (not (sockets_in4.find(addr) == sockets_in4.end()));
266  };
267 
268 public:
269 
273  void
274  clear_listening_sockets_in6() {
275  for (std::map<rofl::common::ctspaddress_in6, csocket*>::iterator
276  it = sockets_in6.begin(); it != sockets_in6.end(); ++it) {
277  delete it->second;
278  }
279  };
280 
285  add_listening_socket_in6(
286  enum rofl::csocket::socket_type_t socket_type,
287  const rofl::cparams& socket_params) {
288 
290  rofl::caddress_in6(socket_params.get_param(rofl::csocket::PARAM_KEY_LOCAL_HOSTNAME).get_string()),
291  atoi(socket_params.get_param(rofl::csocket::PARAM_KEY_LOCAL_PORT).get_string().c_str()));
292 
293  if (sockets_in6.find(addr) != sockets_in6.end()) {
294  delete sockets_in6[addr];
295  }
296  (sockets_in6[addr] = csocket::csocket_factory(socket_type, this))->listen(socket_params);
297  return *(sockets_in6[addr]);
298  };
299 
304  set_listening_socket_in6(
305  const rofl::common::ctspaddress_in6& addr,
306  enum rofl::csocket::socket_type_t socket_type,
307  const rofl::cparams& socket_params) {
308  if (sockets_in6.find(addr) == sockets_in6.end()) {
309  (sockets_in6[addr] = csocket::csocket_factory(socket_type, this))->listen(socket_params);
310  }
311  return *(sockets_in6[addr]);
312  };
313 
318  set_listening_socket_in6(
319  const rofl::common::ctspaddress_in6& addr) {
320  if (sockets_in6.find(addr) == sockets_in6.end()) {
321  throw eRofShimNotFound("crofshim::set_listening_socket_in6()");
322  }
323  return *(sockets_in6[addr]);
324  };
325 
329  const rofl::csocket&
330  get_listening_socket_in6(
331  const rofl::common::ctspaddress_in6& addr) const {
332  if (sockets_in6.find(addr) == sockets_in6.end()) {
333  throw eRofShimNotFound("crofshim::get_listening_socket_in6()");
334  }
335  return *(sockets_in6.at(addr));
336  };
337 
341  void
342  drop_listening_socket_in6(const rofl::common::ctspaddress_in6& addr) {
343  if (sockets_in6.find(addr) == sockets_in6.end()) {
344  return;
345  }
346  delete sockets_in6[addr];
347  sockets_in6.erase(addr);
348  };
349 
353  bool
354  has_listening_socket_in6(const rofl::common::ctspaddress_in6& addr) const {
355  return (not (sockets_in6.find(addr) == sockets_in6.end()));
356  };
357 
358 protected:
359 
363  virtual void
364  handle_message(
366  delete msg; /* to be overwritten */
367  };
368 
372  virtual void
373  handle_message(
375  delete msg; /* to be overwritten */
376  };
377 
381  virtual void
382  send_message(
383  crofsock *rofsock, rofl::openflow::cofmsg *msg) {
384  try {
385  rofsock->send_message(msg);
386  } catch (rofl::eSocketTxAgainCongestion& e) {
387 
388  } catch (rofl::eSocketTxAgainPacketDropped& e) {
389 
390  } catch (rofl::eSocketTxAgainTxQueueFull& e) {
391 
392  } catch (rofl::eSocketTxAgain& e) {
393 
394  }
395  };
396 
397 private:
398 
399  friend class crofsock_env;
400 
404  virtual void
405  handle_connect_refused(crofsock& rofsock) {
406  delete &rofsock;
407  };
408 
412  virtual void
413  handle_connect_failed(crofsock& rofsock) {
414  delete &rofsock;
415  };
416 
420  virtual void
421  handle_connected(crofsock& rofsock) {
422  std::cerr << "RADDR:" << rofsock.get_socket().get_raddr();
423  switch (rofsock.get_socket().get_domain()) {
424  case AF_INET: {
427  rofsock.get_socket().get_raddr().ca_s4addr, rofsock.get_socket().get_raddr().salen),
428  be16toh(rofsock.get_socket().get_raddr().ca_s4addr->sin_port));
429  if (rofsockets_in4.find(addr) != rofsockets_in4.end()) {
430  delete rofsockets_in4[addr];
431  }
432  rofsockets_in4[addr] = &rofsock;
433  } break;
434  case AF_INET6: {
437  rofsock.get_socket().get_raddr().ca_s6addr, rofsock.get_socket().get_raddr().salen),
438  be16toh(rofsock.get_socket().get_raddr().ca_s6addr->sin6_port));
439  if (rofsockets_in6.find(addr) != rofsockets_in6.end()) {
440  delete rofsockets_in6[addr];
441  }
442  rofsockets_in6[addr] = &rofsock;
443  } break;
444  default: {
445  delete &rofsock;
446  };
447  }
448  };
449 
450  virtual void
451  handle_closed(crofsock& rofsock) {
452  switch (rofsock.get_socket().get_domain()) {
453  case AF_INET: {
456  rofsock.get_socket().get_raddr().ca_s4addr, rofsock.get_socket().get_raddr().salen),
457  be16toh(rofsock.get_socket().get_raddr().ca_s4addr->sin_port));
458  rofsockets_in4.erase(addr);
459  } break;
460  case AF_INET6: {
463  rofsock.get_socket().get_raddr().ca_s6addr, rofsock.get_socket().get_raddr().salen),
464  be16toh(rofsock.get_socket().get_raddr().ca_s6addr->sin6_port));
465  rofsockets_in6.erase(addr);
466  } break;
467  default: {
468  };
469  }
470  delete &rofsock;
471  };
472 
473  virtual void
474  handle_write(crofsock& rofsock) {
475  /* TODO: handle situation after congestion */
476  };
477 
478  virtual void
479  recv_message(crofsock& rofsock, rofl::openflow::cofmsg *msg) {
480  switch (rofsock.get_socket().get_domain()) {
481  case AF_INET: {
484  rofsock.get_socket().get_raddr().ca_s4addr, rofsock.get_socket().get_raddr().salen),
485  be16toh(rofsock.get_socket().get_raddr().ca_s4addr->sin_port));
486  handle_message(addr, msg);
487  } break;
488  case AF_INET6: {
491  rofsock.get_socket().get_raddr().ca_s6addr, rofsock.get_socket().get_raddr().salen),
492  be16toh(rofsock.get_socket().get_raddr().ca_s6addr->sin6_port));
493  handle_message(addr, msg);
494  } break;
495  default: {
496  delete msg;
497  };
498  }
499  }
500 
501 private:
502 
503  friend class csocket_env;
504 
505  virtual void
506  handle_listen(csocket& socket, int newsd) {
507  (new crofsock(this))->accept(socket.get_socket_type(), socket.get_socket_params(), newsd);
508  };
509 
510  virtual void
511  handle_accepted(csocket& socket) {};
512 
513  virtual void
514  handle_accept_refused(csocket& socket) {};
515 
516  virtual void
517  handle_connected(csocket& socket) {};
518 
519  virtual void
520  handle_connect_refused(csocket& socket) {};
521 
522  virtual void
523  handle_connect_failed(csocket& socket) {};
524 
525  virtual void
526  handle_read(csocket& socket) {};
527 
528  virtual void
529  handle_write(csocket& socket) {};
530 
531  virtual void
532  handle_closed(csocket& socket) {};
533 
534 private:
535 
536  std::map<rofl::common::ctspaddress_in4, csocket*> sockets_in4; // listening csocket instances
537  std::map<rofl::common::ctspaddress_in6, csocket*> sockets_in6; // listening csocket instances
538  std::map<rofl::common::ctspaddress_in4, crofsock*> rofsockets_in4;
539  std::map<rofl::common::ctspaddress_in6, crofsock*> rofsockets_in6;
540 };
541 
542 }; // end of namespace openflow
543 }; // end of namespace rofl
544 
545 #endif /* CROFSHIM_H_ */
546 
Definition: cparams.h:20
Definition: csocket.h:34
Definition: crofshim.h:22
A single socket.
Definition: csocket.h:182
Definition: caddress.h:589
Definition: csocket.h:32
Definition: csocket.h:33
A socket capable of talking OpenFlow via TCP and vice versa.
Definition: crofsock.h:111
Definition: ctspaddress.h:169
Definition: crofshim.h:32
Definition: csocket.h:35
Definition: caddress.h:415
An abstract interface defining the consumer side of a csocket.
Definition: csocket.h:58
Definition: crofshim.h:26
Definition: ctspaddress.h:88
Environment expected by a rofl::crofsock instance.
Definition: crofsock.h:76
Definition: croflexception.h:27
Definition: cofmsg.h:62