00001 /* -*- C++ -*- */ 00002 00003 //============================================================================= 00004 /** 00005 * @file INET_Addr.h 00006 * 00007 * $Id: INET_Addr.h 81030 2008-03-20 12:43:29Z johnnyw $ 00008 * 00009 * @author Douglas C. Schmidt <schmidt@cs.wustl.edu> 00010 */ 00011 //============================================================================= 00012 00013 #ifndef ACE_INET_ADDR_H 00014 #define ACE_INET_ADDR_H 00015 #include /**/ "ace/pre.h" 00016 00017 #include "ace/Sock_Connect.h" 00018 00019 #if !defined (ACE_LACKS_PRAGMA_ONCE) 00020 # pragma once 00021 #endif /* ACE_LACKS_PRAGMA_ONCE */ 00022 00023 #include "ace/Addr.h" 00024 00025 #if defined(ACE_VXWORKS) 00026 // Needed to get INET_ADDR_LEN 00027 # include /**/ "inetLib.h" 00028 #endif /* ACE_VXWORKS */ 00029 00030 ACE_BEGIN_VERSIONED_NAMESPACE_DECL 00031 00032 /** 00033 * @class ACE_INET_Addr 00034 * 00035 * @brief Defines a C++ wrapper facade for the Internet domain address 00036 * family format. 00037 */ 00038 class ACE_Export ACE_INET_Addr : public ACE_Addr 00039 { 00040 public: 00041 // = Initialization methods. 00042 00043 /// Default constructor. 00044 ACE_INET_Addr (void); 00045 00046 /// Copy constructor. 00047 ACE_INET_Addr (const ACE_INET_Addr &); 00048 00049 /// Creates an ACE_INET_Addr from a sockaddr_in structure. 00050 ACE_INET_Addr (const sockaddr_in *addr, int len); 00051 00052 /// Creates an ACE_INET_Addr from a @a port_number and the remote 00053 /// @a host_name. The port number is assumed to be in host byte order. 00054 /// To set a port already in network byte order, please @see set(). 00055 /// Use address_family to select IPv6 (PF_INET6) vs. IPv4 (PF_INET). 00056 ACE_INET_Addr (u_short port_number, 00057 const char host_name[], 00058 int address_family = AF_UNSPEC); 00059 00060 /** 00061 * Initializes an ACE_INET_Addr from the @a address, which can be 00062 * "ip-number:port-number" (e.g., "tango.cs.wustl.edu:1234" or 00063 * "128.252.166.57:1234"). If there is no ':' in the @a address it 00064 * is assumed to be a port number, with the IP address being 00065 * INADDR_ANY. 00066 */ 00067 explicit ACE_INET_Addr (const char address[], 00068 int address_family = AF_UNSPEC); 00069 00070 /** 00071 * Creates an ACE_INET_Addr from a @a port_number and an Internet 00072 * <ip_addr>. This method assumes that @a port_number and <ip_addr> 00073 * are in host byte order. If you have addressing information in 00074 * network byte order, @see set(). 00075 */ 00076 explicit ACE_INET_Addr (u_short port_number, 00077 ACE_UINT32 ip_addr = INADDR_ANY); 00078 00079 /// Uses <getservbyname> to create an ACE_INET_Addr from a 00080 /// <port_name>, the remote @a host_name, and the @a protocol. 00081 ACE_INET_Addr (const char port_name[], 00082 const char host_name[], 00083 const char protocol[] = "tcp"); 00084 00085 /** 00086 * Uses <getservbyname> to create an ACE_INET_Addr from a 00087 * <port_name>, an Internet <ip_addr>, and the @a protocol. This 00088 * method assumes that <ip_addr> is in host byte order. 00089 */ 00090 ACE_INET_Addr (const char port_name[], 00091 ACE_UINT32 ip_addr, 00092 const char protocol[] = "tcp"); 00093 00094 #if defined (ACE_HAS_WCHAR) 00095 ACE_INET_Addr (u_short port_number, 00096 const wchar_t host_name[], 00097 int address_family = AF_UNSPEC); 00098 00099 explicit ACE_INET_Addr (const wchar_t address[], 00100 int address_family = AF_UNSPEC); 00101 00102 ACE_INET_Addr (const wchar_t port_name[], 00103 const wchar_t host_name[], 00104 const wchar_t protocol[] = ACE_TEXT_WIDE ("tcp")); 00105 00106 ACE_INET_Addr (const wchar_t port_name[], 00107 ACE_UINT32 ip_addr, 00108 const wchar_t protocol[] = ACE_TEXT_WIDE ("tcp")); 00109 #endif /* ACE_HAS_WCHAR */ 00110 00111 /// Default dtor. 00112 ~ACE_INET_Addr (void); 00113 00114 // = Direct initialization methods. 00115 00116 // These methods are useful after the object has been constructed. 00117 00118 /// Initializes from another ACE_INET_Addr. 00119 int set (const ACE_INET_Addr &); 00120 00121 /** 00122 * Initializes an ACE_INET_Addr from a @a port_number and the 00123 * remote @a host_name. If @a encode is non-zero then @a port_number is 00124 * converted into network byte order, otherwise it is assumed to be 00125 * in network byte order already and are passed straight through. 00126 * address_family can be used to select IPv4/IPv6 if the OS has 00127 * IPv6 capability (ACE_HAS_IPV6 is defined). To specify IPv6, use 00128 * the value AF_INET6. To specify IPv4, use AF_INET. 00129 */ 00130 int set (u_short port_number, 00131 const char host_name[], 00132 int encode = 1, 00133 int address_family = AF_UNSPEC); 00134 00135 /** 00136 * Initializes an ACE_INET_Addr from a @a port_number and an Internet 00137 * @a ip_addr. If @a encode is non-zero then the port number and IP address 00138 * are converted into network byte order, otherwise they are assumed to be 00139 * in network byte order already and are passed straight through. 00140 * 00141 * If <map> is non-zero and IPv6 support has been compiled in, 00142 * then this address will be set to the IPv4-mapped IPv6 address of it. 00143 */ 00144 int set (u_short port_number, 00145 ACE_UINT32 ip_addr = INADDR_ANY, 00146 int encode = 1, 00147 int map = 0); 00148 00149 /// Uses <getservbyname> to initialize an ACE_INET_Addr from a 00150 /// <port_name>, the remote @a host_name, and the @a protocol. 00151 int set (const char port_name[], 00152 const char host_name[], 00153 const char protocol[] = "tcp"); 00154 00155 /** 00156 * Uses <getservbyname> to initialize an ACE_INET_Addr from a 00157 * <port_name>, an <ip_addr>, and the @a protocol. This assumes that 00158 * <ip_addr> is already in network byte order. 00159 */ 00160 int set (const char port_name[], 00161 ACE_UINT32 ip_addr, 00162 const char protocol[] = "tcp"); 00163 00164 /** 00165 * Initializes an ACE_INET_Addr from the @a addr, which can be 00166 * "ip-number:port-number" (e.g., "tango.cs.wustl.edu:1234" or 00167 * "128.252.166.57:1234"). If there is no ':' in the @a address it 00168 * is assumed to be a port number, with the IP address being 00169 * INADDR_ANY. 00170 */ 00171 int set (const char addr[], int address_family = AF_UNSPEC); 00172 00173 /// Creates an ACE_INET_Addr from a sockaddr_in structure. 00174 int set (const sockaddr_in *, 00175 int len); 00176 00177 #if defined (ACE_HAS_WCHAR) 00178 int set (u_short port_number, 00179 const wchar_t host_name[], 00180 int encode = 1, 00181 int address_family = AF_UNSPEC); 00182 00183 int set (const wchar_t port_name[], 00184 const wchar_t host_name[], 00185 const wchar_t protocol[] = ACE_TEXT_WIDE ("tcp")); 00186 00187 int set (const wchar_t port_name[], 00188 ACE_UINT32 ip_addr, 00189 const wchar_t protocol[] = ACE_TEXT_WIDE ("tcp")); 00190 00191 int set (const wchar_t addr[], int address_family = AF_UNSPEC); 00192 #endif /* ACE_HAS_WCHAR */ 00193 00194 /// Return a pointer to the underlying network address. 00195 virtual void *get_addr (void) const; 00196 int get_addr_size(void) const; 00197 00198 /// Set a pointer to the address. 00199 virtual void set_addr (void *, int len); 00200 00201 /// Set a pointer to the address. 00202 virtual void set_addr (void *, int len, int map); 00203 00204 /** 00205 * Transform the current ACE_INET_Addr address into string format. 00206 * If <ipaddr_format> is non-0 this produces "ip-number:port-number" 00207 * (e.g., "128.252.166.57:1234"), whereas if <ipaddr_format> is 0 00208 * this produces "ip-name:port-number" (e.g., 00209 * "tango.cs.wustl.edu:1234"). Returns -1 if the @a size of the 00210 * <buffer> is too small, else 0. 00211 */ 00212 virtual int addr_to_string (ACE_TCHAR buffer[], 00213 size_t size, 00214 int ipaddr_format = 1) const; 00215 00216 /** 00217 * Initializes an ACE_INET_Addr from the @a address, which can be 00218 * "ip-addr:port-number" (e.g., "tango.cs.wustl.edu:1234"), 00219 * "ip-addr:port-name" (e.g., "tango.cs.wustl.edu:telnet"), 00220 * "ip-number:port-number" (e.g., "128.252.166.57:1234"), or 00221 * "ip-number:port-name" (e.g., "128.252.166.57:telnet"). If there 00222 * is no ':' in the @a address it is assumed to be a port number, 00223 * with the IP address being INADDR_ANY. 00224 */ 00225 virtual int string_to_addr (const char address[], 00226 int address_family = AF_UNSPEC); 00227 00228 #if defined (ACE_HAS_WCHAR) 00229 /* 00230 virtual int string_to_addr (const char address[]); 00231 */ 00232 #endif /* ACE_HAS_WCHAR */ 00233 00234 /** 00235 * Sets the port number without affecting the host name. If 00236 * @a encode is enabled then @a port_number is converted into network 00237 * byte order, otherwise it is assumed to be in network byte order 00238 * already and are passed straight through. 00239 */ 00240 void set_port_number (u_short, 00241 int encode = 1); 00242 00243 /** 00244 * Sets the address without affecting the port number. If 00245 * @a encode is enabled then <ip_addr> is converted into network 00246 * byte order, otherwise it is assumed to be in network byte order 00247 * already and are passed straight through. The size of the address 00248 * is specified in the @a len parameter. 00249 * If <map> is non-zero, IPv6 support has been compiled in, and 00250 * <ip_addr> is an IPv4 address, then this address is set to the IPv4-mapped 00251 * IPv6 address of it. 00252 */ 00253 int set_address (const char *ip_addr, 00254 int len, 00255 int encode = 1, 00256 int map = 0); 00257 00258 #if (defined (__linux__) || defined (ACE_WIN32)) && defined (ACE_HAS_IPV6) 00259 /** 00260 * Sets the interface that should be used for this address. This only has 00261 * an effect when the address is link local, otherwise it does nothing. 00262 */ 00263 int set_interface (const char *intf_name); 00264 #endif /* (__linux__ || ACE_WIN32) && ACE_HAS_IPV6 */ 00265 00266 /// Return the port number, converting it into host byte-order. 00267 u_short get_port_number (void) const; 00268 00269 /** 00270 * Return the character representation of the name of the host, 00271 * storing it in the <hostname> (which is assumed to be 00272 * <hostnamelen> bytes long). This version is reentrant. If 00273 * <hostnamelen> is greater than 0 then <hostname> will be 00274 * NUL-terminated even if -1 is returned. 00275 */ 00276 int get_host_name (char hostname[], 00277 size_t hostnamelen) const; 00278 00279 #if defined (ACE_HAS_WCHAR) 00280 int get_host_name (wchar_t hostname[], 00281 size_t hostnamelen) const; 00282 #endif /* ACE_HAS_WCHAR */ 00283 00284 /** 00285 * Return the character representation of the hostname. This 00286 * version is non-reentrant since it returns a pointer to a static 00287 * data area. You should therefore either (1) do a "deep copy" of 00288 * the address returned by get_host_name(), e.g., using strdup() or 00289 * (2) use the "reentrant" version of get_host_name() described 00290 * above. 00291 */ 00292 const char *get_host_name (void) const; 00293 00294 /** 00295 * Return the "dotted decimal" Internet address representation of 00296 * the hostname storing it in the @a addr (which is assumed to be 00297 * @a addr_size bytes long). This version is reentrant. 00298 */ 00299 const char *get_host_addr (char *addr, int addr_size) const; 00300 00301 /** 00302 * Return the "dotted decimal" Internet address representation of 00303 * the hostname. This version is non-reentrant since it returns a 00304 * pointer to a static data area. You should therefore either 00305 * (1) do a "deep copy" of the address returned by get_host_addr(), e.g., 00306 * using strdup() or (2) use the "reentrant" version of 00307 * get_host_addr() described above. 00308 */ 00309 const char *get_host_addr (void) const; 00310 00311 /// Return the 4-byte IP address, converting it into host byte 00312 /// order. 00313 ACE_UINT32 get_ip_address (void) const; 00314 00315 /// Return @c true if the IP address is INADDR_ANY or IN6ADDR_ANY. 00316 bool is_any (void) const; 00317 00318 /// Return @c true if the IP address is IPv4/IPv6 loopback address. 00319 bool is_loopback (void) const; 00320 00321 /// Return @c true if the IP address is IPv4/IPv6 multicast address. 00322 bool is_multicast (void) const; 00323 00324 #if defined (ACE_HAS_IPV6) 00325 /// Return @c true if the IP address is IPv6 linklocal address. 00326 bool is_linklocal (void) const; 00327 00328 /// Return @c true if the IP address is IPv4-mapped IPv6 address. 00329 bool is_ipv4_mapped_ipv6 (void) const; 00330 00331 /// Return @c true if the IP address is IPv4-compatible IPv6 address. 00332 bool is_ipv4_compat_ipv6 (void) const; 00333 #endif /* ACE_HAS_IPV6 */ 00334 00335 /** 00336 * Returns @c true if @c this is less than @a rhs. In this context, 00337 * "less than" is defined in terms of IP address and TCP port 00338 * number. This operator makes it possible to use @c ACE_INET_Addrs 00339 * in STL maps. 00340 */ 00341 bool operator < (const ACE_INET_Addr &rhs) const; 00342 00343 /// Compare two addresses for equality. The addresses are considered 00344 /// equal if they contain the same IP address and port number. 00345 bool operator == (const ACE_INET_Addr &SAP) const; 00346 00347 /// Compare two addresses for inequality. 00348 bool operator != (const ACE_INET_Addr &SAP) const; 00349 00350 /// A variation of the equality operator, this method only compares the 00351 /// IP address and ignores the port number. 00352 bool is_ip_equal (const ACE_INET_Addr &SAP) const; 00353 00354 /// Computes and returns hash value. 00355 virtual u_long hash (void) const; 00356 00357 /// Dump the state of an object. 00358 void dump (void) const; 00359 00360 /// Declare the dynamic allocation hooks. 00361 ACE_ALLOC_HOOK_DECLARE; 00362 00363 private: 00364 /// Insure that @a hostname is properly null-terminated. 00365 int get_host_name_i (char hostname[], size_t hostnamelen) const; 00366 00367 // Methods to gain access to the actual address of 00368 // the underlying internet address structure. 00369 void *ip_addr_pointer (void) const; 00370 int ip_addr_size (void) const; 00371 int determine_type (void) const; 00372 00373 /// Initialize underlying inet_addr_ to default values 00374 void reset (void); 00375 00376 /// Underlying representation. 00377 /// This union uses the knowledge that the two structures share the 00378 /// first member, sa_family (as all sockaddr structures do). 00379 union 00380 { 00381 sockaddr_in in4_; 00382 #if defined (ACE_HAS_IPV6) 00383 sockaddr_in6 in6_; 00384 #endif /* ACE_HAS_IPV6 */ 00385 } inet_addr_; 00386 00387 #if defined (ACE_VXWORKS) 00388 char buf_[INET_ADDR_LEN]; 00389 #endif 00390 }; 00391 00392 ACE_END_VERSIONED_NAMESPACE_DECL 00393 00394 #if defined (__ACE_INLINE__) 00395 #include "ace/INET_Addr.inl" 00396 #endif /* __ACE_INLINE__ */ 00397 00398 #include /**/ "ace/post.h" 00399 #endif /* ACE_INET_ADDR_H */