diff options
Diffstat (limited to 'lib')
-rw-r--r-- | lib/setopt.c | 6 | ||||
-rw-r--r-- | lib/transfer.c | 15 | ||||
-rw-r--r-- | lib/url.c | 19 | ||||
-rw-r--r-- | lib/urldata.h | 1 |
4 files changed, 35 insertions, 6 deletions
diff --git a/lib/setopt.c b/lib/setopt.c index 22956a20f..1627aba6d 100644 --- a/lib/setopt.c +++ b/lib/setopt.c @@ -1204,6 +1204,12 @@ CURLcode Curl_vsetopt(struct Curl_easy *data, CURLoption option, return CURLE_BAD_FUNCTION_ARGUMENT; data->set.low_speed_time = arg; break; + case CURLOPT_CURLU: + /* + * pass CURLU to set URL + */ + data->set.uh = va_arg(param, CURLU *); + break; case CURLOPT_URL: /* * The URL to fetch. diff --git a/lib/transfer.c b/lib/transfer.c index de6043d7d..32ca5a496 100644 --- a/lib/transfer.c +++ b/lib/transfer.c @@ -1353,17 +1353,30 @@ void Curl_init_CONNECT(struct Curl_easy *data) CURLcode Curl_pretransfer(struct Curl_easy *data) { CURLcode result; - if(!data->change.url) { + + if(!data->change.url && !data->set.uh) { /* we can't do anything without URL */ failf(data, "No URL set!"); return CURLE_URL_MALFORMAT; } + /* since the URL may have been redirected in a previous use of this handle */ if(data->change.url_alloc) { /* the already set URL is allocated, free it first! */ Curl_safefree(data->change.url); data->change.url_alloc = FALSE; } + + if(!data->change.url && data->set.uh) { + CURLUcode uc; + uc = curl_url_get(data->set.uh, + CURLUPART_URL, &data->set.str[STRING_SET_URL], 0); + if(uc) { + failf(data, "No URL set!"); + return CURLE_URL_MALFORMAT; + } + } + data->change.url = data->set.str[STRING_SET_URL]; /* Init the SSL session ID cache here. We do it here since we want to do it @@ -2026,7 +2026,13 @@ static CURLcode parseurlandfillconn(struct Curl_easy *data, Curl_up_free(data); /* cleanup previous leftovers first */ /* parse the URL */ - uh = data->state.uh = curl_url(); + if(data->set.uh) { + uh = data->set.uh; + } + else { + uh = data->state.uh = curl_url(); + } + if(!uh) return CURLE_OUT_OF_MEMORY; @@ -2043,15 +2049,17 @@ static CURLcode parseurlandfillconn(struct Curl_easy *data, data->change.url_alloc = TRUE; } - uc = curl_url_set(uh, CURLUPART_URL, data->change.url, + if(!data->set.uh) { + uc = curl_url_set(uh, CURLUPART_URL, data->change.url, CURLU_GUESS_SCHEME | CURLU_NON_SUPPORT_SCHEME | (data->set.disallow_username_in_url ? CURLU_DISALLOW_USER : 0) | (data->set.path_as_is ? CURLU_PATH_AS_IS : 0)); - if(uc) { - DEBUGF(infof(data, "curl_url_set rejected %s\n", data->change.url)); - return Curl_uc_to_curlcode(uc); + if(uc) { + DEBUGF(infof(data, "curl_url_set rejected %s\n", data->change.url)); + return Curl_uc_to_curlcode(uc); + } } uc = curl_url_get(uh, CURLUPART_SCHEME, &data->state.up.scheme, 0); @@ -2193,6 +2201,7 @@ static CURLcode parseurlandfillconn(struct Curl_easy *data, return CURLE_OK; } + /* * If we're doing a resumed transfer, we need to setup our stuff * properly. diff --git a/lib/urldata.h b/lib/urldata.h index 11a6a22c6..eae73a19f 100644 --- a/lib/urldata.h +++ b/lib/urldata.h @@ -1728,6 +1728,7 @@ struct UserDefined { bool doh_get; /* use GET for DoH requests, instead of POST */ multidone_func fmultidone; struct Curl_easy *dohfor; /* this is a DoH request for that transfer */ + CURLU *uh; /* URL handle for the current parsed URL */ }; struct Names { |