Curl_updateconninfo: don't do anything for UDP "connections"
[platform/upstream/curl.git] / lib / connect.c
1 /***************************************************************************
2  *                                  _   _ ____  _
3  *  Project                     ___| | | |  _ \| |
4  *                             / __| | | | |_) | |
5  *                            | (__| |_| |  _ <| |___
6  *                             \___|\___/|_| \_\_____|
7  *
8  * Copyright (C) 1998 - 2014, Daniel Stenberg, <daniel@haxx.se>, et al.
9  *
10  * This software is licensed as described in the file COPYING, which
11  * you should have received as part of this distribution. The terms
12  * are also available at http://curl.haxx.se/docs/copyright.html.
13  *
14  * You may opt to use, copy, modify, merge, publish, distribute and/or sell
15  * copies of the Software, and permit persons to whom the Software is
16  * furnished to do so, under the terms of the COPYING file.
17  *
18  * This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
19  * KIND, either express or implied.
20  *
21  ***************************************************************************/
22
23 #include "curl_setup.h"
24
25 #ifdef HAVE_NETINET_IN_H
26 #include <netinet/in.h> /* <netinet/tcp.h> may need it */
27 #endif
28 #ifdef HAVE_SYS_UN_H
29 #include <sys/un.h> /* for sockaddr_un */
30 #endif
31 #ifdef HAVE_NETINET_TCP_H
32 #include <netinet/tcp.h> /* for TCP_NODELAY */
33 #endif
34 #ifdef HAVE_SYS_IOCTL_H
35 #include <sys/ioctl.h>
36 #endif
37 #ifdef HAVE_NETDB_H
38 #include <netdb.h>
39 #endif
40 #ifdef HAVE_FCNTL_H
41 #include <fcntl.h>
42 #endif
43 #ifdef HAVE_ARPA_INET_H
44 #include <arpa/inet.h>
45 #endif
46
47 #if (defined(HAVE_IOCTL_FIONBIO) && defined(NETWARE))
48 #include <sys/filio.h>
49 #endif
50 #ifdef NETWARE
51 #undef in_addr_t
52 #define in_addr_t unsigned long
53 #endif
54 #ifdef __VMS
55 #include <in.h>
56 #include <inet.h>
57 #endif
58
59 #define _MPRINTF_REPLACE /* use our functions only */
60 #include <curl/mprintf.h>
61
62 #include "urldata.h"
63 #include "sendf.h"
64 #include "if2ip.h"
65 #include "strerror.h"
66 #include "connect.h"
67 #include "curl_memory.h"
68 #include "select.h"
69 #include "url.h" /* for Curl_safefree() */
70 #include "multiif.h"
71 #include "sockaddr.h" /* required for Curl_sockaddr_storage */
72 #include "inet_ntop.h"
73 #include "inet_pton.h"
74 #include "vtls/vtls.h" /* for Curl_ssl_check_cxn() */
75 #include "progress.h"
76 #include "warnless.h"
77 #include "conncache.h"
78 #include "multihandle.h"
79
80 /* The last #include file should be: */
81 #include "memdebug.h"
82
83 #ifdef __SYMBIAN32__
84 /* This isn't actually supported under Symbian OS */
85 #undef SO_NOSIGPIPE
86 #endif
87
88 static bool verifyconnect(curl_socket_t sockfd, int *error);
89
90 #if defined(__DragonFly__) || defined(HAVE_WINSOCK_H)
91 /* DragonFlyBSD and Windows use millisecond units */
92 #define KEEPALIVE_FACTOR(x) (x *= 1000)
93 #else
94 #define KEEPALIVE_FACTOR(x)
95 #endif
96
97 #if defined(HAVE_WINSOCK_H) && !defined(SIO_KEEPALIVE_VALS)
98 #define SIO_KEEPALIVE_VALS    _WSAIOW(IOC_VENDOR,4)
99
100 struct tcp_keepalive {
101   u_long onoff;
102   u_long keepalivetime;
103   u_long keepaliveinterval;
104 };
105 #endif
106
107 static void
108 tcpkeepalive(struct SessionHandle *data,
109              curl_socket_t sockfd)
110 {
111   int optval = data->set.tcp_keepalive?1:0;
112
113   /* only set IDLE and INTVL if setting KEEPALIVE is successful */
114   if(setsockopt(sockfd, SOL_SOCKET, SO_KEEPALIVE,
115         (void *)&optval, sizeof(optval)) < 0) {
116     infof(data, "Failed to set SO_KEEPALIVE on fd %d\n", sockfd);
117   }
118   else {
119 #if defined(SIO_KEEPALIVE_VALS)
120     struct tcp_keepalive vals;
121     DWORD dummy;
122     vals.onoff = 1;
123     optval = curlx_sltosi(data->set.tcp_keepidle);
124     KEEPALIVE_FACTOR(optval);
125     vals.keepalivetime = optval;
126     optval = curlx_sltosi(data->set.tcp_keepintvl);
127     KEEPALIVE_FACTOR(optval);
128     vals.keepaliveinterval = optval;
129     if(WSAIoctl(sockfd, SIO_KEEPALIVE_VALS, (LPVOID) &vals, sizeof(vals),
130                 NULL, 0, &dummy, NULL, NULL) != 0) {
131       infof(data, "Failed to set SIO_KEEPALIVE_VALS on fd %d: %d\n",
132             (int)sockfd, WSAGetLastError());
133     }
134 #else
135 #ifdef TCP_KEEPIDLE
136     optval = curlx_sltosi(data->set.tcp_keepidle);
137     KEEPALIVE_FACTOR(optval);
138     if(setsockopt(sockfd, IPPROTO_TCP, TCP_KEEPIDLE,
139           (void *)&optval, sizeof(optval)) < 0) {
140       infof(data, "Failed to set TCP_KEEPIDLE on fd %d\n", sockfd);
141     }
142 #endif
143 #ifdef TCP_KEEPINTVL
144     optval = curlx_sltosi(data->set.tcp_keepintvl);
145     KEEPALIVE_FACTOR(optval);
146     if(setsockopt(sockfd, IPPROTO_TCP, TCP_KEEPINTVL,
147           (void *)&optval, sizeof(optval)) < 0) {
148       infof(data, "Failed to set TCP_KEEPINTVL on fd %d\n", sockfd);
149     }
150 #endif
151 #ifdef TCP_KEEPALIVE
152     /* Mac OS X style */
153     optval = curlx_sltosi(data->set.tcp_keepidle);
154     KEEPALIVE_FACTOR(optval);
155     if(setsockopt(sockfd, IPPROTO_TCP, TCP_KEEPALIVE,
156           (void *)&optval, sizeof(optval)) < 0) {
157       infof(data, "Failed to set TCP_KEEPALIVE on fd %d\n", sockfd);
158     }
159 #endif
160 #endif
161   }
162 }
163
164 static CURLcode
165 singleipconnect(struct connectdata *conn,
166                 const Curl_addrinfo *ai, /* start connecting to this */
167                 curl_socket_t *sock);
168
169 /*
170  * Curl_timeleft() returns the amount of milliseconds left allowed for the
171  * transfer/connection. If the value is negative, the timeout time has already
172  * elapsed.
173  *
174  * The start time is stored in progress.t_startsingle - as set with
175  * Curl_pgrsTime(..., TIMER_STARTSINGLE);
176  *
177  * If 'nowp' is non-NULL, it points to the current time.
178  * 'duringconnect' is FALSE if not during a connect, as then of course the
179  * connect timeout is not taken into account!
180  *
181  * @unittest: 1303
182  */
183 long Curl_timeleft(struct SessionHandle *data,
184                    struct timeval *nowp,
185                    bool duringconnect)
186 {
187   int timeout_set = 0;
188   long timeout_ms = duringconnect?DEFAULT_CONNECT_TIMEOUT:0;
189   struct timeval now;
190
191   /* if a timeout is set, use the most restrictive one */
192
193   if(data->set.timeout > 0)
194     timeout_set |= 1;
195   if(duringconnect && (data->set.connecttimeout > 0))
196     timeout_set |= 2;
197
198   switch (timeout_set) {
199   case 1:
200     timeout_ms = data->set.timeout;
201     break;
202   case 2:
203     timeout_ms = data->set.connecttimeout;
204     break;
205   case 3:
206     if(data->set.timeout < data->set.connecttimeout)
207       timeout_ms = data->set.timeout;
208     else
209       timeout_ms = data->set.connecttimeout;
210     break;
211   default:
212     /* use the default */
213     if(!duringconnect)
214       /* if we're not during connect, there's no default timeout so if we're
215          at zero we better just return zero and not make it a negative number
216          by the math below */
217       return 0;
218     break;
219   }
220
221   if(!nowp) {
222     now = Curl_tvnow();
223     nowp = &now;
224   }
225
226   /* subtract elapsed time */
227   timeout_ms -= Curl_tvdiff(*nowp, data->progress.t_startsingle);
228   if(!timeout_ms)
229     /* avoid returning 0 as that means no timeout! */
230     return -1;
231
232   return timeout_ms;
233 }
234
235 static CURLcode bindlocal(struct connectdata *conn,
236                           curl_socket_t sockfd, int af)
237 {
238   struct SessionHandle *data = conn->data;
239
240   struct Curl_sockaddr_storage sa;
241   struct sockaddr *sock = (struct sockaddr *)&sa;  /* bind to this address */
242   curl_socklen_t sizeof_sa = 0; /* size of the data sock points to */
243   struct sockaddr_in *si4 = (struct sockaddr_in *)&sa;
244 #ifdef ENABLE_IPV6
245   struct sockaddr_in6 *si6 = (struct sockaddr_in6 *)&sa;
246 #endif
247
248   struct Curl_dns_entry *h=NULL;
249   unsigned short port = data->set.localport; /* use this port number, 0 for
250                                                 "random" */
251   /* how many port numbers to try to bind to, increasing one at a time */
252   int portnum = data->set.localportrange;
253   const char *dev = data->set.str[STRING_DEVICE];
254   int error;
255   char myhost[256] = "";
256   int done = 0; /* -1 for error, 1 for address found */
257   bool is_interface = FALSE;
258   bool is_host = FALSE;
259   static const char *if_prefix = "if!";
260   static const char *host_prefix = "host!";
261
262   /*************************************************************
263    * Select device to bind socket to
264    *************************************************************/
265   if(!dev && !port)
266     /* no local kind of binding was requested */
267     return CURLE_OK;
268
269   memset(&sa, 0, sizeof(struct Curl_sockaddr_storage));
270
271   if(dev && (strlen(dev)<255) ) {
272     if(strncmp(if_prefix, dev, strlen(if_prefix)) == 0) {
273       dev += strlen(if_prefix);
274       is_interface = TRUE;
275     }
276     else if(strncmp(host_prefix, dev, strlen(host_prefix)) == 0) {
277       dev += strlen(host_prefix);
278       is_host = TRUE;
279     }
280
281     /* interface */
282     if(!is_host) {
283       switch(Curl_if2ip(af, conn->scope, dev, myhost, sizeof(myhost))) {
284         case IF2IP_NOT_FOUND:
285           if(is_interface) {
286             /* Do not fall back to treating it as a host name */
287             failf(data, "Couldn't bind to interface '%s'", dev);
288             return CURLE_INTERFACE_FAILED;
289           }
290           break;
291         case IF2IP_AF_NOT_SUPPORTED:
292           /* Signal the caller to try another address family if available */
293           return CURLE_UNSUPPORTED_PROTOCOL;
294         case IF2IP_FOUND:
295           is_interface = TRUE;
296           /*
297            * We now have the numerical IP address in the 'myhost' buffer
298            */
299           infof(data, "Local Interface %s is ip %s using address family %i\n",
300                 dev, myhost, af);
301           done = 1;
302
303 #ifdef SO_BINDTODEVICE
304           /* I am not sure any other OSs than Linux that provide this feature,
305            * and at the least I cannot test. --Ben
306            *
307            * This feature allows one to tightly bind the local socket to a
308            * particular interface.  This will force even requests to other
309            * local interfaces to go out the external interface.
310            *
311            *
312            * Only bind to the interface when specified as interface, not just
313            * as a hostname or ip address.
314            */
315           if(setsockopt(sockfd, SOL_SOCKET, SO_BINDTODEVICE,
316                         dev, (curl_socklen_t)strlen(dev)+1) != 0) {
317             error = SOCKERRNO;
318             infof(data, "SO_BINDTODEVICE %s failed with errno %d: %s;"
319                   " will do regular bind\n",
320                   dev, error, Curl_strerror(conn, error));
321             /* This is typically "errno 1, error: Operation not permitted" if
322                you're not running as root or another suitable privileged
323                user */
324           }
325 #endif
326           break;
327       }
328     }
329     if(!is_interface) {
330       /*
331        * This was not an interface, resolve the name as a host name
332        * or IP number
333        *
334        * Temporarily force name resolution to use only the address type
335        * of the connection. The resolve functions should really be changed
336        * to take a type parameter instead.
337        */
338       long ipver = conn->ip_version;
339       int rc;
340
341       if(af == AF_INET)
342         conn->ip_version = CURL_IPRESOLVE_V4;
343 #ifdef ENABLE_IPV6
344       else if(af == AF_INET6)
345         conn->ip_version = CURL_IPRESOLVE_V6;
346 #endif
347
348       rc = Curl_resolv(conn, dev, 0, &h);
349       if(rc == CURLRESOLV_PENDING)
350         (void)Curl_resolver_wait_resolv(conn, &h);
351       conn->ip_version = ipver;
352
353       if(h) {
354         /* convert the resolved address, sizeof myhost >= INET_ADDRSTRLEN */
355         Curl_printable_address(h->addr, myhost, sizeof(myhost));
356         infof(data, "Name '%s' family %i resolved to '%s' family %i\n",
357               dev, af, myhost, h->addr->ai_family);
358         Curl_resolv_unlock(data, h);
359         done = 1;
360       }
361       else {
362         /*
363          * provided dev was no interface (or interfaces are not supported
364          * e.g. solaris) no ip address and no domain we fail here
365          */
366         done = -1;
367       }
368     }
369
370     if(done > 0) {
371 #ifdef ENABLE_IPV6
372       /* ipv6 address */
373       if(af == AF_INET6) {
374 #ifdef HAVE_SOCKADDR_IN6_SIN6_SCOPE_ID
375         char *scope_ptr = strchr(myhost, '%');
376         if(scope_ptr)
377           *(scope_ptr++) = 0;
378 #endif
379         if(Curl_inet_pton(AF_INET6, myhost, &si6->sin6_addr) > 0) {
380           si6->sin6_family = AF_INET6;
381           si6->sin6_port = htons(port);
382 #ifdef HAVE_SOCKADDR_IN6_SIN6_SCOPE_ID
383           if(scope_ptr)
384             /* The "myhost" string either comes from Curl_if2ip or from
385                Curl_printable_address. The latter returns only numeric scope
386                IDs and the former returns none at all.  So the scope ID, if
387                present, is known to be numeric */
388             si6->sin6_scope_id = atoi(scope_ptr);
389 #endif
390         }
391         sizeof_sa = sizeof(struct sockaddr_in6);
392       }
393       else
394 #endif
395       /* ipv4 address */
396       if((af == AF_INET) &&
397          (Curl_inet_pton(AF_INET, myhost, &si4->sin_addr) > 0)) {
398         si4->sin_family = AF_INET;
399         si4->sin_port = htons(port);
400         sizeof_sa = sizeof(struct sockaddr_in);
401       }
402     }
403
404     if(done < 1) {
405       failf(data, "Couldn't bind to '%s'", dev);
406       return CURLE_INTERFACE_FAILED;
407     }
408   }
409   else {
410     /* no device was given, prepare sa to match af's needs */
411 #ifdef ENABLE_IPV6
412     if(af == AF_INET6) {
413       si6->sin6_family = AF_INET6;
414       si6->sin6_port = htons(port);
415       sizeof_sa = sizeof(struct sockaddr_in6);
416     }
417     else
418 #endif
419     if(af == AF_INET) {
420       si4->sin_family = AF_INET;
421       si4->sin_port = htons(port);
422       sizeof_sa = sizeof(struct sockaddr_in);
423     }
424   }
425
426   for(;;) {
427     if(bind(sockfd, sock, sizeof_sa) >= 0) {
428       /* we succeeded to bind */
429       struct Curl_sockaddr_storage add;
430       curl_socklen_t size = sizeof(add);
431       memset(&add, 0, sizeof(struct Curl_sockaddr_storage));
432       if(getsockname(sockfd, (struct sockaddr *) &add, &size) < 0) {
433         data->state.os_errno = error = SOCKERRNO;
434         failf(data, "getsockname() failed with errno %d: %s",
435               error, Curl_strerror(conn, error));
436         return CURLE_INTERFACE_FAILED;
437       }
438       infof(data, "Local port: %hu\n", port);
439       conn->bits.bound = TRUE;
440       return CURLE_OK;
441     }
442
443     if(--portnum > 0) {
444       infof(data, "Bind to local port %hu failed, trying next\n", port);
445       port++; /* try next port */
446       /* We re-use/clobber the port variable here below */
447       if(sock->sa_family == AF_INET)
448         si4->sin_port = ntohs(port);
449 #ifdef ENABLE_IPV6
450       else
451         si6->sin6_port = ntohs(port);
452 #endif
453     }
454     else
455       break;
456   }
457
458   data->state.os_errno = error = SOCKERRNO;
459   failf(data, "bind failed with errno %d: %s",
460         error, Curl_strerror(conn, error));
461
462   return CURLE_INTERFACE_FAILED;
463 }
464
465 /*
466  * verifyconnect() returns TRUE if the connect really has happened.
467  */
468 static bool verifyconnect(curl_socket_t sockfd, int *error)
469 {
470   bool rc = TRUE;
471 #ifdef SO_ERROR
472   int err = 0;
473   curl_socklen_t errSize = sizeof(err);
474
475 #ifdef WIN32
476   /*
477    * In October 2003 we effectively nullified this function on Windows due to
478    * problems with it using all CPU in multi-threaded cases.
479    *
480    * In May 2004, we bring it back to offer more info back on connect failures.
481    * Gisle Vanem could reproduce the former problems with this function, but
482    * could avoid them by adding this SleepEx() call below:
483    *
484    *    "I don't have Rational Quantify, but the hint from his post was
485    *    ntdll::NtRemoveIoCompletion(). So I'd assume the SleepEx (or maybe
486    *    just Sleep(0) would be enough?) would release whatever
487    *    mutex/critical-section the ntdll call is waiting on.
488    *
489    *    Someone got to verify this on Win-NT 4.0, 2000."
490    */
491
492 #ifdef _WIN32_WCE
493   Sleep(0);
494 #else
495   SleepEx(0, FALSE);
496 #endif
497
498 #endif
499
500   if(0 != getsockopt(sockfd, SOL_SOCKET, SO_ERROR, (void *)&err, &errSize))
501     err = SOCKERRNO;
502 #ifdef _WIN32_WCE
503   /* Old WinCE versions don't support SO_ERROR */
504   if(WSAENOPROTOOPT == err) {
505     SET_SOCKERRNO(0);
506     err = 0;
507   }
508 #endif
509 #ifdef __minix
510   /* Minix 3.1.x doesn't support getsockopt on UDP sockets */
511   if(EBADIOCTL == err) {
512     SET_SOCKERRNO(0);
513     err = 0;
514   }
515 #endif
516   if((0 == err) || (EISCONN == err))
517     /* we are connected, awesome! */
518     rc = TRUE;
519   else
520     /* This wasn't a successful connect */
521     rc = FALSE;
522   if(error)
523     *error = err;
524 #else
525   (void)sockfd;
526   if(error)
527     *error = SOCKERRNO;
528 #endif
529   return rc;
530 }
531
532 /* Used within the multi interface. Try next IP address, return TRUE if no
533    more address exists or error */
534 static CURLcode trynextip(struct connectdata *conn,
535                           int sockindex,
536                           int tempindex)
537 {
538   CURLcode rc = CURLE_COULDNT_CONNECT;
539
540   /* First clean up after the failed socket.
541      Don't close it yet to ensure that the next IP's socket gets a different
542      file descriptor, which can prevent bugs when the curl_multi_socket_action
543      interface is used with certain select() replacements such as kqueue. */
544   curl_socket_t fd_to_close = conn->tempsock[tempindex];
545   conn->tempsock[tempindex] = CURL_SOCKET_BAD;
546
547   if(sockindex == FIRSTSOCKET) {
548     Curl_addrinfo *ai;
549     int family;
550
551     if(conn->tempaddr[tempindex]) {
552       /* find next address in the same protocol family */
553       family = conn->tempaddr[tempindex]->ai_family;
554       ai = conn->tempaddr[tempindex]->ai_next;
555     }
556     else {
557       /* happy eyeballs - try the other protocol family */
558       int firstfamily = conn->tempaddr[0]->ai_family;
559 #ifdef ENABLE_IPV6
560       family = (firstfamily == AF_INET) ? AF_INET6 : AF_INET;
561 #else
562       family = firstfamily;
563 #endif
564       ai = conn->tempaddr[0]->ai_next;
565     }
566
567     while(ai) {
568       while(ai && ai->ai_family != family)
569         ai = ai->ai_next;
570
571       if(ai) {
572         rc = singleipconnect(conn, ai, &conn->tempsock[tempindex]);
573         conn->tempaddr[tempindex] = ai;
574         if(rc == CURLE_COULDNT_CONNECT) {
575           ai = ai->ai_next;
576           continue;
577         }
578       }
579       break;
580     }
581   }
582
583   if(fd_to_close != CURL_SOCKET_BAD)
584     Curl_closesocket(conn, fd_to_close);
585
586   return rc;
587 }
588
589 /* Copies connection info into the session handle to make it available
590    when the session handle is no longer associated with a connection. */
591 void Curl_persistconninfo(struct connectdata *conn)
592 {
593   memcpy(conn->data->info.conn_primary_ip, conn->primary_ip, MAX_IPADR_LEN);
594   memcpy(conn->data->info.conn_local_ip, conn->local_ip, MAX_IPADR_LEN);
595   conn->data->info.conn_primary_port = conn->primary_port;
596   conn->data->info.conn_local_port = conn->local_port;
597 }
598
599 /* retrieves ip address and port from a sockaddr structure */
600 static bool getaddressinfo(struct sockaddr* sa, char* addr,
601                            long* port)
602 {
603   unsigned short us_port;
604   struct sockaddr_in* si = NULL;
605 #ifdef ENABLE_IPV6
606   struct sockaddr_in6* si6 = NULL;
607 #endif
608 #if defined(HAVE_SYS_UN_H) && defined(AF_UNIX)
609   struct sockaddr_un* su = NULL;
610 #endif
611
612   switch (sa->sa_family) {
613     case AF_INET:
614       si = (struct sockaddr_in*) sa;
615       if(Curl_inet_ntop(sa->sa_family, &si->sin_addr,
616                         addr, MAX_IPADR_LEN)) {
617         us_port = ntohs(si->sin_port);
618         *port = us_port;
619         return TRUE;
620       }
621       break;
622 #ifdef ENABLE_IPV6
623     case AF_INET6:
624       si6 = (struct sockaddr_in6*)sa;
625       if(Curl_inet_ntop(sa->sa_family, &si6->sin6_addr,
626                         addr, MAX_IPADR_LEN)) {
627         us_port = ntohs(si6->sin6_port);
628         *port = us_port;
629         return TRUE;
630       }
631       break;
632 #endif
633 #if defined(HAVE_SYS_UN_H) && defined(AF_UNIX)
634     case AF_UNIX:
635       su = (struct sockaddr_un*)sa;
636       snprintf(addr, MAX_IPADR_LEN, "%s", su->sun_path);
637       *port = 0;
638       return TRUE;
639 #endif
640     default:
641       break;
642   }
643
644   addr[0] = '\0';
645   *port = 0;
646
647   return FALSE;
648 }
649
650 /* retrieves the start/end point information of a socket of an established
651    connection */
652 void Curl_updateconninfo(struct connectdata *conn, curl_socket_t sockfd)
653 {
654   int error;
655   curl_socklen_t len;
656   struct Curl_sockaddr_storage ssrem;
657   struct Curl_sockaddr_storage ssloc;
658   struct SessionHandle *data = conn->data;
659
660   if(conn->socktype == SOCK_DGRAM)
661     /* there's no connection! */
662     return;
663
664   if(!conn->bits.reuse) {
665
666     len = sizeof(struct Curl_sockaddr_storage);
667     if(getpeername(sockfd, (struct sockaddr*) &ssrem, &len)) {
668       error = SOCKERRNO;
669       failf(data, "getpeername() failed with errno %d: %s",
670             error, Curl_strerror(conn, error));
671       return;
672     }
673
674     len = sizeof(struct Curl_sockaddr_storage);
675     if(getsockname(sockfd, (struct sockaddr*) &ssloc, &len)) {
676       error = SOCKERRNO;
677       failf(data, "getsockname() failed with errno %d: %s",
678             error, Curl_strerror(conn, error));
679       return;
680     }
681
682     if(!getaddressinfo((struct sockaddr*)&ssrem,
683                         conn->primary_ip, &conn->primary_port)) {
684       error = ERRNO;
685       failf(data, "ssrem inet_ntop() failed with errno %d: %s",
686             error, Curl_strerror(conn, error));
687       return;
688     }
689     memcpy(conn->ip_addr_str, conn->primary_ip, MAX_IPADR_LEN);
690
691     if(!getaddressinfo((struct sockaddr*)&ssloc,
692                        conn->local_ip, &conn->local_port)) {
693       error = ERRNO;
694       failf(data, "ssloc inet_ntop() failed with errno %d: %s",
695             error, Curl_strerror(conn, error));
696       return;
697     }
698
699   }
700
701   /* persist connection info in session handle */
702   Curl_persistconninfo(conn);
703 }
704
705 /*
706  * Curl_is_connected() checks if the socket has connected.
707  */
708
709 CURLcode Curl_is_connected(struct connectdata *conn,
710                            int sockindex,
711                            bool *connected)
712 {
713   struct SessionHandle *data = conn->data;
714   CURLcode code = CURLE_OK;
715   long allow;
716   int error = 0;
717   struct timeval now;
718   int result;
719   int i;
720
721   DEBUGASSERT(sockindex >= FIRSTSOCKET && sockindex <= SECONDARYSOCKET);
722
723   *connected = FALSE; /* a very negative world view is best */
724
725   if(conn->bits.tcpconnect[sockindex]) {
726     /* we are connected already! */
727     *connected = TRUE;
728     return CURLE_OK;
729   }
730
731   now = Curl_tvnow();
732
733   /* figure out how long time we have left to connect */
734   allow = Curl_timeleft(data, &now, TRUE);
735
736   if(allow < 0) {
737     /* time-out, bail out, go home */
738     failf(data, "Connection time-out");
739     return CURLE_OPERATION_TIMEDOUT;
740   }
741
742   for(i=0; i<2; i++) {
743     if(conn->tempsock[i] == CURL_SOCKET_BAD)
744       continue;
745
746 #ifdef mpeix
747     /* Call this function once now, and ignore the results. We do this to
748        "clear" the error state on the socket so that we can later read it
749        reliably. This is reported necessary on the MPE/iX operating system. */
750     (void)verifyconnect(conn->tempsock[i], NULL);
751 #endif
752
753     /* check socket for connect */
754     result = Curl_socket_ready(CURL_SOCKET_BAD, conn->tempsock[i], 0);
755
756     if(result == 0) { /* no connection yet */
757       if(curlx_tvdiff(now, conn->connecttime) >= conn->timeoutms_per_addr) {
758         infof(data, "After %ldms connect time, move on!\n",
759               conn->timeoutms_per_addr);
760         error = ETIMEDOUT;
761       }
762
763       /* should we try another protocol family? */
764       if(i == 0 && conn->tempaddr[1] == NULL &&
765          curlx_tvdiff(now, conn->connecttime) >= HAPPY_EYEBALLS_TIMEOUT) {
766         trynextip(conn, sockindex, 1);
767       }
768     }
769     else if(result == CURL_CSELECT_OUT) {
770       if(verifyconnect(conn->tempsock[i], &error)) {
771         /* we are connected with TCP, awesome! */
772         int other = i ^ 1;
773
774         /* use this socket from now on */
775         conn->sock[sockindex] = conn->tempsock[i];
776         conn->ip_addr = conn->tempaddr[i];
777         conn->tempsock[i] = CURL_SOCKET_BAD;
778
779         /* close the other socket, if open */
780         if(conn->tempsock[other] != CURL_SOCKET_BAD) {
781           Curl_closesocket(conn, conn->tempsock[other]);
782           conn->tempsock[other] = CURL_SOCKET_BAD;
783         }
784
785         /* see if we need to do any proxy magic first once we connected */
786         code = Curl_connected_proxy(conn, sockindex);
787         if(code)
788           return code;
789
790         conn->bits.tcpconnect[sockindex] = TRUE;
791
792         *connected = TRUE;
793         if(sockindex == FIRSTSOCKET)
794           Curl_pgrsTime(data, TIMER_CONNECT); /* connect done */
795         Curl_updateconninfo(conn, conn->sock[sockindex]);
796         Curl_verboseconnect(conn);
797
798         return CURLE_OK;
799       }
800       else
801         infof(data, "Connection failed\n");
802     }
803     else if(result & CURL_CSELECT_ERR)
804       (void)verifyconnect(conn->tempsock[i], &error);
805
806     /*
807      * The connection failed here, we should attempt to connect to the "next
808      * address" for the given host. But first remember the latest error.
809      */
810     if(error) {
811       char ipaddress[MAX_IPADR_LEN];
812       data->state.os_errno = error;
813       SET_SOCKERRNO(error);
814       Curl_printable_address(conn->tempaddr[i], ipaddress, MAX_IPADR_LEN);
815       infof(data, "connect to %s port %ld failed: %s\n",
816             ipaddress, conn->port, Curl_strerror(conn, error));
817
818       conn->timeoutms_per_addr = conn->tempaddr[i]->ai_next == NULL ?
819                                  allow : allow / 2;
820
821       code = trynextip(conn, sockindex, i);
822     }
823   }
824
825   if(code) {
826     /* no more addresses to try */
827
828     /* if the first address family runs out of addresses to try before
829        the happy eyeball timeout, go ahead and try the next family now */
830     if(conn->tempaddr[1] == NULL) {
831       int rc;
832       rc = trynextip(conn, sockindex, 1);
833       if(rc == CURLE_OK)
834         return CURLE_OK;
835     }
836
837     failf(data, "Failed to connect to %s port %ld: %s",
838           conn->bits.proxy?conn->proxy.name:conn->host.name,
839           conn->port, Curl_strerror(conn, error));
840   }
841
842   return code;
843 }
844
845 static void tcpnodelay(struct connectdata *conn,
846                        curl_socket_t sockfd)
847 {
848 #ifdef TCP_NODELAY
849   struct SessionHandle *data= conn->data;
850   curl_socklen_t onoff = (curl_socklen_t) data->set.tcp_nodelay;
851   int level = IPPROTO_TCP;
852
853 #if 0
854   /* The use of getprotobyname() is disabled since it isn't thread-safe on
855      numerous systems. On these getprotobyname_r() should be used instead, but
856      that exists in at least one 4 arg version and one 5 arg version, and
857      since the proto number rarely changes anyway we now just use the hard
858      coded number. The "proper" fix would need a configure check for the
859      correct function much in the same style the gethostbyname_r versions are
860      detected. */
861   struct protoent *pe = getprotobyname("tcp");
862   if(pe)
863     level = pe->p_proto;
864 #endif
865
866   if(setsockopt(sockfd, level, TCP_NODELAY, (void *)&onoff,
867                 sizeof(onoff)) < 0)
868     infof(data, "Could not set TCP_NODELAY: %s\n",
869           Curl_strerror(conn, SOCKERRNO));
870   else
871     infof(data,"TCP_NODELAY set\n");
872 #else
873   (void)conn;
874   (void)sockfd;
875 #endif
876 }
877
878 #ifdef SO_NOSIGPIPE
879 /* The preferred method on Mac OS X (10.2 and later) to prevent SIGPIPEs when
880    sending data to a dead peer (instead of relying on the 4th argument to send
881    being MSG_NOSIGNAL). Possibly also existing and in use on other BSD
882    systems? */
883 static void nosigpipe(struct connectdata *conn,
884                       curl_socket_t sockfd)
885 {
886   struct SessionHandle *data= conn->data;
887   int onoff = 1;
888   if(setsockopt(sockfd, SOL_SOCKET, SO_NOSIGPIPE, (void *)&onoff,
889                 sizeof(onoff)) < 0)
890     infof(data, "Could not set SO_NOSIGPIPE: %s\n",
891           Curl_strerror(conn, SOCKERRNO));
892 }
893 #else
894 #define nosigpipe(x,y) Curl_nop_stmt
895 #endif
896
897 #ifdef USE_WINSOCK
898 /* When you run a program that uses the Windows Sockets API, you may
899    experience slow performance when you copy data to a TCP server.
900
901    http://support.microsoft.com/kb/823764
902
903    Work-around: Make the Socket Send Buffer Size Larger Than the Program Send
904    Buffer Size
905
906    The problem described in this knowledge-base is applied only to pre-Vista
907    Windows.  Following function trying to detect OS version and skips
908    SO_SNDBUF adjustment for Windows Vista and above.
909 */
910 #define DETECT_OS_NONE 0
911 #define DETECT_OS_PREVISTA 1
912 #define DETECT_OS_VISTA_OR_LATER 2
913
914 void Curl_sndbufset(curl_socket_t sockfd)
915 {
916   int val = CURL_MAX_WRITE_SIZE + 32;
917   int curval = 0;
918   int curlen = sizeof(curval);
919
920   OSVERSIONINFO osver;
921   static int detectOsState = DETECT_OS_NONE;
922
923   if(detectOsState == DETECT_OS_NONE) {
924     memset(&osver, 0, sizeof(osver));
925     osver.dwOSVersionInfoSize = sizeof(osver);
926     detectOsState = DETECT_OS_PREVISTA;
927     if(GetVersionEx(&osver)) {
928       if(osver.dwMajorVersion >= 6)
929         detectOsState = DETECT_OS_VISTA_OR_LATER;
930     }
931   }
932   if(detectOsState == DETECT_OS_VISTA_OR_LATER)
933     return;
934
935   if(getsockopt(sockfd, SOL_SOCKET, SO_SNDBUF, (char *)&curval, &curlen) == 0)
936     if(curval > val)
937       return;
938
939   setsockopt(sockfd, SOL_SOCKET, SO_SNDBUF, (const char *)&val, sizeof(val));
940 }
941 #endif
942
943
944 /*
945  * singleipconnect()
946  *
947  * Note that even on connect fail it returns CURLE_OK, but with 'sock' set to
948  * CURL_SOCKET_BAD. Other errors will however return proper errors.
949  *
950  * singleipconnect() connects to the given IP only, and it may return without
951  * having connected.
952  */
953 static CURLcode
954 singleipconnect(struct connectdata *conn,
955                 const Curl_addrinfo *ai,
956                 curl_socket_t *sockp)
957 {
958   struct Curl_sockaddr_ex addr;
959   int rc;
960   int error = 0;
961   bool isconnected = FALSE;
962   struct SessionHandle *data = conn->data;
963   curl_socket_t sockfd;
964   CURLcode res = CURLE_OK;
965   char ipaddress[MAX_IPADR_LEN];
966   long port;
967
968   *sockp = CURL_SOCKET_BAD;
969
970   res = Curl_socket(conn, ai, &addr, &sockfd);
971   if(res)
972     /* Failed to create the socket, but still return OK since we signal the
973        lack of socket as well. This allows the parent function to keep looping
974        over alternative addresses/socket families etc. */
975     return CURLE_OK;
976
977   /* store remote address and port used in this connection attempt */
978   if(!getaddressinfo((struct sockaddr*)&addr.sa_addr,
979                      ipaddress, &port)) {
980     /* malformed address or bug in inet_ntop, try next address */
981     error = ERRNO;
982     failf(data, "sa_addr inet_ntop() failed with errno %d: %s",
983           error, Curl_strerror(conn, error));
984     Curl_closesocket(conn, sockfd);
985     return CURLE_OK;
986   }
987   infof(data, "  Trying %s...\n", ipaddress);
988
989   if(data->set.tcp_nodelay)
990     tcpnodelay(conn, sockfd);
991
992   nosigpipe(conn, sockfd);
993
994   Curl_sndbufset(sockfd);
995
996   if(data->set.tcp_keepalive)
997     tcpkeepalive(data, sockfd);
998
999   if(data->set.fsockopt) {
1000     /* activate callback for setting socket options */
1001     error = data->set.fsockopt(data->set.sockopt_client,
1002                                sockfd,
1003                                CURLSOCKTYPE_IPCXN);
1004
1005     if(error == CURL_SOCKOPT_ALREADY_CONNECTED)
1006       isconnected = TRUE;
1007     else if(error) {
1008       Curl_closesocket(conn, sockfd); /* close the socket and bail out */
1009       return CURLE_ABORTED_BY_CALLBACK;
1010     }
1011   }
1012
1013   /* possibly bind the local end to an IP, interface or port */
1014   res = bindlocal(conn, sockfd, addr.family);
1015   if(res) {
1016     Curl_closesocket(conn, sockfd); /* close socket and bail out */
1017     if(res == CURLE_UNSUPPORTED_PROTOCOL) {
1018       /* The address family is not supported on this interface.
1019          We can continue trying addresses */
1020       return CURLE_OK;
1021     }
1022     return res;
1023   }
1024
1025   /* set socket non-blocking */
1026   curlx_nonblock(sockfd, TRUE);
1027
1028   conn->connecttime = Curl_tvnow();
1029   if(conn->num_addr > 1)
1030     Curl_expire(data, conn->timeoutms_per_addr);
1031
1032   /* Connect TCP sockets, bind UDP */
1033   if(!isconnected && (conn->socktype == SOCK_STREAM)) {
1034     rc = connect(sockfd, &addr.sa_addr, addr.addrlen);
1035     if(-1 == rc)
1036       error = SOCKERRNO;
1037   }
1038   else {
1039     *sockp = sockfd;
1040     return CURLE_OK;
1041   }
1042
1043 #ifdef ENABLE_IPV6
1044   conn->bits.ipv6 = (addr.family == AF_INET6)?TRUE:FALSE;
1045 #endif
1046
1047   if(-1 == rc) {
1048     switch(error) {
1049     case EINPROGRESS:
1050     case EWOULDBLOCK:
1051 #if defined(EAGAIN)
1052 #if (EAGAIN) != (EWOULDBLOCK)
1053       /* On some platforms EAGAIN and EWOULDBLOCK are the
1054        * same value, and on others they are different, hence
1055        * the odd #if
1056        */
1057     case EAGAIN:
1058 #endif
1059 #endif
1060       res = CURLE_OK;
1061       break;
1062
1063     default:
1064       /* unknown error, fallthrough and try another address! */
1065       infof(data, "Immediate connect fail for %s: %s\n",
1066             ipaddress, Curl_strerror(conn,error));
1067       data->state.os_errno = error;
1068
1069       /* connect failed */
1070       Curl_closesocket(conn, sockfd);
1071       res = CURLE_COULDNT_CONNECT;
1072     }
1073   }
1074
1075   if(!res)
1076     *sockp = sockfd;
1077
1078   return res;
1079 }
1080
1081 /*
1082  * TCP connect to the given host with timeout, proxy or remote doesn't matter.
1083  * There might be more than one IP address to try out. Fill in the passed
1084  * pointer with the connected socket.
1085  */
1086
1087 CURLcode Curl_connecthost(struct connectdata *conn,  /* context */
1088                           const struct Curl_dns_entry *remotehost)
1089 {
1090   struct SessionHandle *data = conn->data;
1091   struct timeval before = Curl_tvnow();
1092   CURLcode res = CURLE_COULDNT_CONNECT;
1093
1094   long timeout_ms = Curl_timeleft(data, &before, TRUE);
1095
1096   if(timeout_ms < 0) {
1097     /* a precaution, no need to continue if time already is up */
1098     failf(data, "Connection time-out");
1099     return CURLE_OPERATION_TIMEDOUT;
1100   }
1101
1102   conn->num_addr = Curl_num_addresses(remotehost->addr);
1103   conn->tempaddr[0] = remotehost->addr;
1104   conn->tempaddr[1] = NULL;
1105   conn->tempsock[0] = CURL_SOCKET_BAD;
1106   conn->tempsock[1] = CURL_SOCKET_BAD;
1107   Curl_expire(conn->data,
1108               HAPPY_EYEBALLS_TIMEOUT + (MULTI_TIMEOUT_INACCURACY/1000));
1109
1110   /* Max time for the next connection attempt */
1111   conn->timeoutms_per_addr =
1112     conn->tempaddr[0]->ai_next == NULL ? timeout_ms : timeout_ms / 2;
1113
1114   /* start connecting to first IP */
1115   while(conn->tempaddr[0]) {
1116     res = singleipconnect(conn, conn->tempaddr[0], &(conn->tempsock[0]));
1117     if(res == CURLE_OK)
1118         break;
1119     conn->tempaddr[0] = conn->tempaddr[0]->ai_next;
1120   }
1121
1122   if(conn->tempsock[0] == CURL_SOCKET_BAD)
1123     return res;
1124
1125   data->info.numconnects++; /* to track the number of connections made */
1126
1127   return CURLE_OK;
1128 }
1129
1130 struct connfind {
1131   struct connectdata *tofind;
1132   bool found;
1133 };
1134
1135 static int conn_is_conn(struct connectdata *conn, void *param)
1136 {
1137   struct connfind *f = (struct connfind *)param;
1138   if(conn == f->tofind) {
1139     f->found = TRUE;
1140     return 1;
1141   }
1142   return 0;
1143 }
1144
1145 /*
1146  * Used to extract socket and connectdata struct for the most recent
1147  * transfer on the given SessionHandle.
1148  *
1149  * The returned socket will be CURL_SOCKET_BAD in case of failure!
1150  */
1151 curl_socket_t Curl_getconnectinfo(struct SessionHandle *data,
1152                                   struct connectdata **connp)
1153 {
1154   curl_socket_t sockfd;
1155
1156   DEBUGASSERT(data);
1157
1158   /* this only works for an easy handle that has been used for
1159      curl_easy_perform()! */
1160   if(data->state.lastconnect && data->multi_easy) {
1161     struct connectdata *c = data->state.lastconnect;
1162     struct connfind find;
1163     find.tofind = data->state.lastconnect;
1164     find.found = FALSE;
1165
1166     Curl_conncache_foreach(data->multi_easy->conn_cache, &find, conn_is_conn);
1167
1168     if(!find.found) {
1169       data->state.lastconnect = NULL;
1170       return CURL_SOCKET_BAD;
1171     }
1172
1173     if(connp)
1174       /* only store this if the caller cares for it */
1175       *connp = c;
1176     sockfd = c->sock[FIRSTSOCKET];
1177     /* we have a socket connected, let's determine if the server shut down */
1178     /* determine if ssl */
1179     if(c->ssl[FIRSTSOCKET].use) {
1180       /* use the SSL context */
1181       if(!Curl_ssl_check_cxn(c))
1182         return CURL_SOCKET_BAD;   /* FIN received */
1183     }
1184 /* Minix 3.1 doesn't support any flags on recv; just assume socket is OK */
1185 #ifdef MSG_PEEK
1186     else {
1187       /* use the socket */
1188       char buf;
1189       if(recv((RECV_TYPE_ARG1)c->sock[FIRSTSOCKET], (RECV_TYPE_ARG2)&buf,
1190               (RECV_TYPE_ARG3)1, (RECV_TYPE_ARG4)MSG_PEEK) == 0) {
1191         return CURL_SOCKET_BAD;   /* FIN received */
1192       }
1193     }
1194 #endif
1195   }
1196   else
1197     return CURL_SOCKET_BAD;
1198
1199   return sockfd;
1200 }
1201
1202 /*
1203  * Close a socket.
1204  *
1205  * 'conn' can be NULL, beware!
1206  */
1207 int Curl_closesocket(struct connectdata *conn,
1208                       curl_socket_t sock)
1209 {
1210   if(conn && conn->fclosesocket) {
1211     if((sock == conn->sock[SECONDARYSOCKET]) &&
1212        conn->sock_accepted[SECONDARYSOCKET])
1213       /* if this socket matches the second socket, and that was created with
1214          accept, then we MUST NOT call the callback but clear the accepted
1215          status */
1216       conn->sock_accepted[SECONDARYSOCKET] = FALSE;
1217     else
1218       return conn->fclosesocket(conn->closesocket_client, sock);
1219   }
1220   sclose(sock);
1221
1222   if(conn)
1223     /* tell the multi-socket code about this */
1224     Curl_multi_closed(conn, sock);
1225
1226   return 0;
1227 }
1228
1229 /*
1230  * Create a socket based on info from 'conn' and 'ai'.
1231  *
1232  * 'addr' should be a pointer to the correct struct to get data back, or NULL.
1233  * 'sockfd' must be a pointer to a socket descriptor.
1234  *
1235  * If the open socket callback is set, used that!
1236  *
1237  */
1238 CURLcode Curl_socket(struct connectdata *conn,
1239                      const Curl_addrinfo *ai,
1240                      struct Curl_sockaddr_ex *addr,
1241                      curl_socket_t *sockfd)
1242 {
1243   struct SessionHandle *data = conn->data;
1244   struct Curl_sockaddr_ex dummy;
1245
1246   if(!addr)
1247     /* if the caller doesn't want info back, use a local temp copy */
1248     addr = &dummy;
1249
1250   /*
1251    * The Curl_sockaddr_ex structure is basically libcurl's external API
1252    * curl_sockaddr structure with enough space available to directly hold
1253    * any protocol-specific address structures. The variable declared here
1254    * will be used to pass / receive data to/from the fopensocket callback
1255    * if this has been set, before that, it is initialized from parameters.
1256    */
1257
1258   addr->family = ai->ai_family;
1259   addr->socktype = conn->socktype;
1260   addr->protocol = conn->socktype==SOCK_DGRAM?IPPROTO_UDP:ai->ai_protocol;
1261   addr->addrlen = ai->ai_addrlen;
1262
1263   if(addr->addrlen > sizeof(struct Curl_sockaddr_storage))
1264      addr->addrlen = sizeof(struct Curl_sockaddr_storage);
1265   memcpy(&addr->sa_addr, ai->ai_addr, addr->addrlen);
1266
1267   if(data->set.fopensocket)
1268    /*
1269     * If the opensocket callback is set, all the destination address
1270     * information is passed to the callback. Depending on this information the
1271     * callback may opt to abort the connection, this is indicated returning
1272     * CURL_SOCKET_BAD; otherwise it will return a not-connected socket. When
1273     * the callback returns a valid socket the destination address information
1274     * might have been changed and this 'new' address will actually be used
1275     * here to connect.
1276     */
1277     *sockfd = data->set.fopensocket(data->set.opensocket_client,
1278                                     CURLSOCKTYPE_IPCXN,
1279                                     (struct curl_sockaddr *)addr);
1280   else
1281     /* opensocket callback not set, so simply create the socket now */
1282     *sockfd = socket(addr->family, addr->socktype, addr->protocol);
1283
1284   if(*sockfd == CURL_SOCKET_BAD)
1285     /* no socket, no connection */
1286     return CURLE_COULDNT_CONNECT;
1287
1288 #if defined(ENABLE_IPV6) && defined(HAVE_SOCKADDR_IN6_SIN6_SCOPE_ID)
1289   if(conn->scope && (addr->family == AF_INET6)) {
1290     struct sockaddr_in6 * const sa6 = (void *)&addr->sa_addr;
1291     sa6->sin6_scope_id = conn->scope;
1292   }
1293 #endif
1294
1295   return CURLE_OK;
1296
1297 }