1 /* Copyright Joyent, Inc. and other Node contributors. All rights reserved.
2  *
3  * Permission is hereby granted, free of charge, to any person obtaining a copy
4  * of this software and associated documentation files (the "Software"), to
5  * deal in the Software without restriction, including without limitation the
6  * rights to use, copy, modify, merge, publish, distribute, sublicense, and/or
7  * sell copies of the Software, and to permit persons to whom the Software is
8  * furnished to do so, subject to the following conditions:
9  *
10  * The above copyright notice and this permission notice shall be included in
11  * all copies or substantial portions of the Software.
12  *
13  * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
14  * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
15  * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
16  * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
17  * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
18  * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS
19  * IN THE SOFTWARE.
20  */
21 
22 #include "uv.h"
23 #include "internal.h"
24 
25 #include <stdlib.h>
26 #include <unistd.h>
27 #include <assert.h>
28 #include <errno.h>
29 
30 
new_socket(uv_tcp_t * handle,int domain,unsigned long flags)31 static int new_socket(uv_tcp_t* handle, int domain, unsigned long flags) {
32   struct sockaddr_storage saddr;
33   socklen_t slen;
34   int sockfd;
35   int err;
36 
37   err = uv__socket(domain, SOCK_STREAM, 0);
38   if (err < 0)
39     return err;
40   sockfd = err;
41 
42   err = uv__stream_open((uv_stream_t*) handle, sockfd, flags);
43   if (err) {
44     uv__close(sockfd);
45     return err;
46   }
47 
48   if (flags & UV_HANDLE_BOUND) {
49     /* Bind this new socket to an arbitrary port */
50     slen = sizeof(saddr);
51     memset(&saddr, 0, sizeof(saddr));
52     if (getsockname(uv__stream_fd(handle), (struct sockaddr*) &saddr, &slen)) {
53       uv__close(sockfd);
54       return UV__ERR(errno);
55     }
56 
57     if (bind(uv__stream_fd(handle), (struct sockaddr*) &saddr, slen)) {
58       uv__close(sockfd);
59       return UV__ERR(errno);
60     }
61   }
62 
63   return 0;
64 }
65 
66 
maybe_new_socket(uv_tcp_t * handle,int domain,unsigned long flags)67 static int maybe_new_socket(uv_tcp_t* handle, int domain, unsigned long flags) {
68   struct sockaddr_storage saddr;
69   socklen_t slen;
70 
71   if (domain == AF_UNSPEC) {
72     handle->flags |= flags;
73     return 0;
74   }
75 
76   if (uv__stream_fd(handle) != -1) {
77 
78     if (flags & UV_HANDLE_BOUND) {
79 
80       if (handle->flags & UV_HANDLE_BOUND) {
81         /* It is already bound to a port. */
82         handle->flags |= flags;
83         return 0;
84       }
85 
86       /* Query to see if tcp socket is bound. */
87       slen = sizeof(saddr);
88       memset(&saddr, 0, sizeof(saddr));
89       if (getsockname(uv__stream_fd(handle), (struct sockaddr*) &saddr, &slen))
90         return UV__ERR(errno);
91 
92       if ((saddr.ss_family == AF_INET6 &&
93           ((struct sockaddr_in6*) &saddr)->sin6_port != 0) ||
94           (saddr.ss_family == AF_INET &&
95           ((struct sockaddr_in*) &saddr)->sin_port != 0)) {
96         /* Handle is already bound to a port. */
97         handle->flags |= flags;
98         return 0;
99       }
100 
101       /* Bind to arbitrary port */
102       if (bind(uv__stream_fd(handle), (struct sockaddr*) &saddr, slen))
103         return UV__ERR(errno);
104     }
105 
106     handle->flags |= flags;
107     return 0;
108   }
109 
110   return new_socket(handle, domain, flags);
111 }
112 
113 
uv_tcp_init_ex(uv_loop_t * loop,uv_tcp_t * tcp,unsigned int flags)114 int uv_tcp_init_ex(uv_loop_t* loop, uv_tcp_t* tcp, unsigned int flags) {
115   int domain;
116 
117   /* Use the lower 8 bits for the domain */
118   domain = flags & 0xFF;
119   if (domain != AF_INET && domain != AF_INET6 && domain != AF_UNSPEC)
120     return UV_EINVAL;
121 
122   if (flags & ~0xFF)
123     return UV_EINVAL;
124 
125   uv__stream_init(loop, (uv_stream_t*)tcp, UV_TCP);
126 
127   /* If anything fails beyond this point we need to remove the handle from
128    * the handle queue, since it was added by uv__handle_init in uv_stream_init.
129    */
130 
131   if (domain != AF_UNSPEC) {
132     int err = maybe_new_socket(tcp, domain, 0);
133     if (err) {
134       QUEUE_REMOVE(&tcp->handle_queue);
135       return err;
136     }
137   }
138 
139   return 0;
140 }
141 
142 
uv_tcp_init(uv_loop_t * loop,uv_tcp_t * tcp)143 int uv_tcp_init(uv_loop_t* loop, uv_tcp_t* tcp) {
144   return uv_tcp_init_ex(loop, tcp, AF_UNSPEC);
145 }
146 
147 
uv__tcp_bind(uv_tcp_t * tcp,const struct sockaddr * addr,unsigned int addrlen,unsigned int flags)148 int uv__tcp_bind(uv_tcp_t* tcp,
149                  const struct sockaddr* addr,
150                  unsigned int addrlen,
151                  unsigned int flags) {
152   int err;
153   int on;
154 
155   /* Cannot set IPv6-only mode on non-IPv6 socket. */
156   if ((flags & UV_TCP_IPV6ONLY) && addr->sa_family != AF_INET6)
157     return UV_EINVAL;
158 
159   err = maybe_new_socket(tcp, addr->sa_family, 0);
160   if (err)
161     return err;
162 
163   on = 1;
164   if (setsockopt(tcp->io_watcher.fd, SOL_SOCKET, SO_REUSEADDR, &on, sizeof(on)))
165     return UV__ERR(errno);
166 
167 #ifndef __OpenBSD__
168 #ifdef IPV6_V6ONLY
169   if (addr->sa_family == AF_INET6) {
170     on = (flags & UV_TCP_IPV6ONLY) != 0;
171     if (setsockopt(tcp->io_watcher.fd,
172                    IPPROTO_IPV6,
173                    IPV6_V6ONLY,
174                    &on,
175                    sizeof on) == -1) {
176 #if defined(__MVS__)
177       if (errno == EOPNOTSUPP)
178         return UV_EINVAL;
179 #endif
180       return UV__ERR(errno);
181     }
182   }
183 #endif
184 #endif
185 
186   errno = 0;
187   if (bind(tcp->io_watcher.fd, addr, addrlen) && errno != EADDRINUSE) {
188     if (errno == EAFNOSUPPORT)
189       /* OSX, other BSDs and SunoS fail with EAFNOSUPPORT when binding a
190        * socket created with AF_INET to an AF_INET6 address or vice versa. */
191       return UV_EINVAL;
192     return UV__ERR(errno);
193   }
194   tcp->delayed_error = UV__ERR(errno);
195 
196   tcp->flags |= UV_HANDLE_BOUND;
197   if (addr->sa_family == AF_INET6)
198     tcp->flags |= UV_HANDLE_IPV6;
199 
200   return 0;
201 }
202 
203 
uv__tcp_connect(uv_connect_t * req,uv_tcp_t * handle,const struct sockaddr * addr,unsigned int addrlen,uv_connect_cb cb)204 int uv__tcp_connect(uv_connect_t* req,
205                     uv_tcp_t* handle,
206                     const struct sockaddr* addr,
207                     unsigned int addrlen,
208                     uv_connect_cb cb) {
209   int err;
210   int r;
211 
212   assert(handle->type == UV_TCP);
213 
214   if (handle->connect_req != NULL)
215     return UV_EALREADY;  /* FIXME(bnoordhuis) UV_EINVAL or maybe UV_EBUSY. */
216 
217   if (handle->delayed_error != 0)
218     goto out;
219 
220   err = maybe_new_socket(handle,
221                          addr->sa_family,
222                          UV_HANDLE_READABLE | UV_HANDLE_WRITABLE);
223   if (err)
224     return err;
225 
226   do {
227     errno = 0;
228     r = connect(uv__stream_fd(handle), addr, addrlen);
229   } while (r == -1 && errno == EINTR);
230 
231   /* We not only check the return value, but also check the errno != 0.
232    * Because in rare cases connect() will return -1 but the errno
233    * is 0 (for example, on Android 4.3, OnePlus phone A0001_12_150227)
234    * and actually the tcp three-way handshake is completed.
235    */
236   if (r == -1 && errno != 0) {
237     if (errno == EINPROGRESS)
238       ; /* not an error */
239     else if (errno == ECONNREFUSED
240 #if defined(__OpenBSD__)
241       || errno == EINVAL
242 #endif
243       )
244     /* If we get ECONNREFUSED (Solaris) or EINVAL (OpenBSD) wait until the
245      * next tick to report the error. Solaris and OpenBSD wants to report
246      * immediately -- other unixes want to wait.
247      */
248       handle->delayed_error = UV__ERR(ECONNREFUSED);
249     else
250       return UV__ERR(errno);
251   }
252 
253 out:
254 
255   uv__req_init(handle->loop, req, UV_CONNECT);
256   req->cb = cb;
257   req->handle = (uv_stream_t*) handle;
258   QUEUE_INIT(&req->queue);
259   handle->connect_req = req;
260 
261   uv__io_start(handle->loop, &handle->io_watcher, POLLOUT);
262 
263   if (handle->delayed_error)
264     uv__io_feed(handle->loop, &handle->io_watcher);
265 
266   return 0;
267 }
268 
269 
uv_tcp_open(uv_tcp_t * handle,uv_os_sock_t sock)270 int uv_tcp_open(uv_tcp_t* handle, uv_os_sock_t sock) {
271   int err;
272 
273   if (uv__fd_exists(handle->loop, sock))
274     return UV_EEXIST;
275 
276   err = uv__nonblock(sock, 1);
277   if (err)
278     return err;
279 
280   return uv__stream_open((uv_stream_t*)handle,
281                          sock,
282                          UV_HANDLE_READABLE | UV_HANDLE_WRITABLE);
283 }
284 
285 
uv_tcp_getsockname(const uv_tcp_t * handle,struct sockaddr * name,int * namelen)286 int uv_tcp_getsockname(const uv_tcp_t* handle,
287                        struct sockaddr* name,
288                        int* namelen) {
289 
290   if (handle->delayed_error)
291     return handle->delayed_error;
292 
293   return uv__getsockpeername((const uv_handle_t*) handle,
294                              getsockname,
295                              name,
296                              namelen);
297 }
298 
299 
uv_tcp_getpeername(const uv_tcp_t * handle,struct sockaddr * name,int * namelen)300 int uv_tcp_getpeername(const uv_tcp_t* handle,
301                        struct sockaddr* name,
302                        int* namelen) {
303 
304   if (handle->delayed_error)
305     return handle->delayed_error;
306 
307   return uv__getsockpeername((const uv_handle_t*) handle,
308                              getpeername,
309                              name,
310                              namelen);
311 }
312 
313 
uv_tcp_close_reset(uv_tcp_t * handle,uv_close_cb close_cb)314 int uv_tcp_close_reset(uv_tcp_t* handle, uv_close_cb close_cb) {
315   int fd;
316   struct linger l = { 1, 0 };
317 
318   /* Disallow setting SO_LINGER to zero due to some platform inconsistencies */
319   if (handle->flags & UV_HANDLE_SHUTTING)
320     return UV_EINVAL;
321 
322   fd = uv__stream_fd(handle);
323   if (0 != setsockopt(fd, SOL_SOCKET, SO_LINGER, &l, sizeof(l)))
324     return UV__ERR(errno);
325 
326   uv_close((uv_handle_t*) handle, close_cb);
327   return 0;
328 }
329 
330 
uv_tcp_listen(uv_tcp_t * tcp,int backlog,uv_connection_cb cb)331 int uv_tcp_listen(uv_tcp_t* tcp, int backlog, uv_connection_cb cb) {
332   static int single_accept_cached = -1;
333   unsigned long flags;
334   int single_accept;
335   int err;
336 
337   if (tcp->delayed_error)
338     return tcp->delayed_error;
339 
340   single_accept = uv__load_relaxed(&single_accept_cached);
341   if (single_accept == -1) {
342     const char* val = getenv("UV_TCP_SINGLE_ACCEPT");
343     single_accept = (val != NULL && atoi(val) != 0);  /* Off by default. */
344     uv__store_relaxed(&single_accept_cached, single_accept);
345   }
346 
347   if (single_accept)
348     tcp->flags |= UV_HANDLE_TCP_SINGLE_ACCEPT;
349 
350   flags = 0;
351 #if defined(__MVS__)
352   /* on zOS the listen call does not bind automatically
353      if the socket is unbound. Hence the manual binding to
354      an arbitrary port is required to be done manually
355   */
356   flags |= UV_HANDLE_BOUND;
357 #endif
358   err = maybe_new_socket(tcp, AF_INET, flags);
359   if (err)
360     return err;
361 
362   if (listen(tcp->io_watcher.fd, backlog))
363     return UV__ERR(errno);
364 
365   tcp->connection_cb = cb;
366   tcp->flags |= UV_HANDLE_BOUND;
367 
368   /* Start listening for connections. */
369   tcp->io_watcher.cb = uv__server_io;
370   uv__io_start(tcp->loop, &tcp->io_watcher, POLLIN);
371 
372   return 0;
373 }
374 
375 
uv__tcp_nodelay(int fd,int on)376 int uv__tcp_nodelay(int fd, int on) {
377   if (setsockopt(fd, IPPROTO_TCP, TCP_NODELAY, &on, sizeof(on)))
378     return UV__ERR(errno);
379   return 0;
380 }
381 
382 
uv__tcp_keepalive(int fd,int on,unsigned int delay)383 int uv__tcp_keepalive(int fd, int on, unsigned int delay) {
384   if (setsockopt(fd, SOL_SOCKET, SO_KEEPALIVE, &on, sizeof(on)))
385     return UV__ERR(errno);
386 
387 #ifdef TCP_KEEPIDLE
388   if (on) {
389     int intvl = 1;  /*  1 second; same as default on Win32 */
390     int cnt = 10;  /* 10 retries; same as hardcoded on Win32 */
391     if (setsockopt(fd, IPPROTO_TCP, TCP_KEEPIDLE, &delay, sizeof(delay)))
392       return UV__ERR(errno);
393     if (setsockopt(fd, IPPROTO_TCP, TCP_KEEPINTVL, &intvl, sizeof(intvl)))
394       return UV__ERR(errno);
395     if (setsockopt(fd, IPPROTO_TCP, TCP_KEEPCNT, &cnt, sizeof(cnt)))
396       return UV__ERR(errno);
397   }
398 #endif
399 
400   /* Solaris/SmartOS, if you don't support keep-alive,
401    * then don't advertise it in your system headers...
402    */
403   /* FIXME(bnoordhuis) That's possibly because sizeof(delay) should be 1. */
404 #if defined(TCP_KEEPALIVE) && !defined(__sun)
405   if (on && setsockopt(fd, IPPROTO_TCP, TCP_KEEPALIVE, &delay, sizeof(delay)))
406     return UV__ERR(errno);
407 #endif
408 
409   return 0;
410 }
411 
412 
uv_tcp_nodelay(uv_tcp_t * handle,int on)413 int uv_tcp_nodelay(uv_tcp_t* handle, int on) {
414   int err;
415 
416   if (uv__stream_fd(handle) != -1) {
417     err = uv__tcp_nodelay(uv__stream_fd(handle), on);
418     if (err)
419       return err;
420   }
421 
422   if (on)
423     handle->flags |= UV_HANDLE_TCP_NODELAY;
424   else
425     handle->flags &= ~UV_HANDLE_TCP_NODELAY;
426 
427   return 0;
428 }
429 
430 
uv_tcp_keepalive(uv_tcp_t * handle,int on,unsigned int delay)431 int uv_tcp_keepalive(uv_tcp_t* handle, int on, unsigned int delay) {
432   int err;
433 
434   if (uv__stream_fd(handle) != -1) {
435     err =uv__tcp_keepalive(uv__stream_fd(handle), on, delay);
436     if (err)
437       return err;
438   }
439 
440   if (on)
441     handle->flags |= UV_HANDLE_TCP_KEEPALIVE;
442   else
443     handle->flags &= ~UV_HANDLE_TCP_KEEPALIVE;
444 
445   /* TODO Store delay if uv__stream_fd(handle) == -1 but don't want to enlarge
446    *      uv_tcp_t with an int that's almost never used...
447    */
448 
449   return 0;
450 }
451 
452 
uv_tcp_simultaneous_accepts(uv_tcp_t * handle,int enable)453 int uv_tcp_simultaneous_accepts(uv_tcp_t* handle, int enable) {
454   if (enable)
455     handle->flags &= ~UV_HANDLE_TCP_SINGLE_ACCEPT;
456   else
457     handle->flags |= UV_HANDLE_TCP_SINGLE_ACCEPT;
458   return 0;
459 }
460 
461 
uv__tcp_close(uv_tcp_t * handle)462 void uv__tcp_close(uv_tcp_t* handle) {
463   uv__stream_close((uv_stream_t*)handle);
464 }
465 
466 
uv_socketpair(int type,int protocol,uv_os_sock_t fds[2],int flags0,int flags1)467 int uv_socketpair(int type, int protocol, uv_os_sock_t fds[2], int flags0, int flags1) {
468   uv_os_sock_t temp[2];
469   int err;
470 #if defined(__FreeBSD__) || defined(__linux__)
471   int flags;
472 
473   flags = type | SOCK_CLOEXEC;
474   if ((flags0 & UV_NONBLOCK_PIPE) && (flags1 & UV_NONBLOCK_PIPE))
475     flags |= SOCK_NONBLOCK;
476 
477   if (socketpair(AF_UNIX, flags, protocol, temp))
478     return UV__ERR(errno);
479 
480   if (flags & UV_FS_O_NONBLOCK) {
481     fds[0] = temp[0];
482     fds[1] = temp[1];
483     return 0;
484   }
485 #else
486   if (socketpair(AF_UNIX, type, protocol, temp))
487     return UV__ERR(errno);
488 
489   if ((err = uv__cloexec(temp[0], 1)))
490     goto fail;
491   if ((err = uv__cloexec(temp[1], 1)))
492     goto fail;
493 #endif
494 
495   if (flags0 & UV_NONBLOCK_PIPE)
496     if ((err = uv__nonblock(temp[0], 1)))
497         goto fail;
498   if (flags1 & UV_NONBLOCK_PIPE)
499     if ((err = uv__nonblock(temp[1], 1)))
500       goto fail;
501 
502   fds[0] = temp[0];
503   fds[1] = temp[1];
504   return 0;
505 
506 fail:
507   uv__close(temp[0]);
508   uv__close(temp[1]);
509   return err;
510 }
511