From: Stanislav Malyshev Date: Mon, 1 Sep 2014 22:08:02 +0000 (-0700) Subject: Reintroduce fix from pull #770 in a PHP 7 way X-Git-Tag: PRE_PHP7_REMOVALS~161 X-Git-Url: https://granicus.if.org/sourcecode?a=commitdiff_plain;h=d5b0606a6246eee293e7ac937fcb5fdc231f61dd;p=php Reintroduce fix from pull #770 in a PHP 7 way --- diff --git a/Zend/zend.c b/Zend/zend.c index a918bb0b9e..334a8df29b 100644 --- a/Zend/zend.c +++ b/Zend/zend.c @@ -812,10 +812,35 @@ void zend_shutdown(TSRMLS_D) /* {{{ */ zend_shutdown_timeout_thread(); #endif zend_destroy_rsrc_list(&EG(persistent_list) TSRMLS_CC); + if (EG(active)) + { + /* + * The order of destruction is important here. + * See bugs #65463 and 66036. + */ + zend_function *func; + zend_class_entry *ce; + + ZEND_HASH_REVERSE_FOREACH_PTR(GLOBAL_FUNCTION_TABLE, func) { + if (func->type == ZEND_USER_FUNCTION) { + zend_cleanup_op_array_data((zend_op_array *) func); + } + } ZEND_HASH_FOREACH_END(); + ZEND_HASH_REVERSE_FOREACH_PTR(GLOBAL_CLASS_TABLE, ce) { + if (ce->type == ZEND_USER_CLASS) { + zend_cleanup_user_class_data(ce TSRMLS_CC); + } else { + break; + } + } ZEND_HASH_FOREACH_END(); + zend_cleanup_internal_classes(TSRMLS_C); + zend_hash_reverse_apply(GLOBAL_FUNCTION_TABLE, (apply_func_t) clean_non_persistent_function_full TSRMLS_CC); + zend_hash_reverse_apply(GLOBAL_CLASS_TABLE, (apply_func_t) clean_non_persistent_class_full TSRMLS_CC); + } zend_destroy_modules(); - virtual_cwd_deactivate(TSRMLS_C); - virtual_cwd_shutdown(); + virtual_cwd_deactivate(TSRMLS_C); + virtual_cwd_shutdown(); zend_hash_destroy(GLOBAL_FUNCTION_TABLE); zend_hash_destroy(GLOBAL_CLASS_TABLE); diff --git a/Zend/zend_compile.h b/Zend/zend_compile.h index 71a622f417..89bb2b8457 100644 --- a/Zend/zend_compile.h +++ b/Zend/zend_compile.h @@ -491,6 +491,8 @@ ZEND_API void zend_cleanup_user_class_data(zend_class_entry *ce TSRMLS_DC); ZEND_API void zend_cleanup_internal_class_data(zend_class_entry *ce TSRMLS_DC); ZEND_API void zend_cleanup_internal_classes(TSRMLS_D); ZEND_API void zend_cleanup_op_array_data(zend_op_array *op_array); +ZEND_API int clean_non_persistent_function_full(zval *zv TSRMLS_DC); +ZEND_API int clean_non_persistent_class_full(zval *zv TSRMLS_DC); ZEND_API void destroy_zend_function(zend_function *function TSRMLS_DC); ZEND_API void zend_function_dtor(zval *zv); diff --git a/Zend/zend_execute_API.c b/Zend/zend_execute_API.c index 5984e2dc82..7842ecfb91 100644 --- a/Zend/zend_execute_API.c +++ b/Zend/zend_execute_API.c @@ -110,7 +110,7 @@ static int clean_non_persistent_function(zval *zv TSRMLS_DC) /* {{{ */ } /* }}} */ -static int clean_non_persistent_function_full(zval *zv TSRMLS_DC) /* {{{ */ +ZEND_API int clean_non_persistent_function_full(zval *zv TSRMLS_DC) /* {{{ */ { zend_function *function = Z_PTR_P(zv); return (function->type == ZEND_INTERNAL_FUNCTION) ? ZEND_HASH_APPLY_KEEP : ZEND_HASH_APPLY_REMOVE; @@ -124,7 +124,7 @@ static int clean_non_persistent_class(zval *zv TSRMLS_DC) /* {{{ */ } /* }}} */ -static int clean_non_persistent_class_full(zval *zv TSRMLS_DC) /* {{{ */ +ZEND_API int clean_non_persistent_class_full(zval *zv TSRMLS_DC) /* {{{ */ { zend_class_entry *ce = Z_PTR_P(zv); return (ce->type == ZEND_INTERNAL_CLASS) ? ZEND_HASH_APPLY_KEEP : ZEND_HASH_APPLY_REMOVE;