url.c: Fix dot file path cleanup when using an HTTP proxy
[platform/upstream/curl.git] / lib / url.c
1 /***************************************************************************
2  *                                  _   _ ____  _
3  *  Project                     ___| | | |  _ \| |
4  *                             / __| | | | |_) | |
5  *                            | (__| |_| |  _ <| |___
6  *                             \___|\___/|_| \_\_____|
7  *
8  * Copyright (C) 1998 - 2013, 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>
27 #endif
28 #ifdef HAVE_NETDB_H
29 #include <netdb.h>
30 #endif
31 #ifdef HAVE_ARPA_INET_H
32 #include <arpa/inet.h>
33 #endif
34 #ifdef HAVE_NET_IF_H
35 #include <net/if.h>
36 #endif
37 #ifdef HAVE_SYS_IOCTL_H
38 #include <sys/ioctl.h>
39 #endif
40
41 #ifdef HAVE_SYS_PARAM_H
42 #include <sys/param.h>
43 #endif
44
45 #ifdef __VMS
46 #include <in.h>
47 #include <inet.h>
48 #endif
49
50 #ifndef HAVE_SOCKET
51 #error "We can't compile without socket() support!"
52 #endif
53
54 #ifdef HAVE_LIMITS_H
55 #include <limits.h>
56 #endif
57
58 #ifdef USE_LIBIDN
59 #include <idna.h>
60 #include <tld.h>
61 #include <stringprep.h>
62 #ifdef HAVE_IDN_FREE_H
63 #include <idn-free.h>
64 #else
65 /* prototype from idn-free.h, not provided by libidn 0.4.5's make install! */
66 void idn_free (void *ptr);
67 #endif
68 #ifndef HAVE_IDN_FREE
69 /* if idn_free() was not found in this version of libidn use free() instead */
70 #define idn_free(x) (free)(x)
71 #endif
72 #elif defined(USE_WIN32_IDN)
73 /* prototype for curl_win32_idn_to_ascii() */
74 int curl_win32_idn_to_ascii(const char *in, char **out);
75 #endif  /* USE_LIBIDN */
76
77 #include "urldata.h"
78 #include "netrc.h"
79
80 #include "formdata.h"
81 #include "sslgen.h"
82 #include "hostip.h"
83 #include "transfer.h"
84 #include "sendf.h"
85 #include "progress.h"
86 #include "cookie.h"
87 #include "strequal.h"
88 #include "strerror.h"
89 #include "escape.h"
90 #include "strtok.h"
91 #include "share.h"
92 #include "content_encoding.h"
93 #include "http_digest.h"
94 #include "http_negotiate.h"
95 #include "select.h"
96 #include "multiif.h"
97 #include "easyif.h"
98 #include "speedcheck.h"
99 #include "rawstr.h"
100 #include "warnless.h"
101 #include "non-ascii.h"
102 #include "inet_pton.h"
103
104 /* And now for the protocols */
105 #include "ftp.h"
106 #include "dict.h"
107 #include "telnet.h"
108 #include "tftp.h"
109 #include "http.h"
110 #include "file.h"
111 #include "curl_ldap.h"
112 #include "ssh.h"
113 #include "imap.h"
114 #include "url.h"
115 #include "connect.h"
116 #include "inet_ntop.h"
117 #include "curl_ntlm.h"
118 #include "curl_ntlm_wb.h"
119 #include "socks.h"
120 #include "curl_rtmp.h"
121 #include "gopher.h"
122 #include "http_proxy.h"
123 #include "bundles.h"
124 #include "conncache.h"
125 #include "multihandle.h"
126 #include "pipeline.h"
127 #include "dotdot.h"
128
129 #define _MPRINTF_REPLACE /* use our functions only */
130 #include <curl/mprintf.h>
131
132 #include "curl_memory.h"
133 /* The last #include file should be: */
134 #include "memdebug.h"
135
136 /* Local static prototypes */
137 static struct connectdata *
138 find_oldest_idle_connection(struct SessionHandle *data);
139 static struct connectdata *
140 find_oldest_idle_connection_in_bundle(struct SessionHandle *data,
141                                       struct connectbundle *bundle);
142 static void conn_free(struct connectdata *conn);
143 static void signalPipeClose(struct curl_llist *pipeline, bool pipe_broke);
144 static CURLcode do_init(struct connectdata *conn);
145 static CURLcode parse_url_login(struct SessionHandle *data,
146                                 struct connectdata *conn,
147                                 char *user, char *passwd, char *options);
148 static CURLcode parse_login_details(const char *login, const size_t len,
149                                     char **userptr, char **passwdptr,
150                                     char **optionsptr);
151 /*
152  * Protocol table.
153  */
154
155 static const struct Curl_handler * const protocols[] = {
156
157 #ifndef CURL_DISABLE_HTTP
158   &Curl_handler_http,
159 #endif
160
161 #if defined(USE_SSL) && !defined(CURL_DISABLE_HTTP)
162   &Curl_handler_https,
163 #endif
164
165 #ifndef CURL_DISABLE_FTP
166   &Curl_handler_ftp,
167 #endif
168
169 #if defined(USE_SSL) && !defined(CURL_DISABLE_FTP)
170   &Curl_handler_ftps,
171 #endif
172
173 #ifndef CURL_DISABLE_TELNET
174   &Curl_handler_telnet,
175 #endif
176
177 #ifndef CURL_DISABLE_DICT
178   &Curl_handler_dict,
179 #endif
180
181 #ifndef CURL_DISABLE_LDAP
182   &Curl_handler_ldap,
183 #if !defined(CURL_DISABLE_LDAPS) && \
184     ((defined(USE_OPENLDAP) && defined(USE_SSL)) || \
185      (!defined(USE_OPENLDAP) && defined(HAVE_LDAP_SSL)))
186   &Curl_handler_ldaps,
187 #endif
188 #endif
189
190 #ifndef CURL_DISABLE_FILE
191   &Curl_handler_file,
192 #endif
193
194 #ifndef CURL_DISABLE_TFTP
195   &Curl_handler_tftp,
196 #endif
197
198 #ifdef USE_LIBSSH2
199   &Curl_handler_scp,
200   &Curl_handler_sftp,
201 #endif
202
203 #ifndef CURL_DISABLE_IMAP
204   &Curl_handler_imap,
205 #ifdef USE_SSL
206   &Curl_handler_imaps,
207 #endif
208 #endif
209
210 #ifndef CURL_DISABLE_POP3
211   &Curl_handler_pop3,
212 #ifdef USE_SSL
213   &Curl_handler_pop3s,
214 #endif
215 #endif
216
217 #ifndef CURL_DISABLE_SMTP
218   &Curl_handler_smtp,
219 #ifdef USE_SSL
220   &Curl_handler_smtps,
221 #endif
222 #endif
223
224 #ifndef CURL_DISABLE_RTSP
225   &Curl_handler_rtsp,
226 #endif
227
228 #ifndef CURL_DISABLE_GOPHER
229   &Curl_handler_gopher,
230 #endif
231
232 #ifdef USE_LIBRTMP
233   &Curl_handler_rtmp,
234   &Curl_handler_rtmpt,
235   &Curl_handler_rtmpe,
236   &Curl_handler_rtmpte,
237   &Curl_handler_rtmps,
238   &Curl_handler_rtmpts,
239 #endif
240
241   (struct Curl_handler *) NULL
242 };
243
244 /*
245  * Dummy handler for undefined protocol schemes.
246  */
247
248 static const struct Curl_handler Curl_handler_dummy = {
249   "<no protocol>",                      /* scheme */
250   ZERO_NULL,                            /* setup_connection */
251   ZERO_NULL,                            /* do_it */
252   ZERO_NULL,                            /* done */
253   ZERO_NULL,                            /* do_more */
254   ZERO_NULL,                            /* connect_it */
255   ZERO_NULL,                            /* connecting */
256   ZERO_NULL,                            /* doing */
257   ZERO_NULL,                            /* proto_getsock */
258   ZERO_NULL,                            /* doing_getsock */
259   ZERO_NULL,                            /* domore_getsock */
260   ZERO_NULL,                            /* perform_getsock */
261   ZERO_NULL,                            /* disconnect */
262   ZERO_NULL,                            /* readwrite */
263   0,                                    /* defport */
264   0,                                    /* protocol */
265   PROTOPT_NONE                          /* flags */
266 };
267
268 void Curl_freeset(struct SessionHandle *data)
269 {
270   /* Free all dynamic strings stored in the data->set substructure. */
271   enum dupstring i;
272   for(i=(enum dupstring)0; i < STRING_LAST; i++)
273     Curl_safefree(data->set.str[i]);
274
275   if(data->change.referer_alloc) {
276     Curl_safefree(data->change.referer);
277     data->change.referer_alloc = FALSE;
278   }
279   data->change.referer = NULL;
280 }
281
282 static CURLcode setstropt(char **charp, char *s)
283 {
284   /* Release the previous storage at `charp' and replace by a dynamic storage
285      copy of `s'. Return CURLE_OK or CURLE_OUT_OF_MEMORY. */
286
287   Curl_safefree(*charp);
288
289   if(s) {
290     s = strdup(s);
291
292     if(!s)
293       return CURLE_OUT_OF_MEMORY;
294
295     *charp = s;
296   }
297
298   return CURLE_OK;
299 }
300
301 static CURLcode setstropt_userpwd(char *option, char **userp, char **passwdp,
302                                   char **optionsp)
303 {
304   CURLcode result = CURLE_OK;
305   char *user = NULL;
306   char *passwd = NULL;
307   char *options = NULL;
308
309   /* Parse the login details if specified. It not then we treat NULL as a hint
310      to clear the existing data */
311   if(option) {
312     result = parse_login_details(option, strlen(option),
313                                  (userp ? &user : NULL),
314                                  (passwdp ? &passwd : NULL),
315                                  (optionsp ? &options : NULL));
316   }
317
318   if(!result) {
319     /* Store the username part of option if required */
320     if(userp) {
321       if(!user && option && option[0] == ':') {
322         /* Allocate an empty string instead of returning NULL as user name */
323         user = strdup("");
324         if(!user)
325           result = CURLE_OUT_OF_MEMORY;
326       }
327
328       Curl_safefree(*userp);
329       *userp = user;
330     }
331
332     /* Store the password part of option if required */
333     if(passwdp) {
334       Curl_safefree(*passwdp);
335       *passwdp = passwd;
336     }
337
338     /* Store the options part of option if required */
339     if(optionsp) {
340       Curl_safefree(*optionsp);
341       *optionsp = options;
342     }
343   }
344
345   return result;
346 }
347
348 CURLcode Curl_dupset(struct SessionHandle *dst, struct SessionHandle *src)
349 {
350   CURLcode r = CURLE_OK;
351   enum dupstring i;
352
353   /* Copy src->set into dst->set first, then deal with the strings
354      afterwards */
355   dst->set = src->set;
356
357   /* clear all string pointers first */
358   memset(dst->set.str, 0, STRING_LAST * sizeof(char *));
359
360   /* duplicate all strings */
361   for(i=(enum dupstring)0; i< STRING_LAST; i++) {
362     r = setstropt(&dst->set.str[i], src->set.str[i]);
363     if(r != CURLE_OK)
364       break;
365   }
366
367   /* If a failure occurred, freeing has to be performed externally. */
368   return r;
369 }
370
371 /*
372  * This is the internal function curl_easy_cleanup() calls. This should
373  * cleanup and free all resources associated with this sessionhandle.
374  *
375  * NOTE: if we ever add something that attempts to write to a socket or
376  * similar here, we must ignore SIGPIPE first. It is currently only done
377  * when curl_easy_perform() is invoked.
378  */
379
380 CURLcode Curl_close(struct SessionHandle *data)
381 {
382   struct Curl_multi *m;
383
384   if(!data)
385     return CURLE_OK;
386
387   Curl_expire(data, 0); /* shut off timers */
388
389   m = data->multi;
390
391   if(m)
392     /* This handle is still part of a multi handle, take care of this first
393        and detach this handle from there. */
394     curl_multi_remove_handle(data->multi, data);
395
396   if(data->multi_easy)
397     /* when curl_easy_perform() is used, it creates its own multi handle to
398        use and this is the one */
399     curl_multi_cleanup(data->multi_easy);
400
401   /* Destroy the timeout list that is held in the easy handle. It is
402      /normally/ done by curl_multi_remove_handle() but this is "just in
403      case" */
404   if(data->state.timeoutlist) {
405     Curl_llist_destroy(data->state.timeoutlist, NULL);
406     data->state.timeoutlist = NULL;
407   }
408
409   data->magic = 0; /* force a clear AFTER the possibly enforced removal from
410                       the multi handle, since that function uses the magic
411                       field! */
412
413   if(data->state.rangestringalloc)
414     free(data->state.range);
415
416   /* Free the pathbuffer */
417   Curl_safefree(data->state.pathbuffer);
418   data->state.path = NULL;
419
420   Curl_safefree(data->state.proto.generic);
421
422   /* Close down all open SSL info and sessions */
423   Curl_ssl_close_all(data);
424   Curl_safefree(data->state.first_host);
425   Curl_safefree(data->state.scratch);
426   Curl_ssl_free_certinfo(data);
427
428   if(data->change.referer_alloc) {
429     Curl_safefree(data->change.referer);
430     data->change.referer_alloc = FALSE;
431   }
432   data->change.referer = NULL;
433
434   if(data->change.url_alloc) {
435     Curl_safefree(data->change.url);
436     data->change.url_alloc = FALSE;
437   }
438   data->change.url = NULL;
439
440   Curl_safefree(data->state.headerbuff);
441
442   Curl_flush_cookies(data, 1);
443
444   Curl_digest_cleanup(data);
445
446   Curl_safefree(data->info.contenttype);
447   Curl_safefree(data->info.wouldredirect);
448
449   /* this destroys the channel and we cannot use it anymore after this */
450   Curl_resolver_cleanup(data->state.resolver);
451
452   Curl_convert_close(data);
453
454   /* No longer a dirty share, if it exists */
455   if(data->share) {
456     Curl_share_lock(data, CURL_LOCK_DATA_SHARE, CURL_LOCK_ACCESS_SINGLE);
457     data->share->dirty--;
458     Curl_share_unlock(data, CURL_LOCK_DATA_SHARE);
459   }
460
461   Curl_freeset(data);
462   free(data);
463   return CURLE_OK;
464 }
465
466 /*
467  * Initialize the UserDefined fields within a SessionHandle.
468  * This may be safely called on a new or existing SessionHandle.
469  */
470 CURLcode Curl_init_userdefined(struct UserDefined *set)
471 {
472   CURLcode res = CURLE_OK;
473
474   set->out = stdout; /* default output to stdout */
475   set->in  = stdin;  /* default input from stdin */
476   set->err  = stderr;  /* default stderr to stderr */
477
478   /* use fwrite as default function to store output */
479   set->fwrite_func = (curl_write_callback)fwrite;
480
481   /* use fread as default function to read input */
482   set->fread_func = (curl_read_callback)fread;
483   set->is_fread_set = 0;
484   set->is_fwrite_set = 0;
485
486   set->seek_func = ZERO_NULL;
487   set->seek_client = ZERO_NULL;
488
489   /* conversion callbacks for non-ASCII hosts */
490   set->convfromnetwork = ZERO_NULL;
491   set->convtonetwork   = ZERO_NULL;
492   set->convfromutf8    = ZERO_NULL;
493
494   set->infilesize = -1;      /* we don't know any size */
495   set->postfieldsize = -1;   /* unknown size */
496   set->maxredirs = -1;       /* allow any amount by default */
497
498   set->httpreq = HTTPREQ_GET; /* Default HTTP request */
499   set->rtspreq = RTSPREQ_OPTIONS; /* Default RTSP request */
500   set->ftp_use_epsv = TRUE;   /* FTP defaults to EPSV operations */
501   set->ftp_use_eprt = TRUE;   /* FTP defaults to EPRT operations */
502   set->ftp_use_pret = FALSE;  /* mainly useful for drftpd servers */
503   set->ftp_filemethod = FTPFILE_MULTICWD;
504
505   set->dns_cache_timeout = 60; /* Timeout every 60 seconds by default */
506
507   /* Set the default size of the SSL session ID cache */
508   set->ssl.max_ssl_sessions = 5;
509
510   set->proxyport = CURL_DEFAULT_PROXY_PORT; /* from url.h */
511   set->proxytype = CURLPROXY_HTTP; /* defaults to HTTP proxy */
512   set->httpauth = CURLAUTH_BASIC;  /* defaults to basic */
513   set->proxyauth = CURLAUTH_BASIC; /* defaults to basic */
514
515   /* make libcurl quiet by default: */
516   set->hide_progress = TRUE;  /* CURLOPT_NOPROGRESS changes these */
517
518   /*
519    * libcurl 7.10 introduced SSL verification *by default*! This needs to be
520    * switched off unless wanted.
521    */
522   set->ssl.verifypeer = TRUE;
523   set->ssl.verifyhost = TRUE;
524 #ifdef USE_TLS_SRP
525   set->ssl.authtype = CURL_TLSAUTH_NONE;
526 #endif
527   set->ssh_auth_types = CURLSSH_AUTH_DEFAULT; /* defaults to any auth
528                                                       type */
529   set->ssl.sessionid = TRUE; /* session ID caching enabled by default */
530
531   set->new_file_perms = 0644;    /* Default permissions */
532   set->new_directory_perms = 0755; /* Default permissions */
533
534   /* for the *protocols fields we don't use the CURLPROTO_ALL convenience
535      define since we internally only use the lower 16 bits for the passed
536      in bitmask to not conflict with the private bits */
537   set->allowed_protocols = CURLPROTO_ALL;
538   set->redir_protocols =
539     CURLPROTO_ALL & ~(CURLPROTO_FILE|CURLPROTO_SCP); /* not FILE or SCP */
540
541 #if defined(HAVE_GSSAPI) || defined(USE_WINDOWS_SSPI)
542   /*
543    * disallow unprotected protection negotiation NEC reference implementation
544    * seem not to follow rfc1961 section 4.3/4.4
545    */
546   set->socks5_gssapi_nec = FALSE;
547   /* set default gssapi service name */
548   res = setstropt(&set->str[STRING_SOCKS5_GSSAPI_SERVICE],
549                   (char *) CURL_DEFAULT_SOCKS5_GSSAPI_SERVICE);
550   if(res != CURLE_OK)
551     return res;
552 #endif
553
554   /* This is our preferred CA cert bundle/path since install time */
555 #if defined(CURL_CA_BUNDLE)
556   res = setstropt(&set->str[STRING_SSL_CAFILE], (char *) CURL_CA_BUNDLE);
557 #elif defined(CURL_CA_PATH)
558   res = setstropt(&set->str[STRING_SSL_CAPATH], (char *) CURL_CA_PATH);
559 #endif
560
561   set->wildcardmatch  = FALSE;
562   set->chunk_bgn      = ZERO_NULL;
563   set->chunk_end      = ZERO_NULL;
564
565   /* tcp keepalives are disabled by default, but provide reasonable values for
566    * the interval and idle times.
567    */
568   set->tcp_keepalive = FALSE;
569   set->tcp_keepintvl = 60;
570   set->tcp_keepidle = 60;
571
572   return res;
573 }
574
575 /**
576  * Curl_open()
577  *
578  * @param curl is a pointer to a sessionhandle pointer that gets set by this
579  * function.
580  * @return CURLcode
581  */
582
583 CURLcode Curl_open(struct SessionHandle **curl)
584 {
585   CURLcode res = CURLE_OK;
586   struct SessionHandle *data;
587   CURLcode status;
588
589   /* Very simple start-up: alloc the struct, init it with zeroes and return */
590   data = calloc(1, sizeof(struct SessionHandle));
591   if(!data) {
592     /* this is a very serious error */
593     DEBUGF(fprintf(stderr, "Error: calloc of SessionHandle failed\n"));
594     return CURLE_OUT_OF_MEMORY;
595   }
596
597   data->magic = CURLEASY_MAGIC_NUMBER;
598
599   status = Curl_resolver_init(&data->state.resolver);
600   if(status) {
601     DEBUGF(fprintf(stderr, "Error: resolver_init failed\n"));
602     free(data);
603     return status;
604   }
605
606   /* We do some initial setup here, all those fields that can't be just 0 */
607
608   data->state.headerbuff = malloc(HEADERSIZE);
609   if(!data->state.headerbuff) {
610     DEBUGF(fprintf(stderr, "Error: malloc of headerbuff failed\n"));
611     res = CURLE_OUT_OF_MEMORY;
612   }
613   else {
614     Curl_easy_initHandleData(data);
615     res = Curl_init_userdefined(&data->set);
616
617     data->state.headersize=HEADERSIZE;
618
619     Curl_convert_init(data);
620
621     /* most recent connection is not yet defined */
622     data->state.lastconnect = NULL;
623
624     data->progress.flags |= PGRS_HIDE;
625     data->state.current_speed = -1; /* init to negative == impossible */
626
627     data->wildcard.state = CURLWC_INIT;
628     data->wildcard.filelist = NULL;
629     data->set.fnmatch = ZERO_NULL;
630     data->set.maxconnects = DEFAULT_CONNCACHE_SIZE; /* for easy handles */
631   }
632
633   if(res) {
634     Curl_resolver_cleanup(data->state.resolver);
635     if(data->state.headerbuff)
636       free(data->state.headerbuff);
637     Curl_freeset(data);
638     free(data);
639     data = NULL;
640   }
641   else
642     *curl = data;
643
644   return res;
645 }
646
647 CURLcode Curl_setopt(struct SessionHandle *data, CURLoption option,
648                      va_list param)
649 {
650   char *argptr;
651   CURLcode result = CURLE_OK;
652   long arg;
653 #ifndef CURL_DISABLE_HTTP
654   curl_off_t bigsize;
655 #endif
656
657   switch(option) {
658   case CURLOPT_DNS_CACHE_TIMEOUT:
659     data->set.dns_cache_timeout = va_arg(param, long);
660     break;
661   case CURLOPT_DNS_USE_GLOBAL_CACHE:
662     /* remember we want this enabled */
663     arg = va_arg(param, long);
664     data->set.global_dns_cache = (0 != arg)?TRUE:FALSE;
665     break;
666   case CURLOPT_SSL_CIPHER_LIST:
667     /* set a list of cipher we want to use in the SSL connection */
668     result = setstropt(&data->set.str[STRING_SSL_CIPHER_LIST],
669                        va_arg(param, char *));
670     break;
671
672   case CURLOPT_RANDOM_FILE:
673     /*
674      * This is the path name to a file that contains random data to seed
675      * the random SSL stuff with. The file is only used for reading.
676      */
677     result = setstropt(&data->set.str[STRING_SSL_RANDOM_FILE],
678                        va_arg(param, char *));
679     break;
680   case CURLOPT_EGDSOCKET:
681     /*
682      * The Entropy Gathering Daemon socket pathname
683      */
684     result = setstropt(&data->set.str[STRING_SSL_EGDSOCKET],
685                        va_arg(param, char *));
686     break;
687   case CURLOPT_MAXCONNECTS:
688     /*
689      * Set the absolute number of maximum simultaneous alive connection that
690      * libcurl is allowed to have.
691      */
692     data->set.maxconnects = va_arg(param, long);
693     break;
694   case CURLOPT_FORBID_REUSE:
695     /*
696      * When this transfer is done, it must not be left to be reused by a
697      * subsequent transfer but shall be closed immediately.
698      */
699     data->set.reuse_forbid = (0 != va_arg(param, long))?TRUE:FALSE;
700     break;
701   case CURLOPT_FRESH_CONNECT:
702     /*
703      * This transfer shall not use a previously cached connection but
704      * should be made with a fresh new connect!
705      */
706     data->set.reuse_fresh = (0 != va_arg(param, long))?TRUE:FALSE;
707     break;
708   case CURLOPT_VERBOSE:
709     /*
710      * Verbose means infof() calls that give a lot of information about
711      * the connection and transfer procedures as well as internal choices.
712      */
713     data->set.verbose = (0 != va_arg(param, long))?TRUE:FALSE;
714     break;
715   case CURLOPT_HEADER:
716     /*
717      * Set to include the header in the general data output stream.
718      */
719     data->set.include_header = (0 != va_arg(param, long))?TRUE:FALSE;
720     break;
721   case CURLOPT_NOPROGRESS:
722     /*
723      * Shut off the internal supported progress meter
724      */
725     data->set.hide_progress = (0 != va_arg(param, long))?TRUE:FALSE;
726     if(data->set.hide_progress)
727       data->progress.flags |= PGRS_HIDE;
728     else
729       data->progress.flags &= ~PGRS_HIDE;
730     break;
731   case CURLOPT_NOBODY:
732     /*
733      * Do not include the body part in the output data stream.
734      */
735     data->set.opt_no_body = (0 != va_arg(param, long))?TRUE:FALSE;
736     break;
737   case CURLOPT_FAILONERROR:
738     /*
739      * Don't output the >=300 error code HTML-page, but instead only
740      * return error.
741      */
742     data->set.http_fail_on_error = (0 != va_arg(param, long))?TRUE:FALSE;
743     break;
744   case CURLOPT_UPLOAD:
745   case CURLOPT_PUT:
746     /*
747      * We want to sent data to the remote host. If this is HTTP, that equals
748      * using the PUT request.
749      */
750     data->set.upload = (0 != va_arg(param, long))?TRUE:FALSE;
751     if(data->set.upload) {
752       /* If this is HTTP, PUT is what's needed to "upload" */
753       data->set.httpreq = HTTPREQ_PUT;
754       data->set.opt_no_body = FALSE; /* this is implied */
755     }
756     else
757       /* In HTTP, the opposite of upload is GET (unless NOBODY is true as
758          then this can be changed to HEAD later on) */
759       data->set.httpreq = HTTPREQ_GET;
760     break;
761   case CURLOPT_FILETIME:
762     /*
763      * Try to get the file time of the remote document. The time will
764      * later (possibly) become available using curl_easy_getinfo().
765      */
766     data->set.get_filetime = (0 != va_arg(param, long))?TRUE:FALSE;
767     break;
768   case CURLOPT_FTP_CREATE_MISSING_DIRS:
769     /*
770      * An FTP option that modifies an upload to create missing directories on
771      * the server.
772      */
773     switch(va_arg(param, long)) {
774     case 0:
775       data->set.ftp_create_missing_dirs = 0;
776       break;
777     case 1:
778       data->set.ftp_create_missing_dirs = 1;
779       break;
780     case 2:
781       data->set.ftp_create_missing_dirs = 2;
782       break;
783     default:
784       /* reserve other values for future use */
785       result = CURLE_UNKNOWN_OPTION;
786       break;
787     }
788     break;
789   case CURLOPT_SERVER_RESPONSE_TIMEOUT:
790     /*
791      * Option that specifies how quickly an server response must be obtained
792      * before it is considered failure. For pingpong protocols.
793      */
794     data->set.server_response_timeout = va_arg( param , long ) * 1000;
795     break;
796   case CURLOPT_TFTP_BLKSIZE:
797     /*
798      * TFTP option that specifies the block size to use for data transmission
799      */
800     data->set.tftp_blksize = va_arg(param, long);
801     break;
802   case CURLOPT_DIRLISTONLY:
803     /*
804      * An option that changes the command to one that asks for a list
805      * only, no file info details.
806      */
807     data->set.ftp_list_only = (0 != va_arg(param, long))?TRUE:FALSE;
808     break;
809   case CURLOPT_APPEND:
810     /*
811      * We want to upload and append to an existing file.
812      */
813     data->set.ftp_append = (0 != va_arg(param, long))?TRUE:FALSE;
814     break;
815   case CURLOPT_FTP_FILEMETHOD:
816     /*
817      * How do access files over FTP.
818      */
819     data->set.ftp_filemethod = (curl_ftpfile)va_arg(param, long);
820     break;
821   case CURLOPT_NETRC:
822     /*
823      * Parse the $HOME/.netrc file
824      */
825     data->set.use_netrc = (enum CURL_NETRC_OPTION)va_arg(param, long);
826     break;
827   case CURLOPT_NETRC_FILE:
828     /*
829      * Use this file instead of the $HOME/.netrc file
830      */
831     result = setstropt(&data->set.str[STRING_NETRC_FILE],
832                        va_arg(param, char *));
833     break;
834   case CURLOPT_TRANSFERTEXT:
835     /*
836      * This option was previously named 'FTPASCII'. Renamed to work with
837      * more protocols than merely FTP.
838      *
839      * Transfer using ASCII (instead of BINARY).
840      */
841     data->set.prefer_ascii = (0 != va_arg(param, long))?TRUE:FALSE;
842     break;
843   case CURLOPT_TIMECONDITION:
844     /*
845      * Set HTTP time condition. This must be one of the defines in the
846      * curl/curl.h header file.
847      */
848     data->set.timecondition = (curl_TimeCond)va_arg(param, long);
849     break;
850   case CURLOPT_TIMEVALUE:
851     /*
852      * This is the value to compare with the remote document with the
853      * method set with CURLOPT_TIMECONDITION
854      */
855     data->set.timevalue = (time_t)va_arg(param, long);
856     break;
857   case CURLOPT_SSLVERSION:
858     /*
859      * Set explicit SSL version to try to connect with, as some SSL
860      * implementations are lame.
861      */
862     data->set.ssl.version = va_arg(param, long);
863     break;
864
865 #ifndef CURL_DISABLE_HTTP
866   case CURLOPT_AUTOREFERER:
867     /*
868      * Switch on automatic referer that gets set if curl follows locations.
869      */
870     data->set.http_auto_referer = (0 != va_arg(param, long))?TRUE:FALSE;
871     break;
872
873   case CURLOPT_ACCEPT_ENCODING:
874     /*
875      * String to use at the value of Accept-Encoding header.
876      *
877      * If the encoding is set to "" we use an Accept-Encoding header that
878      * encompasses all the encodings we support.
879      * If the encoding is set to NULL we don't send an Accept-Encoding header
880      * and ignore an received Content-Encoding header.
881      *
882      */
883     argptr = va_arg(param, char *);
884     result = setstropt(&data->set.str[STRING_ENCODING],
885                        (argptr && !*argptr)?
886                        (char *) ALL_CONTENT_ENCODINGS: argptr);
887     break;
888
889   case CURLOPT_TRANSFER_ENCODING:
890     data->set.http_transfer_encoding = (0 != va_arg(param, long))?TRUE:FALSE;
891     break;
892
893   case CURLOPT_FOLLOWLOCATION:
894     /*
895      * Follow Location: header hints on a HTTP-server.
896      */
897     data->set.http_follow_location = (0 != va_arg(param, long))?TRUE:FALSE;
898     break;
899
900   case CURLOPT_UNRESTRICTED_AUTH:
901     /*
902      * Send authentication (user+password) when following locations, even when
903      * hostname changed.
904      */
905     data->set.http_disable_hostname_check_before_authentication =
906       (0 != va_arg(param, long))?TRUE:FALSE;
907     break;
908
909   case CURLOPT_MAXREDIRS:
910     /*
911      * The maximum amount of hops you allow curl to follow Location:
912      * headers. This should mostly be used to detect never-ending loops.
913      */
914     data->set.maxredirs = va_arg(param, long);
915     break;
916
917   case CURLOPT_POSTREDIR:
918   {
919     /*
920      * Set the behaviour of POST when redirecting
921      * CURL_REDIR_GET_ALL - POST is changed to GET after 301 and 302
922      * CURL_REDIR_POST_301 - POST is kept as POST after 301
923      * CURL_REDIR_POST_302 - POST is kept as POST after 302
924      * CURL_REDIR_POST_303 - POST is kept as POST after 303
925      * CURL_REDIR_POST_ALL - POST is kept as POST after 301, 302 and 303
926      * other - POST is kept as POST after 301 and 302
927      */
928     int postRedir = curlx_sltosi(va_arg(param, long));
929     data->set.keep_post = postRedir & CURL_REDIR_POST_ALL;
930   }
931   break;
932
933   case CURLOPT_POST:
934     /* Does this option serve a purpose anymore? Yes it does, when
935        CURLOPT_POSTFIELDS isn't used and the POST data is read off the
936        callback! */
937     if(va_arg(param, long)) {
938       data->set.httpreq = HTTPREQ_POST;
939       data->set.opt_no_body = FALSE; /* this is implied */
940     }
941     else
942       data->set.httpreq = HTTPREQ_GET;
943     break;
944
945   case CURLOPT_COPYPOSTFIELDS:
946     /*
947      * A string with POST data. Makes curl HTTP POST. Even if it is NULL.
948      * If needed, CURLOPT_POSTFIELDSIZE must have been set prior to
949      *  CURLOPT_COPYPOSTFIELDS and not altered later.
950      */
951     argptr = va_arg(param, char *);
952
953     if(!argptr || data->set.postfieldsize == -1)
954       result = setstropt(&data->set.str[STRING_COPYPOSTFIELDS], argptr);
955     else {
956       /*
957        *  Check that requested length does not overflow the size_t type.
958        */
959
960       if((data->set.postfieldsize < 0) ||
961          ((sizeof(curl_off_t) != sizeof(size_t)) &&
962           (data->set.postfieldsize > (curl_off_t)((size_t)-1))))
963         result = CURLE_OUT_OF_MEMORY;
964       else {
965         char * p;
966
967         (void) setstropt(&data->set.str[STRING_COPYPOSTFIELDS], NULL);
968
969         /* Allocate even when size == 0. This satisfies the need of possible
970            later address compare to detect the COPYPOSTFIELDS mode, and
971            to mark that postfields is used rather than read function or
972            form data.
973         */
974         p = malloc((size_t)(data->set.postfieldsize?
975                             data->set.postfieldsize:1));
976
977         if(!p)
978           result = CURLE_OUT_OF_MEMORY;
979         else {
980           if(data->set.postfieldsize)
981             memcpy(p, argptr, (size_t)data->set.postfieldsize);
982
983           data->set.str[STRING_COPYPOSTFIELDS] = p;
984         }
985       }
986     }
987
988     data->set.postfields = data->set.str[STRING_COPYPOSTFIELDS];
989     data->set.httpreq = HTTPREQ_POST;
990     break;
991
992   case CURLOPT_POSTFIELDS:
993     /*
994      * Like above, but use static data instead of copying it.
995      */
996     data->set.postfields = va_arg(param, void *);
997     /* Release old copied data. */
998     (void) setstropt(&data->set.str[STRING_COPYPOSTFIELDS], NULL);
999     data->set.httpreq = HTTPREQ_POST;
1000     break;
1001
1002   case CURLOPT_POSTFIELDSIZE:
1003     /*
1004      * The size of the POSTFIELD data to prevent libcurl to do strlen() to
1005      * figure it out. Enables binary posts.
1006      */
1007     bigsize = va_arg(param, long);
1008
1009     if(data->set.postfieldsize < bigsize &&
1010        data->set.postfields == data->set.str[STRING_COPYPOSTFIELDS]) {
1011       /* Previous CURLOPT_COPYPOSTFIELDS is no longer valid. */
1012       (void) setstropt(&data->set.str[STRING_COPYPOSTFIELDS], NULL);
1013       data->set.postfields = NULL;
1014     }
1015
1016     data->set.postfieldsize = bigsize;
1017     break;
1018
1019   case CURLOPT_POSTFIELDSIZE_LARGE:
1020     /*
1021      * The size of the POSTFIELD data to prevent libcurl to do strlen() to
1022      * figure it out. Enables binary posts.
1023      */
1024     bigsize = va_arg(param, curl_off_t);
1025
1026     if(data->set.postfieldsize < bigsize &&
1027        data->set.postfields == data->set.str[STRING_COPYPOSTFIELDS]) {
1028       /* Previous CURLOPT_COPYPOSTFIELDS is no longer valid. */
1029       (void) setstropt(&data->set.str[STRING_COPYPOSTFIELDS], NULL);
1030       data->set.postfields = NULL;
1031     }
1032
1033     data->set.postfieldsize = bigsize;
1034     break;
1035
1036   case CURLOPT_HTTPPOST:
1037     /*
1038      * Set to make us do HTTP POST
1039      */
1040     data->set.httppost = va_arg(param, struct curl_httppost *);
1041     data->set.httpreq = HTTPREQ_POST_FORM;
1042     data->set.opt_no_body = FALSE; /* this is implied */
1043     break;
1044
1045   case CURLOPT_REFERER:
1046     /*
1047      * String to set in the HTTP Referer: field.
1048      */
1049     if(data->change.referer_alloc) {
1050       Curl_safefree(data->change.referer);
1051       data->change.referer_alloc = FALSE;
1052     }
1053     result = setstropt(&data->set.str[STRING_SET_REFERER],
1054                        va_arg(param, char *));
1055     data->change.referer = data->set.str[STRING_SET_REFERER];
1056     break;
1057
1058   case CURLOPT_USERAGENT:
1059     /*
1060      * String to use in the HTTP User-Agent field
1061      */
1062     result = setstropt(&data->set.str[STRING_USERAGENT],
1063                        va_arg(param, char *));
1064     break;
1065
1066   case CURLOPT_HTTPHEADER:
1067     /*
1068      * Set a list with HTTP headers to use (or replace internals with)
1069      */
1070     data->set.headers = va_arg(param, struct curl_slist *);
1071     break;
1072
1073   case CURLOPT_HTTP200ALIASES:
1074     /*
1075      * Set a list of aliases for HTTP 200 in response header
1076      */
1077     data->set.http200aliases = va_arg(param, struct curl_slist *);
1078     break;
1079
1080 #if !defined(CURL_DISABLE_COOKIES)
1081   case CURLOPT_COOKIE:
1082     /*
1083      * Cookie string to send to the remote server in the request.
1084      */
1085     result = setstropt(&data->set.str[STRING_COOKIE],
1086                        va_arg(param, char *));
1087     break;
1088
1089   case CURLOPT_COOKIEFILE:
1090     /*
1091      * Set cookie file to read and parse. Can be used multiple times.
1092      */
1093     argptr = (char *)va_arg(param, void *);
1094     if(argptr) {
1095       struct curl_slist *cl;
1096       /* append the cookie file name to the list of file names, and deal with
1097          them later */
1098       cl = curl_slist_append(data->change.cookielist, argptr);
1099       if(!cl) {
1100         curl_slist_free_all(data->change.cookielist);
1101         data->change.cookielist = NULL;
1102         return CURLE_OUT_OF_MEMORY;
1103       }
1104       data->change.cookielist = cl; /* store the list for later use */
1105     }
1106     break;
1107
1108   case CURLOPT_COOKIEJAR:
1109     /*
1110      * Set cookie file name to dump all cookies to when we're done.
1111      */
1112     result = setstropt(&data->set.str[STRING_COOKIEJAR],
1113                        va_arg(param, char *));
1114
1115     /*
1116      * Activate the cookie parser. This may or may not already
1117      * have been made.
1118      */
1119     data->cookies = Curl_cookie_init(data, NULL, data->cookies,
1120                                      data->set.cookiesession);
1121     break;
1122
1123   case CURLOPT_COOKIESESSION:
1124     /*
1125      * Set this option to TRUE to start a new "cookie session". It will
1126      * prevent the forthcoming read-cookies-from-file actions to accept
1127      * cookies that are marked as being session cookies, as they belong to a
1128      * previous session.
1129      *
1130      * In the original Netscape cookie spec, "session cookies" are cookies
1131      * with no expire date set. RFC2109 describes the same action if no
1132      * 'Max-Age' is set and RFC2965 includes the RFC2109 description and adds
1133      * a 'Discard' action that can enforce the discard even for cookies that
1134      * have a Max-Age.
1135      *
1136      * We run mostly with the original cookie spec, as hardly anyone implements
1137      * anything else.
1138      */
1139     data->set.cookiesession = (0 != va_arg(param, long))?TRUE:FALSE;
1140     break;
1141
1142   case CURLOPT_COOKIELIST:
1143     argptr = va_arg(param, char *);
1144
1145     if(argptr == NULL)
1146       break;
1147
1148     Curl_share_lock(data, CURL_LOCK_DATA_COOKIE, CURL_LOCK_ACCESS_SINGLE);
1149
1150     if(Curl_raw_equal(argptr, "ALL")) {
1151       /* clear all cookies */
1152       Curl_cookie_clearall(data->cookies);
1153     }
1154     else if(Curl_raw_equal(argptr, "SESS")) {
1155       /* clear session cookies */
1156       Curl_cookie_clearsess(data->cookies);
1157     }
1158     else if(Curl_raw_equal(argptr, "FLUSH")) {
1159       /* flush cookies to file */
1160       Curl_flush_cookies(data, 0);
1161     }
1162     else {
1163       if(!data->cookies)
1164         /* if cookie engine was not running, activate it */
1165         data->cookies = Curl_cookie_init(data, NULL, NULL, TRUE);
1166
1167       argptr = strdup(argptr);
1168       if(!argptr) {
1169         result = CURLE_OUT_OF_MEMORY;
1170       }
1171       else {
1172
1173         if(checkprefix("Set-Cookie:", argptr))
1174           /* HTTP Header format line */
1175           Curl_cookie_add(data, data->cookies, TRUE, argptr + 11, NULL, NULL);
1176
1177         else
1178           /* Netscape format line */
1179           Curl_cookie_add(data, data->cookies, FALSE, argptr, NULL, NULL);
1180
1181         free(argptr);
1182       }
1183     }
1184     Curl_share_unlock(data, CURL_LOCK_DATA_COOKIE);
1185
1186     break;
1187 #endif /* CURL_DISABLE_COOKIES */
1188
1189   case CURLOPT_HTTPGET:
1190     /*
1191      * Set to force us do HTTP GET
1192      */
1193     if(va_arg(param, long)) {
1194       data->set.httpreq = HTTPREQ_GET;
1195       data->set.upload = FALSE; /* switch off upload */
1196       data->set.opt_no_body = FALSE; /* this is implied */
1197     }
1198     break;
1199
1200   case CURLOPT_HTTP_VERSION:
1201     /*
1202      * This sets a requested HTTP version to be used. The value is one of
1203      * the listed enums in curl/curl.h.
1204      */
1205     data->set.httpversion = va_arg(param, long);
1206     break;
1207
1208   case CURLOPT_HTTPAUTH:
1209     /*
1210      * Set HTTP Authentication type BITMASK.
1211      */
1212   {
1213     int bitcheck;
1214     bool authbits;
1215     unsigned long auth = va_arg(param, unsigned long);
1216
1217     if(auth == CURLAUTH_NONE) {
1218       data->set.httpauth = auth;
1219       break;
1220     }
1221
1222     /* the DIGEST_IE bit is only used to set a special marker, for all the
1223        rest we need to handle it as normal DIGEST */
1224     data->state.authhost.iestyle = (auth & CURLAUTH_DIGEST_IE)?TRUE:FALSE;
1225
1226     if(auth & CURLAUTH_DIGEST_IE) {
1227       auth |= CURLAUTH_DIGEST; /* set standard digest bit */
1228       auth &= ~CURLAUTH_DIGEST_IE; /* unset ie digest bit */
1229     }
1230
1231     /* switch off bits we can't support */
1232 #ifndef USE_NTLM
1233     auth &= ~CURLAUTH_NTLM;    /* no NTLM support */
1234     auth &= ~CURLAUTH_NTLM_WB; /* no NTLM_WB support */
1235 #elif !defined(NTLM_WB_ENABLED)
1236     auth &= ~CURLAUTH_NTLM_WB; /* no NTLM_WB support */
1237 #endif
1238 #ifndef USE_HTTP_NEGOTIATE
1239     auth &= ~CURLAUTH_GSSNEGOTIATE; /* no GSS-Negotiate without GSSAPI or
1240                                        WINDOWS_SSPI */
1241 #endif
1242
1243     /* check if any auth bit lower than CURLAUTH_ONLY is still set */
1244     bitcheck = 0;
1245     authbits = FALSE;
1246     while(bitcheck < 31) {
1247       if(auth & (1UL << bitcheck++)) {
1248         authbits = TRUE;
1249         break;
1250       }
1251     }
1252     if(!authbits)
1253       return CURLE_NOT_BUILT_IN; /* no supported types left! */
1254
1255     data->set.httpauth = auth;
1256   }
1257   break;
1258
1259 #endif   /* CURL_DISABLE_HTTP */
1260
1261   case CURLOPT_CUSTOMREQUEST:
1262     /*
1263      * Set a custom string to use as request
1264      */
1265     result = setstropt(&data->set.str[STRING_CUSTOMREQUEST],
1266                        va_arg(param, char *));
1267
1268     /* we don't set
1269        data->set.httpreq = HTTPREQ_CUSTOM;
1270        here, we continue as if we were using the already set type
1271        and this just changes the actual request keyword */
1272     break;
1273
1274 #ifndef CURL_DISABLE_PROXY
1275   case CURLOPT_HTTPPROXYTUNNEL:
1276     /*
1277      * Tunnel operations through the proxy instead of normal proxy use
1278      */
1279     data->set.tunnel_thru_httpproxy = (0 != va_arg(param, long))?TRUE:FALSE;
1280     break;
1281
1282   case CURLOPT_PROXYPORT:
1283     /*
1284      * Explicitly set HTTP proxy port number.
1285      */
1286     data->set.proxyport = va_arg(param, long);
1287     break;
1288
1289   case CURLOPT_PROXYAUTH:
1290     /*
1291      * Set HTTP Authentication type BITMASK.
1292      */
1293   {
1294     int bitcheck;
1295     bool authbits;
1296     unsigned long auth = va_arg(param, unsigned long);
1297
1298     if(auth == CURLAUTH_NONE) {
1299       data->set.proxyauth = auth;
1300       break;
1301     }
1302
1303     /* the DIGEST_IE bit is only used to set a special marker, for all the
1304        rest we need to handle it as normal DIGEST */
1305     data->state.authproxy.iestyle = (auth & CURLAUTH_DIGEST_IE)?TRUE:FALSE;
1306
1307     if(auth & CURLAUTH_DIGEST_IE) {
1308       auth |= CURLAUTH_DIGEST; /* set standard digest bit */
1309       auth &= ~CURLAUTH_DIGEST_IE; /* unset ie digest bit */
1310     }
1311     /* switch off bits we can't support */
1312 #ifndef USE_NTLM
1313     auth &= ~CURLAUTH_NTLM;    /* no NTLM support */
1314     auth &= ~CURLAUTH_NTLM_WB; /* no NTLM_WB support */
1315 #elif !defined(NTLM_WB_ENABLED)
1316     auth &= ~CURLAUTH_NTLM_WB; /* no NTLM_WB support */
1317 #endif
1318 #ifndef USE_HTTP_NEGOTIATE
1319     auth &= ~CURLAUTH_GSSNEGOTIATE; /* no GSS-Negotiate without GSSAPI or
1320                                        WINDOWS_SSPI */
1321 #endif
1322
1323     /* check if any auth bit lower than CURLAUTH_ONLY is still set */
1324     bitcheck = 0;
1325     authbits = FALSE;
1326     while(bitcheck < 31) {
1327       if(auth & (1UL << bitcheck++)) {
1328         authbits = TRUE;
1329         break;
1330       }
1331     }
1332     if(!authbits)
1333       return CURLE_NOT_BUILT_IN; /* no supported types left! */
1334
1335     data->set.proxyauth = auth;
1336   }
1337   break;
1338
1339   case CURLOPT_PROXY:
1340     /*
1341      * Set proxy server:port to use as HTTP proxy.
1342      *
1343      * If the proxy is set to "" we explicitly say that we don't want to use a
1344      * proxy (even though there might be environment variables saying so).
1345      *
1346      * Setting it to NULL, means no proxy but allows the environment variables
1347      * to decide for us.
1348      */
1349     result = setstropt(&data->set.str[STRING_PROXY],
1350                        va_arg(param, char *));
1351     break;
1352
1353   case CURLOPT_PROXYTYPE:
1354     /*
1355      * Set proxy type. HTTP/HTTP_1_0/SOCKS4/SOCKS4a/SOCKS5/SOCKS5_HOSTNAME
1356      */
1357     data->set.proxytype = (curl_proxytype)va_arg(param, long);
1358     break;
1359
1360   case CURLOPT_PROXY_TRANSFER_MODE:
1361     /*
1362      * set transfer mode (;type=<a|i>) when doing FTP via an HTTP proxy
1363      */
1364     switch (va_arg(param, long)) {
1365     case 0:
1366       data->set.proxy_transfer_mode = FALSE;
1367       break;
1368     case 1:
1369       data->set.proxy_transfer_mode = TRUE;
1370       break;
1371     default:
1372       /* reserve other values for future use */
1373       result = CURLE_UNKNOWN_OPTION;
1374       break;
1375     }
1376     break;
1377 #endif   /* CURL_DISABLE_PROXY */
1378
1379 #if defined(HAVE_GSSAPI) || defined(USE_WINDOWS_SSPI)
1380   case CURLOPT_SOCKS5_GSSAPI_SERVICE:
1381     /*
1382      * Set gssapi service name
1383      */
1384     result = setstropt(&data->set.str[STRING_SOCKS5_GSSAPI_SERVICE],
1385                        va_arg(param, char *));
1386     break;
1387
1388   case CURLOPT_SOCKS5_GSSAPI_NEC:
1389     /*
1390      * set flag for nec socks5 support
1391      */
1392     data->set.socks5_gssapi_nec = (0 != va_arg(param, long))?TRUE:FALSE;
1393     break;
1394 #endif
1395
1396   case CURLOPT_WRITEHEADER:
1397     /*
1398      * Custom pointer to pass the header write callback function
1399      */
1400     data->set.writeheader = (void *)va_arg(param, void *);
1401     break;
1402   case CURLOPT_ERRORBUFFER:
1403     /*
1404      * Error buffer provided by the caller to get the human readable
1405      * error string in.
1406      */
1407     data->set.errorbuffer = va_arg(param, char *);
1408     break;
1409   case CURLOPT_FILE:
1410     /*
1411      * FILE pointer to write to. Or possibly
1412      * used as argument to the write callback.
1413      */
1414     data->set.out = va_arg(param, void *);
1415     break;
1416   case CURLOPT_FTPPORT:
1417     /*
1418      * Use FTP PORT, this also specifies which IP address to use
1419      */
1420     result = setstropt(&data->set.str[STRING_FTPPORT],
1421                        va_arg(param, char *));
1422     data->set.ftp_use_port = (NULL != data->set.str[STRING_FTPPORT]) ?
1423                              TRUE:FALSE;
1424     break;
1425
1426   case CURLOPT_FTP_USE_EPRT:
1427     data->set.ftp_use_eprt = (0 != va_arg(param, long))?TRUE:FALSE;
1428     break;
1429
1430   case CURLOPT_FTP_USE_EPSV:
1431     data->set.ftp_use_epsv = (0 != va_arg(param, long))?TRUE:FALSE;
1432     break;
1433
1434   case CURLOPT_FTP_USE_PRET:
1435     data->set.ftp_use_pret = (0 != va_arg(param, long))?TRUE:FALSE;
1436     break;
1437
1438   case CURLOPT_FTP_SSL_CCC:
1439     data->set.ftp_ccc = (curl_ftpccc)va_arg(param, long);
1440     break;
1441
1442   case CURLOPT_FTP_SKIP_PASV_IP:
1443     /*
1444      * Enable or disable FTP_SKIP_PASV_IP, which will disable/enable the
1445      * bypass of the IP address in PASV responses.
1446      */
1447     data->set.ftp_skip_ip = (0 != va_arg(param, long))?TRUE:FALSE;
1448     break;
1449
1450   case CURLOPT_INFILE:
1451     /*
1452      * FILE pointer to read the file to be uploaded from. Or possibly
1453      * used as argument to the read callback.
1454      */
1455     data->set.in = va_arg(param, void *);
1456     break;
1457   case CURLOPT_INFILESIZE:
1458     /*
1459      * If known, this should inform curl about the file size of the
1460      * to-be-uploaded file.
1461      */
1462     data->set.infilesize = va_arg(param, long);
1463     break;
1464   case CURLOPT_INFILESIZE_LARGE:
1465     /*
1466      * If known, this should inform curl about the file size of the
1467      * to-be-uploaded file.
1468      */
1469     data->set.infilesize = va_arg(param, curl_off_t);
1470     break;
1471   case CURLOPT_LOW_SPEED_LIMIT:
1472     /*
1473      * The low speed limit that if transfers are below this for
1474      * CURLOPT_LOW_SPEED_TIME, the transfer is aborted.
1475      */
1476     data->set.low_speed_limit=va_arg(param, long);
1477     break;
1478   case CURLOPT_MAX_SEND_SPEED_LARGE:
1479     /*
1480      * When transfer uploads are faster then CURLOPT_MAX_SEND_SPEED_LARGE
1481      * bytes per second the transfer is throttled..
1482      */
1483     data->set.max_send_speed=va_arg(param, curl_off_t);
1484     break;
1485   case CURLOPT_MAX_RECV_SPEED_LARGE:
1486     /*
1487      * When receiving data faster than CURLOPT_MAX_RECV_SPEED_LARGE bytes per
1488      * second the transfer is throttled..
1489      */
1490     data->set.max_recv_speed=va_arg(param, curl_off_t);
1491     break;
1492   case CURLOPT_LOW_SPEED_TIME:
1493     /*
1494      * The low speed time that if transfers are below the set
1495      * CURLOPT_LOW_SPEED_LIMIT during this time, the transfer is aborted.
1496      */
1497     data->set.low_speed_time=va_arg(param, long);
1498     break;
1499   case CURLOPT_URL:
1500     /*
1501      * The URL to fetch.
1502      */
1503     if(data->change.url_alloc) {
1504       /* the already set URL is allocated, free it first! */
1505       Curl_safefree(data->change.url);
1506       data->change.url_alloc = FALSE;
1507     }
1508     result = setstropt(&data->set.str[STRING_SET_URL],
1509                        va_arg(param, char *));
1510     data->change.url = data->set.str[STRING_SET_URL];
1511     break;
1512   case CURLOPT_PORT:
1513     /*
1514      * The port number to use when getting the URL
1515      */
1516     data->set.use_port = va_arg(param, long);
1517     break;
1518   case CURLOPT_TIMEOUT:
1519     /*
1520      * The maximum time you allow curl to use for a single transfer
1521      * operation.
1522      */
1523     data->set.timeout = va_arg(param, long) * 1000L;
1524     break;
1525
1526   case CURLOPT_TIMEOUT_MS:
1527     data->set.timeout = va_arg(param, long);
1528     break;
1529
1530   case CURLOPT_CONNECTTIMEOUT:
1531     /*
1532      * The maximum time you allow curl to use to connect.
1533      */
1534     data->set.connecttimeout = va_arg(param, long) * 1000L;
1535     break;
1536
1537   case CURLOPT_CONNECTTIMEOUT_MS:
1538     data->set.connecttimeout = va_arg(param, long);
1539     break;
1540
1541   case CURLOPT_ACCEPTTIMEOUT_MS:
1542     /*
1543      * The maximum time you allow curl to wait for server connect
1544      */
1545     data->set.accepttimeout = va_arg(param, long);
1546     break;
1547
1548   case CURLOPT_USERPWD:
1549     /*
1550      * user:password;options to use in the operation
1551      */
1552     result = setstropt_userpwd(va_arg(param, char *),
1553                                &data->set.str[STRING_USERNAME],
1554                                &data->set.str[STRING_PASSWORD],
1555                                &data->set.str[STRING_OPTIONS]);
1556     break;
1557   case CURLOPT_USERNAME:
1558     /*
1559      * authentication user name to use in the operation
1560      */
1561     result = setstropt(&data->set.str[STRING_USERNAME],
1562                        va_arg(param, char *));
1563     break;
1564   case CURLOPT_PASSWORD:
1565     /*
1566      * authentication password to use in the operation
1567      */
1568     result = setstropt(&data->set.str[STRING_PASSWORD],
1569                        va_arg(param, char *));
1570     break;
1571   case CURLOPT_POSTQUOTE:
1572     /*
1573      * List of RAW FTP commands to use after a transfer
1574      */
1575     data->set.postquote = va_arg(param, struct curl_slist *);
1576     break;
1577   case CURLOPT_PREQUOTE:
1578     /*
1579      * List of RAW FTP commands to use prior to RETR (Wesley Laxton)
1580      */
1581     data->set.prequote = va_arg(param, struct curl_slist *);
1582     break;
1583   case CURLOPT_QUOTE:
1584     /*
1585      * List of RAW FTP commands to use before a transfer
1586      */
1587     data->set.quote = va_arg(param, struct curl_slist *);
1588     break;
1589   case CURLOPT_RESOLVE:
1590     /*
1591      * List of NAME:[address] names to populate the DNS cache with
1592      * Prefix the NAME with dash (-) to _remove_ the name from the cache.
1593      *
1594      * Names added with this API will remain in the cache until explicitly
1595      * removed or the handle is cleaned up.
1596      *
1597      * This API can remove any name from the DNS cache, but only entries
1598      * that aren't actually in use right now will be pruned immediately.
1599      */
1600     data->set.resolve = va_arg(param, struct curl_slist *);
1601     data->change.resolve = data->set.resolve;
1602     break;
1603   case CURLOPT_PROGRESSFUNCTION:
1604     /*
1605      * Progress callback function
1606      */
1607     data->set.fprogress = va_arg(param, curl_progress_callback);
1608     if(data->set.fprogress)
1609       data->progress.callback = TRUE; /* no longer internal */
1610     else
1611       data->progress.callback = FALSE; /* NULL enforces internal */
1612     break;
1613
1614   case CURLOPT_XFERINFOFUNCTION:
1615     /*
1616      * Transfer info callback function
1617      */
1618     data->set.fxferinfo = va_arg(param, curl_xferinfo_callback);
1619     if(data->set.fxferinfo)
1620       data->progress.callback = TRUE; /* no longer internal */
1621     else
1622       data->progress.callback = FALSE; /* NULL enforces internal */
1623
1624     break;
1625
1626   case CURLOPT_PROGRESSDATA:
1627     /*
1628      * Custom client data to pass to the progress callback
1629      */
1630     data->set.progress_client = va_arg(param, void *);
1631     break;
1632
1633 #ifndef CURL_DISABLE_PROXY
1634   case CURLOPT_PROXYUSERPWD:
1635     /*
1636      * user:password needed to use the proxy
1637      */
1638     result = setstropt_userpwd(va_arg(param, char *),
1639                                &data->set.str[STRING_PROXYUSERNAME],
1640                                &data->set.str[STRING_PROXYPASSWORD], NULL);
1641     break;
1642   case CURLOPT_PROXYUSERNAME:
1643     /*
1644      * authentication user name to use in the operation
1645      */
1646     result = setstropt(&data->set.str[STRING_PROXYUSERNAME],
1647                        va_arg(param, char *));
1648     break;
1649   case CURLOPT_PROXYPASSWORD:
1650     /*
1651      * authentication password to use in the operation
1652      */
1653     result = setstropt(&data->set.str[STRING_PROXYPASSWORD],
1654                        va_arg(param, char *));
1655     break;
1656   case CURLOPT_NOPROXY:
1657     /*
1658      * proxy exception list
1659      */
1660     result = setstropt(&data->set.str[STRING_NOPROXY],
1661                        va_arg(param, char *));
1662     break;
1663 #endif
1664
1665   case CURLOPT_RANGE:
1666     /*
1667      * What range of the file you want to transfer
1668      */
1669     result = setstropt(&data->set.str[STRING_SET_RANGE],
1670                        va_arg(param, char *));
1671     break;
1672   case CURLOPT_RESUME_FROM:
1673     /*
1674      * Resume transfer at the give file position
1675      */
1676     data->set.set_resume_from = va_arg(param, long);
1677     break;
1678   case CURLOPT_RESUME_FROM_LARGE:
1679     /*
1680      * Resume transfer at the give file position
1681      */
1682     data->set.set_resume_from = va_arg(param, curl_off_t);
1683     break;
1684   case CURLOPT_DEBUGFUNCTION:
1685     /*
1686      * stderr write callback.
1687      */
1688     data->set.fdebug = va_arg(param, curl_debug_callback);
1689     /*
1690      * if the callback provided is NULL, it'll use the default callback
1691      */
1692     break;
1693   case CURLOPT_DEBUGDATA:
1694     /*
1695      * Set to a void * that should receive all error writes. This
1696      * defaults to CURLOPT_STDERR for normal operations.
1697      */
1698     data->set.debugdata = va_arg(param, void *);
1699     break;
1700   case CURLOPT_STDERR:
1701     /*
1702      * Set to a FILE * that should receive all error writes. This
1703      * defaults to stderr for normal operations.
1704      */
1705     data->set.err = va_arg(param, FILE *);
1706     if(!data->set.err)
1707       data->set.err = stderr;
1708     break;
1709   case CURLOPT_HEADERFUNCTION:
1710     /*
1711      * Set header write callback
1712      */
1713     data->set.fwrite_header = va_arg(param, curl_write_callback);
1714     break;
1715   case CURLOPT_WRITEFUNCTION:
1716     /*
1717      * Set data write callback
1718      */
1719     data->set.fwrite_func = va_arg(param, curl_write_callback);
1720     if(!data->set.fwrite_func) {
1721       data->set.is_fwrite_set = 0;
1722       /* When set to NULL, reset to our internal default function */
1723       data->set.fwrite_func = (curl_write_callback)fwrite;
1724     }
1725     else
1726       data->set.is_fwrite_set = 1;
1727     break;
1728   case CURLOPT_READFUNCTION:
1729     /*
1730      * Read data callback
1731      */
1732     data->set.fread_func = va_arg(param, curl_read_callback);
1733     if(!data->set.fread_func) {
1734       data->set.is_fread_set = 0;
1735       /* When set to NULL, reset to our internal default function */
1736       data->set.fread_func = (curl_read_callback)fread;
1737     }
1738     else
1739       data->set.is_fread_set = 1;
1740     break;
1741   case CURLOPT_SEEKFUNCTION:
1742     /*
1743      * Seek callback. Might be NULL.
1744      */
1745     data->set.seek_func = va_arg(param, curl_seek_callback);
1746     break;
1747   case CURLOPT_SEEKDATA:
1748     /*
1749      * Seek control callback. Might be NULL.
1750      */
1751     data->set.seek_client = va_arg(param, void *);
1752     break;
1753   case CURLOPT_CONV_FROM_NETWORK_FUNCTION:
1754     /*
1755      * "Convert from network encoding" callback
1756      */
1757     data->set.convfromnetwork = va_arg(param, curl_conv_callback);
1758     break;
1759   case CURLOPT_CONV_TO_NETWORK_FUNCTION:
1760     /*
1761      * "Convert to network encoding" callback
1762      */
1763     data->set.convtonetwork = va_arg(param, curl_conv_callback);
1764     break;
1765   case CURLOPT_CONV_FROM_UTF8_FUNCTION:
1766     /*
1767      * "Convert from UTF-8 encoding" callback
1768      */
1769     data->set.convfromutf8 = va_arg(param, curl_conv_callback);
1770     break;
1771   case CURLOPT_IOCTLFUNCTION:
1772     /*
1773      * I/O control callback. Might be NULL.
1774      */
1775     data->set.ioctl_func = va_arg(param, curl_ioctl_callback);
1776     break;
1777   case CURLOPT_IOCTLDATA:
1778     /*
1779      * I/O control data pointer. Might be NULL.
1780      */
1781     data->set.ioctl_client = va_arg(param, void *);
1782     break;
1783   case CURLOPT_SSLCERT:
1784     /*
1785      * String that holds file name of the SSL certificate to use
1786      */
1787     result = setstropt(&data->set.str[STRING_CERT],
1788                        va_arg(param, char *));
1789     break;
1790   case CURLOPT_SSLCERTTYPE:
1791     /*
1792      * String that holds file type of the SSL certificate to use
1793      */
1794     result = setstropt(&data->set.str[STRING_CERT_TYPE],
1795                        va_arg(param, char *));
1796     break;
1797   case CURLOPT_SSLKEY:
1798     /*
1799      * String that holds file name of the SSL key to use
1800      */
1801     result = setstropt(&data->set.str[STRING_KEY],
1802                        va_arg(param, char *));
1803     break;
1804   case CURLOPT_SSLKEYTYPE:
1805     /*
1806      * String that holds file type of the SSL key to use
1807      */
1808     result = setstropt(&data->set.str[STRING_KEY_TYPE],
1809                        va_arg(param, char *));
1810     break;
1811   case CURLOPT_KEYPASSWD:
1812     /*
1813      * String that holds the SSL or SSH private key password.
1814      */
1815     result = setstropt(&data->set.str[STRING_KEY_PASSWD],
1816                        va_arg(param, char *));
1817     break;
1818   case CURLOPT_SSLENGINE:
1819     /*
1820      * String that holds the SSL crypto engine.
1821      */
1822     argptr = va_arg(param, char *);
1823     if(argptr && argptr[0])
1824       result = Curl_ssl_set_engine(data, argptr);
1825     break;
1826
1827   case CURLOPT_SSLENGINE_DEFAULT:
1828     /*
1829      * flag to set engine as default.
1830      */
1831     result = Curl_ssl_set_engine_default(data);
1832     break;
1833   case CURLOPT_CRLF:
1834     /*
1835      * Kludgy option to enable CRLF conversions. Subject for removal.
1836      */
1837     data->set.crlf = (0 != va_arg(param, long))?TRUE:FALSE;
1838     break;
1839
1840   case CURLOPT_INTERFACE:
1841     /*
1842      * Set what interface or address/hostname to bind the socket to when
1843      * performing an operation and thus what from-IP your connection will use.
1844      */
1845     result = setstropt(&data->set.str[STRING_DEVICE],
1846                        va_arg(param, char *));
1847     break;
1848   case CURLOPT_LOCALPORT:
1849     /*
1850      * Set what local port to bind the socket to when performing an operation.
1851      */
1852     data->set.localport = curlx_sltous(va_arg(param, long));
1853     break;
1854   case CURLOPT_LOCALPORTRANGE:
1855     /*
1856      * Set number of local ports to try, starting with CURLOPT_LOCALPORT.
1857      */
1858     data->set.localportrange = curlx_sltosi(va_arg(param, long));
1859     break;
1860   case CURLOPT_KRBLEVEL:
1861     /*
1862      * A string that defines the kerberos security level.
1863      */
1864     result = setstropt(&data->set.str[STRING_KRB_LEVEL],
1865                        va_arg(param, char *));
1866     data->set.krb = (NULL != data->set.str[STRING_KRB_LEVEL])?TRUE:FALSE;
1867     break;
1868   case CURLOPT_GSSAPI_DELEGATION:
1869     /*
1870      * GSSAPI credential delegation
1871      */
1872     data->set.gssapi_delegation = va_arg(param, long);
1873     break;
1874   case CURLOPT_SSL_VERIFYPEER:
1875     /*
1876      * Enable peer SSL verifying.
1877      */
1878     data->set.ssl.verifypeer = (0 != va_arg(param, long))?TRUE:FALSE;
1879     break;
1880   case CURLOPT_SSL_VERIFYHOST:
1881     /*
1882      * Enable verification of the host name in the peer certificate
1883      */
1884     arg = va_arg(param, long);
1885
1886     /* Obviously people are not reading documentation and too many thought
1887        this argument took a boolean when it wasn't and misused it. We thus ban
1888        1 as a sensible input and we warn about its use. Then we only have the
1889        2 action internally stored as TRUE. */
1890
1891     if(1 == arg) {
1892       failf(data, "CURLOPT_SSL_VERIFYHOST no longer supports 1 as value!");
1893       return CURLE_BAD_FUNCTION_ARGUMENT;
1894     }
1895
1896     data->set.ssl.verifyhost = (0 != arg)?TRUE:FALSE;
1897     break;
1898 #ifdef USE_SSLEAY
1899     /* since these two options are only possible to use on an OpenSSL-
1900        powered libcurl we #ifdef them on this condition so that libcurls
1901        built against other SSL libs will return a proper error when trying
1902        to set this option! */
1903   case CURLOPT_SSL_CTX_FUNCTION:
1904     /*
1905      * Set a SSL_CTX callback
1906      */
1907     data->set.ssl.fsslctx = va_arg(param, curl_ssl_ctx_callback);
1908     break;
1909   case CURLOPT_SSL_CTX_DATA:
1910     /*
1911      * Set a SSL_CTX callback parameter pointer
1912      */
1913     data->set.ssl.fsslctxp = va_arg(param, void *);
1914     break;
1915 #endif
1916 #if defined(USE_SSLEAY) || defined(USE_QSOSSL) || defined(USE_GSKIT)
1917   case CURLOPT_CERTINFO:
1918     data->set.ssl.certinfo = (0 != va_arg(param, long))?TRUE:FALSE;
1919     break;
1920 #endif
1921   case CURLOPT_CAINFO:
1922     /*
1923      * Set CA info for SSL connection. Specify file name of the CA certificate
1924      */
1925     result = setstropt(&data->set.str[STRING_SSL_CAFILE],
1926                        va_arg(param, char *));
1927     break;
1928   case CURLOPT_CAPATH:
1929     /*
1930      * Set CA path info for SSL connection. Specify directory name of the CA
1931      * certificates which have been prepared using openssl c_rehash utility.
1932      */
1933     /* This does not work on windows. */
1934     result = setstropt(&data->set.str[STRING_SSL_CAPATH],
1935                        va_arg(param, char *));
1936     break;
1937   case CURLOPT_CRLFILE:
1938     /*
1939      * Set CRL file info for SSL connection. Specify file name of the CRL
1940      * to check certificates revocation
1941      */
1942     result = setstropt(&data->set.str[STRING_SSL_CRLFILE],
1943                        va_arg(param, char *));
1944     break;
1945   case CURLOPT_ISSUERCERT:
1946     /*
1947      * Set Issuer certificate file
1948      * to check certificates issuer
1949      */
1950     result = setstropt(&data->set.str[STRING_SSL_ISSUERCERT],
1951                        va_arg(param, char *));
1952     break;
1953   case CURLOPT_TELNETOPTIONS:
1954     /*
1955      * Set a linked list of telnet options
1956      */
1957     data->set.telnet_options = va_arg(param, struct curl_slist *);
1958     break;
1959
1960   case CURLOPT_BUFFERSIZE:
1961     /*
1962      * The application kindly asks for a differently sized receive buffer.
1963      * If it seems reasonable, we'll use it.
1964      */
1965     data->set.buffer_size = va_arg(param, long);
1966
1967     if((data->set.buffer_size> (BUFSIZE -1 )) ||
1968        (data->set.buffer_size < 1))
1969       data->set.buffer_size = 0; /* huge internal default */
1970
1971     break;
1972
1973   case CURLOPT_NOSIGNAL:
1974     /*
1975      * The application asks not to set any signal() or alarm() handlers,
1976      * even when using a timeout.
1977      */
1978     data->set.no_signal = (0 != va_arg(param, long))?TRUE:FALSE;
1979     break;
1980
1981   case CURLOPT_SHARE:
1982   {
1983     struct Curl_share *set;
1984     set = va_arg(param, struct Curl_share *);
1985
1986     /* disconnect from old share, if any */
1987     if(data->share) {
1988       Curl_share_lock(data, CURL_LOCK_DATA_SHARE, CURL_LOCK_ACCESS_SINGLE);
1989
1990       if(data->dns.hostcachetype == HCACHE_SHARED) {
1991         data->dns.hostcache = NULL;
1992         data->dns.hostcachetype = HCACHE_NONE;
1993       }
1994
1995 #if !defined(CURL_DISABLE_HTTP) && !defined(CURL_DISABLE_COOKIES)
1996       if(data->share->cookies == data->cookies)
1997         data->cookies = NULL;
1998 #endif
1999
2000       if(data->share->sslsession == data->state.session)
2001         data->state.session = NULL;
2002
2003       data->share->dirty--;
2004
2005       Curl_share_unlock(data, CURL_LOCK_DATA_SHARE);
2006       data->share = NULL;
2007     }
2008
2009     /* use new share if it set */
2010     data->share = set;
2011     if(data->share) {
2012
2013       Curl_share_lock(data, CURL_LOCK_DATA_SHARE, CURL_LOCK_ACCESS_SINGLE);
2014
2015       data->share->dirty++;
2016
2017       if(data->share->hostcache) {
2018         /* use shared host cache */
2019         data->dns.hostcache = data->share->hostcache;
2020         data->dns.hostcachetype = HCACHE_SHARED;
2021       }
2022 #if !defined(CURL_DISABLE_HTTP) && !defined(CURL_DISABLE_COOKIES)
2023       if(data->share->cookies) {
2024         /* use shared cookie list, first free own one if any */
2025         if(data->cookies)
2026           Curl_cookie_cleanup(data->cookies);
2027         /* enable cookies since we now use a share that uses cookies! */
2028         data->cookies = data->share->cookies;
2029       }
2030 #endif   /* CURL_DISABLE_HTTP */
2031       if(data->share->sslsession) {
2032         data->set.ssl.max_ssl_sessions = data->share->max_ssl_sessions;
2033         data->state.session = data->share->sslsession;
2034       }
2035       Curl_share_unlock(data, CURL_LOCK_DATA_SHARE);
2036
2037     }
2038     /* check for host cache not needed,
2039      * it will be done by curl_easy_perform */
2040   }
2041   break;
2042
2043   case CURLOPT_PRIVATE:
2044     /*
2045      * Set private data pointer.
2046      */
2047     data->set.private_data = va_arg(param, void *);
2048     break;
2049
2050   case CURLOPT_MAXFILESIZE:
2051     /*
2052      * Set the maximum size of a file to download.
2053      */
2054     data->set.max_filesize = va_arg(param, long);
2055     break;
2056
2057 #ifdef USE_SSL
2058   case CURLOPT_USE_SSL:
2059     /*
2060      * Make transfers attempt to use SSL/TLS.
2061      */
2062     data->set.use_ssl = (curl_usessl)va_arg(param, long);
2063     break;
2064
2065   case CURLOPT_SSL_OPTIONS:
2066     arg = va_arg(param, long);
2067     data->set.ssl_enable_beast = arg&CURLSSLOPT_ALLOW_BEAST?TRUE:FALSE;
2068     break;
2069
2070 #endif
2071   case CURLOPT_FTPSSLAUTH:
2072     /*
2073      * Set a specific auth for FTP-SSL transfers.
2074      */
2075     data->set.ftpsslauth = (curl_ftpauth)va_arg(param, long);
2076     break;
2077
2078   case CURLOPT_IPRESOLVE:
2079     data->set.ipver = va_arg(param, long);
2080     break;
2081
2082   case CURLOPT_MAXFILESIZE_LARGE:
2083     /*
2084      * Set the maximum size of a file to download.
2085      */
2086     data->set.max_filesize = va_arg(param, curl_off_t);
2087     break;
2088
2089   case CURLOPT_TCP_NODELAY:
2090     /*
2091      * Enable or disable TCP_NODELAY, which will disable/enable the Nagle
2092      * algorithm
2093      */
2094     data->set.tcp_nodelay = (0 != va_arg(param, long))?TRUE:FALSE;
2095     break;
2096
2097   case CURLOPT_FTP_ACCOUNT:
2098     result = setstropt(&data->set.str[STRING_FTP_ACCOUNT],
2099                        va_arg(param, char *));
2100     break;
2101
2102   case CURLOPT_IGNORE_CONTENT_LENGTH:
2103     data->set.ignorecl = (0 != va_arg(param, long))?TRUE:FALSE;
2104     break;
2105
2106   case CURLOPT_CONNECT_ONLY:
2107     /*
2108      * No data transfer, set up connection and let application use the socket
2109      */
2110     data->set.connect_only = (0 != va_arg(param, long))?TRUE:FALSE;
2111     break;
2112
2113   case CURLOPT_FTP_ALTERNATIVE_TO_USER:
2114     result = setstropt(&data->set.str[STRING_FTP_ALTERNATIVE_TO_USER],
2115                        va_arg(param, char *));
2116     break;
2117
2118   case CURLOPT_SOCKOPTFUNCTION:
2119     /*
2120      * socket callback function: called after socket() but before connect()
2121      */
2122     data->set.fsockopt = va_arg(param, curl_sockopt_callback);
2123     break;
2124
2125   case CURLOPT_SOCKOPTDATA:
2126     /*
2127      * socket callback data pointer. Might be NULL.
2128      */
2129     data->set.sockopt_client = va_arg(param, void *);
2130     break;
2131
2132   case CURLOPT_OPENSOCKETFUNCTION:
2133     /*
2134      * open/create socket callback function: called instead of socket(),
2135      * before connect()
2136      */
2137     data->set.fopensocket = va_arg(param, curl_opensocket_callback);
2138     break;
2139
2140   case CURLOPT_OPENSOCKETDATA:
2141     /*
2142      * socket callback data pointer. Might be NULL.
2143      */
2144     data->set.opensocket_client = va_arg(param, void *);
2145     break;
2146
2147   case CURLOPT_CLOSESOCKETFUNCTION:
2148     /*
2149      * close socket callback function: called instead of close()
2150      * when shutting down a connection
2151      */
2152     data->set.fclosesocket = va_arg(param, curl_closesocket_callback);
2153     break;
2154
2155   case CURLOPT_CLOSESOCKETDATA:
2156     /*
2157      * socket callback data pointer. Might be NULL.
2158      */
2159     data->set.closesocket_client = va_arg(param, void *);
2160     break;
2161
2162   case CURLOPT_SSL_SESSIONID_CACHE:
2163     data->set.ssl.sessionid = (0 != va_arg(param, long))?TRUE:FALSE;
2164     break;
2165
2166 #ifdef USE_LIBSSH2
2167     /* we only include SSH options if explicitly built to support SSH */
2168   case CURLOPT_SSH_AUTH_TYPES:
2169     data->set.ssh_auth_types = va_arg(param, long);
2170     break;
2171
2172   case CURLOPT_SSH_PUBLIC_KEYFILE:
2173     /*
2174      * Use this file instead of the $HOME/.ssh/id_dsa.pub file
2175      */
2176     result = setstropt(&data->set.str[STRING_SSH_PUBLIC_KEY],
2177                        va_arg(param, char *));
2178     break;
2179
2180   case CURLOPT_SSH_PRIVATE_KEYFILE:
2181     /*
2182      * Use this file instead of the $HOME/.ssh/id_dsa file
2183      */
2184     result = setstropt(&data->set.str[STRING_SSH_PRIVATE_KEY],
2185                        va_arg(param, char *));
2186     break;
2187   case CURLOPT_SSH_HOST_PUBLIC_KEY_MD5:
2188     /*
2189      * Option to allow for the MD5 of the host public key to be checked
2190      * for validation purposes.
2191      */
2192     result = setstropt(&data->set.str[STRING_SSH_HOST_PUBLIC_KEY_MD5],
2193                        va_arg(param, char *));
2194     break;
2195 #ifdef HAVE_LIBSSH2_KNOWNHOST_API
2196   case CURLOPT_SSH_KNOWNHOSTS:
2197     /*
2198      * Store the file name to read known hosts from.
2199      */
2200     result = setstropt(&data->set.str[STRING_SSH_KNOWNHOSTS],
2201                        va_arg(param, char *));
2202     break;
2203
2204   case CURLOPT_SSH_KEYFUNCTION:
2205     /* setting to NULL is fine since the ssh.c functions themselves will
2206        then rever to use the internal default */
2207     data->set.ssh_keyfunc = va_arg(param, curl_sshkeycallback);
2208     break;
2209
2210   case CURLOPT_SSH_KEYDATA:
2211     /*
2212      * Custom client data to pass to the SSH keyfunc callback
2213      */
2214     data->set.ssh_keyfunc_userp = va_arg(param, void *);
2215     break;
2216 #endif /* HAVE_LIBSSH2_KNOWNHOST_API */
2217
2218 #endif /* USE_LIBSSH2 */
2219
2220   case CURLOPT_HTTP_TRANSFER_DECODING:
2221     /*
2222      * disable libcurl transfer encoding is used
2223      */
2224     data->set.http_te_skip = (0 == va_arg(param, long))?TRUE:FALSE;
2225     break;
2226
2227   case CURLOPT_HTTP_CONTENT_DECODING:
2228     /*
2229      * raw data passed to the application when content encoding is used
2230      */
2231     data->set.http_ce_skip = (0 == va_arg(param, long))?TRUE:FALSE;
2232     break;
2233
2234   case CURLOPT_NEW_FILE_PERMS:
2235     /*
2236      * Uses these permissions instead of 0644
2237      */
2238     data->set.new_file_perms = va_arg(param, long);
2239     break;
2240
2241   case CURLOPT_NEW_DIRECTORY_PERMS:
2242     /*
2243      * Uses these permissions instead of 0755
2244      */
2245     data->set.new_directory_perms = va_arg(param, long);
2246     break;
2247
2248   case CURLOPT_ADDRESS_SCOPE:
2249     /*
2250      * We always get longs when passed plain numericals, but for this value we
2251      * know that an unsigned int will always hold the value so we blindly
2252      * typecast to this type
2253      */
2254     data->set.scope = curlx_sltoui(va_arg(param, long));
2255     break;
2256
2257   case CURLOPT_PROTOCOLS:
2258     /* set the bitmask for the protocols that are allowed to be used for the
2259        transfer, which thus helps the app which takes URLs from users or other
2260        external inputs and want to restrict what protocol(s) to deal
2261        with. Defaults to CURLPROTO_ALL. */
2262     data->set.allowed_protocols = va_arg(param, long);
2263     break;
2264
2265   case CURLOPT_REDIR_PROTOCOLS:
2266     /* set the bitmask for the protocols that libcurl is allowed to follow to,
2267        as a subset of the CURLOPT_PROTOCOLS ones. That means the protocol needs
2268        to be set in both bitmasks to be allowed to get redirected to. Defaults
2269        to all protocols except FILE and SCP. */
2270     data->set.redir_protocols = va_arg(param, long);
2271     break;
2272
2273   case CURLOPT_MAIL_FROM:
2274     /* Set the SMTP mail originator */
2275     result = setstropt(&data->set.str[STRING_MAIL_FROM],
2276                        va_arg(param, char *));
2277     break;
2278
2279   case CURLOPT_MAIL_AUTH:
2280     /* Set the SMTP auth originator */
2281     result = setstropt(&data->set.str[STRING_MAIL_AUTH],
2282                        va_arg(param, char *));
2283     break;
2284
2285   case CURLOPT_MAIL_RCPT:
2286     /* Set the list of mail recipients */
2287     data->set.mail_rcpt = va_arg(param, struct curl_slist *);
2288     break;
2289
2290   case CURLOPT_SASL_IR:
2291     /* Enable/disable SASL initial response */
2292     data->set.sasl_ir = (0 != va_arg(param, long)) ? TRUE : FALSE;
2293     break;
2294
2295   case CURLOPT_RTSP_REQUEST:
2296     {
2297       /*
2298        * Set the RTSP request method (OPTIONS, SETUP, PLAY, etc...)
2299        * Would this be better if the RTSPREQ_* were just moved into here?
2300        */
2301       long curl_rtspreq = va_arg(param, long);
2302       Curl_RtspReq rtspreq = RTSPREQ_NONE;
2303       switch(curl_rtspreq) {
2304         case CURL_RTSPREQ_OPTIONS:
2305           rtspreq = RTSPREQ_OPTIONS;
2306           break;
2307
2308         case CURL_RTSPREQ_DESCRIBE:
2309           rtspreq = RTSPREQ_DESCRIBE;
2310           break;
2311
2312         case CURL_RTSPREQ_ANNOUNCE:
2313           rtspreq = RTSPREQ_ANNOUNCE;
2314           break;
2315
2316         case CURL_RTSPREQ_SETUP:
2317           rtspreq = RTSPREQ_SETUP;
2318           break;
2319
2320         case CURL_RTSPREQ_PLAY:
2321           rtspreq = RTSPREQ_PLAY;
2322           break;
2323
2324         case CURL_RTSPREQ_PAUSE:
2325           rtspreq = RTSPREQ_PAUSE;
2326           break;
2327
2328         case CURL_RTSPREQ_TEARDOWN:
2329           rtspreq = RTSPREQ_TEARDOWN;
2330           break;
2331
2332         case CURL_RTSPREQ_GET_PARAMETER:
2333           rtspreq = RTSPREQ_GET_PARAMETER;
2334           break;
2335
2336         case CURL_RTSPREQ_SET_PARAMETER:
2337           rtspreq = RTSPREQ_SET_PARAMETER;
2338           break;
2339
2340         case CURL_RTSPREQ_RECORD:
2341           rtspreq = RTSPREQ_RECORD;
2342           break;
2343
2344         case CURL_RTSPREQ_RECEIVE:
2345           rtspreq = RTSPREQ_RECEIVE;
2346           break;
2347         default:
2348           rtspreq = RTSPREQ_NONE;
2349       }
2350
2351       data->set.rtspreq = rtspreq;
2352     break;
2353     }
2354
2355
2356   case CURLOPT_RTSP_SESSION_ID:
2357     /*
2358      * Set the RTSP Session ID manually. Useful if the application is
2359      * resuming a previously established RTSP session
2360      */
2361     result = setstropt(&data->set.str[STRING_RTSP_SESSION_ID],
2362                        va_arg(param, char *));
2363     break;
2364
2365   case CURLOPT_RTSP_STREAM_URI:
2366     /*
2367      * Set the Stream URI for the RTSP request. Unless the request is
2368      * for generic server options, the application will need to set this.
2369      */
2370     result = setstropt(&data->set.str[STRING_RTSP_STREAM_URI],
2371                        va_arg(param, char *));
2372     break;
2373
2374   case CURLOPT_RTSP_TRANSPORT:
2375     /*
2376      * The content of the Transport: header for the RTSP request
2377      */
2378     result = setstropt(&data->set.str[STRING_RTSP_TRANSPORT],
2379                        va_arg(param, char *));
2380     break;
2381
2382   case CURLOPT_RTSP_CLIENT_CSEQ:
2383     /*
2384      * Set the CSEQ number to issue for the next RTSP request. Useful if the
2385      * application is resuming a previously broken connection. The CSEQ
2386      * will increment from this new number henceforth.
2387      */
2388     data->state.rtsp_next_client_CSeq = va_arg(param, long);
2389     break;
2390
2391   case CURLOPT_RTSP_SERVER_CSEQ:
2392     /* Same as the above, but for server-initiated requests */
2393     data->state.rtsp_next_client_CSeq = va_arg(param, long);
2394     break;
2395
2396   case CURLOPT_INTERLEAVEDATA:
2397     data->set.rtp_out = va_arg(param, void *);
2398     break;
2399   case CURLOPT_INTERLEAVEFUNCTION:
2400     /* Set the user defined RTP write function */
2401     data->set.fwrite_rtp = va_arg(param, curl_write_callback);
2402     break;
2403
2404   case CURLOPT_WILDCARDMATCH:
2405     data->set.wildcardmatch = (0 != va_arg(param, long))?TRUE:FALSE;
2406     break;
2407   case CURLOPT_CHUNK_BGN_FUNCTION:
2408     data->set.chunk_bgn = va_arg(param, curl_chunk_bgn_callback);
2409     break;
2410   case CURLOPT_CHUNK_END_FUNCTION:
2411     data->set.chunk_end = va_arg(param, curl_chunk_end_callback);
2412     break;
2413   case CURLOPT_FNMATCH_FUNCTION:
2414     data->set.fnmatch = va_arg(param, curl_fnmatch_callback);
2415     break;
2416   case CURLOPT_CHUNK_DATA:
2417     data->wildcard.customptr = va_arg(param, void *);
2418     break;
2419   case CURLOPT_FNMATCH_DATA:
2420     data->set.fnmatch_data = va_arg(param, void *);
2421     break;
2422 #ifdef USE_TLS_SRP
2423   case CURLOPT_TLSAUTH_USERNAME:
2424     result = setstropt(&data->set.str[STRING_TLSAUTH_USERNAME],
2425                        va_arg(param, char *));
2426     if(data->set.str[STRING_TLSAUTH_USERNAME] && !data->set.ssl.authtype)
2427       data->set.ssl.authtype = CURL_TLSAUTH_SRP; /* default to SRP */
2428     break;
2429   case CURLOPT_TLSAUTH_PASSWORD:
2430     result = setstropt(&data->set.str[STRING_TLSAUTH_PASSWORD],
2431                        va_arg(param, char *));
2432     if(data->set.str[STRING_TLSAUTH_USERNAME] && !data->set.ssl.authtype)
2433       data->set.ssl.authtype = CURL_TLSAUTH_SRP; /* default to SRP */
2434     break;
2435   case CURLOPT_TLSAUTH_TYPE:
2436     if(strnequal((char *)va_arg(param, char *), "SRP", strlen("SRP")))
2437       data->set.ssl.authtype = CURL_TLSAUTH_SRP;
2438     else
2439       data->set.ssl.authtype = CURL_TLSAUTH_NONE;
2440     break;
2441 #endif
2442   case CURLOPT_DNS_SERVERS:
2443     result = Curl_set_dns_servers(data, va_arg(param, char *));
2444     break;
2445
2446   case CURLOPT_TCP_KEEPALIVE:
2447     data->set.tcp_keepalive = (0 != va_arg(param, long))?TRUE:FALSE;
2448     break;
2449   case CURLOPT_TCP_KEEPIDLE:
2450     data->set.tcp_keepidle = va_arg(param, long);
2451     break;
2452   case CURLOPT_TCP_KEEPINTVL:
2453     data->set.tcp_keepintvl = va_arg(param, long);
2454     break;
2455
2456   default:
2457     /* unknown tag and its companion, just ignore: */
2458     result = CURLE_UNKNOWN_OPTION;
2459     break;
2460   }
2461
2462   return result;
2463 }
2464
2465 static void conn_free(struct connectdata *conn)
2466 {
2467   if(!conn)
2468     return;
2469
2470   /* possible left-overs from the async name resolvers */
2471   Curl_resolver_cancel(conn);
2472
2473   /* close the SSL stuff before we close any sockets since they will/may
2474      write to the sockets */
2475   Curl_ssl_close(conn, FIRSTSOCKET);
2476   Curl_ssl_close(conn, SECONDARYSOCKET);
2477
2478   /* close possibly still open sockets */
2479   if(CURL_SOCKET_BAD != conn->sock[SECONDARYSOCKET])
2480     Curl_closesocket(conn, conn->sock[SECONDARYSOCKET]);
2481   if(CURL_SOCKET_BAD != conn->sock[FIRSTSOCKET])
2482     Curl_closesocket(conn, conn->sock[FIRSTSOCKET]);
2483
2484 #if defined(USE_NTLM) && defined(NTLM_WB_ENABLED)
2485   Curl_ntlm_wb_cleanup(conn);
2486 #endif
2487
2488   Curl_safefree(conn->user);
2489   Curl_safefree(conn->passwd);
2490   Curl_safefree(conn->options);
2491   Curl_safefree(conn->proxyuser);
2492   Curl_safefree(conn->proxypasswd);
2493   Curl_safefree(conn->allocptr.proxyuserpwd);
2494   Curl_safefree(conn->allocptr.uagent);
2495   Curl_safefree(conn->allocptr.userpwd);
2496   Curl_safefree(conn->allocptr.accept_encoding);
2497   Curl_safefree(conn->allocptr.te);
2498   Curl_safefree(conn->allocptr.rangeline);
2499   Curl_safefree(conn->allocptr.ref);
2500   Curl_safefree(conn->allocptr.host);
2501   Curl_safefree(conn->allocptr.cookiehost);
2502   Curl_safefree(conn->allocptr.rtsp_transport);
2503   Curl_safefree(conn->trailer);
2504   Curl_safefree(conn->host.rawalloc); /* host name buffer */
2505   Curl_safefree(conn->proxy.rawalloc); /* proxy name buffer */
2506   Curl_safefree(conn->master_buffer);
2507
2508   Curl_llist_destroy(conn->send_pipe, NULL);
2509   Curl_llist_destroy(conn->recv_pipe, NULL);
2510
2511   conn->send_pipe = NULL;
2512   conn->recv_pipe = NULL;
2513
2514   Curl_safefree(conn->localdev);
2515   Curl_free_ssl_config(&conn->ssl_config);
2516
2517   free(conn); /* free all the connection oriented data */
2518 }
2519
2520 CURLcode Curl_disconnect(struct connectdata *conn, bool dead_connection)
2521 {
2522   struct SessionHandle *data;
2523   if(!conn)
2524     return CURLE_OK; /* this is closed and fine already */
2525   data = conn->data;
2526
2527   if(!data) {
2528     DEBUGF(fprintf(stderr, "DISCONNECT without easy handle, ignoring\n"));
2529     return CURLE_OK;
2530   }
2531
2532   if(conn->dns_entry != NULL) {
2533     Curl_resolv_unlock(data, conn->dns_entry);
2534     conn->dns_entry = NULL;
2535   }
2536
2537   Curl_hostcache_prune(data); /* kill old DNS cache entries */
2538
2539   {
2540     int has_host_ntlm = (conn->ntlm.state != NTLMSTATE_NONE);
2541     int has_proxy_ntlm = (conn->proxyntlm.state != NTLMSTATE_NONE);
2542
2543     /* Authentication data is a mix of connection-related and sessionhandle-
2544        related stuff. NTLM is connection-related so when we close the shop
2545        we shall forget. */
2546
2547     if(has_host_ntlm) {
2548       data->state.authhost.done = FALSE;
2549       data->state.authhost.picked =
2550         data->state.authhost.want;
2551     }
2552
2553     if(has_proxy_ntlm) {
2554       data->state.authproxy.done = FALSE;
2555       data->state.authproxy.picked =
2556         data->state.authproxy.want;
2557     }
2558
2559     if(has_host_ntlm || has_proxy_ntlm)
2560       data->state.authproblem = FALSE;
2561   }
2562
2563   /* Cleanup NTLM connection-related data */
2564   Curl_http_ntlm_cleanup(conn);
2565
2566   /* Cleanup possible redirect junk */
2567   if(data->req.newurl) {
2568     free(data->req.newurl);
2569     data->req.newurl = NULL;
2570   }
2571
2572   if(conn->handler->disconnect)
2573     /* This is set if protocol-specific cleanups should be made */
2574     conn->handler->disconnect(conn, dead_connection);
2575
2576     /* unlink ourselves! */
2577   infof(data, "Closing connection %d\n", conn->connection_id);
2578   Curl_conncache_remove_conn(data->state.conn_cache, conn);
2579
2580 #if defined(USE_LIBIDN)
2581   if(conn->host.encalloc)
2582     idn_free(conn->host.encalloc); /* encoded host name buffer, must be freed
2583                                       with idn_free() since this was allocated
2584                                       by libidn */
2585   if(conn->proxy.encalloc)
2586     idn_free(conn->proxy.encalloc); /* encoded proxy name buffer, must be
2587                                        freed with idn_free() since this was
2588                                        allocated by libidn */
2589 #elif defined(USE_WIN32_IDN)
2590   free(conn->host.encalloc); /* encoded host name buffer, must be freed with
2591                                 idn_free() since this was allocated by
2592                                 curl_win32_idn_to_ascii */
2593   if(conn->proxy.encalloc)
2594     free(conn->proxy.encalloc); /* encoded proxy name buffer, must be freed
2595                                    with idn_free() since this was allocated by
2596                                    curl_win32_idn_to_ascii */
2597 #endif
2598
2599   Curl_ssl_close(conn, FIRSTSOCKET);
2600
2601   /* Indicate to all handles on the pipe that we're dead */
2602   if(Curl_multi_pipeline_enabled(data->multi)) {
2603     signalPipeClose(conn->send_pipe, TRUE);
2604     signalPipeClose(conn->recv_pipe, TRUE);
2605   }
2606
2607   conn_free(conn);
2608   data->state.current_conn = NULL;
2609   Curl_speedinit(data);
2610
2611   return CURLE_OK;
2612 }
2613
2614 /*
2615  * This function should return TRUE if the socket is to be assumed to
2616  * be dead. Most commonly this happens when the server has closed the
2617  * connection due to inactivity.
2618  */
2619 static bool SocketIsDead(curl_socket_t sock)
2620 {
2621   int sval;
2622   bool ret_val = TRUE;
2623
2624   sval = Curl_socket_ready(sock, CURL_SOCKET_BAD, 0);
2625   if(sval == 0)
2626     /* timeout */
2627     ret_val = FALSE;
2628
2629   return ret_val;
2630 }
2631
2632 static bool IsPipeliningPossible(const struct SessionHandle *handle,
2633                                  const struct connectdata *conn)
2634 {
2635   if((conn->handler->protocol & CURLPROTO_HTTP) &&
2636      Curl_multi_pipeline_enabled(handle->multi) &&
2637      (handle->set.httpreq == HTTPREQ_GET ||
2638       handle->set.httpreq == HTTPREQ_HEAD) &&
2639      handle->set.httpversion != CURL_HTTP_VERSION_1_0)
2640     return TRUE;
2641
2642   return FALSE;
2643 }
2644
2645 bool Curl_isPipeliningEnabled(const struct SessionHandle *handle)
2646 {
2647   return Curl_multi_pipeline_enabled(handle->multi);
2648 }
2649
2650 CURLcode Curl_addHandleToPipeline(struct SessionHandle *data,
2651                                   struct curl_llist *pipeline)
2652 {
2653   if(!Curl_llist_insert_next(pipeline, pipeline->tail, data))
2654     return CURLE_OUT_OF_MEMORY;
2655   infof(data, "Curl_addHandleToPipeline: length: %d\n", pipeline->size);
2656   return CURLE_OK;
2657 }
2658
2659 int Curl_removeHandleFromPipeline(struct SessionHandle *handle,
2660                                   struct curl_llist *pipeline)
2661 {
2662   struct curl_llist_element *curr;
2663
2664   curr = pipeline->head;
2665   while(curr) {
2666     if(curr->ptr == handle) {
2667       Curl_llist_remove(pipeline, curr, NULL);
2668       return 1; /* we removed a handle */
2669     }
2670     curr = curr->next;
2671   }
2672
2673   return 0;
2674 }
2675
2676 #if 0 /* this code is saved here as it is useful for debugging purposes */
2677 static void Curl_printPipeline(struct curl_llist *pipeline)
2678 {
2679   struct curl_llist_element *curr;
2680
2681   curr = pipeline->head;
2682   while(curr) {
2683     struct SessionHandle *data = (struct SessionHandle *) curr->ptr;
2684     infof(data, "Handle in pipeline: %s\n", data->state.path);
2685     curr = curr->next;
2686   }
2687 }
2688 #endif
2689
2690 static struct SessionHandle* gethandleathead(struct curl_llist *pipeline)
2691 {
2692   struct curl_llist_element *curr = pipeline->head;
2693   if(curr) {
2694     return (struct SessionHandle *) curr->ptr;
2695   }
2696
2697   return NULL;
2698 }
2699
2700 /* remove the specified connection from all (possible) pipelines and related
2701    queues */
2702 void Curl_getoff_all_pipelines(struct SessionHandle *data,
2703                                struct connectdata *conn)
2704 {
2705   bool recv_head = (conn->readchannel_inuse &&
2706     (gethandleathead(conn->recv_pipe) == data)) ? TRUE : FALSE;
2707
2708   bool send_head = (conn->writechannel_inuse &&
2709     (gethandleathead(conn->send_pipe) == data)) ? TRUE : FALSE;
2710
2711   if(Curl_removeHandleFromPipeline(data, conn->recv_pipe) && recv_head)
2712     conn->readchannel_inuse = FALSE;
2713   if(Curl_removeHandleFromPipeline(data, conn->send_pipe) && send_head)
2714     conn->writechannel_inuse = FALSE;
2715 }
2716
2717 static void signalPipeClose(struct curl_llist *pipeline, bool pipe_broke)
2718 {
2719   struct curl_llist_element *curr;
2720
2721   if(!pipeline)
2722     return;
2723
2724   curr = pipeline->head;
2725   while(curr) {
2726     struct curl_llist_element *next = curr->next;
2727     struct SessionHandle *data = (struct SessionHandle *) curr->ptr;
2728
2729 #ifdef DEBUGBUILD /* debug-only code */
2730     if(data->magic != CURLEASY_MAGIC_NUMBER) {
2731       /* MAJOR BADNESS */
2732       infof(data, "signalPipeClose() found BAAD easy handle\n");
2733     }
2734 #endif
2735
2736     if(pipe_broke)
2737       data->state.pipe_broke = TRUE;
2738     Curl_multi_handlePipeBreak(data);
2739     Curl_llist_remove(pipeline, curr, NULL);
2740     curr = next;
2741   }
2742 }
2743
2744 /*
2745  * This function finds the connection in the connection
2746  * cache that has been unused for the longest time.
2747  *
2748  * Returns the pointer to the oldest idle connection, or NULL if none was
2749  * found.
2750  */
2751 static struct connectdata *
2752 find_oldest_idle_connection(struct SessionHandle *data)
2753 {
2754   struct conncache *bc = data->state.conn_cache;
2755   struct curl_hash_iterator iter;
2756   struct curl_llist_element *curr;
2757   struct curl_hash_element *he;
2758   long highscore=-1;
2759   long score;
2760   struct timeval now;
2761   struct connectdata *conn_candidate = NULL;
2762   struct connectbundle *bundle;
2763
2764   now = Curl_tvnow();
2765
2766   Curl_hash_start_iterate(bc->hash, &iter);
2767
2768   he = Curl_hash_next_element(&iter);
2769   while(he) {
2770     struct connectdata *conn;
2771
2772     bundle = he->ptr;
2773
2774     curr = bundle->conn_list->head;
2775     while(curr) {
2776       conn = curr->ptr;
2777
2778       if(!conn->inuse) {
2779         /* Set higher score for the age passed since the connection was used */
2780         score = Curl_tvdiff(now, conn->now);
2781
2782         if(score > highscore) {
2783           highscore = score;
2784           conn_candidate = conn;
2785         }
2786       }
2787       curr = curr->next;
2788     }
2789
2790     he = Curl_hash_next_element(&iter);
2791   }
2792
2793   return conn_candidate;
2794 }
2795
2796 /*
2797  * This function finds the connection in the connection
2798  * bundle that has been unused for the longest time.
2799  *
2800  * Returns the pointer to the oldest idle connection, or NULL if none was
2801  * found.
2802  */
2803 static struct connectdata *
2804 find_oldest_idle_connection_in_bundle(struct SessionHandle *data,
2805                                       struct connectbundle *bundle)
2806 {
2807   struct curl_llist_element *curr;
2808   long highscore=-1;
2809   long score;
2810   struct timeval now;
2811   struct connectdata *conn_candidate = NULL;
2812   struct connectdata *conn;
2813
2814   (void)data;
2815
2816   now = Curl_tvnow();
2817
2818   curr = bundle->conn_list->head;
2819   while(curr) {
2820     conn = curr->ptr;
2821
2822     if(!conn->inuse) {
2823       /* Set higher score for the age passed since the connection was used */
2824       score = Curl_tvdiff(now, conn->now);
2825
2826       if(score > highscore) {
2827         highscore = score;
2828         conn_candidate = conn;
2829       }
2830     }
2831     curr = curr->next;
2832   }
2833
2834   return conn_candidate;
2835 }
2836
2837 /*
2838  * Given one filled in connection struct (named needle), this function should
2839  * detect if there already is one that has all the significant details
2840  * exactly the same and thus should be used instead.
2841  *
2842  * If there is a match, this function returns TRUE - and has marked the
2843  * connection as 'in-use'. It must later be called with ConnectionDone() to
2844  * return back to 'idle' (unused) state.
2845  *
2846  * The force_reuse flag is set if the connection must be used, even if
2847  * the pipelining strategy wants to open a new connection instead of reusing.
2848  */
2849 static bool
2850 ConnectionExists(struct SessionHandle *data,
2851                  struct connectdata *needle,
2852                  struct connectdata **usethis,
2853                  bool *force_reuse)
2854 {
2855   struct connectdata *check;
2856   struct connectdata *chosen = 0;
2857   bool canPipeline = IsPipeliningPossible(data, needle);
2858   bool wantNTLM = (data->state.authhost.want==CURLAUTH_NTLM) ||
2859                   (data->state.authhost.want==CURLAUTH_NTLM_WB) ? TRUE : FALSE;
2860   struct connectbundle *bundle;
2861
2862   *force_reuse = FALSE;
2863
2864   /* We can't pipe if the site is blacklisted */
2865   if(canPipeline && Curl_pipeline_site_blacklisted(data, needle)) {
2866     canPipeline = FALSE;
2867   }
2868
2869   /* Look up the bundle with all the connections to this
2870      particular host */
2871   bundle = Curl_conncache_find_bundle(data->state.conn_cache,
2872                                       needle->host.name);
2873   if(bundle) {
2874     size_t max_pipe_len = Curl_multi_max_pipeline_length(data->multi);
2875     size_t best_pipe_len = max_pipe_len;
2876     struct curl_llist_element *curr;
2877
2878     infof(data, "Found bundle for host %s: %p\n", needle->host.name, bundle);
2879
2880     /* We can't pipe if we don't know anything about the server */
2881     if(canPipeline && !bundle->server_supports_pipelining) {
2882       infof(data, "Server doesn't support pipelining\n");
2883       canPipeline = FALSE;
2884     }
2885
2886     curr = bundle->conn_list->head;
2887     while(curr) {
2888       bool match = FALSE;
2889       bool credentialsMatch = FALSE;
2890       size_t pipeLen;
2891
2892       /*
2893        * Note that if we use a HTTP proxy, we check connections to that
2894        * proxy and not to the actual remote server.
2895        */
2896       check = curr->ptr;
2897       curr = curr->next;
2898
2899       pipeLen = check->send_pipe->size + check->recv_pipe->size;
2900
2901       if(!pipeLen && !check->inuse) {
2902         /* The check for a dead socket makes sense only if there are no
2903            handles in pipeline and the connection isn't already marked in
2904            use */
2905         bool dead;
2906         if(check->handler->protocol & CURLPROTO_RTSP)
2907           /* RTSP is a special case due to RTP interleaving */
2908           dead = Curl_rtsp_connisdead(check);
2909         else
2910           dead = SocketIsDead(check->sock[FIRSTSOCKET]);
2911
2912         if(dead) {
2913           check->data = data;
2914           infof(data, "Connection %d seems to be dead!\n",
2915                 check->connection_id);
2916
2917           /* disconnect resources */
2918           Curl_disconnect(check, /* dead_connection */ TRUE);
2919           continue;
2920         }
2921       }
2922
2923       if(canPipeline) {
2924         /* Make sure the pipe has only GET requests */
2925         struct SessionHandle* sh = gethandleathead(check->send_pipe);
2926         struct SessionHandle* rh = gethandleathead(check->recv_pipe);
2927         if(sh) {
2928           if(!IsPipeliningPossible(sh, check))
2929             continue;
2930         }
2931         else if(rh) {
2932           if(!IsPipeliningPossible(rh, check))
2933             continue;
2934         }
2935       }
2936       else {
2937         if(pipeLen > 0) {
2938           /* can only happen within multi handles, and means that another easy
2939              handle is using this connection */
2940           continue;
2941         }
2942
2943         if(Curl_resolver_asynch()) {
2944           /* ip_addr_str[0] is NUL only if the resolving of the name hasn't
2945              completed yet and until then we don't re-use this connection */
2946           if(!check->ip_addr_str[0]) {
2947             infof(data,
2948                   "Connection #%ld is still name resolving, can't reuse\n",
2949                   check->connection_id);
2950             continue;
2951           }
2952         }
2953
2954         if((check->sock[FIRSTSOCKET] == CURL_SOCKET_BAD) ||
2955            check->bits.close) {
2956           /* Don't pick a connection that hasn't connected yet or that is going
2957              to get closed. */
2958           infof(data, "Connection #%ld isn't open enough, can't reuse\n",
2959                 check->connection_id);
2960 #ifdef DEBUGBUILD
2961           if(check->recv_pipe->size > 0) {
2962             infof(data,
2963                   "BAD! Unconnected #%ld has a non-empty recv pipeline!\n",
2964                   check->connection_id);
2965           }
2966 #endif
2967           continue;
2968         }
2969       }
2970
2971       if((needle->handler->flags&PROTOPT_SSL) !=
2972          (check->handler->flags&PROTOPT_SSL))
2973         /* don't do mixed SSL and non-SSL connections */
2974         if(!(needle->handler->protocol & check->handler->protocol))
2975           /* except protocols that have been upgraded via TLS */
2976           continue;
2977
2978       if(needle->handler->flags&PROTOPT_SSL) {
2979         if((data->set.ssl.verifypeer != check->verifypeer) ||
2980            (data->set.ssl.verifyhost != check->verifyhost))
2981           continue;
2982       }
2983
2984       if(needle->bits.proxy != check->bits.proxy)
2985         /* don't do mixed proxy and non-proxy connections */
2986         continue;
2987
2988       if(!canPipeline && check->inuse)
2989         /* this request can't be pipelined but the checked connection is
2990            already in use so we skip it */
2991         continue;
2992
2993       if(needle->localdev || needle->localport) {
2994         /* If we are bound to a specific local end (IP+port), we must not
2995            re-use a random other one, although if we didn't ask for a
2996            particular one we can reuse one that was bound.
2997
2998            This comparison is a bit rough and too strict. Since the input
2999            parameters can be specified in numerous ways and still end up the
3000            same it would take a lot of processing to make it really accurate.
3001            Instead, this matching will assume that re-uses of bound connections
3002            will most likely also re-use the exact same binding parameters and
3003            missing out a few edge cases shouldn't hurt anyone very much.
3004         */
3005         if((check->localport != needle->localport) ||
3006            (check->localportrange != needle->localportrange) ||
3007            !check->localdev ||
3008            !needle->localdev ||
3009            strcmp(check->localdev, needle->localdev))
3010           continue;
3011       }
3012
3013       if((needle->handler->protocol & CURLPROTO_FTP) ||
3014          ((needle->handler->protocol & CURLPROTO_HTTP) && wantNTLM)) {
3015          /* This is FTP or HTTP+NTLM, verify that we're using the same name
3016             and password as well */
3017          if(!strequal(needle->user, check->user) ||
3018             !strequal(needle->passwd, check->passwd)) {
3019             /* one of them was different */
3020             continue;
3021          }
3022          credentialsMatch = TRUE;
3023       }
3024
3025       if(!needle->bits.httpproxy || needle->handler->flags&PROTOPT_SSL ||
3026          (needle->bits.httpproxy && check->bits.httpproxy &&
3027           needle->bits.tunnel_proxy && check->bits.tunnel_proxy &&
3028           Curl_raw_equal(needle->proxy.name, check->proxy.name) &&
3029           (needle->port == check->port))) {
3030         /* The requested connection does not use a HTTP proxy or it uses SSL or
3031            it is a non-SSL protocol tunneled over the same http proxy name and
3032            port number or it is a non-SSL protocol which is allowed to be
3033            upgraded via TLS */
3034
3035         if((Curl_raw_equal(needle->handler->scheme, check->handler->scheme) ||
3036             needle->handler->protocol & check->handler->protocol) &&
3037            Curl_raw_equal(needle->host.name, check->host.name) &&
3038            needle->remote_port == check->remote_port) {
3039           if(needle->handler->flags & PROTOPT_SSL) {
3040             /* This is a SSL connection so verify that we're using the same
3041                SSL options as well */
3042             if(!Curl_ssl_config_matches(&needle->ssl_config,
3043                                         &check->ssl_config)) {
3044               DEBUGF(infof(data,
3045                            "Connection #%ld has different SSL parameters, "
3046                            "can't reuse\n",
3047                            check->connection_id));
3048               continue;
3049             }
3050             else if(check->ssl[FIRSTSOCKET].state != ssl_connection_complete) {
3051               DEBUGF(infof(data,
3052                            "Connection #%ld has not started SSL connect, "
3053                            "can't reuse\n",
3054                            check->connection_id));
3055               continue;
3056             }
3057           }
3058           match = TRUE;
3059         }
3060       }
3061       else { /* The requested needle connection is using a proxy,
3062                 is the checked one using the same host, port and type? */
3063         if(check->bits.proxy &&
3064            (needle->proxytype == check->proxytype) &&
3065            (needle->bits.tunnel_proxy == check->bits.tunnel_proxy) &&
3066            Curl_raw_equal(needle->proxy.name, check->proxy.name) &&
3067            needle->port == check->port) {
3068           /* This is the same proxy connection, use it! */
3069           match = TRUE;
3070         }
3071       }
3072
3073       if(match) {
3074         /* If we are looking for an NTLM connection, check if this is already
3075            authenticating with the right credentials. If not, keep looking so
3076            that we can reuse NTLM connections if possible. (Especially we
3077            must not reuse the same connection if partway through
3078            a handshake!) */
3079         if(wantNTLM) {
3080           if(credentialsMatch && check->ntlm.state != NTLMSTATE_NONE) {
3081             chosen = check;
3082
3083             /* We must use this connection, no other */
3084             *force_reuse = TRUE;
3085             break;
3086           }
3087           else
3088             continue;
3089         }
3090
3091         if(canPipeline) {
3092           /* We can pipeline if we want to. Let's continue looking for
3093              the optimal connection to use, i.e the shortest pipe that is not
3094              blacklisted. */
3095
3096           if(pipeLen == 0) {
3097             /* We have the optimal connection. Let's stop looking. */
3098             chosen = check;
3099             break;
3100           }
3101
3102           /* We can't use the connection if the pipe is full */
3103           if(pipeLen >= max_pipe_len)
3104             continue;
3105
3106           /* We can't use the connection if the pipe is penalized */
3107           if(Curl_pipeline_penalized(data, check))
3108             continue;
3109
3110           if(pipeLen < best_pipe_len) {
3111             /* This connection has a shorter pipe so far. We'll pick this
3112                and continue searching */
3113             chosen = check;
3114             best_pipe_len = pipeLen;
3115             continue;
3116           }
3117         }
3118         else {
3119           /* We have found a connection. Let's stop searching. */
3120           chosen = check;
3121           break;
3122         }
3123       }
3124     }
3125   }
3126
3127   if(chosen) {
3128     *usethis = chosen;
3129     return TRUE; /* yes, we found one to use! */
3130   }
3131
3132   return FALSE; /* no matching connecting exists */
3133 }
3134
3135 /* Mark the connection as 'idle', or close it if the cache is full.
3136    Returns TRUE if the connection is kept, or FALSE if it was closed. */
3137 static bool
3138 ConnectionDone(struct SessionHandle *data, struct connectdata *conn)
3139 {
3140   /* data->multi->maxconnects can be negative, deal with it. */
3141   size_t maxconnects =
3142     (data->multi->maxconnects < 0) ? 0 : data->multi->maxconnects;
3143   struct connectdata *conn_candidate = NULL;
3144
3145   /* Mark the current connection as 'unused' */
3146   conn->inuse = FALSE;
3147
3148   if(maxconnects > 0 &&
3149      data->state.conn_cache->num_connections > maxconnects) {
3150     infof(data, "Connection cache is full, closing the oldest one.\n");
3151
3152     conn_candidate = find_oldest_idle_connection(data);
3153
3154     if(conn_candidate) {
3155       /* Set the connection's owner correctly */
3156       conn_candidate->data = data;
3157
3158       /* the winner gets the honour of being disconnected */
3159       (void)Curl_disconnect(conn_candidate, /* dead_connection */ FALSE);
3160     }
3161   }
3162
3163   return (conn_candidate == conn) ? FALSE : TRUE;
3164 }
3165
3166 /*
3167  * The given input connection struct pointer is to be stored in the connection
3168  * cache. If the cache is already full, least interesting existing connection
3169  * (if any) gets closed.
3170  *
3171  * The given connection should be unique. That must've been checked prior to
3172  * this call.
3173  */
3174 static CURLcode ConnectionStore(struct SessionHandle *data,
3175                                 struct connectdata *conn)
3176 {
3177   static int connection_id_counter = 0;
3178
3179   CURLcode result;
3180
3181   /* Assign a number to the connection for easier tracking in the log
3182      output */
3183   conn->connection_id = connection_id_counter++;
3184
3185   result = Curl_conncache_add_conn(data->state.conn_cache, conn);
3186   if(result != CURLE_OK)
3187     conn->connection_id = -1;
3188
3189   return result;
3190 }
3191
3192 /* after a TCP connection to the proxy has been verified, this function does
3193    the next magic step.
3194
3195    Note: this function's sub-functions call failf()
3196
3197 */
3198 CURLcode Curl_connected_proxy(struct connectdata *conn)
3199 {
3200   if(!conn->bits.proxy)
3201     return CURLE_OK;
3202
3203   switch(conn->proxytype) {
3204 #ifndef CURL_DISABLE_PROXY
3205   case CURLPROXY_SOCKS5:
3206   case CURLPROXY_SOCKS5_HOSTNAME:
3207     return Curl_SOCKS5(conn->proxyuser, conn->proxypasswd,
3208                        conn->host.name, conn->remote_port,
3209                        FIRSTSOCKET, conn);
3210
3211   case CURLPROXY_SOCKS4:
3212     return Curl_SOCKS4(conn->proxyuser, conn->host.name,
3213                        conn->remote_port, FIRSTSOCKET, conn, FALSE);
3214
3215   case CURLPROXY_SOCKS4A:
3216     return Curl_SOCKS4(conn->proxyuser, conn->host.name,
3217                        conn->remote_port, FIRSTSOCKET, conn, TRUE);
3218
3219 #endif /* CURL_DISABLE_PROXY */
3220   case CURLPROXY_HTTP:
3221   case CURLPROXY_HTTP_1_0:
3222     /* do nothing here. handled later. */
3223     break;
3224   default:
3225     break;
3226   } /* switch proxytype */
3227
3228   return CURLE_OK;
3229 }
3230
3231 static CURLcode ConnectPlease(struct SessionHandle *data,
3232                               struct connectdata *conn,
3233                               bool *connected)
3234 {
3235   CURLcode result;
3236   Curl_addrinfo *addr;
3237 #ifndef CURL_DISABLE_VERBOSE_STRINGS
3238   char *hostname = conn->bits.proxy?conn->proxy.name:conn->host.name;
3239
3240   infof(data, "About to connect() to %s%s port %ld (#%ld)\n",
3241         conn->bits.proxy?"proxy ":"",
3242         hostname, conn->port, conn->connection_id);
3243 #else
3244   (void)data;
3245 #endif
3246
3247   /*************************************************************
3248    * Connect to server/proxy
3249    *************************************************************/
3250   result= Curl_connecthost(conn,
3251                            conn->dns_entry,
3252                            &conn->sock[FIRSTSOCKET],
3253                            &addr,
3254                            connected);
3255   if(CURLE_OK == result) {
3256     /* All is cool, we store the current information */
3257     conn->ip_addr = addr;
3258
3259     if(*connected) {
3260       result = Curl_connected_proxy(conn);
3261       if(!result) {
3262         conn->bits.tcpconnect[FIRSTSOCKET] = TRUE;
3263         Curl_pgrsTime(data, TIMER_CONNECT); /* connect done */
3264       }
3265     }
3266   }
3267
3268   if(result)
3269     *connected = FALSE; /* mark it as not connected */
3270
3271   return result;
3272 }
3273
3274 /*
3275  * verboseconnect() displays verbose information after a connect
3276  */
3277 #ifndef CURL_DISABLE_VERBOSE_STRINGS
3278 void Curl_verboseconnect(struct connectdata *conn)
3279 {
3280   if(conn->data->set.verbose)
3281     infof(conn->data, "Connected to %s (%s) port %ld (#%ld)\n",
3282           conn->bits.proxy ? conn->proxy.dispname : conn->host.dispname,
3283           conn->ip_addr_str, conn->port, conn->connection_id);
3284 }
3285 #endif
3286
3287 int Curl_protocol_getsock(struct connectdata *conn,
3288                           curl_socket_t *socks,
3289                           int numsocks)
3290 {
3291   if(conn->handler->proto_getsock)
3292     return conn->handler->proto_getsock(conn, socks, numsocks);
3293   return GETSOCK_BLANK;
3294 }
3295
3296 int Curl_doing_getsock(struct connectdata *conn,
3297                        curl_socket_t *socks,
3298                        int numsocks)
3299 {
3300   if(conn && conn->handler->doing_getsock)
3301     return conn->handler->doing_getsock(conn, socks, numsocks);
3302   return GETSOCK_BLANK;
3303 }
3304
3305 /*
3306  * We are doing protocol-specific connecting and this is being called over and
3307  * over from the multi interface until the connection phase is done on
3308  * protocol layer.
3309  */
3310
3311 CURLcode Curl_protocol_connecting(struct connectdata *conn,
3312                                   bool *done)
3313 {
3314   CURLcode result=CURLE_OK;
3315
3316   if(conn && conn->handler->connecting) {
3317     *done = FALSE;
3318     result = conn->handler->connecting(conn, done);
3319   }
3320   else
3321     *done = TRUE;
3322
3323   return result;
3324 }
3325
3326 /*
3327  * We are DOING this is being called over and over from the multi interface
3328  * until the DOING phase is done on protocol layer.
3329  */
3330
3331 CURLcode Curl_protocol_doing(struct connectdata *conn, bool *done)
3332 {
3333   CURLcode result=CURLE_OK;
3334
3335   if(conn && conn->handler->doing) {
3336     *done = FALSE;
3337     result = conn->handler->doing(conn, done);
3338   }
3339   else
3340     *done = TRUE;
3341
3342   return result;
3343 }
3344
3345 /*
3346  * We have discovered that the TCP connection has been successful, we can now
3347  * proceed with some action.
3348  *
3349  */
3350 CURLcode Curl_protocol_connect(struct connectdata *conn,
3351                                bool *protocol_done)
3352 {
3353   CURLcode result=CURLE_OK;
3354
3355   *protocol_done = FALSE;
3356
3357   if(conn->bits.tcpconnect[FIRSTSOCKET] && conn->bits.protoconnstart) {
3358     /* We already are connected, get back. This may happen when the connect
3359        worked fine in the first call, like when we connect to a local server
3360        or proxy. Note that we don't know if the protocol is actually done.
3361
3362        Unless this protocol doesn't have any protocol-connect callback, as
3363        then we know we're done. */
3364     if(!conn->handler->connecting)
3365       *protocol_done = TRUE;
3366
3367     return CURLE_OK;
3368   }
3369
3370   if(!conn->bits.protoconnstart) {
3371
3372     result = Curl_proxy_connect(conn);
3373     if(result)
3374       return result;
3375
3376     if(conn->bits.tunnel_proxy && conn->bits.httpproxy &&
3377        (conn->tunnel_state[FIRSTSOCKET] != TUNNEL_COMPLETE))
3378       /* when using an HTTP tunnel proxy, await complete tunnel establishment
3379          before proceeding further. Return CURLE_OK so we'll be called again */
3380       return CURLE_OK;
3381
3382     if(conn->handler->connect_it) {
3383       /* is there a protocol-specific connect() procedure? */
3384
3385       /* Call the protocol-specific connect function */
3386       result = conn->handler->connect_it(conn, protocol_done);
3387     }
3388     else
3389       *protocol_done = TRUE;
3390
3391     /* it has started, possibly even completed but that knowledge isn't stored
3392        in this bit! */
3393     if(!result)
3394       conn->bits.protoconnstart = TRUE;
3395   }
3396
3397   return result; /* pass back status */
3398 }
3399
3400 /*
3401  * Helpers for IDNA convertions.
3402  */
3403 static bool is_ASCII_name(const char *hostname)
3404 {
3405   const unsigned char *ch = (const unsigned char*)hostname;
3406
3407   while(*ch) {
3408     if(*ch++ & 0x80)
3409       return FALSE;
3410   }
3411   return TRUE;
3412 }
3413
3414 #ifdef USE_LIBIDN
3415 /*
3416  * Check if characters in hostname is allowed in Top Level Domain.
3417  */
3418 static bool tld_check_name(struct SessionHandle *data,
3419                            const char *ace_hostname)
3420 {
3421   size_t err_pos;
3422   char *uc_name = NULL;
3423   int rc;
3424 #ifndef CURL_DISABLE_VERBOSE_STRINGS
3425   const char *tld_errmsg = "<no msg>";
3426 #else
3427   (void)data;
3428 #endif
3429
3430   /* Convert (and downcase) ACE-name back into locale's character set */
3431   rc = idna_to_unicode_lzlz(ace_hostname, &uc_name, 0);
3432   if(rc != IDNA_SUCCESS)
3433     return FALSE;
3434
3435   rc = tld_check_lz(uc_name, &err_pos, NULL);
3436 #ifndef CURL_DISABLE_VERBOSE_STRINGS
3437 #ifdef HAVE_TLD_STRERROR
3438   if(rc != TLD_SUCCESS)
3439     tld_errmsg = tld_strerror((Tld_rc)rc);
3440 #endif
3441   if(rc == TLD_INVALID)
3442     infof(data, "WARNING: %s; pos %u = `%c'/0x%02X\n",
3443           tld_errmsg, err_pos, uc_name[err_pos],
3444           uc_name[err_pos] & 255);
3445   else if(rc != TLD_SUCCESS)
3446     infof(data, "WARNING: TLD check for %s failed; %s\n",
3447           uc_name, tld_errmsg);
3448 #endif /* CURL_DISABLE_VERBOSE_STRINGS */
3449   if(uc_name)
3450      idn_free(uc_name);
3451   if(rc != TLD_SUCCESS)
3452     return FALSE;
3453
3454   return TRUE;
3455 }
3456 #endif
3457
3458 /*
3459  * Perform any necessary IDN conversion of hostname
3460  */
3461 static void fix_hostname(struct SessionHandle *data,
3462                          struct connectdata *conn, struct hostname *host)
3463 {
3464 #ifndef USE_LIBIDN
3465   (void)data;
3466   (void)conn;
3467 #elif defined(CURL_DISABLE_VERBOSE_STRINGS)
3468   (void)conn;
3469 #endif
3470
3471   /* set the name we use to display the host name */
3472   host->dispname = host->name;
3473   if(!is_ASCII_name(host->name)) {
3474 #ifdef USE_LIBIDN
3475   /*************************************************************
3476    * Check name for non-ASCII and convert hostname to ACE form.
3477    *************************************************************/
3478   if(stringprep_check_version(LIBIDN_REQUIRED_VERSION)) {
3479     char *ace_hostname = NULL;
3480     int rc = idna_to_ascii_lz(host->name, &ace_hostname, 0);
3481     infof (data, "Input domain encoded as `%s'\n",
3482            stringprep_locale_charset ());
3483     if(rc != IDNA_SUCCESS)
3484       infof(data, "Failed to convert %s to ACE; %s\n",
3485             host->name, Curl_idn_strerror(conn,rc));
3486     else {
3487       /* tld_check_name() displays a warning if the host name contains
3488          "illegal" characters for this TLD */
3489       (void)tld_check_name(data, ace_hostname);
3490
3491       host->encalloc = ace_hostname;
3492       /* change the name pointer to point to the encoded hostname */
3493       host->name = host->encalloc;
3494     }
3495   }
3496 #elif defined(USE_WIN32_IDN)
3497   /*************************************************************
3498    * Check name for non-ASCII and convert hostname to ACE form.
3499    *************************************************************/
3500     char *ace_hostname = NULL;
3501     int rc = curl_win32_idn_to_ascii(host->name, &ace_hostname);
3502     if(rc == 0)
3503       infof(data, "Failed to convert %s to ACE;\n",
3504             host->name);
3505     else {
3506       host->encalloc = ace_hostname;
3507       /* change the name pointer to point to the encoded hostname */
3508       host->name = host->encalloc;
3509     }
3510 #else
3511     infof(data, "IDN support not present, can't parse Unicode domains\n");
3512 #endif
3513   }
3514 }
3515
3516 static void llist_dtor(void *user, void *element)
3517 {
3518   (void)user;
3519   (void)element;
3520   /* Do nothing */
3521 }
3522
3523 /*
3524  * Allocate and initialize a new connectdata object.
3525  */
3526 static struct connectdata *allocate_conn(struct SessionHandle *data)
3527 {
3528   struct connectdata *conn = calloc(1, sizeof(struct connectdata));
3529   if(!conn)
3530     return NULL;
3531
3532   conn->handler = &Curl_handler_dummy;  /* Be sure we have a handler defined
3533                                            already from start to avoid NULL
3534                                            situations and checks */
3535
3536   /* and we setup a few fields in case we end up actually using this struct */
3537
3538   conn->sock[FIRSTSOCKET] = CURL_SOCKET_BAD;     /* no file descriptor */
3539   conn->sock[SECONDARYSOCKET] = CURL_SOCKET_BAD; /* no file descriptor */
3540   conn->connection_id = -1;    /* no ID */
3541   conn->port = -1; /* unknown at this point */
3542
3543   /* Default protocol-independent behavior doesn't support persistent
3544      connections, so we set this to force-close. Protocols that support
3545      this need to set this to FALSE in their "curl_do" functions. */
3546   conn->bits.close = TRUE;
3547
3548   /* Store creation time to help future close decision making */
3549   conn->created = Curl_tvnow();
3550
3551   conn->data = data; /* Setup the association between this connection
3552                         and the SessionHandle */
3553
3554   conn->proxytype = data->set.proxytype; /* type */
3555
3556 #ifdef CURL_DISABLE_PROXY
3557
3558   conn->bits.proxy = FALSE;
3559   conn->bits.httpproxy = FALSE;
3560   conn->bits.proxy_user_passwd = FALSE;
3561   conn->bits.tunnel_proxy = FALSE;
3562
3563 #else /* CURL_DISABLE_PROXY */
3564
3565   /* note that these two proxy bits are now just on what looks to be
3566      requested, they may be altered down the road */
3567   conn->bits.proxy = (data->set.str[STRING_PROXY] &&
3568                       *data->set.str[STRING_PROXY])?TRUE:FALSE;
3569   conn->bits.httpproxy = (conn->bits.proxy &&
3570                           (conn->proxytype == CURLPROXY_HTTP ||
3571                            conn->proxytype == CURLPROXY_HTTP_1_0))?TRUE:FALSE;
3572   conn->bits.proxy_user_passwd =
3573     (NULL != data->set.str[STRING_PROXYUSERNAME])?TRUE:FALSE;
3574   conn->bits.tunnel_proxy = data->set.tunnel_thru_httpproxy;
3575
3576 #endif /* CURL_DISABLE_PROXY */
3577
3578   conn->bits.user_passwd = (NULL != data->set.str[STRING_USERNAME])?TRUE:FALSE;
3579   conn->bits.ftp_use_epsv = data->set.ftp_use_epsv;
3580   conn->bits.ftp_use_eprt = data->set.ftp_use_eprt;
3581
3582   conn->verifypeer = data->set.ssl.verifypeer;
3583   conn->verifyhost = data->set.ssl.verifyhost;
3584
3585   conn->ip_version = data->set.ipver;
3586
3587 #if defined(USE_NTLM) && defined(NTLM_WB_ENABLED)
3588   conn->ntlm_auth_hlpr_socket = CURL_SOCKET_BAD;
3589   conn->ntlm_auth_hlpr_pid = 0;
3590   conn->challenge_header = NULL;
3591   conn->response_header = NULL;
3592 #endif
3593
3594   if(Curl_multi_pipeline_enabled(data->multi) &&
3595       !conn->master_buffer) {
3596     /* Allocate master_buffer to be used for pipelining */
3597     conn->master_buffer = calloc(BUFSIZE, sizeof (char));
3598     if(!conn->master_buffer)
3599       goto error;
3600   }
3601
3602   /* Initialize the pipeline lists */
3603   conn->send_pipe = Curl_llist_alloc((curl_llist_dtor) llist_dtor);
3604   conn->recv_pipe = Curl_llist_alloc((curl_llist_dtor) llist_dtor);
3605   if(!conn->send_pipe || !conn->recv_pipe)
3606     goto error;
3607
3608 #if defined(HAVE_KRB4) || defined(HAVE_GSSAPI)
3609   conn->data_prot = PROT_CLEAR;
3610 #endif
3611
3612   /* Store the local bind parameters that will be used for this connection */
3613   if(data->set.str[STRING_DEVICE]) {
3614     conn->localdev = strdup(data->set.str[STRING_DEVICE]);
3615     if(!conn->localdev)
3616       goto error;
3617   }
3618   conn->localportrange = data->set.localportrange;
3619   conn->localport = data->set.localport;
3620
3621   /* the close socket stuff needs to be copied to the connection struct as
3622      it may live on without (this specific) SessionHandle */
3623   conn->fclosesocket = data->set.fclosesocket;
3624   conn->closesocket_client = data->set.closesocket_client;
3625
3626   return conn;
3627   error:
3628
3629   Curl_llist_destroy(conn->send_pipe, NULL);
3630   Curl_llist_destroy(conn->recv_pipe, NULL);
3631
3632   conn->send_pipe = NULL;
3633   conn->recv_pipe = NULL;
3634
3635   Curl_safefree(conn->master_buffer);
3636   Curl_safefree(conn->localdev);
3637   Curl_safefree(conn);
3638   return NULL;
3639 }
3640
3641 static CURLcode findprotocol(struct SessionHandle *data,
3642                              struct connectdata *conn,
3643                              const char *protostr)
3644 {
3645   const struct Curl_handler * const *pp;
3646   const struct Curl_handler *p;
3647
3648   /* Scan protocol handler table and match against 'protostr' to set a few
3649      variables based on the URL. Now that the handler may be changed later
3650      when the protocol specific setup function is called. */
3651   for(pp = protocols; (p = *pp) != NULL; pp++) {
3652     if(Curl_raw_equal(p->scheme, protostr)) {
3653       /* Protocol found in table. Check if allowed */
3654       if(!(data->set.allowed_protocols & p->protocol))
3655         /* nope, get out */
3656         break;
3657
3658       /* it is allowed for "normal" request, now do an extra check if this is
3659          the result of a redirect */
3660       if(data->state.this_is_a_follow &&
3661          !(data->set.redir_protocols & p->protocol))
3662         /* nope, get out */
3663         break;
3664
3665       /* Perform setup complement if some. */
3666       conn->handler = conn->given = p;
3667
3668       /* 'port' and 'remote_port' are set in setup_connection_internals() */
3669       return CURLE_OK;
3670     }
3671   }
3672
3673
3674   /* The protocol was not found in the table, but we don't have to assign it
3675      to anything since it is already assigned to a dummy-struct in the
3676      create_conn() function when the connectdata struct is allocated. */
3677   failf(data, "Protocol %s not supported or disabled in " LIBCURL_NAME,
3678         protostr);
3679
3680   return CURLE_UNSUPPORTED_PROTOCOL;
3681 }
3682
3683 /*
3684  * Parse URL and fill in the relevant members of the connection struct.
3685  */
3686 static CURLcode parseurlandfillconn(struct SessionHandle *data,
3687                                     struct connectdata *conn,
3688                                     bool *prot_missing,
3689                                     char *user, char *passwd, char *options)
3690 {
3691   char *at;
3692   char *fragment;
3693   char *path = data->state.path;
3694   char *query;
3695   int rc;
3696   char protobuf[16];
3697   const char *protop;
3698   CURLcode result;
3699   bool rebuild_url = FALSE;
3700
3701   *prot_missing = FALSE;
3702
3703   /*************************************************************
3704    * Parse the URL.
3705    *
3706    * We need to parse the url even when using the proxy, because we will need
3707    * the hostname and port in case we are trying to SSL connect through the
3708    * proxy -- and we don't know if we will need to use SSL until we parse the
3709    * url ...
3710    ************************************************************/
3711   if((2 == sscanf(data->change.url, "%15[^:]:%[^\n]",
3712                   protobuf, path)) &&
3713      Curl_raw_equal(protobuf, "file")) {
3714     if(path[0] == '/' && path[1] == '/') {
3715       /* Allow omitted hostname (e.g. file:/<path>).  This is not strictly
3716        * speaking a valid file: URL by RFC 1738, but treating file:/<path> as
3717        * file://localhost/<path> is similar to how other schemes treat missing
3718        * hostnames.  See RFC 1808. */
3719
3720       /* This cannot be done with strcpy() in a portable manner, since the
3721          memory areas overlap! */
3722       memmove(path, path + 2, strlen(path + 2)+1);
3723     }
3724     /*
3725      * we deal with file://<host>/<path> differently since it supports no
3726      * hostname other than "localhost" and "127.0.0.1", which is unique among
3727      * the URL protocols specified in RFC 1738
3728      */
3729     if(path[0] != '/') {
3730       /* the URL included a host name, we ignore host names in file:// URLs
3731          as the standards don't define what to do with them */
3732       char *ptr=strchr(path, '/');
3733       if(ptr) {
3734         /* there was a slash present
3735
3736            RFC1738 (section 3.1, page 5) says:
3737
3738            The rest of the locator consists of data specific to the scheme,
3739            and is known as the "url-path". It supplies the details of how the
3740            specified resource can be accessed. Note that the "/" between the
3741            host (or port) and the url-path is NOT part of the url-path.
3742
3743            As most agents use file://localhost/foo to get '/foo' although the
3744            slash preceding foo is a separator and not a slash for the path,
3745            a URL as file://localhost//foo must be valid as well, to refer to
3746            the same file with an absolute path.
3747         */
3748
3749         if(ptr[1] && ('/' == ptr[1]))
3750           /* if there was two slashes, we skip the first one as that is then
3751              used truly as a separator */
3752           ptr++;
3753
3754         /* This cannot be made with strcpy, as the memory chunks overlap! */
3755         memmove(path, ptr, strlen(ptr)+1);
3756       }
3757     }
3758
3759     protop = "file"; /* protocol string */
3760   }
3761   else {
3762     /* clear path */
3763     path[0]=0;
3764
3765     if(2 > sscanf(data->change.url,
3766                    "%15[^\n:]://%[^\n/?]%[^\n]",
3767                    protobuf,
3768                    conn->host.name, path)) {
3769
3770       /*
3771        * The URL was badly formatted, let's try the browser-style _without_
3772        * protocol specified like 'http://'.
3773        */
3774       rc = sscanf(data->change.url, "%[^\n/?]%[^\n]", conn->host.name, path);
3775       if(1 > rc) {
3776         /*
3777          * We couldn't even get this format.
3778          * djgpp 2.04 has a sscanf() bug where 'conn->host.name' is
3779          * assigned, but the return value is EOF!
3780          */
3781 #if defined(__DJGPP__) && (DJGPP_MINOR == 4)
3782         if(!(rc == -1 && *conn->host.name))
3783 #endif
3784         {
3785           failf(data, "<url> malformed");
3786           return CURLE_URL_MALFORMAT;
3787         }
3788       }
3789
3790       /*
3791        * Since there was no protocol part specified, we guess what protocol it
3792        * is based on the first letters of the server name.
3793        */
3794
3795       /* Note: if you add a new protocol, please update the list in
3796        * lib/version.c too! */
3797
3798       if(checkprefix("FTP.", conn->host.name))
3799         protop = "ftp";
3800       else if(checkprefix("DICT.", conn->host.name))
3801         protop = "DICT";
3802       else if(checkprefix("LDAP.", conn->host.name))
3803         protop = "LDAP";
3804       else if(checkprefix("IMAP.", conn->host.name))
3805         protop = "IMAP";
3806       else if(checkprefix("SMTP.", conn->host.name))
3807         protop = "smtp";
3808       else if(checkprefix("POP3.", conn->host.name))
3809         protop = "pop3";
3810       else {
3811         protop = "http";
3812       }
3813
3814       *prot_missing = TRUE; /* not given in URL */
3815     }
3816     else
3817       protop = protobuf;
3818   }
3819
3820   /* We search for '?' in the host name (but only on the right side of a
3821    * @-letter to allow ?-letters in username and password) to handle things
3822    * like http://example.com?param= (notice the missing '/').
3823    */
3824   at = strchr(conn->host.name, '@');
3825   if(at)
3826     query = strchr(at+1, '?');
3827   else
3828     query = strchr(conn->host.name, '?');
3829
3830   if(query) {
3831     /* We must insert a slash before the '?'-letter in the URL. If the URL had
3832        a slash after the '?', that is where the path currently begins and the
3833        '?string' is still part of the host name.
3834
3835        We must move the trailing part from the host name and put it first in
3836        the path. And have it all prefixed with a slash.
3837     */
3838
3839     size_t hostlen = strlen(query);
3840     size_t pathlen = strlen(path);
3841
3842     /* move the existing path plus the zero byte forward, to make room for
3843        the host-name part */
3844     memmove(path+hostlen+1, path, pathlen+1);
3845
3846      /* now copy the trailing host part in front of the existing path */
3847     memcpy(path+1, query, hostlen);
3848
3849     path[0]='/'; /* prepend the missing slash */
3850     rebuild_url = TRUE;
3851
3852     *query=0; /* now cut off the hostname at the ? */
3853   }
3854   else if(!path[0]) {
3855     /* if there's no path set, use a single slash */
3856     strcpy(path, "/");
3857     rebuild_url = TRUE;
3858   }
3859
3860   /* If the URL is malformatted (missing a '/' after hostname before path) we
3861    * insert a slash here. The only letter except '/' we accept to start a path
3862    * is '?'.
3863    */
3864   if(path[0] == '?') {
3865     /* We need this function to deal with overlapping memory areas. We know
3866        that the memory area 'path' points to is 'urllen' bytes big and that
3867        is bigger than the path. Use +1 to move the zero byte too. */
3868     memmove(&path[1], path, strlen(path)+1);
3869     path[0] = '/';
3870     rebuild_url = TRUE;
3871   }
3872   else {
3873     /* sanitise paths and remove ../ and ./ sequences according to RFC3986 */
3874     char *newp = Curl_dedotdotify(path);
3875     if(!newp)
3876       return CURLE_OUT_OF_MEMORY;
3877
3878     if(strcmp(newp, path)) {
3879       rebuild_url = TRUE;
3880       free(data->state.pathbuffer);
3881       data->state.pathbuffer = newp;
3882       data->state.path = newp;
3883       path = newp;
3884     }
3885     else
3886       free(newp);
3887   }
3888
3889   /*
3890    * "rebuild_url" means that one or more URL components have been modified so
3891    * we need to generate an updated full version.  We need the corrected URL
3892    * when communicating over HTTP proxy and we don't know at this point if
3893    * we're using a proxy or not.
3894    */
3895   if(rebuild_url) {
3896     char *reurl;
3897
3898     size_t plen = strlen(path); /* new path, should be 1 byte longer than
3899                                    the original */
3900     size_t urllen = strlen(data->change.url); /* original URL length */
3901
3902     size_t prefixlen = strlen(conn->host.name);
3903
3904     if(!*prot_missing)
3905       prefixlen += strlen(protop) + strlen("://");
3906
3907     reurl = malloc(urllen + 2); /* 2 for zerobyte + slash */
3908     if(!reurl)
3909       return CURLE_OUT_OF_MEMORY;
3910
3911     /* copy the prefix */
3912     memcpy(reurl, data->change.url, prefixlen);
3913
3914     /* append the trailing piece + zerobyte */
3915     memcpy(&reurl[prefixlen], path, plen + 1);
3916
3917     /* possible free the old one */
3918     if(data->change.url_alloc) {
3919       Curl_safefree(data->change.url);
3920       data->change.url_alloc = FALSE;
3921     }
3922
3923     infof(data, "Rebuilt URL to: %s\n", reurl);
3924
3925     data->change.url = reurl;
3926     data->change.url_alloc = TRUE; /* free this later */
3927   }
3928
3929   /*
3930    * Parse the login details from the URL and strip them out of
3931    * the host name
3932    */
3933   result = parse_url_login(data, conn, user, passwd, options);
3934   if(result != CURLE_OK)
3935     return result;
3936
3937   if(conn->host.name[0] == '[') {
3938     /* This looks like an IPv6 address literal.  See if there is an address
3939        scope.  */
3940     char *percent = strstr (conn->host.name, "%25");
3941     if(percent) {
3942       char *endp;
3943       unsigned long scope = strtoul (percent + 3, &endp, 10);
3944       if(*endp == ']') {
3945         /* The address scope was well formed.  Knock it out of the
3946            hostname. */
3947         memmove(percent, endp, strlen(endp)+1);
3948         if(!data->state.this_is_a_follow)
3949           /* Don't honour a scope given in a Location: header */
3950           conn->scope = (unsigned int)scope;
3951       }
3952       else
3953         infof(data, "Invalid IPv6 address format\n");
3954     }
3955   }
3956
3957   if(data->set.scope)
3958     /* Override any scope that was set above.  */
3959     conn->scope = data->set.scope;
3960
3961   /* Remove the fragment part of the path. Per RFC 2396, this is always the
3962      last part of the URI. We are looking for the first '#' so that we deal
3963      gracefully with non conformant URI such as http://example.com#foo#bar. */
3964   fragment = strchr(path, '#');
3965   if(fragment) {
3966     *fragment = 0;
3967
3968     /* we know the path part ended with a fragment, so we know the full URL
3969        string does too and we need to cut it off from there so it isn't used
3970        over proxy */
3971     fragment = strchr(data->change.url, '#');
3972     if(fragment)
3973       *fragment = 0;
3974   }
3975
3976   /*
3977    * So if the URL was A://B/C#D,
3978    *   protop is A
3979    *   conn->host.name is B
3980    *   data->state.path is /C
3981    */
3982
3983   return findprotocol(data, conn, protop);
3984 }
3985
3986 /*
3987  * If we're doing a resumed transfer, we need to setup our stuff
3988  * properly.
3989  */
3990 static CURLcode setup_range(struct SessionHandle *data)
3991 {
3992   struct UrlState *s = &data->state;
3993   s->resume_from = data->set.set_resume_from;
3994   if(s->resume_from || data->set.str[STRING_SET_RANGE]) {
3995     if(s->rangestringalloc)
3996       free(s->range);
3997
3998     if(s->resume_from)
3999       s->range = aprintf("%" FORMAT_OFF_TU "-", s->resume_from);
4000     else
4001       s->range = strdup(data->set.str[STRING_SET_RANGE]);
4002
4003     s->rangestringalloc = (s->range)?TRUE:FALSE;
4004
4005     if(!s->range)
4006       return CURLE_OUT_OF_MEMORY;
4007
4008     /* tell ourselves to fetch this range */
4009     s->use_range = TRUE;        /* enable range download */
4010   }
4011   else
4012     s->use_range = FALSE; /* disable range download */
4013
4014   return CURLE_OK;
4015 }
4016
4017
4018 /***************************************************************
4019 * Setup connection internals specific to the requested protocol.
4020 * This MUST get called after proxy magic has been figured out.
4021 ***************************************************************/
4022 static CURLcode setup_connection_internals(struct connectdata *conn)
4023 {
4024   const struct Curl_handler * p;
4025   CURLcode result;
4026
4027   conn->socktype = SOCK_STREAM; /* most of them are TCP streams */
4028
4029   /* Scan protocol handler table. */
4030
4031   /* Perform setup complement if some. */
4032   p = conn->handler;
4033
4034   if(p->setup_connection) {
4035     result = (*p->setup_connection)(conn);
4036
4037     if(result != CURLE_OK)
4038       return result;
4039
4040     p = conn->handler;              /* May have changed. */
4041   }
4042
4043   if(conn->port < 0)
4044     /* we check for -1 here since if proxy was detected already, this
4045        was very likely already set to the proxy port */
4046     conn->port = p->defport;
4047   conn->remote_port = (unsigned short)conn->given->defport;
4048
4049   return CURLE_OK;
4050 }
4051
4052 #ifndef CURL_DISABLE_PROXY
4053 /****************************************************************
4054 * Checks if the host is in the noproxy list. returns true if it matches
4055 * and therefore the proxy should NOT be used.
4056 ****************************************************************/
4057 static bool check_noproxy(const char* name, const char* no_proxy)
4058 {
4059   /* no_proxy=domain1.dom,host.domain2.dom
4060    *   (a comma-separated list of hosts which should
4061    *   not be proxied, or an asterisk to override
4062    *   all proxy variables)
4063    */
4064   size_t tok_start;
4065   size_t tok_end;
4066   const char* separator = ", ";
4067   size_t no_proxy_len;
4068   size_t namelen;
4069   char *endptr;
4070
4071   if(no_proxy && no_proxy[0]) {
4072     if(Curl_raw_equal("*", no_proxy)) {
4073       return TRUE;
4074     }
4075
4076     /* NO_PROXY was specified and it wasn't just an asterisk */
4077
4078     no_proxy_len = strlen(no_proxy);
4079     endptr = strchr(name, ':');
4080     if(endptr)
4081       namelen = endptr - name;
4082     else
4083       namelen = strlen(name);
4084
4085     for(tok_start = 0; tok_start < no_proxy_len; tok_start = tok_end + 1) {
4086       while(tok_start < no_proxy_len &&
4087             strchr(separator, no_proxy[tok_start]) != NULL) {
4088         /* Look for the beginning of the token. */
4089         ++tok_start;
4090       }
4091
4092       if(tok_start == no_proxy_len)
4093         break; /* It was all trailing separator chars, no more tokens. */
4094
4095       for(tok_end = tok_start; tok_end < no_proxy_len &&
4096             strchr(separator, no_proxy[tok_end]) == NULL; ++tok_end)
4097         /* Look for the end of the token. */
4098         ;
4099
4100       /* To match previous behaviour, where it was necessary to specify
4101        * ".local.com" to prevent matching "notlocal.com", we will leave
4102        * the '.' off.
4103        */
4104       if(no_proxy[tok_start] == '.')
4105         ++tok_start;
4106
4107       if((tok_end - tok_start) <= namelen) {
4108         /* Match the last part of the name to the domain we are checking. */
4109         const char *checkn = name + namelen - (tok_end - tok_start);
4110         if(Curl_raw_nequal(no_proxy + tok_start, checkn,
4111                            tok_end - tok_start)) {
4112           if((tok_end - tok_start) == namelen || *(checkn - 1) == '.') {
4113             /* We either have an exact match, or the previous character is a .
4114              * so it is within the same domain, so no proxy for this host.
4115              */
4116             return TRUE;
4117           }
4118         }
4119       } /* if((tok_end - tok_start) <= namelen) */
4120     } /* for(tok_start = 0; tok_start < no_proxy_len;
4121          tok_start = tok_end + 1) */
4122   } /* NO_PROXY was specified and it wasn't just an asterisk */
4123
4124   return FALSE;
4125 }
4126
4127 /****************************************************************
4128 * Detect what (if any) proxy to use. Remember that this selects a host
4129 * name and is not limited to HTTP proxies only.
4130 * The returned pointer must be freed by the caller (unless NULL)
4131 ****************************************************************/
4132 static char *detect_proxy(struct connectdata *conn)
4133 {
4134   char *proxy = NULL;
4135
4136 #ifndef CURL_DISABLE_HTTP
4137   /* If proxy was not specified, we check for default proxy environment
4138    * variables, to enable i.e Lynx compliance:
4139    *
4140    * http_proxy=http://some.server.dom:port/
4141    * https_proxy=http://some.server.dom:port/
4142    * ftp_proxy=http://some.server.dom:port/
4143    * no_proxy=domain1.dom,host.domain2.dom
4144    *   (a comma-separated list of hosts which should
4145    *   not be proxied, or an asterisk to override
4146    *   all proxy variables)
4147    * all_proxy=http://some.server.dom:port/
4148    *   (seems to exist for the CERN www lib. Probably
4149    *   the first to check for.)
4150    *
4151    * For compatibility, the all-uppercase versions of these variables are
4152    * checked if the lowercase versions don't exist.
4153    */
4154   char *no_proxy=NULL;
4155   char proxy_env[128];
4156
4157   no_proxy=curl_getenv("no_proxy");
4158   if(!no_proxy)
4159     no_proxy=curl_getenv("NO_PROXY");
4160
4161   if(!check_noproxy(conn->host.name, no_proxy)) {
4162     /* It was not listed as without proxy */
4163     const char *protop = conn->handler->scheme;
4164     char *envp = proxy_env;
4165     char *prox;
4166
4167     /* Now, build <protocol>_proxy and check for such a one to use */
4168     while(*protop)
4169       *envp++ = (char)tolower((int)*protop++);
4170
4171     /* append _proxy */
4172     strcpy(envp, "_proxy");
4173
4174     /* read the protocol proxy: */
4175     prox=curl_getenv(proxy_env);
4176
4177     /*
4178      * We don't try the uppercase version of HTTP_PROXY because of
4179      * security reasons:
4180      *
4181      * When curl is used in a webserver application
4182      * environment (cgi or php), this environment variable can
4183      * be controlled by the web server user by setting the
4184      * http header 'Proxy:' to some value.
4185      *
4186      * This can cause 'internal' http/ftp requests to be
4187      * arbitrarily redirected by any external attacker.
4188      */
4189     if(!prox && !Curl_raw_equal("http_proxy", proxy_env)) {
4190       /* There was no lowercase variable, try the uppercase version: */
4191       Curl_strntoupper(proxy_env, proxy_env, sizeof(proxy_env));
4192       prox=curl_getenv(proxy_env);
4193     }
4194
4195     if(prox && *prox) { /* don't count "" strings */
4196       proxy = prox; /* use this */
4197     }
4198     else {
4199       proxy = curl_getenv("all_proxy"); /* default proxy to use */
4200       if(!proxy)
4201         proxy=curl_getenv("ALL_PROXY");
4202     }
4203   } /* if(!check_noproxy(conn->host.name, no_proxy)) - it wasn't specified
4204        non-proxy */
4205   if(no_proxy)
4206     free(no_proxy);
4207
4208 #else /* !CURL_DISABLE_HTTP */
4209
4210   (void)conn;
4211 #endif /* CURL_DISABLE_HTTP */
4212
4213   return proxy;
4214 }
4215
4216 /*
4217  * If this is supposed to use a proxy, we need to figure out the proxy
4218  * host name, so that we can re-use an existing connection
4219  * that may exist registered to the same proxy host.
4220  * proxy will be freed before this function returns.
4221  */
4222 static CURLcode parse_proxy(struct SessionHandle *data,
4223                             struct connectdata *conn, char *proxy)
4224 {
4225   char *prox_portno;
4226   char *endofprot;
4227
4228   /* We use 'proxyptr' to point to the proxy name from now on... */
4229   char *proxyptr;
4230   char *portptr;
4231   char *atsign;
4232
4233   /* We do the proxy host string parsing here. We want the host name and the
4234    * port name. Accept a protocol:// prefix
4235    */
4236
4237   /* Parse the protocol part if present */
4238   endofprot = strstr(proxy, "://");
4239   if(endofprot) {
4240     proxyptr = endofprot+3;
4241     if(checkprefix("socks5h", proxy))
4242       conn->proxytype = CURLPROXY_SOCKS5_HOSTNAME;
4243     else if(checkprefix("socks5", proxy))
4244       conn->proxytype = CURLPROXY_SOCKS5;
4245     else if(checkprefix("socks4a", proxy))
4246       conn->proxytype = CURLPROXY_SOCKS4A;
4247     else if(checkprefix("socks4", proxy) || checkprefix("socks", proxy))
4248       conn->proxytype = CURLPROXY_SOCKS4;
4249     /* Any other xxx:// : change to http proxy */
4250   }
4251   else
4252     proxyptr = proxy; /* No xxx:// head: It's a HTTP proxy */
4253
4254   /* Is there a username and password given in this proxy url? */
4255   atsign = strchr(proxyptr, '@');
4256   if(atsign) {
4257     CURLcode res = CURLE_OK;
4258     char *proxyuser = NULL;
4259     char *proxypasswd = NULL;
4260
4261     res = parse_login_details(proxyptr, atsign - proxyptr,
4262                               &proxyuser, &proxypasswd, NULL);
4263     if(!res) {
4264       /* found user and password, rip them out.  note that we are
4265          unescaping them, as there is otherwise no way to have a
4266          username or password with reserved characters like ':' in
4267          them. */
4268       Curl_safefree(conn->proxyuser);
4269       if(proxyuser && strlen(proxyuser) < MAX_CURL_USER_LENGTH)
4270         conn->proxyuser = curl_easy_unescape(data, proxyuser, 0, NULL);
4271       else
4272         conn->proxyuser = strdup("");
4273
4274       if(!conn->proxyuser)
4275         res = CURLE_OUT_OF_MEMORY;
4276       else {
4277         Curl_safefree(conn->proxypasswd);
4278         if(proxypasswd && strlen(proxypasswd) < MAX_CURL_PASSWORD_LENGTH)
4279           conn->proxypasswd = curl_easy_unescape(data, proxypasswd, 0, NULL);
4280         else
4281           conn->proxypasswd = strdup("");
4282
4283         if(!conn->proxypasswd)
4284           res = CURLE_OUT_OF_MEMORY;
4285       }
4286
4287       if(!res) {
4288         conn->bits.proxy_user_passwd = TRUE; /* enable it */
4289         atsign++; /* the right side of the @-letter */
4290
4291         if(atsign)
4292           proxyptr = atsign; /* now use this instead */
4293         else
4294           res = CURLE_OUT_OF_MEMORY;
4295       }
4296     }
4297
4298     Curl_safefree(proxyuser);
4299     Curl_safefree(proxypasswd);
4300
4301     if(res)
4302       return res;
4303   }
4304
4305   /* start scanning for port number at this point */
4306   portptr = proxyptr;
4307
4308   /* detect and extract RFC2732-style IPv6-addresses */
4309   if(*proxyptr == '[') {
4310     char *ptr = ++proxyptr; /* advance beyond the initial bracket */
4311     while(*ptr && (ISXDIGIT(*ptr) || (*ptr == ':') || (*ptr == '%') ||
4312                    (*ptr == '.')))
4313       ptr++;
4314     if(*ptr == ']')
4315       /* yeps, it ended nicely with a bracket as well */
4316       *ptr++ = 0;
4317     else
4318       infof(data, "Invalid IPv6 address format\n");
4319     portptr = ptr;
4320     /* Note that if this didn't end with a bracket, we still advanced the
4321      * proxyptr first, but I can't see anything wrong with that as no host
4322      * name nor a numeric can legally start with a bracket.
4323      */
4324   }
4325
4326   /* Get port number off proxy.server.com:1080 */
4327   prox_portno = strchr(portptr, ':');
4328   if(prox_portno) {
4329     *prox_portno = 0x0; /* cut off number from host name */
4330     prox_portno ++;
4331     /* now set the local port number */
4332     conn->port = strtol(prox_portno, NULL, 10);
4333   }
4334   else {
4335     if(proxyptr[0]=='/')
4336       /* If the first character in the proxy string is a slash, fail
4337          immediately. The following code will otherwise clear the string which
4338          will lead to code running as if no proxy was set! */
4339       return CURLE_COULDNT_RESOLVE_PROXY;
4340
4341     /* without a port number after the host name, some people seem to use
4342        a slash so we strip everything from the first slash */
4343     atsign = strchr(proxyptr, '/');
4344     if(atsign)
4345       *atsign = 0x0; /* cut off path part from host name */
4346
4347     if(data->set.proxyport)
4348       /* None given in the proxy string, then get the default one if it is
4349          given */
4350       conn->port = data->set.proxyport;
4351   }
4352
4353   /* now, clone the cleaned proxy host name */
4354   conn->proxy.rawalloc = strdup(proxyptr);
4355   conn->proxy.name = conn->proxy.rawalloc;
4356
4357   if(!conn->proxy.rawalloc)
4358     return CURLE_OUT_OF_MEMORY;
4359
4360   return CURLE_OK;
4361 }
4362
4363 /*
4364  * Extract the user and password from the authentication string
4365  */
4366 static CURLcode parse_proxy_auth(struct SessionHandle *data,
4367                                  struct connectdata *conn)
4368 {
4369   char proxyuser[MAX_CURL_USER_LENGTH]="";
4370   char proxypasswd[MAX_CURL_PASSWORD_LENGTH]="";
4371
4372   if(data->set.str[STRING_PROXYUSERNAME] != NULL) {
4373     strncpy(proxyuser, data->set.str[STRING_PROXYUSERNAME],
4374             MAX_CURL_USER_LENGTH);
4375     proxyuser[MAX_CURL_USER_LENGTH-1] = '\0';   /*To be on safe side*/
4376   }
4377   if(data->set.str[STRING_PROXYPASSWORD] != NULL) {
4378     strncpy(proxypasswd, data->set.str[STRING_PROXYPASSWORD],
4379             MAX_CURL_PASSWORD_LENGTH);
4380     proxypasswd[MAX_CURL_PASSWORD_LENGTH-1] = '\0'; /*To be on safe side*/
4381   }
4382
4383   conn->proxyuser = curl_easy_unescape(data, proxyuser, 0, NULL);
4384   if(!conn->proxyuser)
4385     return CURLE_OUT_OF_MEMORY;
4386
4387   conn->proxypasswd = curl_easy_unescape(data, proxypasswd, 0, NULL);
4388   if(!conn->proxypasswd)
4389     return CURLE_OUT_OF_MEMORY;
4390
4391   return CURLE_OK;
4392 }
4393 #endif /* CURL_DISABLE_PROXY */
4394
4395 /*
4396  * parse_url_login()
4397  *
4398  * Parse the login details (user name, password and options) from the URL and
4399  * strip them out of the host name
4400  *
4401  * Inputs: data->set.use_netrc (CURLOPT_NETRC)
4402  *         conn->host.name
4403  *
4404  * Outputs: (almost :- all currently undefined)
4405  *          conn->bits.user_passwd  - non-zero if non-default passwords exist
4406  *          user                    - non-zero length if defined
4407  *          passwd                  - non-zero length if defined
4408  *          options                 - non-zero length if defined
4409  *          conn->host.name         - remove user name and password
4410  */
4411 static CURLcode parse_url_login(struct SessionHandle *data,
4412                                 struct connectdata *conn,
4413                                 char *user, char *passwd, char *options)
4414 {
4415   CURLcode result = CURLE_OK;
4416   char *userp = NULL;
4417   char *passwdp = NULL;
4418   char *optionsp = NULL;
4419
4420   /* At this point, we're hoping all the other special cases have
4421    * been taken care of, so conn->host.name is at most
4422    *    [user[:password][;options]]@]hostname
4423    *
4424    * We need somewhere to put the embedded details, so do that first.
4425    */
4426
4427   char *ptr = strchr(conn->host.name, '@');
4428   char *login = conn->host.name;
4429
4430   user[0] = 0;   /* to make everything well-defined */
4431   passwd[0] = 0;
4432   options[0] = 0;
4433
4434   /* We will now try to extract the
4435    * possible login information in a string like:
4436    * ftp://user:password@ftp.my.site:8021/README */
4437   if(ptr) {
4438     /* There's login information to the left of the @ */
4439
4440     conn->host.name = ++ptr;
4441
4442     /* So the hostname is sane.  Only bother interpreting the
4443      * results if we could care.  It could still be wasted
4444      * work because it might be overtaken by the programmatically
4445      * set user/passwd, but doing that first adds more cases here :-(
4446      */
4447
4448     if(data->set.use_netrc != CURL_NETRC_REQUIRED) {
4449       /* We could use the login information in the URL so extract it */
4450       result = parse_login_details(login, ptr - login - 1,
4451                                    &userp, &passwdp, &optionsp);
4452       if(!result) {
4453         if(userp) {
4454           char *newname;
4455
4456           /* We have a user in the URL */
4457           conn->bits.userpwd_in_url = TRUE;
4458           conn->bits.user_passwd = TRUE; /* enable user+password */
4459
4460           /* Decode the user */
4461           newname = curl_easy_unescape(data, userp, 0, NULL);
4462           if(!newname) {
4463             Curl_safefree(userp);
4464             Curl_safefree(passwdp);
4465             Curl_safefree(optionsp);
4466             return CURLE_OUT_OF_MEMORY;
4467           }
4468
4469           if(strlen(newname) < MAX_CURL_USER_LENGTH)
4470             strcpy(user, newname);
4471
4472           free(newname);
4473         }
4474
4475         if(passwdp) {
4476           /* We have a password in the URL so decode it */
4477           char *newpasswd = curl_easy_unescape(data, passwdp, 0, NULL);
4478           if(!newpasswd) {
4479             Curl_safefree(userp);
4480             Curl_safefree(passwdp);
4481             Curl_safefree(optionsp);
4482             return CURLE_OUT_OF_MEMORY;
4483           }
4484
4485           if(strlen(newpasswd) < MAX_CURL_PASSWORD_LENGTH)
4486             strcpy(passwd, newpasswd);
4487
4488           free(newpasswd);
4489         }
4490
4491         if(optionsp) {
4492           /* We have an options list in the URL so decode it */
4493           char *newoptions = curl_easy_unescape(data, optionsp, 0, NULL);
4494           if(!newoptions) {
4495             Curl_safefree(userp);
4496             Curl_safefree(passwdp);
4497             Curl_safefree(optionsp);
4498             return CURLE_OUT_OF_MEMORY;
4499           }
4500
4501           if(strlen(newoptions) < MAX_CURL_OPTIONS_LENGTH)
4502             strcpy(options, newoptions);
4503
4504           free(newoptions);
4505         }
4506       }
4507
4508       Curl_safefree(userp);
4509       Curl_safefree(passwdp);
4510       Curl_safefree(optionsp);
4511     }
4512   }
4513
4514   return result;
4515 }
4516
4517 /*
4518  * parse_login_details()
4519  *
4520  * This is used to parse a login string for user name, password and options in
4521  * the following formats:
4522  *
4523  *   user
4524  *   user:password
4525  *   user:password;options
4526  *   user;options
4527  *   user;options:password
4528  *   :password
4529  *   :password;options
4530  *   ;options
4531  *   ;options:password
4532  *
4533  * Parameters:
4534  *
4535  * login    [in]     - The login string.
4536  * len      [in]     - The length of the login string.
4537  * userp    [in/out] - The address where a pointer to newly allocated memory
4538  *                     holding the user will be stored upon completion.
4539  * passdwp  [in/out] - The address where a pointer to newly allocated memory
4540  *                     holding the password will be stored upon completion.
4541  * optionsp [in/out] - The address where a pointer to newly allocated memory
4542  *                     holding the options will be stored upon completion.
4543  *
4544  * Returns CURLE_OK on success.
4545  */
4546 static CURLcode parse_login_details(const char *login, const size_t len,
4547                                     char **userp, char **passwdp,
4548                                     char **optionsp)
4549 {
4550   CURLcode result = CURLE_OK;
4551   char *ubuf = NULL;
4552   char *pbuf = NULL;
4553   char *obuf = NULL;
4554   const char *psep = NULL;
4555   const char *osep = NULL;
4556   size_t ulen;
4557   size_t plen;
4558   size_t olen;
4559
4560   /* Attempt to find the password separator */
4561   if(passwdp) {
4562     psep = strchr(login, ':');
4563
4564     /* Within the constraint of the login string */
4565     if(psep >= login + len)
4566       psep = NULL;
4567   }
4568
4569   /* Attempt to find the options separator */
4570   if(optionsp) {
4571     osep = strchr(login, ';');
4572
4573     /* Within the constraint of the login string */
4574     if(osep >= login + len)
4575       osep = NULL;
4576   }
4577
4578   /* Calculate the portion lengths */
4579   ulen = (psep ?
4580           (size_t)(osep && psep > osep ? osep - login : psep - login) :
4581           (osep ? (size_t)(osep - login) : len));
4582   plen = (psep ?
4583           (osep && osep > psep ? (size_t)(osep - psep) :
4584                                  (size_t)(login + len - psep)) - 1 : 0);
4585   olen = (osep ?
4586           (psep && psep > osep ? (size_t)(psep - osep) :
4587                                  (size_t)(login + len - osep)) - 1 : 0);
4588
4589   /* Allocate the user portion buffer */
4590   if(userp && ulen) {
4591     ubuf = malloc(ulen + 1);
4592     if(!ubuf)
4593       result = CURLE_OUT_OF_MEMORY;
4594   }
4595
4596   /* Allocate the password portion buffer */
4597   if(!result && passwdp && plen) {
4598     pbuf = malloc(plen + 1);
4599     if(!pbuf) {
4600       Curl_safefree(ubuf);
4601       result = CURLE_OUT_OF_MEMORY;
4602     }
4603   }
4604
4605   /* Allocate the options portion buffer */
4606   if(!result && optionsp && olen) {
4607     obuf = malloc(olen + 1);
4608     if(!obuf) {
4609       Curl_safefree(pbuf);
4610       Curl_safefree(ubuf);
4611       result = CURLE_OUT_OF_MEMORY;
4612     }
4613   }
4614
4615   if(!result) {
4616     /* Store the user portion if necessary */
4617     if(ubuf) {
4618       memcpy(ubuf, login, ulen);
4619       ubuf[ulen] = '\0';
4620       Curl_safefree(*userp);
4621       *userp = ubuf;
4622     }
4623
4624     /* Store the password portion if necessary */
4625     if(pbuf) {
4626       memcpy(pbuf, psep + 1, plen);
4627       pbuf[plen] = '\0';
4628       Curl_safefree(*passwdp);
4629       *passwdp = pbuf;
4630     }
4631
4632     /* Store the options portion if necessary */
4633     if(obuf) {
4634       memcpy(obuf, osep + 1, olen);
4635       obuf[olen] = '\0';
4636       Curl_safefree(*optionsp);
4637       *optionsp = obuf;
4638     }
4639   }
4640
4641   return result;
4642 }
4643
4644 /*************************************************************
4645  * Figure out the remote port number and fix it in the URL
4646  *
4647  * No matter if we use a proxy or not, we have to figure out the remote
4648  * port number of various reasons.
4649  *
4650  * To be able to detect port number flawlessly, we must not confuse them
4651  * IPv6-specified addresses in the [0::1] style. (RFC2732)
4652  *
4653  * The conn->host.name is currently [user:passwd@]host[:port] where host
4654  * could be a hostname, IPv4 address or IPv6 address.
4655  *
4656  * The port number embedded in the URL is replaced, if necessary.
4657  *************************************************************/
4658 static CURLcode parse_remote_port(struct SessionHandle *data,
4659                                   struct connectdata *conn)
4660 {
4661   char *portptr;
4662   char endbracket;
4663
4664   /* Note that at this point, the IPv6 address cannot contain any scope
4665      suffix as that has already been removed in the parseurlandfillconn()
4666      function */
4667   if((1 == sscanf(conn->host.name, "[%*45[0123456789abcdefABCDEF:.]%c",
4668                   &endbracket)) &&
4669      (']' == endbracket)) {
4670     /* this is a RFC2732-style specified IP-address */
4671     conn->bits.ipv6_ip = TRUE;
4672
4673     conn->host.name++; /* skip over the starting bracket */
4674     portptr = strchr(conn->host.name, ']');
4675     if(portptr) {
4676       *portptr++ = '\0'; /* zero terminate, killing the bracket */
4677       if(':' != *portptr)
4678         portptr = NULL; /* no port number available */
4679     }
4680   }
4681   else {
4682 #ifdef ENABLE_IPV6
4683     struct in6_addr in6;
4684     if(Curl_inet_pton(AF_INET6, conn->host.name, &in6) > 0) {
4685       /* This is a numerical IPv6 address, meaning this is a wrongly formatted
4686          URL */
4687       failf(data, "IPv6 numerical address used in URL without brackets");
4688       return CURLE_URL_MALFORMAT;
4689     }
4690 #endif
4691
4692     portptr = strrchr(conn->host.name, ':');
4693   }
4694
4695   if(data->set.use_port && data->state.allow_port) {
4696     /* if set, we use this and ignore the port possibly given in the URL */
4697     conn->remote_port = (unsigned short)data->set.use_port;
4698     if(portptr)
4699       *portptr = '\0'; /* cut off the name there anyway - if there was a port
4700                       number - since the port number is to be ignored! */
4701     if(conn->bits.httpproxy) {
4702       /* we need to create new URL with the new port number */
4703       char *url;
4704       char type[12]="";
4705
4706       if(conn->bits.type_set)
4707         snprintf(type, sizeof(type), ";type=%c",
4708                  data->set.prefer_ascii?'A':
4709                  (data->set.ftp_list_only?'D':'I'));
4710
4711       /*
4712        * This synthesized URL isn't always right--suffixes like ;type=A are
4713        * stripped off. It would be better to work directly from the original
4714        * URL and simply replace the port part of it.
4715        */
4716       url = aprintf("%s://%s%s%s:%hu%s%s%s", conn->given->scheme,
4717                     conn->bits.ipv6_ip?"[":"", conn->host.name,
4718                     conn->bits.ipv6_ip?"]":"", conn->remote_port,
4719                     data->state.slash_removed?"/":"", data->state.path,
4720                     type);
4721       if(!url)
4722         return CURLE_OUT_OF_MEMORY;
4723
4724       if(data->change.url_alloc) {
4725         Curl_safefree(data->change.url);
4726         data->change.url_alloc = FALSE;
4727       }
4728
4729       data->change.url = url;
4730       data->change.url_alloc = TRUE;
4731     }
4732   }
4733   else if(portptr) {
4734     /* no CURLOPT_PORT given, extract the one from the URL */
4735
4736     char *rest;
4737     unsigned long port;
4738
4739     port=strtoul(portptr+1, &rest, 10);  /* Port number must be decimal */
4740
4741     if(rest != (portptr+1) && *rest == '\0') {
4742       /* The colon really did have only digits after it,
4743        * so it is either a port number or a mistake */
4744
4745       if(port > 0xffff) {   /* Single unix standard says port numbers are
4746                               * 16 bits long */
4747         failf(data, "Port number too large: %lu", port);
4748         return CURLE_URL_MALFORMAT;
4749       }
4750
4751       *portptr = '\0'; /* cut off the name there */
4752       conn->remote_port = curlx_ultous(port);
4753     }
4754     else if(!port)
4755       /* Browser behavior adaptation. If there's a colon with no digits after,
4756          just cut off the name there which makes us ignore the colon and just
4757          use the default port. Firefox and Chrome both do that. */
4758       *portptr = '\0';
4759   }
4760   return CURLE_OK;
4761 }
4762
4763 /*
4764  * Override the login details from the URL with that in the CURLOPT_USERPWD
4765  * option or a .netrc file, if applicable.
4766  */
4767 static void override_login(struct SessionHandle *data,
4768                            struct connectdata *conn,
4769                            char *user, char *passwd, char *options)
4770 {
4771   if(data->set.str[STRING_USERNAME]) {
4772     strncpy(user, data->set.str[STRING_USERNAME], MAX_CURL_USER_LENGTH);
4773     user[MAX_CURL_USER_LENGTH - 1] = '\0';   /* To be on safe side */
4774   }
4775
4776   if(data->set.str[STRING_PASSWORD]) {
4777     strncpy(passwd, data->set.str[STRING_PASSWORD], MAX_CURL_PASSWORD_LENGTH);
4778     passwd[MAX_CURL_PASSWORD_LENGTH - 1] = '\0'; /* To be on safe side */
4779   }
4780
4781   if(data->set.str[STRING_OPTIONS]) {
4782     strncpy(options, data->set.str[STRING_OPTIONS], MAX_CURL_OPTIONS_LENGTH);
4783     options[MAX_CURL_OPTIONS_LENGTH - 1] = '\0'; /* To be on safe side */
4784   }
4785
4786   conn->bits.netrc = FALSE;
4787   if(data->set.use_netrc != CURL_NETRC_IGNORED) {
4788     if(Curl_parsenetrc(conn->host.name,
4789                        user, passwd,
4790                        data->set.str[STRING_NETRC_FILE])) {
4791       infof(data, "Couldn't find host %s in the "
4792             DOT_CHAR "netrc file; using defaults\n",
4793             conn->host.name);
4794     }
4795     else {
4796       /* set bits.netrc TRUE to remember that we got the name from a .netrc
4797          file, so that it is safe to use even if we followed a Location: to a
4798          different host or similar. */
4799       conn->bits.netrc = TRUE;
4800
4801       conn->bits.user_passwd = TRUE; /* enable user+password */
4802     }
4803   }
4804 }
4805
4806 /*
4807  * Set password so it's available in the connection.
4808  */
4809 static CURLcode set_login(struct connectdata *conn,
4810                           const char *user, const char *passwd,
4811                           const char *options)
4812 {
4813   CURLcode result = CURLE_OK;
4814
4815   /* If our protocol needs a password and we have none, use the defaults */
4816   if((conn->handler->flags & PROTOPT_NEEDSPWD) && !conn->bits.user_passwd) {
4817     /* Store the default user */
4818     conn->user = strdup(CURL_DEFAULT_USER);
4819
4820     /* Store the default password */
4821     if(conn->user)
4822       conn->passwd = strdup(CURL_DEFAULT_PASSWORD);
4823     else
4824       conn->passwd = NULL;
4825
4826     /* This is the default password, so DON'T set conn->bits.user_passwd */
4827   }
4828   else {
4829     /* Store the user, zero-length if not set */
4830     conn->user = strdup(user);
4831
4832     /* Store the password (only if user is present), zero-length if not set */
4833     if(conn->user)
4834       conn->passwd = strdup(passwd);
4835     else
4836       conn->passwd = NULL;
4837   }
4838
4839   if(!conn->user || !conn->passwd)
4840     result = CURLE_OUT_OF_MEMORY;
4841
4842   /* Store the options, null if not set */
4843   if(!result && options[0]) {
4844     conn->options = strdup(options);
4845
4846     if(!conn->options)
4847       result = CURLE_OUT_OF_MEMORY;
4848   }
4849
4850   return result;
4851 }
4852
4853 /*************************************************************
4854  * Resolve the address of the server or proxy
4855  *************************************************************/
4856 static CURLcode resolve_server(struct SessionHandle *data,
4857                                struct connectdata *conn,
4858                                bool *async)
4859 {
4860   CURLcode result=CURLE_OK;
4861   long timeout_ms = Curl_timeleft(data, NULL, TRUE);
4862
4863   /*************************************************************
4864    * Resolve the name of the server or proxy
4865    *************************************************************/
4866   if(conn->bits.reuse)
4867     /* We're reusing the connection - no need to resolve anything, and
4868        fix_hostname() was called already in create_conn() for the re-use
4869        case. */
4870     *async = FALSE;
4871
4872   else {
4873     /* this is a fresh connect */
4874     int rc;
4875     struct Curl_dns_entry *hostaddr;
4876
4877     /* set a pointer to the hostname we display */
4878     fix_hostname(data, conn, &conn->host);
4879
4880     if(!conn->proxy.name || !*conn->proxy.name) {
4881       /* If not connecting via a proxy, extract the port from the URL, if it is
4882        * there, thus overriding any defaults that might have been set above. */
4883       conn->port =  conn->remote_port; /* it is the same port */
4884
4885       /* Resolve target host right on */
4886       rc = Curl_resolv_timeout(conn, conn->host.name, (int)conn->port,
4887                                &hostaddr, timeout_ms);
4888       if(rc == CURLRESOLV_PENDING)
4889         *async = TRUE;
4890
4891       else if(rc == CURLRESOLV_TIMEDOUT)
4892         result = CURLE_OPERATION_TIMEDOUT;
4893
4894       else if(!hostaddr) {
4895         failf(data, "Couldn't resolve host '%s'", conn->host.dispname);
4896         result =  CURLE_COULDNT_RESOLVE_HOST;
4897         /* don't return yet, we need to clean up the timeout first */
4898       }
4899     }
4900     else {
4901       /* This is a proxy that hasn't been resolved yet. */
4902
4903       /* IDN-fix the proxy name */
4904       fix_hostname(data, conn, &conn->proxy);
4905
4906       /* resolve proxy */
4907       rc = Curl_resolv_timeout(conn, conn->proxy.name, (int)conn->port,
4908                                &hostaddr, timeout_ms);
4909
4910       if(rc == CURLRESOLV_PENDING)
4911         *async = TRUE;
4912
4913       else if(rc == CURLRESOLV_TIMEDOUT)
4914         result = CURLE_OPERATION_TIMEDOUT;
4915
4916       else if(!hostaddr) {
4917         failf(data, "Couldn't resolve proxy '%s'", conn->proxy.dispname);
4918         result = CURLE_COULDNT_RESOLVE_PROXY;
4919         /* don't return yet, we need to clean up the timeout first */
4920       }
4921     }
4922     DEBUGASSERT(conn->dns_entry == NULL);
4923     conn->dns_entry = hostaddr;
4924   }
4925
4926   return result;
4927 }
4928
4929 /*
4930  * Cleanup the connection just allocated before we can move along and use the
4931  * previously existing one.  All relevant data is copied over and old_conn is
4932  * ready for freeing once this function returns.
4933  */
4934 static void reuse_conn(struct connectdata *old_conn,
4935                        struct connectdata *conn)
4936 {
4937   if(old_conn->proxy.rawalloc)
4938     free(old_conn->proxy.rawalloc);
4939
4940   /* free the SSL config struct from this connection struct as this was
4941      allocated in vain and is targeted for destruction */
4942   Curl_free_ssl_config(&old_conn->ssl_config);
4943
4944   conn->data = old_conn->data;
4945
4946   /* get the user+password information from the old_conn struct since it may
4947    * be new for this request even when we re-use an existing connection */
4948   conn->bits.user_passwd = old_conn->bits.user_passwd;
4949   if(conn->bits.user_passwd) {
4950     /* use the new user name and password though */
4951     Curl_safefree(conn->user);
4952     Curl_safefree(conn->passwd);
4953     conn->user = old_conn->user;
4954     conn->passwd = old_conn->passwd;
4955     old_conn->user = NULL;
4956     old_conn->passwd = NULL;
4957   }
4958
4959   conn->bits.proxy_user_passwd = old_conn->bits.proxy_user_passwd;
4960   if(conn->bits.proxy_user_passwd) {
4961     /* use the new proxy user name and proxy password though */
4962     Curl_safefree(conn->proxyuser);
4963     Curl_safefree(conn->proxypasswd);
4964     conn->proxyuser = old_conn->proxyuser;
4965     conn->proxypasswd = old_conn->proxypasswd;
4966     old_conn->proxyuser = NULL;
4967     old_conn->proxypasswd = NULL;
4968   }
4969
4970   /* host can change, when doing keepalive with a proxy or if the case is
4971      different this time etc */
4972   Curl_safefree(conn->host.rawalloc);
4973   conn->host=old_conn->host;
4974
4975   /* persist connection info in session handle */
4976   Curl_persistconninfo(conn);
4977
4978   /* re-use init */
4979   conn->bits.reuse = TRUE; /* yes, we're re-using here */
4980
4981   Curl_safefree(old_conn->user);
4982   Curl_safefree(old_conn->passwd);
4983   Curl_safefree(old_conn->proxyuser);
4984   Curl_safefree(old_conn->proxypasswd);
4985   Curl_safefree(old_conn->localdev);
4986
4987   Curl_llist_destroy(old_conn->send_pipe, NULL);
4988   Curl_llist_destroy(old_conn->recv_pipe, NULL);
4989
4990   old_conn->send_pipe = NULL;
4991   old_conn->recv_pipe = NULL;
4992
4993   Curl_safefree(old_conn->master_buffer);
4994 }
4995
4996 /**
4997  * create_conn() sets up a new connectdata struct, or re-uses an already
4998  * existing one, and resolves host name.
4999  *
5000  * if this function returns CURLE_OK and *async is set to TRUE, the resolve
5001  * response will be coming asynchronously. If *async is FALSE, the name is
5002  * already resolved.
5003  *
5004  * @param data The sessionhandle pointer
5005  * @param in_connect is set to the next connection data pointer
5006  * @param async is set TRUE when an async DNS resolution is pending
5007  * @see Curl_setup_conn()
5008  *
5009  * *NOTE* this function assigns the conn->data pointer!
5010  */
5011
5012 static CURLcode create_conn(struct SessionHandle *data,
5013                             struct connectdata **in_connect,
5014                             bool *async)
5015 {
5016   CURLcode result = CURLE_OK;
5017   struct connectdata *conn;
5018   struct connectdata *conn_temp = NULL;
5019   size_t urllen;
5020   char user[MAX_CURL_USER_LENGTH];
5021   char passwd[MAX_CURL_PASSWORD_LENGTH];
5022   char options[MAX_CURL_OPTIONS_LENGTH];
5023   bool reuse;
5024   char *proxy = NULL;
5025   bool prot_missing = FALSE;
5026   bool no_connections_available = FALSE;
5027   bool force_reuse;
5028   size_t max_host_connections = Curl_multi_max_host_connections(data->multi);
5029   size_t max_total_connections = Curl_multi_max_total_connections(data->multi);
5030
5031   *async = FALSE;
5032
5033   /*************************************************************
5034    * Check input data
5035    *************************************************************/
5036
5037   if(!data->change.url)
5038     return CURLE_URL_MALFORMAT;
5039
5040   /* First, split up the current URL in parts so that we can use the
5041      parts for checking against the already present connections. In order
5042      to not have to modify everything at once, we allocate a temporary
5043      connection data struct and fill in for comparison purposes. */
5044   conn = allocate_conn(data);
5045
5046   if(!conn)
5047     return CURLE_OUT_OF_MEMORY;
5048
5049   /* We must set the return variable as soon as possible, so that our
5050      parent can cleanup any possible allocs we may have done before
5051      any failure */
5052   *in_connect = conn;
5053
5054   /* This initing continues below, see the comment "Continue connectdata
5055    * initialization here" */
5056
5057   /***********************************************************
5058    * We need to allocate memory to store the path in. We get the size of the
5059    * full URL to be sure, and we need to make it at least 256 bytes since
5060    * other parts of the code will rely on this fact
5061    ***********************************************************/
5062 #define LEAST_PATH_ALLOC 256
5063   urllen=strlen(data->change.url);
5064   if(urllen < LEAST_PATH_ALLOC)
5065     urllen=LEAST_PATH_ALLOC;
5066
5067   /*
5068    * We malloc() the buffers below urllen+2 to make room for 2 possibilities:
5069    * 1 - an extra terminating zero
5070    * 2 - an extra slash (in case a syntax like "www.host.com?moo" is used)
5071    */
5072
5073   Curl_safefree(data->state.pathbuffer);
5074   data->state.path = NULL;
5075
5076   data->state.pathbuffer = malloc(urllen+2);
5077   if(NULL == data->state.pathbuffer)
5078     return CURLE_OUT_OF_MEMORY; /* really bad error */
5079   data->state.path = data->state.pathbuffer;
5080
5081   conn->host.rawalloc = malloc(urllen+2);
5082   if(NULL == conn->host.rawalloc) {
5083     Curl_safefree(data->state.pathbuffer);
5084     data->state.path = NULL;
5085     return CURLE_OUT_OF_MEMORY;
5086   }
5087
5088   conn->host.name = conn->host.rawalloc;
5089   conn->host.name[0] = 0;
5090
5091   result = parseurlandfillconn(data, conn, &prot_missing, user, passwd,
5092                                options);
5093   if(result != CURLE_OK)
5094     return result;
5095
5096   /*************************************************************
5097    * No protocol part in URL was used, add it!
5098    *************************************************************/
5099   if(prot_missing) {
5100     /* We're guessing prefixes here and if we're told to use a proxy or if
5101        we're gonna follow a Location: later or... then we need the protocol
5102        part added so that we have a valid URL. */
5103     char *reurl;
5104
5105     reurl = aprintf("%s://%s", conn->handler->scheme, data->change.url);
5106
5107     if(!reurl) {
5108       Curl_safefree(proxy);
5109       return CURLE_OUT_OF_MEMORY;
5110     }
5111
5112     if(data->change.url_alloc) {
5113       Curl_safefree(data->change.url);
5114       data->change.url_alloc = FALSE;
5115     }
5116
5117     data->change.url = reurl;
5118     data->change.url_alloc = TRUE; /* free this later */
5119   }
5120
5121   /*************************************************************
5122    * If the protocol can't handle url query strings, then cut
5123    * of the unhandable part
5124    *************************************************************/
5125   if((conn->given->flags&PROTOPT_NOURLQUERY)) {
5126     char *path_q_sep = strchr(conn->data->state.path, '?');
5127     if(path_q_sep) {
5128       /* according to rfc3986, allow the query (?foo=bar)
5129          also on protocols that can't handle it.
5130
5131          cut the string-part after '?'
5132       */
5133
5134       /* terminate the string */
5135       path_q_sep[0] = 0;
5136     }
5137   }
5138
5139 #ifndef CURL_DISABLE_PROXY
5140   /*************************************************************
5141    * Extract the user and password from the authentication string
5142    *************************************************************/
5143   if(conn->bits.proxy_user_passwd) {
5144     result = parse_proxy_auth(data, conn);
5145     if(result != CURLE_OK)
5146       return result;
5147   }
5148
5149   /*************************************************************
5150    * Detect what (if any) proxy to use
5151    *************************************************************/
5152   if(data->set.str[STRING_PROXY]) {
5153     proxy = strdup(data->set.str[STRING_PROXY]);
5154     /* if global proxy is set, this is it */
5155     if(NULL == proxy) {
5156       failf(data, "memory shortage");
5157       return CURLE_OUT_OF_MEMORY;
5158     }
5159   }
5160
5161   if(data->set.str[STRING_NOPROXY] &&
5162      check_noproxy(conn->host.name, data->set.str[STRING_NOPROXY])) {
5163     if(proxy) {
5164       free(proxy);  /* proxy is in exception list */
5165       proxy = NULL;
5166     }
5167   }
5168   else if(!proxy)
5169     proxy = detect_proxy(conn);
5170
5171   if(proxy && (!*proxy || (conn->handler->flags & PROTOPT_NONETWORK))) {
5172     free(proxy);  /* Don't bother with an empty proxy string or if the
5173                      protocol doesn't work with network */
5174     proxy = NULL;
5175   }
5176
5177   /***********************************************************************
5178    * If this is supposed to use a proxy, we need to figure out the proxy host
5179    * name, proxy type and port number, so that we can re-use an existing
5180    * connection that may exist registered to the same proxy host.
5181    ***********************************************************************/
5182   if(proxy) {
5183     result = parse_proxy(data, conn, proxy);
5184
5185     free(proxy); /* parse_proxy copies the proxy string */
5186
5187     if(result)
5188       return result;
5189
5190     if((conn->proxytype == CURLPROXY_HTTP) ||
5191        (conn->proxytype == CURLPROXY_HTTP_1_0)) {
5192 #ifdef CURL_DISABLE_HTTP
5193       /* asking for a HTTP proxy is a bit funny when HTTP is disabled... */
5194       return CURLE_UNSUPPORTED_PROTOCOL;
5195 #else
5196       /* force this connection's protocol to become HTTP if not already
5197          compatible - if it isn't tunneling through */
5198       if(!(conn->handler->protocol & CURLPROTO_HTTP) &&
5199          !conn->bits.tunnel_proxy)
5200         conn->handler = &Curl_handler_http;
5201
5202       conn->bits.httpproxy = TRUE;
5203 #endif
5204     }
5205     else
5206       conn->bits.httpproxy = FALSE; /* not a HTTP proxy */
5207     conn->bits.proxy = TRUE;
5208   }
5209   else {
5210     /* we aren't using the proxy after all... */
5211     conn->bits.proxy = FALSE;
5212     conn->bits.httpproxy = FALSE;
5213     conn->bits.proxy_user_passwd = FALSE;
5214     conn->bits.tunnel_proxy = FALSE;
5215   }
5216
5217 #endif /* CURL_DISABLE_PROXY */
5218
5219   /*************************************************************
5220    * Setup internals depending on protocol. Needs to be done after
5221    * we figured out what/if proxy to use.
5222    *************************************************************/
5223   result = setup_connection_internals(conn);
5224   if(result != CURLE_OK) {
5225     Curl_safefree(proxy);
5226     return result;
5227   }
5228
5229   conn->recv[FIRSTSOCKET] = Curl_recv_plain;
5230   conn->send[FIRSTSOCKET] = Curl_send_plain;
5231   conn->recv[SECONDARYSOCKET] = Curl_recv_plain;
5232   conn->send[SECONDARYSOCKET] = Curl_send_plain;
5233
5234   /***********************************************************************
5235    * file: is a special case in that it doesn't need a network connection
5236    ***********************************************************************/
5237 #ifndef CURL_DISABLE_FILE
5238   if(conn->handler->flags & PROTOPT_NONETWORK) {
5239     bool done;
5240     /* this is supposed to be the connect function so we better at least check
5241        that the file is present here! */
5242     DEBUGASSERT(conn->handler->connect_it);
5243     result = conn->handler->connect_it(conn, &done);
5244
5245     /* Setup a "faked" transfer that'll do nothing */
5246     if(CURLE_OK == result) {
5247       conn->data = data;
5248       conn->bits.tcpconnect[FIRSTSOCKET] = TRUE; /* we are "connected */
5249
5250       ConnectionStore(data, conn);
5251
5252       /*
5253        * Setup whatever necessary for a resumed transfer
5254        */
5255       result = setup_range(data);
5256       if(result) {
5257         DEBUGASSERT(conn->handler->done);
5258         /* we ignore the return code for the protocol-specific DONE */
5259         (void)conn->handler->done(conn, result, FALSE);
5260         return result;
5261       }
5262
5263       Curl_setup_transfer(conn, -1, -1, FALSE, NULL, /* no download */
5264                           -1, NULL); /* no upload */
5265     }
5266
5267     /* since we skip do_init() */
5268     Curl_speedinit(data);
5269
5270     return result;
5271   }
5272 #endif
5273
5274   /*************************************************************
5275    * If the protocol is using SSL and HTTP proxy is used, we set
5276    * the tunnel_proxy bit.
5277    *************************************************************/
5278   if((conn->given->flags&PROTOPT_SSL) && conn->bits.httpproxy)
5279     conn->bits.tunnel_proxy = TRUE;
5280
5281   /*************************************************************
5282    * Figure out the remote port number and fix it in the URL
5283    *************************************************************/
5284   result = parse_remote_port(data, conn);
5285   if(result != CURLE_OK)
5286     return result;
5287
5288   /* Check for overridden login details and set them accordingly */
5289   override_login(data, conn, user, passwd, options);
5290   result = set_login(conn, user, passwd, options);
5291   if(result != CURLE_OK)
5292     return result;
5293
5294   /* Get a cloned copy of the SSL config situation stored in the
5295      connection struct. But to get this going nicely, we must first make
5296      sure that the strings in the master copy are pointing to the correct
5297      strings in the session handle strings array!
5298
5299      Keep in mind that the pointers in the master copy are pointing to strings
5300      that will be freed as part of the SessionHandle struct, but all cloned
5301      copies will be separately allocated.
5302   */
5303   data->set.ssl.CApath = data->set.str[STRING_SSL_CAPATH];
5304   data->set.ssl.CAfile = data->set.str[STRING_SSL_CAFILE];
5305   data->set.ssl.CRLfile = data->set.str[STRING_SSL_CRLFILE];
5306   data->set.ssl.issuercert = data->set.str[STRING_SSL_ISSUERCERT];
5307   data->set.ssl.random_file = data->set.str[STRING_SSL_RANDOM_FILE];
5308   data->set.ssl.egdsocket = data->set.str[STRING_SSL_EGDSOCKET];
5309   data->set.ssl.cipher_list = data->set.str[STRING_SSL_CIPHER_LIST];
5310 #ifdef USE_TLS_SRP
5311   data->set.ssl.username = data->set.str[STRING_TLSAUTH_USERNAME];
5312   data->set.ssl.password = data->set.str[STRING_TLSAUTH_PASSWORD];
5313 #endif
5314
5315   if(!Curl_clone_ssl_config(&data->set.ssl, &conn->ssl_config))
5316     return CURLE_OUT_OF_MEMORY;
5317
5318   /*************************************************************
5319    * Check the current list of connections to see if we can
5320    * re-use an already existing one or if we have to create a
5321    * new one.
5322    *************************************************************/
5323
5324   /* reuse_fresh is TRUE if we are told to use a new connection by force, but
5325      we only acknowledge this option if this is not a re-used connection
5326      already (which happens due to follow-location or during a HTTP
5327      authentication phase). */
5328   if(data->set.reuse_fresh && !data->state.this_is_a_follow)
5329     reuse = FALSE;
5330   else
5331     reuse = ConnectionExists(data, conn, &conn_temp, &force_reuse);
5332
5333   /* If we found a reusable connection, we may still want to
5334      open a new connection if we are pipelining. */
5335   if(reuse && !force_reuse && IsPipeliningPossible(data, conn_temp)) {
5336     size_t pipelen = conn_temp->send_pipe->size + conn_temp->recv_pipe->size;
5337     if(pipelen > 0) {
5338       infof(data, "Found connection %d, with requests in the pipe (%d)\n",
5339             conn_temp->connection_id, pipelen);
5340
5341       if(conn_temp->bundle->num_connections < max_host_connections &&
5342          data->state.conn_cache->num_connections < max_total_connections) {
5343         /* We want a new connection anyway */
5344         reuse = FALSE;
5345
5346         infof(data, "We can reuse, but we want a new connection anyway\n");
5347       }
5348     }
5349   }
5350
5351   if(reuse) {
5352     /*
5353      * We already have a connection for this, we got the former connection
5354      * in the conn_temp variable and thus we need to cleanup the one we
5355      * just allocated before we can move along and use the previously
5356      * existing one.
5357      */
5358     conn_temp->inuse = TRUE; /* mark this as being in use so that no other
5359                                 handle in a multi stack may nick it */
5360     reuse_conn(conn, conn_temp);
5361     free(conn);          /* we don't need this anymore */
5362     conn = conn_temp;
5363     *in_connect = conn;
5364
5365     /* set a pointer to the hostname we display */
5366     fix_hostname(data, conn, &conn->host);
5367
5368     infof(data, "Re-using existing connection! (#%ld) with host %s\n",
5369           conn->connection_id,
5370           conn->proxy.name?conn->proxy.dispname:conn->host.dispname);
5371   }
5372   else {
5373     /* We have decided that we want a new connection. However, we may not
5374        be able to do that if we have reached the limit of how many
5375        connections we are allowed to open. */
5376     struct connectbundle *bundle;
5377
5378     bundle = Curl_conncache_find_bundle(data->state.conn_cache,
5379                                         conn->host.name);
5380     if(max_host_connections > 0 && bundle &&
5381        (bundle->num_connections >= max_host_connections)) {
5382       struct connectdata *conn_candidate;
5383
5384       /* The bundle is full. Let's see if we can kill a connection. */
5385       conn_candidate = find_oldest_idle_connection_in_bundle(data, bundle);
5386
5387       if(conn_candidate) {
5388         /* Set the connection's owner correctly, then kill it */
5389         conn_candidate->data = data;
5390         (void)Curl_disconnect(conn_candidate, /* dead_connection */ FALSE);
5391       }
5392       else
5393         no_connections_available = TRUE;
5394     }
5395
5396     if(max_total_connections > 0 &&
5397        (data->state.conn_cache->num_connections >= max_total_connections)) {
5398       struct connectdata *conn_candidate;
5399
5400       /* The cache is full. Let's see if we can kill a connection. */
5401       conn_candidate = find_oldest_idle_connection(data);
5402
5403       if(conn_candidate) {
5404         /* Set the connection's owner correctly, then kill it */
5405         conn_candidate->data = data;
5406         (void)Curl_disconnect(conn_candidate, /* dead_connection */ FALSE);
5407       }
5408       else
5409         no_connections_available = TRUE;
5410     }
5411
5412
5413     if(no_connections_available) {
5414       infof(data, "No connections available.\n");
5415
5416       conn_free(conn);
5417       *in_connect = NULL;
5418
5419       return CURLE_NO_CONNECTION_AVAILABLE;
5420     }
5421     else {
5422       /*
5423        * This is a brand new connection, so let's store it in the connection
5424        * cache of ours!
5425        */
5426       ConnectionStore(data, conn);
5427     }
5428   }
5429
5430   /* Mark the connection as used */
5431   conn->inuse = TRUE;
5432
5433   /* Setup and init stuff before DO starts, in preparing for the transfer. */
5434   do_init(conn);
5435
5436   /*
5437    * Setup whatever necessary for a resumed transfer
5438    */
5439   result = setup_range(data);
5440   if(result)
5441     return result;
5442
5443   /* Continue connectdata initialization here. */
5444
5445   /*
5446    * Inherit the proper values from the urldata struct AFTER we have arranged
5447    * the persistent connection stuff
5448    */
5449   conn->fread_func = data->set.fread_func;
5450   conn->fread_in = data->set.in;
5451   conn->seek_func = data->set.seek_func;
5452   conn->seek_client = data->set.seek_client;
5453
5454   /*************************************************************
5455    * Resolve the address of the server or proxy
5456    *************************************************************/
5457   result = resolve_server(data, conn, async);
5458
5459   return result;
5460 }
5461
5462 /* Curl_setup_conn() is called after the name resolve initiated in
5463  * create_conn() is all done.
5464  *
5465  * Curl_setup_conn() also handles reused connections
5466  *
5467  * conn->data MUST already have been setup fine (in create_conn)
5468  */
5469
5470 CURLcode Curl_setup_conn(struct connectdata *conn,
5471                          bool *protocol_done)
5472 {
5473   CURLcode result = CURLE_OK;
5474   struct SessionHandle *data = conn->data;
5475
5476   Curl_pgrsTime(data, TIMER_NAMELOOKUP);
5477
5478   if(conn->handler->flags & PROTOPT_NONETWORK) {
5479     /* nothing to setup when not using a network */
5480     *protocol_done = TRUE;
5481     return result;
5482   }
5483   *protocol_done = FALSE; /* default to not done */
5484
5485   /* set proxy_connect_closed to false unconditionally already here since it
5486      is used strictly to provide extra information to a parent function in the
5487      case of proxy CONNECT failures and we must make sure we don't have it
5488      lingering set from a previous invoke */
5489   conn->bits.proxy_connect_closed = FALSE;
5490
5491   /*
5492    * Set user-agent. Used for HTTP, but since we can attempt to tunnel
5493    * basically anything through a http proxy we can't limit this based on
5494    * protocol.
5495    */
5496   if(data->set.str[STRING_USERAGENT]) {
5497     Curl_safefree(conn->allocptr.uagent);
5498     conn->allocptr.uagent =
5499       aprintf("User-Agent: %s\r\n", data->set.str[STRING_USERAGENT]);
5500     if(!conn->allocptr.uagent)
5501       return CURLE_OUT_OF_MEMORY;
5502   }
5503
5504   data->req.headerbytecount = 0;
5505
5506 #ifdef CURL_DO_LINEEND_CONV
5507   data->state.crlf_conversions = 0; /* reset CRLF conversion counter */
5508 #endif /* CURL_DO_LINEEND_CONV */
5509
5510   /* set start time here for timeout purposes in the connect procedure, it
5511      is later set again for the progress meter purpose */
5512   conn->now = Curl_tvnow();
5513
5514   for(;;) {
5515     /* loop for CURL_SERVER_CLOSED_CONNECTION */
5516
5517     if(CURL_SOCKET_BAD == conn->sock[FIRSTSOCKET]) {
5518       /* Try to connect only if not already connected */
5519       bool connected = FALSE;
5520
5521       result = ConnectPlease(data, conn, &connected);
5522
5523       if(result && !conn->ip_addr) {
5524         /* transport connection failure not related with authentication */
5525         conn->bits.tcpconnect[FIRSTSOCKET] = FALSE;
5526         return result;
5527       }
5528
5529       if(connected) {
5530         result = Curl_protocol_connect(conn, protocol_done);
5531         if(CURLE_OK == result)
5532           conn->bits.tcpconnect[FIRSTSOCKET] = TRUE;
5533       }
5534       else
5535         conn->bits.tcpconnect[FIRSTSOCKET] = FALSE;
5536
5537       /* if the connection was closed by the server while exchanging
5538          authentication informations, retry with the new set
5539          authentication information */
5540       if(conn->bits.proxy_connect_closed) {
5541         /* reset the error buffer */
5542         if(data->set.errorbuffer)
5543           data->set.errorbuffer[0] = '\0';
5544         data->state.errorbuf = FALSE;
5545         continue;
5546       }
5547
5548       if(CURLE_OK != result)
5549         return result;
5550     }
5551     else {
5552       Curl_pgrsTime(data, TIMER_CONNECT); /* we're connected already */
5553       Curl_pgrsTime(data, TIMER_APPCONNECT); /* we're connected already */
5554       conn->bits.tcpconnect[FIRSTSOCKET] = TRUE;
5555       *protocol_done = TRUE;
5556       Curl_verboseconnect(conn);
5557       Curl_updateconninfo(conn, conn->sock[FIRSTSOCKET]);
5558     }
5559     /* Stop the loop now */
5560     break;
5561   }
5562
5563   conn->now = Curl_tvnow(); /* time this *after* the connect is done, we
5564                                set this here perhaps a second time */
5565
5566 #ifdef __EMX__
5567   /*
5568    * This check is quite a hack. We're calling _fsetmode to fix the problem
5569    * with fwrite converting newline characters (you get mangled text files,
5570    * and corrupted binary files when you download to stdout and redirect it to
5571    * a file).
5572    */
5573
5574   if((data->set.out)->_handle == NULL) {
5575     _fsetmode(stdout, "b");
5576   }
5577 #endif
5578
5579   return result;
5580 }
5581
5582 CURLcode Curl_connect(struct SessionHandle *data,
5583                       struct connectdata **in_connect,
5584                       bool *asyncp,
5585                       bool *protocol_done)
5586 {
5587   CURLcode code;
5588
5589   *asyncp = FALSE; /* assume synchronous resolves by default */
5590
5591   /* call the stuff that needs to be called */
5592   code = create_conn(data, in_connect, asyncp);
5593
5594   if(CURLE_OK == code) {
5595     /* no error */
5596     if((*in_connect)->send_pipe->size || (*in_connect)->recv_pipe->size)
5597       /* pipelining */
5598       *protocol_done = TRUE;
5599     else if(!*asyncp) {
5600       /* DNS resolution is done: that's either because this is a reused
5601          connection, in which case DNS was unnecessary, or because DNS
5602          really did finish already (synch resolver/fast async resolve) */
5603       code = Curl_setup_conn(*in_connect, protocol_done);
5604     }
5605   }
5606
5607   if(code == CURLE_NO_CONNECTION_AVAILABLE) {
5608     *in_connect = NULL;
5609     return code;
5610   }
5611
5612   if(code && *in_connect) {
5613     /* We're not allowed to return failure with memory left allocated
5614        in the connectdata struct, free those here */
5615     Curl_disconnect(*in_connect, FALSE); /* close the connection */
5616     *in_connect = NULL;           /* return a NULL */
5617   }
5618
5619   return code;
5620 }
5621
5622 CURLcode Curl_done(struct connectdata **connp,
5623                    CURLcode status,  /* an error if this is called after an
5624                                         error was detected */
5625                    bool premature)
5626 {
5627   CURLcode result;
5628   struct connectdata *conn;
5629   struct SessionHandle *data;
5630
5631   DEBUGASSERT(*connp);
5632
5633   conn = *connp;
5634   data = conn->data;
5635
5636   if(conn->bits.done)
5637     /* Stop if Curl_done() has already been called */
5638     return CURLE_OK;
5639
5640   Curl_getoff_all_pipelines(data, conn);
5641
5642   if((conn->send_pipe->size + conn->recv_pipe->size != 0 &&
5643       !data->set.reuse_forbid &&
5644       !conn->bits.close))
5645     /* Stop if pipeline is not empty and we do not have to close
5646        connection. */
5647     return CURLE_OK;
5648
5649   conn->bits.done = TRUE; /* called just now! */
5650
5651   /* Cleanup possible redirect junk */
5652   if(data->req.newurl) {
5653     free(data->req.newurl);
5654     data->req.newurl = NULL;
5655   }
5656   if(data->req.location) {
5657     free(data->req.location);
5658     data->req.location = NULL;
5659   }
5660
5661   Curl_resolver_cancel(conn);
5662
5663   if(conn->dns_entry) {
5664     Curl_resolv_unlock(data, conn->dns_entry); /* done with this */
5665     conn->dns_entry = NULL;
5666   }
5667
5668   if(status == CURLE_ABORTED_BY_CALLBACK)
5669     /* When we're aborted due to a callback return code it basically have to
5670        be counted as premature as there is trouble ahead if we don't. We have
5671        many callbacks and protocols work differently, we could potentially do
5672        this more fine-grained in the future. */
5673     premature = TRUE;
5674
5675   /* this calls the protocol-specific function pointer previously set */
5676   if(conn->handler->done)
5677     result = conn->handler->done(conn, status, premature);
5678   else
5679     result = CURLE_OK;
5680
5681   if(Curl_pgrsDone(conn) && !result)
5682     result = CURLE_ABORTED_BY_CALLBACK;
5683
5684   /* if the transfer was completed in a paused state there can be buffered
5685      data left to write and then kill */
5686   if(data->state.tempwrite) {
5687     free(data->state.tempwrite);
5688     data->state.tempwrite = NULL;
5689   }
5690
5691   /* if data->set.reuse_forbid is TRUE, it means the libcurl client has
5692      forced us to close this no matter what we think.
5693
5694      if conn->bits.close is TRUE, it means that the connection should be
5695      closed in spite of all our efforts to be nice, due to protocol
5696      restrictions in our or the server's end
5697
5698      if premature is TRUE, it means this connection was said to be DONE before
5699      the entire request operation is complete and thus we can't know in what
5700      state it is for re-using, so we're forced to close it. In a perfect world
5701      we can add code that keep track of if we really must close it here or not,
5702      but currently we have no such detail knowledge.
5703   */
5704   if(data->set.reuse_forbid || conn->bits.close || premature) {
5705     CURLcode res2 = Curl_disconnect(conn, premature); /* close connection */
5706
5707     /* If we had an error already, make sure we return that one. But
5708        if we got a new error, return that. */
5709     if(!result && res2)
5710       result = res2;
5711   }
5712   else {
5713     /* the connection is no longer in use */
5714     if(ConnectionDone(data, conn)) {
5715       /* remember the most recently used connection */
5716       data->state.lastconnect = conn;
5717
5718       infof(data, "Connection #%ld to host %s left intact\n",
5719             conn->connection_id,
5720             conn->bits.httpproxy?conn->proxy.dispname:conn->host.dispname);
5721     }
5722     else
5723       data->state.lastconnect = NULL;
5724   }
5725
5726   *connp = NULL; /* to make the caller of this function better detect that
5727                     this was either closed or handed over to the connection
5728                     cache here, and therefore cannot be used from this point on
5729                  */
5730
5731   return result;
5732 }
5733
5734 /*
5735  * do_init() inits the readwrite session. This is inited each time (in the DO
5736  * function before the protocol-specific DO functions are invoked) for a
5737  * transfer, sometimes multiple times on the same SessionHandle. Make sure
5738  * nothing in here depends on stuff that are setup dynamically for the
5739  * transfer.
5740  */
5741
5742 static CURLcode do_init(struct connectdata *conn)
5743 {
5744   struct SessionHandle *data = conn->data;
5745   struct SingleRequest *k = &data->req;
5746
5747   conn->bits.done = FALSE; /* Curl_done() is not called yet */
5748   conn->bits.do_more = FALSE; /* by default there's no curl_do_more() to use */
5749   data->state.expect100header = FALSE;
5750
5751   if(data->set.opt_no_body)
5752     /* in HTTP lingo, no body means using the HEAD request... */
5753     data->set.httpreq = HTTPREQ_HEAD;
5754   else if(HTTPREQ_HEAD == data->set.httpreq)
5755     /* ... but if unset there really is no perfect method that is the
5756        "opposite" of HEAD but in reality most people probably think GET
5757        then. The important thing is that we can't let it remain HEAD if the
5758        opt_no_body is set FALSE since then we'll behave wrong when getting
5759        HTTP. */
5760     data->set.httpreq = HTTPREQ_GET;
5761
5762   /* NB: the content encoding software depends on this initialization */
5763   Curl_easy_initHandleData(data);
5764
5765   k->start = Curl_tvnow(); /* start time */
5766   k->now = k->start;   /* current time is now */
5767   k->header = TRUE; /* assume header */
5768
5769   k->bytecount = 0;
5770
5771   k->buf = data->state.buffer;
5772   k->uploadbuf = data->state.uploadbuffer;
5773   k->hbufp = data->state.headerbuff;
5774   k->ignorebody=FALSE;
5775
5776   Curl_speedinit(data);
5777
5778   Curl_pgrsSetUploadCounter(data, 0);
5779   Curl_pgrsSetDownloadCounter(data, 0);
5780
5781   return CURLE_OK;
5782 }
5783
5784 /*
5785  * do_complete is called when the DO actions are complete.
5786  *
5787  * We init chunking and trailer bits to their default values here immediately
5788  * before receiving any header data for the current request in the pipeline.
5789  */
5790 static void do_complete(struct connectdata *conn)
5791 {
5792   conn->data->req.chunk=FALSE;
5793   conn->data->req.maxfd = (conn->sockfd>conn->writesockfd?
5794                            conn->sockfd:conn->writesockfd)+1;
5795   Curl_pgrsTime(conn->data, TIMER_PRETRANSFER);
5796 }
5797
5798 CURLcode Curl_do(struct connectdata **connp, bool *done)
5799 {
5800   CURLcode result=CURLE_OK;
5801   struct connectdata *conn = *connp;
5802   struct SessionHandle *data = conn->data;
5803
5804   if(conn->handler->do_it) {
5805     /* generic protocol-specific function pointer set in curl_connect() */
5806     result = conn->handler->do_it(conn, done);
5807
5808     /* This was formerly done in transfer.c, but we better do it here */
5809     if((CURLE_SEND_ERROR == result) && conn->bits.reuse) {
5810       /*
5811        * If the connection is using an easy handle, call reconnect
5812        * to re-establish the connection.  Otherwise, let the multi logic
5813        * figure out how to re-establish the connection.
5814        */
5815       if(!data->multi) {
5816         result = Curl_reconnect_request(connp);
5817
5818         if(result == CURLE_OK) {
5819           /* ... finally back to actually retry the DO phase */
5820           conn = *connp; /* re-assign conn since Curl_reconnect_request
5821                             creates a new connection */
5822           result = conn->handler->do_it(conn, done);
5823         }
5824       }
5825       else
5826         return result;
5827     }
5828
5829     if((result == CURLE_OK) && *done)
5830       /* do_complete must be called after the protocol-specific DO function */
5831       do_complete(conn);
5832   }
5833   return result;
5834 }
5835
5836 /*
5837  * Curl_do_more() is called during the DO_MORE multi state. It is basically a
5838  * second stage DO state which (wrongly) was introduced to support FTP's
5839  * second connection.
5840  *
5841  * TODO: A future libcurl should be able to work away this state.
5842  *
5843  */
5844
5845 CURLcode Curl_do_more(struct connectdata *conn, bool *completed)
5846 {
5847   CURLcode result=CURLE_OK;
5848
5849   *completed = FALSE;
5850
5851   if(conn->handler->do_more)
5852     result = conn->handler->do_more(conn, completed);
5853
5854   if(!result && *completed)
5855     /* do_complete must be called after the protocol-specific DO function */
5856     do_complete(conn);
5857
5858   return result;
5859 }
5860
5861 /* Called on connect, and if there's already a protocol-specific struct
5862    allocated for a different connection, this frees it that it can be setup
5863    properly later on. */
5864 void Curl_reset_reqproto(struct connectdata *conn)
5865 {
5866   struct SessionHandle *data = conn->data;
5867   if(data->state.proto.generic && data->state.current_conn != conn) {
5868     free(data->state.proto.generic);
5869     data->state.proto.generic = NULL;
5870   }
5871   data->state.current_conn = conn;
5872 }