diff --git a/lib/urlapi.c b/lib/urlapi.c index a3111f9db6..a2d3c7e35a 100644 --- a/lib/urlapi.c +++ b/lib/urlapi.c @@ -496,6 +496,9 @@ static CURLUcode hostname_check(struct Curl_URL *u, char *hostname, * Output the "normalized" version of that input string in plain quad decimal * integers. * + * A single dot following the numerical address is accepted and "swallowed" as + * if it was never there. + * * Returns the host type. * * @unittest 1675 @@ -527,17 +530,26 @@ UNITTEST int ipv4_normalize(struct dynbuf *host) else rc = curlx_str_number(&c, &l, UINT_MAX); - if(rc) - return HOST_NAME; - - parts[n] = (unsigned int)l; + if(rc) { + if(!n || (rc != STRE_NO_NUM) || *c) + return HOST_NAME; + n--; + } + else + parts[n] = (unsigned int)l; switch(*c) { case '.': - if(n == 3) - return HOST_NAME; - n++; - c++; + if(n == 3) { + if(c[1]) + /* something follows this dot */ + return HOST_NAME; + done = TRUE; + } + else { + n++; + c++; + } break; case '\0': diff --git a/tests/data/test1560 b/tests/data/test1560 index e0d792800b..e27229739f 100644 --- a/tests/data/test1560 +++ b/tests/data/test1560 @@ -37,7 +37,7 @@ lib%TESTNUMBER success -Allocations: 3100 +Allocations: 3200 diff --git a/tests/libtest/lib1560.c b/tests/libtest/lib1560.c index e833c304e3..533a44e983 100644 --- a/tests/libtest/lib1560.c +++ b/tests/libtest/lib1560.c @@ -625,6 +625,23 @@ static const struct testcase get_parts_list[] = { }; static const struct urltestcase get_url_list[] = { + {"https://127.1.", "https://127.0.0.1/", 0, 0, CURLUE_OK}, + {"https://127.1.:443", "https://127.0.0.1:443/", 0, 0, CURLUE_OK}, + {"https://127.1.?moo", "https://127.0.0.1/?moo", 0, 0, CURLUE_OK}, + {"https://127.1.#moo", "https://127.0.0.1/#moo", 0, 0, CURLUE_OK}, + {"https://127.1.a", "https://127.1.a/", 0, 0, CURLUE_OK}, + {"https://127.1..", "", 0, 0, CURLUE_BAD_HOSTNAME}, + {"https://127.1..:443", "", 0, 0, CURLUE_BAD_HOSTNAME}, + {"https://127.1..?moo", "", 0, 0, CURLUE_BAD_HOSTNAME}, + {"https://127.1..#moo", "", 0, 0, CURLUE_BAD_HOSTNAME}, + {"https://127.1.1.", "https://127.1.0.1/", 0, 0, CURLUE_OK}, + {"https://127.1.1./foo", "https://127.1.0.1/foo", 0, 0, CURLUE_OK}, + {"https://127.1.1.1.", "https://127.1.1.1/", 0, 0, CURLUE_OK}, + {"https://127.1", "https://127.0.0.1/", 0, 0, CURLUE_OK}, + {"https://127.0.0.1.", "https://127.0.0.1/", 0, 0, CURLUE_OK}, + {"https://127.0.0.0xff.", "https://127.0.0.255/", 0, 0, CURLUE_OK}, + {"https://127.0.0.1..", "", 0, 0, CURLUE_BAD_HOSTNAME}, + {"https://127.0.0.256..", "", 0, 0, CURLUE_BAD_HOSTNAME}, {"http://hej./", "http://hej./", 0, 0, CURLUE_OK}, {"http://hej../", "", 0, 0, CURLUE_BAD_HOSTNAME}, {"http://hej.../", "", 0, 0, CURLUE_BAD_HOSTNAME}, @@ -743,9 +760,9 @@ static const struct urltestcase get_url_list[] = { {"https://16843009", "https://1.1.1.1/", 0, 0, CURLUE_OK}, {"https://0177.1", "https://127.0.0.1/", 0, 0, CURLUE_OK}, {"https://0111.02.0x3", "https://73.2.0.3/", 0, 0, CURLUE_OK}, - {"https://0111.02.0x3.", "https://0111.02.0x3./", 0, 0, CURLUE_OK}, + {"https://0111.02.0x3.", "https://73.2.0.3/", 0, 0, CURLUE_OK}, {"https://0111.02.030", "https://73.2.0.24/", 0, 0, CURLUE_OK}, - {"https://0111.02.030.", "https://0111.02.030./", 0, 0, CURLUE_OK}, + {"https://0111.02.030.", "https://73.2.0.24/", 0, 0, CURLUE_OK}, {"https://0xff.0xff.0377.255", "https://255.255.255.255/", 0, 0, CURLUE_OK}, {"https://1.0xffffff", "https://1.255.255.255/", 0, 0, CURLUE_OK}, /* IPv4 numerical overflows or syntax errors will not normalize */