pinet.h (10164B)
1 /* 2 * 3 * C++ Portable Types Library (PTypes) 4 * Version 2.1.1 Released 27-Jun-2007 5 * 6 * Copyright (C) 2001-2007 Hovik Melikyan 7 * 8 * http://www.melikyan.com/ptypes/ 9 * 10 */ 11 12 #ifndef __PINET_H__ 13 #define __PINET_H__ 14 15 #ifndef __PPORT_H__ 16 #include "pport.h" 17 #endif 18 19 #ifndef __PTYPES_H__ 20 #include "ptypes.h" 21 #endif 22 23 #ifndef __PSTREAMS_H__ 24 #include "pstreams.h" 25 #endif 26 27 28 #ifdef WIN32 29 # include <winsock2.h> 30 #else 31 # include <netdb.h> // for socklen_t 32 # include <sys/types.h> 33 # include <sys/socket.h> 34 #endif 35 36 37 namespace ptypes { 38 39 40 #ifdef _MSC_VER 41 #pragma pack(push, 4) 42 #endif 43 44 45 // 46 // BSD-compatible socket error codes for Win32 47 // 48 49 #if defined(WSAENOTSOCK) && !defined(ENOTSOCK) 50 51 #define EWOULDBLOCK WSAEWOULDBLOCK 52 #define EINPROGRESS WSAEINPROGRESS 53 #define EALREADY WSAEALREADY 54 #define ENOTSOCK WSAENOTSOCK 55 #define EDESTADDRREQ WSAEDESTADDRREQ 56 #define EMSGSIZE WSAEMSGSIZE 57 #define EPROTOTYPE WSAEPROTOTYPE 58 #define ENOPROTOOPT WSAENOPROTOOPT 59 #define EPROTONOSUPPORT WSAEPROTONOSUPPORT 60 #define ESOCKTNOSUPPORT WSAESOCKTNOSUPPORT 61 #define EOPNOTSUPP WSAEOPNOTSUPP 62 #define EPFNOSUPPORT WSAEPFNOSUPPORT 63 #define EAFNOSUPPORT WSAEAFNOSUPPORT 64 #define EADDRINUSE WSAEADDRINUSE 65 #define EADDRNOTAVAIL WSAEADDRNOTAVAIL 66 #define ENETDOWN WSAENETDOWN 67 #define ENETUNREACH WSAENETUNREACH 68 #define ENETRESET WSAENETRESET 69 #define ECONNABORTED WSAECONNABORTED 70 #define ECONNRESET WSAECONNRESET 71 #define ENOBUFS WSAENOBUFS 72 #define EISCONN WSAEISCONN 73 #define ENOTCONN WSAENOTCONN 74 #define ESHUTDOWN WSAESHUTDOWN 75 #define ETOOMANYREFS WSAETOOMANYREFS 76 #define ETIMEDOUT WSAETIMEDOUT 77 #define ECONNREFUSED WSAECONNREFUSED 78 #define ELOOP WSAELOOP 79 // #define ENAMETOOLONG WSAENAMETOOLONG 80 #define EHOSTDOWN WSAEHOSTDOWN 81 #define EHOSTUNREACH WSAEHOSTUNREACH 82 // #define ENOTEMPTY WSAENOTEMPTY 83 #define EPROCLIM WSAEPROCLIM 84 #define EUSERS WSAEUSERS 85 #define EDQUOT WSAEDQUOT 86 #define ESTALE WSAESTALE 87 #define EREMOTE WSAEREMOTE 88 89 // NOTE: these are not errno constants in UNIX! 90 #define HOST_NOT_FOUND WSAHOST_NOT_FOUND 91 #define TRY_AGAIN WSATRY_AGAIN 92 #define NO_RECOVERY WSANO_RECOVERY 93 #define NO_DATA WSANO_DATA 94 95 #endif 96 97 98 // shutdown() constants 99 100 #if defined(SD_RECEIVE) && !defined(SHUT_RD) 101 # define SHUT_RD SD_RECEIVE 102 # define SHUT_WR SD_SEND 103 # define SHUT_RDWR SD_BOTH 104 #endif 105 106 107 // max backlog value for listen() 108 109 #ifndef SOMAXCONN 110 # define SOMAXCONN -1 111 #endif 112 113 typedef char* sockval_t; 114 115 #ifndef WIN32 116 # define closesocket close 117 #endif 118 119 120 #if (defined(__DARWIN__) && !defined(_SOCKLEN_T)) || defined(WIN32) || defined(__hpux) 121 typedef int psocklen; 122 #else 123 typedef socklen_t psocklen; 124 #endif 125 126 127 // -------------------------------------------------------------------- // 128 // --- IP address class and DNS utilities ---------------------------- // 129 // -------------------------------------------------------------------- // 130 131 // 132 // IP address 133 // 134 135 struct ptpublic ipaddress 136 { 137 public: 138 union 139 { 140 uchar data[4]; 141 ulong ldata; 142 }; 143 ipaddress() {} 144 ipaddress(ulong a) { ldata = a; } 145 ipaddress(const ipaddress& a) { ldata = a.ldata; } 146 ipaddress(int a, int b, int c, int d); 147 ipaddress& operator= (ulong a) { ldata = a; return *this; } 148 ipaddress& operator= (const ipaddress& a) { ldata = a.ldata; return *this; } 149 uchar& operator [] (int i) { return data[i]; } 150 operator ulong() const { return ldata; } 151 }; 152 153 154 ptpublic extern ipaddress ipnone; 155 ptpublic extern ipaddress ipany; 156 ptpublic extern ipaddress ipbcast; 157 158 159 // 160 // IP peer info: host name, IP and the port name 161 // used internally in ipstream and ipmessage 162 // 163 164 165 class ptpublic ippeerinfo: public noncopyable 166 { 167 protected: 168 ipaddress ip; // target IP 169 string host; // target host name; either IP or hostname must be specified 170 int port; // target port number 171 172 void notfound(); // throws a (estream*) exception 173 174 ptpublic friend bool ptdecl psockname(int, ippeerinfo&); 175 176 public: 177 ippeerinfo(); 178 ippeerinfo(ipaddress iip, const string& ihost, int iport); 179 180 ipaddress get_ip(); // resolves the host name if necessary (only once) 181 string get_host(); // performs reverse-lookup if necessary (only once) 182 int get_port() { return port; } 183 void clear(); 184 string asstring(bool showport) const; 185 }; 186 187 188 ptpublic string ptdecl iptostring(ipaddress ip); 189 ptpublic ipaddress ptdecl phostbyname(const char* name); 190 ptpublic string ptdecl phostbyaddr(ipaddress ip); 191 ptpublic string ptdecl phostcname(const char* name); 192 193 // internal utilities 194 ptpublic int ptdecl usockerrno(); 195 ptpublic const char* ptdecl usockerrmsg(int code); 196 ptpublic bool ptdecl psockwait(int handle, int timeout); 197 ptpublic bool ptdecl psockname(int handle, ippeerinfo&); 198 199 200 // -------------------------------------------------------------------- // 201 // --- TCP socket classes -------------------------------------------- // 202 // -------------------------------------------------------------------- // 203 204 205 // additional IO status codes 206 207 const int IO_RESOLVING = 10; 208 const int IO_RESOLVED = 11; 209 const int IO_CONNECTING = 20; 210 const int IO_CONNECTED = 21; 211 212 213 // 214 // ipstream 215 // 216 217 class ptpublic ipstream: public fdxstm, public ippeerinfo 218 { 219 friend class ipstmserver; 220 221 protected: 222 int svsocket; // server socket descriptor, used internally by ipstmserver 223 224 #ifdef WIN32 225 // sockets are not compatible with file handles on Windows 226 virtual int dorawread(char* buf, int count); 227 virtual int dorawwrite(const char* buf, int count); 228 #endif 229 230 virtual int uerrno(); 231 virtual const char* uerrmsg(int code); 232 virtual void doopen(); 233 virtual large doseek(large newpos, ioseekmode mode); 234 virtual void doclose(); 235 virtual void sockopt(int socket); 236 void closehandle(); 237 238 public: 239 ipstream(); 240 ipstream(ipaddress ip, int port); 241 ipstream(const char* host, int port); 242 ipstream(const string& host, int port); 243 virtual ~ipstream(); 244 virtual int classid(); 245 246 virtual string get_streamname(); 247 248 bool waitfor(int timeout); 249 ipaddress get_myip(); 250 int get_myport(); 251 void set_ip(ipaddress); 252 void set_host(const string&); 253 void set_host(const char*); 254 void set_port(int); 255 }; 256 257 258 // 259 // common internal interfaces for ipstmserver and ipmsgserver 260 // 261 262 class ipbindinfo: public unknown, public ippeerinfo 263 { 264 public: 265 int handle; 266 267 ipbindinfo(ipaddress iip, const string& ihost, int iport); 268 virtual ~ipbindinfo(); 269 }; 270 271 272 class ptpublic ipsvbase: public unknown 273 { 274 protected: 275 int socktype; 276 bool active; 277 tobjlist<ipbindinfo> addrlist; // list of local socket addresses to bind to 278 279 void error(ippeerinfo& peer, int code, const char* defmsg); 280 bool dopoll(int* i, int timeout); 281 void setupfds(void* set, int i); 282 virtual void open(); 283 virtual void close(); 284 virtual void dobind(ipbindinfo*) = 0; 285 virtual void sockopt(int socket); 286 287 public: 288 ipsvbase(int isocktype); 289 virtual ~ipsvbase(); 290 291 int bind(ipaddress ip, int port); 292 int bindall(int port); 293 294 int get_addrcount() { return addrlist.get_count(); } 295 const ipbindinfo& get_addr(int i) { return *addrlist[i]; } 296 void clear(); 297 }; 298 299 300 // 301 // ipstmserver 302 // 303 304 class ptpublic ipstmserver: public ipsvbase 305 { 306 protected: 307 virtual void dobind(ipbindinfo*); 308 309 public: 310 ipstmserver(); 311 virtual ~ipstmserver(); 312 313 bool poll(int i = -1, int timeout = 0); 314 bool serve(ipstream& client, int i = -1, int timeout = -1); 315 }; 316 317 318 // -------------------------------------------------------------------- // 319 // --- UDP socket classes -------------------------------------------- // 320 // -------------------------------------------------------------------- // 321 322 323 // 324 // ipmessage 325 // 326 327 class ptpublic ipmessage: public unknown, public ippeerinfo 328 { 329 protected: 330 int handle; 331 332 void error(int code, const char* msg); 333 void open(); 334 void close(); 335 virtual void sockopt(int socket); 336 337 public: 338 ipmessage(); 339 ipmessage(ipaddress ip, int port); 340 ipmessage(const char* host, int port); 341 ipmessage(const string& host, int port); 342 virtual ~ipmessage(); 343 344 void set_ip(ipaddress iip); 345 void set_host(const string&); 346 void set_host(const char*); 347 void set_port(int); 348 ipaddress get_myip(); 349 int get_myport(); 350 int get_handle() { return handle; } 351 352 bool waitfor(int timeout); 353 int receive(char* buf, int count, ipaddress& src); 354 int receive(char* buf, int count); 355 string receive(int max, ipaddress& src); 356 string receive(int max); 357 void send(const char* buf, int count); 358 void send(const string& s) { send(s, length(s)); } 359 }; 360 361 362 // 363 // ipmsgserver 364 // 365 366 class ptpublic ipmsgserver: public ipsvbase, public ippeerinfo 367 { 368 protected: 369 int handle; 370 371 virtual void close(); 372 virtual void dobind(ipbindinfo*); 373 374 public: 375 ipmsgserver(); 376 virtual ~ipmsgserver(); 377 378 int get_handle() { return handle; } 379 380 bool poll(int i = -1, int timeout = 0); 381 int receive(char* buf, int count); 382 string receive(int max); 383 void send(const char* buf, int count); 384 void send(const string& s) { send(s, length(s)); } 385 void sendto(const char* buf, int count, ipaddress ip, int port); 386 void sendto(const string& s, ipaddress ip, int port) 387 { sendto(s, length(s), ip, port); } 388 }; 389 390 391 #ifdef _MSC_VER 392 #pragma pack(pop) 393 #endif 394 395 396 } 397 398 399 #endif // __PINET_H__ 400