summaryrefslogtreecommitdiffstats
path: root/Utilities/cmcurl/lib/url.c
diff options
context:
space:
mode:
Diffstat (limited to 'Utilities/cmcurl/lib/url.c')
-rw-r--r--Utilities/cmcurl/lib/url.c165
1 files changed, 97 insertions, 68 deletions
diff --git a/Utilities/cmcurl/lib/url.c b/Utilities/cmcurl/lib/url.c
index 0fb6268..61dad44 100644
--- a/Utilities/cmcurl/lib/url.c
+++ b/Utilities/cmcurl/lib/url.c
@@ -414,7 +414,7 @@ CURLcode Curl_close(struct Curl_easy **datap)
Curl_hsts_cleanup(&data->hsts);
curl_slist_free_all(data->set.hstslist); /* clean up list */
#endif
-#if !defined(CURL_DISABLE_HTTP) && !defined(CURL_DISABLE_CRYPTO_AUTH)
+#if !defined(CURL_DISABLE_HTTP) && !defined(CURL_DISABLE_DIGEST_AUTH)
Curl_http_auth_cleanup_digest(data);
#endif
Curl_safefree(data->info.contenttype);
@@ -457,6 +457,11 @@ CURLcode Curl_close(struct Curl_easy **datap)
}
#endif
+ Curl_mime_cleanpart(data->state.formp);
+#ifndef CURL_DISABLE_HTTP
+ Curl_safefree(data->state.formp);
+#endif
+
/* destruct wildcard structures if it is needed */
Curl_wildcard_dtor(&data->wildcard);
Curl_freeset(data);
@@ -490,7 +495,7 @@ CURLcode Curl_init_userdefined(struct Curl_easy *data)
set->filesize = -1; /* we don't know the size */
set->postfieldsize = -1; /* unknown size */
- set->maxredirs = -1; /* allow any amount by default */
+ set->maxredirs = 30; /* sensible default */
set->method = HTTPREQ_GET; /* Default HTTP request */
#ifndef CURL_DISABLE_RTSP
@@ -659,6 +664,9 @@ CURLcode Curl_open(struct Curl_easy **curl)
/* most recent connection is not yet defined */
data->state.lastconnect_id = -1;
+ data->state.recent_conn_id = -1;
+ /* and not assigned an id yet */
+ data->id = -1;
data->progress.flags |= PGRS_HIDE;
data->state.current_speed = -1; /* init to negative == impossible */
@@ -680,7 +688,7 @@ CURLcode Curl_open(struct Curl_easy **curl)
static void conn_shutdown(struct Curl_easy *data)
{
DEBUGASSERT(data);
- infof(data, "Closing connection %ld", data->conn->connection_id);
+ infof(data, "Closing connection");
/* possible left-overs from the async name resolvers */
Curl_resolver_cancel(data);
@@ -763,7 +771,8 @@ void Curl_disconnect(struct Curl_easy *data,
/* the transfer must be detached from the connection */
DEBUGASSERT(!data->conn);
- DEBUGF(infof(data, "Curl_disconnect(conn #%ld, dead=%d)",
+ DEBUGF(infof(data, "Curl_disconnect(conn #%"
+ CURL_FORMAT_CURL_OFF_T ", dead=%d)",
conn->connection_id, dead_connection));
/*
* If this connection isn't marked to force-close, leave it open if there
@@ -879,8 +888,8 @@ static bool conn_maxage(struct Curl_easy *data,
idletime /= 1000; /* integer seconds is fine */
if(idletime > data->set.maxage_conn) {
- infof(data, "Too old connection (%ld seconds idle), disconnect it",
- idletime);
+ infof(data, "Too old connection (%" CURL_FORMAT_TIMEDIFF_T
+ " seconds idle), disconnect it", idletime);
return TRUE;
}
@@ -889,8 +898,8 @@ static bool conn_maxage(struct Curl_easy *data,
if(data->set.maxlifetime_conn && lifetime > data->set.maxlifetime_conn) {
infof(data,
- "Too old connection (%ld seconds since creation), disconnect it",
- lifetime);
+ "Too old connection (%" CURL_FORMAT_TIMEDIFF_T
+ " seconds since creation), disconnect it", lifetime);
return TRUE;
}
@@ -937,22 +946,25 @@ static bool extract_if_dead(struct connectdata *conn,
else {
bool input_pending;
+ Curl_attach_connection(data, conn);
dead = !Curl_conn_is_alive(data, conn, &input_pending);
if(input_pending) {
/* For reuse, we want a "clean" connection state. The includes
* that we expect - in general - no waiting input data. Input
* waiting might be a TLS Notify Close, for example. We reject
* that.
- * For protocols where data from other other end may arrive at
+ * For protocols where data from other end may arrive at
* any time (HTTP/2 PING for example), the protocol handler needs
* to install its own `connection_check` callback.
*/
dead = TRUE;
}
+ Curl_detach_connection(data);
}
if(dead) {
- infof(data, "Connection %ld seems to be dead", conn->connection_id);
+ infof(data, "Connection %" CURL_FORMAT_CURL_OFF_T " seems to be dead",
+ conn->connection_id);
Curl_conncache_remove_conn(data, conn, FALSE);
return TRUE;
}
@@ -1066,6 +1078,9 @@ ConnectionExists(struct Curl_easy *data,
bool wantProxyNTLMhttp = FALSE;
#endif
#endif
+ /* plain HTTP with upgrade */
+ bool h2upgrade = (data->state.httpwant == CURL_HTTP_VERSION_2_0) &&
+ (needle->handler->protocol & CURLPROTO_HTTP);
*force_reuse = FALSE;
*waitpipe = FALSE;
@@ -1088,7 +1103,7 @@ ConnectionExists(struct Curl_easy *data,
infof(data, "Server doesn't support multiplex yet, wait");
*waitpipe = TRUE;
CONNCACHE_UNLOCK(data);
- return FALSE; /* no re-use */
+ return FALSE; /* no reuse */
}
infof(data, "Server doesn't support multiplex (yet)");
@@ -1128,7 +1143,7 @@ ConnectionExists(struct Curl_easy *data,
}
if(data->set.ipver != CURL_IPRESOLVE_WHATEVER
- && data->set.ipver != check->ip_version) {
+ && data->set.ipver != check->ip_version) {
/* skip because the connection is not via the requested IP version */
continue;
}
@@ -1143,23 +1158,18 @@ ConnectionExists(struct Curl_easy *data,
continue;
}
- if(Curl_resolver_asynch()) {
- /* primary_ip[0] is NUL only if the resolving of the name hasn't
- completed yet and until then we don't re-use this connection */
- if(!check->primary_ip[0]) {
- infof(data,
- "Connection #%ld is still name resolving, can't reuse",
- check->connection_id);
- continue;
- }
- }
+ if(Curl_resolver_asynch() &&
+ /* primary_ip[0] is NUL only if the resolving of the name hasn't
+ completed yet and until then we don't reuse this connection */
+ !check->primary_ip[0])
+ continue;
}
if(!Curl_conn_is_connected(check, FIRSTSOCKET)) {
foundPendingCandidate = TRUE;
/* Don't pick a connection that hasn't connected yet */
- infof(data, "Connection #%ld isn't open enough, can't reuse",
- check->connection_id);
+ infof(data, "Connection #%" CURL_FORMAT_CURL_OFF_T
+ " isn't open enough, can't reuse", check->connection_id);
continue;
}
@@ -1231,6 +1241,17 @@ ConnectionExists(struct Curl_easy *data,
}
#endif
+ if(h2upgrade && !check->httpversion && canmultiplex) {
+ if(data->set.pipewait) {
+ infof(data, "Server upgrade doesn't support multiplex yet, wait");
+ *waitpipe = TRUE;
+ CONNCACHE_UNLOCK(data);
+ return FALSE; /* no reuse */
+ }
+ infof(data, "Server upgrade cannot be used");
+ continue; /* can't be used atm */
+ }
+
if(!canmultiplex && CONN_INUSE(check))
/* this request can't be multiplexed but the checked connection is
already in use so we skip it */
@@ -1247,14 +1268,14 @@ ConnectionExists(struct Curl_easy *data,
if(needle->localdev || needle->localport) {
/* If we are bound to a specific local end (IP+port), we must not
- re-use a random other one, although if we didn't ask for a
+ reuse a random other one, although if we didn't ask for a
particular one we can reuse one that was bound.
This comparison is a bit rough and too strict. Since the input
parameters can be specified in numerous ways and still end up the
same it would take a lot of processing to make it really accurate.
- Instead, this matching will assume that re-uses of bound connections
- will most likely also re-use the exact same binding parameters and
+ Instead, this matching will assume that reuses of bound connections
+ will most likely also reuse the exact same binding parameters and
missing out a few edge cases shouldn't hurt anyone very much.
*/
if((check->localport != needle->localport) ||
@@ -1287,7 +1308,7 @@ ConnectionExists(struct Curl_easy *data,
(((check->httpversion >= 20) &&
(data->state.httpwant < CURL_HTTP_VERSION_2_0))
|| ((check->httpversion >= 30) &&
- (data->state.httpwant < CURL_HTTP_VERSION_3))))
+ (data->state.httpwant < CURL_HTTP_VERSION_3))))
continue;
#ifdef USE_SSH
else if(get_protocol_family(needle->handler) & PROTO_FAMILY_SSH) {
@@ -1335,8 +1356,8 @@ ConnectionExists(struct Curl_easy *data,
if(!Curl_ssl_config_matches(&needle->ssl_config,
&check->ssl_config)) {
DEBUGF(infof(data,
- "Connection #%ld has different SSL parameters, "
- "can't reuse",
+ "Connection #%" CURL_FORMAT_CURL_OFF_T
+ " has different SSL parameters, can't reuse",
check->connection_id));
continue;
}
@@ -1477,14 +1498,8 @@ void Curl_verboseconnect(struct Curl_easy *data,
struct connectdata *conn)
{
if(data->set.verbose)
- infof(data, "Connected to %s (%s) port %u (#%ld)",
-#ifndef CURL_DISABLE_PROXY
- conn->bits.socksproxy ? conn->socks_proxy.host.dispname :
- conn->bits.httpproxy ? conn->http_proxy.host.dispname :
-#endif
- conn->bits.conn_to_host ? conn->conn_to_host.dispname :
- conn->host.dispname,
- conn->primary_ip, conn->port, conn->connection_id);
+ infof(data, "Connected to %s (%s) port %u",
+ CURL_CONN_HOST_DISPNAME(conn), conn->primary_ip, conn->port);
}
#endif
@@ -1580,8 +1595,10 @@ static struct connectdata *allocate_conn(struct Curl_easy *data)
if(!conn->localdev)
goto error;
}
+#ifndef CURL_DISABLE_BINDLOCAL
conn->localportrange = data->set.localportrange;
conn->localport = data->set.localport;
+#endif
/* the close socket stuff needs to be copied to the connection struct as
it may live on without (this specific) Curl_easy */
@@ -1857,7 +1874,7 @@ static CURLcode parseurlandfillconn(struct Curl_easy *data,
* User name and password set with their own options override the
* credentials possibly set in the URL.
*/
- if(!data->state.aptr.passwd) {
+ if(!data->set.str[STRING_PASSWORD]) {
uc = curl_url_get(uh, CURLUPART_PASSWORD, &data->state.up.password, 0);
if(!uc) {
char *decoded;
@@ -2016,13 +2033,13 @@ void Curl_free_request_state(struct Curl_easy *data)
{
Curl_safefree(data->req.p.http);
Curl_safefree(data->req.newurl);
-
#ifndef CURL_DISABLE_DOH
if(data->req.doh) {
Curl_close(&data->req.doh->probe[0].easy);
Curl_close(&data->req.doh->probe[1].easy);
}
#endif
+ Curl_client_cleanup(data);
}
@@ -2059,7 +2076,6 @@ static char *detect_proxy(struct Curl_easy *data,
char proxy_env[128];
const char *protop = conn->handler->scheme;
char *envp = proxy_env;
- char *prox;
#ifdef CURL_DISABLE_VERBOSE_STRINGS
(void)data;
#endif
@@ -2072,7 +2088,7 @@ static char *detect_proxy(struct Curl_easy *data,
strcpy(envp, "_proxy");
/* read the protocol proxy: */
- prox = curl_getenv(proxy_env);
+ proxy = curl_getenv(proxy_env);
/*
* We don't try the uppercase version of HTTP_PROXY because of
@@ -2086,23 +2102,35 @@ static char *detect_proxy(struct Curl_easy *data,
* This can cause 'internal' http/ftp requests to be
* arbitrarily redirected by any external attacker.
*/
- if(!prox && !strcasecompare("http_proxy", proxy_env)) {
+ if(!proxy && !strcasecompare("http_proxy", proxy_env)) {
/* There was no lowercase variable, try the uppercase version: */
Curl_strntoupper(proxy_env, proxy_env, sizeof(proxy_env));
- prox = curl_getenv(proxy_env);
+ proxy = curl_getenv(proxy_env);
}
envp = proxy_env;
- if(prox) {
- proxy = prox; /* use this */
- }
- else {
- envp = (char *)"all_proxy";
- proxy = curl_getenv(envp); /* default proxy to use */
+ if(!proxy) {
+#ifdef USE_WEBSOCKETS
+ /* websocket proxy fallbacks */
+ if(strcasecompare("ws_proxy", proxy_env)) {
+ proxy = curl_getenv("http_proxy");
+ }
+ else if(strcasecompare("wss_proxy", proxy_env)) {
+ proxy = curl_getenv("https_proxy");
+ if(!proxy)
+ proxy = curl_getenv("HTTPS_PROXY");
+ }
if(!proxy) {
- envp = (char *)"ALL_PROXY";
- proxy = curl_getenv(envp);
+#endif
+ envp = (char *)"all_proxy";
+ proxy = curl_getenv(envp); /* default proxy to use */
+ if(!proxy) {
+ envp = (char *)"ALL_PROXY";
+ proxy = curl_getenv(envp);
+ }
+#ifdef USE_WEBSOCKETS
}
+#endif
}
if(proxy)
infof(data, "Uses proxy env variable %s == '%s'", envp, proxy);
@@ -2113,7 +2141,7 @@ static char *detect_proxy(struct Curl_easy *data,
/*
* If this is supposed to use a proxy, we need to figure out the proxy
- * host name, so that we can re-use an existing connection
+ * host name, so that we can reuse an existing connection
* that may exist registered to the same proxy host.
*/
static CURLcode parse_proxy(struct Curl_easy *data,
@@ -2434,7 +2462,7 @@ static CURLcode create_conn_helper_init_proxy(struct Curl_easy *data,
/***********************************************************************
* If this is supposed to use a proxy, we need to figure out the proxy host
- * name, proxy type and port number, so that we can re-use an existing
+ * name, proxy type and port number, so that we can reuse an existing
* connection that may exist registered to the same proxy host.
***********************************************************************/
if(proxy || socksproxy) {
@@ -2702,7 +2730,9 @@ static CURLcode override_login(struct Curl_easy *data,
data->set.str[STRING_NETRC_FILE]);
if(ret > 0) {
infof(data, "Couldn't find host %s in the %s file; using defaults",
- conn->host.name, data->set.str[STRING_NETRC_FILE]);
+ conn->host.name,
+ (data->set.str[STRING_NETRC_FILE] ?
+ data->set.str[STRING_NETRC_FILE] : ".netrc"));
}
else if(ret < 0) {
failf(data, ".netrc parser error");
@@ -3197,8 +3227,8 @@ static CURLcode resolve_host(struct Curl_easy *data,
if(rc == CURLRESOLV_PENDING)
*async = TRUE;
else if(rc == CURLRESOLV_TIMEDOUT) {
- failf(data, "Failed to resolve host '%s' with timeout after %ld ms",
- connhost->dispname,
+ failf(data, "Failed to resolve host '%s' with timeout after %"
+ CURL_FORMAT_TIMEDIFF_T " ms", connhost->dispname,
Curl_timediff(Curl_now(), data->progress.t_startsingle));
return CURLE_OPERATION_TIMEDOUT;
}
@@ -3252,7 +3282,7 @@ static CURLcode resolve_server(struct Curl_easy *data,
/* Resolve the name of the server or proxy */
if(conn->bits.reuse) {
/* We're reusing the connection - no need to resolve anything, and
- idnconvert_hostname() was called already in create_conn() for the re-use
+ idnconvert_hostname() was called already in create_conn() for the reuse
case. */
*async = FALSE;
return CURLE_OK;
@@ -3271,7 +3301,7 @@ static void reuse_conn(struct Curl_easy *data,
struct connectdata *existing)
{
/* get the user+password information from the temp struct since it may
- * be new for this request even when we re-use an existing connection */
+ * be new for this request even when we reuse an existing connection */
if(temp->user) {
/* use the new user name and password though */
Curl_safefree(existing->user);
@@ -3331,14 +3361,14 @@ static void reuse_conn(struct Curl_easy *data,
existing->hostname_resolve = temp->hostname_resolve;
temp->hostname_resolve = NULL;
- /* re-use init */
- existing->bits.reuse = TRUE; /* yes, we're re-using here */
+ /* reuse init */
+ existing->bits.reuse = TRUE; /* yes, we're reusing here */
conn_free(data, temp);
}
/**
- * create_conn() sets up a new connectdata struct, or re-uses an already
+ * create_conn() sets up a new connectdata struct, or reuses an already
* existing one, and resolves host name.
*
* if this function returns CURLE_OK and *async is set to TRUE, the resolve
@@ -3650,7 +3680,7 @@ static CURLcode create_conn(struct Curl_easy *data,
/*************************************************************
* Check the current list of connections to see if we can
- * re-use an already existing one or if we have to create a
+ * reuse an already existing one or if we have to create a
* new one.
*************************************************************/
@@ -3658,7 +3688,7 @@ static CURLcode create_conn(struct Curl_easy *data,
DEBUGASSERT(conn->passwd);
/* reuse_fresh is TRUE if we are told to use a new connection by force, but
- we only acknowledge this option if this is not a re-used connection
+ we only acknowledge this option if this is not a reused connection
already (which happens due to follow-location or during an HTTP
authentication phase). CONNECT_ONLY transfers also refuse reuse. */
if((data->set.reuse_fresh && !data->state.followlocation) ||
@@ -3678,15 +3708,14 @@ static CURLcode create_conn(struct Curl_easy *data,
*in_connect = conn;
#ifndef CURL_DISABLE_PROXY
- infof(data, "Re-using existing connection #%ld with %s %s",
- conn->connection_id,
+ infof(data, "Re-using existing connection with %s %s",
conn->bits.proxy?"proxy":"host",
conn->socks_proxy.host.name ? conn->socks_proxy.host.dispname :
conn->http_proxy.host.name ? conn->http_proxy.host.dispname :
conn->host.dispname);
#else
- infof(data, "Re-using existing connection #%ld with host %s",
- conn->connection_id, conn->host.dispname);
+ infof(data, "Re-using existing connection with host %s",
+ conn->host.dispname);
#endif
}
else {