From: Matteo Beccati Date: Tue, 18 Aug 2020 16:10:39 +0000 (+0200) Subject: Fix #47021: SoapClient stumbles over WSDL delivered with "Transfer-Encoding: chunked" X-Git-Tag: php-7.3.23RC1~33 X-Git-Url: https://granicus.if.org/sourcecode?a=commitdiff_plain;h=f7c43b8c72822a4722bd7404c6f65e15b2b912c1;p=php Fix #47021: SoapClient stumbles over WSDL delivered with "Transfer-Encoding: chunked" --- diff --git a/NEWS b/NEWS index 5757c09f51..4748996c26 100644 --- a/NEWS +++ b/NEWS @@ -38,6 +38,10 @@ PHP NEWS . Fixed bug #64705 (errorInfo property of PDOException is null when PDO::__construct() fails). (Ahmed Abdou) +- SOAP: + . Fixed bug #47021 (SoapClient stumbles over WSDL delivered with + "Transfer-Encoding: chunked"). (Matteo) + - Standard: . Fixed bug #79930 (array_merge_recursive() crashes when called with array with single reference). (Nikita) diff --git a/ext/soap/php_http.c b/ext/soap/php_http.c index fb3089ec27..b054d9ba9e 100644 --- a/ext/soap/php_http.c +++ b/ext/soap/php_http.c @@ -1375,11 +1375,24 @@ static char *get_http_header_value(char *headers, char *type) /* match */ tmp = pos + typelen; + + /* strip leading whitespace */ + while (*tmp == ' ' || *tmp == '\t') { + tmp++; + } + eol = strchr(tmp, '\n'); if (eol == NULL) { eol = headers + headerslen; - } else if (eol > tmp && *(eol-1) == '\r') { - eol--; + } else if (eol > tmp) { + if (*(eol-1) == '\r') { + eol--; + } + + /* strip trailing whitespace */ + while (eol > tmp && (*(eol-1) == ' ' || *(eol-1) == '\t')) { + eol--; + } } return estrndup(tmp, eol - tmp); } diff --git a/ext/soap/tests/bug47021.phpt b/ext/soap/tests/bug47021.phpt new file mode 100644 index 0000000000..757e74ef15 --- /dev/null +++ b/ext/soap/tests/bug47021.phpt @@ -0,0 +1,80 @@ +--TEST-- +Bug #47021 SoapClient (SoapClient stumbles over WSDL delivered with "Transfer-Encoding: chunked") +--INI-- +soap.wsdl_cache_enabled=0 +--SKIPIF-- + +--FILE-- + $v) { + $chunks[$k] = sprintf("%08x\r\n%s\r\n", strlen($v), $v); + } + + return join('', $chunks); +} + +$wsdl = file_get_contents(__DIR__.'/server030.wsdl'); + +$soap = << +text0text1text2text3text4text5text6text7text8text9 +EOF; + +$responses = [ + "data://text/plain,HTTP/1.1 200 OK\r\n". + "Content-Type: text/xml;charset=utf-8\r\n". + "Transfer-Encoding: \t chunked\t \r\n". + "Connection: close\r\n". + "\r\n". + chunk_body($wsdl, 64), + "data://text/plain,HTTP/1.1 200 OK\r\n". + "Content-Type: text/xml;charset=utf-8\r\n". + "Transfer-Encoding: \t chunked\t \r\n". + "Connection: close\r\n". + "\r\n". + chunk_body($soap, 156), +]; + + +$pid = http_server('tcp://127.0.0.1:12342', $responses); + +$options = [ + 'trace' => true, + 'location' => 'http://127.0.0.1:12342/', +]; + +class BugSoapClient extends SoapClient +{ + public function __doRequest($request, $location, $action, $version, $one_way = null) + { + $response = parent::__doRequest($request, $location, $action, $version, $one_way); + + var_dump(strlen($response)); + + return $response; + } +} + +$client = new BugSoapClient('http://127.0.0.1:12342/', $options); + +var_dump(count($client->getItems())); + +http_server_kill($pid); + +?> +--EXPECT-- +int(1291) +int(10)