PageRenderTime 38ms CodeModel.GetById 15ms RepoModel.GetById 1ms app.codeStats 0ms

/elements/userlevel/socket.hh

https://github.com/bhesmans/click
C++ Header | 247 lines | 67 code | 18 blank | 162 comment | 0 complexity | e8ba4bb2048da3b1ff39292dfdef5052 MD5 | raw file
Possible License(s): GPL-2.0, BSD-3-Clause
  1. // -*- mode: c++; c-basic-offset: 2 -*-
  2. #ifndef CLICK_SOCKET_HH
  3. #define CLICK_SOCKET_HH
  4. #include <click/element.hh>
  5. #include <click/string.hh>
  6. #include <click/task.hh>
  7. #include <click/timer.hh>
  8. #include <click/notifier.hh>
  9. #include "../ip/iproutetable.hh"
  10. #include <sys/un.h>
  11. CLICK_DECLS
  12. /*
  13. =c
  14. Socket("TCP", IP, PORTNUMBER [, LOCALIP] [, LOCALPORTNUMBER] [, I<KEYWORDS>])
  15. Socket("UDP", IP, PORTNUMBER [, LOCALIP] [, LOCALPORTNUMBER] [, I<KEYWORDS>])
  16. Socket("UNIX", FILENAME [, LOCALFILENAME] [, I<KEYWORDS>])
  17. Socket("UNIX_DGRAM", FILENAME [, LOCALFILENAME] [, I<KEYWORDS>])
  18. =s comm
  19. a socket transport (user-level)
  20. =d
  21. Transports packets over various types of sockets. Packets do not flow
  22. through Socket elements (i.e., Socket is an "x/y" element). Instead,
  23. input packets are sent to a remote host or process, and packets
  24. received from the remote host or process are emitted on the output.
  25. A Socket element of type "TCP" or "UNIX" may be either a server (the
  26. default if CLIENT is not set) or a client (if CLIENT is set or if the
  27. element has no outputs). If a server, the specified address/port/file
  28. is bound and connections are accepted one at a time. If a client, a
  29. connection attempt is made to the specified address/port/file during
  30. element initialization.
  31. A Socket element of type "UDP" or "UNIX_DGRAM" may also be either a
  32. server or client. However, because datagram sockets are not connection
  33. oriented, a datagram server may receive (and thus emit) packets from
  34. multiple remote hosts or processes. If a server, input packets are
  35. sent to the last remote host or process to send a packet to the
  36. server. If a client, input packets are sent to the specified
  37. address/port/file.
  38. For convenience, if a client UDP Socket is configured with a zero IP
  39. address, the Socket will send input packets to the destination IP
  40. annotation of each packet.
  41. If "LOCALIP"/"LOCALPORTNUMBER" or "LOCALFILENAME" is specified, CLIENT
  42. is assumed if not set and the specified local address/port/file will
  43. be bound before the connection attempt is made. If CLIENT is set to
  44. false, any "LOCALIP"/"LOCALPORTNUMBER" and "LOCALFILENAME" arguments
  45. are ignored.
  46. Socket inputs are agnostic, i.e., they may be either "pull" or
  47. "push". If pushed, packets will block on the underlying socket;
  48. otherwise, the socket will pull packets as it can accept them. For
  49. best performance, place a Notifier element (such as NotifierQueue)
  50. upstream of a "pull" Socket.
  51. Keyword arguments are:
  52. =over 8
  53. =item SNAPLEN
  54. Unsigned integer. Maximum length of packets that can be
  55. received. Default is 2048 bytes.
  56. =item NODELAY
  57. Boolean. Applies to TCP sockets only. If set, disable the Nagle
  58. algorithm. This means that segments are always sent as soon as
  59. possible, even if there is only a small amount of data. When not set,
  60. data is buffered until there is a sufficient amount to send out,
  61. thereby avoiding the frequent sending of small packets, which results
  62. in poor utilization of the network. Default is true.
  63. =item CLIENT
  64. Boolean. If set, forces the socket to connect() (if SOCK_STREAM) to
  65. the specified address/port (if AF_INET) or file handle (if AF_UNIX),
  66. instead of bind()-ing and listen()-ing to it.
  67. Default is false. However, if a Socket element has no output and
  68. CLIENT is unspecified, it is assumed to be a client socket. If a
  69. Socket element has no input and CLIENT is unspecified, it is assumed
  70. to be a server socket.
  71. =item SNDBUF
  72. Unsigned integer. Sets the maximum size in bytes of the underlying
  73. socket send buffer. The default value is set by the wmem_default
  74. sysctl and the maximum allowed value is set by the wmem_max sysctl.
  75. =item RCVBUF
  76. Unsigned integer. Sets the maximum size in bytes of the underlying
  77. socket receive buffer. The default value is set by the rmem_default
  78. sysctl and the maximum allowed value is set by the rmem_max sysctl.
  79. =item TIMESTAMP
  80. Boolean. If set, sets the timestamp field on received packets to the
  81. current time. Default is true.
  82. =item ALLOW
  83. The name of an IPRouteTable element, like RadixIPLookup or
  84. DirectIPLookup. If set and the Socket element is a server, the Socket
  85. element will lookup source IP addresses of clients in the specified
  86. IPRouteTable before accepting a connection (if SOCK_STREAM) or
  87. datagram (if SOCK_DGRAM). If the address is found, the connection or
  88. datagram is accepted. If the address is not found, the DENY table will
  89. then be checked (see below).
  90. =item DENY
  91. The name of an IPRouteTable element, like RadixIPLookup or
  92. DirectIPLookup. If set and the Socket element is a server, the Socket
  93. element will lookup source IP addresses of clients in the specified
  94. IPRouteTable before accepting a connection (if SOCK_STREAM) or
  95. datagram (if SOCK_DGRAM). If the address is found, the connection or
  96. datagram is dropped, otherwise it is accepted. Note that the ALLOW
  97. table, if specified, is checked first. Wildcard matches may be
  98. specified with netmasks; for example, to deny all hosts, specify a
  99. route to "0.0.0.0/0" in the DENY table.
  100. =item VERBOSE
  101. Boolean. When true, Socket will print messages whenever it accepts a
  102. new connection or drops an old one. Default is false.
  103. =item PROPER
  104. Boolean. PlanetLab specific. If true and Click has been configured
  105. --with-proper, use Proper to bind a reserved port.
  106. =item HEADROOM
  107. Integer. Per-packet headroom. Defaults to 28.
  108. =back
  109. =e
  110. // A server socket
  111. Socket(TCP, 0.0.0.0, 80) -> ...
  112. // A client socket
  113. ... -> Socket(TCP, 1.2.3.4, 80)
  114. // A bi-directional server socket (handles one client at a time)
  115. ... -> Socket(TCP, 0.0.0.0, 80) -> ...
  116. // A bi-directional client socket
  117. ... -> Socket(TCP, 1.2.3.4, 80, CLIENT true) -> ...
  118. // A bi-directional client socket bound to a particular local port
  119. ... -> Socket(TCP, 1.2.3.4, 80, 0.0.0.0, 54321) -> ...
  120. // A localhost server socket
  121. allow :: RadixIPLookup(127.0.0.1 0);
  122. deny :: RadixIPLookup(0.0.0.0/0 0);
  123. allow -> deny -> allow; // (makes the configuration valid)
  124. Socket(TCP, 0.0.0.0, 80, ALLOW allow, DENY deny) -> ...
  125. =a RawSocket */
  126. class Socket : public Element { public:
  127. Socket() CLICK_COLD;
  128. ~Socket() CLICK_COLD;
  129. const char *class_name() const { return "Socket"; }
  130. const char *port_count() const { return "0-1/0-1"; }
  131. const char *processing() const { return "a/h"; }
  132. const char *flow_code() const { return "x/y"; }
  133. const char *flags() const { return "S3"; }
  134. virtual int configure(Vector<String> &conf, ErrorHandler *) CLICK_COLD;
  135. virtual int initialize(ErrorHandler *) CLICK_COLD;
  136. virtual void cleanup(CleanupStage) CLICK_COLD;
  137. void add_handlers() CLICK_COLD;
  138. bool run_task(Task *);
  139. void selected(int fd, int mask);
  140. void push(int port, Packet*);
  141. bool allowed(IPAddress);
  142. void close_active(void);
  143. int write_packet(Packet*);
  144. protected:
  145. Task _task;
  146. Timer _timer;
  147. private:
  148. int _fd; // socket descriptor
  149. int _active; // connection descriptor
  150. // local address to bind()
  151. union { struct sockaddr_in in; struct sockaddr_un un; } _local;
  152. socklen_t _local_len;
  153. // remote address to connect() to or sendto() (for
  154. // non-connection-mode sockets)
  155. union { struct sockaddr_in in; struct sockaddr_un un; } _remote;
  156. socklen_t _remote_len;
  157. NotifierSignal _signal; // packet is available to pull()
  158. WritablePacket *_rq; // queue to receive pulled packets
  159. int _backoff; // backoff timer for when sendto() blocks
  160. Packet *_wq; // queue to store pulled packet for when sendto() blocks
  161. int _events; // keeps track of the events for which select() is waiting
  162. int _family; // AF_INET or AF_UNIX
  163. int _socktype; // SOCK_STREAM or SOCK_DGRAM
  164. int _protocol; // for AF_INET, IPPROTO_TCP, IPPROTO_UDP, etc.
  165. IPAddress _local_ip; // for AF_INET, address to bind()
  166. uint16_t _local_port; // for AF_INET, port to bind()
  167. String _local_pathname; // for AF_UNIX, file to bind()
  168. IPAddress _remote_ip; // for AF_INET, address to connect() to or sendto()
  169. uint16_t _remote_port; // for AF_INET, port to connect() to or sendto()
  170. String _remote_pathname; // for AF_UNIX, file to sendto()
  171. bool _timestamp; // set the timestamp on received packets
  172. int _sndbuf; // maximum socket send buffer in bytes
  173. int _rcvbuf; // maximum socket receive buffer in bytes
  174. int _snaplen; // maximum received packet length
  175. unsigned _headroom;
  176. int _nodelay; // disable Nagle algorithm
  177. bool _verbose; // be verbose
  178. bool _client; // client or server
  179. bool _proper; // (PlanetLab only) use Proper to bind port
  180. IPRouteTable *_allow; // lookup table of good hosts
  181. IPRouteTable *_deny; // lookup table of bad hosts
  182. int initialize_socket_error(ErrorHandler *, const char *);
  183. };
  184. CLICK_ENDDECLS
  185. #endif