X-Git-Url: https://git.m6w6.name/?p=m6w6%2Fext-http;a=blobdiff_plain;f=http_message_object.c;h=18d3793dea0d90a55216af845a9eefdff253f168;hp=99bc2768df149988b7197ceecf2218ead8c5e70f;hb=76d019d55561c397209d49f7d594f2cfe022cdf9;hpb=89572c25844ea2a641a6bef11b2cd1e1be699282 diff --git a/http_message_object.c b/http_message_object.c index 99bc276..18d3793 100644 --- a/http_message_object.c +++ b/http_message_object.c @@ -30,58 +30,61 @@ #include "php_http_exception_object.h" #include "phpstr/phpstr.h" +#include "missing.h" -#define HTTP_BEGIN_ARGS(method, req_args) HTTP_BEGIN_ARGS_EX(HttpMessage, method, ZEND_RETURN_REFERENCE_AGNOSTIC, req_args) -#define HTTP_EMPTY_ARGS(method, ret_ref) HTTP_EMPTY_ARGS_EX(HttpMessage, method, ret_ref) -#define HTTP_MESSAGE_ME(method, visibility) PHP_ME(HttpMessage, method, HTTP_ARGS(HttpMessage, method), visibility) +ZEND_EXTERN_MODULE_GLOBALS(http); -HTTP_BEGIN_ARGS(__construct, 0) +#define HTTP_BEGIN_ARGS(method, ret_ref, req_args) HTTP_BEGIN_ARGS_EX(HttpMessage, method, ret_ref, req_args) +#define HTTP_EMPTY_ARGS(method, ret_ref) HTTP_EMPTY_ARGS_EX(HttpMessage, method, ret_ref) +#define HTTP_MESSAGE_ME(method, visibility) PHP_ME(HttpMessage, method, HTTP_ARGS(HttpMessage, method), visibility) + +HTTP_BEGIN_ARGS(__construct, 0, 0) HTTP_ARG_VAL(message, 0) HTTP_END_ARGS; -HTTP_BEGIN_ARGS(fromString, 1) +HTTP_BEGIN_ARGS(fromString, 1, 1) HTTP_ARG_VAL(message, 0) HTTP_END_ARGS; HTTP_EMPTY_ARGS(getBody, 0); HTTP_EMPTY_ARGS(getHeaders, 0); -HTTP_BEGIN_ARGS(setHeaders, 1) +HTTP_BEGIN_ARGS(setHeaders, 0, 1) HTTP_ARG_VAL(headers, 0) HTTP_END_ARGS; -HTTP_BEGIN_ARGS(addHeaders, 1) +HTTP_BEGIN_ARGS(addHeaders, 0, 1) HTTP_ARG_VAL(headers, 0) HTTP_ARG_VAL(append, 0) HTTP_END_ARGS; HTTP_EMPTY_ARGS(getType, 0); -HTTP_BEGIN_ARGS(setType, 1) +HTTP_BEGIN_ARGS(setType, 0, 1) HTTP_ARG_VAL(type, 0) HTTP_END_ARGS; HTTP_EMPTY_ARGS(getResponseCode, 0); -HTTP_BEGIN_ARGS(setResponseCode, 1) +HTTP_BEGIN_ARGS(setResponseCode, 0, 1) HTTP_ARG_VAL(response_code, 0) HTTP_END_ARGS; HTTP_EMPTY_ARGS(getRequestMethod, 0); -HTTP_BEGIN_ARGS(setRequestMethod, 1) +HTTP_BEGIN_ARGS(setRequestMethod, 0, 1) HTTP_ARG_VAL(request_method, 0) HTTP_END_ARGS; HTTP_EMPTY_ARGS(getRequestUri, 0); -HTTP_BEGIN_ARGS(setRequestUri, 1) +HTTP_BEGIN_ARGS(setRequestUri, 0, 1) HTTP_ARG_VAL(uri, 0) HTTP_END_ARGS; HTTP_EMPTY_ARGS(getHttpVersion, 0); -HTTP_BEGIN_ARGS(setHttpVersion, 1) +HTTP_BEGIN_ARGS(setHttpVersion, 0, 1) HTTP_ARG_VAL(http_version, 0) HTTP_END_ARGS; HTTP_EMPTY_ARGS(getParentMessage, 1); HTTP_EMPTY_ARGS(send, 0); -HTTP_BEGIN_ARGS(toString, 0) +HTTP_BEGIN_ARGS(toString, 0, 0) HTTP_ARG_VAL(include_parent, 0) HTTP_END_ARGS; @@ -136,6 +139,7 @@ void _http_message_object_init(INIT_FUNC_ARGS) http_message_object_handlers.read_property = http_message_object_read_prop; http_message_object_handlers.write_property = http_message_object_write_prop; http_message_object_handlers.get_properties = http_message_object_get_props; + http_message_object_handlers.get_property_ptr_ptr = NULL; } zend_object_value _http_message_object_new(zend_class_entry *ce TSRMLS_DC) @@ -164,7 +168,7 @@ zend_object_value _http_message_object_new_ex(zend_class_entry *ce, http_message ALLOC_HASHTABLE(OBJ_PROP(o)); zend_hash_init(OBJ_PROP(o), 0, NULL, ZVAL_PTR_DTOR, 0); - ov.handle = zend_objects_store_put(o, (zend_objects_store_dtor_t) zend_objects_destroy_object, http_message_object_free, NULL TSRMLS_CC); + ov.handle = putObject(http_message_object, o); ov.handlers = &http_message_object_handlers; return ov; @@ -179,6 +183,10 @@ static inline void _http_message_object_declare_default_properties(TSRMLS_D) { zend_class_entry *ce = http_message_object_ce; + DCL_CONST(long, "NONE", HTTP_MSG_NONE); + DCL_CONST(long, "REQUEST", HTTP_MSG_REQUEST); + DCL_CONST(long, "RESPONSE", HTTP_MSG_RESPONSE); + DCL_PROP(PROTECTED, long, type, HTTP_MSG_NONE); DCL_PROP(PROTECTED, string, body, ""); DCL_PROP(PROTECTED, string, requestMethod, ""); @@ -216,12 +224,15 @@ static zval *_http_message_object_read_prop(zval *object, zval *member, int type http_message *msg = obj->message; zval *return_value; - /* tmp var */ - ALLOC_ZVAL(return_value); + return_value = &EG(uninitialized_zval); return_value->refcount = 0; + return_value->is_ref = 0; +#if 0 + fprintf(stderr, "Read HttpMessage::$%s\n", Z_STRVAL_P(member)); +#endif if (!EG(scope) || !instanceof_function(EG(scope), obj->zo.ce TSRMLS_CC)) { - zend_error(E_WARNING, "Cannot access protected property %s::$%s", obj->zo.ce->name, Z_STRVAL_P(member)); + zend_error(HE_WARNING, "Cannot access protected property %s::$%s", obj->zo.ce->name, Z_STRVAL_P(member)); return EG(uninitialized_zval_ptr); } @@ -255,8 +266,18 @@ static zval *_http_message_object_read_prop(zval *object, zval *member, int type break; case HTTP_MSG_PROPHASH_HEADERS: - array_init(return_value); - zend_hash_copy(Z_ARRVAL_P(return_value), &msg->hdrs, (copy_ctor_func_t) zval_add_ref, NULL, sizeof(zval *)); + /* This is needed for situations like + * $this->headers['foo'] = 'bar'; + */ + if (type == BP_VAR_W) { + return_value->refcount = 1; + return_value->is_ref = 1; + Z_TYPE_P(return_value) = IS_ARRAY; + Z_ARRVAL_P(return_value) = &msg->hdrs; + } else { + array_init(return_value); + zend_hash_copy(Z_ARRVAL_P(return_value), &msg->hdrs, (copy_ctor_func_t) zval_add_ref, NULL, sizeof(zval *)); + } break; case HTTP_MSG_PROPHASH_PARENT_MESSAGE: @@ -307,15 +328,18 @@ static void _http_message_object_write_prop(zval *object, zval *member, zval *va getObjectEx(http_message_object, obj, object); http_message *msg = obj->message; +#if 0 + fprintf(stderr, "Write HttpMessage::$%s\n", Z_STRVAL_P(member)); +#endif if (!EG(scope) || !instanceof_function(EG(scope), obj->zo.ce TSRMLS_CC)) { - zend_error(E_WARNING, "Cannot access protected property %s::$%s", obj->zo.ce->name, Z_STRVAL_P(member)); + zend_error(HE_WARNING, "Cannot access protected property %s::$%s", obj->zo.ce->name, Z_STRVAL_P(member)); } switch (zend_get_hash_value(Z_STRVAL_P(member), Z_STRLEN_P(member) + 1)) { case HTTP_MSG_PROPHASH_TYPE: convert_to_long_ex(&value); - if (Z_LVAL_P(value) != msg->type) { + if ((http_message_type) Z_LVAL_P(value) != msg->type) { if (HTTP_MSG_TYPE(REQUEST, msg)) { if (msg->info.request.method) { efree(msg->info.request.method); @@ -631,7 +655,7 @@ PHP_METHOD(HttpMessage, getResponseCode) getObject(http_message_object, obj); if (!HTTP_MSG_TYPE(RESPONSE, obj->message)) { - http_error(E_NOTICE, HTTP_E_MSG, "HttpMessage is not of type HTTP_MSG_RESPONSE"); + http_error(HE_NOTICE, HTTP_E_MESSAGE_TYPE, "HttpMessage is not of type HTTP_MSG_RESPONSE"); RETURN_NULL(); } @@ -652,7 +676,7 @@ PHP_METHOD(HttpMessage, setResponseCode) getObject(http_message_object, obj); if (!HTTP_MSG_TYPE(RESPONSE, obj->message)) { - http_error(E_WARNING, HTTP_E_MSG, "HttpMessage is not of type HTTP_MSG_RESPONSE"); + http_error(HE_WARNING, HTTP_E_MESSAGE_TYPE, "HttpMessage is not of type HTTP_MSG_RESPONSE"); RETURN_FALSE; } @@ -660,7 +684,7 @@ PHP_METHOD(HttpMessage, setResponseCode) RETURN_FALSE; } if (code < 100 || code > 510) { - http_error_ex(E_WARNING, HTTP_E_PARAM, "Invalid response code (100-510): %ld", code); + http_error_ex(HE_WARNING, HTTP_E_INVALID_PARAM, "Invalid response code (100-510): %ld", code); RETURN_FALSE; } @@ -682,7 +706,7 @@ PHP_METHOD(HttpMessage, getRequestMethod) getObject(http_message_object, obj); if (!HTTP_MSG_TYPE(REQUEST, obj->message)) { - http_error(E_NOTICE, HTTP_E_MSG, "HttpMessage is not of type HTTP_MSG_REQUEST"); + http_error(HE_NOTICE, HTTP_E_MESSAGE_TYPE, "HttpMessage is not of type HTTP_MSG_REQUEST"); RETURN_NULL(); } @@ -703,7 +727,7 @@ PHP_METHOD(HttpMessage, setRequestMethod) getObject(http_message_object, obj); if (!HTTP_MSG_TYPE(REQUEST, obj->message)) { - http_error(E_WARNING, HTTP_E_MSG, "HttpMessage is not of type HTTP_MSG_REQUEST"); + http_error(HE_WARNING, HTTP_E_MESSAGE_TYPE, "HttpMessage is not of type HTTP_MSG_REQUEST"); RETURN_FALSE; } @@ -711,11 +735,11 @@ PHP_METHOD(HttpMessage, setRequestMethod) RETURN_FALSE; } if (method_len < 1) { - http_error(E_WARNING, HTTP_E_PARAM, "Cannot set HttpMessage::requestMethod to an empty string"); + http_error(HE_WARNING, HTTP_E_INVALID_PARAM, "Cannot set HttpMessage::requestMethod to an empty string"); RETURN_FALSE; } if (SUCCESS != http_check_method(method)) { - http_error_ex(E_WARNING, HTTP_E_PARAM, "Unkown request method: %s", method); + http_error_ex(HE_WARNING, HTTP_E_REQUEST_METHOD, "Unkown request method: %s", method); RETURN_FALSE; } @@ -736,7 +760,7 @@ PHP_METHOD(HttpMessage, getRequestUri) getObject(http_message_object, obj); if (!HTTP_MSG_TYPE(REQUEST, obj->message)) { - http_error(E_WARNING, HTTP_E_MSG, "HttpMessage is not of type HTTP_MSG_REQUEST"); + http_error(HE_WARNING, HTTP_E_MESSAGE_TYPE, "HttpMessage is not of type HTTP_MSG_REQUEST"); RETURN_NULL(); } @@ -758,14 +782,14 @@ PHP_METHOD(HttpMessage, setRequestUri) getObject(http_message_object, obj); if (!HTTP_MSG_TYPE(REQUEST, obj->message)) { - http_error(E_WARNING, HTTP_E_MSG, "HttpMessage is not of type HTTP_MSG_REQUEST"); + http_error(HE_WARNING, HTTP_E_MESSAGE_TYPE, "HttpMessage is not of type HTTP_MSG_REQUEST"); RETURN_FALSE; } if (SUCCESS != zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "s", &URI, &URIlen)) { RETURN_FALSE; } if (URIlen < 1) { - http_error(E_WARNING, HTTP_E_PARAM, "Cannot set HttpMessage::requestUri to an empty string"); + http_error(HE_WARNING, HTTP_E_INVALID_PARAM, "Cannot set HttpMessage::requestUri to an empty string"); RETURN_FALSE; } @@ -784,7 +808,7 @@ PHP_METHOD(HttpMessage, getHttpVersion) IF_RETVAL_USED { char ver[4] = {0}; - float version; + double version; getObject(http_message_object, obj); switch (obj->message->type) @@ -801,7 +825,7 @@ PHP_METHOD(HttpMessage, getHttpVersion) default: RETURN_NULL(); } - sprintf(ver, "%1.1f", version); + sprintf(ver, "%1.1lf", version); RETURN_STRINGL(ver, 3, 1); } } @@ -823,21 +847,21 @@ PHP_METHOD(HttpMessage, setHttpVersion) } if (HTTP_MSG_TYPE(NONE, obj->message)) { - http_error(E_WARNING, HTTP_E_MSG, "Message is neither of type HTTP_MSG_RESPONSE nor HTTP_MSG_REQUEST"); + http_error(HE_WARNING, HTTP_E_MESSAGE_TYPE, "Message is neither of type HTTP_MSG_RESPONSE nor HTTP_MSG_REQUEST"); RETURN_FALSE; } convert_to_double(zv); - sprintf(v, "%1.1f", Z_DVAL_P(zv)); + sprintf(v, "%1.1lf", Z_DVAL_P(zv)); if (strcmp(v, "1.0") && strcmp(v, "1.1")) { - http_error_ex(E_WARNING, HTTP_E_PARAM, "Invalid HTTP protocol version (1.0 or 1.1): %s", v); + http_error_ex(HE_WARNING, HTTP_E_INVALID_PARAM, "Invalid HTTP protocol version (1.0 or 1.1): %s", v); RETURN_FALSE; } if (HTTP_MSG_TYPE(RESPONSE, obj->message)) { - obj->message->info.response.http_version = (float) Z_DVAL_P(zv); + obj->message->info.response.http_version = Z_DVAL_P(zv); } else { - obj->message->info.request.http_version = (float) Z_DVAL_P(zv); + obj->message->info.request.http_version = Z_DVAL_P(zv); } RETURN_TRUE; }