refactor for 7.2
authorMichael Wallner <mike@php.net>
Wed, 7 Feb 2018 11:45:52 +0000 (12:45 +0100)
committerMichael Wallner <mike@php.net>
Thu, 8 Feb 2018 12:07:36 +0000 (13:07 +0100)
12 files changed:
scripts/gen_stubs.php
src/php_http_message.c
src/php_http_message_body.c
src/php_http_misc.c
src/php_http_url.c
tests/bug66388.phpt
tests/helper/server.inc
tests/skipif.inc
tests/urlparser004.phpt
tests/urlparser006.phpt
tests/urlparser010.phpt
tests/urlparser012.phpt

index 20a1f0fdd853b35d459090e1a43f33a3e4d6cbf2..5f28545aec073d20b2a8668ffe3db95e1967134c 100755 (executable)
@@ -1,8 +1,11 @@
 #!/usr/bin/env php
 <?php
 
-function m($m) {
+function m($m, $c = null) {
        $n = "";
+       if ($c && $c->isInterface()) {
+               $m ^= ReflectionMethod::IS_ABSTRACT;
+       }
        foreach (Reflection::getModifierNames($m) as $mn) {
                $n .= $mn . " ";
        }
@@ -169,7 +172,7 @@ foreach ($namespaces as $ns) {
 
             foreach ($c->getMethods() as $m) {
                 if ($m->getDeclaringClass()->getName() == $c->getName()) {
-                    fprintf($out, "\t\t%sfunction %s(", m($m->getModifiers()), 
+                    fprintf($out, "\t\t%sfunction %s(", m($m->getModifiers(), $c), 
                             $m->getName());
                     $ps = array();
                     foreach ($m->getParameters() as $p) {
index 413edab57711604aa5350a5b4a4cd506e58a43dc..d076b6aef6173a69e914d24a3135c208535ee083 100644 (file)
@@ -75,7 +75,7 @@ php_http_message_t *php_http_message_init_env(php_http_message_t *message, php_h
                        break;
 
                case PHP_HTTP_RESPONSE:
-                       message = php_http_message_init(NULL, type, NULL);
+                       message = php_http_message_init(message, type, NULL);
                        if (!SG(sapi_headers).http_status_line || !php_http_info_parse((php_http_info_t *) &message->http, SG(sapi_headers).http_status_line)) {
                                if (!(message->http.info.response.code = SG(sapi_headers).http_response_code)) {
                                        message->http.info.response.code = 200;
@@ -538,12 +538,14 @@ static php_http_message_object_prophandler_t *php_http_message_object_get_propha
        return zend_hash_str_find_ptr(&php_http_message_object_prophandlers, name_str->val, name_str->len);
 }
 static void php_http_message_object_prophandler_get_type(php_http_message_object_t *obj, zval *return_value) {
+       zval_ptr_dtor(return_value);
        RETVAL_LONG(obj->message->type);
 }
 static void php_http_message_object_prophandler_set_type(php_http_message_object_t *obj, zval *value) {
        php_http_message_set_type(obj->message, zval_get_long(value));
 }
 static void php_http_message_object_prophandler_get_request_method(php_http_message_object_t *obj, zval *return_value) {
+       zval_ptr_dtor(return_value);
        if (PHP_HTTP_MESSAGE_TYPE(REQUEST, obj->message) && obj->message->http.info.request.method) {
                RETVAL_STRING(obj->message->http.info.request.method);
        } else {
@@ -561,6 +563,7 @@ static void php_http_message_object_prophandler_get_request_url(php_http_message
        char *url_str;
        size_t url_len;
 
+       zval_ptr_dtor(return_value);
        if (PHP_HTTP_MESSAGE_TYPE(REQUEST, obj->message) && obj->message->http.info.request.url && php_http_url_to_string(obj->message->http.info.request.url, &url_str, &url_len, 0)) {
                RETVAL_STR(php_http_cs2zs(url_str, url_len));
        } else {
@@ -573,6 +576,7 @@ static void php_http_message_object_prophandler_set_request_url(php_http_message
        }
 }
 static void php_http_message_object_prophandler_get_response_status(php_http_message_object_t *obj, zval *return_value) {
+       zval_ptr_dtor(return_value);
        if (PHP_HTTP_MESSAGE_TYPE(RESPONSE, obj->message) && obj->message->http.info.response.status) {
                RETVAL_STRING(obj->message->http.info.response.status);
        } else {
@@ -587,6 +591,7 @@ static void php_http_message_object_prophandler_set_response_status(php_http_mes
        }
 }
 static void php_http_message_object_prophandler_get_response_code(php_http_message_object_t *obj, zval *return_value) {
+       zval_ptr_dtor(return_value);
        if (PHP_HTTP_MESSAGE_TYPE(RESPONSE, obj->message)) {
                RETVAL_LONG(obj->message->http.info.response.code);
        } else {
@@ -603,6 +608,7 @@ static void php_http_message_object_prophandler_get_http_version(php_http_messag
        char *version_str;
        size_t version_len;
 
+       zval_ptr_dtor(return_value);
        php_http_version_to_string(&obj->message->http.version, &version_str, &version_len, NULL, NULL);
        RETVAL_STR(php_http_cs2zs(version_str, version_len));
 }
@@ -612,28 +618,43 @@ static void php_http_message_object_prophandler_set_http_version(php_http_messag
        zend_string_release(zs);
 }
 static void php_http_message_object_prophandler_get_headers(php_http_message_object_t *obj, zval *return_value ) {
+       zval tmp;
+
+       ZVAL_COPY_VALUE(&tmp, return_value);
        array_init(return_value);
        array_copy(&obj->message->hdrs, Z_ARRVAL_P(return_value));
+       zval_ptr_dtor(&tmp);
 }
 static void php_http_message_object_prophandler_set_headers(php_http_message_object_t *obj, zval *value) {
        int converted = 0;
+       HashTable garbage, *src;
 
        if (Z_TYPE_P(value) != IS_ARRAY && Z_TYPE_P(value) != IS_OBJECT) {
                converted = 1;
                SEPARATE_ZVAL(value);
                convert_to_array(value);
        }
+       src = HASH_OF(value);
 
-       zend_hash_clean(&obj->message->hdrs);
+       garbage = obj->message->hdrs;
+       zend_hash_init(&obj->message->hdrs, zend_hash_num_elements(src), NULL, ZVAL_PTR_DTOR, 0);
        array_copy(HASH_OF(value), &obj->message->hdrs);
 
+       if (GC_REFCOUNT(&garbage) <= 1 && (garbage.u.flags & HASH_FLAG_INITIALIZED)) {
+               efree(HT_GET_DATA_ADDR(&garbage));
+       }
+
        if (converted) {
                zval_ptr_dtor(value);
        }
 }
 static void php_http_message_object_prophandler_get_body(php_http_message_object_t *obj, zval *return_value) {
        if (obj->body) {
+               zval tmp;
+
+               ZVAL_COPY_VALUE(&tmp, return_value);
                RETVAL_OBJECT(&obj->body->zo, 1);
+               zval_ptr_dtor(&tmp);
        } else {
                RETVAL_NULL();
        }
@@ -643,7 +664,11 @@ static void php_http_message_object_prophandler_set_body(php_http_message_object
 }
 static void php_http_message_object_prophandler_get_parent_message(php_http_message_object_t *obj, zval *return_value) {
        if (obj->message->parent) {
+               zval tmp;
+
+               ZVAL_COPY_VALUE(&tmp, return_value);
                RETVAL_OBJECT(&obj->parent->zo, 1);
+               zval_ptr_dtor(&tmp);
        } else {
                RETVAL_NULL();
        }
@@ -652,10 +677,10 @@ static void php_http_message_object_prophandler_set_parent_message(php_http_mess
        if (Z_TYPE_P(value) == IS_OBJECT && instanceof_function(Z_OBJCE_P(value), php_http_message_class_entry)) {
                php_http_message_object_t *parent_obj = PHP_HTTP_OBJ(NULL, value);
 
+               Z_ADDREF_P(value);
                if (obj->message->parent) {
                        zend_object_release(&obj->parent->zo);
                }
-               Z_ADDREF_P(value);
                obj->parent = parent_obj;
                obj->message->parent = parent_obj->message;
        }
@@ -785,7 +810,6 @@ ZEND_RESULT_CODE php_http_message_object_set_body(php_http_message_object_t *msg
 
        if (!body_obj->body) {
                body_obj->body = php_http_message_body_init(NULL, NULL);
-               php_stream_to_zval(php_http_message_body_stream(body_obj->body), body_obj->gc);
        }
        if (msg_obj->body) {
                zend_object_release(&msg_obj->body->zo);
@@ -878,32 +902,27 @@ static zval *php_http_message_object_read_prop(zval *object, zval *member, int t
        zend_string *member_name = zval_get_string(member);
        php_http_message_object_prophandler_t *handler = php_http_message_object_get_prophandler(member_name);
 
-       if (!handler || type == BP_VAR_R || type == BP_VAR_IS) {
-               return_value = zend_get_std_object_handlers()->read_property(object, member, type, cache_slot, tmp);
+       return_value = zend_get_std_object_handlers()->read_property(object, member, type, cache_slot, tmp);
 
-               if (handler) {
+       if (handler && handler->read) {
+               if (type == BP_VAR_R || type == BP_VAR_IS) {
                        php_http_message_object_t *obj = PHP_HTTP_OBJ(NULL, object);
-                       zval tmp2;
 
-                       PHP_HTTP_MESSAGE_OBJECT_INIT(obj);
-                       handler->read(obj, &tmp2);
-
-                       zval_ptr_dtor(return_value);
-                       ZVAL_COPY_VALUE(return_value, &tmp2);
-               }
-               zend_string_release(member_name);
-               return return_value;
-       } else {
-               php_property_proxy_t *proxy;
-               php_property_proxy_object_t *proxy_obj;
+                       handler->read(obj, return_value);
+               } else {
+                       php_property_proxy_t *proxy;
+                       php_property_proxy_object_t *proxy_obj;
 
-               proxy = php_property_proxy_init(object, member_name);
-               proxy_obj = php_property_proxy_object_new_ex(NULL, proxy);
+                       proxy = php_property_proxy_init(object, member_name);
+                       proxy_obj = php_property_proxy_object_new_ex(NULL, proxy);
 
-               ZVAL_OBJ(tmp, &proxy_obj->zo);
-               zend_string_release(member_name);
-               return tmp;
+                       ZVAL_OBJ(tmp, &proxy_obj->zo);
+                       return_value = tmp;
+               }
        }
+
+       zend_string_release(member_name);
+       return return_value;
 }
 
 static void php_http_message_object_write_prop(zval *object, zval *member, zval *value, void **cache_slot)
index 18ff936c8df5f1dddc4b235758630d07e5116bb3..e630176176f92e33c1765574615eda197179994c 100644 (file)
@@ -91,7 +91,7 @@ void php_http_message_body_free(php_http_message_body_t **body_ptr)
        if (*body_ptr) {
                php_http_message_body_t *body = *body_ptr;
                if (!--body->refcount) {
-                       zend_list_close(body->res);
+                       zend_list_delete(body->res);
                        body->res = NULL;
                        PTR_FREE(body->boundary);
                        efree(body);
index 064598cea3db9c992f9d1685990fe1178fd537dd..467988bd1043e738f66ff69a380698d5c0dfaffb 100644 (file)
@@ -87,7 +87,7 @@ int php_http_match(const char *haystack_str, const char *needle_str, int flags)
        return result;
 }
 
-char *php_http_pretty_key(register char *key, size_t key_len, zend_bool uctitle, zend_bool xhyphen)
+char *php_http_pretty_key(char *key, size_t key_len, zend_bool uctitle, zend_bool xhyphen)
 {
        size_t i = 1;
        int wasalpha;
index 361e61c514486d5ed9d979e1f9cb0fbeb341dcb3..0e3b2ee48e262930a2ce85be3f93d6a4814e42d6 100644 (file)
@@ -663,7 +663,7 @@ php_http_url_t *php_http_url_copy(const php_http_url_t *url, zend_bool persisten
        return cpy;
 }
 
-static size_t parse_mb_utf8(unsigned *wc, const char *ptr, const char *end)
+static inline size_t parse_mb_utf8(unsigned *wc, const char *ptr, const char *end)
 {
        unsigned wchar;
        size_t consumed = utf8towc(&wchar, (const unsigned char *) ptr, end - ptr);
@@ -679,7 +679,7 @@ static size_t parse_mb_utf8(unsigned *wc, const char *ptr, const char *end)
 }
 
 #if PHP_HTTP_HAVE_WCHAR
-static size_t parse_mb_loc(unsigned *wc, const char *ptr, const char *end)
+static inline size_t parse_mb_loc(unsigned *wc, const char *ptr, const char *end)
 {
        wchar_t wchar;
        size_t consumed = 0;
@@ -723,7 +723,7 @@ static const char * const parse_what[] = {
 
 static const char parse_xdigits[] = "0123456789ABCDEF";
 
-static size_t parse_mb(struct parse_state *state, parse_mb_what_t what, const char *ptr, const char *end, const char *begin, zend_bool force_silent)
+static inline size_t parse_mb(struct parse_state *state, parse_mb_what_t what, const char *ptr, const char *end, const char *begin, zend_bool force_silent)
 {
        unsigned wchar;
        size_t consumed = 0;
index 97f8419603369e152c0bbbd078d276c4016beff9..df53d9c0c0d40570bc6ddcb0ab20ced21d73580e 100644 (file)
@@ -25,6 +25,7 @@ server("proxy.inc", function($port) {
                        'Content-Length' => 0
                )
        );
+       $client->setOptions(["timeout" => 30]);
        $client->enqueue($request);
        echo $client->send()->getResponse()->getResponseCode();
 });
index 78a63eee3098f71de890ad2dce7e88956b4ecda5..af71a0e2a66f2244ed350f0801e46fa5cb1e6aed 100644 (file)
@@ -95,9 +95,9 @@ function nghttpd($cb) {
                        $stdout = $pipes[1];
                        $stderr = $pipes[2];
                        
-                       usleep(50000);
+                       sleep(1);
                        $status = proc_get_status($proc);
-                       
+                       logger("nghttpd: %s", new http\Params($status));
                        if (!$status["running"]) {
                                continue;
                        }
@@ -121,6 +121,7 @@ function nghttpd($cb) {
 function proc($bin, $args, $cb) {
        $spec = array(array("pipe","r"), array("pipe","w"), array("pipe","w"));
        $comm = escapeshellcmd($bin) . " ". implode(" ", array_map("escapeshellarg", $args));
+       logger("proc: %s %s", $bin, implode(" ", $args));
        if (($proc = proc_open($comm, $spec, $pipes, __DIR__))) {
                $stdin = $pipes[0];
                $stdout = $pipes[1];
index 4844defba0ad07ea61918f1aa4c023d1ed9a95d5..a9e161ab48722e20c0e57741fb1226effab20101 100644 (file)
@@ -1,7 +1,23 @@
 <?php
-function _ext($ext) { extension_loaded($ext) or die("skip $ext extension needed\n"); }
 _ext("http");
 
+function _ext($ext) { 
+       if (!extension_loaded($ext)) {
+               die("skip $ext extension needed\n");
+       }
+}
+
+function utf8locale() {
+       if (stristr(setlocale(LC_CTYPE, "C.UTF-8"), "utf")) {
+               return true;
+       }
+       $locale = setlocale(LC_CTYPE, null);
+       if (stristr($locale, "utf") && substr($locale, -1) === "8") {
+               return true;
+       }
+       return false;
+}
+
 function skip_online_test($message = "skip test requiring internet connection\n") {
        if (getenv("SKIP_ONLINE_TESTS")) {
                die($message);
@@ -33,4 +49,4 @@ function skip_http2_test($message = "skip need http2 support") {
                }
        }
        die("$message (nghttpd in PATH)\n");
-}
\ No newline at end of file
+}
index 9172138eeb971b7330ae7a401a047f37e2712cf5..36d6983eed9e09bb4fc65f1331b42d5358c65621 100644 (file)
@@ -4,7 +4,7 @@ url parser multibyte/locale
 <?php
 include "skipif.inc";
 if (!defined("http\\Url::PARSE_MBLOC") or
-       !stristr(setlocale(LC_CTYPE, "C.UTF-8"), "utf")) {
+       !utf8locale()) {
        die("skip need http\\Url::PARSE_MBLOC support and LC_CTYPE=*.UTF-8");
 }
 ?>
index d701bf57c64b9b0db356d5af96b8dbb4ce4cd467..e047ada501481cd9bd3acefc53d7bfe768833107 100644 (file)
@@ -5,7 +5,7 @@ url parser multibyte/locale/idna
 include "skipif.inc";
 if (!defined("http\\Url::PARSE_MBLOC") or
        !defined("http\\Url::PARSE_TOIDN_2003") or
-       !stristr(setlocale(LC_CTYPE, "C.UTF-8"), ".utf")) {
+       !utf8locale()) {
        die("skip need http\\Url::PARSE_MBLOC|http\\Url::PARSE_TOIDN_2003 support and LC_CTYPE=*.UTF-8");
 }
 ?>
index e1675ce409f3985acce0f6af9be3767e4bd884bf..f5382085e17a481ac626c3fa0a50a75bdeb9058e 100644 (file)
@@ -4,7 +4,7 @@ url parser multibyte/locale/topct
 <?php
 include "skipif.inc";
 if (!defined("http\\Url::PARSE_MBLOC") or
-       !stristr(setlocale(LC_CTYPE, "C.UTF-8"), ".utf")) {
+       !utf8locale()) {
        die("skip need http\\Url::PARSE_MBLOC support and LC_CTYPE=*.UTF-8");
 }
 
index 5f8efae457f0b15e6105d385868fa49303e18db6..d80cd1313556649e049ca4ba34f9aa3e5548394c 100644 (file)
@@ -5,7 +5,7 @@ url parser multibyte/locale/topct
 include "skipif.inc";
 if (!defined("http\\Url::PARSE_MBLOC") or
        !defined("http\\Url::PARSE_TOIDN") or
-       !stristr(setlocale(LC_CTYPE, "C.UTF-8"), ".utf")) {
+       !utf8locale()) {
        die("skip need http\\Url::PARSE_MBLOC|http\Url::PARSE_TOIDN support and LC_CTYPE=*.UTF-8");
 }