UCommon
|
00001 // Copyright (C) 1999-2005 Open Source Telecom Corporation. 00002 // Copyright (C) 2006-2014 David Sugar, Tycho Softworks. 00003 // Copyright (C) 2015 Cherokees of Idaho. 00004 // 00005 // This program is free software; you can redistribute it and/or modify 00006 // it under the terms of the GNU General Public License as published by 00007 // the Free Software Foundation; either version 2 of the License, or 00008 // (at your option) any later version. 00009 // 00010 // This program is distributed in the hope that it will be useful, 00011 // but WITHOUT ANY WARRANTY; without even the implied warranty of 00012 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 00013 // GNU General Public License for more details. 00014 // 00015 // You should have received a copy of the GNU Lesser General Public License 00016 // along with this program. If not, see <http://www.gnu.org/licenses/>. 00017 // 00018 // As a special exception, you may use this file as part of a free software 00019 // library without restriction. Specifically, if other files instantiate 00020 // templates or use macros or inline functions from this file, or you compile 00021 // this file and link it with other files to produce an executable, this 00022 // file does not by itself cause the resulting executable to be covered by 00023 // the GNU General Public License. This exception does not however 00024 // invalidate any other reasons why the executable file might be covered by 00025 // the GNU General Public License. 00026 // 00027 // This exception applies only to the code released under the name GNU 00028 // Common C++. If you copy code from other releases into a copy of GNU 00029 // Common C++, as the General Public License permits, the exception does 00030 // not apply to the code that you add in this way. To avoid misleading 00031 // anyone as to the status of such modified files, you must delete 00032 // this exception notice from them. 00033 // 00034 // If you write modifications of your own for GNU Common C++, it is your choice 00035 // whether to permit this exception to apply to your modifications. 00036 // If you do not wish that, delete this exception notice. 00037 // 00038 00044 #ifndef COMMONCPP_UDP_H_ 00045 #define COMMONCPP_UDP_H_ 00046 00047 #include <cstdio> 00048 00049 #ifndef COMMONCPP_CONFIG_H_ 00050 #include <commoncpp/config.h> 00051 #endif 00052 00053 #ifndef COMMONCPP_STRING_H_ 00054 #include <commoncpp/string.h> 00055 #endif 00056 00057 #ifndef COMMONCPP_ADDRESS_H_ 00058 #include <commoncpp/address.h> 00059 #endif 00060 00061 #ifndef COMMONCPP_SOCKET_H_ 00062 #include <commoncpp/socket.h> 00063 #endif 00064 00065 namespace ost { 00066 00099 class __EXPORT UDPSocket : public Socket 00100 { 00101 private: 00102 inline Error setKeepAlive(bool enable) 00103 {return Socket::setKeepAlive(enable);} 00104 00105 protected: 00106 Socket::address peer; 00107 00108 Family family; 00109 00110 public: 00114 UDPSocket(Family family = IPV4); 00115 00119 UDPSocket(const char *name, Family family = IPV4); 00120 00130 UDPSocket(const ucommon::Socket::address &bind); 00131 UDPSocket(const IPV4Address &bind, tpport_t port); 00132 #ifdef CCXX_IPV6 00133 UDPSocket(const IPV6Address &bind, tpport_t port); 00134 #endif 00135 00139 virtual ~UDPSocket(); 00140 00144 inline Error setLoopback(bool enable) 00145 {return Socket::setLoopbackByFamily(enable, family);} 00146 00150 inline Error setMulticast(bool enable) 00151 {return Socket::setMulticastByFamily(enable, family);} 00152 00156 inline Error setTimeToLive(char ttl) 00157 {return Socket::setTimeToLiveByFamily(ttl, family);} 00158 00166 void setPeer(const ucommon::Socket::address &host); 00167 void connect(const ucommon::Socket::address &host); 00168 00169 void setPeer(const IPV4Host &host, tpport_t port); 00170 void connect(const IPV4Host &host, tpport_t port); 00171 #ifdef CCXX_IPV6 00172 void setPeer(const IPV6Host &host, tpport_t port); 00173 void connect(const IPV6Host &host, tpport_t port); 00174 #endif 00175 00183 Socket::Error getInterfaceIndex(const char *ethX,int& InterfaceIndex); 00184 00193 Socket::Error join(const ucommon::Socket::address &ia, int InterfaceIndex=0); 00194 Socket::Error join(const IPV4Multicast &ia,int InterfaceIndex); 00195 00203 ssize_t send(const void *buf, size_t len); 00204 00213 ssize_t receive(void *buf, size_t len, bool reply = false); 00214 00223 ucommon::Socket::address getPeer(); 00224 00225 IPV4Host getIPV4Peer(tpport_t *port = NULL); 00226 inline IPV4Host getPeer(tpport_t *port) 00227 {return getIPV4Peer(port);} 00228 00229 #ifdef CCXX_IPV6 00230 IPV6Host getIPV6Peer(tpport_t *port = NULL); 00231 #endif 00232 00240 inline ssize_t peek(void *buf, size_t len) 00241 {return ::recv(so, (char *)buf, len, MSG_PEEK);} 00242 00246 void setPeer(const char *service); 00247 void connect(const char *service); 00248 00253 Error disconnect(void); 00254 }; 00255 00264 class __EXPORT UDPBroadcast : public UDPSocket 00265 { 00266 private: 00267 void setPeer(const IPV4Host &ia, tpport_t port); 00268 00269 Error setBroadcast(bool enable) 00270 {return Socket::setBroadcast(enable);} 00271 00272 public: 00279 UDPBroadcast(const IPV4Address &ia, tpport_t port); 00280 00287 void setPeer(const IPV4Broadcast &subnet, tpport_t port); 00288 }; 00289 00298 class __EXPORT UDPTransmit : protected UDPSocket 00299 { 00300 private: 00308 Error cConnect(const IPV4Address &ia, tpport_t port); 00309 00310 protected: 00314 UDPTransmit(Family family = IPV4); 00315 00328 UDPTransmit(const ucommon::Socket::address &bind); 00329 00330 UDPTransmit(const IPV4Address &bind, tpport_t port = 5005); 00331 #ifdef CCXX_IPV6 00332 UDPTransmit(const IPV6Address &bind, tpport_t port = 5005); 00333 #endif 00334 00344 Error connect(const ucommon::Socket::address &host); 00345 00346 Error connect(const IPV4Host &host, tpport_t port); 00347 #ifdef CCXX_IPV6 00348 Error connect(const IPV6Address &host, tpport_t port); 00349 #endif 00350 00360 Error connect(const IPV4Broadcast &subnet, tpport_t port); 00361 00369 Error connect(const IPV4Multicast &mgroup, tpport_t port); 00370 #ifdef CCXX_IPV6 00371 Error connect(const IPV6Multicast &mgroup, tpport_t port); 00372 #endif 00373 00381 inline ssize_t send(const void *buf, size_t len) 00382 {return ::send(so, (const char *)buf, len, MSG_NOSIGNAL);} 00383 00387 inline void endTransmitter(void) 00388 {Socket::endSocket();} 00389 00390 /* 00391 * Get transmitter socket. 00392 * 00393 * @return transmitter. 00394 */ 00395 inline SOCKET getTransmitter(void) 00396 {return so;}; 00397 00398 inline Error setMulticast(bool enable) 00399 {return Socket::setMulticastByFamily(enable, family);} 00400 00401 inline Error setTimeToLive(unsigned char ttl) 00402 {return Socket::setTimeToLiveByFamily(ttl, family);} 00403 00404 public: 00414 inline ssize_t transmit(const char *buffer, size_t len) 00415 {return ::send(so, buffer, len, MSG_DONTWAIT|MSG_NOSIGNAL);} 00416 00423 inline bool isOutputReady(unsigned long timeout = 0l) 00424 {return Socket::isPending(Socket::pendingOutput, timeout);} 00425 00426 00427 inline Error setRouting(bool enable) 00428 {return Socket::setRouting(enable);} 00429 00430 inline Error setTypeOfService(Tos tos) 00431 {return Socket::setTypeOfService(tos);} 00432 00433 inline Error setBroadcast(bool enable) 00434 {return Socket::setBroadcast(enable);} 00435 }; 00436 00445 class __EXPORT UDPReceive : protected UDPSocket 00446 { 00447 protected: 00457 UDPReceive(const ucommon::Socket::address &bind); 00458 UDPReceive(const IPV4Address &bind, tpport_t port); 00459 #ifdef CCXX_IPV6 00460 UDPReceive(const IPV6Address &bind, tpport_t port); 00461 #endif 00462 00472 Error connect(const ucommon::Socket::address &host); 00473 Error connect(const IPV4Host &host, tpport_t port); 00474 #ifdef CCXX_IPV6 00475 Error connect(const IPV6Host &host, tpport_t port); 00476 #endif 00477 00484 bool isPendingReceive(timeout_t timeout) 00485 {return Socket::isPending(Socket::pendingInput, timeout);} 00486 00490 inline void endReceiver(void) 00491 {Socket::endSocket();} 00492 00493 inline SOCKET getReceiver(void) const 00494 {return so;} 00495 00496 inline Error setRouting(bool enable) 00497 {return Socket::setRouting(enable);} 00498 00499 inline Error setMulticast(bool enable) 00500 {return Socket::setMulticastByFamily(enable, family);} 00501 00502 inline Error join(const ucommon::Socket::address &ia) 00503 {return Socket::join(ia);} 00504 00505 inline Error join(const IPV4Multicast &ia) 00506 {return Socket::join(ia);} 00507 00508 #ifdef CCXX_IPV6 00509 inline Error join(const IPV6Multicast &ia) 00510 {return Socket::join(ia);} 00511 #endif 00512 00513 inline Error drop(const IPV4Multicast &ia) 00514 {return Socket::drop(ia);} 00515 00516 #ifdef CCXX_IPV6 00517 inline Error drop(const IPV6Multicast &ia) 00518 {return Socket::drop(ia);} 00519 #endif 00520 00521 public: 00529 inline ssize_t receive(void *buf, size_t len) 00530 {return ::recv(so, (char *)buf, len, 0);} 00531 00538 inline bool isInputReady(timeout_t timeout = TIMEOUT_INF) 00539 {return Socket::isPending(Socket::pendingInput, timeout);} 00540 }; 00541 00552 class __EXPORT UDPDuplex : public UDPTransmit, public UDPReceive 00553 { 00554 public: 00562 UDPDuplex(const ucommon::Socket::address &bind); 00563 UDPDuplex(const IPV4Address &bind, tpport_t port); 00564 #ifdef CCXX_IPV6 00565 UDPDuplex(const IPV6Address &bind, tpport_t port); 00566 #endif 00567 00577 Error connect(const ucommon::Socket::address &host); 00578 Error connect(const IPV4Host &host, tpport_t port); 00579 #ifdef CCXX_IPV6 00580 Error connect(const IPV6Host &host, tpport_t port); 00581 #endif 00582 00589 Error disconnect(void); 00590 }; 00591 00592 } // namespace ost 00593 00594 #endif