]> granicus.if.org Git - php/commitdiff
Back up fake_scope in zend_call_function
authorNikita Popov <nikita.ppv@gmail.com>
Tue, 9 Jun 2020 14:30:46 +0000 (16:30 +0200)
committerNikita Popov <nikita.ppv@gmail.com>
Tue, 9 Jun 2020 14:33:33 +0000 (16:33 +0200)
We regularly find new places where we forgot to reset fake_scope.
Instead of having to handle this for each caller of zend_call_function()
and similar APIs, handle it directly in zend_call_function().

Zend/zend.c
Zend/zend_execute_API.c
Zend/zend_object_handlers.c
Zend/zend_objects.c

index fd535325371ecc1b1f7ccc75b36ef826cfe135b9..b72184e7268474192809eab23d049636b7c4a8dc 100644 (file)
@@ -1271,7 +1271,6 @@ static ZEND_COLD void zend_error_impl(
        zend_class_entry *saved_class_entry;
        zend_stack loop_var_stack;
        zend_stack delayed_oplines_stack;
-       zend_class_entry *orig_fake_scope;
        int type = orig_type & E_ALL;
 
        /* Report about uncaught exception in case of fatal errors */
@@ -1357,9 +1356,6 @@ static ZEND_COLD void zend_error_impl(
                                CG(in_compilation) = 0;
                        }
 
-                       orig_fake_scope = EG(fake_scope);
-                       EG(fake_scope) = NULL;
-
                        if (call_user_function(CG(function_table), NULL, &orig_user_error_handler, &retval, 4, params) == SUCCESS) {
                                if (Z_TYPE(retval) != IS_UNDEF) {
                                        if (Z_TYPE(retval) == IS_FALSE) {
@@ -1372,8 +1368,6 @@ static ZEND_COLD void zend_error_impl(
                                zend_error_cb(orig_type, error_filename, error_lineno, message);
                        }
 
-                       EG(fake_scope) = orig_fake_scope;
-
                        if (in_compilation) {
                                CG(active_class_entry) = saved_class_entry;
                                RESTORE_STACK(loop_var_stack);
index c5626a0df30c9b2c0f0a25118d64fd9d2343657e..b650444d1c3943872bfeb16cb9c75c7ea25a593b 100644 (file)
@@ -646,6 +646,7 @@ int zend_call_function(zend_fcall_info *fci, zend_fcall_info_cache *fci_cache) /
        zend_function *func;
        uint32_t call_info;
        void *object_or_called_scope;
+       zend_class_entry *orig_fake_scope;
 
        ZVAL_UNDEF(fci->retval);
 
@@ -791,6 +792,8 @@ int zend_call_function(zend_fcall_info *fci, zend_fcall_info_cache *fci_cache) /
                ZEND_ADD_CALL_FLAG(call, call_info);
        }
 
+       orig_fake_scope = EG(fake_scope);
+       EG(fake_scope) = NULL;
        if (func->type == ZEND_USER_FUNCTION) {
                int call_via_handler = (func->common.fn_flags & ZEND_ACC_CALL_VIA_TRAMPOLINE) != 0;
                const zend_op *current_opline_before_exception = EG(opline_before_exception);
@@ -841,6 +844,7 @@ int zend_call_function(zend_fcall_info *fci, zend_fcall_info_cache *fci_cache) /
                        }
                }
        }
+       EG(fake_scope) = orig_fake_scope;
 
        zend_vm_stack_free_call_frame(call);
 
@@ -914,7 +918,6 @@ ZEND_API zend_class_entry *zend_lookup_class_ex(zend_string *name, zend_string *
        zend_string *lc_name;
        zend_fcall_info fcall_info;
        zend_fcall_info_cache fcall_cache;
-       zend_class_entry *orig_fake_scope;
 
        if (key) {
                lc_name = key;
@@ -1005,14 +1008,11 @@ ZEND_API zend_class_entry *zend_lookup_class_ex(zend_string *name, zend_string *
        fcall_cache.called_scope = NULL;
        fcall_cache.object = NULL;
 
-       orig_fake_scope = EG(fake_scope);
-       EG(fake_scope) = NULL;
        zend_exception_save();
        if ((zend_call_function(&fcall_info, &fcall_cache) == SUCCESS) && !EG(exception)) {
                ce = zend_hash_find_ptr(EG(class_table), lc_name);
        }
        zend_exception_restore();
-       EG(fake_scope) = orig_fake_scope;
 
        zval_ptr_dtor(&args[0]);
        zval_ptr_dtor_str(&fcall_info.function_name);
index 05944bbbdf15fb2217453f7e59ed6088a157c1ec..e8d391ed041b85f33e1afc04de6bd62ca81a4b33 100644 (file)
@@ -177,58 +177,34 @@ ZEND_API HashTable *zend_std_get_debug_info(zend_object *object, int *is_temp) /
 
 static void zend_std_call_getter(zend_object *zobj, zend_string *prop_name, zval *retval) /* {{{ */
 {
-       zend_class_entry *orig_fake_scope = EG(fake_scope);
        zval member;
-
-       EG(fake_scope) = NULL;
-
        ZVAL_STR(&member, prop_name);
        zend_call_known_instance_method_with_1_params(zobj->ce->__get, zobj, retval, &member);
-
-       EG(fake_scope) = orig_fake_scope;
 }
 /* }}} */
 
 static void zend_std_call_setter(zend_object *zobj, zend_string *prop_name, zval *value) /* {{{ */
 {
-       zend_class_entry *orig_fake_scope = EG(fake_scope);
        zval args[2];
-
-       EG(fake_scope) = NULL;
-
        ZVAL_STR(&args[0], prop_name);
        ZVAL_COPY_VALUE(&args[1], value);
        zend_call_known_instance_method(zobj->ce->__set, zobj, NULL, 2, args);
-
-       EG(fake_scope) = orig_fake_scope;
 }
 /* }}} */
 
 static void zend_std_call_unsetter(zend_object *zobj, zend_string *prop_name) /* {{{ */
 {
-       zend_class_entry *orig_fake_scope = EG(fake_scope);
        zval member;
-
-       EG(fake_scope) = NULL;
-
        ZVAL_STR(&member, prop_name);
        zend_call_known_instance_method_with_1_params(zobj->ce->__unset, zobj, NULL, &member);
-
-       EG(fake_scope) = orig_fake_scope;
 }
 /* }}} */
 
 static void zend_std_call_issetter(zend_object *zobj, zend_string *prop_name, zval *retval) /* {{{ */
 {
-       zend_class_entry *orig_fake_scope = EG(fake_scope);
        zval member;
-
-       EG(fake_scope) = NULL;
-
        ZVAL_STR(&member, prop_name);
        zend_call_known_instance_method_with_1_params(zobj->ce->__isset, zobj, retval, &member);
-
-       EG(fake_scope) = orig_fake_scope;
 }
 /* }}} */
 
@@ -1711,12 +1687,9 @@ ZEND_API int zend_std_cast_object_tostring(zend_object *readobj, zval *writeobj,
                        zend_class_entry *ce = readobj->ce;
                        if (ce->__tostring) {
                                zval retval;
-                               zend_class_entry *fake_scope = EG(fake_scope);
-                               EG(fake_scope) = NULL;
                                GC_ADDREF(readobj);
                                zend_call_known_instance_method_with_0_params(ce->__tostring, readobj, &retval);
                                zend_object_release(readobj);
-                               EG(fake_scope) = fake_scope;
                                if (EXPECTED(Z_TYPE(retval) == IS_STRING)) {
                                        ZVAL_COPY_VALUE(writeobj, &retval);
                                        return SUCCESS;
index f25983ece3fbf2e7b2d3177f72a7e112625d6b3c..0e873f06812933de86921050446278f47bf4e707 100644 (file)
@@ -97,7 +97,6 @@ ZEND_API void zend_objects_destroy_object(zend_object *object)
 
        if (destructor) {
                zend_object *old_exception;
-               zend_class_entry *orig_fake_scope;
 
                if (destructor->op_array.fn_flags & (ZEND_ACC_PRIVATE|ZEND_ACC_PROTECTED)) {
                        if (destructor->op_array.fn_flags & ZEND_ACC_PRIVATE) {
@@ -156,8 +155,6 @@ ZEND_API void zend_objects_destroy_object(zend_object *object)
                                EG(exception) = NULL;
                        }
                }
-               orig_fake_scope = EG(fake_scope);
-               EG(fake_scope) = NULL;
 
                zend_call_known_instance_method_with_0_params(destructor, object, NULL);
 
@@ -169,7 +166,6 @@ ZEND_API void zend_objects_destroy_object(zend_object *object)
                        }
                }
                OBJ_RELEASE(object);
-               EG(fake_scope) = orig_fake_scope;
        }
 }