mirror of
https://github.com/moparisthebest/curl
synced 2025-02-28 17:31:46 -05:00
urlapi: add CURLUPART_ZONEID to set and get
The zoneid can be used with IPv6 numerical addresses. Updated test 1560 to verify. Closes #3834
This commit is contained in:
parent
0eec832603
commit
2d0e9b40d3
@ -35,7 +35,6 @@
|
|||||||
1.16 Try to URL encode given URL
|
1.16 Try to URL encode given URL
|
||||||
1.17 Add support for IRIs
|
1.17 Add support for IRIs
|
||||||
1.18 try next proxy if one doesn't work
|
1.18 try next proxy if one doesn't work
|
||||||
1.19 add CURLUPART_SCOPEID
|
|
||||||
1.20 SRV and URI DNS records
|
1.20 SRV and URI DNS records
|
||||||
1.21 Have the URL API offer IDN decoding
|
1.21 Have the URL API offer IDN decoding
|
||||||
1.22 CURLINFO_PAUSE_STATE
|
1.22 CURLINFO_PAUSE_STATE
|
||||||
@ -373,11 +372,6 @@
|
|||||||
|
|
||||||
https://github.com/curl/curl/issues/896
|
https://github.com/curl/curl/issues/896
|
||||||
|
|
||||||
1.19 add CURLUPART_SCOPEID
|
|
||||||
|
|
||||||
Add support for CURLUPART_SCOPEID to curl_url_set() and curl_url_get(). It is
|
|
||||||
only really used when the host name is an IPv6 numerical address.
|
|
||||||
|
|
||||||
1.20 SRV and URI DNS records
|
1.20 SRV and URI DNS records
|
||||||
|
|
||||||
Offer support for resolving SRV and URI DNS records for libcurl to know which
|
Offer support for resolving SRV and URI DNS records for libcurl to know which
|
||||||
|
@ -5,7 +5,7 @@
|
|||||||
.\" * | (__| |_| | _ <| |___
|
.\" * | (__| |_| | _ <| |___
|
||||||
.\" * \___|\___/|_| \_\_____|
|
.\" * \___|\___/|_| \_\_____|
|
||||||
.\" *
|
.\" *
|
||||||
.\" * Copyright (C) 1998 - 2018, Daniel Stenberg, <daniel@haxx.se>, et al.
|
.\" * Copyright (C) 1998 - 2019, Daniel Stenberg, <daniel@haxx.se>, et al.
|
||||||
.\" *
|
.\" *
|
||||||
.\" * This software is licensed as described in the file COPYING, which
|
.\" * This software is licensed as described in the file COPYING, which
|
||||||
.\" * you should have received as part of this distribution. The terms
|
.\" * you should have received as part of this distribution. The terms
|
||||||
@ -76,6 +76,10 @@ Scheme cannot be URL decoded on get.
|
|||||||
.IP CURLUPART_PASSWORD
|
.IP CURLUPART_PASSWORD
|
||||||
.IP CURLUPART_OPTIONS
|
.IP CURLUPART_OPTIONS
|
||||||
.IP CURLUPART_HOST
|
.IP CURLUPART_HOST
|
||||||
|
If the host part is an IPv6 numeric address, the zoneid will not be part of
|
||||||
|
the extracted host but is provided separately in \fICURLUPART_ZONEID\fP.
|
||||||
|
.IP CURLUPART_ZONEID
|
||||||
|
If the host name is a numeric IPv6 address, this field might also be set.
|
||||||
.IP CURLUPART_PORT
|
.IP CURLUPART_PORT
|
||||||
Port cannot be URL decoded on get.
|
Port cannot be URL decoded on get.
|
||||||
.IP CURLUPART_PATH
|
.IP CURLUPART_PATH
|
||||||
@ -104,7 +108,7 @@ If this function returns an error, no URL part is returned.
|
|||||||
}
|
}
|
||||||
.fi
|
.fi
|
||||||
.SH AVAILABILITY
|
.SH AVAILABILITY
|
||||||
Added in curl 7.62.0
|
Added in curl 7.62.0. CURLUPART_ZONEID was added in 7.65.0.
|
||||||
.SH "SEE ALSO"
|
.SH "SEE ALSO"
|
||||||
.BR curl_url_cleanup "(3), " curl_url "(3), " curl_url_set "(3), "
|
.BR curl_url_cleanup "(3), " curl_url "(3), " curl_url_set "(3), "
|
||||||
.BR curl_url_dup "(3), "
|
.BR curl_url_dup "(3), "
|
||||||
|
@ -62,6 +62,8 @@ Scheme cannot be URL decoded on set.
|
|||||||
.IP CURLUPART_HOST
|
.IP CURLUPART_HOST
|
||||||
The host name can use IDNA. The string must then be encoded as your locale
|
The host name can use IDNA. The string must then be encoded as your locale
|
||||||
says or UTF-8 (when winidn is used).
|
says or UTF-8 (when winidn is used).
|
||||||
|
.IP CURLUPART_ZONEID
|
||||||
|
If the host name is a numeric IPv6 address, this field can also be set.
|
||||||
.IP CURLUPART_PORT
|
.IP CURLUPART_PORT
|
||||||
Port cannot be URL encoded on set. The given port number is provided as a
|
Port cannot be URL encoded on set. The given port number is provided as a
|
||||||
string and the decimal number must be between 1 and 65535. Anything else will
|
string and the decimal number must be between 1 and 65535. Anything else will
|
||||||
@ -127,7 +129,7 @@ If this function returns an error, no URL part is returned.
|
|||||||
curl_url_cleanup(url);
|
curl_url_cleanup(url);
|
||||||
.fi
|
.fi
|
||||||
.SH AVAILABILITY
|
.SH AVAILABILITY
|
||||||
Added in curl 7.62.0
|
Added in curl 7.62.0. CURLUPART_ZONEID was added in 7.65.0.
|
||||||
.SH "SEE ALSO"
|
.SH "SEE ALSO"
|
||||||
.BR curl_url_cleanup "(3), " curl_url "(3), " curl_url_get "(3), "
|
.BR curl_url_cleanup "(3), " curl_url "(3), " curl_url_get "(3), "
|
||||||
.BR curl_url_dup "(3), "
|
.BR curl_url_dup "(3), "
|
||||||
|
@ -764,6 +764,7 @@ CURLUPART_QUERY 7.62.0
|
|||||||
CURLUPART_SCHEME 7.62.0
|
CURLUPART_SCHEME 7.62.0
|
||||||
CURLUPART_URL 7.62.0
|
CURLUPART_URL 7.62.0
|
||||||
CURLUPART_USER 7.62.0
|
CURLUPART_USER 7.62.0
|
||||||
|
CURLUPART_ZONEID 7.65.0
|
||||||
CURLUSESSL_ALL 7.17.0
|
CURLUSESSL_ALL 7.17.0
|
||||||
CURLUSESSL_CONTROL 7.17.0
|
CURLUSESSL_CONTROL 7.17.0
|
||||||
CURLUSESSL_NONE 7.17.0
|
CURLUSESSL_NONE 7.17.0
|
||||||
|
@ -60,7 +60,8 @@ typedef enum {
|
|||||||
CURLUPART_PORT,
|
CURLUPART_PORT,
|
||||||
CURLUPART_PATH,
|
CURLUPART_PATH,
|
||||||
CURLUPART_QUERY,
|
CURLUPART_QUERY,
|
||||||
CURLUPART_FRAGMENT
|
CURLUPART_FRAGMENT,
|
||||||
|
CURLUPART_ZONEID /* added in 7.65.0 */
|
||||||
} CURLUPart;
|
} CURLUPart;
|
||||||
|
|
||||||
#define CURLU_DEFAULT_PORT (1<<0) /* return default port number */
|
#define CURLU_DEFAULT_PORT (1<<0) /* return default port number */
|
||||||
|
35
lib/urlapi.c
35
lib/urlapi.c
@ -56,7 +56,7 @@ struct Curl_URL {
|
|||||||
char *password;
|
char *password;
|
||||||
char *options; /* IMAP only? */
|
char *options; /* IMAP only? */
|
||||||
char *host;
|
char *host;
|
||||||
char *scopeid; /* for numerical IPv6 addresses */
|
char *zoneid; /* for numerical IPv6 addresses */
|
||||||
char *port;
|
char *port;
|
||||||
char *path;
|
char *path;
|
||||||
char *query;
|
char *query;
|
||||||
@ -75,7 +75,7 @@ static void free_urlhandle(struct Curl_URL *u)
|
|||||||
free(u->password);
|
free(u->password);
|
||||||
free(u->options);
|
free(u->options);
|
||||||
free(u->host);
|
free(u->host);
|
||||||
free(u->scopeid);
|
free(u->zoneid);
|
||||||
free(u->port);
|
free(u->port);
|
||||||
free(u->path);
|
free(u->path);
|
||||||
free(u->query);
|
free(u->query);
|
||||||
@ -606,7 +606,7 @@ static CURLUcode hostname_check(struct Curl_URL *u, char *hostname)
|
|||||||
len = strspn(hostname, l);
|
len = strspn(hostname, l);
|
||||||
if(hlen != len) {
|
if(hlen != len) {
|
||||||
/* this could now be '%[zone id]' */
|
/* this could now be '%[zone id]' */
|
||||||
char scopeid[16];
|
char zoneid[16];
|
||||||
if(hostname[len] == '%') {
|
if(hostname[len] == '%') {
|
||||||
int i = 0;
|
int i = 0;
|
||||||
char *h = &hostname[len + 1];
|
char *h = &hostname[len + 1];
|
||||||
@ -614,12 +614,12 @@ static CURLUcode hostname_check(struct Curl_URL *u, char *hostname)
|
|||||||
if(!strncmp(h, "25", 2) && h[2] && (h[2] != ']'))
|
if(!strncmp(h, "25", 2) && h[2] && (h[2] != ']'))
|
||||||
h += 2;
|
h += 2;
|
||||||
while(*h && (*h != ']') && (i < 15))
|
while(*h && (*h != ']') && (i < 15))
|
||||||
scopeid[i++] = *h++;
|
zoneid[i++] = *h++;
|
||||||
if(!i || (']' != *h))
|
if(!i || (']' != *h))
|
||||||
return CURLUE_MALFORMED_INPUT;
|
return CURLUE_MALFORMED_INPUT;
|
||||||
scopeid[i] = 0;
|
zoneid[i] = 0;
|
||||||
u->scopeid = strdup(scopeid);
|
u->zoneid = strdup(zoneid);
|
||||||
if(!u->scopeid)
|
if(!u->zoneid)
|
||||||
return CURLUE_OUT_OF_MEMORY;
|
return CURLUE_OUT_OF_MEMORY;
|
||||||
hostname[len] = ']'; /* insert end bracket */
|
hostname[len] = ']'; /* insert end bracket */
|
||||||
hostname[len + 1] = 0; /* terminate the hostname */
|
hostname[len + 1] = 0; /* terminate the hostname */
|
||||||
@ -997,6 +997,9 @@ CURLUcode curl_url_get(CURLU *u, CURLUPart what,
|
|||||||
ptr = u->host;
|
ptr = u->host;
|
||||||
ifmissing = CURLUE_NO_HOST;
|
ifmissing = CURLUE_NO_HOST;
|
||||||
break;
|
break;
|
||||||
|
case CURLUPART_ZONEID:
|
||||||
|
ptr = u->zoneid;
|
||||||
|
break;
|
||||||
case CURLUPART_PORT:
|
case CURLUPART_PORT:
|
||||||
ptr = u->port;
|
ptr = u->port;
|
||||||
ifmissing = CURLUE_NO_PORT;
|
ifmissing = CURLUE_NO_PORT;
|
||||||
@ -1082,16 +1085,16 @@ CURLUcode curl_url_get(CURLU *u, CURLUPart what,
|
|||||||
if(h && !(h->flags & PROTOPT_URLOPTIONS))
|
if(h && !(h->flags & PROTOPT_URLOPTIONS))
|
||||||
options = NULL;
|
options = NULL;
|
||||||
|
|
||||||
if((u->host[0] == '[') && u->scopeid) {
|
if((u->host[0] == '[') && u->zoneid) {
|
||||||
/* make it '[ host %25 scopeid ]' */
|
/* make it '[ host %25 zoneid ]' */
|
||||||
size_t hostlen = strlen(u->host);
|
size_t hostlen = strlen(u->host);
|
||||||
size_t alen = hostlen + 3 + strlen(u->scopeid) + 1;
|
size_t alen = hostlen + 3 + strlen(u->zoneid) + 1;
|
||||||
allochost = malloc(alen);
|
allochost = malloc(alen);
|
||||||
if(!allochost)
|
if(!allochost)
|
||||||
return CURLUE_OUT_OF_MEMORY;
|
return CURLUE_OUT_OF_MEMORY;
|
||||||
memcpy(allochost, u->host, hostlen - 1);
|
memcpy(allochost, u->host, hostlen - 1);
|
||||||
msnprintf(&allochost[hostlen - 1], alen - hostlen + 1,
|
msnprintf(&allochost[hostlen - 1], alen - hostlen + 1,
|
||||||
"%%25%s]", u->scopeid);
|
"%%25%s]", u->zoneid);
|
||||||
}
|
}
|
||||||
|
|
||||||
url = aprintf("%s://%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s",
|
url = aprintf("%s://%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s",
|
||||||
@ -1184,6 +1187,9 @@ CURLUcode curl_url_set(CURLU *u, CURLUPart what,
|
|||||||
case CURLUPART_HOST:
|
case CURLUPART_HOST:
|
||||||
storep = &u->host;
|
storep = &u->host;
|
||||||
break;
|
break;
|
||||||
|
case CURLUPART_ZONEID:
|
||||||
|
storep = &u->zoneid;
|
||||||
|
break;
|
||||||
case CURLUPART_PORT:
|
case CURLUPART_PORT:
|
||||||
u->portnum = 0;
|
u->portnum = 0;
|
||||||
storep = &u->port;
|
storep = &u->port;
|
||||||
@ -1227,8 +1233,11 @@ CURLUcode curl_url_set(CURLU *u, CURLUPart what,
|
|||||||
break;
|
break;
|
||||||
case CURLUPART_HOST:
|
case CURLUPART_HOST:
|
||||||
storep = &u->host;
|
storep = &u->host;
|
||||||
free(u->scopeid);
|
free(u->zoneid);
|
||||||
u->scopeid = NULL;
|
u->zoneid = NULL;
|
||||||
|
break;
|
||||||
|
case CURLUPART_ZONEID:
|
||||||
|
storep = &u->zoneid;
|
||||||
break;
|
break;
|
||||||
case CURLUPART_PORT:
|
case CURLUPART_PORT:
|
||||||
{
|
{
|
||||||
|
@ -38,6 +38,8 @@ we got https://[::1]/hello.html
|
|||||||
we got https://example.com/hello.html
|
we got https://example.com/hello.html
|
||||||
we got https://[fe80::20c:29ff:fe9c:409b%25eth0]/hello.html
|
we got https://[fe80::20c:29ff:fe9c:409b%25eth0]/hello.html
|
||||||
we got [fe80::20c:29ff:fe9c:409b]
|
we got [fe80::20c:29ff:fe9c:409b]
|
||||||
|
we got eth0
|
||||||
|
we got https://[fe80::20c:29ff:fe9c:409b%25clown]/hello.html
|
||||||
success
|
success
|
||||||
</stdout>
|
</stdout>
|
||||||
</verify>
|
</verify>
|
||||||
|
@ -414,6 +414,10 @@ static int checkurl(const char *url, const char *out)
|
|||||||
|
|
||||||
/* !checksrc! disable SPACEBEFORECOMMA 1 */
|
/* !checksrc! disable SPACEBEFORECOMMA 1 */
|
||||||
static struct setcase set_parts_list[] = {
|
static struct setcase set_parts_list[] = {
|
||||||
|
{"https://[::1%25fake]:1234/",
|
||||||
|
"zoneid=NULL,",
|
||||||
|
"https://[::1]:1234/",
|
||||||
|
0, 0, CURLUE_OK, CURLUE_OK},
|
||||||
{"https://host:1234/",
|
{"https://host:1234/",
|
||||||
"port=NULL,",
|
"port=NULL,",
|
||||||
"https://host/",
|
"https://host/",
|
||||||
@ -547,6 +551,8 @@ static CURLUPart part2id(char *part)
|
|||||||
return CURLUPART_QUERY;
|
return CURLUPART_QUERY;
|
||||||
if(!strcmp("fragment", part))
|
if(!strcmp("fragment", part))
|
||||||
return CURLUPART_FRAGMENT;
|
return CURLUPART_FRAGMENT;
|
||||||
|
if(!strcmp("zoneid", part))
|
||||||
|
return CURLUPART_ZONEID;
|
||||||
return 9999; /* bad input => bad output */
|
return 9999; /* bad input => bad output */
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -571,6 +577,9 @@ static CURLUcode updateurl(CURLU *u, const char *cmd, unsigned int setflags)
|
|||||||
/* for debugging this */
|
/* for debugging this */
|
||||||
fprintf(stderr, "%s = %s [%d]\n", part, value, (int)what);
|
fprintf(stderr, "%s = %s [%d]\n", part, value, (int)what);
|
||||||
#endif
|
#endif
|
||||||
|
if(what > CURLUPART_ZONEID)
|
||||||
|
fprintf(stderr, "UNKNOWN part '%s'\n", part);
|
||||||
|
|
||||||
if(!strcmp("NULL", value))
|
if(!strcmp("NULL", value))
|
||||||
uc = curl_url_set(u, what, NULL, setflags);
|
uc = curl_url_set(u, what, NULL, setflags);
|
||||||
else if(!strcmp("\"\"", value))
|
else if(!strcmp("\"\"", value))
|
||||||
@ -942,6 +951,35 @@ static int scopeid(void)
|
|||||||
curl_free(url);
|
curl_free(url);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
rc = curl_url_get(u, CURLUPART_ZONEID, &url, 0);
|
||||||
|
if(rc != CURLUE_OK) {
|
||||||
|
fprintf(stderr, "%s:%d curl_url_get CURLUPART_ZONEID returned %d\n",
|
||||||
|
__FILE__, __LINE__, (int)rc);
|
||||||
|
error++;
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
printf("we got %s\n", url);
|
||||||
|
curl_free(url);
|
||||||
|
}
|
||||||
|
|
||||||
|
rc = curl_url_set(u, CURLUPART_ZONEID, "clown", 0);
|
||||||
|
if(rc != CURLUE_OK) {
|
||||||
|
fprintf(stderr, "%s:%d curl_url_set CURLUPART_ZONEID returned %d\n",
|
||||||
|
__FILE__, __LINE__, (int)rc);
|
||||||
|
error++;
|
||||||
|
}
|
||||||
|
|
||||||
|
rc = curl_url_get(u, CURLUPART_URL, &url, 0);
|
||||||
|
if(rc != CURLUE_OK) {
|
||||||
|
fprintf(stderr, "%s:%d curl_url_get CURLUPART_URL returned %d\n",
|
||||||
|
__FILE__, __LINE__, (int)rc);
|
||||||
|
error++;
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
printf("we got %s\n", url);
|
||||||
|
curl_free(url);
|
||||||
|
}
|
||||||
|
|
||||||
curl_url_cleanup(u);
|
curl_url_cleanup(u);
|
||||||
|
|
||||||
return error;
|
return error;
|
||||||
|
Loading…
x
Reference in New Issue
Block a user