]> CyberLeo.Net >> Repos - FreeBSD/releng/10.2.git/blob - contrib/llvm/tools/lldb/source/Host/common/SocketAddress.cpp
- Copy stable/10@285827 to releng/10.2 in preparation for 10.2-RC1
[FreeBSD/releng/10.2.git] / contrib / llvm / tools / lldb / source / Host / common / SocketAddress.cpp
1 //===-- SocketAddress.cpp ---------------------------------------*- C++ -*-===//
2 //
3 //                     The LLVM Compiler Infrastructure
4 //
5 // This file is distributed under the University of Illinois Open Source
6 // License. See LICENSE.TXT for details.
7 //
8 //===----------------------------------------------------------------------===//
9
10 #include "lldb/Host/SocketAddress.h"
11 #include <stddef.h>
12
13 // C Includes
14 #if !defined(_MSC_VER)
15 #include <arpa/inet.h>
16 #endif
17 #include <assert.h>
18 #include <string.h>
19
20 // C++ Includes
21 // Other libraries and framework includes
22 // Project includes
23
24 using namespace lldb_private;
25
26 //----------------------------------------------------------------------
27 // SocketAddress constructor
28 //----------------------------------------------------------------------
29 SocketAddress::SocketAddress ()
30 {
31     Clear ();
32 }
33
34 SocketAddress::SocketAddress (const struct sockaddr &s)
35 {
36     m_socket_addr.sa = s;
37 }
38
39
40 SocketAddress::SocketAddress (const struct sockaddr_in &s)
41 {
42     m_socket_addr.sa_ipv4 = s;
43 }
44
45
46 SocketAddress::SocketAddress (const struct sockaddr_in6 &s)
47 {
48     m_socket_addr.sa_ipv6 = s;
49 }
50
51
52 SocketAddress::SocketAddress (const struct sockaddr_storage &s)
53 {
54     m_socket_addr.sa_storage = s;
55 }
56
57 //----------------------------------------------------------------------
58 // SocketAddress copy constructor
59 //----------------------------------------------------------------------
60 SocketAddress::SocketAddress (const SocketAddress& rhs) :
61     m_socket_addr (rhs.m_socket_addr)
62 {
63 }
64
65 //----------------------------------------------------------------------
66 // Destructor
67 //----------------------------------------------------------------------
68 SocketAddress::~SocketAddress()
69 {
70 }
71
72 void
73 SocketAddress::Clear ()
74 {
75     memset (&m_socket_addr, 0, sizeof(m_socket_addr));
76 }
77
78 bool
79 SocketAddress::IsValid () const
80 {
81     return GetLength () != 0;
82 }
83
84 static socklen_t 
85 GetFamilyLength (sa_family_t family)
86 {
87     switch (family)
88     {
89         case AF_INET:  return sizeof(struct sockaddr_in);
90         case AF_INET6: return sizeof(struct sockaddr_in6);
91     }
92     assert(0 && "Unsupported address family");
93 }
94
95 socklen_t
96 SocketAddress::GetLength () const
97 {
98 #if defined(__APPLE__) || defined(__FreeBSD__) || defined(__NetBSD__)
99     return m_socket_addr.sa.sa_len;
100 #else
101     return GetFamilyLength (GetFamily());
102 #endif
103 }
104
105 socklen_t
106 SocketAddress::GetMaxLength ()
107 {
108     return sizeof (sockaddr_t);
109 }
110
111 sa_family_t
112 SocketAddress::GetFamily () const
113 {
114     return m_socket_addr.sa.sa_family;
115 }
116
117 void
118 SocketAddress::SetFamily (sa_family_t family)
119 {
120     m_socket_addr.sa.sa_family = family;
121 #if defined(__APPLE__) || defined(__FreeBSD__) || defined(__NetBSD__)
122     m_socket_addr.sa.sa_len = GetFamilyLength (family);
123 #endif
124 }
125
126 uint16_t
127 SocketAddress::GetPort () const
128 {
129     switch (GetFamily())
130     {
131         case AF_INET:   return ntohs(m_socket_addr.sa_ipv4.sin_port);
132         case AF_INET6:  return ntohs(m_socket_addr.sa_ipv6.sin6_port);
133     }
134     return 0;
135 }
136
137 bool
138 SocketAddress::SetPort (uint16_t port)
139 {
140     switch (GetFamily())
141     {
142         case AF_INET:   
143             m_socket_addr.sa_ipv4.sin_port = htons(port);
144             return true;
145
146         case AF_INET6:  
147             m_socket_addr.sa_ipv6.sin6_port = htons(port);
148             return true;
149     }
150     return false;
151 }
152
153 //----------------------------------------------------------------------
154 // SocketAddress assignment operator
155 //----------------------------------------------------------------------
156 const SocketAddress&
157 SocketAddress::operator=(const SocketAddress& rhs)
158 {
159     if (this != &rhs)
160         m_socket_addr = rhs.m_socket_addr;
161     return *this;
162 }
163
164 const SocketAddress&
165 SocketAddress::operator=(const struct addrinfo *addr_info)
166 {
167     Clear();
168     if (addr_info && 
169         addr_info->ai_addr &&
170         addr_info->ai_addrlen > 0&& 
171         addr_info->ai_addrlen <= sizeof m_socket_addr)
172     {
173         ::memcpy (&m_socket_addr, 
174                   addr_info->ai_addr, 
175                   addr_info->ai_addrlen);
176     }
177     return *this;
178 }
179
180 const SocketAddress&
181 SocketAddress::operator=(const struct sockaddr &s)
182 {
183     m_socket_addr.sa = s;
184     return *this;
185 }
186
187 const SocketAddress&
188 SocketAddress::operator=(const struct sockaddr_in &s)
189 {
190     m_socket_addr.sa_ipv4 = s;
191     return *this;
192 }
193
194 const SocketAddress&
195 SocketAddress::operator=(const struct sockaddr_in6 &s)
196 {
197     m_socket_addr.sa_ipv6 = s;
198     return *this;
199 }
200
201 const SocketAddress&
202 SocketAddress::operator=(const struct sockaddr_storage &s)
203 {
204     m_socket_addr.sa_storage = s;
205     return *this;
206 }
207
208 bool
209 SocketAddress::getaddrinfo (const char *host,
210                             const char *service,
211                             int ai_family,
212                             int ai_socktype,
213                             int ai_protocol,
214                             int ai_flags)
215 {
216     struct addrinfo hints;
217     memset(&hints, 0, sizeof(hints));
218     hints.ai_family = ai_family;
219     hints.ai_socktype = ai_socktype;
220     hints.ai_protocol = ai_protocol;
221     hints.ai_flags = ai_flags;
222
223     struct addrinfo *service_info_list = NULL;
224     int err = ::getaddrinfo (host, service, &hints, &service_info_list);
225     if (err == 0 && service_info_list)
226         *this = service_info_list;
227     else
228         Clear();
229     
230     :: freeaddrinfo (service_info_list);
231     return IsValid();
232 }
233
234
235 bool
236 SocketAddress::SetToLocalhost (sa_family_t family, uint16_t port)
237 {
238     switch (family)
239     {
240         case AF_INET:   
241             SetFamily (AF_INET);
242             if (SetPort (port))
243             {
244                 m_socket_addr.sa_ipv4.sin_addr.s_addr = htonl (INADDR_LOOPBACK);
245                 return true;
246             }
247             break;
248
249         case AF_INET6:  
250             SetFamily (AF_INET6);
251             if (SetPort (port))
252             {
253                 m_socket_addr.sa_ipv6.sin6_addr = in6addr_loopback;
254                 return true;
255             }            
256             break;
257
258     }
259     Clear();
260     return false;
261 }
262
263 bool
264 SocketAddress::SetToAnyAddress (sa_family_t family, uint16_t port)
265 {
266     switch (family)
267     {
268         case AF_INET:
269             SetFamily (AF_INET);
270             if (SetPort (port))
271             {
272                 m_socket_addr.sa_ipv4.sin_addr.s_addr = htonl (INADDR_ANY);
273                 return true;
274             }
275             break;
276             
277         case AF_INET6:
278             SetFamily (AF_INET6);
279             if (SetPort (port))
280             {
281                 m_socket_addr.sa_ipv6.sin6_addr = in6addr_any;
282                 return true;
283             }
284             break;
285             
286     }
287     Clear();
288     return false;
289 }