├── DIFF.md ├── README.md ├── TODO.md └── phpc.h /DIFF.md: -------------------------------------------------------------------------------- 1 | # Difference between PHP 5 and PHP 7 2 | 3 | ## Object 4 | 5 | ### Common 6 | - get object from `zval`s 7 | - 5: zend_object_store_get_object(d1 TSRMLS_CC) 8 | - 7: from offset : `(php_object_struct *)((char*)(obj) - XtOffsetOf(php_object_struct, std))` 9 | 10 | 11 | ### Handlers 12 | - extra handlers in 7 13 | - `handlers.offset = XtOffsetOf(php_object_struct, std)` 14 | - `handlers.free_obj = object_free_storage_function 15 | 16 | #### create_object_ex (ex method for clone and new) 17 | - return 18 | - 5: `zend_object_value (retval)` 19 | - 7: `zend_object * (&intern->std)` 20 | - intern 21 | - 5: `calloc(1, sizeof(php_object_struct))` 22 | - 7: `ecalloc(1, sizeof(php_object_struct) + sizeof(zval) * (class_type->default_properties_count - 1))` 23 | - init props 24 | - 5: always 25 | - 7: only for new object (not for clone) 26 | - save new intern 27 | - 5: for clone 28 | - 7: never (it's taken from offset) 29 | - handlers 30 | - 5: `retval.handlers` 31 | - 7: `intern->std.handlers` 32 | - object store 33 | - 5: `zend_objects_store_put(intern, (zend_objects_store_dtor_t)zend_objects_destroy_object, (zend_objects_free_object_storage_t) object_free_storage_function, NULL TSRMLS_CC)` 34 | - 7: none (it's set in init) 35 | 36 | #### create_object 37 | - return 38 | - 5: `zend_object_value (retval)` 39 | - 7: `zend_object * (&intern->std)` 40 | - 2nd argument 41 | - 5: NULL (intern reference) 42 | - 7: 1 (whether to init props) 43 | 44 | #### clone_obj 45 | - return 46 | - 5: `zend_object_value (retval)` 47 | - 7: `zend_object * (&intern->std)` 48 | - new object : `new_obj` 49 | - 5: reference arg to create_object_ex 50 | - 7: XtOffsetOf of the create_object_ex result 51 | - new object value : `new_ov` 52 | - 5: result of create_object_ex 53 | - 7: none 54 | - clone members 55 | - 5: `zend_objects_clone_members(&new_obj->std, new_ov, &old_obj->std, Z_OBJ_HANDLE_P(this_ptr) TSRMLS_CC)` 56 | - 7: `zend_objects_clone_members(&new_obj->std, &old_obj->std TSRMLS_CC)` 57 | 58 | #### compare_object 59 | - get object from `zval`s (see above) 60 | 61 | #### get_gc 62 | - table pointer (second argument) 63 | - 5: `zval ***table` 64 | - 7: `zval **table` 65 | 66 | #### get_properties 67 | - modifying existing props from `zend_std_get_properties` 68 | - 5: `zval *`: use `MAKE_STD_ZVAL` and then save 69 | - 7: `zval`: save as it is 70 | 71 | #### free_storage 72 | - get object from `zval`s (see above) 73 | - free object 74 | - 5: `efree(intern)` 75 | - 7: do nothing 76 | 77 | #### get_property_ptr_ptr 78 | - return 79 | - 5: `zval **`: ptr of ptr to the engine zval or NULL if overloaded 80 | - 7: `zval *`: ptr to engine zval or NULL if overloaded 81 | - 4th parameter 82 | - 5: `const zend_literal *key` 83 | - 7: `void **cache_slot` 84 | - member name handling (2nd param) 85 | - 5: convert it to string zval if needed and free it if conversion changed zval 86 | - 7: get zend_string from zval and release the string at the end 87 | 88 | #### read_property 89 | - return 90 | - 5: `zval **`: ptr of ptr to the engine zval or NULL if overloaded 91 | - 7: `zval *`: ptr to engine zval or NULL if overloaded 92 | - 4th parameter 93 | - 5: `const zend_literal *key` 94 | - 7: `void **cache_slot` 95 | - extra `zval *rv` last (5th) parameter in 7 96 | - the same as zend_read_property 97 | - also when calling std handler 98 | - member name handling (2nd param) 99 | - 5: convert it to string zval if needed and free it if conversion changed zval 100 | - 7: get zend_string from zval and release the string at the end 101 | - we need to ensure in 5 that retval is temporary variable 102 | - `Z_SET_REFCOUNT_P(retval, 0); Z_UNSET_ISREF_P(retval);` 103 | 104 | 105 | ### Methods 106 | - all have the common issue for getting object from zval (see above) 107 | 108 | ### __construct 109 | - 7: It is possible to call `ZEND_CTOR_MAKE_NULL()` if init fails 110 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # PHP Compatibility layer 2 | 3 | A header for PHP extensions that will allow writing code for PHP 5 and PHP 7 without using too many `ifdef` compiler conditions. 4 | 5 | See [the TODO list](TODO.md) for more details about planned features. -------------------------------------------------------------------------------- /TODO.md: -------------------------------------------------------------------------------- 1 | # TODO list 2 | 3 | ## conversion 4 | - phpc_convert_to_string_ex -> phpc_convert_to_string 5 | 6 | ## ZPP (phpc_parse_parameters) 7 | - P, S (is it needed?) 8 | - Z is not supported 9 | 10 | ## HashTable 11 | - wrap util functions 12 | - zend_hash_merge 13 | - zend_hash_sort 14 | - zend_hash_compare 15 | - zend_hash_minmax 16 | - add apply functions 17 | - zend_hash_apply 18 | - zend_hash_apply_with_argument 19 | - zend_hash_apply_with_arguments 20 | - add possibility to duplicate key 21 | - zend_hash_get_current_key_ex 22 | 23 | ## Object 24 | - Address all differences in [the DIFF list](DIFF.md) 25 | -------------------------------------------------------------------------------- /phpc.h: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2014-2016 Jakub Zelenka. All rights reserved. 3 | * 4 | * Permission is hereby granted, free of charge, to any person obtaining a 5 | * copy of this software and associated documentation files (the "Software"), 6 | * to deal in the Software without restriction, including without limitation 7 | * the rights to use, copy, modify, merge, publish, distribute, sublicense, 8 | * and/or sell copies of the Software, and to permit persons to whom the 9 | * Software is furnished to do so, subject to the following conditions: 10 | * 11 | * The above copyright notice and this permission notice shall be included in 12 | * all copies or substantial portions of the Software. 13 | * 14 | * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 15 | * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 16 | * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 17 | * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 18 | * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING 19 | * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER 20 | * DEALINGS IN THE SOFTWARE. 21 | * 22 | */ 23 | 24 | 25 | #ifndef PHPC_H 26 | #define PHPC_H 27 | 28 | #if PHP_VERSION_ID < 50199 29 | #error "Only PHP 5.2+ supported" 30 | #endif 31 | 32 | /* no operation */ 33 | #define PHPC_NOOP ((void) 0) 34 | 35 | /* COMMON (used definitions) */ 36 | 37 | /* common object macros */ 38 | #define PHPC_CLASS_TYPE _phpc_class_type 39 | #define PHPC_SELF _phpc_self 40 | #define PHPC_OBJ_STRUCT_NAME(_name) struct _phpc_##_name##__obj 41 | #define PHPC_OBJ_STRUCT_DECLARE(_name, _ptr) PHPC_OBJ_STRUCT_NAME(_name) *_ptr 42 | #define PHPC_OBJ_GET_HANDLER_FCE(_name, _type) _name##__##_type 43 | #define PHPC_OBJ_DEFINE_HANDLER_FCE(_rtype, _name, _type) \ 44 | static _rtype PHPC_OBJ_GET_HANDLER_FCE(_name, _type) 45 | #define PHPC_OBJ_GET_HANDLER_FCE_INLINE_DEF(_rtype, _name, _type) \ 46 | PHPC_OBJ_DEFINE_HANDLER_FCE(inline _rtype, _name, _type) 47 | #define PHPC_OBJ_GET_HANDLER_VAR_NAME(_name) _phpc_##_name##__handlers 48 | #define PHPC_OBJ_DEFINE_HANDLER_VAR(_name) \ 49 | static zend_object_handlers PHPC_OBJ_GET_HANDLER_VAR_NAME(_name) 50 | #define PHPC_OBJ_INIT_HANDLERS(_name) \ 51 | memcpy(&PHPC_OBJ_GET_HANDLER_VAR_NAME(_name), \ 52 | zend_get_std_object_handlers(), sizeof(zend_object_handlers)) 53 | 54 | /* for arginfo */ 55 | #ifndef ZEND_BEGIN_ARG_WITH_TENTATIVE_RETURN_TYPE_INFO_EX 56 | #define ZEND_BEGIN_ARG_WITH_TENTATIVE_RETURN_TYPE_INFO_EX(name, return_reference, required_num_args, type, allow_null) \ 57 | ZEND_BEGIN_ARG_INFO_EX(name, 0, return_reference, required_num_args) 58 | #endif 59 | 60 | /* ZEND_ACC_CTOR and ZEND_ACC_DTOR is removed in 7.4 */ 61 | #ifndef ZEND_ACC_CTOR 62 | #define ZEND_ACC_CTOR 0 63 | #endif 64 | #ifndef ZEND_ACC_DTOR 65 | #define ZEND_ACC_DTOR 0 66 | #endif 67 | 68 | #if PHP_VERSION_ID < 50299 69 | #define phpc_function_entry zend_function_entry 70 | #else 71 | #define phpc_function_entry const zend_function_entry 72 | #endif 73 | 74 | #if PHP_VERSION_ID < 50399 75 | /* initializing properties in obejct (object_properties_init was added in PHP 5.4) */ 76 | #define PHPC_OBJ_PROPERTIES_INIT(_zo, _class_type) \ 77 | do { \ 78 | zval *_phpc_tmp; \ 79 | zend_hash_copy((*(_zo)).properties, \ 80 | &(_class_type)->default_properties, \ 81 | (copy_ctor_func_t) zval_add_ref, \ 82 | (void *) &_phpc_tmp, \ 83 | sizeof(zval *)); \ 84 | } while(0) 85 | 86 | /* write property */ 87 | #define PHPC_OBJ_STD_WRITE_PROPERTY(_obj, _member, _value) \ 88 | Z_OBJ_HT_P(_obj)->write_property(_obj, _member, _value TSRMLS_CC) 89 | #else 90 | #define PHPC_OBJ_PROPERTIES_INIT object_properties_init 91 | #define PHPC_OBJ_STD_WRITE_PROPERTY(_obj, _member, _value) \ 92 | zend_std_write_property(_obj, _member, _value, NULL TSRMLS_CC) 93 | #endif 94 | 95 | /* common fcall macros */ 96 | #define PHPC_FCALL_PARAMS_NAME(_pname) _phpc_fcall_params__ ## _pname 97 | 98 | /* integer conversions */ 99 | #define PHPC_CONVERT_NUMBER(_pn, _n, _exc_over, _exc_under, _type_from, _type_to, _max, _min) \ 100 | if (_pn > (_type_from) _max) { \ 101 | _exc_over; \ 102 | } else if (_pn < (_type_from) _min) { \ 103 | _exc_under; \ 104 | } \ 105 | _n = (_type_to) _pn 106 | 107 | #define PHPC_CONVERT_NUMBER_SIGNED(_pn, _n, _exc_over, _type_from, _type_to, _max) \ 108 | if (_pn > (_type_from) _max) { \ 109 | _exc_over; \ 110 | } \ 111 | _n = (_type_to) _pn 112 | 113 | #define PHPC_LONG_TO_INT_EX2(_plv, _lv, _exc_over, _exc_under) \ 114 | PHPC_CONVERT_NUMBER(_plv, _lv, _exc_over, _exc_under, long, int, INT_MAX, INT_MIN) 115 | #define PHPC_LONG_TO_INT_EX(_plv, _lv, _exc) \ 116 | PHPC_LONG_TO_INT_EX2(_plv, _lv, _exc, _exc) 117 | #define PHPC_LONG_TO_INT(_plv, _lv) \ 118 | PHPC_LONG_TO_INT_EX2(_plv, _lv, _lv = INT_MAX, _lv = INT_MIN) 119 | 120 | 121 | #if PHP_MAJOR_VERSION < 8 122 | /* PHP 5 and 7 */ 123 | /* object */ 124 | #define phpc_obj_t zval 125 | #define PHPC_OBJ_TO_POBJ(_obj) Z_OBJ_P(_obj) 126 | #define PHPC_OBJ_FOR_PROP(_obj) (_obj) 127 | #define PHPC_OBJ_HANDLER_COMPARE_NAME compare_objects 128 | 129 | #define PHPC_FCALL_FCI_INIT(_fci, _callback, _count, _no_separ) \ 130 | do { \ 131 | (_fci).params = PHPC_FCALL_PARAMS_NAME(_callback); \ 132 | (_fci).param_count = (_count); \ 133 | (_fci).no_separation = (_no_separ); \ 134 | } while (0) 135 | #else 136 | /* PHP 8 */ 137 | 138 | /* object */ 139 | #define phpc_obj_t zend_object 140 | #define PHPC_OBJ_TO_POBJ(_obj) (_obj) 141 | #define PHPC_OBJ_FOR_PROP(_obj) Z_OBJ_P(_obj) 142 | #define PHPC_OBJ_HANDLER_COMPARE_NAME compare 143 | 144 | /* fcall */ 145 | #define PHPC_FCALL_FCI_INIT(_fci, _callback, _count, _no_separ) \ 146 | do { \ 147 | (_fci).params = PHPC_FCALL_PARAMS_NAME(_callback); \ 148 | (_fci).param_count = (_count); \ 149 | } while (0) 150 | /* ZTS */ 151 | #define TSRMLS_D void 152 | #define TSRMLS_DC 153 | #define TSRMLS_C 154 | #define TSRMLS_CC 155 | #define TSRMLS_FETCH() 156 | #endif 157 | 158 | #define PHPC_OBJ_STD_GET_PROPERTIES(_obj) \ 159 | zend_std_get_properties((_obj) TSRMLS_CC) 160 | 161 | 162 | #if PHP_MAJOR_VERSION == 5 163 | 164 | /* MODULE */ 165 | 166 | #ifdef ZTS 167 | #define PHPC_MODULE_GLOBALS_ACCESSOR(_module, _v) \ 168 | TSRMG(_module ## _globals_id, zend_ ## _module ## _globals *, _v) 169 | #else 170 | #define PHPC_MODULE_GLOBALS_ACCESSOR(_module, _v) \ 171 | (_module ## _globals._v) 172 | #endif 173 | 174 | #define PHPC_MODULE_HAS_THREAD_CACHE 0 175 | 176 | 177 | /* INTEGER */ 178 | 179 | /* long type */ 180 | typedef long phpc_long_t; 181 | /* unsigned long type */ 182 | typedef unsigned long phpc_ulong_t; 183 | /* offset type */ 184 | typedef off_t phpc_off_t; 185 | /* string length type */ 186 | typedef int phpc_str_size_t; 187 | 188 | #define PHPC_LONG_TO_LONG_EX2(_plv, _lv, _exc_over, _exc_under) \ 189 | _lv = _plv 190 | #define PHPC_LONG_TO_LONG_EX(_plv, _lv, _exc) \ 191 | _lv = _plv 192 | #define PHPC_LONG_TO_LONG(_plv, _lv) \ 193 | _lv = _plv 194 | 195 | #define PHPC_SIZE_TO_LONG_EX PHPC_LONG_TO_LONG_EX 196 | #define PHPC_SIZE_TO_LONG PHPC_LONG_TO_LONG 197 | 198 | #define PHPC_SIZE_TO_INT_EX PHPC_LONG_TO_LONG_EX 199 | #define PHPC_SIZE_TO_INT PHPC_LONG_TO_LONG 200 | 201 | 202 | /* STRING */ 203 | 204 | /* accessor and convertor macros */ 205 | #define PHPC_STR_VAL(_name) _name##__val 206 | #define PHPC_STR_LEN(_name) _name##__len 207 | #define PHPC_STR_LEN_FMT "d" 208 | #define PHPC_STR_LEN_UNUSED(_name) (void) PHPC_STR_LEN(_name) 209 | #define PHPC_STR_LEN_FROM_VAL(_name) strlen(PHPC_STR_VAL(_name)) 210 | #define PHPC_STR_LEN_DECLARE(_name) int PHPC_STR_LEN(_name) 211 | #define PHPC_STR_LEN_FETCH(_name) PHPC_STR_LEN(_name) = PHPC_STR_LEN_FROM_VAL(_name) 212 | #define PHPC_STR_LEN_DECLARE_AND_FETCH(_name) int PHPC_STR_LEN_FETCH(_name) 213 | #define PHPC_STR_EXISTS(_name) PHPC_STR_VAL(_name) 214 | #define PHPC_STR_DECLARE(_name) char *PHPC_STR_VAL(_name); int PHPC_STR_LEN(_name) 215 | #define PHPC_STR_ARG(_name) char *PHPC_STR_VAL(_name), int PHPC_STR_LEN(_name) 216 | #define PHPC_STR_ARG_VAL(_name) char *PHPC_STR_VAL(_name) 217 | #define PHPC_STR_ARG_PTR(_name) char **PHPC_STR_VAL(_name), int *PHPC_STR_LEN(_name) 218 | #define PHPC_STR_ARG_PTR_VAL(_name) char **PHPC_STR_VAL(_name) 219 | #define PHPC_STR_PASS(_name) PHPC_STR_VAL(_name), PHPC_STR_LEN(_name) 220 | #define PHPC_STR_PASS_VAL(_name) PHPC_STR_VAL(_name) 221 | #define PHPC_STR_PASS_PTR(_name) &PHPC_STR_VAL(_name), &PHPC_STR_LEN(_name) 222 | #define PHPC_STR_PASS_PTR_VAL(_name) &PHPC_STR_VAL(_name) 223 | #define PHPC_STR_DEREF_VAL(_name) *PHPC_STR_VAL(_name) 224 | #define PHPC_STR_FROM_PTR_STR(_str, _strp) \ 225 | PHPC_STR_VAL(_str) = *PHPC_STR_VAL(_strp); \ 226 | PHPC_STR_LEN(_str) = *PHPC_STR_LEN(_strp) 227 | #define PHPC_STR_FROM_PTR_VAL(_str, _strpv) \ 228 | PHPC_STR_VAL(_str) = *PHPC_STR_VAL(_strpv); \ 229 | PHPC_STR_LEN(_str) = strlen(*PHPC_STR_VAL(_strpv)) 230 | #define PHPC_STR_FROM_ZVAL(_str, _zv) \ 231 | PHPC_STR_VAL(_str) = Z_STRVAL(_zv); \ 232 | PHPC_STR_LEN(_str) = Z_STRLEN(_zv) 233 | #define PHPC_STR_FROM_PZVAL(_str, _pzv) \ 234 | PHPC_STR_VAL(_str) = Z_STRVAL_P(_pzv); \ 235 | PHPC_STR_LEN(_str) = Z_STRLEN_P(_pzv) 236 | #define PHPC_STR_RETURN(_name) \ 237 | RETURN_STRINGL(PHPC_STR_VAL(_name), PHPC_STR_LEN(_name), 0) 238 | 239 | /* wrapper macros */ 240 | #define PHPC_STR_INIT(_name, _cstr, _len) do { \ 241 | PHPC_STR_VAL(_name) = emalloc(_len + 1); \ 242 | memcpy(PHPC_STR_VAL(_name), _cstr, _len); \ 243 | PHPC_STR_VAL(_name)[_len] = 0; \ 244 | PHPC_STR_LEN(_name) = _len; \ 245 | } while (0) 246 | #define PHPC_STR_ALLOC(_name, _len) do { \ 247 | PHPC_STR_VAL(_name) = emalloc(_len + 1); \ 248 | PHPC_STR_LEN(_name) = _len; \ 249 | } while (0) 250 | #define PHPC_STR_REALLOC(_name, _len) do { \ 251 | PHPC_STR_VAL(_name) = erealloc(PHPC_STR_VAL(_name), _len + 1); \ 252 | PHPC_STR_LEN(_name) = _len; \ 253 | } while (0) 254 | #define PHPC_STR_RELEASE(_name) efree(PHPC_STR_VAL(_name)) 255 | 256 | /* C string */ 257 | #define PHPC_CSTRL_RETURN(_name, _len) RETURN_STRINGL(_name, _len, 1) 258 | #define PHPC_CSTR_RETURN(_name) RETURN_STRING(_name, 1) 259 | #define PHPC_CSTR_EMPTY_RETURN RETURN_EMPTY_STRING 260 | #define PHPC_CSTRL_RETVAL(_name, _len) RETVAL_STRINGL(_name, _len, 1) 261 | #define PHPC_CSTR_RETVAL(_name) RETVAL_STRING(_name, 1) 262 | #define PHPC_CSTR_EMPTY_RETVAL RETVAL_EMPTY_STRING 263 | 264 | /* ZSTR */ 265 | #define PHPC_ZSTR_VAL(_name) _name 266 | 267 | /* Smart string */ 268 | #if defined(PHPC_SMART_STR_INCLUDE) || defined(PHPC_SMART_CSTR_INCLUDE) 269 | #include "ext/standard/php_smart_str.h" 270 | 271 | #ifdef PHPC_SMART_CSTR_INCLUDE 272 | /* smart_str for C string has been renamed in PHP 7 so we have to wrap it */ 273 | #define phpc_smart_cstr smart_str 274 | #define phpc_smart_cstr_alloc smart_str_alloc 275 | #define phpc_smart_cstr_free smart_str_free 276 | #define phpc_smart_cstr_append smart_str_append 277 | #define phpc_smart_cstr_appends smart_str_appends 278 | #define phpc_smart_cstr_appendl smart_str_appendl 279 | #define phpc_smart_cstr_appendc smart_str_appendc 280 | #define phpc_smart_cstr_append_long smart_str_append_long 281 | #define phpc_smart_cstr_append_unsigned smart_str_append_unsigned 282 | #define phpc_smart_cstr_0 smart_str_0 283 | #endif /* PHPC_SMART_CSTR_INCLUDE */ 284 | 285 | #endif /* PHPC_SMART_STR_INCLUDE || PHPC_SMART_CSTR_INCLUDE */ 286 | 287 | 288 | /* RESOURCE */ 289 | typedef zend_rsrc_list_entry phpc_res_entry_t; 290 | typedef long phpc_res_value_t; 291 | 292 | #define PHPC_RES_REGISTER(_entry, _type) \ 293 | zend_list_insert(_entry, _type TSRMLS_CC) 294 | #define PHPC_RES_FETCH(_pz_res, _res_type_name, _res_type) \ 295 | zend_fetch_resource(&(_pz_res) TSRMLS_CC, -1, _res_type_name, NULL, 1, _res_type) 296 | #define PHPC_RES_FETCH2(_pz_res, _res_type_name, _res_type_1, _res_type_2) \ 297 | zend_fetch_resource(&(_pz_res) TSRMLS_CC, -1, _res_type_name, NULL, 2, _res_type_1, _res_type_2) 298 | #define PHPC_RES_DELETE(_pz_res) \ 299 | zend_list_delete(Z_LVAL_P(_pz_res)) 300 | #define PHPC_RES_CLOSE PHPC_RES_DELETE 301 | 302 | /* resource to zval */ 303 | #define PHPC_RES_PZVAL(_res, _pzv) \ 304 | ZVAL_RESOURCE(_pzv, _res) 305 | #define PHPC_RES_RETVAL RETVAL_RESOURCE 306 | #define PHPC_RES_RETURN RETURN_RESOURCE 307 | 308 | 309 | /* OBJECT */ 310 | #define PHPC_CLASS_REGISTER_EX(_orig_class_entry, _parent_ce, _parent_name) \ 311 | zend_register_internal_class_ex(&_orig_class_entry, _parent_ce, _parent_name TSRMLS_CC) 312 | #define PHPC_CLASS_REGISTER(_orig_class_entry) \ 313 | zend_register_internal_class(&_orig_class_entry TSRMLS_CC) 314 | 315 | /* struct spec */ 316 | #define PHPC_OBJ_STRUCT_MEMBER_FIRST zend_object std; 317 | #define PHPC_OBJ_STRUCT_MEMBER_LAST 318 | #define PHPC_OBJ_STRUCT_BEGIN(_name) \ 319 | PHPC_OBJ_STRUCT_NAME(_name) { PHPC_OBJ_STRUCT_MEMBER_FIRST 320 | #define PHPC_OBJ_STRUCT_END() \ 321 | PHPC_OBJ_STRUCT_MEMBER_LAST }; 322 | 323 | /* object convertors */ 324 | #define PHPC_OBJ_FROM_ZOBJ(_name, _object) \ 325 | (PHPC_OBJ_STRUCT_NAME(_name) *) _object 326 | #define PHPC_OBJ_FROM_ZVAL(_name, _zv) \ 327 | (PHPC_OBJ_STRUCT_NAME(_name) *) zend_object_store_get_object(_zv TSRMLS_CC) 328 | #define PHPC_OBJ_FROM_POBJ PHPC_OBJ_FROM_ZVAL 329 | 330 | /* create_ex object handler helper */ 331 | #define PHPC_OBJ_HANDLER_CREATE_EX(_name) \ 332 | PHPC_OBJ_GET_HANDLER_FCE_INLINE_DEF(zend_object_value, _name, create_ex) \ 333 | (zend_class_entry *PHPC_CLASS_TYPE, PHPC_OBJ_STRUCT_NAME(_name) **_phpc_objptr TSRMLS_DC) 334 | #define PHPC_OBJ_HANDLER_CREATE_EX_IS_NEW() (_phpc_objptr == NULL) 335 | #define PHPC_OBJ_HANDLER_CREATE_EX_DECLARE() zend_object_value _phpc_retval 336 | #define PHPC_OBJ_HANDLER_CREATE_EX_ALLOC(_name) \ 337 | ecalloc(1, sizeof(PHPC_OBJ_STRUCT_NAME(_name))); 338 | #define PHPC_OBJ_HANDLER_INIT_CREATE_EX_PROPS(_intern) \ 339 | do { \ 340 | if (_phpc_objptr) { \ 341 | *_phpc_objptr = _intern; \ 342 | } \ 343 | zend_object_std_init(&_intern->std, PHPC_CLASS_TYPE TSRMLS_CC); \ 344 | PHPC_OBJ_PROPERTIES_INIT(&_intern->std, PHPC_CLASS_TYPE); \ 345 | } while(0) 346 | #define PHPC_OBJ_HANDLER_CREATE_EX_RETURN_EX(_name, _intern) \ 347 | do { \ 348 | _phpc_retval.handle = zend_objects_store_put((_intern), \ 349 | (zend_objects_store_dtor_t) zend_objects_destroy_object, \ 350 | (zend_objects_free_object_storage_t) PHPC_OBJ_GET_HANDLER_FCE(_name, free), \ 351 | NULL TSRMLS_CC); \ 352 | _phpc_retval.handlers = &PHPC_OBJ_GET_HANDLER_VAR_NAME(_name); \ 353 | return _phpc_retval; \ 354 | } while(0) 355 | 356 | /* create object handler */ 357 | #define PHPC_OBJ_HANDLER_CREATE(_name) \ 358 | PHPC_OBJ_DEFINE_HANDLER_FCE(zend_object_value, _name, create) \ 359 | (zend_class_entry *PHPC_CLASS_TYPE TSRMLS_DC) 360 | #define PHPC_OBJ_HANDLER_CREATE_RETURN(_name) \ 361 | return PHPC_OBJ_GET_HANDLER_FCE(_name, create_ex)(PHPC_CLASS_TYPE, NULL TSRMLS_CC) 362 | 363 | /* clone object handler */ 364 | #define PHPC_OBJ_HANDLER_CLONE(_name) \ 365 | PHPC_OBJ_DEFINE_HANDLER_FCE(zend_object_value, _name, clone)(phpc_obj_t *PHPC_SELF TSRMLS_DC) 366 | #define PHPC_OBJ_HANDLER_CLONE_DECLARE() zend_object_value _phpc_retval 367 | #define PHPC_OBJ_HANDLER_CLONE_MEMBERS(_name, _new_obj, _old_obj) \ 368 | do { \ 369 | _phpc_retval = PHPC_OBJ_GET_HANDLER_FCE(_name, create_ex)(_old_obj->std.ce, &_new_obj TSRMLS_CC); \ 370 | zend_objects_clone_members(&_new_obj->std, _phpc_retval, &_old_obj->std, Z_OBJ_HANDLE_P(PHPC_SELF) TSRMLS_CC); \ 371 | } while(0) 372 | #define PHPC_OBJ_HANDLER_CLONE_RETURN_EX(_new_obj) return _phpc_retval 373 | 374 | /* free object handler */ 375 | #define PHPC_OBJ_HANDLER_FREE(_name) \ 376 | PHPC_OBJ_DEFINE_HANDLER_FCE(void, _name, free)(void *_phpc_object TSRMLS_DC) 377 | #define PHPC_OBJ_HANDLER_FREE_DTOR(_intern) \ 378 | do { \ 379 | zend_object_std_dtor(&(_intern)->std TSRMLS_CC); \ 380 | efree(_intern); \ 381 | } while(0) 382 | 383 | /* compare object handler */ 384 | #define PHPC_OBJ_HANDLER_COMPARE(_name) \ 385 | PHPC_OBJ_DEFINE_HANDLER_FCE(int, _name, compare)(zval *_phpc_obj1, zval *_phpc_obj2 TSRMLS_DC) 386 | #define PHPC_OBJ_HANDLER_COMPARE_FETCH(_name, _id, _obj) \ 387 | PHPC_OBJ_STRUCT_DECLARE(_name, _obj) = PHPC_OBJ_FROM_ZVAL(_name, _phpc_obj ## _id) 388 | 389 | /* handler setters */ 390 | #define PHPC_OBJ_SET_SPECIFIC_HANDLER_OFFSET(_handlers, _name) PHPC_NOOP 391 | #define PHPC_OBJ_SET_SPECIFIC_HANDLER_FREE(_handlers, _name) PHPC_NOOP 392 | 393 | /* read propery */ 394 | #define PHPC_READ_PROPERTY_RV_NAME 395 | #define PHPC_READ_PROPERTY_RV_DECLARE PHPC_NOOP 396 | #define PHPC_READ_PROPERTY(_scope, _object, _name, _name_len, _silent) \ 397 | zend_read_property(_scope, _object, _name, _name_len, _silent TSRMLS_CC) 398 | 399 | /* HASH */ 400 | 401 | /* apply count */ 402 | #define PHPC_HASH_HAS_APPLY_COUNT(_ht) (_ht->nApplyCount > 0) 403 | #define PHPC_HASH_GET_APPLY_COUNT(_ht) _ht->nApplyCount 404 | #define PHPC_HASH_INC_APPLY_COUNT(_ht) _ht->nApplyCount++ 405 | #define PHPC_HASH_DEC_APPLY_COUNT(_ht) _ht->nApplyCount-- 406 | #define PHPC_HASH_APPLY_PROTECTION(_ht) 1 407 | 408 | /* add ptr */ 409 | #define PHPC_HASH_INDEX_ADD_PTR(_ht, _idx, _ptr, _ptr_size) \ 410 | zend_hash_index_update(_ht, _idx, _ptr, _ptr_size, NULL) 411 | #define PHPC_HASH_STR_ADD_PTR(_ht, _str, _ptr, _ptr_size) \ 412 | zend_hash_add(_ht, PHPC_STR_VAL(_str), PHPC_STR_LEN(_str) + 1, _ptr, _ptr_size, NULL) 413 | #define PHPC_HASH_CSTRL_ADD_PTR(_ht, _cstr_value, _cstr_len, _ptr, _ptr_size) \ 414 | zend_hash_add(_ht, _cstr_value, (_cstr_len) + 1, _ptr, _ptr_size, NULL) 415 | #define PHPC_HASH_CSTR_ADD_PTR(_ht, _cstr_value, _ptr, _ptr_size) \ 416 | zend_hash_add(_ht, _cstr_value, strlen(_cstr_value) + 1, _ptr, _ptr_size, NULL) 417 | /* add */ 418 | #define PHPC_HASH_INDEX_ADD(_ht, _idx, _pzv) \ 419 | zend_hash_index_update(_ht, _idx, &_pzv, sizeof(_pzv), NULL) 420 | #define PHPC_HASH_STR_ADD(_ht, _str, _pzv) \ 421 | zend_hash_add(_ht, PHPC_STR_VAL(_str), PHPC_STR_LEN(_str) + 1, &_pzv, sizeof(_pzv), NULL) 422 | #define PHPC_HASH_CSTRL_ADD(_ht, _cstr_value, _cstr_len, _pzv) \ 423 | zend_hash_add(_ht, _cstr_value, (_cstr_len) + 1, &_pzv, sizeof(_pzv), NULL) 424 | #define PHPC_HASH_CSTR_ADD(_ht, _cstr_value, _pzv) \ 425 | zend_hash_add(_ht, _cstr_value, strlen(_cstr_value) + 1, &_pzv, sizeof(_pzv), NULL) 426 | 427 | /* next insert */ 428 | #define PHPC_HASH_NEXT_INDEX_INSERT_PTR(_ht, _ptr, _ptr_size) \ 429 | zend_hash_next_index_insert(_ht, _ptr, _ptr_size, NULL) 430 | #define PHPC_HASH_NEXT_INDEX_INSERT(_ht, _pzv) \ 431 | zend_hash_next_index_insert(_ht, _pzv, sizeof(_pzv), NULL) 432 | 433 | /* update ptr */ 434 | #define PHPC_HASH_INDEX_UPDATE_PTR(_ht, _idx, _ptr, _ptr_size) \ 435 | zend_hash_index_update(_ht, _idx, _ptr, _ptr_size, NULL) 436 | #define PHPC_HASH_STR_UPDATE_PTR(_ht, _str, _ptr, _ptr_size) \ 437 | zend_hash_update(_ht, PHPC_STR_VAL(_str), PHPC_STR_LEN(_str) + 1, _ptr, _ptr_size, NULL) 438 | #define PHPC_HASH_CSTRL_UPDATE_PTR(_ht, _cstr_value, _cstr_len, _ptr, _ptr_size) \ 439 | zend_hash_update(_ht, _cstr_value, (_cstr_len) + 1, _ptr, _ptr_size, NULL) 440 | #define PHPC_HASH_CSTR_UPDATE_PTR(_ht, _cstr_value, _ptr, _ptr_size) \ 441 | zend_hash_update(_ht, _cstr_value, strlen(_cstr_value) + 1, _ptr, _ptr_size, NULL) 442 | /* update */ 443 | #define PHPC_HASH_INDEX_UPDATE(_ht, _idx, _pzv) \ 444 | zend_hash_index_update(_ht, _idx, &_pzv, sizeof(_pzv), NULL) 445 | #define PHPC_HASH_STR_UPDATE(_ht, _str, _pzv) \ 446 | zend_hash_update(_ht, PHPC_STR_VAL(_str), PHPC_STR_LEN(_str) + 1, &_pzv, sizeof(_pzv), NULL) 447 | #define PHPC_HASH_CSTRL_UPDATE(_ht, _cstr_value, _cstr_len, _pzv) \ 448 | zend_hash_update(_ht, _cstr_value, (_cstr_len) + 1, &_pzv, sizeof(_pzv), NULL) 449 | #define PHPC_HASH_CSTR_UPDATE(_ht, _cstr_value, _pzv) \ 450 | zend_hash_update(_ht, _cstr_value, strlen(_cstr_value) + 1, &_pzv, sizeof(_pzv), NULL) 451 | 452 | /* delete */ 453 | #define PHPC_HASH_INDEX_DELETE(_ht, _idx) \ 454 | zend_hash_index_del(_ht, _idx) 455 | #define PHPC_HASH_STR_DELETE(_ht, _str) \ 456 | zend_hash_del(_ht, PHPC_STR_VAL(_str), PHPC_STR_LEN(_str) + 1) 457 | #define PHPC_HASH_CSTRL_DELETE(_ht, _cstr_value, _cstr_len) \ 458 | zend_hash_del(_ht, _cstr_value, (_cstr_len) + 1) 459 | #define PHPC_HASH_CSTR_DELETE(_ht, _cstr_value) \ 460 | zend_hash_del(_ht, _cstr_value, strlen(_cstr_value) + 1) 461 | 462 | /* exists */ 463 | #define PHPC_HASH_INDEX_EXISTS(_ht, _idx) \ 464 | zend_hash_index_exists(_ht, _idx) 465 | #define PHPC_HASH_STR_EXISTS(_ht, _str) \ 466 | zend_hash_exists(_ht, PHPC_STR_VAL(_str), PHPC_STR_LEN(_str) + 1) 467 | #define PHPC_HASH_CSTRL_EXISTS(_ht, _cstr_value, _cstr_len) \ 468 | zend_hash_exists(_ht, _cstr_value, (_cstr_len) + 1) 469 | #define PHPC_HASH_CSTR_EXISTS(_ht, _cstr_value) \ 470 | zend_hash_exists(_ht, _cstr_value, strlen(_cstr_value) + 1) 471 | 472 | /* find */ 473 | #define PHPC_HASH_INDEX_FIND(_ht, _idx, _ppv) \ 474 | zend_hash_index_find(_ht, _idx, (void **) &_ppv) 475 | #define PHPC_HASH_STR_FIND(_ht, _str, _ppv) \ 476 | zend_hash_find(_ht, PHPC_STR_VAL(_str), PHPC_STR_LEN(_str) + 1, (void **) &_ppv) 477 | #define PHPC_HASH_CSTRL_FIND(_ht, _cstr_value, _cstr_len, _ppv) \ 478 | zend_hash_find(_ht, _cstr_value, (_cstr_len) + 1, (void **) &_ppv) 479 | #define PHPC_HASH_CSTR_FIND(_ht, _cstr_value, _ppv) \ 480 | zend_hash_find(_ht, _cstr_value, strlen(_cstr_value) + 1, (void **) &_ppv) 481 | /* find ptr */ 482 | #define PHPC_HASH_STR_FIND_PTR PHPC_HASH_STR_FIND 483 | #define PHPC_HASH_INDEX_FIND_PTR PHPC_HASH_INDEX_FIND 484 | #define PHPC_HASH_CSTRL_FIND_PTR PHPC_HASH_CSTRL_FIND 485 | #define PHPC_HASH_CSTR_FIND_PTR PHPC_HASH_CSTR_FIND 486 | /* not found value */ 487 | #define PHPC_HASH_NOT_FOUND FAILURE 488 | 489 | /* key and data getter */ 490 | #define PHPC_HASH_GET_CURRENT_KEY_EX(_ht, _str, _num_index, _pos) \ 491 | do { \ 492 | unsigned int _phpc_current_key_len; \ 493 | zend_hash_get_current_key_ex(_ht, &PHPC_STR_VAL(_str), \ 494 | &_phpc_current_key_len, &_num_index, 0, _pos); \ 495 | PHPC_STR_LEN(_str) = _phpc_current_key_len - 1; \ 496 | } while(0) 497 | #define PHPC_HASH_GET_CURRENT_DATA_EX(_ht, _val, _pos) \ 498 | zend_hash_get_current_data_ex(_ht, (void **) &(_val), _pos) 499 | 500 | #define PHPC_HASH_GET_CURRENT_KEY(_ht, _str, _num_index) \ 501 | zend_hash_get_current_key(_ht, &PHPC_STR_VAL(_str), &_num_index, 0) 502 | #define PHPC_HASH_GET_CURRENT_DATA(_ht, _val) \ 503 | zend_hash_get_current_data(_ht, (void **) &(_val)) 504 | 505 | /* copy */ 506 | #define PHPC_HASH_COPY_EX(_target, _source, _copy_ctr) \ 507 | zend_hash_copy(_target, _source, NULL, NULL, sizeof(zval *)) 508 | 509 | /* key result constant has been renamed in 5.4 */ 510 | #if PHP_VERSION_ID < 50399 511 | #define _PHPC_HASH_KEY_NON_EXISTENT HASH_KEY_NON_EXISTANT 512 | #else 513 | #define _PHPC_HASH_KEY_NON_EXISTENT HASH_KEY_NON_EXISTENT 514 | #endif 515 | 516 | /* iteration for each element */ 517 | #define PHPC_HASH_FOREACH_KEY(_ht, _h, _key) do { \ 518 | HashPosition _pos; \ 519 | uint _str_length; \ 520 | int _key_type; \ 521 | for (zend_hash_internal_pointer_reset_ex((_ht), &_pos); \ 522 | (_key_type = zend_hash_get_current_key_ex( \ 523 | (_ht), &PHPC_STR_VAL(_key), &_str_length, &_h, 0, &_pos)) != _PHPC_HASH_KEY_NON_EXISTENT; \ 524 | zend_hash_move_forward_ex((_ht), &_pos) ) { \ 525 | if (_key_type == HASH_KEY_IS_STRING) { \ 526 | PHPC_STR_LEN(_key) = (int) _str_length - 1; \ 527 | } else { \ 528 | PHPC_STR_VAL(_key) = NULL; \ 529 | PHPC_STR_LEN(_key) = 0; \ 530 | } 531 | 532 | #define PHPC_HASH_FOREACH_VAL(_ht, _ppv) do { \ 533 | HashPosition _pos; \ 534 | for (zend_hash_internal_pointer_reset_ex((_ht), &_pos); \ 535 | zend_hash_get_current_data_ex((_ht), (void **) &(_ppv), &_pos) == SUCCESS; \ 536 | zend_hash_move_forward_ex((_ht), &_pos) ) { 537 | 538 | #define PHPC_HASH_FOREACH_VAL_IND PHPC_HASH_FOREACH_VAL 539 | 540 | #define _PHPC_HASH_FOREACH_KEY_VAL(_ht, _ph, _key, _ppv, _use_h) \ 541 | PHPC_HASH_FOREACH_VAL(_ht, _ppv) \ 542 | int _key_type; \ 543 | uint _str_length; \ 544 | ulong _num_index, *_pnum_index; \ 545 | if (_use_h) { \ 546 | _pnum_index = _ph; \ 547 | } else { \ 548 | _pnum_index = &_num_index; \ 549 | } \ 550 | _key_type = zend_hash_get_current_key_ex(_ht, &PHPC_STR_VAL(_key), &_str_length, _pnum_index, 0, &_pos); \ 551 | if (_key_type == HASH_KEY_IS_STRING) { \ 552 | PHPC_STR_LEN(_key) = (int) _str_length - 1; \ 553 | } else { \ 554 | PHPC_STR_VAL(_key) = NULL; \ 555 | PHPC_STR_LEN(_key) = 0; \ 556 | } 557 | 558 | #define PHPC_HASH_FOREACH_KEY_VAL(_ht, _h, _key, _ppv) \ 559 | _PHPC_HASH_FOREACH_KEY_VAL(_ht, &_h, _key, _ppv, 1) 560 | 561 | 562 | #define PHPC_HASH_FOREACH_KEY_VAL_IND PHPC_HASH_FOREACH_KEY_VAL 563 | 564 | #define PHPC_HASH_FOREACH_STR_KEY_VAL(_ht, _key, _ppv) \ 565 | _PHPC_HASH_FOREACH_KEY_VAL(_ht, NULL, _key, _ppv, 0) 566 | 567 | #define PHPC_HASH_FOREACH_STR_KEY_VAL_IND PHPC_HASH_FOREACH_STR_KEY_VAL 568 | 569 | #define PHPC_HASH_FOREACH_END() } } while (0) 570 | 571 | /* hash to zval */ 572 | #define PHPC_HASH_PZVAL(_ht, _pzv) \ 573 | do { \ 574 | Z_ARRVAL_P(_pzv) = _ht; \ 575 | Z_TYPE_P(_pzv) = IS_ARRAY; \ 576 | } while(0) 577 | #define PHPC_HASH_RETVAL(_ht) \ 578 | PHPC_HASH_PZVAL(_ht, return_value) 579 | #define PHPC_HASH_RETURN(_ht) \ 580 | do { \ 581 | PHPC_HASH_RETVAL(_ht); \ 582 | return; \ 583 | } while(0) 584 | 585 | 586 | /* SYMTABLE */ 587 | 588 | /* update*/ 589 | #define PHPC_SYMTABLE_UPDATE(_ht, _str, _pzv) \ 590 | zend_symtable_update(_ht, PHPC_STR_VAL(_str), PHPC_STR_LEN(_str) + 1, &_pzv, sizeof(_pzv), NULL) 591 | 592 | 593 | /* ARRAY */ 594 | 595 | #define PHPC_ARRAY_ADD_ASSOC_NULL_EX(_arr, _key, _key_len) \ 596 | add_assoc_null_ex(_arr, _key, (_key_len) + 1) 597 | #define PHPC_ARRAY_ADD_ASSOC_BOOL_EX(_arr, _key, _key_len, _b) \ 598 | add_assoc_bool_ex(_arr, _key, (_key_len) + 1, _b) 599 | #define PHPC_ARRAY_ADD_ASSOC_LONG_EX(_arr, _key, _key_len, _n) \ 600 | add_assoc_long_ex(_arr, _key, (_key_len) + 1, _n) 601 | #define PHPC_ARRAY_ADD_ASSOC_RESOURCE_EX(_arr, _key, _key_len, _r) \ 602 | add_assoc_resource_ex(_arr, _key, (_key_len) + 1, _r) 603 | #define PHPC_ARRAY_ADD_ASSOC_DOUBLE_EX(_arr, _key, _key_len, _d) \ 604 | add_assoc_double_ex(_arr, _key, (_key_len) + 1, _d) 605 | #define PHPC_ARRAY_ADD_ASSOC_STR_EX(_arr, _key, _key_len, _str) \ 606 | add_assoc_stringl_ex(_arr, _key, (_key_len) + 1, PHPC_STR_VAL(_str), PHPC_STR_LEN(_str), 0) 607 | #define PHPC_ARRAY_ADD_ASSOC_CSTR_EX(_arr, _key, _key_len, _cstr) \ 608 | add_assoc_string_ex(_arr, _key, (_key_len) + 1, _cstr, 1) 609 | #define PHPC_ARRAY_ADD_ASSOC_CSTRL_EX(_arr, _key, _key_len, _cstr, _cstr_len) \ 610 | add_assoc_stringl_ex(_arr, _key, (_key_len) + 1, _cstr, _cstr_len, 1) 611 | #define PHPC_ARRAY_ADD_ASSOC_ZVAL_EX(_arr, _key, _key_len, _zv) \ 612 | add_assoc_zval_ex(_arr, _key, (_key_len) + 1, _zv) 613 | #define PHPC_ARRAY_ADD_ASSOC_VAL_EX(_arr, _key, _key_len, _pv) \ 614 | add_assoc_zval_ex(_arr, _key, (_key_len) + 1, _pv) 615 | 616 | #define PHPC_ARRAY_ADD_ASSOC_STR(_arr, _key, _str) \ 617 | add_assoc_stringl(_arr, _key, PHPC_STR_VAL(_str), PHPC_STR_LEN(_str), 0) 618 | #define PHPC_ARRAY_ADD_ASSOC_CSTR(_arr, _key, _cstr) \ 619 | add_assoc_string(_arr, _key, _cstr, 1) 620 | #define PHPC_ARRAY_ADD_ASSOC_CSTRL(_arr, _key, _cstr, _cstr_len) \ 621 | add_assoc_stringl(_arr, _key, _cstr, _cstr_len, 1) 622 | #define PHPC_ARRAY_ADD_ASSOC_VAL add_assoc_zval 623 | 624 | #define PHPC_ARRAY_ADD_INDEX_STR(_arr, _idx, _str) \ 625 | add_index_stringl(_arr, _idx, PHPC_STR_VAL(_str), PHPC_STR_LEN(_str), 0) 626 | #define PHPC_ARRAY_ADD_INDEX_CSTR(_arr, _idx, _cstr) \ 627 | add_index_string(_arr, _idx, _cstr, 1) 628 | #define PHPC_ARRAY_ADD_INDEX_CSTRL(_arr, _idx, _cstr, _cstr_len) \ 629 | add_index_stringl(_arr, _idx, _cstr, _cstr_len, 1) 630 | #define PHPC_ARRAY_ADD_INDEX_VAL add_index_zval 631 | 632 | #define PHPC_ARRAY_ADD_NEXT_INDEX_STR(_arr, _str) \ 633 | add_next_index_stringl(_arr, PHPC_STR_VAL(_str), PHPC_STR_LEN(_str), 0) 634 | #define PHPC_ARRAY_ADD_NEXT_INDEX_CSTR(_arr, _cstr) \ 635 | add_next_index_string(_arr, _cstr, 1) 636 | #define PHPC_ARRAY_ADD_NEXT_INDEX_CSTRL(_arr, _cstr, _cstr_len) \ 637 | add_next_index_stringl(_arr, _cstr, _cstr_len, 1) 638 | #define PHPC_ARRAY_ADD_NEXT_INDEX_VAL add_next_index_zval 639 | 640 | 641 | /* FCALL */ 642 | #define _PHPC_FCALL_VARS_NAME(_pname) _phpc_fcall_vars__ ## _pname 643 | 644 | #define PHPC_FCALL_PARAMS_DECLARE(_pname, _count) \ 645 | int _phpc_fcall_params_count = _count; \ 646 | zval *_PHPC_FCALL_VARS_NAME(_pname)[_count]; \ 647 | zval **PHPC_FCALL_PARAMS_NAME(_pname)[_count] 648 | 649 | #define PHPC_FCALL_PARAMS_INIT(_pname) \ 650 | do { \ 651 | int _idx; \ 652 | for (_idx = 0; _idx < _phpc_fcall_params_count; _idx++) \ 653 | PHPC_FCALL_PARAMS_NAME(_pname)[_idx] = &_PHPC_FCALL_VARS_NAME(_pname)[_idx]; \ 654 | } while(0) 655 | 656 | #define PHPC_FCALL_PARAM_PZVAL(_pname, _idx) \ 657 | _PHPC_FCALL_VARS_NAME(_pname)[_idx] 658 | 659 | #define PHPC_FCALL_PARAM_VAL(_pname, _idx) \ 660 | _PHPC_FCALL_VARS_NAME(_pname)[_idx] 661 | 662 | #define PHPC_FCALL_PARAM_UNDEF(_pname, _idx) \ 663 | ZVAL_NULL(PHPC_FCALL_PARAM_PZVAL(_pname, _idx)) 664 | 665 | #define PHPC_FCALL_RETVAL(_fci, _pv) \ 666 | (_fci).retval_ptr_ptr = &(_pv) 667 | 668 | /* ZVAL */ 669 | typedef zval * phpc_val; 670 | 671 | #define PHPC_TYPE Z_TYPE_P 672 | #define PHPC_TYPE_P Z_TYPE_PP 673 | 674 | #define PHPC_LVAL Z_LVAL_P 675 | #define PHPC_LVAL_P Z_LVAL_PP 676 | 677 | #define PHPC_DVAL Z_DVAL_P 678 | #define PHPC_DVAL_P Z_DVAL_PP 679 | 680 | #define PHPC_STRVAL Z_STRVAL_P 681 | #define PHPC_STRVAL_P Z_STRVAL_PP 682 | 683 | #define PHPC_STRLEN Z_STRLEN_P 684 | #define PHPC_STRLEN_P Z_STRLEN_PP 685 | 686 | #define PHPC_ARRVAL Z_ARRVAL_P 687 | #define PHPC_ARRVAL_P Z_ARRVAL_PP 688 | 689 | #define PHPC_OBJ_HT Z_OBJ_HT_P 690 | #define PHPC_OBJ_HT_P Z_OBJ_HT_PP 691 | 692 | #define PHPC_OBJ_HANDLER Z_OBJ_HANDLER_P 693 | #define PHPC_OBJ_HANDLER_P Z_OBJ_HANDLER_PP 694 | 695 | #define PHPC_OBJ_HANDLE Z_OBJ_HANDLE_P 696 | #define PHPC_OBJ_HANDLE_P Z_OBJ_HANDLE_PP 697 | 698 | #define PHPC_OBJCE Z_OBJCE_P 699 | #define PHPC_OBJCE_P Z_OBJCE_PP 700 | 701 | #define PHPC_OBJPROP Z_OBJPROP_P 702 | #define PHPC_OBJPROP_P Z_OBJPROP_PP 703 | 704 | #define PHPC_OBJDEBUG Z_OBJDEBUG_P 705 | #define PHPC_OBJDEBUG_P Z_OBJDEBUG_PP 706 | 707 | #define PHPC_REFCOUNTED(_zv) 1 708 | #define PHPC_REFCOUNTED_P(_pzv) 1 709 | 710 | #define PHPC_PZVAL_CAST_TO_PVAL(_pzv) &_pzv 711 | 712 | #define PHPC_VAL_CAST_TO_ZVAL(_pv) *(_pv) 713 | #define PHPC_VAL_CAST_TO_PZVAL(_pv) _pv 714 | #define PHPC_PVAL_CAST_TO_PZVAL(_ppv) *(_ppv) 715 | 716 | #define PHPC_VAL_TO_ZVAL(_pv, _zv) _zv = *(_pv) 717 | #define PHPC_VAL_TO_PZVAL(_pv, _zv) _zv = _pv 718 | #define PHPC_PVAL_TO_PZVAL(_ppv, _zv) _zv = *(_ppv) 719 | 720 | #define PHPC_VAL_MAKE MAKE_STD_ZVAL 721 | #define PHPC_VAL_FREE FREE_ZVAL 722 | #define PHPC_VAL_UNDEF(_pv) _pv = NULL 723 | #define PHPC_VAL_ISUNDEF(_pv) _pv == NULL 724 | #define PHPC_VAL_COPY(_pv, _zv) ZVAL_ZVAL(_pv, _zv, 1, 0) 725 | #define PHPC_VAL_ASSIGN(_pv, _zv) _pv = _zv 726 | 727 | #define PHPC_PZVAL_MAKE MAKE_STD_ZVAL 728 | #define PHPC_PZVAL_FREE FREE_ZVAL 729 | #define PHPC_PZVAL_SET(_pv, _zv) ZVAL_ZVAL(_pv, _zv, 0, 0) 730 | #define PHPC_PVAL_DEREF(_pv) PHPC_NOOP 731 | #define PHPC_PZVAL_DEREF(_pv) PHPC_NOOP 732 | 733 | #define PHPC_PZVAL_COPY_INIT INIT_PZVAL_COPY 734 | #define PHPC_PZVAL_COPY(_pzv_dst, _pzv_src) \ 735 | *_pzv_dst = *_pzv_src 736 | 737 | #define PHPC_VAL_NEW_STR(_pv, _str) \ 738 | ZVAL_STRINGL(_pv, PHPC_STR_VAL(_str), PHPC_STR_LEN(_str), 0) 739 | #define PHPC_VAL_STR PHPC_VAL_NEW_STR 740 | #define PHPC_VAL_CSTR(_pv, _cstr) \ 741 | ZVAL_STRING(_pv, _cstr, 1) 742 | #define PHPC_VAL_CSTRL(_pv, _cstr, _cstr_len) \ 743 | ZVAL_STRINGL(_pv, _cstr, _cstr_len, 1) 744 | 745 | #define PHPC_PZVAL_NEW_STR PHPC_VAL_NEW_STR 746 | #define PHPC_PZVAL_STR PHPC_VAL_STR 747 | #define PHPC_PZVAL_CSTR PHPC_VAL_CSTR 748 | #define PHPC_PZVAL_CSTRL PHPC_VAL_CSTRL 749 | 750 | #define PHPC_ZVAL_COPY(_zv_dst, _zv_src) \ 751 | _zv_dst = _zv_src 752 | 753 | #define PHPC_ZVAL_NEW_STR(_zv, _str) \ 754 | PHPC_VAL_STR(&_zv, _str) 755 | #define PHPC_ZVAL_STR PHPC_ZVAL_NEW_STR 756 | #define PHPC_ZVAL_CSTR(_zv, _cstr) \ 757 | PHPC_VAL_CSTR(&_zv, _cstr) 758 | #define PHPC_ZVAL_CSTRL(_zv, _cstr, _cstr_len) \ 759 | PHPC_VAL_CSTRL(&_zv, _cstr, _cstr_len) 760 | 761 | #define PHPC_ZVAL_IS_TRUE(_zv) \ 762 | (Z_TYPE(_zv) == IS_BOOL && Z_BVAL(_zv)) 763 | #define PHPC_ZVAL_IS_FALSE(_zv) \ 764 | (Z_TYPE(_zv) == IS_BOOL && !Z_BVAL(_zv)) 765 | 766 | #define PHPC_VAL_IS_TRUE(_pv) PHPC_ZVAL_IS_TRUE(*_pv) 767 | #define PHPC_VAL_IS_FALSE(_pv) PHPC_ZVAL_IS_FALSE(*_pv) 768 | 769 | /* Function end */ 770 | #if (PHP_MINOR_VERSION == 3 && PHP_RELEASE_VERSION >= 7) || (PHP_MINOR_VERSION >= 4) 771 | #define PHPC_FE_END PHP_FE_END 772 | #else 773 | #define PHPC_FE_END {NULL,NULL,NULL} 774 | #endif 775 | 776 | 777 | /* ZPP */ 778 | 779 | /* path flag */ 780 | #if PHP_VERSION_ID < 50399 781 | #define PHPC_ZPP_PATH_FLAG "s" 782 | #else 783 | #define PHPC_ZPP_PATH_FLAG "p" 784 | #endif 785 | 786 | /* args */ 787 | #define PHPC_ZPP_ARGS_DECLARE() \ 788 | int _phpc_zpp_args_count = 0; \ 789 | zval ***_phpc_zpp_args_array 790 | 791 | #if PHP_API_VERSION < 20090626 792 | #define PHPC_ZPP_ARGS_LOAD_EX(_flag, _num_args, _return) \ 793 | do { \ 794 | const char *_phpc_zpp_args_type_str = #_flag; \ 795 | _phpc_zpp_args_count = _num_args; \ 796 | _phpc_zpp_args_array = (zval ***) safe_emalloc(_num_args, sizeof (zval **), 0); \ 797 | if ((_phpc_zpp_args_type_str[0] == '+' && _num_args == 0) || \ 798 | zend_get_parameters_array_ex(_phpc_zpp_args_count, _phpc_zpp_args_array) == FAILURE) { \ 799 | efree(_phpc_zpp_args_array); \ 800 | zend_wrong_param_count(TSRMLS_C); \ 801 | _return; \ 802 | } \ 803 | } while (0) 804 | #else 805 | #define PHPC_ZPP_ARGS_LOAD_EX(_flag, _num_args, _return) \ 806 | do { \ 807 | if (zend_parse_parameters(_num_args TSRMLS_CC, #_flag, \ 808 | &_phpc_zpp_args_array, &_phpc_zpp_args_count) == FAILURE) { \ 809 | _return; \ 810 | } \ 811 | } while(0) 812 | #endif 813 | 814 | #define PHPC_ZPP_ARGS_GET_PVAL(_arg_pos) \ 815 | _phpc_zpp_args_array[_arg_pos] 816 | 817 | #define PHPC_ZPP_ARGS_FREE() \ 818 | if (_phpc_zpp_args_count > 0) \ 819 | efree(_phpc_zpp_args_array) 820 | 821 | 822 | /* STREAM */ 823 | #if PHP_VERSION_ID < 50600 824 | typedef char phpc_stream_opener_char_t; 825 | #else 826 | typedef const char phpc_stream_opener_char_t; 827 | #endif 828 | #define PHPC_STREAM_WRAPPERDATA_ALLOC(stream) MAKE_STD_ZVAL(stream->wrapperdata) 829 | #define PHPC_STREAM_WRAPPERDATA_ISSET(stream) stream->wrapperdata 830 | #define PHPC_STREAM_WRAPPERDATA_UNSET(stream) \ 831 | do { \ 832 | zval_ptr_dtor(&stream->wrapperdata); \ 833 | stream->wrapperdata = NULL; \ 834 | } while(0) 835 | #define PHPC_STREAM_CONTEXT_GET_OPTION(_ctx, _wrappername, _optionname, _ppv) \ 836 | php_stream_context_get_option(_ctx, _wrappername, _optionname, &_ppv) 837 | #define PHPC_STREAM_CONTEXT_OPTION_NOT_FOUND FAILURE 838 | 839 | 840 | #else /* PHP 7 */ 841 | 842 | /* MODULE */ 843 | 844 | #define PHPC_MODULE_GLOBALS_ACCESSOR ZEND_MODULE_GLOBALS_ACCESSOR 845 | 846 | #define PHPC_MODULE_HAS_THREAD_CACHE defined(ZTS) && defined(COMPILE_DL_JSON) 847 | 848 | 849 | /* INTEGER */ 850 | 851 | /* long type */ 852 | typedef zend_long phpc_long_t; 853 | /* unsigned long type */ 854 | typedef zend_ulong phpc_ulong_t; 855 | /* offset type */ 856 | typedef zend_off_t phpc_off_t; 857 | /* string length type */ 858 | typedef size_t phpc_str_size_t; 859 | 860 | #define PHPC_LONG_TO_LONG_EX2(_plv, _lv, _exc_over, _exc_under) \ 861 | PHPC_CONVERT_NUMBER(_plv, _lv, _exc_over, _exc_under, phpc_long_t, long, LONG_MAX, LONG_MIN) 862 | #define PHPC_LONG_TO_LONG_EX(_plv, _lv, _exc) \ 863 | PHPC_LONG_TO_LONG_EX2(_plv, _lv, _exc, _exc) 864 | #define PHPC_LONG_TO_LONG(_plv, _lv) \ 865 | PHPC_LONG_TO_LONG_EX2(_plv, _lv, _lv = LONG_MAX, _lv = LONG_MIN) 866 | 867 | #define PHPC_SIZE_TO_LONG_EX(_plv, _lv, _exc_over) \ 868 | PHPC_CONVERT_NUMBER_SIGNED(_plv, _lv, _exc_over, size_t, long, LONG_MAX) 869 | #define PHPC_SIZE_TO_LONG(_plv, _lv) \ 870 | PHPC_SIZE_TO_LONG_EX(_plv, _lv, _lv = LONG_MAX) 871 | 872 | #define PHPC_SIZE_TO_INT_EX(_plv, _lv, _exc_over) \ 873 | PHPC_CONVERT_NUMBER_SIGNED(_plv, _lv, _exc_over, size_t, int, INT_MAX) 874 | #define PHPC_SIZE_TO_INT(_plv, _lv) \ 875 | PHPC_SIZE_TO_LONG_EX(_plv, _lv, _lv = INT_MAX) 876 | 877 | 878 | /* STRING */ 879 | 880 | /* accessor and convertor macros */ 881 | #define PHPC_STR_VAL ZSTR_VAL 882 | #define PHPC_STR_LEN ZSTR_LEN 883 | #define PHPC_STR_LEN_FMT "zu" 884 | #define PHPC_STR_LEN_UNUSED(_name) PHPC_NOOP 885 | #define PHPC_STR_LEN_FROM_VAL PHPC_STR_LEN 886 | #define PHPC_STR_LEN_DECLARE(_name) PHPC_NOOP 887 | #define PHPC_STR_LEN_FETCH(_name) PHPC_NOOP 888 | #define PHPC_STR_LEN_DECLARE_AND_FETCH(_name) PHPC_NOOP 889 | #define PHPC_STR_EXISTS(_name) (_name) 890 | #define PHPC_STR_DECLARE(_name) zend_string *_name 891 | #define PHPC_STR_ARG(_name) zend_string *_name 892 | #define PHPC_STR_ARG_VAL PHPC_STR_ARG 893 | #define PHPC_STR_ARG_PTR(_name) zend_string **_name 894 | #define PHPC_STR_ARG_PTR_VAL PHPC_STR_ARG_PTR 895 | #define PHPC_STR_PASS(_name) _name 896 | #define PHPC_STR_PASS_VAL PHPC_STR_PASS 897 | #define PHPC_STR_PASS_PTR(_name) &_name 898 | #define PHPC_STR_PASS_PTR_VAL PHPC_STR_PASS_PTR 899 | #define PHPC_STR_DEREF_VAL(_name) *_name 900 | #define PHPC_STR_FROM_PTR_STR(_str, _strp) _str = *_strp 901 | #define PHPC_STR_FROM_PTR_VAL(_str, _strpv) _str = *_strpv 902 | #define PHPC_STR_RETURN RETURN_STR 903 | #define PHPC_STR_FROM_ZVAL(_str, _zv) _str = Z_STR(_zv) 904 | #define PHPC_STR_FROM_PZVAL(_str, _pzv) _str = Z_STR_P(_pzv) 905 | /* wrapper macros */ 906 | #define PHPC_STR_INIT(_name, _cstr, _len) \ 907 | _name = zend_string_init(_cstr, _len, 0) 908 | #define PHPC_STR_ALLOC(_name, _len) \ 909 | _name = zend_string_alloc(_len, 0) 910 | #define PHPC_STR_REALLOC(_name, _len) \ 911 | _name = zend_string_realloc(_name, _len, 0) 912 | #define PHPC_STR_RELEASE(_name) \ 913 | zend_string_release(_name) 914 | 915 | /* C string */ 916 | #define PHPC_CSTRL_RETURN RETURN_STRINGL 917 | #define PHPC_CSTR_RETURN RETURN_STRING 918 | #define PHPC_CSTR_EMPTY_RETURN RETURN_EMPTY_STRING 919 | #define PHPC_CSTRL_RETVAL RETVAL_STRINGL 920 | #define PHPC_CSTR_RETVAL RETVAL_STRING 921 | #define PHPC_CSTR_EMPTY_RETVAL RETVAL_EMPTY_STRING 922 | 923 | /* ZSTR */ 924 | #define PHPC_ZSTR_VAL ZSTR_VAL 925 | 926 | /* Smart string */ 927 | #ifdef PHPC_SMART_STR_INCLUDE 928 | #include "zend_smart_str.h" 929 | #endif /* PHPC_SMART_STR_INCLUDE */ 930 | 931 | #ifdef PHPC_SMART_CSTR_INCLUDE 932 | #include "ext/standard/php_smart_string.h" 933 | /* smart_str for C string has been renamed in PHP 7 so we have to wrap it */ 934 | #define phpc_smart_cstr smart_string 935 | #define phpc_smart_cstr_alloc smart_string_alloc 936 | #define phpc_smart_cstr_free smart_string_free 937 | #define phpc_smart_cstr_append smart_string_append 938 | #define phpc_smart_cstr_appends smart_string_appends 939 | #define phpc_smart_cstr_appendl smart_string_appendl 940 | #define phpc_smart_cstr_appendc smart_string_appendc 941 | #define phpc_smart_cstr_append_long smart_string_append_long 942 | #define phpc_smart_cstr_append_unsigned smart_string_append_unsigned 943 | #define phpc_smart_cstr_0 smart_string_0 944 | #endif /* PHPC_SMART_CSTR_INCLUDE */ 945 | 946 | 947 | /* RESOURCE */ 948 | typedef zend_resource phpc_res_entry_t; 949 | typedef zend_resource * phpc_res_value_t; 950 | 951 | #define PHPC_RES_REGISTER zend_register_resource 952 | #define PHPC_RES_FETCH(_pz_res, _res_type_name, _res_type) \ 953 | zend_fetch_resource(Z_RES_P(_pz_res), _res_type_name, _res_type) 954 | #define PHPC_RES_FETCH2(_pz_res, _res_type_name, _res_type_1, _res_type_2) \ 955 | zend_fetch_resource2(Z_RES_P(_pz_res), _res_type_name, _res_type_1, _res_type_2) 956 | #define PHPC_RES_DELETE(_pz_res) \ 957 | zend_list_delete(Z_RES_P(_pz_res)) 958 | #define PHPC_RES_CLOSE(_pz_res) \ 959 | zend_list_close(Z_RES_P(_pz_res)) 960 | 961 | /* resource to zval */ 962 | #define PHPC_RES_PZVAL(_res, _pzv) \ 963 | ZVAL_RES(_pzv, _res) 964 | #define PHPC_RES_RETVAL RETVAL_RES 965 | #define PHPC_RES_RETURN RETURN_RES 966 | 967 | 968 | /* OBJECT */ 969 | #define PHPC_CLASS_REGISTER_EX(_orig_class_entry, _parent_ce, _parent_name) \ 970 | zend_register_internal_class_ex(&_orig_class_entry, _parent_ce) 971 | #define PHPC_CLASS_REGISTER(_orig_class_entry) \ 972 | zend_register_internal_class(&_orig_class_entry) 973 | 974 | /* struct spec */ 975 | #define PHPC_OBJ_STRUCT_MEMBER_FIRST 976 | #define PHPC_OBJ_STRUCT_MEMBER_LAST zend_object std; 977 | #define PHPC_OBJ_STRUCT_BEGIN(_name) \ 978 | PHPC_OBJ_STRUCT_NAME(_name) { PHPC_OBJ_STRUCT_MEMBER_FIRST 979 | #define PHPC_OBJ_STRUCT_END() \ 980 | PHPC_OBJ_STRUCT_MEMBER_LAST }; 981 | 982 | #define PHPC_OBJ_FROM_ZOBJ(_name, _object) \ 983 | (PHPC_OBJ_STRUCT_NAME(_name) *)((char*)(_object) - XtOffsetOf(PHPC_OBJ_STRUCT_NAME(_name), std)) 984 | #define PHPC_OBJ_FROM_ZVAL(_name, _zv) \ 985 | PHPC_OBJ_FROM_ZOBJ(_name, Z_OBJ_P(_zv)) 986 | #if PHP_MAJOR_VERSION < 8 987 | #define PHPC_OBJ_FROM_POBJ PHPC_OBJ_FROM_ZVAL 988 | #else 989 | #define PHPC_OBJ_FROM_POBJ PHPC_OBJ_FROM_ZOBJ 990 | #endif 991 | 992 | /* create_ex object handler helper */ 993 | #define PHPC_OBJ_HANDLER_CREATE_EX(_name) \ 994 | PHPC_OBJ_GET_HANDLER_FCE_INLINE_DEF(zend_object *, _name, create_ex) \ 995 | (zend_class_entry *PHPC_CLASS_TYPE, int _phpc_init_props) 996 | #define PHPC_OBJ_HANDLER_CREATE_EX_IS_NEW() _phpc_init_props 997 | #define PHPC_OBJ_HANDLER_CREATE_EX_DECLARE() PHPC_NOOP 998 | #define PHPC_OBJ_HANDLER_CREATE_EX_ALLOC(_name) \ 999 | ecalloc(1, sizeof(PHPC_OBJ_STRUCT_NAME(_name)) + sizeof(zval) * (PHPC_CLASS_TYPE->default_properties_count - 1)); 1000 | #define PHPC_OBJ_HANDLER_INIT_CREATE_EX_PROPS(_intern) \ 1001 | do { \ 1002 | zend_object_std_init(&_intern->std, PHPC_CLASS_TYPE); \ 1003 | if (_phpc_init_props) { \ 1004 | PHPC_OBJ_PROPERTIES_INIT(&_intern->std, PHPC_CLASS_TYPE); \ 1005 | } \ 1006 | } while(0) 1007 | #define PHPC_OBJ_HANDLER_CREATE_EX_RETURN_EX(_name, _intern) \ 1008 | do { \ 1009 | _intern->std.handlers = &PHPC_OBJ_GET_HANDLER_VAR_NAME(_name); \ 1010 | return &_intern->std; \ 1011 | } while(0) 1012 | 1013 | /* create object handler */ 1014 | #define PHPC_OBJ_HANDLER_CREATE(_name) \ 1015 | PHPC_OBJ_DEFINE_HANDLER_FCE(zend_object *, _name, create) \ 1016 | (zend_class_entry *PHPC_CLASS_TYPE) 1017 | #define PHPC_OBJ_HANDLER_CREATE_RETURN(_name) \ 1018 | return PHPC_OBJ_GET_HANDLER_FCE(_name, create_ex)(PHPC_CLASS_TYPE, 1) 1019 | 1020 | /* clone object handler */ 1021 | #define PHPC_OBJ_HANDLER_CLONE(_name) \ 1022 | PHPC_OBJ_DEFINE_HANDLER_FCE(zend_object *, _name, clone)(phpc_obj_t *PHPC_SELF) 1023 | #define PHPC_OBJ_HANDLER_CLONE_DECLARE() PHPC_NOOP 1024 | #define PHPC_OBJ_HANDLER_CLONE_MEMBERS(_name, _new_obj, _old_obj) \ 1025 | do { \ 1026 | _new_obj = PHPC_OBJ_FROM_ZOBJ(_name, PHPC_OBJ_GET_HANDLER_FCE(_name, create_ex)(_old_obj->std.ce, 0)); \ 1027 | zend_objects_clone_members(&_new_obj->std, &_old_obj->std); \ 1028 | } while(0) 1029 | #define PHPC_OBJ_HANDLER_CLONE_RETURN_EX(_new_obj) return &_new_obj->std; 1030 | 1031 | /* free object handler */ 1032 | #define PHPC_OBJ_HANDLER_FREE(_name) \ 1033 | PHPC_OBJ_DEFINE_HANDLER_FCE(void, _name, free)(zend_object *_phpc_object) 1034 | #define PHPC_OBJ_HANDLER_FREE_DTOR(_intern) \ 1035 | zend_object_std_dtor(&(_intern)->std) 1036 | 1037 | /* compare object handler */ 1038 | #define PHPC_OBJ_HANDLER_COMPARE(_name) \ 1039 | PHPC_OBJ_DEFINE_HANDLER_FCE(int, _name, compare)(zval *_phpc_obj1, zval *_phpc_obj2) 1040 | #define PHPC_OBJ_HANDLER_COMPARE_FETCH(_name, _id, _obj) \ 1041 | PHPC_OBJ_STRUCT_DECLARE(_name, _obj) = PHPC_OBJ_FROM_ZVAL(_name, _phpc_obj ## _id) 1042 | 1043 | /* handler setters */ 1044 | #define PHPC_OBJ_SET_SPECIFIC_HANDLER_OFFSET(_handlers, _name) \ 1045 | (_handlers).offset = XtOffsetOf(PHPC_OBJ_STRUCT_NAME(_name), std) 1046 | #define PHPC_OBJ_SET_SPECIFIC_HANDLER_FREE(_handlers, _name) \ 1047 | (_handlers).free_obj = PHPC_OBJ_GET_HANDLER_FCE(_name, free) 1048 | 1049 | /* read propery */ 1050 | #define PHPC_READ_PROPERTY_RV_NAME _phpc_read_property_rv 1051 | #define PHPC_READ_PROPERTY_RV_DECLARE zval PHPC_READ_PROPERTY_RV_NAME 1052 | #define PHPC_READ_PROPERTY(_scope, _object, _name, _name_len, _silent) \ 1053 | zend_read_property(_scope, PHPC_OBJ_FOR_PROP(_object), _name, _name_len, _silent, &PHPC_READ_PROPERTY_RV_NAME) 1054 | 1055 | 1056 | /* HASH */ 1057 | 1058 | /* recursion protection */ 1059 | #if PHP_VERSION_ID < 70299 1060 | #define PHPC_HASH_HAS_APPLY_COUNT(_tht) (ZEND_HASH_GET_APPLY_COUNT(_tht) > 0) 1061 | #define PHPC_HASH_GET_APPLY_COUNT ZEND_HASH_GET_APPLY_COUNT 1062 | #define PHPC_HASH_INC_APPLY_COUNT ZEND_HASH_INC_APPLY_COUNT 1063 | #define PHPC_HASH_DEC_APPLY_COUNT ZEND_HASH_DEC_APPLY_COUNT 1064 | #define PHPC_HASH_APPLY_PROTECTION ZEND_HASH_APPLY_PROTECTION 1065 | #else 1066 | #define PHPC_HASH_HAS_APPLY_COUNT GC_IS_RECURSIVE 1067 | #define PHPC_HASH_GET_APPLY_COUNT GC_IS_RECURSIVE 1068 | #define PHPC_HASH_INC_APPLY_COUNT GC_PROTECT_RECURSION 1069 | #define PHPC_HASH_DEC_APPLY_COUNT GC_UNPROTECT_RECURSION 1070 | #define PHPC_HASH_APPLY_PROTECTION(_tht) (!(GC_FLAGS(_tht) & GC_IMMUTABLE)) 1071 | #endif 1072 | /* add ptr */ 1073 | #define PHPC_HASH_INDEX_ADD_PTR(_ht, _idx, _ptr, _ptr_size) \ 1074 | zend_hash_index_add_ptr(_ht, _idx, _ptr) 1075 | #define PHPC_HASH_STR_ADD_PTR(_ht, _str, _ptr, _ptr_size) \ 1076 | zend_hash_add_ptr(_ht, _str, _ptr) 1077 | #define PHPC_HASH_CSTRL_ADD_PTR(_ht, _cstr_value, _cstr_len, _ptr, _ptr_size) \ 1078 | zend_hash_str_add_ptr(_ht, _cstr_value, _cstr_len, _ptr) 1079 | #define PHPC_HASH_CSTR_ADD_PTR(_ht, _cstr_value, _ptr, _ptr_size) \ 1080 | zend_hash_str_add_ptr(_ht, _cstr_value, strlen(_cstr_value), _ptr) 1081 | /* add */ 1082 | #define PHPC_HASH_INDEX_ADD zend_hash_index_add 1083 | #define PHPC_HASH_STR_ADD zend_hash_add 1084 | #define PHPC_HASH_CSTRL_ADD zend_hash_str_add 1085 | #define PHPC_HASH_CSTR_ADD(_ht, _cstr_value, _pzv) \ 1086 | zend_hash_str_add(_ht, _cstr_value, strlen(_cstr_value), _pzv) 1087 | 1088 | /* next insert */ 1089 | #define PHPC_HASH_NEXT_INDEX_INSERT_PTR(_ht, _ptr, _ptr_size) \ 1090 | zend_hash_next_index_insert_ptr(_ht, _ptr) 1091 | #define PHPC_HASH_NEXT_INDEX_INSERT zend_hash_next_index_insert 1092 | 1093 | /* update ptr */ 1094 | #define PHPC_HASH_INDEX_UPDATE_PTR(_ht, _idx, _ptr, _ptr_size) \ 1095 | zend_hash_index_update_ptr(_ht, _idx, _ptr) 1096 | #define PHPC_HASH_STR_UPDATE_PTR(_ht, _str, _ptr, _ptr_size) \ 1097 | zend_hash_update_ptr(_ht, _str, _ptr) 1098 | #define PHPC_HASH_CSTRL_UPDATE_PTR(_ht, _cstr_value, _cstr_len, _ptr, _ptr_size) \ 1099 | zend_hash_str_update_ptr(_ht, _cstr_value, _cstr_len, _ptr) 1100 | #define PHPC_HASH_CSTR_UPDATE_PTR(_ht, _cstr_value, _ptr, _ptr_size) \ 1101 | zend_hash_str_update_ptr(_ht, _cstr_value, strlen(_cstr_value), _ptr) 1102 | /* update */ 1103 | #define PHPC_HASH_INDEX_UPDATE zend_hash_index_update 1104 | #define PHPC_HASH_STR_UPDATE zend_hash_update 1105 | #define PHPC_HASH_CSTRL_UPDATE zend_hash_str_update 1106 | #define PHPC_HASH_CSTR_UPDATE(_ht, _cstr_value, _pzv) \ 1107 | zend_hash_str_update(_ht, _cstr_value, strlen(_cstr_value), _pzv) 1108 | 1109 | /* delete */ 1110 | #define PHPC_HASH_INDEX_DELETE zend_hash_index_del 1111 | #define PHPC_HASH_STR_DELETE zend_hash_del 1112 | #define PHPC_HASH_CSTRL_DELETE zend_hash_str_del 1113 | #define PHPC_HASH_CSTR_DELETE(_ht, _cstr_value) \ 1114 | zend_hash_str_del(_ht, _cstr_value, strlen(_cstr_value)) 1115 | 1116 | /* exists */ 1117 | #define PHPC_HASH_INDEX_EXISTS zend_hash_index_exists 1118 | #define PHPC_HASH_STR_EXISTS zend_hash_exists 1119 | #define PHPC_HASH_CSTRL_EXISTS zend_hash_str_exists 1120 | #define PHPC_HASH_CSTR_EXISTS(_ht, _cstr_value) \ 1121 | zend_hash_str_exists(_ht, _cstr_value, strlen(_cstr_value)) 1122 | 1123 | /* find */ 1124 | #define PHPC_HASH_STR_FIND(_ht, _str, _ppv) \ 1125 | _ppv = zend_hash_find(_ht, _str) 1126 | #define PHPC_HASH_CSTRL_FIND(_ht, _cstr_value, _cstr_len, _ppv) \ 1127 | _ppv = zend_hash_str_find(_ht, _cstr_value, _cstr_len) 1128 | #define PHPC_HASH_CSTR_FIND(_ht, _cstr_value, _ppv) \ 1129 | _ppv = zend_hash_str_find(_ht, _cstr_value, strlen(_cstr_value)) 1130 | #define PHPC_HASH_INDEX_FIND(_ht, _idx, _ppv) \ 1131 | _ppv = zend_hash_index_find(_ht, _idx) 1132 | /* find ptr */ 1133 | #define PHPC_HASH_STR_FIND_PTR(_ht, _str, _ptr) \ 1134 | _ptr = zend_hash_find_ptr(_ht, _str) 1135 | #define PHPC_HASH_CSTRL_FIND_PTR(_ht, _cstr_value, _cstr_len, _ptr) \ 1136 | _ptr = zend_hash_str_find_ptr(_ht, _cstr_value, _cstr_len) 1137 | #define PHPC_HASH_CSTR_FIND_PTR(_ht, _cstr_value, _ptr) \ 1138 | _ptr = zend_hash_str_find_ptr(_ht, _cstr_value, strlen(_cstr_value)) 1139 | #define PHPC_HASH_INDEX_FIND_PTR(_ht, _idx, _ptr) \ 1140 | _ptr = zend_hash_index_find_ptr(_ht, _idx) 1141 | /* not found value */ 1142 | #define PHPC_HASH_NOT_FOUND NULL 1143 | 1144 | /* iteration for each element */ 1145 | #define PHPC_HASH_FOREACH_KEY ZEND_HASH_FOREACH_KEY 1146 | #define PHPC_HASH_FOREACH_VAL ZEND_HASH_FOREACH_VAL 1147 | #define PHPC_HASH_FOREACH_VAL_IND ZEND_HASH_FOREACH_VAL_IND 1148 | #define PHPC_HASH_FOREACH_KEY_VAL ZEND_HASH_FOREACH_KEY_VAL 1149 | #define PHPC_HASH_FOREACH_KEY_VAL_IND ZEND_HASH_FOREACH_KEY_VAL_IND 1150 | #define PHPC_HASH_FOREACH_STR_KEY_VAL ZEND_HASH_FOREACH_STR_KEY_VAL 1151 | #define PHPC_HASH_FOREACH_STR_KEY_VAL_IND ZEND_HASH_FOREACH_STR_KEY_VAL_IND 1152 | #define PHPC_HASH_FOREACH_END ZEND_HASH_FOREACH_END 1153 | 1154 | /* key and data getter */ 1155 | #define PHPC_HASH_GET_CURRENT_KEY_EX(_ht, _str, _num_index, _pos) \ 1156 | zend_hash_get_current_key_ex(_ht, &_str, &_num_index, _pos) 1157 | #define PHPC_HASH_GET_CURRENT_DATA_EX(_ht, _val, _pos) \ 1158 | _val = zend_hash_get_current_data_ex(_ht, _pos) 1159 | 1160 | #define PHPC_HASH_GET_CURRENT_KEY(_ht, _str, _num_index) \ 1161 | zend_hash_get_current_key(_ht, &_str, &_num_index) 1162 | #define PHPC_HASH_GET_CURRENT_DATA(_ht, _val) \ 1163 | _val = zend_hash_get_current_data(_ht) 1164 | 1165 | /* copy */ 1166 | #define PHPC_HASH_COPY_EX(_target, _source, _copy_ctr) \ 1167 | zend_hash_copy(_target, _source, NULL) 1168 | 1169 | /* hash to zval */ 1170 | #define PHPC_HASH_PZVAL(_ht, _pzv) \ 1171 | ZVAL_ARR(_pzv, _ht) 1172 | #define PHPC_HASH_RETVAL RETVAL_ARR 1173 | #define PHPC_HASH_RETURN RETURN_ARR 1174 | 1175 | 1176 | /* SYMTABLE */ 1177 | 1178 | /* update*/ 1179 | #define PHPC_SYMTABLE_UPDATE zend_symtable_update 1180 | 1181 | 1182 | /* ARRAY */ 1183 | 1184 | #define PHPC_ARRAY_ADD_ASSOC_NULL_EX add_assoc_null_ex 1185 | #define PHPC_ARRAY_ADD_ASSOC_BOOL_EX add_assoc_bool_ex 1186 | #define PHPC_ARRAY_ADD_ASSOC_LONG_EX add_assoc_long_ex 1187 | #define PHPC_ARRAY_ADD_ASSOC_RESOURCE_EX add_assoc_resource_ex 1188 | #define PHPC_ARRAY_ADD_ASSOC_DOUBLE_EX add_assoc_double_ex 1189 | #define PHPC_ARRAY_ADD_ASSOC_STR_EX add_assoc_str_ex 1190 | #define PHPC_ARRAY_ADD_ASSOC_CSTR_EX add_assoc_string_ex 1191 | #define PHPC_ARRAY_ADD_ASSOC_CSTRL_EX add_assoc_stringl_ex 1192 | #define PHPC_ARRAY_ADD_ASSOC_ZVAL_EX add_assoc_zval_ex 1193 | #define PHPC_ARRAY_ADD_ASSOC_VAL_EX(_arr, _key, _key_len, _pv) \ 1194 | add_assoc_zval_ex(_arr, _key, _key_len, &_pv) 1195 | 1196 | #define PHPC_ARRAY_ADD_ASSOC_STR add_assoc_str 1197 | #define PHPC_ARRAY_ADD_ASSOC_CSTR add_assoc_string 1198 | #define PHPC_ARRAY_ADD_ASSOC_CSTRL add_assoc_stringl 1199 | #define PHPC_ARRAY_ADD_ASSOC_VAL(_arr, _key, _pv) \ 1200 | add_assoc_zval(_arr, _key, &_pv) 1201 | 1202 | #define PHPC_ARRAY_ADD_INDEX_STR add_index_str 1203 | #define PHPC_ARRAY_ADD_INDEX_CSTR add_index_string 1204 | #define PHPC_ARRAY_ADD_INDEX_CSTRL add_index_stringl 1205 | #define PHPC_ARRAY_ADD_INDEX_VAL(_arr, _idx, _pv) \ 1206 | add_index_zval(_arr, _idx, &_pv) 1207 | 1208 | #define PHPC_ARRAY_ADD_NEXT_INDEX_STR add_next_index_str 1209 | #define PHPC_ARRAY_ADD_NEXT_INDEX_CSTR add_next_index_string 1210 | #define PHPC_ARRAY_ADD_NEXT_INDEX_CSTRL add_next_index_stringl 1211 | #define PHPC_ARRAY_ADD_NEXT_INDEX_VAL(_arr, _pv) \ 1212 | add_next_index_zval(_arr, &_pv) 1213 | 1214 | /* FCALL */ 1215 | #define PHPC_FCALL_PARAMS_DECLARE(_pname, _count) \ 1216 | zval PHPC_FCALL_PARAMS_NAME(_pname)[_count] 1217 | 1218 | #define PHPC_FCALL_PARAMS_INIT(_pname) PHPC_NOOP 1219 | 1220 | #define PHPC_FCALL_PARAM_PZVAL(_pname, _idx) \ 1221 | &PHPC_FCALL_PARAMS_NAME(_pname)[_idx] 1222 | 1223 | #define PHPC_FCALL_PARAM_VAL(_pname, _idx) \ 1224 | PHPC_FCALL_PARAMS_NAME(_pname)[_idx] 1225 | 1226 | #define PHPC_FCALL_PARAM_UNDEF(_pname, _idx) \ 1227 | ZVAL_UNDEF(PHPC_FCALL_PARAM_PZVAL(_pname, _idx)) 1228 | 1229 | #define PHPC_FCALL_RETVAL(_fci, _pv) \ 1230 | (_fci).retval = (&_pv) 1231 | 1232 | 1233 | /* ZVAL */ 1234 | typedef zval phpc_val; 1235 | 1236 | #define PHPC_TYPE Z_TYPE 1237 | #define PHPC_TYPE_P Z_TYPE_P 1238 | 1239 | #define PHPC_LVAL Z_LVAL 1240 | #define PHPC_LVAL_P Z_LVAL_P 1241 | 1242 | #define PHPC_DVAL Z_DVAL 1243 | #define PHPC_DVAL_P Z_DVAL_P 1244 | 1245 | #define PHPC_STRVAL Z_STRVAL 1246 | #define PHPC_STRVAL_P Z_STRVAL_P 1247 | 1248 | #define PHPC_STRLEN Z_STRLEN 1249 | #define PHPC_STRLEN_P Z_STRLEN_P 1250 | 1251 | #define PHPC_ARRVAL Z_ARRVAL 1252 | #define PHPC_ARRVAL_P Z_ARRVAL_P 1253 | 1254 | #define PHPC_OBJ_HT Z_OBJ_HT 1255 | #define PHPC_OBJ_HT_P Z_OBJ_HT_P 1256 | 1257 | #define PHPC_OBJ_HANDLER Z_OBJ_HANDLER 1258 | #define PHPC_OBJ_HANDLER_P Z_OBJ_HANDLER_P 1259 | 1260 | #define PHPC_OBJ_HANDLE Z_OBJ_HANDLE 1261 | #define PHPC_OBJ_HANDLE_P Z_OBJ_HANDLE_P 1262 | 1263 | #define PHPC_OBJCE Z_OBJCE 1264 | #define PHPC_OBJCE_P Z_OBJCE_P 1265 | 1266 | #define PHPC_OBJPROP Z_OBJPROP 1267 | #define PHPC_OBJPROP_P Z_OBJPROP_P 1268 | 1269 | #define PHPC_OBJDEBUG Z_OBJDEBUG 1270 | #define PHPC_OBJDEBUG_P Z_OBJDEBUG_P 1271 | 1272 | #define PHPC_REFCOUNTED Z_REFCOUNTED 1273 | #define PHPC_REFCOUNTED_P Z_REFCOUNTED_P 1274 | 1275 | #define PHPC_PZVAL_CAST_TO_PVAL(_pzv) _pzv 1276 | 1277 | #define PHPC_VAL_CAST_TO_ZVAL(_pv) _pv 1278 | #define PHPC_VAL_CAST_TO_PZVAL(_pv) &(_pv) 1279 | #define PHPC_PVAL_CAST_TO_PZVAL(_ppv) _ppv 1280 | 1281 | #define PHPC_VAL_TO_ZVAL(_pv, _zv) _zv = _pv 1282 | #define PHPC_VAL_TO_PZVAL(_pv, _zv) _zv = &(_pv) 1283 | #define PHPC_PVAL_TO_PZVAL(_ppv, _zv) _zv = _ppv 1284 | 1285 | #define PHPC_VAL_MAKE(_pv) PHPC_NOOP 1286 | #define PHPC_VAL_FREE(_pv) PHPC_NOOP 1287 | #define PHPC_VAL_UNDEF(_pv) ZVAL_UNDEF(&(_pv)) 1288 | #define PHPC_VAL_ISUNDEF(_pv) Z_ISUNDEF(_pv) 1289 | #define PHPC_VAL_COPY(_pv, _zv) ZVAL_COPY(&(_pv), _zv) 1290 | #define PHPC_VAL_ASSIGN PHPC_VAL_COPY 1291 | 1292 | #define PHPC_PZVAL_MAKE(_pzv) PHPC_NOOP 1293 | #define PHPC_PZVAL_FREE(_pzv) PHPC_NOOP 1294 | #define PHPC_PZVAL_SET(_pv, _zv) _pv = _zv 1295 | #define PHPC_PVAL_DEREF ZVAL_DEREF 1296 | #define PHPC_PZVAL_DEREF ZVAL_DEREF 1297 | 1298 | #define PHPC_PZVAL_COPY_INIT ZVAL_COPY_VALUE 1299 | #define PHPC_PZVAL_COPY ZVAL_COPY_VALUE 1300 | 1301 | #define PHPC_VAL_NEW_STR(_pv, _str) \ 1302 | ZVAL_NEW_STR(&_pv, _str) 1303 | #define PHPC_VAL_STR(_pv, _str) \ 1304 | ZVAL_STR(&_pv, _str) 1305 | #define PHPC_VAL_CSTR(_pv, _cstr) \ 1306 | ZVAL_STRING(&_pv, _cstr) 1307 | #define PHPC_VAL_CSTRL(_pv, _cstr, _cstr_len) \ 1308 | ZVAL_STRINGL(&_pv, _cstr, _cstr_len) 1309 | 1310 | #define PHPC_PZVAL_NEW_STR ZVAL_NEW_STR 1311 | #define PHPC_PZVAL_STR ZVAL_STR 1312 | #define PHPC_PZVAL_CSTR ZVAL_STRING 1313 | #define PHPC_PZVAL_CSTRL ZVAL_STRINGL 1314 | 1315 | #define PHPC_ZVAL_COPY(_zv_dst, _zv_src) \ 1316 | ZVAL_COPY_VALUE(&_zv_dst, &_zv_src) 1317 | 1318 | #define PHPC_ZVAL_NEW_STR PHPC_VAL_NEW_STR 1319 | #define PHPC_ZVAL_STR PHPC_VAL_STR 1320 | #define PHPC_ZVAL_CSTR PHPC_VAL_CSTR 1321 | #define PHPC_ZVAL_CSTRL PHPC_VAL_CSTRL 1322 | 1323 | #define PHPC_ZVAL_IS_TRUE(_zv) \ 1324 | (Z_TYPE(_zv) == IS_TRUE) 1325 | #define PHPC_ZVAL_IS_FALSE(_zv) \ 1326 | (Z_TYPE(_zv) == IS_FALSE) 1327 | 1328 | #define PHPC_VAL_IS_TRUE PHPC_ZVAL_IS_TRUE 1329 | #define PHPC_VAL_IS_FALSE PHPC_ZVAL_IS_FALSE 1330 | 1331 | #define PHPC_FE_END PHP_FE_END 1332 | 1333 | 1334 | /* ZPP */ 1335 | 1336 | /* path flag */ 1337 | #define PHPC_ZPP_PATH_FLAG "p" 1338 | 1339 | /* args */ 1340 | #define PHPC_ZPP_ARGS_DECLARE() \ 1341 | int _phpc_zpp_args_count = 0; \ 1342 | zval *_phpc_zpp_args_array 1343 | 1344 | #define PHPC_ZPP_ARGS_LOAD_EX(_flag, _num_args, _return) \ 1345 | do { \ 1346 | if (zend_parse_parameters(_num_args, #_flag, \ 1347 | &_phpc_zpp_args_array, &_phpc_zpp_args_count) == FAILURE) { \ 1348 | _return; \ 1349 | } \ 1350 | } while(0) 1351 | 1352 | #define PHPC_ZPP_ARGS_GET_PVAL(_arg_pos) \ 1353 | &_phpc_zpp_args_array[_arg_pos] 1354 | 1355 | #define PHPC_ZPP_ARGS_FREE() PHPC_NOOP 1356 | 1357 | 1358 | /* STREAM */ 1359 | typedef const char phpc_stream_opener_char_t; 1360 | #define PHPC_STREAM_WRAPPERDATA_ALLOC(stream) PHPC_NOOP 1361 | #define PHPC_STREAM_WRAPPERDATA_ISSET(stream) (Z_TYPE(stream->wrapperdata) != IS_UNDEF) 1362 | #define PHPC_STREAM_WRAPPERDATA_UNSET(stream) \ 1363 | do { \ 1364 | zval_ptr_dtor(&stream->wrapperdata); \ 1365 | ZVAL_UNDEF(&stream->wrapperdata); \ 1366 | } while(0) 1367 | #define PHPC_STREAM_CONTEXT_GET_OPTION(_ctx, _wrappername, _optionname, _ppv) \ 1368 | _ppv = php_stream_context_get_option(_ctx, _wrappername, _optionname) 1369 | #define PHPC_STREAM_CONTEXT_OPTION_NOT_FOUND NULL 1370 | 1371 | #endif /* PHP_MAJOR_VERSION */ 1372 | 1373 | 1374 | /* COMMON (dependent definitions) */ 1375 | 1376 | /* object structure */ 1377 | #define PHP_OBJ_GET_HANDLER_OBJ_FROM_ZOBJ(_name) \ 1378 | PHPC_OBJ_FROM_ZOBJ(_name, _phpc_object) 1379 | #define PHPC_OBJ_STRUCT_DECLARE_AND_FETCH_FROM_ZOBJ(_name, _ptr) \ 1380 | PHPC_OBJ_STRUCT_DECLARE(_name, _ptr) = PHP_OBJ_GET_HANDLER_OBJ_FROM_ZOBJ(_name) 1381 | #define PHPC_OBJ_FROM_SELF(_name) \ 1382 | PHPC_OBJ_FROM_POBJ(_name, PHPC_SELF) 1383 | 1384 | 1385 | /* this object */ 1386 | #define PHPC_THIS _phpc_this 1387 | #define PHPC_THIS_DECLARE(_name) PHPC_OBJ_STRUCT_DECLARE(_name, PHPC_THIS) 1388 | #define PHPC_THIS_FETCH_FROM_ZVAL(_name, _zv) \ 1389 | PHPC_THIS = PHPC_OBJ_FROM_ZVAL(_name, _zv) 1390 | #define PHPC_THIS_FETCH(_name) \ 1391 | PHPC_THIS_FETCH_FROM_ZVAL(_name, getThis()) 1392 | #define PHPC_THIS_DECLARE_AND_FETCH_FROM_ZVAL(_name, _zv) \ 1393 | PHPC_THIS_DECLARE(_name) = PHPC_THIS_FETCH_FROM_ZVAL(_name, _zv) 1394 | #define PHPC_THIS_FETCH_FROM_SELF(_name) \ 1395 | PHPC_THIS = PHPC_OBJ_FROM_SELF(_name) 1396 | #define PHPC_THIS_DECLARE_AND_FETCH_FROM_SELF(_name) \ 1397 | PHPC_THIS_DECLARE(_name) = PHPC_OBJ_FROM_SELF(_name) 1398 | #define PHPC_THIS_DECLARE_AND_FETCH(_name) \ 1399 | PHPC_THIS_DECLARE_AND_FETCH_FROM_ZVAL(_name, getThis()) 1400 | 1401 | /* that object */ 1402 | #define PHPC_THAT _phpc_that 1403 | #define PHPC_THAT_DECLARE(_name) PHPC_OBJ_STRUCT_DECLARE(_name, PHPC_THAT) 1404 | 1405 | /* object helper create_ex */ 1406 | #define PHPC_OBJ_HANDLER_CREATE_EX_INIT(_name) \ 1407 | PHPC_OBJ_HANDLER_CREATE_EX_DECLARE(); \ 1408 | PHPC_THIS_DECLARE(_name); \ 1409 | PHPC_THIS = PHPC_OBJ_HANDLER_CREATE_EX_ALLOC(_name); \ 1410 | PHPC_OBJ_HANDLER_INIT_CREATE_EX_PROPS(PHPC_THIS) 1411 | #define PHPC_OBJ_HANDLER_CREATE_EX_RETURN(_name) \ 1412 | PHPC_OBJ_HANDLER_CREATE_EX_RETURN_EX(_name, PHPC_THIS) 1413 | 1414 | /* object handler clone */ 1415 | #define PHPC_OBJ_HANDLER_CLONE_INIT(_name) \ 1416 | PHPC_OBJ_HANDLER_CLONE_DECLARE(); \ 1417 | PHPC_THIS_DECLARE(_name); \ 1418 | PHPC_THAT_DECLARE(_name); \ 1419 | PHPC_THIS = PHPC_OBJ_FROM_SELF(_name); \ 1420 | PHPC_OBJ_HANDLER_CLONE_MEMBERS(_name, PHPC_THAT, PHPC_THIS) 1421 | #define PHPC_OBJ_HANDLER_CLONE_RETURN() \ 1422 | PHPC_OBJ_HANDLER_CLONE_RETURN_EX(PHPC_THAT) 1423 | 1424 | /* object handler free */ 1425 | #define PHPC_OBJ_HANDLER_FREE_INIT(_name) \ 1426 | PHPC_OBJ_STRUCT_DECLARE_AND_FETCH_FROM_ZOBJ(_name, PHPC_THIS); 1427 | #define PHPC_OBJ_HANDLER_FREE_DESTROY() \ 1428 | PHPC_OBJ_HANDLER_FREE_DTOR(PHPC_THIS) 1429 | 1430 | /* object handler compare */ 1431 | #define PHPC_OBJ_HANDLER_COMPARE_INIT(_name) \ 1432 | PHPC_OBJ_HANDLER_COMPARE_FETCH(_name, 1, PHPC_THIS); \ 1433 | PHPC_OBJ_HANDLER_COMPARE_FETCH(_name, 2, PHPC_THAT) 1434 | 1435 | /* object handler get_gc */ 1436 | #define PHPC_GC_TABLE _phpc_gc_table 1437 | #define PHPC_GC_N _phpc_gc_n 1438 | #define PHPC_OBJ_HANDLER_GET_GC(_name) \ 1439 | PHPC_OBJ_DEFINE_HANDLER_FCE(HashTable *, _name, get_gc)\ 1440 | (phpc_obj_t *PHPC_SELF, phpc_val **PHPC_GC_TABLE, int *PHPC_GC_N TSRMLS_DC) 1441 | 1442 | /* object handler get_debug_info */ 1443 | #define PHPC_DEBUG_INFO_IS_TEMP _phpc_debug_info_is_temp 1444 | #define PHPC_OBJ_HANDLER_GET_DEBUG_INFO(_name) \ 1445 | PHPC_OBJ_DEFINE_HANDLER_FCE(HashTable *, _name, get_debug_info)\ 1446 | (phpc_obj_t *PHPC_SELF, int *PHPC_DEBUG_INFO_IS_TEMP TSRMLS_DC) 1447 | 1448 | /* object handler get_properties */ 1449 | #define PHPC_OBJ_HANDLER_GET_PROPERTIES(_name) \ 1450 | PHPC_OBJ_DEFINE_HANDLER_FCE(HashTable *, _name, get_properties)\ 1451 | (phpc_obj_t *PHPC_SELF TSRMLS_DC) 1452 | 1453 | /* object handler setters */ 1454 | #define PHPC_CLASS_SET_HANDLER_CREATE(_class_entry, _name) \ 1455 | _class_entry.create_object = PHPC_OBJ_GET_HANDLER_FCE(_name, create) 1456 | #define PHPC_OBJ_SET_SPECIFIC_HANDLER_CLONE(_handlers, _name) \ 1457 | (_handlers).clone_obj = PHPC_OBJ_GET_HANDLER_FCE(_name, clone) 1458 | #define PHPC_OBJ_SET_HANDLER_CLONE(_name) \ 1459 | PHPC_OBJ_SET_SPECIFIC_HANDLER_CLONE(PHPC_OBJ_GET_HANDLER_VAR_NAME(_name), _name) 1460 | #define PHPC_OBJ_SET_HANDLER_COMPARE(_name) \ 1461 | PHPC_OBJ_GET_HANDLER_VAR_NAME(_name).PHPC_OBJ_HANDLER_COMPARE_NAME \ 1462 | = PHPC_OBJ_GET_HANDLER_FCE(_name, compare) 1463 | #define PHPC_OBJ_HAS_HANDLER_GET_GC (PHP_VERSION_ID > 50399) 1464 | #if PHPC_OBJ_HAS_HANDLER_GET_GC 1465 | #define PHPC_OBJ_SET_HANDLER_GET_GC(_name) \ 1466 | PHPC_OBJ_GET_HANDLER_VAR_NAME(_name).get_gc = PHPC_OBJ_GET_HANDLER_FCE(_name, get_gc) 1467 | #else 1468 | #define PHPC_OBJ_SET_HANDLER_GET_GC(_name) PHPC_NOOP 1469 | #endif 1470 | #define PHPC_OBJ_HAS_HANDLER_GET_DEBUG_INFO (PHP_VERSION_ID > 50299) 1471 | #if PHPC_OBJ_HAS_HANDLER_GET_DEBUG_INFO 1472 | #define PHPC_OBJ_SET_HANDLER_GET_DEBUG_INFO(_name) \ 1473 | PHPC_OBJ_GET_HANDLER_VAR_NAME(_name).get_debug_info = PHPC_OBJ_GET_HANDLER_FCE(_name, get_debug_info) 1474 | #else 1475 | #define PHPC_OBJ_SET_HANDLER_GET_DEBUG_INFO(_name) PHPC_NOOP 1476 | #endif 1477 | /* there is such handler in 5.2 but we would have to re-implement zend_std_get_properties */ 1478 | #define PHPC_OBJ_HAS_HANDLER_GET_PROPERTIES (PHP_VERSION_ID > 50299) 1479 | #if PHPC_OBJ_HAS_HANDLER_GET_PROPERTIES 1480 | #define PHPC_OBJ_SET_HANDLER_GET_PROPERTIES(_name) \ 1481 | PHPC_OBJ_GET_HANDLER_VAR_NAME(_name).get_properties = PHPC_OBJ_GET_HANDLER_FCE(_name, get_properties) 1482 | #else 1483 | #define PHPC_OBJ_SET_HANDLER_GET_PROPERTIES(_name) PHPC_NOOP 1484 | #endif 1485 | #define PHPC_OBJ_SET_HANDLER_OFFSET(_name) \ 1486 | PHPC_OBJ_SET_SPECIFIC_HANDLER_OFFSET(PHPC_OBJ_GET_HANDLER_VAR_NAME(_name), _name) 1487 | #define PHPC_OBJ_SET_HANDLER_FREE(_name) \ 1488 | PHPC_OBJ_SET_SPECIFIC_HANDLER_FREE(PHPC_OBJ_GET_HANDLER_VAR_NAME(_name), _name) 1489 | 1490 | /* hash */ 1491 | #define PHPC_HASH_ALLOC ALLOC_HASHTABLE 1492 | #define PHPC_HASH_INIT zend_hash_init 1493 | #define PHPC_HASH_NUM_ELEMENTS zend_hash_num_elements 1494 | 1495 | #define PHPC_HASH_HAS_MORE_ELEMENTS_EX zend_hash_has_more_elements_ex 1496 | #define PHPC_HASH_MOVE_FORWARD_EX zend_hash_move_forward_ex 1497 | #define PHPC_HASH_MOVE_BACKWARDS_EX zend_hash_move_backwards_ex 1498 | #define PHPC_HASH_GET_CURRENT_KEY_ZVAL_EX zend_hash_get_current_key_zval_ex 1499 | #define PHPC_HASH_GET_CURRENT_KEY_TYPE_EX zend_hash_get_current_key_type_ex 1500 | #define PHPC_HASH_INTERNAL_POINTER_RESET_EX zend_hash_internal_pointer_reset_ex 1501 | #define PHPC_HASH_INTERNAL_POINTER_END_EX zend_hash_internal_pointer_end_ex 1502 | 1503 | #define PHPC_HASH_HAS_MORE_ELEMENTS zend_hash_has_more_elements 1504 | #define PHPC_HASH_MOVE_FORWARD zend_hash_move_forward 1505 | #define PHPC_HASH_MOVE_BACKWARDS zend_hash_move_backwards 1506 | #define PHPC_HASH_GET_CURRENT_KEY_ZVAL zend_hash_get_current_key_zval 1507 | #define PHPC_HASH_GET_CURRENT_KEY_TYPE zend_hash_get_current_key_type 1508 | #define PHPC_HASH_INTERNAL_POINTER_RESET zend_hash_internal_pointer_reset 1509 | #define PHPC_HASH_INTERNAL_POINTER_END zend_hash_internal_pointer_end 1510 | 1511 | /* find */ 1512 | #define PHPC_HASH_IS_FOUND(_found) ((_found) != PHPC_HASH_NOT_FOUND) 1513 | /* find in cond */ 1514 | #define PHPC_HASH_STR_FIND_IN_COND(_ht, _str, _ppv) \ 1515 | PHPC_HASH_IS_FOUND(PHPC_HASH_STR_FIND(_ht, _str, _ppv)) 1516 | #define PHPC_HASH_CSTRL_FIND_IN_COND(_ht, _cstr_value, _cstr_len, _ppv) \ 1517 | PHPC_HASH_IS_FOUND(PHPC_HASH_CSTRL_FIND(_ht, _cstr_value, _cstr_len, _ppv)) 1518 | #define PHPC_HASH_CSTR_FIND_IN_COND(_ht, _cstr_value, _ppv) \ 1519 | PHPC_HASH_IS_FOUND(PHPC_HASH_CSTR_FIND(_ht, _cstr_value, _ppv)) 1520 | #define PHPC_HASH_INDEX_FIND_IN_COND(_ht, _idx, _ppv) \ 1521 | PHPC_HASH_IS_FOUND(PHPC_HASH_INDEX_FIND(_ht, _idx, _ppv)) 1522 | /* find ptr in cond */ 1523 | #define PHPC_HASH_STR_FIND_PTR_IN_COND(_ht, _str, _ptr) \ 1524 | PHPC_HASH_IS_FOUND(PHPC_HASH_STR_FIND_PTR(_ht, _str, _ptr)) 1525 | #define PHPC_HASH_CSTRL_FIND_PTR_IN_COND(_ht, _cstr_value, _cstr_len, _ptr) \ 1526 | PHPC_HASH_IS_FOUND(PHPC_HASH_CSTRL_FIND_PTR(_ht, _cstr_value, _cstr_len, _ptr)) 1527 | #define PHPC_HASH_CSTR_FIND_PTR_IN_COND(_ht, _cstr_value, _ptr) \ 1528 | PHPC_HASH_IS_FOUND(PHPC_HASH_CSTR_FIND_PTR(_ht, _cstr_value, _ptr)) 1529 | #define PHPC_HASH_INDEX_FIND_PTR_IN_COND(_ht, _idx, _ptr) \ 1530 | PHPC_HASH_IS_FOUND(PHPC_HASH_INDEX_FIND_PTR(_ht, _idx, _ptr)) 1531 | 1532 | /* copy */ 1533 | #define PHPC_HASH_COPY(_target, _source) \ 1534 | PHPC_HASH_COPY_EX(_target, _source, NULL) 1535 | 1536 | /* array */ 1537 | #define PHPC_ARRAY_INIT array_init 1538 | #if PHP_VERSION_ID < 50299 1539 | #define PHPC_ARRAY_INIT_SIZE(_arr, _size) array_init(_arr) 1540 | #else 1541 | #define PHPC_ARRAY_INIT_SIZE array_init_size 1542 | #endif 1543 | 1544 | #define PHPC_ARRAY_ADD_ASSOC_NULL add_assoc_null 1545 | #define PHPC_ARRAY_ADD_ASSOC_BOOL add_assoc_bool 1546 | #define PHPC_ARRAY_ADD_ASSOC_LONG add_assoc_long 1547 | #define PHPC_ARRAY_ADD_ASSOC_RESOURCE add_assoc_resource 1548 | #define PHPC_ARRAY_ADD_ASSOC_DOUBLE add_assoc_double 1549 | #define PHPC_ARRAY_ADD_ASSOC_ZVAL add_assoc_zval 1550 | 1551 | #define PHPC_ARRAY_ADD_INDEX_NULL add_index_null 1552 | #define PHPC_ARRAY_ADD_INDEX_BOOL add_index_bool 1553 | #define PHPC_ARRAY_ADD_INDEX_LONG add_index_long 1554 | #define PHPC_ARRAY_ADD_INDEX_RESOURCE add_index_resource 1555 | #define PHPC_ARRAY_ADD_INDEX_DOUBLE add_index_double 1556 | #define PHPC_ARRAY_ADD_INDEX_ZVAL add_index_zval 1557 | 1558 | #define PHPC_ARRAY_ADD_NEXT_INDEX_NULL add_next_index_null 1559 | #define PHPC_ARRAY_ADD_NEXT_INDEX_BOOL add_next_index_bool 1560 | #define PHPC_ARRAY_ADD_NEXT_INDEX_LONG add_next_index_long 1561 | #define PHPC_ARRAY_ADD_NEXT_INDEX_RESOURCE add_next_index_resource 1562 | #define PHPC_ARRAY_ADD_NEXT_INDEX_DOUBLE add_next_index_double 1563 | #define PHPC_ARRAY_ADD_NEXT_INDEX_ZVAL add_next_index_zval 1564 | 1565 | /* ZPP */ 1566 | /* alias for path flag */ 1567 | #define PHPC_PATH_ZPP_FLAG PHPC_ZPP_PATH_FLAG 1568 | 1569 | /* args loading */ 1570 | #define PHPC_ZPP_ARGS_LOAD(_flag) PHPC_ZPP_ARGS_LOAD_EX(_flag, ZEND_NUM_ARGS(), return) 1571 | 1572 | #define PHPC_ZPP_ARGS_LOOP_START_EX(_start) \ 1573 | do { \ 1574 | int _phpc_zpp_args_i; \ 1575 | for (_phpc_zpp_args_i = _start; _phpc_zpp_args_i < _phpc_zpp_args_count; _phpc_zpp_args_i++) 1576 | 1577 | #define PHPC_ZPP_ARGS_LOOP_START() PHPC_ZPP_ARGS_LOOP_START_EX(0) 1578 | 1579 | #define PHPC_ZPP_ARGS_LOOP_END() \ 1580 | } while(0) 1581 | 1582 | #define PHPC_ZPP_ARGS_GET_CURRENT_PVAL() PHPC_ZPP_ARGS_GET_PVAL(_phpc_zpp_args_i) 1583 | 1584 | #define PHPC_ZPP_ARGS_COUNT _phpc_zpp_args_count 1585 | 1586 | /* FCALL */ 1587 | #if PHP_API_VERSION < 20090626 1588 | #define PHPC_FCALL_INFO_INIT(_callable, _check_flags, _fci, _fci_cache, _callable_name, _error) \ 1589 | zend_fcall_info_init(_callable, &fci, &fci_cache TSRMLS_CC) 1590 | #else 1591 | #define PHPC_FCALL_INFO_INIT(_callable, _check_flags, _fci, _fci_cache, _callable_name, _error) \ 1592 | zend_fcall_info_init(_callable, _check_flags, _fci, _fci_cache, _callable_name, _error TSRMLS_CC) 1593 | #endif 1594 | 1595 | /* stream */ 1596 | #define PHPC_STREAM_CONTEXT_GET_OPTION_IN_COND(_ctx, _wrappername, _optionname, _ppv) \ 1597 | ((PHPC_STREAM_CONTEXT_GET_OPTION(_ctx, _wrappername, _optionname, _ppv)) != \ 1598 | PHPC_STREAM_CONTEXT_OPTION_NOT_FOUND) 1599 | 1600 | #if (PHP_MAJOR_VERSION == 5 && PHP_MINOR_VERSION >= 6) || (PHP_MAJOR_VERSION > 5) 1601 | #define PHPC_STREAM_LOCATE_URL_WRAPPER(_path, _path_for_open, _options) \ 1602 | php_stream_locate_url_wrapper(_path, (const char **) _path_for_open, _options TSRMLS_CC) 1603 | #else 1604 | #define PHPC_STREAM_LOCATE_URL_WRAPPER(_path, _path_for_open, _options) \ 1605 | php_stream_locate_url_wrapper(_path, (char **) _path_for_open, _options TSRMLS_CC) 1606 | #endif 1607 | 1608 | #if (PHP_MAJOR_VERSION == 8 && PHP_MINOR_VERSION >= 1) || (PHP_MAJOR_VERSION > 8) 1609 | #define PHPC_PHP_STAT(_filename, _filename_length, _type, _return_value) do { \ 1610 | zend_string *_phpc_stat_str = zend_string_init(_filename, _filename_length, 0); \ 1611 | php_stat(_phpc_stat_str, _type, _return_value); \ 1612 | zend_string_release(_phpc_stat_str); \ 1613 | } while (0) 1614 | 1615 | #else 1616 | #define PHPC_PHP_STAT php_stat 1617 | #endif 1618 | 1619 | #endif /* PHPC_H */ 1620 | 1621 | --------------------------------------------------------------------------------