/* {{{ PHP_RINIT_FUNCTION */ static PHP_RINIT_FUNCTION(uopz) { zend_class_entry *ce = NULL; zend_string *spl; #ifdef ZTS ZEND_TSRMLS_CACHE_UPDATE(); #endif spl = zend_string_init(ZEND_STRL("RuntimeException"), 0); spl_ce_RuntimeException = (ce = zend_lookup_class(spl)) ? ce : zend_exception_get_default(); zend_string_release(spl); spl = zend_string_init(ZEND_STRL("InvalidArgumentException"), 0); spl_ce_InvalidArgumentException = (ce = zend_lookup_class(spl)) ? ce : zend_exception_get_default(); zend_string_release(spl); uopz_request_init(); return SUCCESS; } /* }}} */
int uopz_constant_handler(UOPZ_OPCODE_HANDLER_ARGS) { /* {{{ */ #if PHP_VERSION_ID >= 70100 if (CACHED_PTR(Z_CACHE_SLOT_P(EX_CONSTANT(EX(opline)->op2)))) { CACHE_PTR(Z_CACHE_SLOT_P(EX_CONSTANT(EX(opline)->op2)), NULL); } #else if (EX(opline)->op1_type == IS_UNUSED) { if (CACHED_PTR(Z_CACHE_SLOT_P(EX_CONSTANT(EX(opline)->op2)))) { CACHE_PTR(Z_CACHE_SLOT_P(EX_CONSTANT(EX(opline)->op2)), NULL); } } else { zend_string *key = NULL; zval *mock = NULL; zend_class_entry *poser = NULL; if (EX(opline)->op1_type == IS_CONST) { key = zend_string_tolower(Z_STR_P(EX_CONSTANT(EX(opline)->op1))); if ((mock = zend_hash_find(&UOPZ(mocks), key))) { if (Z_TYPE_P(mock) == IS_OBJECT) { poser = Z_OBJCE_P(mock); } else poser = zend_lookup_class(Z_STR_P(mock)); CACHE_PTR(Z_CACHE_SLOT_P(EX_CONSTANT(EX(opline)->op1)), poser); } if (CACHED_PTR(Z_CACHE_SLOT_P(EX_CONSTANT(EX(opline)->op2)))) { CACHE_PTR(Z_CACHE_SLOT_P(EX_CONSTANT(EX(opline)->op2)), NULL); } zend_string_release(key); } else { key = zend_string_tolower(Z_CE_P(EX_VAR(EX(opline)->op1.var))->name); if ((mock = zend_hash_find(&UOPZ(mocks), key))) { if (Z_TYPE_P(mock) == IS_OBJECT) { poser = Z_OBJCE_P(mock); } else poser = zend_lookup_class(Z_STR_P(mock)); Z_CE_P(EX_VAR(EX(opline)->op1.var)) = poser; } CACHE_POLYMORPHIC_PTR(Z_CACHE_SLOT_P(EX_CONSTANT(EX(opline)->op2)), Z_CE_P(EX_VAR(EX(opline)->op1.var)), NULL); zend_string_release(key); } } #endif if (uopz_fetch_constant_handler) { return uopz_fetch_constant_handler(UOPZ_OPCODE_HANDLER_ARGS_PASSTHRU); } return ZEND_USER_OPCODE_DISPATCH; } /* }}} */
int uopz_class_constant_handler(UOPZ_OPCODE_HANDLER_ARGS) { /* {{{ */ if (EX(opline)->op1_type == IS_CONST) { zval *name = EX_CONSTANT(EX(opline)->op1); zend_string *key = Z_STR_P(name); zval *mock = NULL; zend_class_entry *poser = NULL; key = zend_string_tolower(key); if ((mock = zend_hash_find(&UOPZ(mocks), key))) { if (Z_TYPE_P(mock) == IS_OBJECT) { poser = Z_OBJCE_P(mock); } else poser = zend_lookup_class(Z_STR_P(mock)); if (poser) { CACHE_PTR(Z_CACHE_SLOT_P(name), poser); } } zend_string_release(key); } CACHE_PTR(Z_CACHE_SLOT_P(EX_CONSTANT(EX(opline)->op2)), NULL); if (uopz_fetch_class_constant_handler) { return uopz_fetch_class_constant_handler(UOPZ_OPCODE_HANDLER_ARGS_PASSTHRU); } return ZEND_USER_OPCODE_DISPATCH; } /* }}} */
/* {{{ proto mixed uopz_get_property(object instance, string property) proto mixed uopz_get_property(string class, string property) */ static PHP_FUNCTION(uopz_get_property) { zval *scope = NULL; zval *prop = NULL; if (uopz_parse_parameters("zz", &scope, &prop) != SUCCESS || !scope || !prop || (Z_TYPE_P(scope) != IS_OBJECT && Z_TYPE_P(scope) != IS_STRING) || Z_TYPE_P(prop) != IS_STRING) { uopz_refuse_parameters( "unexpected paramter combination, expected " "(class, property) or (object, property)"); return; } if (Z_TYPE_P(scope) == IS_OBJECT) { uopz_get_property(scope, prop, return_value); } else { zend_class_entry *ce = zend_lookup_class(Z_STR_P(scope)); if (!ce) { return; } uopz_get_static_property(ce, Z_STR_P(prop), return_value); } } /* }}} */
int uopz_add_class_handler(UOPZ_OPCODE_HANDLER_ARGS) { /* {{{ */ zval *name = EX_CONSTANT(EX(opline)->op2); zend_string *key = zend_string_tolower(Z_STR_P(name)); zval *mock = NULL; if ((mock = zend_hash_find(&UOPZ(mocks), key))) { if (Z_TYPE_P(mock) == IS_STRING) { zend_class_entry *ce = zend_lookup_class(Z_STR_P(mock)); if (ce) { CACHE_PTR(Z_CACHE_SLOT_P(name), ce); } } else { CACHE_PTR(Z_CACHE_SLOT_P(name), Z_OBJCE_P(mock)); } } zend_string_release(key); if (uopz_add_trait_handler || uopz_add_interface_handler) { switch (EX(opline)->opcode) { case ZEND_ADD_INTERFACE: return uopz_add_interface_handler(UOPZ_OPCODE_HANDLER_ARGS_PASSTHRU); case ZEND_ADD_TRAIT: return uopz_add_trait_handler(UOPZ_OPCODE_HANDLER_ARGS_PASSTHRU); } } return ZEND_USER_OPCODE_DISPATCH; } /* }}} */
zend_class_entry *air_loader_lookup_class(const char *classname, int len TSRMLS_DC) { zend_class_entry **pp_ce = NULL; int status = zend_lookup_class(classname, len, &pp_ce TSRMLS_CC); if (status == FAILURE || ((*pp_ce)->ce_flags & (ZEND_ACC_INTERFACE | (ZEND_ACC_TRAIT - ZEND_ACC_EXPLICIT_ABSTRACT_CLASS))) != 0){ return NULL; } return *pp_ce; }
static void SWIG_ZTS_SetPointerZval(zval *z, void *ptr, swig_type_info *type, int newobject TSRMLS_DC) { swig_object_wrapper *value=NULL; /* * First test for Null pointers. Return those as PHP native NULL */ if (!ptr ) { ZVAL_NULL(z); return; } if (type->clientdata) { if (! (*(int *)(type->clientdata))) zend_error(E_ERROR, "Type: %s failed to register with zend",type->name); value=(swig_object_wrapper *)emalloc(sizeof(swig_object_wrapper)); value->ptr=ptr; value->newobject=newobject; if (newobject <= 1) { /* Just register the pointer as a resource. */ ZEND_REGISTER_RESOURCE(z, value, *(int *)(type->clientdata)); } else { /* * Wrap the resource in an object, the resource will be accessible * via the "_cPtr" member. This is currently only used by * directorin typemaps. */ value->newobject = 0; zval *resource; MAKE_STD_ZVAL(resource); ZEND_REGISTER_RESOURCE(resource, value, *(int *)(type->clientdata)); zend_class_entry **ce = NULL; zval *classname; MAKE_STD_ZVAL(classname); /* _p_Foo -> Foo */ ZVAL_STRING(classname, (char*)type->name+3, 1); /* class names are stored in lowercase */ php_strtolower(Z_STRVAL_PP(&classname), Z_STRLEN_PP(&classname)); if (zend_lookup_class(Z_STRVAL_P(classname), Z_STRLEN_P(classname), &ce TSRMLS_CC) != SUCCESS) { /* class does not exist */ object_init(z); } else { object_init_ex(z, *ce); } Z_SET_REFCOUNT_P(z, 1); Z_SET_ISREF_P(z); zend_hash_update(HASH_OF(z), (char*)"_cPtr", sizeof("_cPtr"), (void*)&resource, sizeof(zval), NULL); FREE_ZVAL(classname); } return; } zend_error(E_ERROR, "Type: %s not registered with zend",type->name); }
/** * Checks if a interface exist */ int zephir_interface_exists(const zval *class_name, int autoload) { zend_class_entry *ce; if (Z_TYPE_P(class_name) == IS_STRING) { if ((ce = zend_lookup_class(Z_STR_P(class_name))) != NULL) { return ((ce->ce_flags & ZEND_ACC_INTERFACE) > 0); } return 0; } php_error_docref(NULL TSRMLS_CC, E_WARNING, "interface name must be a string"); return 0; }
/** * Checks if a class exist */ int zephir_class_exists(const zval *class_name, int autoload) { zend_class_entry *ce; if (Z_TYPE_P(class_name) == IS_STRING) { if ((ce = zend_lookup_class(Z_STR_P(class_name))) != NULL) { return (ce->ce_flags & (ZEND_ACC_INTERFACE | (ZEND_ACC_TRAIT - ZEND_ACC_EXPLICIT_ABSTRACT_CLASS))) == 0; } return 0; } php_error_docref(NULL, E_WARNING, "class name must be a string"); return 0; }
/* {{{ */ zend_bool pthreads_globals_object_connect(zend_ulong address, zend_class_entry *ce, zval *object) { zend_bool valid = 0; if (!address) return valid; if (pthreads_globals_lock()) { if (zend_hash_index_exists(&PTHREADS_G(objects), address)) { valid = 1; } pthreads_globals_unlock(); } if (valid) { /* * This can be done outside of a critical section because there are only two possibilities: * We own the object: no possible pathway to fault (read free'd memory) * We don't own the object: possibly pathway to fault whether we use critical section or not: * We use a critical section: we create the connection knowing that address cannot be freed while doing so * however, as soon as we leave the section, and before the conext that called this routine can reference the connection * object the creating context may have free'd the object. * We don't use a critical section: the object may be freed while we are creating the connection, causing a fault. * * As always, it's necessary for the programmer to retain the appropriate references so that this does not fault, creating connections * in a critical section would be unecessarily slow, not to mention recursively lock mutex (which is fine, but not ideal). */ if (PTHREADS_IN_CREATOR(((pthreads_object_t*)address))) { /* we own the object in this context */ ZVAL_OBJ(object, &((pthreads_object_t*)address)->std); Z_ADDREF_P(object); } else { /* we do not own the object, create a connection */ if (!ce) { /* we may not know the class, can't use ce directly from zend_object because it is from another context */ ce = zend_lookup_class( ((pthreads_object_t*)address)->std.ce->name); } object_init_ex(object, ce); pthreads_connect( (pthreads_object_t*) address, PTHREADS_FETCH_FROM(Z_OBJ_P(object))); } } return valid; } /* }}} */
static zend_class_entry * spl_find_ce_by_name(zend_string *name, zend_bool autoload) { zend_class_entry *ce; if (!autoload) { zend_string *lc_name = zend_string_tolower(name); ce = zend_hash_find_ptr(EG(class_table), lc_name); zend_string_free(lc_name); } else { ce = zend_lookup_class(name); } if (ce == NULL) { php_error_docref(NULL, E_WARNING, "Class %s does not exist%s", ZSTR_VAL(name), autoload ? " and could not be loaded" : ""); return NULL; } return ce; }
static zend_class_entry * spl_find_ce_by_name(char *name, int len, zend_bool autoload TSRMLS_DC) { zend_class_entry **ce; int found; if (!autoload) { char *lc_name; lc_name = do_alloca(len + 1); zend_str_tolower_copy(lc_name, name, len); found = zend_hash_find(EG(class_table), lc_name, len +1, (void **) &ce); free_alloca(lc_name); } else { found = zend_lookup_class(name, len, &ce TSRMLS_CC); } if (found != SUCCESS) { php_error_docref(NULL TSRMLS_CC, E_WARNING, "Class %s does not exist%s", name, autoload ? " and could not be loaded" : ""); return NULL; } return *ce; }
/** * Check whether a class with a certain name exists * @param classname * @param len * @param autoload * @return bool */ bool class_exists(const char *classname, size_t len, bool autoload) { // we need the tsrm_ls variable TSRMLS_FETCH(); // we're going to load a class-entry zend_class_entry **ce; // should we autoload the class? if (autoload) { // no auto-load if (SUCCESS != zend_lookup_class(classname, len, &ce TSRMLS_CC)) return false; // the found "class" could also be an interface or trait, which we do no want return ((*ce)->ce_flags & (ZEND_ACC_INTERFACE | (ZEND_ACC_TRAIT - ZEND_ACC_EXPLICIT_ABSTRACT_CLASS))) == 0; } else { // starting slashes can be ignored if (len > 0 && classname[0] == '\\') { classname++; len--; } // all classes are in lowercase in the hash, so we make // a temporary buffer for storing the lowercase class name // (is this smart? memory allocation is expensive!) std::unique_ptr<char[]> lc_name(new char[len + 1]); // copy the name to lowercase, but ignore the starting slash (if there is one) zend_str_tolower_copy(lc_name.get(), classname, len); // see if there is a class with this name if (SUCCESS != zend_hash_find(EG(class_table), lc_name.get(), len + 1, (void **) &ce)) return false; // the found "class" could also be an interface or trait, which we do no want return !(((*ce)->ce_flags & (ZEND_ACC_INTERFACE | ZEND_ACC_TRAIT)) > ZEND_ACC_EXPLICIT_ABSTRACT_CLASS); } }
PHP_METHOD(Edge_Controller, model) { char *model_name = NULL; char *model_dir = NULL; int mnlen=0; int mdlen=0; if(zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "s|s", &model_name, &mnlen, &model_dir, &mdlen) == FAILURE) { RETURN_FALSE; } char *model_class_name; int class_name_len; class_name_len = spprintf(&model_class_name, 0, "%s%s", model_name, "Model"); zval **z_obj; if(zend_hash_find(Z_ARRVAL_P(EDGE_G(regs)), model_class_name, class_name_len+1, (void **)&z_obj) == SUCCESS) { efree(model_class_name); RETURN_ZVAL(*z_obj, 1, 0); } zval *config; zval *config_data; config = zend_read_static_property(edge_core_ce, ZEND_STRL("config"), 1 TSRMLS_DC); config_data = zend_read_property(edge_config_ce, config, ZEND_STRL("_data"), 1 TSRMLS_DC); zval **models_home_pp; if(zend_hash_find(Z_ARRVAL_P(config_data), "_models_home", strlen("_models_home")+1, (void **)&models_home_pp) == FAILURE) { RETURN_FALSE; } zval *z_model_name; MAKE_STD_ZVAL(z_model_name); ZVAL_STRING(z_model_name, model_class_name, 1); zval *loader; zval *ret; loader = zend_read_static_property(edge_core_ce, ZEND_STRL("loader"), 1 TSRMLS_DC); zend_call_method_with_2_params(&loader, Z_OBJCE_P(loader), NULL, "autoload", &ret, z_model_name, *models_home_pp); zval_ptr_dtor(&z_model_name); if(!Z_BVAL_P(ret)) { php_error_docref(NULL TSRMLS_CC, E_WARNING, "model %s%s load fail", Z_STRVAL_PP(models_home_pp), model_class_name); zend_throw_exception_ex(zend_exception_get_default(TSRMLS_C), 0 TSRMLS_CC, "model %s%s load fail", Z_STRVAL_PP(models_home_pp), model_class_name); zval_ptr_dtor(&ret); efree(model_class_name); RETURN_FALSE; } zval_ptr_dtor(&ret); zend_class_entry **model_ce; if(zend_lookup_class(model_class_name, class_name_len, &model_ce TSRMLS_CC) == FAILURE) { php_error_docref(NULL TSRMLS_CC, E_WARNING, "model class %s not exist", model_class_name); zend_throw_exception_ex(zend_exception_get_default(TSRMLS_C), 0 TSRMLS_CC, "model class %s%s not exist", model_class_name); efree(model_class_name); RETURN_FALSE; } zval *model_obj; MAKE_STD_ZVAL(model_obj); object_init_ex(model_obj, *model_ce); zval **cfptr; if(zend_hash_find(&((*model_ce)->function_table), "__construct", strlen("__construct")+1, (void **)&cfptr) == SUCCESS) { zval *cretval; zend_call_method(&model_obj, *model_ce, NULL, "__construct", strlen("__construct"), &cretval, 0, NULL, NULL TSRMLS_CC); zval_ptr_dtor(&cretval); } zend_hash_update(Z_ARRVAL_P(EDGE_G(regs)), model_class_name, class_name_len+1, (void **)&model_obj, sizeof(zval *), NULL); efree(model_class_name); RETURN_ZVAL(model_obj, 1, 0); }
PHP_METHOD(Edge_Controller, check_login) { zval *chktype, *uin, *key; int had_params = 1; if(zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "zzz", &chktype, &uin, &key) == FAILURE) { MAKE_STD_ZVAL(chktype); MAKE_STD_ZVAL(uin); MAKE_STD_ZVAL(key); ZVAL_NULL(chktype); ZVAL_NULL(uin); ZVAL_NULL(key); had_params = 0; //RETURN_FALSE; } zend_class_entry **login_ce; if(zend_lookup_class("If_Login", strlen("If_Login"), &login_ce TSRMLS_CC) == FAILURE) { RETURN_FALSE; } zval *login_obj; MAKE_STD_ZVAL(login_obj); object_init_ex(login_obj, *login_ce); zval **args[3]; zval *function_name; zval *ret = NULL; MAKE_STD_ZVAL(function_name); ZVAL_STRING(function_name, "check_login", 1); args[0] = &chktype; args[1] = &uin; args[2] = &key; if(call_user_function_ex(&((*login_ce)->function_table), &login_obj, function_name, &ret, 3, args, 0, NULL TSRMLS_CC )== FAILURE) { zval_ptr_dtor(&function_name); zval_ptr_dtor(&login_obj); RETURN_FALSE; } zval_ptr_dtor(&function_name); zval_ptr_dtor(&login_obj); if(had_params == 0) { zval_ptr_dtor(&chktype); zval_ptr_dtor(&uin); zval_ptr_dtor(&key); } RETURN_ZVAL(ret, 1, 1); /* if(Z_TYPE_P(ret) == IS_BOOL) { RETURN_FALSE; } zval *fret; MAKE_STD_ZVAL(fret); ZVAL_STRING(fret, Z_STRVAL_P(uin), 1); array_init(return_value); add_assoc_string(return_value, "nickname", Z_STRVAL_P(fret), 1); zval_ptr_dtor(&fret); */ }
static int php_var_unserialize_internal(UNSERIALIZE_PARAMETER) { const unsigned char *cursor, *limit, *marker, *start; zval *rval_ref; limit = max; cursor = *p; if (YYCURSOR >= YYLIMIT) { return 0; } if (var_hash && (*p)[0] != 'R') { var_push(var_hash, rval); } start = cursor; #line 656 "ext/standard/var_unserializer.c" { YYCTYPE yych; static const unsigned char yybm[] = { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, }; if ((YYLIMIT - YYCURSOR) < 7) YYFILL(7); yych = *YYCURSOR; switch (yych) { case 'C': case 'O': goto yy4; case 'N': goto yy5; case 'R': goto yy6; case 'S': goto yy7; case 'a': goto yy8; case 'b': goto yy9; case 'd': goto yy10; case 'i': goto yy11; case 'o': goto yy12; case 'r': goto yy13; case 's': goto yy14; case '}': goto yy15; default: goto yy2; } yy2: ++YYCURSOR; yy3: #line 1043 "ext/standard/var_unserializer.re" { return 0; } #line 716 "ext/standard/var_unserializer.c" yy4: yych = *(YYMARKER = ++YYCURSOR); if (yych == ':') goto yy17; goto yy3; yy5: yych = *++YYCURSOR; if (yych == ';') goto yy19; goto yy3; yy6: yych = *(YYMARKER = ++YYCURSOR); if (yych == ':') goto yy21; goto yy3; yy7: yych = *(YYMARKER = ++YYCURSOR); if (yych == ':') goto yy22; goto yy3; yy8: yych = *(YYMARKER = ++YYCURSOR); if (yych == ':') goto yy23; goto yy3; yy9: yych = *(YYMARKER = ++YYCURSOR); if (yych == ':') goto yy24; goto yy3; yy10: yych = *(YYMARKER = ++YYCURSOR); if (yych == ':') goto yy25; goto yy3; yy11: yych = *(YYMARKER = ++YYCURSOR); if (yych == ':') goto yy26; goto yy3; yy12: yych = *(YYMARKER = ++YYCURSOR); if (yych == ':') goto yy27; goto yy3; yy13: yych = *(YYMARKER = ++YYCURSOR); if (yych == ':') goto yy28; goto yy3; yy14: yych = *(YYMARKER = ++YYCURSOR); if (yych == ':') goto yy29; goto yy3; yy15: ++YYCURSOR; #line 1037 "ext/standard/var_unserializer.re" { /* this is the case where we have less data than planned */ php_error_docref(NULL, E_NOTICE, "Unexpected end of serialized data"); return 0; /* not sure if it should be 0 or 1 here? */ } #line 769 "ext/standard/var_unserializer.c" yy17: yych = *++YYCURSOR; if (yybm[0+yych] & 128) { goto yy30; } yy18: YYCURSOR = YYMARKER; goto yy3; yy19: ++YYCURSOR; #line 709 "ext/standard/var_unserializer.re" { *p = YYCURSOR; ZVAL_NULL(rval); return 1; } #line 786 "ext/standard/var_unserializer.c" yy21: yych = *++YYCURSOR; if (yych <= '/') goto yy18; if (yych <= '9') goto yy32; goto yy18; yy22: yych = *++YYCURSOR; if (yych <= '/') goto yy18; if (yych <= '9') goto yy34; goto yy18; yy23: yych = *++YYCURSOR; if (yych <= '/') goto yy18; if (yych <= '9') goto yy36; goto yy18; yy24: yych = *++YYCURSOR; if (yych <= '/') goto yy18; if (yych <= '1') goto yy38; goto yy18; yy25: yych = *++YYCURSOR; if (yych <= '/') { if (yych <= ',') { if (yych == '+') goto yy39; goto yy18; } else { if (yych <= '-') goto yy40; if (yych <= '.') goto yy41; goto yy18; } } else { if (yych <= 'I') { if (yych <= '9') goto yy42; if (yych <= 'H') goto yy18; goto yy44; } else { if (yych == 'N') goto yy45; goto yy18; } } yy26: yych = *++YYCURSOR; if (yych <= ',') { if (yych == '+') goto yy46; goto yy18; } else { if (yych <= '-') goto yy46; if (yych <= '/') goto yy18; if (yych <= '9') goto yy47; goto yy18; } yy27: yych = *++YYCURSOR; if (yych <= '/') goto yy18; if (yych <= '9') goto yy49; goto yy18; yy28: yych = *++YYCURSOR; if (yych <= '/') goto yy18; if (yych <= '9') goto yy51; goto yy18; yy29: yych = *++YYCURSOR; if (yych <= '/') goto yy18; if (yych <= '9') goto yy53; goto yy18; yy30: ++YYCURSOR; if ((YYLIMIT - YYCURSOR) < 2) YYFILL(2); yych = *YYCURSOR; if (yybm[0+yych] & 128) { goto yy30; } if (yych <= '/') goto yy18; if (yych <= ':') goto yy55; goto yy18; yy32: ++YYCURSOR; if (YYLIMIT <= YYCURSOR) YYFILL(1); yych = *YYCURSOR; if (yych <= '/') goto yy18; if (yych <= '9') goto yy32; if (yych == ';') goto yy56; goto yy18; yy34: ++YYCURSOR; if ((YYLIMIT - YYCURSOR) < 2) YYFILL(2); yych = *YYCURSOR; if (yych <= '/') goto yy18; if (yych <= '9') goto yy34; if (yych <= ':') goto yy58; goto yy18; yy36: ++YYCURSOR; if ((YYLIMIT - YYCURSOR) < 2) YYFILL(2); yych = *YYCURSOR; if (yych <= '/') goto yy18; if (yych <= '9') goto yy36; if (yych <= ':') goto yy59; goto yy18; yy38: yych = *++YYCURSOR; if (yych == ';') goto yy60; goto yy18; yy39: yych = *++YYCURSOR; if (yych == '.') goto yy41; if (yych <= '/') goto yy18; if (yych <= '9') goto yy42; goto yy18; yy40: yych = *++YYCURSOR; if (yych <= '/') { if (yych != '.') goto yy18; } else { if (yych <= '9') goto yy42; if (yych == 'I') goto yy44; goto yy18; } yy41: yych = *++YYCURSOR; if (yych <= '/') goto yy18; if (yych <= '9') goto yy62; goto yy18; yy42: ++YYCURSOR; if ((YYLIMIT - YYCURSOR) < 3) YYFILL(3); yych = *YYCURSOR; if (yych <= ':') { if (yych <= '.') { if (yych <= '-') goto yy18; goto yy62; } else { if (yych <= '/') goto yy18; if (yych <= '9') goto yy42; goto yy18; } } else { if (yych <= 'E') { if (yych <= ';') goto yy64; if (yych <= 'D') goto yy18; goto yy66; } else { if (yych == 'e') goto yy66; goto yy18; } } yy44: yych = *++YYCURSOR; if (yych == 'N') goto yy67; goto yy18; yy45: yych = *++YYCURSOR; if (yych == 'A') goto yy68; goto yy18; yy46: yych = *++YYCURSOR; if (yych <= '/') goto yy18; if (yych >= ':') goto yy18; yy47: ++YYCURSOR; if (YYLIMIT <= YYCURSOR) YYFILL(1); yych = *YYCURSOR; if (yych <= '/') goto yy18; if (yych <= '9') goto yy47; if (yych == ';') goto yy69; goto yy18; yy49: ++YYCURSOR; if ((YYLIMIT - YYCURSOR) < 2) YYFILL(2); yych = *YYCURSOR; if (yych <= '/') goto yy18; if (yych <= '9') goto yy49; if (yych <= ':') goto yy71; goto yy18; yy51: ++YYCURSOR; if (YYLIMIT <= YYCURSOR) YYFILL(1); yych = *YYCURSOR; if (yych <= '/') goto yy18; if (yych <= '9') goto yy51; if (yych == ';') goto yy72; goto yy18; yy53: ++YYCURSOR; if ((YYLIMIT - YYCURSOR) < 2) YYFILL(2); yych = *YYCURSOR; if (yych <= '/') goto yy18; if (yych <= '9') goto yy53; if (yych <= ':') goto yy74; goto yy18; yy55: yych = *++YYCURSOR; if (yych == '"') goto yy75; goto yy18; yy56: ++YYCURSOR; #line 660 "ext/standard/var_unserializer.re" { zend_long id; *p = YYCURSOR; if (!var_hash) return 0; id = parse_uiv(start + 2) - 1; if (id == -1 || (rval_ref = var_access(var_hash, id)) == NULL) { return 0; } if (Z_ISUNDEF_P(rval_ref) || (Z_ISREF_P(rval_ref) && Z_ISUNDEF_P(Z_REFVAL_P(rval_ref)))) { return 0; } if (Z_ISREF_P(rval_ref)) { ZVAL_COPY(rval, rval_ref); } else { ZVAL_NEW_REF(rval_ref, rval_ref); ZVAL_COPY(rval, rval_ref); } return 1; } #line 1010 "ext/standard/var_unserializer.c" yy58: yych = *++YYCURSOR; if (yych == '"') goto yy77; goto yy18; yy59: yych = *++YYCURSOR; if (yych == '{') goto yy79; goto yy18; yy60: ++YYCURSOR; #line 715 "ext/standard/var_unserializer.re" { *p = YYCURSOR; ZVAL_BOOL(rval, parse_iv(start + 2)); return 1; } #line 1027 "ext/standard/var_unserializer.c" yy62: ++YYCURSOR; if ((YYLIMIT - YYCURSOR) < 3) YYFILL(3); yych = *YYCURSOR; if (yych <= ';') { if (yych <= '/') goto yy18; if (yych <= '9') goto yy62; if (yych <= ':') goto yy18; } else { if (yych <= 'E') { if (yych <= 'D') goto yy18; goto yy66; } else { if (yych == 'e') goto yy66; goto yy18; } } yy64: ++YYCURSOR; #line 763 "ext/standard/var_unserializer.re" { #if SIZEOF_ZEND_LONG == 4 use_double: #endif *p = YYCURSOR; ZVAL_DOUBLE(rval, zend_strtod((const char *)start + 2, NULL)); return 1; } #line 1056 "ext/standard/var_unserializer.c" yy66: yych = *++YYCURSOR; if (yych <= ',') { if (yych == '+') goto yy81; goto yy18; } else { if (yych <= '-') goto yy81; if (yych <= '/') goto yy18; if (yych <= '9') goto yy82; goto yy18; } yy67: yych = *++YYCURSOR; if (yych == 'F') goto yy84; goto yy18; yy68: yych = *++YYCURSOR; if (yych == 'N') goto yy84; goto yy18; yy69: ++YYCURSOR; #line 721 "ext/standard/var_unserializer.re" { #if SIZEOF_ZEND_LONG == 4 int digits = YYCURSOR - start - 3; if (start[2] == '-' || start[2] == '+') { digits--; } /* Use double for large zend_long values that were serialized on a 64-bit system */ if (digits >= MAX_LENGTH_OF_LONG - 1) { if (digits == MAX_LENGTH_OF_LONG - 1) { int cmp = strncmp((char*)YYCURSOR - MAX_LENGTH_OF_LONG, long_min_digits, MAX_LENGTH_OF_LONG - 1); if (!(cmp < 0 || (cmp == 0 && start[2] == '-'))) { goto use_double; } } else { goto use_double; } } #endif *p = YYCURSOR; ZVAL_LONG(rval, parse_iv(start + 2)); return 1; } #line 1104 "ext/standard/var_unserializer.c" yy71: yych = *++YYCURSOR; if (yych == '"') goto yy85; goto yy18; yy72: ++YYCURSOR; #line 685 "ext/standard/var_unserializer.re" { zend_long id; *p = YYCURSOR; if (!var_hash) return 0; id = parse_uiv(start + 2) - 1; if (id == -1 || (rval_ref = var_access(var_hash, id)) == NULL) { return 0; } if (rval_ref == rval) { return 0; } if (Z_ISUNDEF_P(rval_ref) || (Z_ISREF_P(rval_ref) && Z_ISUNDEF_P(Z_REFVAL_P(rval_ref)))) { return 0; } ZVAL_COPY(rval, rval_ref); return 1; } #line 1135 "ext/standard/var_unserializer.c" yy74: yych = *++YYCURSOR; if (yych == '"') goto yy87; goto yy18; yy75: ++YYCURSOR; #line 885 "ext/standard/var_unserializer.re" { size_t len, len2, len3, maxlen; zend_long elements; char *str; zend_string *class_name; zend_class_entry *ce; int incomplete_class = 0; int custom_object = 0; zval user_func; zval retval; zval args[1]; if (!var_hash) return 0; if (*start == 'C') { custom_object = 1; } len2 = len = parse_uiv(start + 2); maxlen = max - YYCURSOR; if (maxlen < len || len == 0) { *p = start + 2; return 0; } str = (char*)YYCURSOR; YYCURSOR += len; if (*(YYCURSOR) != '"') { *p = YYCURSOR; return 0; } if (*(YYCURSOR+1) != ':') { *p = YYCURSOR+1; return 0; } len3 = strspn(str, "0123456789_abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ\177\200\201\202\203\204\205\206\207\210\211\212\213\214\215\216\217\220\221\222\223\224\225\226\227\230\231\232\233\234\235\236\237\240\241\242\243\244\245\246\247\250\251\252\253\254\255\256\257\260\261\262\263\264\265\266\267\270\271\272\273\274\275\276\277\300\301\302\303\304\305\306\307\310\311\312\313\314\315\316\317\320\321\322\323\324\325\326\327\330\331\332\333\334\335\336\337\340\341\342\343\344\345\346\347\350\351\352\353\354\355\356\357\360\361\362\363\364\365\366\367\370\371\372\373\374\375\376\377\\"); if (len3 != len) { *p = YYCURSOR + len3 - len; return 0; } class_name = zend_string_init(str, len, 0); do { if(!unserialize_allowed_class(class_name, var_hash)) { incomplete_class = 1; ce = PHP_IC_ENTRY; break; } /* Try to find class directly */ BG(serialize_lock)++; ce = zend_lookup_class(class_name); if (ce) { BG(serialize_lock)--; if (EG(exception)) { zend_string_release(class_name); return 0; } break; } BG(serialize_lock)--; if (EG(exception)) { zend_string_release(class_name); return 0; } /* Check for unserialize callback */ if ((PG(unserialize_callback_func) == NULL) || (PG(unserialize_callback_func)[0] == '\0')) { incomplete_class = 1; ce = PHP_IC_ENTRY; break; } /* Call unserialize callback */ ZVAL_STRING(&user_func, PG(unserialize_callback_func)); ZVAL_STR_COPY(&args[0], class_name); BG(serialize_lock)++; if (call_user_function_ex(CG(function_table), NULL, &user_func, &retval, 1, args, 0, NULL) != SUCCESS) { BG(serialize_lock)--; if (EG(exception)) { zend_string_release(class_name); zval_ptr_dtor(&user_func); zval_ptr_dtor(&args[0]); return 0; } php_error_docref(NULL, E_WARNING, "defined (%s) but not found", Z_STRVAL(user_func)); incomplete_class = 1; ce = PHP_IC_ENTRY; zval_ptr_dtor(&user_func); zval_ptr_dtor(&args[0]); break; } BG(serialize_lock)--; zval_ptr_dtor(&retval); if (EG(exception)) { zend_string_release(class_name); zval_ptr_dtor(&user_func); zval_ptr_dtor(&args[0]); return 0; } /* The callback function may have defined the class */ BG(serialize_lock)++; if ((ce = zend_lookup_class(class_name)) == NULL) { php_error_docref(NULL, E_WARNING, "Function %s() hasn't defined the class it was called for", Z_STRVAL(user_func)); incomplete_class = 1; ce = PHP_IC_ENTRY; } BG(serialize_lock)--; zval_ptr_dtor(&user_func); zval_ptr_dtor(&args[0]); break; } while (1); *p = YYCURSOR; if (custom_object) { int ret; ret = object_custom(UNSERIALIZE_PASSTHRU, ce); if (ret && incomplete_class) { php_store_class_name(rval, ZSTR_VAL(class_name), len2); } zend_string_release(class_name); return ret; } elements = object_common1(UNSERIALIZE_PASSTHRU, ce); if (elements < 0) { zend_string_release(class_name); return 0; } if (incomplete_class) { php_store_class_name(rval, ZSTR_VAL(class_name), len2); } zend_string_release(class_name); return object_common2(UNSERIALIZE_PASSTHRU, elements); } #line 1294 "ext/standard/var_unserializer.c" yy77: ++YYCURSOR; #line 810 "ext/standard/var_unserializer.re" { size_t len, maxlen; zend_string *str; len = parse_uiv(start + 2); maxlen = max - YYCURSOR; if (maxlen < len) { *p = start + 2; return 0; } if ((str = unserialize_str(&YYCURSOR, len, maxlen)) == NULL) { return 0; } if (*(YYCURSOR) != '"') { zend_string_free(str); *p = YYCURSOR; return 0; } if (*(YYCURSOR + 1) != ';') { efree(str); *p = YYCURSOR + 1; return 0; } YYCURSOR += 2; *p = YYCURSOR; ZVAL_STR(rval, str); return 1; } #line 1331 "ext/standard/var_unserializer.c" yy79: ++YYCURSOR; #line 844 "ext/standard/var_unserializer.re" { zend_long elements = parse_iv(start + 2); /* use iv() not uiv() in order to check data range */ *p = YYCURSOR; if (!var_hash) return 0; if (elements < 0 || elements >= HT_MAX_SIZE) { return 0; } array_init_size(rval, elements); if (elements) { /* we can't convert from packed to hash during unserialization, because reference to some zvals might be keept in var_hash (to support references) */ zend_hash_real_init(Z_ARRVAL_P(rval), 0); } /* The array may contain references to itself, in which case we'll be modifying an * rc>1 array. This is okay, since the array is, ostensibly, only visible to * unserialize (in practice unserialization handlers also see it). Ideally we should * prohibit "r:" references to non-objects, as we only generate them for objects. */ HT_ALLOW_COW_VIOLATION(Z_ARRVAL_P(rval)); if (!process_nested_data(UNSERIALIZE_PASSTHRU, Z_ARRVAL_P(rval), elements, 0)) { return 0; } return finish_nested_data(UNSERIALIZE_PASSTHRU); } #line 1364 "ext/standard/var_unserializer.c" yy81: yych = *++YYCURSOR; if (yych <= '/') goto yy18; if (yych >= ':') goto yy18; yy82: ++YYCURSOR; if (YYLIMIT <= YYCURSOR) YYFILL(1); yych = *YYCURSOR; if (yych <= '/') goto yy18; if (yych <= '9') goto yy82; if (yych == ';') goto yy64; goto yy18; yy84: yych = *++YYCURSOR; if (yych == ';') goto yy89; goto yy18; yy85: ++YYCURSOR; #line 874 "ext/standard/var_unserializer.re" { zend_long elements; if (!var_hash) return 0; elements = object_common1(UNSERIALIZE_PASSTHRU, ZEND_STANDARD_CLASS_DEF_PTR); if (elements < 0 || elements >= HT_MAX_SIZE) { return 0; } return object_common2(UNSERIALIZE_PASSTHRU, elements); } #line 1394 "ext/standard/var_unserializer.c" yy87: ++YYCURSOR; #line 772 "ext/standard/var_unserializer.re" { size_t len, maxlen; char *str; len = parse_uiv(start + 2); maxlen = max - YYCURSOR; if (maxlen < len) { *p = start + 2; return 0; } str = (char*)YYCURSOR; YYCURSOR += len; if (*(YYCURSOR) != '"') { *p = YYCURSOR; return 0; } if (*(YYCURSOR + 1) != ';') { *p = YYCURSOR + 1; return 0; } YYCURSOR += 2; *p = YYCURSOR; if (len == 0) { ZVAL_EMPTY_STRING(rval); } else if (len == 1) { ZVAL_INTERNED_STR(rval, ZSTR_CHAR((zend_uchar)*str)); } else { ZVAL_STRINGL(rval, str, len); } return 1; } #line 1435 "ext/standard/var_unserializer.c" yy89: ++YYCURSOR; #line 747 "ext/standard/var_unserializer.re" { *p = YYCURSOR; if (!strncmp((char*)start + 2, "NAN", 3)) { ZVAL_DOUBLE(rval, ZEND_NAN); } else if (!strncmp((char*)start + 2, "INF", 3)) { ZVAL_DOUBLE(rval, ZEND_INFINITY); } else if (!strncmp((char*)start + 2, "-INF", 4)) { ZVAL_DOUBLE(rval, -ZEND_INFINITY); } else { ZVAL_NULL(rval); } return 1; } #line 1454 "ext/standard/var_unserializer.c" } #line 1045 "ext/standard/var_unserializer.re" return 0; }
int msgpack_convert_object(zval *return_value, zval *tpl, zval **value) { zend_class_entry *ce, **pce; TSRMLS_FETCH(); switch (Z_TYPE_P(tpl)) { case IS_STRING: if (zend_lookup_class( Z_STRVAL_P(tpl), Z_STRLEN_P(tpl), &pce TSRMLS_CC) != SUCCESS) { MSGPACK_ERROR("[msgpack] (%s) Class '%s' not found", __FUNCTION__, Z_STRVAL_P(tpl)); return FAILURE; } ce = *pce; break; case IS_OBJECT: ce = zend_get_class_entry(tpl TSRMLS_CC); break; default: MSGPACK_ERROR("[msgpack] (%s) object type is unsupported", __FUNCTION__); return FAILURE; } if (Z_TYPE_PP(value) == IS_OBJECT) { zend_class_entry *vce; vce = zend_get_class_entry(*value TSRMLS_CC); if (strcmp(ce->name, vce->name) == 0) { *return_value = **value; zval_copy_ctor(return_value); zval_ptr_dtor(value); return SUCCESS; } } object_init_ex(return_value, ce); /* Run the constructor if there is one */ if (ce->constructor && (ce->constructor->common.fn_flags & ZEND_ACC_PUBLIC)) { zval *retval_ptr = NULL; zval ***params = NULL; int num_args = 0; zend_fcall_info fci; zend_fcall_info_cache fcc; #if ZEND_MODULE_API_NO >= 20090626 fci.size = sizeof(fci); fci.function_table = EG(function_table); fci.function_name = NULL; fci.symbol_table = NULL; fci.object_ptr = return_value; fci.retval_ptr_ptr = &retval_ptr; fci.param_count = num_args; fci.params = params; fci.no_separation = 1; fcc.initialized = 1; fcc.function_handler = ce->constructor; fcc.calling_scope = EG(scope); fcc.called_scope = Z_OBJCE_P(return_value); fcc.object_ptr = return_value; #else fci.size = sizeof(fci); fci.function_table = EG(function_table); fci.function_name = NULL; fci.symbol_table = NULL; fci.object_pp = &return_value; fci.retval_ptr_ptr = &retval_ptr; fci.param_count = num_args; fci.params = params; fci.no_separation = 1; fcc.initialized = 1; fcc.function_handler = ce->constructor; fcc.calling_scope = EG(scope); fcc.object_pp = &return_value; #endif if (zend_call_function(&fci, &fcc TSRMLS_CC) == FAILURE) { if (params) { efree(params); } if (retval_ptr) { zval_ptr_dtor(&retval_ptr); } MSGPACK_WARNING( "[msgpack] (%s) Invocation of %s's constructor failed", __FUNCTION__, ce->name); return FAILURE; } if (retval_ptr) { zval_ptr_dtor(&retval_ptr); } if (params) { efree(params); } } switch (Z_TYPE_PP(value)) { case IS_ARRAY: { char *key; uint key_len; int key_type; ulong key_index; zval **data; HashPosition pos; HashTable *ht, *ret; HashTable *var = NULL; int num; ht = HASH_OF(*value); ret = HASH_OF(return_value); num = zend_hash_num_elements(ht); if (num <= 0) { zval_ptr_dtor(value); break; } /* string - php_only mode? */ if (ht->nNumOfElements != ht->nNextFreeElement || ht->nNumOfElements != ret->nNumOfElements) { HashTable *properties = NULL; HashPosition prop_pos; ALLOC_HASHTABLE(var); zend_hash_init(var, num, NULL, NULL, 0); zend_hash_internal_pointer_reset_ex(ht, &pos); for (;; zend_hash_move_forward_ex(ht, &pos)) { key_type = zend_hash_get_current_key_ex( ht, &key, &key_len, &key_index, 0, &pos); if (key_type == HASH_KEY_NON_EXISTANT) { break; } if (zend_hash_get_current_data_ex( ht, (void *)&data, &pos) != SUCCESS) { continue; } if (key_type == HASH_KEY_IS_STRING) { zval *val; MSGPACK_CONVERT_COPY_ZVAL(val, data); if (msgpack_convert_string_to_properties( return_value, key, key_len, val, var) != SUCCESS) { zval_ptr_dtor(&val); MSGPACK_WARNING( "[msgpack] (%s) " "illegal offset type, skip this decoding", __FUNCTION__); } } } /* index */ properties = Z_OBJ_HT_P(return_value)->get_properties( return_value TSRMLS_CC); if (HASH_OF(tpl)) { properties = HASH_OF(tpl); } zend_hash_internal_pointer_reset_ex(properties, &prop_pos); zend_hash_internal_pointer_reset_ex(ht, &pos); for (;; zend_hash_move_forward_ex(ht, &pos)) { key_type = zend_hash_get_current_key_ex( ht, &key, &key_len, &key_index, 0, &pos); if (key_type == HASH_KEY_NON_EXISTANT) { break; } if (zend_hash_get_current_data_ex( ht, (void *)&data, &pos) != SUCCESS) { continue; } switch (key_type) { case HASH_KEY_IS_LONG: { zval *val; MSGPACK_CONVERT_COPY_ZVAL(val, data); if (msgpack_convert_long_to_properties( ret, &properties, &prop_pos, key_index, val, var) != SUCCESS) { zval_ptr_dtor(&val); MSGPACK_WARNING( "[msgpack] (%s) " "illegal offset type, skip this decoding", __FUNCTION__); } break; } case HASH_KEY_IS_STRING: break; default: MSGPACK_WARNING( "[msgpack] (%s) key is not string nor array", __FUNCTION__); break; } } zend_hash_destroy(var); FREE_HASHTABLE(var); } else { HashPosition valpos; int (*convert_function)(zval *, zval *, zval **) = NULL; zval **arydata, *aryval; /* index */ zend_hash_internal_pointer_reset_ex(ret, &pos); zend_hash_internal_pointer_reset_ex(ht, &valpos); for (;; zend_hash_move_forward_ex(ret, &pos), zend_hash_move_forward_ex(ht, &valpos)) { key_type = zend_hash_get_current_key_ex( ret, &key, &key_len, &key_index, 0, &pos); if (key_type == HASH_KEY_NON_EXISTANT) { break; } if (zend_hash_get_current_data_ex( ret, (void *)&data, &pos) != SUCCESS) { continue; } switch (Z_TYPE_PP(data)) { case IS_ARRAY: convert_function = msgpack_convert_array; break; case IS_OBJECT: //case IS_STRING: -- may have default values of // class members, so it's not wise to allow convert_function = msgpack_convert_object; break; default: break; } if (zend_hash_get_current_data_ex( ht, (void *)&arydata, &valpos) != SUCCESS) { MSGPACK_WARNING( "[msgpack] (%s) can't get data value by index", __FUNCTION__); return FAILURE; } MSGPACK_CONVERT_COPY_ZVAL(aryval, arydata); if (convert_function) { zval *rv; ALLOC_INIT_ZVAL(rv); if (convert_function(rv, *data, &aryval) != SUCCESS) { zval_ptr_dtor(&aryval); MSGPACK_WARNING( "[msgpack] (%s) " "convert failure in convert_object", __FUNCTION__); return FAILURE; } zend_symtable_update( ret, key, key_len, &rv, sizeof(rv), NULL); } else { zend_symtable_update( ret, key, key_len, &aryval, sizeof(aryval), NULL); } } } zval_ptr_dtor(value); break; } default: { HashTable *properties = NULL; HashPosition prop_pos; properties = Z_OBJ_HT_P(return_value)->get_properties( return_value TSRMLS_CC); zend_hash_internal_pointer_reset_ex(properties, &prop_pos); if (msgpack_convert_long_to_properties( HASH_OF(return_value), &properties, &prop_pos, 0, *value, NULL) != SUCCESS) { MSGPACK_WARNING( "[msgpack] (%s) illegal offset type, skip this decoding", __FUNCTION__); } break; } } return SUCCESS; }
PHPAPI int php_var_unserialize(UNSERIALIZE_PARAMETER) { const unsigned char *cursor, *limit, *marker, *start; zval **rval_ref; limit = max; cursor = *p; if (YYCURSOR >= YYLIMIT) { return 0; } if (var_hash && cursor[0] != 'R') { var_push(var_hash, rval); } start = cursor; #line 425 "ext/standard/var_unserializer.c" { YYCTYPE yych; static const unsigned char yybm[] = { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, }; if ((YYLIMIT - YYCURSOR) < 7) YYFILL(7); yych = *YYCURSOR; switch (yych) { case 'C': case 'O': goto yy13; case 'N': goto yy5; case 'R': goto yy2; case 'S': goto yy10; case 'a': goto yy11; case 'b': goto yy6; case 'd': goto yy8; case 'i': goto yy7; case 'o': goto yy12; case 'r': goto yy4; case 's': goto yy9; case '}': goto yy14; default: goto yy16; } yy2: yych = *(YYMARKER = ++YYCURSOR); if (yych == ':') goto yy95; yy3: #line 747 "ext/standard/var_unserializer.re" { return 0; } #line 487 "ext/standard/var_unserializer.c" yy4: yych = *(YYMARKER = ++YYCURSOR); if (yych == ':') goto yy89; goto yy3; yy5: yych = *++YYCURSOR; if (yych == ';') goto yy87; goto yy3; yy6: yych = *(YYMARKER = ++YYCURSOR); if (yych == ':') goto yy83; goto yy3; yy7: yych = *(YYMARKER = ++YYCURSOR); if (yych == ':') goto yy77; goto yy3; yy8: yych = *(YYMARKER = ++YYCURSOR); if (yych == ':') goto yy53; goto yy3; yy9: yych = *(YYMARKER = ++YYCURSOR); if (yych == ':') goto yy46; goto yy3; yy10: yych = *(YYMARKER = ++YYCURSOR); if (yych == ':') goto yy39; goto yy3; yy11: yych = *(YYMARKER = ++YYCURSOR); if (yych == ':') goto yy32; goto yy3; yy12: yych = *(YYMARKER = ++YYCURSOR); if (yych == ':') goto yy25; goto yy3; yy13: yych = *(YYMARKER = ++YYCURSOR); if (yych == ':') goto yy17; goto yy3; yy14: ++YYCURSOR; #line 741 "ext/standard/var_unserializer.re" { /* this is the case where we have less data than planned */ php_error_docref(NULL TSRMLS_CC, E_NOTICE, "Unexpected end of serialized data"); return 0; /* not sure if it should be 0 or 1 here? */ } #line 536 "ext/standard/var_unserializer.c" yy16: yych = *++YYCURSOR; goto yy3; yy17: yych = *++YYCURSOR; if (yybm[0+yych] & 128) { goto yy20; } if (yych == '+') goto yy19; yy18: YYCURSOR = YYMARKER; goto yy3; yy19: yych = *++YYCURSOR; if (yybm[0+yych] & 128) { goto yy20; } goto yy18; yy20: ++YYCURSOR; if ((YYLIMIT - YYCURSOR) < 2) YYFILL(2); yych = *YYCURSOR; if (yybm[0+yych] & 128) { goto yy20; } if (yych != ':') goto yy18; yych = *++YYCURSOR; if (yych != '"') goto yy18; ++YYCURSOR; #line 624 "ext/standard/var_unserializer.re" { size_t len, len2, len3, maxlen; long elements; char *class_name; zend_class_entry *ce; zend_class_entry **pce; int incomplete_class = 0; int custom_object = 0; zval *user_func; zval *retval_ptr; zval **args[1]; zval *arg_func_name; if (*start == 'C') { custom_object = 1; } INIT_PZVAL(*rval); len2 = len = parse_uiv(start + 2); maxlen = max - YYCURSOR; if (maxlen < len || len == 0) { *p = start + 2; return 0; } class_name = (char*)YYCURSOR; YYCURSOR += len; if (*(YYCURSOR) != '"') { *p = YYCURSOR; return 0; } if (*(YYCURSOR+1) != ':') { *p = YYCURSOR+1; return 0; } len3 = strspn(class_name, "0123456789_abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ\177\200\201\202\203\204\205\206\207\210\211\212\213\214\215\216\217\220\221\222\223\224\225\226\227\230\231\232\233\234\235\236\237\240\241\242\243\244\245\246\247\250\251\252\253\254\255\256\257\260\261\262\263\264\265\266\267\270\271\272\273\274\275\276\277\300\301\302\303\304\305\306\307\310\311\312\313\314\315\316\317\320\321\322\323\324\325\326\327\330\331\332\333\334\335\336\337\340\341\342\343\344\345\346\347\350\351\352\353\354\355\356\357\360\361\362\363\364\365\366\367\370\371\372\373\374\375\376\377\\"); if (len3 != len) { *p = YYCURSOR + len3 - len; return 0; } class_name = estrndup(class_name, len); do { /* Try to find class directly */ if (zend_lookup_class(class_name, len2, &pce TSRMLS_CC) == SUCCESS) { ce = *pce; break; } /* Check for unserialize callback */ if ((PG(unserialize_callback_func) == NULL) || (PG(unserialize_callback_func)[0] == '\0')) { incomplete_class = 1; ce = PHP_IC_ENTRY; break; } /* Call unserialize callback */ MAKE_STD_ZVAL(user_func); ZVAL_STRING(user_func, PG(unserialize_callback_func), 1); args[0] = &arg_func_name; MAKE_STD_ZVAL(arg_func_name); ZVAL_STRING(arg_func_name, class_name, 1); if (call_user_function_ex(CG(function_table), NULL, user_func, &retval_ptr, 1, args, 0, NULL TSRMLS_CC) != SUCCESS) { php_error_docref(NULL TSRMLS_CC, E_WARNING, "defined (%s) but not found", user_func->value.str.val); incomplete_class = 1; ce = PHP_IC_ENTRY; zval_ptr_dtor(&user_func); zval_ptr_dtor(&arg_func_name); break; } if (retval_ptr) { zval_ptr_dtor(&retval_ptr); } /* The callback function may have defined the class */ if (zend_lookup_class(class_name, len2, &pce TSRMLS_CC) == SUCCESS) { ce = *pce; } else { php_error_docref(NULL TSRMLS_CC, E_WARNING, "Function %s() hasn't defined the class it was called for", user_func->value.str.val); incomplete_class = 1; ce = PHP_IC_ENTRY; } zval_ptr_dtor(&user_func); zval_ptr_dtor(&arg_func_name); break; } while (1); *p = YYCURSOR; if (custom_object) { int ret = object_custom(UNSERIALIZE_PASSTHRU, ce); if (ret && incomplete_class) { php_store_class_name(*rval, class_name, len2); } efree(class_name); return ret; } elements = object_common1(UNSERIALIZE_PASSTHRU, ce); if (incomplete_class) { php_store_class_name(*rval, class_name, len2); } efree(class_name); return object_common2(UNSERIALIZE_PASSTHRU, elements); } #line 683 "ext/standard/var_unserializer.c" yy25: yych = *++YYCURSOR; if (yych <= ',') { if (yych != '+') goto yy18; } else { if (yych <= '-') goto yy26; if (yych <= '/') goto yy18; if (yych <= '9') goto yy27; goto yy18; } yy26: yych = *++YYCURSOR; if (yych <= '/') goto yy18; if (yych >= ':') goto yy18; yy27: ++YYCURSOR; if ((YYLIMIT - YYCURSOR) < 2) YYFILL(2); yych = *YYCURSOR; if (yych <= '/') goto yy18; if (yych <= '9') goto yy27; if (yych >= ';') goto yy18; yych = *++YYCURSOR; if (yych != '"') goto yy18; ++YYCURSOR; #line 616 "ext/standard/var_unserializer.re" { INIT_PZVAL(*rval); return object_common2(UNSERIALIZE_PASSTHRU, object_common1(UNSERIALIZE_PASSTHRU, ZEND_STANDARD_CLASS_DEF_PTR)); } #line 716 "ext/standard/var_unserializer.c" yy32: yych = *++YYCURSOR; if (yych == '+') goto yy33; if (yych <= '/') goto yy18; if (yych <= '9') goto yy34; goto yy18; yy33: yych = *++YYCURSOR; if (yych <= '/') goto yy18; if (yych >= ':') goto yy18; yy34: ++YYCURSOR; if ((YYLIMIT - YYCURSOR) < 2) YYFILL(2); yych = *YYCURSOR; if (yych <= '/') goto yy18; if (yych <= '9') goto yy34; if (yych >= ';') goto yy18; yych = *++YYCURSOR; if (yych != '{') goto yy18; ++YYCURSOR; #line 596 "ext/standard/var_unserializer.re" { long elements = parse_iv(start + 2); /* use iv() not uiv() in order to check data range */ *p = YYCURSOR; if (elements < 0) { return 0; } INIT_PZVAL(*rval); array_init_size(*rval, elements); if (!process_nested_data(UNSERIALIZE_PASSTHRU, Z_ARRVAL_PP(rval), elements, 0)) { return 0; } return finish_nested_data(UNSERIALIZE_PASSTHRU); } #line 757 "ext/standard/var_unserializer.c" yy39: yych = *++YYCURSOR; if (yych == '+') goto yy40; if (yych <= '/') goto yy18; if (yych <= '9') goto yy41; goto yy18; yy40: yych = *++YYCURSOR; if (yych <= '/') goto yy18; if (yych >= ':') goto yy18; yy41: ++YYCURSOR; if ((YYLIMIT - YYCURSOR) < 2) YYFILL(2); yych = *YYCURSOR; if (yych <= '/') goto yy18; if (yych <= '9') goto yy41; if (yych >= ';') goto yy18; yych = *++YYCURSOR; if (yych != '"') goto yy18; ++YYCURSOR; #line 567 "ext/standard/var_unserializer.re" { size_t len, maxlen; char *str; len = parse_uiv(start + 2); maxlen = max - YYCURSOR; if (maxlen < len) { *p = start + 2; return 0; } if ((str = unserialize_str(&YYCURSOR, &len, maxlen)) == NULL) { return 0; } if (*(YYCURSOR) != '"') { efree(str); *p = YYCURSOR; return 0; } YYCURSOR += 2; *p = YYCURSOR; INIT_PZVAL(*rval); ZVAL_STRINGL(*rval, str, len, 0); return 1; } #line 807 "ext/standard/var_unserializer.c" yy46: yych = *++YYCURSOR; if (yych == '+') goto yy47; if (yych <= '/') goto yy18; if (yych <= '9') goto yy48; goto yy18; yy47: yych = *++YYCURSOR; if (yych <= '/') goto yy18; if (yych >= ':') goto yy18; yy48: ++YYCURSOR; if ((YYLIMIT - YYCURSOR) < 2) YYFILL(2); yych = *YYCURSOR; if (yych <= '/') goto yy18; if (yych <= '9') goto yy48; if (yych >= ';') goto yy18; yych = *++YYCURSOR; if (yych != '"') goto yy18; ++YYCURSOR; #line 539 "ext/standard/var_unserializer.re" { size_t len, maxlen; char *str; len = parse_uiv(start + 2); maxlen = max - YYCURSOR; if (maxlen < len) { *p = start + 2; return 0; } str = (char*)YYCURSOR; YYCURSOR += len; if (*(YYCURSOR) != '"') { *p = YYCURSOR; return 0; } YYCURSOR += 2; *p = YYCURSOR; INIT_PZVAL(*rval); ZVAL_STRINGL(*rval, str, len, 1); return 1; } #line 856 "ext/standard/var_unserializer.c" yy53: yych = *++YYCURSOR; if (yych <= '/') { if (yych <= ',') { if (yych == '+') goto yy57; goto yy18; } else { if (yych <= '-') goto yy55; if (yych <= '.') goto yy60; goto yy18; } } else { if (yych <= 'I') { if (yych <= '9') goto yy58; if (yych <= 'H') goto yy18; goto yy56; } else { if (yych != 'N') goto yy18; } } yych = *++YYCURSOR; if (yych == 'A') goto yy76; goto yy18; yy55: yych = *++YYCURSOR; if (yych <= '/') { if (yych == '.') goto yy60; goto yy18; } else { if (yych <= '9') goto yy58; if (yych != 'I') goto yy18; } yy56: yych = *++YYCURSOR; if (yych == 'N') goto yy72; goto yy18; yy57: yych = *++YYCURSOR; if (yych == '.') goto yy60; if (yych <= '/') goto yy18; if (yych >= ':') goto yy18; yy58: ++YYCURSOR; if ((YYLIMIT - YYCURSOR) < 4) YYFILL(4); yych = *YYCURSOR; if (yych <= ':') { if (yych <= '.') { if (yych <= '-') goto yy18; goto yy70; } else { if (yych <= '/') goto yy18; if (yych <= '9') goto yy58; goto yy18; } } else { if (yych <= 'E') { if (yych <= ';') goto yy63; if (yych <= 'D') goto yy18; goto yy65; } else { if (yych == 'e') goto yy65; goto yy18; } } yy60: yych = *++YYCURSOR; if (yych <= '/') goto yy18; if (yych >= ':') goto yy18; yy61: ++YYCURSOR; if ((YYLIMIT - YYCURSOR) < 4) YYFILL(4); yych = *YYCURSOR; if (yych <= ';') { if (yych <= '/') goto yy18; if (yych <= '9') goto yy61; if (yych <= ':') goto yy18; } else { if (yych <= 'E') { if (yych <= 'D') goto yy18; goto yy65; } else { if (yych == 'e') goto yy65; goto yy18; } } yy63: ++YYCURSOR; #line 529 "ext/standard/var_unserializer.re" { #if SIZEOF_LONG == 4 use_double: #endif *p = YYCURSOR; INIT_PZVAL(*rval); ZVAL_DOUBLE(*rval, zend_strtod((const char *)start + 2, NULL)); return 1; } #line 954 "ext/standard/var_unserializer.c" yy65: yych = *++YYCURSOR; if (yych <= ',') { if (yych != '+') goto yy18; } else { if (yych <= '-') goto yy66; if (yych <= '/') goto yy18; if (yych <= '9') goto yy67; goto yy18; } yy66: yych = *++YYCURSOR; if (yych <= ',') { if (yych == '+') goto yy69; goto yy18; } else { if (yych <= '-') goto yy69; if (yych <= '/') goto yy18; if (yych >= ':') goto yy18; } yy67: ++YYCURSOR; if (YYLIMIT <= YYCURSOR) YYFILL(1); yych = *YYCURSOR; if (yych <= '/') goto yy18; if (yych <= '9') goto yy67; if (yych == ';') goto yy63; goto yy18; yy69: yych = *++YYCURSOR; if (yych <= '/') goto yy18; if (yych <= '9') goto yy67; goto yy18; yy70: ++YYCURSOR; if ((YYLIMIT - YYCURSOR) < 4) YYFILL(4); yych = *YYCURSOR; if (yych <= ';') { if (yych <= '/') goto yy18; if (yych <= '9') goto yy70; if (yych <= ':') goto yy18; goto yy63; } else { if (yych <= 'E') { if (yych <= 'D') goto yy18; goto yy65; } else { if (yych == 'e') goto yy65; goto yy18; } } yy72: yych = *++YYCURSOR; if (yych != 'F') goto yy18; yy73: yych = *++YYCURSOR; if (yych != ';') goto yy18; ++YYCURSOR; #line 514 "ext/standard/var_unserializer.re" { *p = YYCURSOR; INIT_PZVAL(*rval); if (!strncmp(start + 2, "NAN", 3)) { ZVAL_DOUBLE(*rval, php_get_nan()); } else if (!strncmp(start + 2, "INF", 3)) { ZVAL_DOUBLE(*rval, php_get_inf()); } else if (!strncmp(start + 2, "-INF", 4)) { ZVAL_DOUBLE(*rval, -php_get_inf()); } return 1; } #line 1028 "ext/standard/var_unserializer.c" yy76: yych = *++YYCURSOR; if (yych == 'N') goto yy73; goto yy18; yy77: yych = *++YYCURSOR; if (yych <= ',') { if (yych != '+') goto yy18; } else { if (yych <= '-') goto yy78; if (yych <= '/') goto yy18; if (yych <= '9') goto yy79; goto yy18; } yy78: yych = *++YYCURSOR; if (yych <= '/') goto yy18; if (yych >= ':') goto yy18; yy79: ++YYCURSOR; if (YYLIMIT <= YYCURSOR) YYFILL(1); yych = *YYCURSOR; if (yych <= '/') goto yy18; if (yych <= '9') goto yy79; if (yych != ';') goto yy18; ++YYCURSOR; #line 487 "ext/standard/var_unserializer.re" { #if SIZEOF_LONG == 4 int digits = YYCURSOR - start - 3; if (start[2] == '-' || start[2] == '+') { digits--; } /* Use double for large long values that were serialized on a 64-bit system */ if (digits >= MAX_LENGTH_OF_LONG - 1) { if (digits == MAX_LENGTH_OF_LONG - 1) { int cmp = strncmp(YYCURSOR - MAX_LENGTH_OF_LONG, long_min_digits, MAX_LENGTH_OF_LONG - 1); if (!(cmp < 0 || (cmp == 0 && start[2] == '-'))) { goto use_double; } } else { goto use_double; } } #endif *p = YYCURSOR; INIT_PZVAL(*rval); ZVAL_LONG(*rval, parse_iv(start + 2)); return 1; } #line 1082 "ext/standard/var_unserializer.c" yy83: yych = *++YYCURSOR; if (yych <= '/') goto yy18; if (yych >= '2') goto yy18; yych = *++YYCURSOR; if (yych != ';') goto yy18; ++YYCURSOR; #line 480 "ext/standard/var_unserializer.re" { *p = YYCURSOR; INIT_PZVAL(*rval); ZVAL_BOOL(*rval, parse_iv(start + 2)); return 1; } #line 1097 "ext/standard/var_unserializer.c" yy87: ++YYCURSOR; #line 473 "ext/standard/var_unserializer.re" { *p = YYCURSOR; INIT_PZVAL(*rval); ZVAL_NULL(*rval); return 1; } #line 1107 "ext/standard/var_unserializer.c" yy89: yych = *++YYCURSOR; if (yych <= ',') { if (yych != '+') goto yy18; } else { if (yych <= '-') goto yy90; if (yych <= '/') goto yy18; if (yych <= '9') goto yy91; goto yy18; } yy90: yych = *++YYCURSOR; if (yych <= '/') goto yy18; if (yych >= ':') goto yy18; yy91: ++YYCURSOR; if (YYLIMIT <= YYCURSOR) YYFILL(1); yych = *YYCURSOR; if (yych <= '/') goto yy18; if (yych <= '9') goto yy91; if (yych != ';') goto yy18; ++YYCURSOR; #line 450 "ext/standard/var_unserializer.re" { long id; *p = YYCURSOR; if (!var_hash) return 0; id = parse_iv(start + 2) - 1; if (id == -1 || var_access(var_hash, id, &rval_ref) != SUCCESS) { return 0; } if (*rval == *rval_ref) return 0; if (*rval != NULL) { zval_ptr_dtor(rval); } *rval = *rval_ref; Z_ADDREF_PP(rval); Z_UNSET_ISREF_PP(rval); return 1; } #line 1153 "ext/standard/var_unserializer.c" yy95: yych = *++YYCURSOR; if (yych <= ',') { if (yych != '+') goto yy18; } else { if (yych <= '-') goto yy96; if (yych <= '/') goto yy18; if (yych <= '9') goto yy97; goto yy18; } yy96: yych = *++YYCURSOR; if (yych <= '/') goto yy18; if (yych >= ':') goto yy18; yy97: ++YYCURSOR; if (YYLIMIT <= YYCURSOR) YYFILL(1); yych = *YYCURSOR; if (yych <= '/') goto yy18; if (yych <= '9') goto yy97; if (yych != ';') goto yy18; ++YYCURSOR; #line 429 "ext/standard/var_unserializer.re" { long id; *p = YYCURSOR; if (!var_hash) return 0; id = parse_iv(start + 2) - 1; if (id == -1 || var_access(var_hash, id, &rval_ref) != SUCCESS) { return 0; } if (*rval != NULL) { zval_ptr_dtor(rval); } *rval = *rval_ref; Z_ADDREF_PP(rval); Z_SET_ISREF_PP(rval); return 1; } #line 1197 "ext/standard/var_unserializer.c" } #line 749 "ext/standard/var_unserializer.re" return 0; }
int uopz_call_handler(UOPZ_OPCODE_HANDLER_ARGS) { /* {{{ */ switch (EX(opline)->opcode) { case ZEND_INIT_FCALL_BY_NAME: case ZEND_INIT_FCALL: case ZEND_INIT_NS_FCALL_BY_NAME: { zval *function_name = EX_CONSTANT(EX(opline)->op2); CACHE_PTR(Z_CACHE_SLOT_P(function_name), NULL); } break; case ZEND_INIT_METHOD_CALL: { if (EX(opline)->op2_type == IS_CONST) { zval *function_name = EX_CONSTANT(EX(opline)->op2); CACHE_POLYMORPHIC_PTR(Z_CACHE_SLOT_P(function_name), NULL, NULL); } } break; case ZEND_INIT_STATIC_METHOD_CALL: { zend_class_entry *ce; zval *mock; zend_string *key = NULL; if (EX(opline)->op1_type == IS_CONST) { key = zend_string_tolower(Z_STR_P(EX_CONSTANT(EX(opline)->op1))); } else if (EX(opline)->op1_type != IS_UNUSED) { ce = Z_CE_P(EX_VAR(EX(opline)->op1.var)); if (!ce) { break; } key = zend_string_tolower(ce->name); } if (key && (mock = zend_hash_find(&UOPZ(mocks), key))) { zend_class_entry *poser; if (Z_TYPE_P(mock) == IS_STRING) { poser = zend_lookup_class(Z_STR_P(mock)); if (!poser) { break; } } else poser = Z_OBJCE_P(mock); if (EX(opline)->op1_type == IS_CONST) { CACHE_PTR(Z_CACHE_SLOT_P(EX_CONSTANT(EX(opline)->op1)), poser); } else { Z_CE_P(EX_VAR(EX(opline)->op1.var)) = poser; } } if (key && EX(opline)->op2_type == IS_CONST) { zval *function_name = EX_CONSTANT(EX(opline)->op2); if (EX(opline)->op1_type == IS_CONST) { CACHE_PTR(Z_CACHE_SLOT_P(function_name), NULL); } else { CACHE_POLYMORPHIC_PTR(Z_CACHE_SLOT_P(function_name), NULL, NULL); } } if (key) { zend_string_release(key); } } break; } switch (EX(opline)->opcode) { case ZEND_INIT_FCALL_BY_NAME: if (uopz_init_fcall_by_name_handler) return uopz_init_fcall_by_name_handler(UOPZ_OPCODE_HANDLER_ARGS_PASSTHRU); case ZEND_INIT_FCALL: if (uopz_init_fcall_handler) return uopz_init_fcall_handler(UOPZ_OPCODE_HANDLER_ARGS_PASSTHRU); case ZEND_INIT_NS_FCALL_BY_NAME: if (uopz_init_ns_fcall_by_name_handler) return uopz_init_ns_fcall_by_name_handler(UOPZ_OPCODE_HANDLER_ARGS_PASSTHRU); case ZEND_INIT_METHOD_CALL: if (uopz_init_method_call_handler) return uopz_init_method_call_handler(UOPZ_OPCODE_HANDLER_ARGS_PASSTHRU); case ZEND_INIT_STATIC_METHOD_CALL: if (uopz_init_static_method_call_handler) return uopz_init_static_method_call_handler(UOPZ_OPCODE_HANDLER_ARGS_PASSTHRU); } return ZEND_USER_OPCODE_DISPATCH; } /* }}} */
ONPHP_METHOD(Singleton, getInstance) { char *name; int length, argc = ZEND_NUM_ARGS(); zend_class_entry **cep; zval *object, *args; zval **stored; zval ***params = NULL; if (argc < 1) { WRONG_PARAM_COUNT; } params = safe_emalloc(sizeof(zval **), argc, 0); if (zend_get_parameters_array_ex(argc, params) == FAILURE) { efree(params); ONPHP_THROW( BaseException, "Failed to get calling arguments for object creation" ); } // replica of historical Singleton's behaviour if (argc > 2) { int i; ALLOC_INIT_ZVAL(args); array_init(args); for (i = 1; i < argc; ++i) { add_next_index_zval(args, *params[i]); } params[1] = &args; argc = 2; } if (Z_TYPE_PP(params[0]) != IS_STRING) { ONPHP_THROW(WrongArgumentException, "strange class name given"); } name = estrdup(Z_STRVAL_PP(params[0])); length = strlen(name); if ( zend_hash_find( Z_ARRVAL_P(instances), name, length + 1, (void **) &stored ) == SUCCESS ) { efree(params); efree(name); object = *stored; zval_copy_ctor(object); } else { // stolen from Reflection's newInstance() if (zend_lookup_class(name, length, &cep TSRMLS_CC) == SUCCESS) { zval *retval_ptr; zend_fcall_info fci; zend_fcall_info_cache fcc; zend_class_entry *ce = *cep; // can use ce->name instead now efree(name); if (!instanceof_function(ce, onphp_ce_Singleton TSRMLS_CC)) { efree(params); ONPHP_THROW( WrongArgumentException, "Class '%s' is something not a Singleton's child", ce->name ); } // we can call protected consturctors, // since all classes are childs of Singleton if (ce->constructor->common.fn_flags & ZEND_ACC_PRIVATE) { efree(params); ONPHP_THROW( BaseException, "Can not call private constructor for '%s' creation", ce->name ); } else if (ce->constructor->common.fn_flags & ZEND_ACC_PUBLIC) { efree(params); ONPHP_THROW( BaseException, "Don't want to deal with '%s' class " "due to public constructor there", ce->name ); } ALLOC_INIT_ZVAL(object); object_init_ex(object, ce); fci.size = sizeof(fci); fci.function_table = EG(function_table); fci.function_name = NULL; fci.symbol_table = NULL; fci.object_pp = &object; fci.retval_ptr_ptr = &retval_ptr; fci.param_count = argc - 1; fci.params = params + 1; fcc.initialized = 1; fcc.function_handler = ce->constructor; fcc.calling_scope = EG(scope); fcc.object_pp = &object; if (zend_call_function(&fci, &fcc TSRMLS_CC) == FAILURE) { zend_throw_exception_ex( onphp_ce_BaseException, 0 TSRMLS_CC, "Failed to call '%s' constructor", ce->name ); } efree(params); if (retval_ptr) { zval_ptr_dtor(&retval_ptr); } if (EG(exception)) { return; } add_assoc_zval_ex(instances, ce->name, length + 1, object); } } RETURN_ZVAL(object, 1, 0); }
PHP_METHOD(Edge_Controller, get) { char *name; int nlen = 0; if(zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "s", &name, &nlen) == FAILURE) { return; } zval * data; data = edge_request_query(EDGE_REQUEST_VARS_GET, name); if(Z_TYPE_P(data) == IS_NULL && nlen != 0) { zval_ptr_dtor(&data); if(strncmp("model", name, nlen) == 0) { zval *arg; zval *ret; zend_object *zobj; zend_class_entry *ce; zobj = Z_OBJ_P(getThis()); ce = zobj->ce; char *controller_prefix; controller_prefix = estrndup(ce->name, ce->name_length - strlen("Controller")); char *model_class_name; spprintf(&model_class_name, 0, "%s", controller_prefix); MAKE_STD_ZVAL(arg); ZVAL_STRING(arg, model_class_name, 1); zend_call_method_with_1_params(&getThis(), edge_controller_ce, NULL, "model", &ret, arg); efree(model_class_name); zval_ptr_dtor(&arg); if(!Z_BVAL_P(ret)) { RETURN_ZVAL(ret, 1, 1); } efree(controller_prefix); RETURN_ZVAL(ret, 1, 1); } else { char *mg_class_name = NULL; name[0] = toupper(name[0]); int mg_class_len = spprintf(&mg_class_name, 0, "If_%s", name); zend_class_entry **mg_ce; if(zend_lookup_class(mg_class_name, mg_class_len, &mg_ce TSRMLS_CC) == FAILURE) { RETURN_FALSE; } zval *mg_obj; MAKE_STD_ZVAL(mg_obj); object_init_ex(mg_obj, *mg_ce); RETURN_ZVAL(mg_obj, 1, 1); } } RETURN_ZVAL(data, 1, 1); }
static void dic_optimizer_get_handler(INTERNAL_FUNCTION_PARAMETERS) { char *id, should_free = 1; zend_ulong id_hash; int id_len, i; long oninvalid, exception_on_invalid_reference_const; zval **found_service, **alias, **method_in_map = NULL, *this_services, *this_aliases, *this_methodMap, *this_loading; zend_function *method = NULL; if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "s|l", &id, &id_len, &oninvalid) == FAILURE) { return; } if (strcasecmp(id, "service_container") == 0) { RETURN_THIS; } this_services = zend_read_property(Z_OBJCE_P(getThis()), getThis(), SYMFONY_DIC_TOKEN_SERVICES_KEY, sizeof(SYMFONY_DIC_TOKEN_SERVICES_KEY) - 1, 0 TSRMLS_CC); this_aliases = zend_read_property(Z_OBJCE_P(getThis()), getThis(), SYMFONY_DIC_TOKEN_ALIASES_KEY, sizeof(SYMFONY_DIC_TOKEN_ALIASES_KEY) - 1, 0 TSRMLS_CC); this_loading = zend_read_property(Z_OBJCE_P(getThis()), getThis(), SYMFONY_DIC_TOKEN_LOADING_KEY, sizeof(SYMFONY_DIC_TOKEN_LOADING_KEY) - 1, 0 TSRMLS_CC); this_methodMap = zend_read_property(Z_OBJCE_P(getThis()), getThis(), SYMFONY_DIC_TOKEN_METHODMAP_KEY, sizeof(SYMFONY_DIC_TOKEN_METHODMAP_KEY) - 1, 0 TSRMLS_CC); if (!SYMFONY_DIC_G(cache_done)) { zval invalidBehavior; zend_class_entry **exception_ce; zend_get_constant_ex("self::EXCEPTION_ON_INVALID_REFERENCE", sizeof("self::EXCEPTION_ON_INVALID_REFERENCE") - 1, &invalidBehavior, Z_OBJCE_P(getThis()), 0 TSRMLS_CC); SYMFONY_DIC_G(invalid_behavior) = Z_LVAL(invalidBehavior); if (FAILURE == zend_lookup_class(SYMFONY_DIC_TOKEN_SERVICE_CIRCULAR_REFERENCE_EXCEPTION_KEY_UP, sizeof(SYMFONY_DIC_TOKEN_SERVICE_CIRCULAR_REFERENCE_EXCEPTION_KEY_UP) - 1, &exception_ce TSRMLS_CC)) { zend_error_noreturn(E_ERROR, "Class %s not found", SYMFONY_DIC_TOKEN_SERVICE_CIRCULAR_REFERENCE_EXCEPTION_KEY_UP); } SYMFONY_DIC_G(ServiceCircularReferenceException) = *exception_ce; if (FAILURE == zend_lookup_class(SYMFONY_DIC_TOKEN_SERVICE_NOT_FOUND_EXCEPTION_KEY_UP, sizeof(SYMFONY_DIC_TOKEN_SERVICE_NOT_FOUND_EXCEPTION_KEY_UP) - 1, &exception_ce TSRMLS_CC)) { zend_error_noreturn(E_ERROR, "Class %s not found", SYMFONY_DIC_TOKEN_SERVICE_NOT_FOUND_EXCEPTION_KEY_UP); } SYMFONY_DIC_G(ServiceNotFoundException) = *exception_ce; if (FAILURE == zend_lookup_class(SYMFONY_DIC_TOKEN_INACTIVE_SCOPE_EXCEPTION_KEY_UP, sizeof(SYMFONY_DIC_TOKEN_INACTIVE_SCOPE_EXCEPTION_KEY_UP) - 1, &exception_ce TSRMLS_CC)) { zend_error_noreturn(E_ERROR, "Class %s not found", SYMFONY_DIC_TOKEN_INACTIVE_SCOPE_EXCEPTION_KEY_UP); } SYMFONY_DIC_G(InactiveScopeException) = *exception_ce; SYMFONY_DIC_G(cache_done) = 1; } exception_on_invalid_reference_const = SYMFONY_DIC_G(invalid_behavior); if (ZEND_NUM_ARGS() <= 1) { oninvalid = exception_on_invalid_reference_const; } if (IS_INTERNED(id)) { id_hash = INTERNED_HASH(id); } else { id_hash = zend_inline_hash_func(id, id_len + 1); } id = estrndup(id, id_len); /* zend_str_tolower will change it otherwise */ for (i = 0; i <= 1; i++, zend_str_tolower(id, id_len), id_hash = zend_inline_hash_func(id, id_len + 1)) { if (zend_hash_quick_find(Z_ARRVAL_P(this_aliases), id, id_len + 1, id_hash, (void **)&alias) == SUCCESS) { should_free = 0; efree(id); id = Z_STRVAL_PP(alias); id_len = Z_STRLEN_PP(alias); id_hash = zend_inline_hash_func(id, id_len + 1); } if (zend_hash_quick_find(Z_ARRVAL_P(this_services), id, id_len + 1, id_hash, (void **)&found_service) == SUCCESS) { RETVAL_ZVAL_FAST(*found_service); goto free_and_return; } } if (zend_hash_quick_exists(Z_ARRVAL_P(this_loading), id, id_len + 1, id_hash)) { zval *ServiceCircularReferenceException; ALLOC_INIT_ZVAL(ServiceCircularReferenceException); /* ctor_args */ object_init_ex(ServiceCircularReferenceException, SYMFONY_DIC_G(ServiceCircularReferenceException)); zend_throw_exception_object(ServiceCircularReferenceException TSRMLS_CC); goto free_and_return; } zend_hash_quick_find(Z_ARRVAL_P(this_methodMap), id, id_len + 1, id_hash, (void **)&method_in_map); if (!method_in_map) { char *new_id; for (i=0; i < id_len; i++) { if (id[i] == '_') { memmove(&id[i], &id[i + 1], --id_len); } } php_strtr(id, id_len, ".\\", "__", 2); id_len = spprintf(&new_id, 0, "get%sservice", id); efree(id); id = new_id; id_hash = zend_inline_hash_func(id, id_len + 1); zend_hash_quick_find(&Z_OBJCE_P(getThis())->function_table, id, id_len + 1, id_hash, (void **)&method); if (!method) { if (oninvalid == exception_on_invalid_reference_const) { zval *ServiceNotFoundException; ALLOC_INIT_ZVAL(ServiceNotFoundException); object_init_ex(ServiceNotFoundException, SYMFONY_DIC_G(ServiceNotFoundException)); zend_throw_exception_object(ServiceNotFoundException TSRMLS_CC); /* ctor_args */ } goto free_and_return; } } else { char *method_name_lc; method_name_lc = zend_str_tolower_dup(Z_STRVAL_PP(method_in_map), Z_STRLEN_PP(method_in_map)); zend_hash_find(&Z_OBJCE_P(getThis())->function_table, method_name_lc, Z_STRLEN_PP(method_in_map) + 1, (void **)&method); efree(method_name_lc); } zend_fcall_info fci = {0}; zend_fcall_info_cache fcic = {0}; zval *loading, *result; ALLOC_INIT_ZVAL(loading); ZVAL_BOOL(loading, 1); zend_hash_quick_add(Z_ARRVAL_P(this_loading), id, id_len + 1, id_hash, &loading, sizeof(zval *), NULL); fcic.called_scope = Z_OBJCE_P(getThis()); fcic.calling_scope = Z_OBJCE_P(getThis()); fcic.function_handler = method; fcic.initialized = 1; fcic.object_ptr = getThis(); fci.retval_ptr_ptr = &result; fci.size = sizeof(zend_fcall_info); zend_call_function(&fci, &fcic TSRMLS_CC); zend_hash_quick_del(Z_ARRVAL_P(this_loading), id, id_len + 1, id_hash); if (!EG(exception)) { RETVAL_ZVAL_FAST(result); } else { zend_hash_quick_del(Z_ARRVAL_P(this_services), id, id_len, id_hash); if (instanceof_function(Z_OBJCE_P(EG(exception)), SYMFONY_DIC_G(InactiveScopeException) TSRMLS_CC) && oninvalid == exception_on_invalid_reference_const) { EG(exception) = NULL; } } zval_ptr_dtor(&result); free_and_return: if (should_free) { efree(id); } return; }
static php_stream_filter *user_filter_factory_create(const char *filtername, zval *filterparams, uint8_t persistent) { struct php_user_filter_data *fdat = NULL; php_stream_filter *filter; zval obj, zfilter; zval func_name; zval retval; size_t len; /* some sanity checks */ if (persistent) { php_error_docref(NULL, E_WARNING, "cannot use a user-space filter with a persistent stream"); return NULL; } len = strlen(filtername); /* determine the classname/class entry */ if (NULL == (fdat = zend_hash_str_find_ptr(BG(user_filter_map), (char*)filtername, len))) { char *period; /* Userspace Filters using ambiguous wildcards could cause problems. i.e.: myfilter.foo.bar will always call into myfilter.foo.* never seeing myfilter.* TODO: Allow failed userfilter creations to continue scanning through the list */ if ((period = strrchr(filtername, '.'))) { char *wildcard = safe_emalloc(len, 1, 3); /* Search for wildcard matches instead */ memcpy(wildcard, filtername, len + 1); /* copy \0 */ period = wildcard + (period - filtername); while (period) { *period = '\0'; strncat(wildcard, ".*", 2); if (NULL != (fdat = zend_hash_str_find_ptr(BG(user_filter_map), wildcard, strlen(wildcard)))) { period = NULL; } else { *period = '\0'; period = strrchr(wildcard, '.'); } } efree(wildcard); } if (fdat == NULL) { php_error_docref(NULL, E_WARNING, "Err, filter \"%s\" is not in the user-filter map, but somehow the user-filter-factory was invoked for it!?", filtername); return NULL; } } /* bind the classname to the actual class */ if (fdat->ce == NULL) { if (NULL == (fdat->ce = zend_lookup_class(fdat->classname))) { php_error_docref(NULL, E_WARNING, "user-filter \"%s\" requires class \"%s\", but that class is not defined", filtername, ZSTR_VAL(fdat->classname)); return NULL; } } filter = php_stream_filter_alloc(&userfilter_ops, NULL, 0); if (filter == NULL) { return NULL; } /* create the object */ object_init_ex(&obj, fdat->ce); /* filtername */ add_property_string(&obj, "filtername", (char*)filtername); /* and the parameters, if any */ if (filterparams) { add_property_zval(&obj, "params", filterparams); } else { add_property_null(&obj, "params"); } /* invoke the constructor */ ZVAL_STRINGL(&func_name, "oncreate", sizeof("oncreate")-1); call_user_function_ex(NULL, &obj, &func_name, &retval, 0, NULL, 0, NULL); if (Z_TYPE(retval) != IS_UNDEF) { if (Z_TYPE(retval) == IS_FALSE) { /* User reported filter creation error "return false;" */ zval_ptr_dtor(&retval); /* Kill the filter (safely) */ ZVAL_UNDEF(&filter->abstract); php_stream_filter_free(filter); /* Kill the object */ zval_ptr_dtor(&obj); /* Report failure to filter_alloc */ return NULL; } zval_ptr_dtor(&retval); } zval_ptr_dtor(&func_name); /* set the filter property, this will be used during cleanup */ ZVAL_RES(&zfilter, zend_register_resource(filter, le_userfilters)); ZVAL_COPY_VALUE(&filter->abstract, &obj); add_property_zval(&obj, "filter", &zfilter); /* add_property_zval increments the refcount which is unwanted here */ zval_ptr_dtor(&zfilter); return filter; }
inline static zend_class_entry* msgpack_unserialize_class( zval **container, char *class_name, size_t name_len) { zend_class_entry *ce, **pce; zend_bool incomplete_class = 0; zval *user_func, *retval_ptr, **args[1], *arg_func_name; TSRMLS_FETCH(); do { /* Try to find class directly */ if (zend_lookup_class(class_name, name_len, &pce TSRMLS_CC) == SUCCESS) { ce = *pce; break; } /* Check for unserialize callback */ if ((PG(unserialize_callback_func) == NULL) || (PG(unserialize_callback_func)[0] == '\0')) { incomplete_class = 1; ce = PHP_IC_ENTRY; break; } /* Call unserialize callback */ ALLOC_INIT_ZVAL(user_func); ZVAL_STRING(user_func, PG(unserialize_callback_func), 1); args[0] = &arg_func_name; ALLOC_INIT_ZVAL(arg_func_name); ZVAL_STRING(arg_func_name, class_name, 1); if (call_user_function_ex( CG(function_table), NULL, user_func, &retval_ptr, 1, args, 0, NULL TSRMLS_CC) != SUCCESS) { MSGPACK_WARNING("[msgpack] (%s) defined (%s) but not found", __FUNCTION__, class_name); incomplete_class = 1; ce = PHP_IC_ENTRY; zval_ptr_dtor(&user_func); zval_ptr_dtor(&arg_func_name); break; } if (retval_ptr) { zval_ptr_dtor(&retval_ptr); } /* The callback function may have defined the class */ if (zend_lookup_class(class_name, name_len, &pce TSRMLS_CC) == SUCCESS) { ce = *pce; } else { MSGPACK_WARNING("[msgpack] (%s) Function %s() hasn't defined " "the class it was called for", __FUNCTION__, class_name); incomplete_class = 1; ce = PHP_IC_ENTRY; } zval_ptr_dtor(&user_func); zval_ptr_dtor(&arg_func_name); } while(0); if (EG(exception)) { MSGPACK_WARNING("[msgpack] (%s) Exception error", __FUNCTION__); return NULL; } object_init_ex(*container, ce); /* store incomplete class name */ if (incomplete_class) { php_store_class_name(*container, class_name, name_len); } return ce; }
PHP_METHOD(jsonrpc_server, register) { zval *closure=NULL; zval *val; zval *name; zval *callbacks; char *lcname; char *name_str, *tmp; int name_len, tmp_len; zval *classname; zend_class_entry **pce; zend_class_entry *ce; zend_function *fptr; zval *object = getThis(); if (zend_parse_parameters_ex(ZEND_PARSE_PARAMS_QUIET, ZEND_NUM_ARGS() TSRMLS_CC, "zO", &name, &closure, zend_ce_closure) == SUCCESS) { fptr = (zend_function*)zend_get_closure_method_def(closure TSRMLS_CC); Z_ADDREF_P(closure); } else if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "zs", &name, &name_str, &name_len) == SUCCESS) { if ((tmp = strstr(name_str, "::")) == NULL) { char *nsname; lcname = zend_str_tolower_dup(name_str, name_len); // Ignore leading "\" nsname = lcname; if (lcname[0] == '\\') { nsname = &lcname[1]; name_len--; } if (zend_hash_find(EG(function_table), nsname, name_len + 1, (void **)&fptr) == FAILURE) { efree(lcname); php_error_docref(NULL TSRMLS_CC, E_WARNING, "Function %s() does not exist", name_str); return; } efree(lcname); }else { tmp_len = tmp - name_str; MAKE_STD_ZVAL(classname); ZVAL_STRINGL(classname, name_str, tmp_len, 1); name_len = name_len - (tmp_len + 2); name_str = tmp + 2; //php_printf("classname: %s, method: %s\n", Z_STRVAL_P(classname), name_str); if (zend_lookup_class(Z_STRVAL_P(classname), Z_STRLEN_P(classname), &pce TSRMLS_CC) == FAILURE) { php_error_docref(NULL TSRMLS_CC, E_WARNING, "Class %s does exist", Z_STRVAL_P(classname)); //zend_throw_exception_ex(reflection_exception_ptr, 0 TSRMLS_CC, // "Class %s does not exist", Z_STRVAL_P(classname)); zval_dtor(classname); return; } ce = *pce; lcname = zend_str_tolower_dup(name_str, name_len); if (zend_hash_find(&ce->function_table, lcname, name_len + 1, (void **) &fptr) == FAILURE) { efree(lcname); php_error_docref(NULL TSRMLS_CC, E_WARNING, "Method %s::%s() does not exist", ce->name, name_str); //zend_throw_exception_ex(reflection_exception_ptr, 0 TSRMLS_CC, // "Method %s::%s() does not exist", ce->name, name_str); return; } efree(lcname); } }else { return ; } callbacks = zend_read_property( php_jsonrpc_server_entry, object, "callbacks", sizeof("callbacks")-1, 0 TSRMLS_CC ); MAKE_STD_ZVAL(val); #if PHP_VERSION_ID < 50399 zend_create_closure(val, fptr TSRMLS_CC); #else zend_create_closure(val, fptr, NULL, NULL TSRMLS_CC); #endif add_assoc_zval(callbacks, Z_STRVAL_P(name), val); zend_update_property(php_jsonrpc_server_entry, object, "callbacks", sizeof("callbacks")-1, callbacks TSRMLS_CC); RETURN_ZVAL(object,1,0); }
int uopz_mock_handler(UOPZ_OPCODE_HANDLER_ARGS) { /* {{{ */ int UOPZ_VM_ACTION = ZEND_USER_OPCODE_DISPATCH; zend_string *key; zval *mock = NULL; zend_class_entry *ce; if (EX(opline)->op1_type == IS_CONST) { ce = CACHED_PTR(Z_CACHE_SLOT_P(EX_CONSTANT(EX(opline)->op1))); if (UNEXPECTED(ce == NULL)) { key = Z_STR_P(EX_CONSTANT(EX(opline)->op1)); } else { key = ce->name; } key = zend_string_tolower(key); } else if(EX(opline)->op1_type == IS_UNUSED) { ce = zend_fetch_class(NULL, EX(opline)->op1.num); if (UNEXPECTED(ce == NULL)) { return UOPZ_VM_ACTION; } key = zend_string_tolower(ce->name); } else { key = zend_string_tolower( Z_CE_P(EX_VAR(EX(opline)->op1.var))->name); } if (UNEXPECTED((mock = zend_hash_find(&UOPZ(mocks), key)))) { switch (Z_TYPE_P(mock)) { case IS_OBJECT: ZVAL_COPY( EX_VAR(EX(opline)->result.var), mock); #if PHP_VERSION_ID < 70100 EX(opline) = OP_JMP_ADDR(EX(opline), EX(opline)->op2); #else if (EX(opline)->extended_value == 0 && (EX(opline)+1)->opcode == ZEND_DO_FCALL) { EX(opline) += 2; } #endif UOPZ_VM_ACTION = ZEND_USER_OPCODE_CONTINUE; break; case IS_STRING: ce = zend_lookup_class(Z_STR_P(mock)); if (EXPECTED(ce)) { if (EX(opline)->op1_type == IS_CONST) { CACHE_PTR(Z_CACHE_SLOT_P(EX_CONSTANT(EX(opline)->op1)), ce); } else if (EX(opline)->op1_type != IS_UNUSED) { Z_CE_P(EX_VAR(EX(opline)->op1.var)) = ce; } else { /* oh dear, can't do what is requested */ } } break; } } zend_string_release(key); if (UOPZ_VM_ACTION == ZEND_USER_OPCODE_DISPATCH) { if (uopz_new_handler) { return uopz_new_handler(UOPZ_OPCODE_HANDLER_ARGS_PASSTHRU); } } return UOPZ_VM_ACTION; } /* }}} */
static void SWIG_ZTS_SetPointerZval(zval *z, void *ptr, swig_type_info *type, int newobject TSRMLS_DC) { /* * First test for Null pointers. Return those as PHP native NULL */ if (!ptr ) { ZVAL_NULL(z); return; } if (type->clientdata) { swig_object_wrapper *value; if (! (*(int *)(type->clientdata))) zend_error(E_ERROR, "Type: %s failed to register with zend",type->name); value=(swig_object_wrapper *)emalloc(sizeof(swig_object_wrapper)); value->ptr=ptr; value->newobject=(newobject & 1); if ((newobject & 2) == 0) { /* Just register the pointer as a resource. */ ZEND_REGISTER_RESOURCE(z, value, *(int *)(type->clientdata)); } else { /* * Wrap the resource in an object, the resource will be accessible * via the "_cPtr" member. This is currently only used by * directorin typemaps. */ zval *resource; zend_class_entry **ce = NULL; const char *type_name = type->name+3; /* +3 so: _p_Foo -> Foo */ size_t type_name_len; int result; const char * p; /* Namespace__Foo -> Foo */ /* FIXME: ugly and goes wrong for classes with __ in their names. */ while ((p = strstr(type_name, "__")) != NULL) { type_name = p + 2; } type_name_len = strlen(type_name); MAKE_STD_ZVAL(resource); ZEND_REGISTER_RESOURCE(resource, value, *(int *)(type->clientdata)); if (SWIG_PREFIX_LEN > 0) { char * classname = (char*)emalloc(SWIG_PREFIX_LEN + type_name_len + 1); strcpy(classname, SWIG_PREFIX); strcpy(classname + SWIG_PREFIX_LEN, type_name); result = zend_lookup_class(classname, SWIG_PREFIX_LEN + type_name_len, &ce TSRMLS_CC); efree(classname); } else { result = zend_lookup_class((char *)type_name, type_name_len, &ce TSRMLS_CC); } if (result != SUCCESS) { /* class does not exist */ object_init(z); } else { object_init_ex(z, *ce); } Z_SET_REFCOUNT_P(z, 1); Z_SET_ISREF_P(z); zend_hash_update(HASH_OF(z), (char*)"_cPtr", sizeof("_cPtr"), (void*)&resource, sizeof(zval), NULL); } return; } zend_error(E_ERROR, "Type: %s not registered with zend",type->name); }
int uopz_fetch_handler(UOPZ_OPCODE_HANDLER_ARGS) { /* {{{ */ zval *name = NULL; zend_string *key = NULL; int UOPZ_VM_ACTION = ZEND_USER_OPCODE_DISPATCH; do { if (EX(opline)->op2_type == IS_UNUSED) { break; } if (EX(opline)->op2_type == IS_CONST) { name = EX_CONSTANT(EX(opline)->op2); if (name) { key = Z_STR_P(name); } } else if (EX(opline)->op2_type != IS_UNUSED) { name = EX_VAR(EX(opline)->op2.var); if (Z_TYPE_P(name) == IS_STRING) { key = Z_STR_P(name); } else if (Z_TYPE_P(name) == IS_OBJECT) { key = Z_OBJCE_P(name)->name; } else { } } if (key) { zval *mock = NULL; zend_class_entry *ce = NULL; zend_string *lookup = zend_string_tolower(key); if (UNEXPECTED((mock = zend_hash_find(&UOPZ(mocks), lookup)))) { switch (Z_TYPE_P(mock)) { case IS_OBJECT: ce = Z_OBJCE_P(mock); break; case IS_STRING: ce = zend_lookup_class(Z_STR_P(mock)); break; } if (ce) { if (EX(opline)->op2_type == IS_CONST) { CACHE_PTR(Z_CACHE_SLOT_P(name), ce); } Z_CE_P(EX_VAR(EX(opline)->result.var)) = ce; UOPZ_VM_ACTION = ZEND_USER_OPCODE_CONTINUE; } } zend_string_release(lookup); } } while(0); if (UOPZ_VM_ACTION == ZEND_USER_OPCODE_CONTINUE) { EX(opline) = EX(opline) + 1; } else { if (uopz_fetch_class_handler) { return uopz_fetch_class_handler(UOPZ_OPCODE_HANDLER_ARGS_PASSTHRU); } } return UOPZ_VM_ACTION; } /* }}} */
PHPAPI int php_var_unserialize_ex(UNSERIALIZE_PARAMETER) { const unsigned char *cursor, *limit, *marker, *start; zval *rval_ref; limit = max; cursor = *p; if (YYCURSOR >= YYLIMIT) { return 0; } if (var_hash && (*p)[0] != 'R') { var_push(var_hash, rval); } start = cursor; #line 518 "ext/standard/var_unserializer.c" { YYCTYPE yych; static const unsigned char yybm[] = { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, }; if ((YYLIMIT - YYCURSOR) < 7) YYFILL(7); yych = *YYCURSOR; switch (yych) { case 'C': case 'O': goto yy13; case 'N': goto yy5; case 'R': goto yy2; case 'S': goto yy10; case 'a': goto yy11; case 'b': goto yy6; case 'd': goto yy8; case 'i': goto yy7; case 'o': goto yy12; case 'r': goto yy4; case 's': goto yy9; case '}': goto yy14; default: goto yy16; } yy2: yych = *(YYMARKER = ++YYCURSOR); if (yych == ':') goto yy95; yy3: #line 873 "ext/standard/var_unserializer.re" { return 0; } #line 580 "ext/standard/var_unserializer.c" yy4: yych = *(YYMARKER = ++YYCURSOR); if (yych == ':') goto yy89; goto yy3; yy5: yych = *++YYCURSOR; if (yych == ';') goto yy87; goto yy3; yy6: yych = *(YYMARKER = ++YYCURSOR); if (yych == ':') goto yy83; goto yy3; yy7: yych = *(YYMARKER = ++YYCURSOR); if (yych == ':') goto yy77; goto yy3; yy8: yych = *(YYMARKER = ++YYCURSOR); if (yych == ':') goto yy53; goto yy3; yy9: yych = *(YYMARKER = ++YYCURSOR); if (yych == ':') goto yy46; goto yy3; yy10: yych = *(YYMARKER = ++YYCURSOR); if (yych == ':') goto yy39; goto yy3; yy11: yych = *(YYMARKER = ++YYCURSOR); if (yych == ':') goto yy32; goto yy3; yy12: yych = *(YYMARKER = ++YYCURSOR); if (yych == ':') goto yy25; goto yy3; yy13: yych = *(YYMARKER = ++YYCURSOR); if (yych == ':') goto yy17; goto yy3; yy14: ++YYCURSOR; #line 867 "ext/standard/var_unserializer.re" { /* this is the case where we have less data than planned */ php_error_docref(NULL, E_NOTICE, "Unexpected end of serialized data"); return 0; /* not sure if it should be 0 or 1 here? */ } #line 629 "ext/standard/var_unserializer.c" yy16: yych = *++YYCURSOR; goto yy3; yy17: yych = *++YYCURSOR; if (yybm[0+yych] & 128) { goto yy20; } if (yych == '+') goto yy19; yy18: YYCURSOR = YYMARKER; goto yy3; yy19: yych = *++YYCURSOR; if (yybm[0+yych] & 128) { goto yy20; } goto yy18; yy20: ++YYCURSOR; if ((YYLIMIT - YYCURSOR) < 2) YYFILL(2); yych = *YYCURSOR; if (yybm[0+yych] & 128) { goto yy20; } if (yych <= '/') goto yy18; if (yych >= ';') goto yy18; yych = *++YYCURSOR; if (yych != '"') goto yy18; ++YYCURSOR; #line 722 "ext/standard/var_unserializer.re" { size_t len, len2, len3, maxlen; zend_long elements; char *str; zend_string *class_name; zend_class_entry *ce; int incomplete_class = 0; int custom_object = 0; zval user_func; zval retval; zval args[1]; if (!var_hash) return 0; if (*start == 'C') { custom_object = 1; } len2 = len = parse_uiv(start + 2); maxlen = max - YYCURSOR; if (maxlen < len || len == 0) { *p = start + 2; return 0; } str = (char*)YYCURSOR; YYCURSOR += len; if (*(YYCURSOR) != '"') { *p = YYCURSOR; return 0; } if (*(YYCURSOR+1) != ':') { *p = YYCURSOR+1; return 0; } len3 = strspn(str, "0123456789_abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ\177\200\201\202\203\204\205\206\207\210\211\212\213\214\215\216\217\220\221\222\223\224\225\226\227\230\231\232\233\234\235\236\237\240\241\242\243\244\245\246\247\250\251\252\253\254\255\256\257\260\261\262\263\264\265\266\267\270\271\272\273\274\275\276\277\300\301\302\303\304\305\306\307\310\311\312\313\314\315\316\317\320\321\322\323\324\325\326\327\330\331\332\333\334\335\336\337\340\341\342\343\344\345\346\347\350\351\352\353\354\355\356\357\360\361\362\363\364\365\366\367\370\371\372\373\374\375\376\377\\"); if (len3 != len) { *p = YYCURSOR + len3 - len; return 0; } class_name = zend_string_init(str, len, 0); do { if(!unserialize_allowed_class(class_name, classes)) { incomplete_class = 1; ce = PHP_IC_ENTRY; break; } /* Try to find class directly */ BG(serialize_lock)++; ce = zend_lookup_class(class_name); if (ce) { BG(serialize_lock)--; if (EG(exception)) { zend_string_release(class_name); return 0; } break; } BG(serialize_lock)--; if (EG(exception)) { zend_string_release(class_name); return 0; } /* Check for unserialize callback */ if ((PG(unserialize_callback_func) == NULL) || (PG(unserialize_callback_func)[0] == '\0')) { incomplete_class = 1; ce = PHP_IC_ENTRY; break; } /* Call unserialize callback */ ZVAL_STRING(&user_func, PG(unserialize_callback_func)); ZVAL_STR_COPY(&args[0], class_name); BG(serialize_lock)++; if (call_user_function_ex(CG(function_table), NULL, &user_func, &retval, 1, args, 0, NULL) != SUCCESS) { BG(serialize_lock)--; if (EG(exception)) { zend_string_release(class_name); zval_ptr_dtor(&user_func); zval_ptr_dtor(&args[0]); return 0; } php_error_docref(NULL, E_WARNING, "defined (%s) but not found", Z_STRVAL(user_func)); incomplete_class = 1; ce = PHP_IC_ENTRY; zval_ptr_dtor(&user_func); zval_ptr_dtor(&args[0]); break; } BG(serialize_lock)--; zval_ptr_dtor(&retval); if (EG(exception)) { zend_string_release(class_name); zval_ptr_dtor(&user_func); zval_ptr_dtor(&args[0]); return 0; } /* The callback function may have defined the class */ if ((ce = zend_lookup_class(class_name)) == NULL) { php_error_docref(NULL, E_WARNING, "Function %s() hasn't defined the class it was called for", Z_STRVAL(user_func)); incomplete_class = 1; ce = PHP_IC_ENTRY; } zval_ptr_dtor(&user_func); zval_ptr_dtor(&args[0]); break; } while (1); *p = YYCURSOR; if (custom_object) { int ret; ret = object_custom(UNSERIALIZE_PASSTHRU, ce); if (ret && incomplete_class) { php_store_class_name(rval, ZSTR_VAL(class_name), len2); } zend_string_release(class_name); return ret; } elements = object_common1(UNSERIALIZE_PASSTHRU, ce); if (incomplete_class) { php_store_class_name(rval, ZSTR_VAL(class_name), len2); } zend_string_release(class_name); return object_common2(UNSERIALIZE_PASSTHRU, elements); } #line 805 "ext/standard/var_unserializer.c" yy25: yych = *++YYCURSOR; if (yych <= ',') { if (yych != '+') goto yy18; } else { if (yych <= '-') goto yy26; if (yych <= '/') goto yy18; if (yych <= '9') goto yy27; goto yy18; } yy26: yych = *++YYCURSOR; if (yych <= '/') goto yy18; if (yych >= ':') goto yy18; yy27: ++YYCURSOR; if ((YYLIMIT - YYCURSOR) < 2) YYFILL(2); yych = *YYCURSOR; if (yych <= '/') goto yy18; if (yych <= '9') goto yy27; if (yych >= ';') goto yy18; yych = *++YYCURSOR; if (yych != '"') goto yy18; ++YYCURSOR; #line 715 "ext/standard/var_unserializer.re" { if (!var_hash) return 0; return object_common2(UNSERIALIZE_PASSTHRU, object_common1(UNSERIALIZE_PASSTHRU, ZEND_STANDARD_CLASS_DEF_PTR)); } #line 837 "ext/standard/var_unserializer.c" yy32: yych = *++YYCURSOR; if (yych == '+') goto yy33; if (yych <= '/') goto yy18; if (yych <= '9') goto yy34; goto yy18; yy33: yych = *++YYCURSOR; if (yych <= '/') goto yy18; if (yych >= ':') goto yy18; yy34: ++YYCURSOR; if ((YYLIMIT - YYCURSOR) < 2) YYFILL(2); yych = *YYCURSOR; if (yych <= '/') goto yy18; if (yych <= '9') goto yy34; if (yych >= ';') goto yy18; yych = *++YYCURSOR; if (yych != '{') goto yy18; ++YYCURSOR; #line 691 "ext/standard/var_unserializer.re" { zend_long elements = parse_iv(start + 2); /* use iv() not uiv() in order to check data range */ *p = YYCURSOR; if (!var_hash) return 0; if (elements < 0) { return 0; } array_init_size(rval, elements); //??? we can't convert from packed to hash during unserialization, because //??? reference to some zvals might be keept in var_hash (to support references) if (elements) { zend_hash_real_init(Z_ARRVAL_P(rval), 0); } if (!process_nested_data(UNSERIALIZE_PASSTHRU, Z_ARRVAL_P(rval), elements, 0)) { return 0; } return finish_nested_data(UNSERIALIZE_PASSTHRU); } #line 882 "ext/standard/var_unserializer.c" yy39: yych = *++YYCURSOR; if (yych == '+') goto yy40; if (yych <= '/') goto yy18; if (yych <= '9') goto yy41; goto yy18; yy40: yych = *++YYCURSOR; if (yych <= '/') goto yy18; if (yych >= ':') goto yy18; yy41: ++YYCURSOR; if ((YYLIMIT - YYCURSOR) < 2) YYFILL(2); yych = *YYCURSOR; if (yych <= '/') goto yy18; if (yych <= '9') goto yy41; if (yych >= ';') goto yy18; yych = *++YYCURSOR; if (yych != '"') goto yy18; ++YYCURSOR; #line 663 "ext/standard/var_unserializer.re" { size_t len, maxlen; zend_string *str; len = parse_uiv(start + 2); maxlen = max - YYCURSOR; if (maxlen < len) { *p = start + 2; return 0; } if ((str = unserialize_str(&YYCURSOR, len, maxlen)) == NULL) { return 0; } if (*(YYCURSOR) != '"') { zend_string_free(str); *p = YYCURSOR; return 0; } YYCURSOR += 2; *p = YYCURSOR; ZVAL_STR(rval, str); return 1; } #line 931 "ext/standard/var_unserializer.c" yy46: yych = *++YYCURSOR; if (yych == '+') goto yy47; if (yych <= '/') goto yy18; if (yych <= '9') goto yy48; goto yy18; yy47: yych = *++YYCURSOR; if (yych <= '/') goto yy18; if (yych >= ':') goto yy18; yy48: ++YYCURSOR; if ((YYLIMIT - YYCURSOR) < 2) YYFILL(2); yych = *YYCURSOR; if (yych <= '/') goto yy18; if (yych <= '9') goto yy48; if (yych >= ';') goto yy18; yych = *++YYCURSOR; if (yych != '"') goto yy18; ++YYCURSOR; #line 636 "ext/standard/var_unserializer.re" { size_t len, maxlen; char *str; len = parse_uiv(start + 2); maxlen = max - YYCURSOR; if (maxlen < len) { *p = start + 2; return 0; } str = (char*)YYCURSOR; YYCURSOR += len; if (*(YYCURSOR) != '"') { *p = YYCURSOR; return 0; } YYCURSOR += 2; *p = YYCURSOR; ZVAL_STRINGL(rval, str, len); return 1; } #line 979 "ext/standard/var_unserializer.c" yy53: yych = *++YYCURSOR; if (yych <= '/') { if (yych <= ',') { if (yych == '+') goto yy57; goto yy18; } else { if (yych <= '-') goto yy55; if (yych <= '.') goto yy60; goto yy18; } } else { if (yych <= 'I') { if (yych <= '9') goto yy58; if (yych <= 'H') goto yy18; goto yy56; } else { if (yych != 'N') goto yy18; } } yych = *++YYCURSOR; if (yych == 'A') goto yy76; goto yy18; yy55: yych = *++YYCURSOR; if (yych <= '/') { if (yych == '.') goto yy60; goto yy18; } else { if (yych <= '9') goto yy58; if (yych != 'I') goto yy18; } yy56: yych = *++YYCURSOR; if (yych == 'N') goto yy72; goto yy18; yy57: yych = *++YYCURSOR; if (yych == '.') goto yy60; if (yych <= '/') goto yy18; if (yych >= ':') goto yy18; yy58: ++YYCURSOR; if ((YYLIMIT - YYCURSOR) < 4) YYFILL(4); yych = *YYCURSOR; if (yych <= ':') { if (yych <= '.') { if (yych <= '-') goto yy18; goto yy70; } else { if (yych <= '/') goto yy18; if (yych <= '9') goto yy58; goto yy18; } } else { if (yych <= 'E') { if (yych <= ';') goto yy63; if (yych <= 'D') goto yy18; goto yy65; } else { if (yych == 'e') goto yy65; goto yy18; } } yy60: yych = *++YYCURSOR; if (yych <= '/') goto yy18; if (yych >= ':') goto yy18; yy61: ++YYCURSOR; if ((YYLIMIT - YYCURSOR) < 4) YYFILL(4); yych = *YYCURSOR; if (yych <= ';') { if (yych <= '/') goto yy18; if (yych <= '9') goto yy61; if (yych <= ':') goto yy18; } else { if (yych <= 'E') { if (yych <= 'D') goto yy18; goto yy65; } else { if (yych == 'e') goto yy65; goto yy18; } } yy63: ++YYCURSOR; #line 627 "ext/standard/var_unserializer.re" { #if SIZEOF_ZEND_LONG == 4 use_double: #endif *p = YYCURSOR; ZVAL_DOUBLE(rval, zend_strtod((const char *)start + 2, NULL)); return 1; } #line 1076 "ext/standard/var_unserializer.c" yy65: yych = *++YYCURSOR; if (yych <= ',') { if (yych != '+') goto yy18; } else { if (yych <= '-') goto yy66; if (yych <= '/') goto yy18; if (yych <= '9') goto yy67; goto yy18; } yy66: yych = *++YYCURSOR; if (yych <= ',') { if (yych == '+') goto yy69; goto yy18; } else { if (yych <= '-') goto yy69; if (yych <= '/') goto yy18; if (yych >= ':') goto yy18; } yy67: ++YYCURSOR; if (YYLIMIT <= YYCURSOR) YYFILL(1); yych = *YYCURSOR; if (yych <= '/') goto yy18; if (yych <= '9') goto yy67; if (yych == ';') goto yy63; goto yy18; yy69: yych = *++YYCURSOR; if (yych <= '/') goto yy18; if (yych <= '9') goto yy67; goto yy18; yy70: ++YYCURSOR; if ((YYLIMIT - YYCURSOR) < 4) YYFILL(4); yych = *YYCURSOR; if (yych <= ';') { if (yych <= '/') goto yy18; if (yych <= '9') goto yy70; if (yych <= ':') goto yy18; goto yy63; } else { if (yych <= 'E') { if (yych <= 'D') goto yy18; goto yy65; } else { if (yych == 'e') goto yy65; goto yy18; } } yy72: yych = *++YYCURSOR; if (yych != 'F') goto yy18; yy73: yych = *++YYCURSOR; if (yych != ';') goto yy18; ++YYCURSOR; #line 611 "ext/standard/var_unserializer.re" { *p = YYCURSOR; if (!strncmp((char*)start + 2, "NAN", 3)) { ZVAL_DOUBLE(rval, php_get_nan()); } else if (!strncmp((char*)start + 2, "INF", 3)) { ZVAL_DOUBLE(rval, php_get_inf()); } else if (!strncmp((char*)start + 2, "-INF", 4)) { ZVAL_DOUBLE(rval, -php_get_inf()); } else { ZVAL_NULL(rval); } return 1; } #line 1151 "ext/standard/var_unserializer.c" yy76: yych = *++YYCURSOR; if (yych == 'N') goto yy73; goto yy18; yy77: yych = *++YYCURSOR; if (yych <= ',') { if (yych != '+') goto yy18; } else { if (yych <= '-') goto yy78; if (yych <= '/') goto yy18; if (yych <= '9') goto yy79; goto yy18; } yy78: yych = *++YYCURSOR; if (yych <= '/') goto yy18; if (yych >= ':') goto yy18; yy79: ++YYCURSOR; if (YYLIMIT <= YYCURSOR) YYFILL(1); yych = *YYCURSOR; if (yych <= '/') goto yy18; if (yych <= '9') goto yy79; if (yych != ';') goto yy18; ++YYCURSOR; #line 585 "ext/standard/var_unserializer.re" { #if SIZEOF_ZEND_LONG == 4 int digits = YYCURSOR - start - 3; if (start[2] == '-' || start[2] == '+') { digits--; } /* Use double for large zend_long values that were serialized on a 64-bit system */ if (digits >= MAX_LENGTH_OF_LONG - 1) { if (digits == MAX_LENGTH_OF_LONG - 1) { int cmp = strncmp((char*)YYCURSOR - MAX_LENGTH_OF_LONG, long_min_digits, MAX_LENGTH_OF_LONG - 1); if (!(cmp < 0 || (cmp == 0 && start[2] == '-'))) { goto use_double; } } else { goto use_double; } } #endif *p = YYCURSOR; ZVAL_LONG(rval, parse_iv(start + 2)); return 1; } #line 1204 "ext/standard/var_unserializer.c" yy83: yych = *++YYCURSOR; if (yych <= '/') goto yy18; if (yych >= '2') goto yy18; yych = *++YYCURSOR; if (yych != ';') goto yy18; ++YYCURSOR; #line 579 "ext/standard/var_unserializer.re" { *p = YYCURSOR; ZVAL_BOOL(rval, parse_iv(start + 2)); return 1; } #line 1218 "ext/standard/var_unserializer.c" yy87: ++YYCURSOR; #line 573 "ext/standard/var_unserializer.re" { *p = YYCURSOR; ZVAL_NULL(rval); return 1; } #line 1227 "ext/standard/var_unserializer.c" yy89: yych = *++YYCURSOR; if (yych <= ',') { if (yych != '+') goto yy18; } else { if (yych <= '-') goto yy90; if (yych <= '/') goto yy18; if (yych <= '9') goto yy91; goto yy18; } yy90: yych = *++YYCURSOR; if (yych <= '/') goto yy18; if (yych >= ':') goto yy18; yy91: ++YYCURSOR; if (YYLIMIT <= YYCURSOR) YYFILL(1); yych = *YYCURSOR; if (yych <= '/') goto yy18; if (yych <= '9') goto yy91; if (yych != ';') goto yy18; ++YYCURSOR; #line 548 "ext/standard/var_unserializer.re" { zend_long id; *p = YYCURSOR; if (!var_hash) return 0; id = parse_iv(start + 2) - 1; if (id == -1 || (rval_ref = var_access(var_hash, id)) == NULL) { return 0; } if (rval_ref == rval) { return 0; } if (Z_ISUNDEF_P(rval_ref) || (Z_ISREF_P(rval_ref) && Z_ISUNDEF_P(Z_REFVAL_P(rval_ref)))) { ZVAL_UNDEF(rval); return 1; } ZVAL_COPY(rval, rval_ref); return 1; } #line 1275 "ext/standard/var_unserializer.c" yy95: yych = *++YYCURSOR; if (yych <= ',') { if (yych != '+') goto yy18; } else { if (yych <= '-') goto yy96; if (yych <= '/') goto yy18; if (yych <= '9') goto yy97; goto yy18; } yy96: yych = *++YYCURSOR; if (yych <= '/') goto yy18; if (yych >= ':') goto yy18; yy97: ++YYCURSOR; if (YYLIMIT <= YYCURSOR) YYFILL(1); yych = *YYCURSOR; if (yych <= '/') goto yy18; if (yych <= '9') goto yy97; if (yych != ';') goto yy18; ++YYCURSOR; #line 522 "ext/standard/var_unserializer.re" { zend_long id; *p = YYCURSOR; if (!var_hash) return 0; id = parse_iv(start + 2) - 1; if (id == -1 || (rval_ref = var_access(var_hash, id)) == NULL) { return 0; } zval_ptr_dtor(rval); if (Z_ISUNDEF_P(rval_ref) || (Z_ISREF_P(rval_ref) && Z_ISUNDEF_P(Z_REFVAL_P(rval_ref)))) { ZVAL_UNDEF(rval); return 1; } if (Z_ISREF_P(rval_ref)) { ZVAL_COPY(rval, rval_ref); } else { ZVAL_NEW_REF(rval_ref, rval_ref); ZVAL_COPY(rval, rval_ref); } return 1; } #line 1324 "ext/standard/var_unserializer.c" } #line 875 "ext/standard/var_unserializer.re" return 0; }
int msgpack_convert_object(zval *return_value, zval *object, zval **value) { zend_class_entry *ce, **pce; HashTable *properties = NULL; HashPosition prop_pos; TSRMLS_FETCH(); switch (Z_TYPE_P(object)) { case IS_STRING: if (zend_lookup_class( Z_STRVAL_P(object), Z_STRLEN_P(object), &pce TSRMLS_CC) != SUCCESS) { MSGPACK_ERROR("[msgpack] (%s) Class '%s' not found", __FUNCTION__, Z_STRVAL_P(object)); return FAILURE; } ce = *pce; break; case IS_OBJECT: ce = zend_get_class_entry(object TSRMLS_CC); break; default: MSGPACK_ERROR("[msgpack] (%s) Object type is unsupported", __FUNCTION__); return FAILURE; } if (Z_TYPE_PP(value) == IS_OBJECT) { zend_class_entry *vce; vce = zend_get_class_entry(*value TSRMLS_CC); if (strcmp(ce->name, vce->name) == 0) { *return_value = **value; zval_copy_ctor(return_value); zval_ptr_dtor(value); return SUCCESS; } } object_init_ex(return_value, ce); properties = Z_OBJ_HT_P(return_value)->get_properties( return_value TSRMLS_CC); if (HASH_OF(object)) { properties = HASH_OF(object); } zend_hash_internal_pointer_reset_ex(properties, &prop_pos); switch (Z_TYPE_PP(value)) { case IS_ARRAY: { char *key; uint key_len; int key_type; ulong key_index; zval **data; HashPosition pos; HashTable *ht, *ret; HashTable *var = NULL; int num; ht = HASH_OF(*value); ret = HASH_OF(return_value); num = zend_hash_num_elements(ht); if (num <= 0) { zval_ptr_dtor(value); break; } ALLOC_HASHTABLE(var); zend_hash_init(var, num, NULL, NULL, 0); /* string */ if (ht->nNumOfElements != ht->nNextFreeElement) { zend_hash_internal_pointer_reset_ex(ht, &pos); for (;; zend_hash_move_forward_ex(ht, &pos)) { key_type = zend_hash_get_current_key_ex( ht, &key, &key_len, &key_index, 0, &pos); if (key_type == HASH_KEY_NON_EXISTANT) { break; } if (zend_hash_get_current_data_ex( ht, (void *)&data, &pos) != SUCCESS) { continue; } if (key_type == HASH_KEY_IS_STRING) { zval *val; MSGPACK_CONVERT_COPY_ZVAL(val, data); if (msgpack_convert_string_to_properties( return_value, key, key_len, val, var) != SUCCESS) { zval_ptr_dtor(&val); MSGPACK_WARNING( "[msgpack] (%s) " "illegal offset type, skip this decoding", __FUNCTION__); } } } } /* index */ zend_hash_internal_pointer_reset_ex(ht, &pos); for (;; zend_hash_move_forward_ex(ht, &pos)) { key_type = zend_hash_get_current_key_ex( ht, &key, &key_len, &key_index, 0, &pos); if (key_type == HASH_KEY_NON_EXISTANT) { break; } if (zend_hash_get_current_data_ex( ht, (void *)&data, &pos) != SUCCESS) { continue; } switch (key_type) { case HASH_KEY_IS_LONG: { zval *val; MSGPACK_CONVERT_COPY_ZVAL(val, data); if (msgpack_convert_long_to_properties( ret, &properties, &prop_pos, key_index, val, var) != SUCCESS) { zval_ptr_dtor(&val); MSGPACK_WARNING( "[msgpack] (%s) " "illegal offset type, skip this decoding", __FUNCTION__); } break; } case HASH_KEY_IS_STRING: break; default: MSGPACK_WARNING( "[msgpack] (%s) key is not string nor array", __FUNCTION__); break; } } zend_hash_destroy(var); FREE_HASHTABLE(var); zval_ptr_dtor(value); break; } default: if (msgpack_convert_long_to_properties( HASH_OF(return_value), &properties, &prop_pos, 0, *value, NULL) != SUCCESS) { MSGPACK_WARNING( "[msgpack] (%s) illegal offset type, skip this decoding", __FUNCTION__); } break; } return SUCCESS; }