summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorChristoph M. Becker <cmbecker69@gmx.de>2020-09-20 13:45:09 +0200
committerChristoph M. Becker <cmbecker69@gmx.de>2020-09-20 15:34:45 +0200
commit81b2f3e5d9fcdffd87a4fcd12bd8c708a97091e1 (patch)
treee8cec26750f3e0065b6a5d63fe88e3602b08748c
parenta7544411dfb833331a19ff10c1082428d80d2ad7 (diff)
downloadphp-git-81b2f3e5d9fcdffd87a4fcd12bd8c708a97091e1.tar.gz
Fix #80114: parse_url does not accept URLs with port 0
URIs with a 0 port are generally valid, so `parse_url()` should recognize such URIs, but still report the port as missing. Co-authored-by: twosee <twose@qq.com> Closes GH-6152.
-rw-r--r--NEWS3
-rw-r--r--ext/standard/tests/url/parse_url_basic_001.phpt9
-rw-r--r--ext/standard/tests/url/parse_url_basic_002.phpt1
-rw-r--r--ext/standard/tests/url/parse_url_basic_003.phpt1
-rw-r--r--ext/standard/tests/url/parse_url_basic_004.phpt1
-rw-r--r--ext/standard/tests/url/parse_url_basic_005.phpt1
-rw-r--r--ext/standard/tests/url/parse_url_basic_006.phpt1
-rw-r--r--ext/standard/tests/url/parse_url_basic_007.phpt1
-rw-r--r--ext/standard/tests/url/parse_url_basic_008.phpt1
-rw-r--r--ext/standard/tests/url/parse_url_basic_009.phpt1
-rw-r--r--ext/standard/tests/url/parse_url_unterminated.phpt9
-rw-r--r--ext/standard/tests/url/urls.inc1
-rw-r--r--ext/standard/url.c10
13 files changed, 36 insertions, 4 deletions
diff --git a/NEWS b/NEWS
index fe2bae3803..98dd586114 100644
--- a/NEWS
+++ b/NEWS
@@ -12,6 +12,9 @@ PHP NEWS
. Fixed bug #80083 (Optimizer pass 6 removes variables used for ibm_db2 data
binding). (Nikita)
+- Standard:
+ . Fixed bug #80114 (parse_url does not accept URLs with port 0). (cmb, twosee)
+
01 Oct 2020, PHP 7.3.23
- Core:
diff --git a/ext/standard/tests/url/parse_url_basic_001.phpt b/ext/standard/tests/url/parse_url_basic_001.phpt
index 51bae9fe1c..063fc28832 100644
--- a/ext/standard/tests/url/parse_url_basic_001.phpt
+++ b/ext/standard/tests/url/parse_url_basic_001.phpt
@@ -859,6 +859,15 @@ echo "Done";
string(3) "%:x"
}
+--> https://example.com:0/: array(3) {
+ ["scheme"]=>
+ string(5) "https"
+ ["host"]=>
+ string(11) "example.com"
+ ["path"]=>
+ string(1) "/"
+}
+
--> http:///blah.com: bool(false)
--> http://:80: bool(false)
diff --git a/ext/standard/tests/url/parse_url_basic_002.phpt b/ext/standard/tests/url/parse_url_basic_002.phpt
index 309c038794..42a8457431 100644
--- a/ext/standard/tests/url/parse_url_basic_002.phpt
+++ b/ext/standard/tests/url/parse_url_basic_002.phpt
@@ -113,6 +113,7 @@ echo "Done";
--> / : NULL
--> /rest/Users?filter={"id":"123"} : NULL
--> %:x : NULL
+--> https://example.com:0/ : string(5) "https"
--> http:///blah.com : bool(false)
--> http://:80 : bool(false)
--> http://user@:80 : bool(false)
diff --git a/ext/standard/tests/url/parse_url_basic_003.phpt b/ext/standard/tests/url/parse_url_basic_003.phpt
index 9649bdadb1..8b0e7eb875 100644
--- a/ext/standard/tests/url/parse_url_basic_003.phpt
+++ b/ext/standard/tests/url/parse_url_basic_003.phpt
@@ -112,6 +112,7 @@ echo "Done";
--> / : NULL
--> /rest/Users?filter={"id":"123"} : NULL
--> %:x : NULL
+--> https://example.com:0/ : string(11) "example.com"
--> http:///blah.com : bool(false)
--> http://:80 : bool(false)
--> http://user@:80 : bool(false)
diff --git a/ext/standard/tests/url/parse_url_basic_004.phpt b/ext/standard/tests/url/parse_url_basic_004.phpt
index 75aacdf847..042daefeda 100644
--- a/ext/standard/tests/url/parse_url_basic_004.phpt
+++ b/ext/standard/tests/url/parse_url_basic_004.phpt
@@ -112,6 +112,7 @@ echo "Done";
--> / : NULL
--> /rest/Users?filter={"id":"123"} : NULL
--> %:x : NULL
+--> https://example.com:0/ : NULL
--> http:///blah.com : bool(false)
--> http://:80 : bool(false)
--> http://user@:80 : bool(false)
diff --git a/ext/standard/tests/url/parse_url_basic_005.phpt b/ext/standard/tests/url/parse_url_basic_005.phpt
index 1463e0a29a..a5ca381a69 100644
--- a/ext/standard/tests/url/parse_url_basic_005.phpt
+++ b/ext/standard/tests/url/parse_url_basic_005.phpt
@@ -112,6 +112,7 @@ echo "Done";
--> / : NULL
--> /rest/Users?filter={"id":"123"} : NULL
--> %:x : NULL
+--> https://example.com:0/ : NULL
--> http:///blah.com : bool(false)
--> http://:80 : bool(false)
--> http://user@:80 : bool(false)
diff --git a/ext/standard/tests/url/parse_url_basic_006.phpt b/ext/standard/tests/url/parse_url_basic_006.phpt
index 78eee265ce..51dcb2018c 100644
--- a/ext/standard/tests/url/parse_url_basic_006.phpt
+++ b/ext/standard/tests/url/parse_url_basic_006.phpt
@@ -112,6 +112,7 @@ echo "Done";
--> / : NULL
--> /rest/Users?filter={"id":"123"} : NULL
--> %:x : NULL
+--> https://example.com:0/ : NULL
--> http:///blah.com : bool(false)
--> http://:80 : bool(false)
--> http://user@:80 : bool(false)
diff --git a/ext/standard/tests/url/parse_url_basic_007.phpt b/ext/standard/tests/url/parse_url_basic_007.phpt
index 85a420c88c..28a6d154f9 100644
--- a/ext/standard/tests/url/parse_url_basic_007.phpt
+++ b/ext/standard/tests/url/parse_url_basic_007.phpt
@@ -112,6 +112,7 @@ echo "Done";
--> / : string(1) "/"
--> /rest/Users?filter={"id":"123"} : string(11) "/rest/Users"
--> %:x : string(3) "%:x"
+--> https://example.com:0/ : string(1) "/"
--> http:///blah.com : bool(false)
--> http://:80 : bool(false)
--> http://user@:80 : bool(false)
diff --git a/ext/standard/tests/url/parse_url_basic_008.phpt b/ext/standard/tests/url/parse_url_basic_008.phpt
index 75952b2ecd..c2adc9e070 100644
--- a/ext/standard/tests/url/parse_url_basic_008.phpt
+++ b/ext/standard/tests/url/parse_url_basic_008.phpt
@@ -112,6 +112,7 @@ echo "Done";
--> / : NULL
--> /rest/Users?filter={"id":"123"} : string(19) "filter={"id":"123"}"
--> %:x : NULL
+--> https://example.com:0/ : NULL
--> http:///blah.com : bool(false)
--> http://:80 : bool(false)
--> http://user@:80 : bool(false)
diff --git a/ext/standard/tests/url/parse_url_basic_009.phpt b/ext/standard/tests/url/parse_url_basic_009.phpt
index ab9232a9a7..3074a08347 100644
--- a/ext/standard/tests/url/parse_url_basic_009.phpt
+++ b/ext/standard/tests/url/parse_url_basic_009.phpt
@@ -112,6 +112,7 @@ echo "Done";
--> / : NULL
--> /rest/Users?filter={"id":"123"} : NULL
--> %:x : NULL
+--> https://example.com:0/ : NULL
--> http:///blah.com : bool(false)
--> http://:80 : bool(false)
--> http://user@:80 : bool(false)
diff --git a/ext/standard/tests/url/parse_url_unterminated.phpt b/ext/standard/tests/url/parse_url_unterminated.phpt
index 6a0cf02745..8af50dbe28 100644
--- a/ext/standard/tests/url/parse_url_unterminated.phpt
+++ b/ext/standard/tests/url/parse_url_unterminated.phpt
@@ -861,6 +861,15 @@ echo "Done";
string(3) "%:x"
}
+--> https://example.com:0/: array(3) {
+ ["scheme"]=>
+ string(5) "https"
+ ["host"]=>
+ string(11) "example.com"
+ ["path"]=>
+ string(1) "/"
+}
+
--> http:///blah.com: bool(false)
--> http://:80: bool(false)
diff --git a/ext/standard/tests/url/urls.inc b/ext/standard/tests/url/urls.inc
index 199f22caea..d334f4e9ab 100644
--- a/ext/standard/tests/url/urls.inc
+++ b/ext/standard/tests/url/urls.inc
@@ -92,6 +92,7 @@ $urls = array(
'/',
'/rest/Users?filter={"id":"123"}',
'%:x',
+'https://example.com:0/',
// Severely malformed URLs that do not parse:
'http:///blah.com',
diff --git a/ext/standard/url.c b/ext/standard/url.c
index 7763759bc1..fde4ff5377 100644
--- a/ext/standard/url.c
+++ b/ext/standard/url.c
@@ -194,10 +194,11 @@ PHPAPI php_url *php_url_parse_ex(char const *str, size_t length)
if (pp - p > 0 && pp - p < 6 && (pp == ue || *pp == '/')) {
zend_long port;
+ char *end;
memcpy(port_buf, p, (pp - p));
port_buf[pp - p] = '\0';
- port = ZEND_STRTOL(port_buf, NULL, 10);
- if (port > 0 && port <= 65535) {
+ port = ZEND_STRTOL(port_buf, &end, 10);
+ if (port >= 0 && port <= 65535 && end != port_buf) {
ret->port = (unsigned short) port;
if (s + 1 < ue && *s == '/' && *(s + 1) == '/') { /* relative-scheme URL */
s += 2;
@@ -258,10 +259,11 @@ parse_host:
return NULL;
} else if (e - p > 0) {
zend_long port;
+ char *end;
memcpy(port_buf, p, (e - p));
port_buf[e - p] = '\0';
- port = ZEND_STRTOL(port_buf, NULL, 10);
- if (port > 0 && port <= 65535) {
+ port = ZEND_STRTOL(port_buf, &end, 10);
+ if (port >= 0 && port <= 65535 && end != port_buf) {
ret->port = (unsigned short)port;
} else {
php_url_free(ret);