PHP  
 PHP: Test and Code Coverage Analysis
downloads | QA | documentation | faq | getting help | mailing lists | reporting bugs | php.net sites | links | my php.net 
 

LCOV - code coverage report
Current view: top level - Zend - zend_builtin_functions.c (source / functions) Hit Total Coverage
Test: PHP Code Coverage Lines: 992 1086 91.3 %
Date: 2015-04-14 Functions: 67 67 100.0 %
Legend: Lines: hit not hit

          Line data    Source code
       1             : /*
       2             :    +----------------------------------------------------------------------+
       3             :    | Zend Engine                                                          |
       4             :    +----------------------------------------------------------------------+
       5             :    | Copyright (c) 1998-2015 Zend Technologies Ltd. (http://www.zend.com) |
       6             :    +----------------------------------------------------------------------+
       7             :    | This source file is subject to version 2.00 of the Zend license,     |
       8             :    | that is bundled with this package in the file LICENSE, and is        |
       9             :    | available through the world-wide-web at the following url:           |
      10             :    | http://www.zend.com/license/2_00.txt.                                |
      11             :    | If you did not receive a copy of the Zend license and are unable to  |
      12             :    | obtain it through the world-wide-web, please send a note to          |
      13             :    | license@zend.com so we can mail you a copy immediately.              |
      14             :    +----------------------------------------------------------------------+
      15             :    | Authors: Andi Gutmans <andi@zend.com>                                |
      16             :    |          Zeev Suraski <zeev@zend.com>                                |
      17             :    +----------------------------------------------------------------------+
      18             : */
      19             : 
      20             : /* $Id$ */
      21             : 
      22             : #include "zend.h"
      23             : #include "zend_API.h"
      24             : #include "zend_builtin_functions.h"
      25             : #include "zend_constants.h"
      26             : #include "zend_ini.h"
      27             : #include "zend_exceptions.h"
      28             : #include "zend_extensions.h"
      29             : #include "zend_closures.h"
      30             : 
      31             : #undef ZEND_TEST_EXCEPTIONS
      32             : 
      33             : static ZEND_FUNCTION(zend_version);
      34             : static ZEND_FUNCTION(func_num_args);
      35             : static ZEND_FUNCTION(func_get_arg);
      36             : static ZEND_FUNCTION(func_get_args);
      37             : static ZEND_FUNCTION(strlen);
      38             : static ZEND_FUNCTION(strcmp);
      39             : static ZEND_FUNCTION(strncmp);
      40             : static ZEND_FUNCTION(strcasecmp);
      41             : static ZEND_FUNCTION(strncasecmp);
      42             : static ZEND_FUNCTION(each);
      43             : static ZEND_FUNCTION(error_reporting);
      44             : static ZEND_FUNCTION(define);
      45             : static ZEND_FUNCTION(defined);
      46             : static ZEND_FUNCTION(get_class);
      47             : static ZEND_FUNCTION(get_called_class);
      48             : static ZEND_FUNCTION(get_parent_class);
      49             : static ZEND_FUNCTION(method_exists);
      50             : static ZEND_FUNCTION(property_exists);
      51             : static ZEND_FUNCTION(class_exists);
      52             : static ZEND_FUNCTION(interface_exists);
      53             : static ZEND_FUNCTION(trait_exists);
      54             : static ZEND_FUNCTION(function_exists);
      55             : static ZEND_FUNCTION(class_alias);
      56             : #if ZEND_DEBUG
      57             : static ZEND_FUNCTION(leak);
      58             : static ZEND_FUNCTION(leak_variable);
      59             : #ifdef ZEND_TEST_EXCEPTIONS
      60             : static ZEND_FUNCTION(crash);
      61             : #endif
      62             : #endif
      63             : static ZEND_FUNCTION(get_included_files);
      64             : static ZEND_FUNCTION(is_subclass_of);
      65             : static ZEND_FUNCTION(is_a);
      66             : static ZEND_FUNCTION(get_class_vars);
      67             : static ZEND_FUNCTION(get_object_vars);
      68             : static ZEND_FUNCTION(get_class_methods);
      69             : static ZEND_FUNCTION(trigger_error);
      70             : static ZEND_FUNCTION(set_error_handler);
      71             : static ZEND_FUNCTION(restore_error_handler);
      72             : static ZEND_FUNCTION(set_exception_handler);
      73             : static ZEND_FUNCTION(restore_exception_handler);
      74             : static ZEND_FUNCTION(get_declared_classes);
      75             : static ZEND_FUNCTION(get_declared_traits);
      76             : static ZEND_FUNCTION(get_declared_interfaces);
      77             : static ZEND_FUNCTION(get_defined_functions);
      78             : static ZEND_FUNCTION(get_defined_vars);
      79             : static ZEND_FUNCTION(create_function);
      80             : static ZEND_FUNCTION(get_resource_type);
      81             : static ZEND_FUNCTION(get_resources);
      82             : static ZEND_FUNCTION(get_loaded_extensions);
      83             : static ZEND_FUNCTION(extension_loaded);
      84             : static ZEND_FUNCTION(get_extension_funcs);
      85             : static ZEND_FUNCTION(get_defined_constants);
      86             : static ZEND_FUNCTION(debug_backtrace);
      87             : static ZEND_FUNCTION(debug_print_backtrace);
      88             : #if ZEND_DEBUG
      89             : static ZEND_FUNCTION(zend_test_func);
      90             : static ZEND_FUNCTION(zend_test_func2);
      91             : #ifdef ZTS
      92             : static ZEND_FUNCTION(zend_thread_id);
      93             : #endif
      94             : #endif
      95             : static ZEND_FUNCTION(gc_collect_cycles);
      96             : static ZEND_FUNCTION(gc_enabled);
      97             : static ZEND_FUNCTION(gc_enable);
      98             : static ZEND_FUNCTION(gc_disable);
      99             : 
     100             : /* {{{ arginfo */
     101             : ZEND_BEGIN_ARG_INFO(arginfo_zend__void, 0)
     102             : ZEND_END_ARG_INFO()
     103             : 
     104             : ZEND_BEGIN_ARG_INFO_EX(arginfo_func_get_arg, 0, 0, 1)
     105             :         ZEND_ARG_INFO(0, arg_num)
     106             : ZEND_END_ARG_INFO()
     107             : 
     108             : ZEND_BEGIN_ARG_INFO_EX(arginfo_strlen, 0, 0, 1)
     109             :         ZEND_ARG_INFO(0, str)
     110             : ZEND_END_ARG_INFO()
     111             : 
     112             : ZEND_BEGIN_ARG_INFO_EX(arginfo_strcmp, 0, 0, 2)
     113             :         ZEND_ARG_INFO(0, str1)
     114             :         ZEND_ARG_INFO(0, str2)
     115             : ZEND_END_ARG_INFO()
     116             : 
     117             : ZEND_BEGIN_ARG_INFO_EX(arginfo_strncmp, 0, 0, 3)
     118             :         ZEND_ARG_INFO(0, str1)
     119             :         ZEND_ARG_INFO(0, str2)
     120             :         ZEND_ARG_INFO(0, len)
     121             : ZEND_END_ARG_INFO()
     122             : 
     123             : ZEND_BEGIN_ARG_INFO_EX(arginfo_each, 0, 0, 1)
     124             :         ZEND_ARG_INFO(1, arr)
     125             : ZEND_END_ARG_INFO()
     126             : 
     127             : ZEND_BEGIN_ARG_INFO_EX(arginfo_error_reporting, 0, 0, 0)
     128             :         ZEND_ARG_INFO(0, new_error_level)
     129             : ZEND_END_ARG_INFO()
     130             : 
     131             : ZEND_BEGIN_ARG_INFO_EX(arginfo_define, 0, 0, 3)
     132             :         ZEND_ARG_INFO(0, constant_name)
     133             :         ZEND_ARG_INFO(0, value)
     134             :         ZEND_ARG_INFO(0, case_insensitive)
     135             : ZEND_END_ARG_INFO()
     136             : 
     137             : ZEND_BEGIN_ARG_INFO_EX(arginfo_defined, 0, 0, 1)
     138             :         ZEND_ARG_INFO(0, constant_name)
     139             : ZEND_END_ARG_INFO()
     140             : 
     141             : ZEND_BEGIN_ARG_INFO_EX(arginfo_get_class, 0, 0, 0)
     142             :         ZEND_ARG_INFO(0, object)
     143             : ZEND_END_ARG_INFO()
     144             : 
     145             : ZEND_BEGIN_ARG_INFO_EX(arginfo_is_subclass_of, 0, 0, 2)
     146             :         ZEND_ARG_INFO(0, object)
     147             :         ZEND_ARG_INFO(0, class_name)
     148             :         ZEND_ARG_INFO(0, allow_string)
     149             : ZEND_END_ARG_INFO()
     150             : 
     151             : ZEND_BEGIN_ARG_INFO_EX(arginfo_get_class_vars, 0, 0, 1)
     152             :         ZEND_ARG_INFO(0, class_name)
     153             : ZEND_END_ARG_INFO()
     154             : 
     155             : ZEND_BEGIN_ARG_INFO_EX(arginfo_get_object_vars, 0, 0, 1)
     156             :         ZEND_ARG_INFO(0, obj)
     157             : ZEND_END_ARG_INFO()
     158             : 
     159             : ZEND_BEGIN_ARG_INFO_EX(arginfo_get_class_methods, 0, 0, 1)
     160             :         ZEND_ARG_INFO(0, class)
     161             : ZEND_END_ARG_INFO()
     162             : 
     163             : ZEND_BEGIN_ARG_INFO_EX(arginfo_method_exists, 0, 0, 2)
     164             :         ZEND_ARG_INFO(0, object)
     165             :         ZEND_ARG_INFO(0, method)
     166             : ZEND_END_ARG_INFO()
     167             : 
     168             : ZEND_BEGIN_ARG_INFO_EX(arginfo_property_exists, 0, 0, 2)
     169             :         ZEND_ARG_INFO(0, object_or_class)
     170             :         ZEND_ARG_INFO(0, property_name)
     171             : ZEND_END_ARG_INFO()
     172             : 
     173             : ZEND_BEGIN_ARG_INFO_EX(arginfo_class_exists, 0, 0, 1)
     174             :         ZEND_ARG_INFO(0, classname)
     175             :         ZEND_ARG_INFO(0, autoload)
     176             : ZEND_END_ARG_INFO()
     177             : 
     178             : ZEND_BEGIN_ARG_INFO_EX(arginfo_trait_exists, 0, 0, 1)
     179             :         ZEND_ARG_INFO(0, traitname)
     180             :         ZEND_ARG_INFO(0, autoload)
     181             : ZEND_END_ARG_INFO()
     182             : 
     183             : ZEND_BEGIN_ARG_INFO_EX(arginfo_function_exists, 0, 0, 1)
     184             :         ZEND_ARG_INFO(0, function_name)
     185             : ZEND_END_ARG_INFO()
     186             : 
     187             : ZEND_BEGIN_ARG_INFO_EX(arginfo_class_alias, 0, 0, 2)
     188             :         ZEND_ARG_INFO(0, user_class_name)
     189             :         ZEND_ARG_INFO(0, alias_name)
     190             :         ZEND_ARG_INFO(0, autoload)
     191             : ZEND_END_ARG_INFO()
     192             : 
     193             : #if ZEND_DEBUG
     194             : ZEND_BEGIN_ARG_INFO_EX(arginfo_leak_variable, 0, 0, 1)
     195             :         ZEND_ARG_INFO(0, variable)
     196             :         ZEND_ARG_INFO(0, leak_data)
     197             : ZEND_END_ARG_INFO()
     198             : #endif
     199             : 
     200             : ZEND_BEGIN_ARG_INFO_EX(arginfo_trigger_error, 0, 0, 1)
     201             :         ZEND_ARG_INFO(0, message)
     202             :         ZEND_ARG_INFO(0, error_type)
     203             : ZEND_END_ARG_INFO()
     204             : 
     205             : ZEND_BEGIN_ARG_INFO_EX(arginfo_set_error_handler, 0, 0, 1)
     206             :         ZEND_ARG_INFO(0, error_handler)
     207             :         ZEND_ARG_INFO(0, error_types)
     208             : ZEND_END_ARG_INFO()
     209             : 
     210             : ZEND_BEGIN_ARG_INFO_EX(arginfo_set_exception_handler, 0, 0, 1)
     211             :         ZEND_ARG_INFO(0, exception_handler)
     212             : ZEND_END_ARG_INFO()
     213             : 
     214             : ZEND_BEGIN_ARG_INFO_EX(arginfo_create_function, 0, 0, 2)
     215             :         ZEND_ARG_INFO(0, args)
     216             :         ZEND_ARG_INFO(0, code)
     217             : ZEND_END_ARG_INFO()
     218             : 
     219             : ZEND_BEGIN_ARG_INFO_EX(arginfo_get_resource_type, 0, 0, 1)
     220             :         ZEND_ARG_INFO(0, res)
     221             : ZEND_END_ARG_INFO()
     222             : 
     223             : ZEND_BEGIN_ARG_INFO_EX(arginfo_get_resources, 0, 0, 0)
     224             :         ZEND_ARG_INFO(0, type)
     225             : ZEND_END_ARG_INFO()
     226             : 
     227             : ZEND_BEGIN_ARG_INFO_EX(arginfo_get_loaded_extensions, 0, 0, 0)
     228             :         ZEND_ARG_INFO(0, zend_extensions)
     229             : ZEND_END_ARG_INFO()
     230             : 
     231             : ZEND_BEGIN_ARG_INFO_EX(arginfo_get_defined_constants, 0, 0, 0)
     232             :         ZEND_ARG_INFO(0, categorize)
     233             : ZEND_END_ARG_INFO()
     234             : 
     235             : ZEND_BEGIN_ARG_INFO_EX(arginfo_debug_backtrace, 0, 0, 0)
     236             :         ZEND_ARG_INFO(0, options)
     237             :         ZEND_ARG_INFO(0, limit)
     238             : ZEND_END_ARG_INFO()
     239             : 
     240             : ZEND_BEGIN_ARG_INFO_EX(arginfo_debug_print_backtrace, 0, 0, 0)
     241             :         ZEND_ARG_INFO(0, options)
     242             : ZEND_END_ARG_INFO()
     243             : 
     244             : ZEND_BEGIN_ARG_INFO_EX(arginfo_extension_loaded, 0, 0, 1)
     245             :         ZEND_ARG_INFO(0, extension_name)
     246             : ZEND_END_ARG_INFO()
     247             : 
     248             : #ifdef ZEND_DEBUG
     249             : ZEND_BEGIN_ARG_WITH_RETURN_TYPE_INFO(arginfo_zend_test_func, IS_ARRAY, NULL, 0)
     250             : ZEND_END_ARG_INFO()
     251             : ZEND_BEGIN_ARG_WITH_RETURN_TYPE_INFO(arginfo_zend_test_func2, IS_ARRAY, NULL, 1)
     252             : ZEND_END_ARG_INFO()
     253             : #endif
     254             : 
     255             : /* }}} */
     256             : 
     257             : static const zend_function_entry builtin_functions[] = { /* {{{ */
     258             :         ZEND_FE(zend_version,           arginfo_zend__void)
     259             :         ZEND_FE(func_num_args,          arginfo_zend__void)
     260             :         ZEND_FE(func_get_arg,           arginfo_func_get_arg)
     261             :         ZEND_FE(func_get_args,          arginfo_zend__void)
     262             :         ZEND_FE(strlen,                 arginfo_strlen)
     263             :         ZEND_FE(strcmp,                 arginfo_strcmp)
     264             :         ZEND_FE(strncmp,                arginfo_strncmp)
     265             :         ZEND_FE(strcasecmp,             arginfo_strcmp)
     266             :         ZEND_FE(strncasecmp,            arginfo_strncmp)
     267             :         ZEND_FE(each,                   arginfo_each)
     268             :         ZEND_FE(error_reporting,        arginfo_error_reporting)
     269             :         ZEND_FE(define,                 arginfo_define)
     270             :         ZEND_FE(defined,                arginfo_defined)
     271             :         ZEND_FE(get_class,              arginfo_get_class)
     272             :         ZEND_FE(get_called_class,       arginfo_zend__void)
     273             :         ZEND_FE(get_parent_class,       arginfo_get_class)
     274             :         ZEND_FE(method_exists,          arginfo_method_exists)
     275             :         ZEND_FE(property_exists,        arginfo_property_exists)
     276             :         ZEND_FE(class_exists,           arginfo_class_exists)
     277             :         ZEND_FE(interface_exists,       arginfo_class_exists)
     278             :         ZEND_FE(trait_exists,           arginfo_trait_exists)
     279             :         ZEND_FE(function_exists,        arginfo_function_exists)
     280             :         ZEND_FE(class_alias,            arginfo_class_alias)
     281             : #if ZEND_DEBUG
     282             :         ZEND_FE(leak,                           NULL)
     283             :         ZEND_FE(leak_variable,          arginfo_leak_variable)
     284             : #ifdef ZEND_TEST_EXCEPTIONS
     285             :         ZEND_FE(crash,                          NULL)
     286             : #endif
     287             : #endif
     288             :         ZEND_FE(get_included_files,     arginfo_zend__void)
     289             :         ZEND_FALIAS(get_required_files, get_included_files,             arginfo_zend__void)
     290             :         ZEND_FE(is_subclass_of,         arginfo_is_subclass_of)
     291             :         ZEND_FE(is_a,                   arginfo_is_subclass_of)
     292             :         ZEND_FE(get_class_vars,         arginfo_get_class_vars)
     293             :         ZEND_FE(get_object_vars,        arginfo_get_object_vars)
     294             :         ZEND_FE(get_class_methods,      arginfo_get_class_methods)
     295             :         ZEND_FE(trigger_error,          arginfo_trigger_error)
     296             :         ZEND_FALIAS(user_error,         trigger_error,          arginfo_trigger_error)
     297             :         ZEND_FE(set_error_handler,              arginfo_set_error_handler)
     298             :         ZEND_FE(restore_error_handler,          arginfo_zend__void)
     299             :         ZEND_FE(set_exception_handler,          arginfo_set_exception_handler)
     300             :         ZEND_FE(restore_exception_handler,      arginfo_zend__void)
     301             :         ZEND_FE(get_declared_classes,           arginfo_zend__void)
     302             :         ZEND_FE(get_declared_traits,            arginfo_zend__void)
     303             :         ZEND_FE(get_declared_interfaces,        arginfo_zend__void)
     304             :         ZEND_FE(get_defined_functions,          arginfo_zend__void)
     305             :         ZEND_FE(get_defined_vars,               arginfo_zend__void)
     306             :         ZEND_FE(create_function,                arginfo_create_function)
     307             :         ZEND_FE(get_resource_type,              arginfo_get_resource_type)
     308             :         ZEND_FE(get_resources,                  arginfo_get_resources)
     309             :         ZEND_FE(get_loaded_extensions,          arginfo_get_loaded_extensions)
     310             :         ZEND_FE(extension_loaded,               arginfo_extension_loaded)
     311             :         ZEND_FE(get_extension_funcs,            arginfo_extension_loaded)
     312             :         ZEND_FE(get_defined_constants,          arginfo_get_defined_constants)
     313             :         ZEND_FE(debug_backtrace,                arginfo_debug_backtrace)
     314             :         ZEND_FE(debug_print_backtrace,          arginfo_debug_print_backtrace)
     315             : #if ZEND_DEBUG
     316             :         ZEND_FE(zend_test_func,         arginfo_zend_test_func)
     317             :         ZEND_FE(zend_test_func2,        arginfo_zend_test_func2)
     318             : #ifdef ZTS
     319             :         ZEND_FE(zend_thread_id,         NULL)
     320             : #endif
     321             : #endif
     322             :         ZEND_FE(gc_collect_cycles,      arginfo_zend__void)
     323             :         ZEND_FE(gc_enabled,             arginfo_zend__void)
     324             :         ZEND_FE(gc_enable,              arginfo_zend__void)
     325             :         ZEND_FE(gc_disable,             arginfo_zend__void)
     326             :         ZEND_FE_END
     327             : };
     328             : /* }}} */
     329             : 
     330       20871 : ZEND_MINIT_FUNCTION(core) { /* {{{ */
     331             :         zend_class_entry class_entry;
     332             : 
     333       20871 :         INIT_CLASS_ENTRY(class_entry, "stdClass", NULL);
     334       20871 :         zend_standard_class_def = zend_register_internal_class(&class_entry);
     335             : 
     336       20871 :         zend_register_default_classes();
     337             : 
     338       20871 :         return SUCCESS;
     339             : }
     340             : /* }}} */
     341             : 
     342             : zend_module_entry zend_builtin_module = { /* {{{ */
     343             :     STANDARD_MODULE_HEADER,
     344             :         "Core",
     345             :         builtin_functions,
     346             :         ZEND_MINIT(core),
     347             :         NULL,
     348             :         NULL,
     349             :         NULL,
     350             :         NULL,
     351             :         ZEND_VERSION,
     352             :         STANDARD_MODULE_PROPERTIES
     353             : };
     354             : /* }}} */
     355             : 
     356       20871 : int zend_startup_builtin_functions(void) /* {{{ */
     357             : {
     358       20871 :         zend_builtin_module.module_number = 0;
     359       20871 :         zend_builtin_module.type = MODULE_PERSISTENT;
     360       20871 :         return (EG(current_module) = zend_register_module_ex(&zend_builtin_module)) == NULL ? FAILURE : SUCCESS;
     361             : }
     362             : /* }}} */
     363             : 
     364             : /* {{{ proto string zend_version(void)
     365             :    Get the version of the Zend Engine */
     366         142 : ZEND_FUNCTION(zend_version)
     367             : {
     368         284 :         RETURN_STRINGL(ZEND_VERSION, sizeof(ZEND_VERSION)-1);
     369             : }
     370             : /* }}} */
     371             : 
     372             : /* {{{ proto int gc_collect_cycles(void)
     373             :    Forces collection of any existing garbage cycles.
     374             :    Returns number of freed zvals */
     375          50 : ZEND_FUNCTION(gc_collect_cycles)
     376             : {
     377          50 :         RETURN_LONG(gc_collect_cycles());
     378             : }
     379             : /* }}} */
     380             : 
     381             : /* {{{ proto void gc_enabled(void)
     382             :    Returns status of the circular reference collector */
     383           6 : ZEND_FUNCTION(gc_enabled)
     384             : {
     385           6 :         RETURN_BOOL(GC_G(gc_enabled));
     386             : }
     387             : /* }}} */
     388             : 
     389             : /* {{{ proto void gc_enable(void)
     390             :    Activates the circular reference collector */
     391           6 : ZEND_FUNCTION(gc_enable)
     392             : {
     393           6 :         zend_string *key = zend_string_init("zend.enable_gc", sizeof("zend.enable_gc")-1, 0);
     394           6 :         zend_alter_ini_entry_chars(key, "1", sizeof("1")-1, ZEND_INI_USER, ZEND_INI_STAGE_RUNTIME);
     395             :         zend_string_release(key);
     396           6 : }
     397             : /* }}} */
     398             : 
     399             : /* {{{ proto void gc_disable(void)
     400             :    Deactivates the circular reference collector */
     401           3 : ZEND_FUNCTION(gc_disable)
     402             : {
     403           3 :         zend_string *key = zend_string_init("zend.enable_gc", sizeof("zend.enable_gc")-1, 0);
     404           3 :         zend_alter_ini_entry_chars(key, "0", sizeof("0")-1, ZEND_INI_USER, ZEND_INI_STAGE_RUNTIME);
     405             :         zend_string_release(key);
     406           3 : }
     407             : /* }}} */
     408             : 
     409             : /* {{{ proto int func_num_args(void)
     410             :    Get the number of arguments that were passed to the function */
     411          16 : ZEND_FUNCTION(func_num_args)
     412             : {
     413          16 :         zend_execute_data *ex = EX(prev_execute_data);
     414             : 
     415          16 :         if (!(ZEND_CALL_INFO(ex) & ZEND_CALL_CODE)) {
     416          14 :                 RETURN_LONG(ZEND_CALL_NUM_ARGS(ex));
     417             :         } else {
     418           2 :                 zend_error(E_WARNING, "func_num_args():  Called from the global scope - no function context");
     419           2 :                 RETURN_LONG(-1);
     420             :         }
     421             : }
     422             : /* }}} */
     423             : 
     424             : /* {{{ proto mixed func_get_arg(int arg_num)
     425             :    Get the $arg_num'th argument that was passed to the function */
     426          42 : ZEND_FUNCTION(func_get_arg)
     427             : {
     428             :         uint32_t arg_count, first_extra_arg;
     429             :         zval *arg;
     430             :         zend_long requested_offset;
     431             :         zend_execute_data *ex;
     432             : 
     433          42 :         if (zend_parse_parameters(ZEND_NUM_ARGS(), "l", &requested_offset) == FAILURE) {
     434           5 :                 return;
     435             :         }
     436             : 
     437          37 :         if (requested_offset < 0) {
     438           4 :                 zend_error(E_WARNING, "func_get_arg():  The argument number should be >= 0");
     439           4 :                 RETURN_FALSE;
     440             :         }
     441             : 
     442          33 :         ex = EX(prev_execute_data);
     443          33 :         if (ZEND_CALL_INFO(ex) & ZEND_CALL_CODE) {
     444           3 :                 zend_error(E_WARNING, "func_get_arg():  Called from the global scope - no function context");
     445           3 :                 RETURN_FALSE;
     446             :         }
     447             : 
     448          30 :         arg_count = ZEND_CALL_NUM_ARGS(ex);
     449             : 
     450          30 :         if (requested_offset >= arg_count) {
     451          16 :                 zend_error(E_WARNING, "func_get_arg():  Argument " ZEND_LONG_FMT " not passed to function", requested_offset);
     452          16 :                 RETURN_FALSE;
     453             :         }
     454             : 
     455          14 :         first_extra_arg = ex->func->op_array.num_args;
     456          19 :         if (requested_offset >= first_extra_arg && (ZEND_CALL_NUM_ARGS(ex) > first_extra_arg)) {
     457           5 :                 arg = ZEND_CALL_VAR_NUM(ex, ex->func->op_array.last_var + ex->func->op_array.T) + (requested_offset - first_extra_arg);
     458             :         } else {
     459           9 :                 arg = ZEND_CALL_ARG(ex, requested_offset + 1);
     460             :         }
     461          42 :         RETURN_ZVAL_FAST(arg);
     462             : }
     463             : /* }}} */
     464             : 
     465             : /* {{{ proto array func_get_args()
     466             :    Get an array of the arguments that were passed to the function */
     467          81 : ZEND_FUNCTION(func_get_args)
     468             : {
     469             :         zval *p, *q;
     470             :         uint32_t arg_count, first_extra_arg;
     471             :         uint32_t i;
     472          81 :         zend_execute_data *ex = EX(prev_execute_data);
     473             : 
     474          81 :         if (ZEND_CALL_INFO(ex) & ZEND_CALL_CODE) {
     475           2 :                 zend_error(E_WARNING, "func_get_args():  Called from the global scope - no function context");
     476           2 :                 RETURN_FALSE;
     477             :         }
     478             : 
     479          79 :         arg_count = ZEND_CALL_NUM_ARGS(ex);
     480             : 
     481          79 :         array_init_size(return_value, arg_count);
     482          79 :         if (arg_count) {
     483          57 :                 first_extra_arg = ex->func->op_array.num_args;
     484          57 :                 zend_hash_real_init(Z_ARRVAL_P(return_value), 1);
     485          57 :                 ZEND_HASH_FILL_PACKED(Z_ARRVAL_P(return_value)) {
     486          57 :                         i = 0;
     487          57 :                         p = ZEND_CALL_ARG(ex, 1);
     488          57 :                         if (arg_count > first_extra_arg) {
     489          72 :                                 while (i < first_extra_arg) {
     490           2 :                                         q = p;
     491           2 :                                         ZVAL_DEREF(q);
     492           2 :                                         if (Z_OPT_REFCOUNTED_P(q)) Z_ADDREF_P(q);
     493           2 :                                         ZEND_HASH_FILL_ADD(q);
     494           2 :                                         p++;
     495           2 :                                         i++;
     496             :                                 }
     497          35 :                                 p = ZEND_CALL_VAR_NUM(ex, ex->func->op_array.last_var + ex->func->op_array.T);
     498             :                         }
     499         197 :                         while (i < arg_count) {
     500          83 :                                 q = p;
     501          83 :                                 ZVAL_DEREF(q);
     502          83 :                                 if (Z_OPT_REFCOUNTED_P(q)) Z_ADDREF_P(q);
     503          83 :                                 ZEND_HASH_FILL_ADD(q);
     504          83 :                                 p++;
     505          83 :                                 i++;
     506             :                         }
     507          57 :                 } ZEND_HASH_FILL_END();
     508             :         }
     509             : }
     510             : /* }}} */
     511             : 
     512             : /* {{{ proto int strlen(string str)
     513             :    Get string length
     514             :    Warning: This function is special-cased by zend_compile.c and so is usually bypassed */
     515         171 : ZEND_FUNCTION(strlen)
     516             : {
     517             :         zend_string *s;
     518             : 
     519             : #ifndef FAST_ZPP
     520             :         if (zend_parse_parameters(ZEND_NUM_ARGS(), "S", &s) == FAILURE) {
     521             :                 return;
     522             :         }
     523             : #else
     524         171 :         ZEND_PARSE_PARAMETERS_START(1, 1)
     525         498 :                 Z_PARAM_STR(s)
     526         171 :         ZEND_PARSE_PARAMETERS_END();
     527             : #endif
     528             : 
     529         164 :         RETVAL_LONG(s->len);
     530             : }
     531             : /* }}} */
     532             : 
     533             : /* {{{ proto int strcmp(string str1, string str2)
     534             :    Binary safe string comparison */
     535      275940 : ZEND_FUNCTION(strcmp)
     536             : {
     537             :         zend_string *s1, *s2;
     538             : 
     539      275940 :         if (zend_parse_parameters(ZEND_NUM_ARGS(), "SS", &s1, &s2) == FAILURE) {
     540           5 :                 return;
     541             :         }
     542             : 
     543      275935 :         RETURN_LONG(zend_binary_strcmp(s1->val, s1->len, s2->val, s2->len));
     544             : }
     545             : /* }}} */
     546             : 
     547             : /* {{{ proto int strncmp(string str1, string str2, int len)
     548             :    Binary safe string comparison */
     549       14416 : ZEND_FUNCTION(strncmp)
     550             : {
     551             :         zend_string *s1, *s2;
     552             :         zend_long len;
     553             : 
     554       14416 :         if (zend_parse_parameters(ZEND_NUM_ARGS(), "SSl", &s1, &s2, &len) == FAILURE) {
     555          20 :                 return;
     556             :         }
     557             : 
     558       14396 :         if (len < 0) {
     559           3 :                 zend_error(E_WARNING, "Length must be greater than or equal to 0");
     560           3 :                 RETURN_FALSE;
     561             :         }
     562             : 
     563       14393 :         RETURN_LONG(zend_binary_strncmp(s1->val, s1->len, s2->val, s2->len, len));
     564             : }
     565             : /* }}} */
     566             : 
     567             : /* {{{ proto int strcasecmp(string str1, string str2)
     568             :    Binary safe case-insensitive string comparison */
     569         755 : ZEND_FUNCTION(strcasecmp)
     570             : {
     571             :         zend_string *s1, *s2;
     572             : 
     573         755 :         if (zend_parse_parameters(ZEND_NUM_ARGS(), "SS", &s1, &s2) == FAILURE) {
     574           6 :                 return;
     575             :         }
     576             : 
     577         749 :         RETURN_LONG(zend_binary_strcasecmp(s1->val, s1->len, s2->val, s2->len));
     578             : }
     579             : /* }}} */
     580             : 
     581             : /* {{{ proto int strncasecmp(string str1, string str2, int len)
     582             :    Binary safe string comparison */
     583       20293 : ZEND_FUNCTION(strncasecmp)
     584             : {
     585             :         zend_string *s1, *s2;
     586             :         zend_long len;
     587             : 
     588       20293 :         if (zend_parse_parameters(ZEND_NUM_ARGS(), "SSl", &s1, &s2, &len) == FAILURE) {
     589          32 :                 return;
     590             :         }
     591             : 
     592       20261 :         if (len < 0) {
     593           3 :                 zend_error(E_WARNING, "Length must be greater than or equal to 0");
     594           3 :                 RETURN_FALSE;
     595             :         }
     596             : 
     597       20258 :         RETURN_LONG(zend_binary_strncasecmp(s1->val, s1->len, s2->val, s2->len, len));
     598             : }
     599             : /* }}} */
     600             : 
     601             : /* {{{ proto array each(array arr)
     602             :    Return the currently pointed key..value pair in the passed array, and advance the pointer to the next element */
     603        1480 : ZEND_FUNCTION(each)
     604             : {
     605             :         zval *array, *entry, tmp;
     606             :         zend_ulong num_key;
     607             :         HashTable *target_hash;
     608             :         zend_string *key;
     609             : 
     610        1480 :         if (zend_parse_parameters(ZEND_NUM_ARGS(), "z/", &array) == FAILURE) {
     611           5 :                 return;
     612             :         }
     613             : 
     614        2985 :         target_hash = HASH_OF(array);
     615        1475 :         if (!target_hash) {
     616          29 :                 zend_error(E_WARNING,"Variable passed to each() is not an array or object");
     617          29 :                 return;
     618             :         }
     619             :         while (1) {
     620        1446 :                 entry = zend_hash_get_current_data(target_hash);
     621        1446 :                 if (!entry) {
     622          59 :                         RETURN_FALSE;
     623        1387 :                 } else if (Z_TYPE_P(entry) == IS_INDIRECT) {
     624           3 :                         entry = Z_INDIRECT_P(entry);
     625           3 :                         if (Z_TYPE_P(entry) == IS_UNDEF) {
     626           0 :                                 zend_hash_move_forward(target_hash);
     627           0 :                                 continue;
     628             :                         }
     629             :                 }
     630        1387 :                 break;
     631           0 :         }
     632        1387 :         array_init_size(return_value, 4);
     633        1387 :         zend_hash_real_init(Z_ARRVAL_P(return_value), 0);
     634             : 
     635             :         /* add value elements */
     636        1387 :         if (Z_ISREF_P(entry)) {
     637           3 :                 ZVAL_DUP(&tmp, Z_REFVAL_P(entry));
     638           3 :                 entry = &tmp;
     639           3 :                 if (Z_REFCOUNTED_P(entry)) Z_ADDREF_P(entry);
     640             :         } else {
     641        1384 :                 if (Z_REFCOUNTED_P(entry)) Z_ADDREF_P(entry);
     642        1384 :                 if (Z_REFCOUNTED_P(entry)) Z_ADDREF_P(entry);
     643             :         }
     644        1387 :         zend_hash_index_add_new(Z_ARRVAL_P(return_value), 1, entry);
     645        1387 :         zend_hash_str_add_new(Z_ARRVAL_P(return_value), "value", sizeof("value")-1, entry);
     646             : 
     647             :         /* add the key elements */
     648        1387 :         if (zend_hash_get_current_key(target_hash, &key, &num_key) == HASH_KEY_IS_STRING) {
     649          43 :                 ZVAL_STR_COPY(&tmp, key);
     650          43 :                 if (Z_REFCOUNTED(tmp)) Z_ADDREF(tmp);
     651             :         } else {
     652        1344 :                 ZVAL_LONG(&tmp, num_key);
     653             :         }
     654        1387 :         zend_hash_index_add_new(Z_ARRVAL_P(return_value), 0, &tmp);
     655        1387 :         zend_hash_str_add_new(Z_ARRVAL_P(return_value), "key", sizeof("key")-1, &tmp);
     656        1387 :         zend_hash_move_forward(target_hash);
     657             : }
     658             : /* }}} */
     659             : 
     660             : /* {{{ proto int error_reporting([int new_error_level])
     661             :    Return the current error_reporting level, and if an argument was passed - change to the new level */
     662        2395 : ZEND_FUNCTION(error_reporting)
     663             : {
     664             :         zval *err;
     665             :         int old_error_reporting;
     666             : 
     667             : #ifndef FAST_ZPP
     668             :         if (zend_parse_parameters(ZEND_NUM_ARGS(), "|z", &err) == FAILURE) {
     669             :                 return;
     670             :         }
     671             : #else
     672        2395 :         ZEND_PARSE_PARAMETERS_START(0, 1)
     673        2395 :                 Z_PARAM_OPTIONAL
     674        2395 :                 Z_PARAM_ZVAL(err)
     675        2395 :         ZEND_PARSE_PARAMETERS_END();
     676             : #endif
     677             : 
     678        2395 :         old_error_reporting = EG(error_reporting);
     679        2395 :         if(ZEND_NUM_ARGS() != 0) {
     680             :                 do {
     681         380 :                         zend_ini_entry *p = EG(error_reporting_ini_entry);
     682             : 
     683         380 :                         if (!p) {
     684         624 :                                 p = zend_hash_str_find_ptr(EG(ini_directives), "error_reporting", sizeof("error_reporting")-1);
     685         312 :                                 if (p) {
     686         312 :                                         EG(error_reporting_ini_entry) = p;
     687             :                                 } else {
     688           0 :                                         break;
     689             :                                 }
     690             :                         }
     691         380 :                         if (!p->modified) {
     692         312 :                                 if (!EG(modified_ini_directives)) {
     693         308 :                                         ALLOC_HASHTABLE(EG(modified_ini_directives));
     694         308 :                                         zend_hash_init(EG(modified_ini_directives), 8, NULL, NULL, 0);
     695             :                                 }
     696         624 :                                 if (EXPECTED(zend_hash_str_add_ptr(EG(modified_ini_directives), "error_reporting", sizeof("error_reporting")-1, p) != NULL)) {
     697         312 :                                         p->orig_value = p->value;
     698         312 :                                         p->orig_modifiable = p->modifiable;
     699         312 :                                         p->modified = 1;
     700             :                                 }
     701          68 :                         } else if (p->orig_value != p->value) {
     702          67 :                                 zend_string_release(p->value);
     703             :                         }
     704             : 
     705         760 :                         p->value = zval_get_string(err);
     706         760 :                         if (Z_TYPE_P(err) == IS_LONG) {
     707         380 :                                 EG(error_reporting) = Z_LVAL_P(err);
     708             :                         } else {
     709           0 :                                 EG(error_reporting) = atoi(p->value->val);
     710             :                         }
     711             :                 } while (0);
     712             :         }
     713             : 
     714        2395 :         RETVAL_LONG(old_error_reporting);
     715             : }
     716             : /* }}} */
     717             : 
     718           6 : static int validate_constant_array(HashTable *ht) /* {{{ */
     719             : {
     720           6 :         int ret = 1;
     721             :         zval *val;
     722             : 
     723           6 :         ht->u.v.nApplyCount++;
     724          31 :         ZEND_HASH_FOREACH_VAL_IND(ht, val) {
     725           9 :                 ZVAL_DEREF(val);
     726           9 :                 if (Z_REFCOUNTED_P(val)) {
     727           4 :                         if (Z_TYPE_P(val) == IS_ARRAY) {
     728           2 :                                 if (!Z_IMMUTABLE_P(val)) {
     729           2 :                                         if (Z_ARRVAL_P(val)->u.v.nApplyCount > 0) {
     730           1 :                                                 zend_error(E_WARNING, "Constants cannot be recursive arrays");
     731           1 :                                                 ret = 0;
     732           1 :                                                 break;
     733           1 :                                         } else if (!validate_constant_array(Z_ARRVAL_P(val))) {
     734           0 :                                                 ret = 0;
     735           0 :                                                 break;
     736             :                                         }
     737             :                                 }
     738           3 :                         } else if (Z_TYPE_P(val) != IS_STRING && Z_TYPE_P(val) != IS_RESOURCE) {
     739           1 :                                 zend_error(E_WARNING, "Constants may only evaluate to scalar values or arrays");
     740           1 :                                 ret = 0;
     741           1 :                                 break;
     742             :                         }
     743             :                 }
     744             :         } ZEND_HASH_FOREACH_END();
     745           6 :         ht->u.v.nApplyCount--;
     746           6 :         return ret;
     747             : }
     748             : /* }}} */
     749             : 
     750           4 : static void copy_constant_array(zval *dst, zval *src) /* {{{ */
     751             : {
     752             :         zend_string *key;
     753             :         zend_ulong idx;
     754             :         zval *new_val, *val;
     755             : 
     756           4 :         array_init_size(dst, zend_hash_num_elements(Z_ARRVAL_P(src)));
     757          25 :         ZEND_HASH_FOREACH_KEY_VAL_IND(Z_ARRVAL_P(src), idx, key, val) {
     758             :                 /* constant arrays can't contain references */
     759           7 :                 ZVAL_DEREF(val);
     760           7 :                 if (key) {
     761           1 :                         new_val = zend_hash_add_new(Z_ARRVAL_P(dst), key, val);
     762             :                 } else {
     763           6 :                         new_val = zend_hash_index_add_new(Z_ARRVAL_P(dst), idx, val);
     764             :                 }
     765           7 :                 if (Z_TYPE_P(val) == IS_ARRAY) {
     766           1 :                         if (!Z_IMMUTABLE_P(val)) {
     767           1 :                                 copy_constant_array(new_val, val);
     768             :                         }
     769           6 :                 } else if (Z_REFCOUNTED_P(val)) {
     770             :                         Z_ADDREF_P(val);
     771             :                 }
     772             :         } ZEND_HASH_FOREACH_END();
     773           4 : }
     774             : /* }}} */
     775             : 
     776             : /* {{{ proto bool define(string constant_name, mixed value, boolean case_insensitive=false)
     777             :    Define a new constant */
     778        3310 : ZEND_FUNCTION(define)
     779             : {
     780             :         zend_string *name;
     781             :         zval *val, val_free;
     782        3310 :         zend_bool non_cs = 0;
     783        3310 :         int case_sensitive = CONST_CS;
     784             :         zend_constant c;
     785             : 
     786             : #ifndef FAST_ZPP
     787             :         if (zend_parse_parameters(ZEND_NUM_ARGS(), "Sz|b", &name, &val, &non_cs) == FAILURE) {
     788             :                 return;
     789             :         }
     790             : #else
     791        3310 :         ZEND_PARSE_PARAMETERS_START(2, 3)
     792        9924 :                 Z_PARAM_STR(name)
     793        3307 :                 Z_PARAM_ZVAL(val)
     794        3307 :                 Z_PARAM_OPTIONAL
     795        3563 :                 Z_PARAM_BOOL(non_cs)
     796        3310 :         ZEND_PARSE_PARAMETERS_END();
     797             : #endif
     798             : 
     799        3306 :         if(non_cs) {
     800         127 :                 case_sensitive = 0;
     801             :         }
     802             : 
     803             :         /* class constant, check if there is name and make sure class is valid & exists */
     804        6612 :         if (zend_memnstr(name->val, "::", sizeof("::") - 1, name->val + name->len)) {
     805           3 :                 zend_error(E_WARNING, "Class constants cannot be defined or redefined");
     806           3 :                 RETURN_FALSE;
     807             :         }
     808             : 
     809        3303 :         ZVAL_UNDEF(&val_free);
     810             : 
     811             : repeat:
     812        6606 :         switch (Z_TYPE_P(val)) {
     813             :                 case IS_LONG:
     814             :                 case IS_DOUBLE:
     815             :                 case IS_STRING:
     816             :                 case IS_FALSE:
     817             :                 case IS_TRUE:
     818             :                 case IS_RESOURCE:
     819             :                 case IS_NULL:
     820        3294 :                         break;
     821             :                 case IS_ARRAY:
     822           5 :                         if (!Z_IMMUTABLE_P(val)) {
     823           5 :                                 if (!validate_constant_array(Z_ARRVAL_P(val))) {
     824           2 :                                         RETURN_FALSE;
     825             :                                 } else {
     826           3 :                                         copy_constant_array(&c.value, val);
     827           3 :                                         goto register_constant;
     828             :                                 }
     829             :                         }
     830           0 :                         break;
     831             :                 case IS_OBJECT:
     832           4 :                         if (Z_TYPE(val_free) == IS_UNDEF) {
     833           4 :                                 if (Z_OBJ_HT_P(val)->get) {
     834             :                                         zval rv;
     835           0 :                                         val = Z_OBJ_HT_P(val)->get(val, &rv);
     836           0 :                                         ZVAL_COPY_VALUE(&val_free, val);
     837           0 :                                         goto repeat;
     838           4 :                                 } else if (Z_OBJ_HT_P(val)->cast_object) {
     839           4 :                                         if (Z_OBJ_HT_P(val)->cast_object(val, &val_free, IS_STRING) == SUCCESS) {
     840           1 :                                                 val = &val_free;
     841           1 :                                                 break;
     842             :                                         }
     843             :                                 }
     844             :                         }
     845             :                         /* no break */
     846             :                 default:
     847           3 :                         zend_error(E_WARNING, "Constants may only evaluate to scalar values or arrays");
     848           3 :                         zval_ptr_dtor(&val_free);
     849           3 :                         RETURN_FALSE;
     850             :         }
     851             : 
     852        3295 :         ZVAL_DUP(&c.value, val);
     853        3295 :         zval_ptr_dtor(&val_free);
     854             : register_constant:
     855        3298 :         c.flags = case_sensitive; /* non persistent */
     856        6596 :         c.name = zend_string_copy(name);
     857        3298 :         c.module_number = PHP_USER_CONSTANT;
     858        3298 :         if (zend_register_constant(&c) == SUCCESS) {
     859        3292 :                 RETURN_TRUE;
     860             :         } else {
     861           6 :                 RETURN_FALSE;
     862             :         }
     863             : }
     864             : /* }}} */
     865             : 
     866             : /* {{{ proto bool defined(string constant_name)
     867             :    Check whether a constant exists
     868             :    Warning: This function is special-cased by zend_compile.c and so is usually bypassed */
     869          23 : ZEND_FUNCTION(defined)
     870             : {
     871             :         zend_string *name;
     872             : 
     873             : #ifndef FAST_ZPP
     874             :         if (zend_parse_parameters(ZEND_NUM_ARGS(), "S", &name) == FAILURE) {
     875             :                 return;
     876             :         }
     877             : #else
     878          23 :         ZEND_PARSE_PARAMETERS_START(1, 1)
     879          69 :                 Z_PARAM_STR(name)
     880          23 :         ZEND_PARSE_PARAMETERS_END();
     881             : #endif
     882             : 
     883          23 :         if (zend_get_constant_ex(name, NULL, ZEND_FETCH_CLASS_SILENT)) {
     884          13 :                 RETURN_TRUE;
     885             :         } else {
     886          10 :                 RETURN_FALSE;
     887             :         }
     888             : }
     889             : /* }}} */
     890             : 
     891             : /* {{{ proto string get_class([object object])
     892             :    Retrieves the class name */
     893         648 : ZEND_FUNCTION(get_class)
     894             : {
     895         648 :         zval *obj = NULL;
     896             : 
     897         648 :         if (zend_parse_parameters(ZEND_NUM_ARGS(), "|o!", &obj) == FAILURE) {
     898          24 :                 RETURN_FALSE;
     899             :         }
     900             : 
     901         624 :         if (!obj) {
     902          12 :                 if (EG(scope)) {
     903          14 :                         RETURN_STR(zend_string_copy(EG(scope)->name));
     904             :                 } else {
     905           5 :                         zend_error(E_WARNING, "get_class() called without object from outside a class");
     906           5 :                         RETURN_FALSE;
     907             :                 }
     908             :         }
     909             : 
     910        1224 :         RETURN_STR(zend_string_copy(Z_OBJCE_P(obj)->name));
     911             : }
     912             : /* }}} */
     913             : 
     914             : /* {{{ proto string get_called_class()
     915             :    Retrieves the "Late Static Binding" class name */
     916          35 : ZEND_FUNCTION(get_called_class)
     917             : {
     918          35 :         if (zend_parse_parameters_none() == FAILURE) {
     919           0 :                 return;
     920             :         }
     921             : 
     922          35 :         if (EX(called_scope)) {
     923          66 :                 RETURN_STR(zend_string_copy(EX(called_scope)->name));
     924           2 :         } else if (!EG(scope))  {
     925           2 :                 zend_error(E_WARNING, "get_called_class() called from outside a class");
     926             :         }
     927           2 :         RETURN_FALSE;
     928             : }
     929             : /* }}} */
     930             : 
     931             : /* {{{ proto string get_parent_class([mixed object])
     932             :    Retrieves the parent class name for object or class or current scope. */
     933          59 : ZEND_FUNCTION(get_parent_class)
     934             : {
     935             :         zval *arg;
     936          59 :         zend_class_entry *ce = NULL;
     937             : 
     938          59 :         if (zend_parse_parameters(ZEND_NUM_ARGS(), "|z", &arg) == FAILURE) {
     939           1 :                 return;
     940             :         }
     941             : 
     942          58 :         if (!ZEND_NUM_ARGS()) {
     943           5 :                 ce = EG(scope);
     944           5 :                 if (ce && ce->parent) {
     945           4 :                         RETURN_STR(zend_string_copy(ce->parent->name));
     946             :                 } else {
     947           3 :                         RETURN_FALSE;
     948             :                 }
     949             :         }
     950             : 
     951         106 :         if (Z_TYPE_P(arg) == IS_OBJECT) {
     952          17 :                 ce = Z_OBJ_P(arg)->ce;
     953          72 :         } else if (Z_TYPE_P(arg) == IS_STRING) {
     954          12 :             ce = zend_lookup_class(Z_STR_P(arg));
     955             :         }
     956             : 
     957          53 :         if (ce && ce->parent) {
     958          10 :                 RETURN_STR(zend_string_copy(ce->parent->name));
     959             :         } else {
     960          48 :                 RETURN_FALSE;
     961             :         }
     962             : }
     963             : /* }}} */
     964             : 
     965         359 : static void is_a_impl(INTERNAL_FUNCTION_PARAMETERS, zend_bool only_subclass) /* {{{ */
     966             : {
     967             :         zval *obj;
     968             :         zend_string *class_name;
     969             :         zend_class_entry *instance_ce;
     970             :         zend_class_entry *ce;
     971         359 :         zend_bool allow_string = only_subclass;
     972             :         zend_bool retval;
     973             : 
     974             : #ifndef FAST_ZPP
     975             :         if (zend_parse_parameters(ZEND_NUM_ARGS(), "zS|b", &obj, &class_name, &allow_string) == FAILURE) {
     976             :                 return;
     977             :         }
     978             : #else
     979         359 :         ZEND_PARSE_PARAMETERS_START(2, 3)
     980         355 :                 Z_PARAM_ZVAL(obj)
     981        1065 :                 Z_PARAM_STR(class_name)
     982         344 :                 Z_PARAM_OPTIONAL
     983         510 :                 Z_PARAM_BOOL(allow_string)
     984         359 :         ZEND_PARSE_PARAMETERS_END();
     985             : #endif
     986             :         /*
     987             :          * allow_string - is_a default is no, is_subclass_of is yes.
     988             :          *   if it's allowed, then the autoloader will be called if the class does not exist.
     989             :          *   default behaviour is different, as 'is_a' used to be used to test mixed return values
     990             :          *   and there is no easy way to deprecate this.
     991             :          */
     992             : 
     993         576 :         if (allow_string && Z_TYPE_P(obj) == IS_STRING) {
     994          92 :                 instance_ce = zend_lookup_class(Z_STR_P(obj));
     995          92 :                 if (!instance_ce) {
     996          48 :                         RETURN_FALSE;
     997             :                 }
     998         500 :         } else if (Z_TYPE_P(obj) == IS_OBJECT) {
     999         100 :                 instance_ce = Z_OBJCE_P(obj);
    1000             :         } else {
    1001         150 :                 RETURN_FALSE;
    1002             :         }
    1003             : 
    1004         219 :         if (!only_subclass && EXPECTED(zend_string_equals(instance_ce->name, class_name))) {
    1005           9 :                 retval = 1;
    1006             :         } else {
    1007         135 :                 ce = zend_lookup_class_ex(class_name, NULL, 0);
    1008         135 :                 if (!ce) {
    1009          63 :                         retval = 0;
    1010             :                 } else {
    1011          87 :                         if (only_subclass && instance_ce == ce) {
    1012          15 :                                 retval = 0;
    1013             :                         } else {
    1014          57 :                                 retval = instanceof_function(instance_ce, ce);
    1015             :                         }
    1016             :                 }
    1017             :         }
    1018             : 
    1019         144 :         RETURN_BOOL(retval);
    1020             : }
    1021             : /* }}} */
    1022             : 
    1023             : /* {{{ proto bool is_subclass_of(mixed object_or_string, string class_name [, bool allow_string=true])
    1024             :    Returns true if the object has this class as one of its parents */
    1025         199 : ZEND_FUNCTION(is_subclass_of)
    1026             : {
    1027         199 :         is_a_impl(INTERNAL_FUNCTION_PARAM_PASSTHRU, 1);
    1028         199 : }
    1029             : /* }}} */
    1030             : 
    1031             : /* {{{ proto bool is_a(mixed object_or_string, string class_name [, bool allow_string=false])
    1032             :    Returns true if the first argument is an object and is this class or has this class as one of its parents, */
    1033         160 : ZEND_FUNCTION(is_a)
    1034             : {
    1035         160 :         is_a_impl(INTERNAL_FUNCTION_PARAM_PASSTHRU, 0);
    1036         160 : }
    1037             : /* }}} */
    1038             : 
    1039             : /* {{{ add_class_vars */
    1040          76 : static void add_class_vars(zend_class_entry *ce, int statics, zval *return_value)
    1041             : {
    1042             :         zend_property_info *prop_info;
    1043             :         zval *prop, prop_copy;
    1044             :         zend_string *key;
    1045             : 
    1046         884 :         ZEND_HASH_FOREACH_STR_KEY_PTR(&ce->properties_info, key, prop_info) {
    1047        1380 :                 if (((prop_info->flags & ZEND_ACC_SHADOW) &&
    1048          18 :                      prop_info->ce != EG(scope)) ||
    1049         388 :                     ((prop_info->flags & ZEND_ACC_PROTECTED) &&
    1050          80 :                      !zend_check_protected(prop_info->ce, EG(scope))) ||
    1051         364 :                     ((prop_info->flags & ZEND_ACC_PRIVATE) &&
    1052          74 :                       ce != EG(scope) &&
    1053          52 :                           prop_info->ce != EG(scope))) {
    1054          92 :                         continue;
    1055             :                 }
    1056         312 :                 prop = NULL;
    1057         350 :                 if (statics && (prop_info->flags & ZEND_ACC_STATIC) != 0) {
    1058          38 :                         prop = &ce->default_static_members_table[prop_info->offset];
    1059         274 :                 } else if (!statics && (prop_info->flags & ZEND_ACC_STATIC) == 0) {
    1060         118 :                         prop = &ce->default_properties_table[OBJ_PROP_TO_NUM(prop_info->offset)];
    1061             :                 }
    1062         468 :                 if (!prop || Z_TYPE_P(prop) == IS_UNDEF) {
    1063         156 :                         continue;
    1064             :                 }
    1065             : 
    1066             :                 /* copy: enforce read only access */
    1067         156 :                 ZVAL_DEREF(prop);
    1068         156 :                 if (UNEXPECTED(Z_COPYABLE_P(prop))) {
    1069          35 :                         ZVAL_DUP(&prop_copy, prop);
    1070          35 :                         prop = &prop_copy;
    1071             :                 } else {
    1072         121 :                         Z_TRY_ADDREF_P(prop);
    1073             :                 }
    1074             : 
    1075             :                 /* this is necessary to make it able to work with default array
    1076             :                  * properties, returned to user */
    1077         156 :                 if (Z_OPT_CONSTANT_P(prop)) {
    1078           0 :                         zval_update_constant(prop, 0);
    1079             :                 }
    1080             : 
    1081         156 :                 zend_hash_add_new(Z_ARRVAL_P(return_value), key, prop);
    1082             :         } ZEND_HASH_FOREACH_END();
    1083          76 : }
    1084             : /* }}} */
    1085             : 
    1086             : /* {{{ proto array get_class_vars(string class_name)
    1087             :    Returns an array of default properties of the class. */
    1088          65 : ZEND_FUNCTION(get_class_vars)
    1089             : {
    1090             :         zend_string *class_name;
    1091             :         zend_class_entry *ce;
    1092             : 
    1093          65 :         if (zend_parse_parameters(ZEND_NUM_ARGS(), "S", &class_name) == FAILURE) {
    1094           7 :                 return;
    1095             :         }
    1096             : 
    1097          58 :         ce = zend_lookup_class(class_name);
    1098          58 :         if (!ce) {
    1099          20 :                 RETURN_FALSE;
    1100             :         } else {
    1101          38 :                 array_init(return_value);
    1102          38 :                 zend_update_class_constants(ce);
    1103          38 :                 add_class_vars(ce, 0, return_value);
    1104          38 :                 add_class_vars(ce, 1, return_value);
    1105             :         }
    1106             : }
    1107             : /* }}} */
    1108             : 
    1109             : /* {{{ proto array get_object_vars(object obj)
    1110             :    Returns an array of object properties */
    1111          73 : ZEND_FUNCTION(get_object_vars)
    1112             : {
    1113             :         zval *obj;
    1114             :         zval *value;
    1115             :         HashTable *properties;
    1116             :         zend_string *key;
    1117             :         zend_object *zobj;
    1118             : 
    1119             : #ifndef FAST_ZPP
    1120             :         if (zend_parse_parameters(ZEND_NUM_ARGS(), "o", &obj) == FAILURE) {
    1121             :                 return;
    1122             :         }
    1123             : #else
    1124          73 :         ZEND_PARSE_PARAMETERS_START(1, 1)
    1125         213 :                 Z_PARAM_OBJECT(obj)
    1126          73 :         ZEND_PARSE_PARAMETERS_END();
    1127             : #endif
    1128             : 
    1129          45 :         if (Z_OBJ_HT_P(obj)->get_properties == NULL) {
    1130           0 :                 RETURN_FALSE;
    1131             :         }
    1132             : 
    1133          45 :         properties = Z_OBJ_HT_P(obj)->get_properties(obj);
    1134             : 
    1135          45 :         if (properties == NULL) {
    1136           0 :                 RETURN_FALSE;
    1137             :         }
    1138             : 
    1139          45 :         zobj = Z_OBJ_P(obj);
    1140             : 
    1141          52 :         if (!zobj->ce->default_properties_count && properties == zobj->properties) {
    1142             :                 /* fast copy */
    1143           7 :                 ZVAL_ARR(return_value, zend_array_dup(properties));
    1144             :         } else {
    1145          38 :                 array_init_size(return_value, zend_hash_num_elements(properties));
    1146             : 
    1147         647 :                 ZEND_HASH_FOREACH_STR_KEY_VAL_IND(properties, key, value) {
    1148         203 :                         if (key) {
    1149         200 :                                 if (zend_check_property_access(zobj, key) == SUCCESS) {
    1150             :                                         /* Not separating references */
    1151         172 :                                         if (Z_REFCOUNTED_P(value)) Z_ADDREF_P(value);
    1152         172 :                                         if (key->val[0] == 0) {
    1153             :                                                 const char *prop_name, *class_name;
    1154             :                                                 size_t prop_len;
    1155          37 :                                                 zend_unmangle_property_name_ex(key, &class_name, &prop_name, &prop_len);
    1156          37 :                                                 zend_hash_str_add_new(Z_ARRVAL_P(return_value), prop_name, prop_len, value);
    1157             :                                         } else {
    1158         135 :                                                 zend_hash_add_new(Z_ARRVAL_P(return_value), key, value);
    1159             :                                         }
    1160             :                                 }
    1161             :                         }
    1162             :                 } ZEND_HASH_FOREACH_END();
    1163             :         }
    1164             : }
    1165             : /* }}} */
    1166             : 
    1167          56 : static int same_name(zend_string *key, zend_string *name) /* {{{ */
    1168             : {
    1169             :         zend_string *lcname;
    1170             :         int ret;
    1171             : 
    1172          56 :         if (key == name) {
    1173          18 :                 return 1;
    1174             :         }
    1175          38 :         if (key->len != name->len) {
    1176           3 :                 return 0;
    1177             :         }
    1178          35 :         lcname = zend_string_tolower(name);
    1179          35 :         ret = memcmp(lcname->val, key->val, key->len) == 0;
    1180             :         zend_string_release(lcname);
    1181          35 :         return ret;
    1182             : }
    1183             : /* }}} */
    1184             : 
    1185             : /* {{{ proto array get_class_methods(mixed class)
    1186             :    Returns an array of method names for class or class instance. */
    1187          73 : ZEND_FUNCTION(get_class_methods)
    1188             : {
    1189             :         zval *klass;
    1190             :         zval method_name;
    1191          73 :         zend_class_entry *ce = NULL;
    1192             :         zend_function *mptr;
    1193             :         zend_string *key;
    1194             : 
    1195          73 :         if (zend_parse_parameters(ZEND_NUM_ARGS(), "z", &klass) == FAILURE) {
    1196           2 :                 return;
    1197             :         }
    1198             : 
    1199         142 :         if (Z_TYPE_P(klass) == IS_OBJECT) {
    1200          10 :                 ce = Z_OBJCE_P(klass);
    1201         122 :         } else if (Z_TYPE_P(klass) == IS_STRING) {
    1202          39 :             ce = zend_lookup_class(Z_STR_P(klass));
    1203             :         }
    1204             : 
    1205          71 :         if (!ce) {
    1206          27 :                 RETURN_NULL();
    1207             :         }
    1208             : 
    1209          44 :         array_init(return_value);
    1210             : 
    1211         532 :         ZEND_HASH_FOREACH_STR_KEY_PTR(&ce->function_table, key, mptr) {
    1212             : 
    1213         428 :                 if ((mptr->common.fn_flags & ZEND_ACC_PUBLIC)
    1214          63 :                  || (EG(scope) &&
    1215          46 :                      (((mptr->common.fn_flags & ZEND_ACC_PROTECTED) &&
    1216          22 :                        zend_check_protected(mptr->common.scope, EG(scope)))
    1217          29 :                    || ((mptr->common.fn_flags & ZEND_ACC_PRIVATE) &&
    1218          24 :                        EG(scope) == mptr->common.scope)))) {
    1219         206 :                         size_t len = mptr->common.function_name->len;
    1220             : 
    1221             :                         /* Do not display old-style inherited constructors */
    1222         206 :                         if (!key) {
    1223           0 :                                 ZVAL_STR_COPY(&method_name, mptr->common.function_name);
    1224           0 :                                 zend_hash_next_index_insert_new(Z_ARRVAL_P(return_value), &method_name);
    1225         229 :                         } else if ((mptr->common.fn_flags & ZEND_ACC_CTOR) == 0 ||
    1226          16 :                             mptr->common.scope == ce ||
    1227           7 :                             zend_binary_strcasecmp(key->val, key->len, mptr->common.function_name->val, len) == 0) {
    1228             : 
    1229         375 :                                 if (mptr->type == ZEND_USER_FUNCTION &&
    1230         112 :                                     *mptr->op_array.refcount > 1 &&
    1231          54 :                                  !same_name(key, mptr->common.function_name)) {
    1232           3 :                                         ZVAL_STR_COPY(&method_name, zend_find_alias_name(mptr->common.scope, key));
    1233           3 :                                         zend_hash_next_index_insert_new(Z_ARRVAL_P(return_value), &method_name);
    1234             :                                 } else {
    1235         203 :                                         ZVAL_STR_COPY(&method_name, mptr->common.function_name);
    1236         203 :                                         zend_hash_next_index_insert_new(Z_ARRVAL_P(return_value), &method_name);
    1237             :                                 }
    1238             :                         }
    1239             :                 }
    1240             :         } ZEND_HASH_FOREACH_END();
    1241             : }
    1242             : /* }}} */
    1243             : 
    1244             : /* {{{ proto bool method_exists(object object, string method)
    1245             :    Checks if the class method exists */
    1246         132 : ZEND_FUNCTION(method_exists)
    1247             : {
    1248             :         zval *klass;
    1249             :         zend_string *method_name;
    1250             :         zend_string *lcname;
    1251             :         zend_class_entry * ce;
    1252             : 
    1253             : #ifndef FAST_ZPP
    1254             :         if (zend_parse_parameters(ZEND_NUM_ARGS(), "zS", &klass, &method_name) == FAILURE) {
    1255             :                 return;
    1256             :         }
    1257             : #else
    1258         132 :         ZEND_PARSE_PARAMETERS_START(2, 2)
    1259         130 :                 Z_PARAM_ZVAL(klass)
    1260         390 :                 Z_PARAM_STR(method_name)
    1261         132 :         ZEND_PARSE_PARAMETERS_END();
    1262             : #endif
    1263         248 :         if (Z_TYPE_P(klass) == IS_OBJECT) {
    1264          70 :                 ce = Z_OBJCE_P(klass);
    1265         108 :         } else if (Z_TYPE_P(klass) == IS_STRING) {
    1266          32 :                 if ((ce = zend_lookup_class(Z_STR_P(klass))) == NULL) {
    1267           5 :                         RETURN_FALSE;
    1268             :                 }
    1269             :         } else {
    1270          22 :                 RETURN_FALSE;
    1271             :         }
    1272             : 
    1273          97 :         lcname = zend_string_tolower(method_name);
    1274          97 :         if (zend_hash_exists(&ce->function_table, lcname)) {
    1275             :                 zend_string_release(lcname);
    1276          65 :                 RETURN_TRUE;
    1277             :         } else {
    1278          32 :                 union _zend_function *func = NULL;
    1279             : 
    1280          90 :                 if (Z_TYPE_P(klass) == IS_OBJECT
    1281          61 :                 && Z_OBJ_HT_P(klass)->get_method != NULL
    1282          58 :                 && (func = Z_OBJ_HT_P(klass)->get_method(&Z_OBJ_P(klass), method_name, NULL)) != NULL
    1283             :                 ) {
    1284           6 :                         if (func->type == ZEND_INTERNAL_FUNCTION
    1285           6 :                         && (func->common.fn_flags & ZEND_ACC_CALL_VIA_HANDLER) != 0
    1286             :                         ) {
    1287             :                                 /* Returns true to the fake Closure's __invoke */
    1288           3 :                                 RETVAL_BOOL(func->common.scope == zend_ce_closure
    1289             :                                         && zend_string_equals_literal(method_name, ZEND_INVOKE_FUNC_NAME));
    1290             : 
    1291             :                                 zend_string_release(lcname);
    1292           3 :                                 zend_string_release(func->common.function_name);
    1293           3 :                                 efree(func);
    1294           3 :                                 return;
    1295             :                         }
    1296             :                         zend_string_release(lcname);
    1297           0 :                         RETURN_TRUE;
    1298             :                 }
    1299             :         }
    1300             :         zend_string_release(lcname);
    1301          29 :         RETURN_FALSE;
    1302             : }
    1303             : /* }}} */
    1304             : 
    1305             : /* {{{ proto bool property_exists(mixed object_or_class, string property_name)
    1306             :    Checks if the object or class has a property */
    1307         128 : ZEND_FUNCTION(property_exists)
    1308             : {
    1309             :         zval *object;
    1310             :         zend_string *property;
    1311             :         zend_class_entry *ce;
    1312             :         zend_property_info *property_info;
    1313             :         zval property_z;
    1314             : 
    1315         128 :         if (zend_parse_parameters(ZEND_NUM_ARGS(), "zS", &object, &property) == FAILURE) {
    1316           4 :                 return;
    1317             :         }
    1318             : 
    1319         124 :         if (property == NULL) {
    1320           0 :                 RETURN_FALSE;
    1321             :         }
    1322             : 
    1323         248 :         if (Z_TYPE_P(object) == IS_STRING) {
    1324          68 :                 ce = zend_lookup_class(Z_STR_P(object));
    1325          68 :                 if (!ce) {
    1326           4 :                         RETURN_FALSE;
    1327             :                 }
    1328         112 :         } else if (Z_TYPE_P(object) == IS_OBJECT) {
    1329          50 :                 ce = Z_OBJCE_P(object);
    1330             :         } else {
    1331           6 :                 zend_error(E_WARNING, "First parameter must either be an object or the name of an existing class");
    1332           6 :                 RETURN_NULL();
    1333             :         }
    1334             : 
    1335         305 :         if ((property_info = zend_hash_find_ptr(&ce->properties_info, property)) != NULL
    1336          77 :                 && (property_info->flags & ZEND_ACC_SHADOW) == 0) {
    1337          70 :                 RETURN_TRUE;
    1338             :         }
    1339             : 
    1340          44 :         ZVAL_STR(&property_z, property);
    1341             : 
    1342         140 :         if (Z_TYPE_P(object) ==  IS_OBJECT &&
    1343          26 :                 Z_OBJ_HANDLER_P(object, has_property) &&
    1344          26 :                 Z_OBJ_HANDLER_P(object, has_property)(object, &property_z, 2, NULL)) {
    1345          11 :                 RETURN_TRUE;
    1346             :         }
    1347          33 :         RETURN_FALSE;
    1348             : }
    1349             : /* }}} */
    1350             : 
    1351             : /* {{{ proto bool class_exists(string classname [, bool autoload])
    1352             :    Checks if the class exists */
    1353         501 : ZEND_FUNCTION(class_exists)
    1354             : {
    1355             :         zend_string *class_name;
    1356             :         zend_string *lc_name;
    1357             :         zend_class_entry *ce;
    1358         501 :         zend_bool autoload = 1;
    1359             : 
    1360             : #ifndef FAST_ZPP
    1361             :         if (zend_parse_parameters(ZEND_NUM_ARGS(), "S|b", &class_name, &autoload) == FAILURE) {
    1362             :                 return;
    1363             :         }
    1364             : #else
    1365         501 :         ZEND_PARSE_PARAMETERS_START(1, 2)
    1366        1494 :                 Z_PARAM_STR(class_name)
    1367         490 :                 Z_PARAM_OPTIONAL
    1368         706 :                 Z_PARAM_BOOL(autoload)
    1369         501 :         ZEND_PARSE_PARAMETERS_END();
    1370             : #endif
    1371             : 
    1372         484 :         if (!autoload) {
    1373          54 :                 if (class_name->val[0] == '\\') {
    1374             :                         /* Ignore leading "\" */
    1375           0 :                         lc_name = zend_string_alloc(class_name->len - 1, 0);
    1376           0 :                         zend_str_tolower_copy(lc_name->val, class_name->val + 1, class_name->len - 1);
    1377             :                 } else {
    1378          54 :                         lc_name = zend_string_tolower(class_name);
    1379             :                 }
    1380             : 
    1381         108 :                 ce = zend_hash_find_ptr(EG(class_table), lc_name);
    1382             :                 zend_string_release(lc_name);
    1383             :         } else {
    1384         430 :                 ce = zend_lookup_class(class_name);
    1385             :         }
    1386             : 
    1387         484 :         if (ce) {
    1388         386 :                 RETURN_BOOL((ce->ce_flags & (ZEND_ACC_INTERFACE | ZEND_ACC_TRAIT)) == 0);
    1389             :         } else {
    1390          98 :                 RETURN_FALSE;
    1391             :         }
    1392             : }
    1393             : /* }}} */
    1394             : 
    1395             : /* {{{ proto bool interface_exists(string classname [, bool autoload])
    1396             :    Checks if the class exists */
    1397         106 : ZEND_FUNCTION(interface_exists)
    1398             : {
    1399             :         zend_string *iface_name, *lc_name;
    1400             :         zend_class_entry *ce;
    1401         106 :         zend_bool autoload = 1;
    1402             : 
    1403             : #ifndef FAST_ZPP
    1404             :         if (zend_parse_parameters(ZEND_NUM_ARGS(), "S|b", &iface_name, &autoload) == FAILURE) {
    1405             :                 return;
    1406             :         }
    1407             : #else
    1408         106 :         ZEND_PARSE_PARAMETERS_START(1, 2)
    1409         309 :                 Z_PARAM_STR(iface_name)
    1410          96 :                 Z_PARAM_OPTIONAL
    1411         212 :                 Z_PARAM_BOOL(autoload)
    1412         106 :         ZEND_PARSE_PARAMETERS_END();
    1413             : #endif
    1414             : 
    1415          90 :         if (!autoload) {
    1416          17 :                 if (iface_name->val[0] == '\\') {
    1417             :                         /* Ignore leading "\" */
    1418           0 :                         lc_name = zend_string_alloc(iface_name->len - 1, 0);
    1419           0 :                         zend_str_tolower_copy(lc_name->val, iface_name->val + 1, iface_name->len - 1);
    1420             :                 } else {
    1421          17 :                         lc_name = zend_string_tolower(iface_name);
    1422             :                 }
    1423          34 :                 ce = zend_hash_find_ptr(EG(class_table), lc_name);
    1424             :                 zend_string_release(lc_name);
    1425          17 :                 RETURN_BOOL(ce && ce->ce_flags & ZEND_ACC_INTERFACE);
    1426             :         }
    1427             : 
    1428          73 :         ce = zend_lookup_class(iface_name);
    1429          73 :         if (ce) {
    1430          34 :                 RETURN_BOOL((ce->ce_flags & ZEND_ACC_INTERFACE) > 0);
    1431             :         } else {
    1432          39 :                 RETURN_FALSE;
    1433             :         }
    1434             : }
    1435             : /* }}} */
    1436             : 
    1437             : /* {{{ proto bool trait_exists(string traitname [, bool autoload])
    1438             :  Checks if the trait exists */
    1439          73 : ZEND_FUNCTION(trait_exists)
    1440             : {
    1441             :         zend_string *trait_name, *lc_name;
    1442             :         zend_class_entry *ce;
    1443          73 :         zend_bool autoload = 1;
    1444             : 
    1445             : #ifndef FAST_ZPP
    1446             :         if (zend_parse_parameters(ZEND_NUM_ARGS(), "S|b", &trait_name, &autoload) == FAILURE) {
    1447             :                 return;
    1448             :         }
    1449             : #else
    1450          73 :         ZEND_PARSE_PARAMETERS_START(1, 2)
    1451         213 :                 Z_PARAM_STR(trait_name)
    1452          64 :                 Z_PARAM_OPTIONAL
    1453         164 :                 Z_PARAM_BOOL(autoload)
    1454          73 :         ZEND_PARSE_PARAMETERS_END();
    1455             : #endif
    1456             : 
    1457          58 :         if (!autoload) {
    1458          11 :                 if (trait_name->val[0] == '\\') {
    1459             :                         /* Ignore leading "\" */
    1460           0 :                         lc_name = zend_string_alloc(trait_name->len - 1, 0);
    1461           0 :                         zend_str_tolower_copy(lc_name->val, trait_name->val + 1, trait_name->len - 1);
    1462             :                 } else {
    1463          11 :                         lc_name = zend_string_tolower(trait_name);
    1464             :                 }
    1465             : 
    1466          22 :                 ce = zend_hash_find_ptr(EG(class_table), lc_name);
    1467             :                 zend_string_release(lc_name);
    1468             :         } else {
    1469          47 :                 ce = zend_lookup_class(trait_name);
    1470             :         }
    1471             : 
    1472          58 :         if (ce) {
    1473          12 :                 RETURN_BOOL((ce->ce_flags & ZEND_ACC_TRAIT) != 0);
    1474             :         } else {
    1475          46 :                 RETURN_FALSE;
    1476             :         }
    1477             : }
    1478             : /* }}} */
    1479             : 
    1480             : /* {{{ proto bool function_exists(string function_name)
    1481             :    Checks if the function exists */
    1482        4399 : ZEND_FUNCTION(function_exists)
    1483             : {
    1484             :         zend_string *name;
    1485             :         zend_function *func;
    1486             :         zend_string *lcname;
    1487             : 
    1488             : #ifndef FAST_ZPP
    1489             :         if (zend_parse_parameters(ZEND_NUM_ARGS(), "S", &name) == FAILURE) {
    1490             :                 return;
    1491             :         }
    1492             : #else
    1493        4399 :         ZEND_PARSE_PARAMETERS_START(1, 1)
    1494       13191 :                 Z_PARAM_STR(name)
    1495        4399 :         ZEND_PARSE_PARAMETERS_END();
    1496             : #endif
    1497             : 
    1498        4393 :         if (name->val[0] == '\\') {
    1499             :                 /* Ignore leading "\" */
    1500           2 :                 lcname = zend_string_alloc(name->len - 1, 0);
    1501           1 :                 zend_str_tolower_copy(lcname->val, name->val + 1, name->len - 1);
    1502             :         } else {
    1503        4392 :                 lcname = zend_string_tolower(name);
    1504             :         }
    1505             : 
    1506        8786 :         func = zend_hash_find_ptr(EG(function_table), lcname);
    1507             :         zend_string_release(lcname);
    1508             : 
    1509             :         /*
    1510             :          * A bit of a hack, but not a bad one: we see if the handler of the function
    1511             :          * is actually one that displays "function is disabled" message.
    1512             :          */
    1513        4393 :         RETURN_BOOL(func && (func->type != ZEND_INTERNAL_FUNCTION ||
    1514             :                 func->internal_function.handler != zif_display_disabled_function));
    1515             : }
    1516             : /* }}} */
    1517             : 
    1518             : /* {{{ proto bool class_alias(string user_class_name , string alias_name [, bool autoload])
    1519             :    Creates an alias for user defined class */
    1520          28 : ZEND_FUNCTION(class_alias)
    1521             : {
    1522             :         zend_string *class_name;
    1523             :         char *alias_name;
    1524             :         zend_class_entry *ce;
    1525             :         size_t alias_name_len;
    1526          28 :         zend_bool autoload = 1;
    1527             : 
    1528          28 :         if (zend_parse_parameters(ZEND_NUM_ARGS(), "Ss|b", &class_name, &alias_name, &alias_name_len, &autoload) == FAILURE) {
    1529           0 :                 return;
    1530             :         }
    1531             : 
    1532          28 :         ce = zend_lookup_class_ex(class_name, NULL, autoload);
    1533             : 
    1534          28 :         if (ce) {
    1535          27 :                 if (ce->type == ZEND_USER_CLASS) {
    1536          26 :                         if (zend_register_class_alias_ex(alias_name, alias_name_len, ce) == SUCCESS) {
    1537          22 :                                 RETURN_TRUE;
    1538             :                         } else {
    1539           4 :                                 zend_error(E_WARNING, "Cannot redeclare class %s", alias_name);
    1540           4 :                                 RETURN_FALSE;
    1541             :                         }
    1542             :                 } else {
    1543           1 :                         zend_error(E_WARNING, "First argument of class_alias() must be a name of user defined class");
    1544           1 :                         RETURN_FALSE;
    1545             :                 }
    1546             :         } else {
    1547           1 :                 zend_error(E_WARNING, "Class '%s' not found", class_name->val);
    1548           1 :                 RETURN_FALSE;
    1549             :         }
    1550             : }
    1551             : /* }}} */
    1552             : 
    1553             : #if ZEND_DEBUG
    1554             : /* {{{ proto void leak(int num_bytes=3)
    1555             :    Cause an intentional memory leak, for testing/debugging purposes */
    1556             : ZEND_FUNCTION(leak)
    1557             : {
    1558             :         zend_long leakbytes=3;
    1559             : 
    1560             :         if (zend_parse_parameters(ZEND_NUM_ARGS(), "|l", &leakbytes) == FAILURE) {
    1561             :                 return;
    1562             :         }
    1563             : 
    1564             :         emalloc(leakbytes);
    1565             : }
    1566             : /* }}} */
    1567             : 
    1568             : /* {{{ proto leak_variable(mixed variable [, bool leak_data]) */
    1569             : ZEND_FUNCTION(leak_variable)
    1570             : {
    1571             :         zval *zv;
    1572             :         zend_bool leak_data = 0;
    1573             : 
    1574             :         if (zend_parse_parameters(ZEND_NUM_ARGS(), "z|b", &zv, &leak_data) == FAILURE) {
    1575             :                 return;
    1576             :         }
    1577             : 
    1578             :         if (!leak_data) {
    1579             :                 Z_ADDREF_P(zv);
    1580             :         } else if (Z_TYPE_P(zv) == IS_RESOURCE) {
    1581             :                 Z_ADDREF_P(zv);
    1582             :         } else if (Z_TYPE_P(zv) == IS_OBJECT) {
    1583             :                 Z_ADDREF_P(zv);
    1584             :         } else {
    1585             :                 zend_error(E_WARNING, "Leaking non-zval data is only applicable to resources and objects");
    1586             :         }
    1587             : }
    1588             : /* }}} */
    1589             : 
    1590             : 
    1591             : #ifdef ZEND_TEST_EXCEPTIONS
    1592             : ZEND_FUNCTION(crash)
    1593             : {
    1594             :         char *nowhere=NULL;
    1595             : 
    1596             :         memcpy(nowhere, "something", sizeof("something"));
    1597             : }
    1598             : #endif
    1599             : 
    1600             : #endif /* ZEND_DEBUG */
    1601             : 
    1602             : /* {{{ proto array get_included_files(void)
    1603             :    Returns an array with the file names that were include_once()'d */
    1604          39 : ZEND_FUNCTION(get_included_files)
    1605             : {
    1606             :         zend_string *entry;
    1607             : 
    1608          39 :         if (zend_parse_parameters_none() == FAILURE) {
    1609           3 :                 return;
    1610             :         }
    1611             : 
    1612          36 :         array_init(return_value);
    1613         178 :         ZEND_HASH_FOREACH_STR_KEY(&EG(included_files), entry) {
    1614          71 :                 if (entry) {
    1615          71 :                         add_next_index_str(return_value, zend_string_copy(entry));
    1616             :                 }
    1617             :         } ZEND_HASH_FOREACH_END();
    1618             : }
    1619             : /* }}} */
    1620             : 
    1621             : /* {{{ proto void trigger_error(string message [, int error_type])
    1622             :    Generates a user-level error/warning/notice message */
    1623          24 : ZEND_FUNCTION(trigger_error)
    1624             : {
    1625          24 :         zend_long error_type = E_USER_NOTICE;
    1626             :         char *message;
    1627             :         size_t message_len;
    1628             : 
    1629          24 :         if (zend_parse_parameters(ZEND_NUM_ARGS(), "s|l", &message, &message_len, &error_type) == FAILURE) {
    1630           2 :                 return;
    1631             :         }
    1632             : 
    1633          22 :         switch (error_type) {
    1634             :                 case E_USER_ERROR:
    1635             :                 case E_USER_WARNING:
    1636             :                 case E_USER_NOTICE:
    1637             :                 case E_USER_DEPRECATED:
    1638          20 :                         break;
    1639             :                 default:
    1640           2 :                         zend_error(E_WARNING, "Invalid error type specified");
    1641           2 :                         RETURN_FALSE;
    1642             :                         break;
    1643             :         }
    1644             : 
    1645          20 :         zend_error((int)error_type, "%s", message);
    1646          19 :         RETURN_TRUE;
    1647             : }
    1648             : /* }}} */
    1649             : 
    1650             : /* {{{ proto string set_error_handler(string error_handler [, int error_types])
    1651             :    Sets a user-defined error handler function.  Returns the previously defined error handler, or false on error */
    1652         280 : ZEND_FUNCTION(set_error_handler)
    1653             : {
    1654             :         zval *error_handler;
    1655         280 :         zend_string *error_handler_name = NULL;
    1656         280 :         zend_long error_type = E_ALL;
    1657             : 
    1658         280 :         if (zend_parse_parameters(ZEND_NUM_ARGS(), "z|l", &error_handler, &error_type) == FAILURE) {
    1659           0 :                 return;
    1660             :         }
    1661             : 
    1662         560 :         if (Z_TYPE_P(error_handler) != IS_NULL) { /* NULL == unset */
    1663         279 :                 if (!zend_is_callable(error_handler, 0, &error_handler_name)) {
    1664           0 :                         zend_error(E_WARNING, "%s() expects the argument (%s) to be a valid callback",
    1665           0 :                                            get_active_function_name(), error_handler_name?error_handler_name->val:"unknown");
    1666           0 :                         zend_string_release(error_handler_name);
    1667           0 :                         return;
    1668             :                 }
    1669         279 :                 zend_string_release(error_handler_name);
    1670             :         }
    1671             : 
    1672         280 :         if (Z_TYPE(EG(user_error_handler)) != IS_UNDEF) {
    1673           8 :                 RETVAL_ZVAL(&EG(user_error_handler), 1, 0);
    1674             : 
    1675           4 :                 zend_stack_push(&EG(user_error_handlers_error_reporting), &EG(user_error_handler_error_reporting));
    1676           4 :                 zend_stack_push(&EG(user_error_handlers), &EG(user_error_handler));
    1677             :         }
    1678             : 
    1679         560 :         if (Z_TYPE_P(error_handler) == IS_NULL) { /* unset user-defined handler */
    1680           1 :                 ZVAL_UNDEF(&EG(user_error_handler));
    1681           1 :                 return;
    1682             :         }
    1683             : 
    1684         279 :         ZVAL_DUP(&EG(user_error_handler), error_handler);
    1685         279 :         EG(user_error_handler_error_reporting) = (int)error_type;
    1686             : }
    1687             : /* }}} */
    1688             : 
    1689             : /* {{{ proto void restore_error_handler(void)
    1690             :    Restores the previously defined error handler function */
    1691           2 : ZEND_FUNCTION(restore_error_handler)
    1692             : {
    1693           2 :         if (Z_TYPE(EG(user_error_handler)) != IS_UNDEF) {
    1694             :                 zval zeh;
    1695             : 
    1696           2 :                 ZVAL_COPY_VALUE(&zeh, &EG(user_error_handler));
    1697           2 :                 ZVAL_UNDEF(&EG(user_error_handler));
    1698           2 :                 zval_ptr_dtor(&zeh);
    1699             :         }
    1700             : 
    1701           2 :         if (zend_stack_is_empty(&EG(user_error_handlers))) {
    1702           2 :                 ZVAL_UNDEF(&EG(user_error_handler));
    1703             :         } else {
    1704             :                 zval *tmp;
    1705           0 :                 EG(user_error_handler_error_reporting) = zend_stack_int_top(&EG(user_error_handlers_error_reporting));
    1706           0 :                 zend_stack_del_top(&EG(user_error_handlers_error_reporting));
    1707           0 :                 tmp = zend_stack_top(&EG(user_error_handlers));
    1708           0 :                 ZVAL_COPY_VALUE(&EG(user_error_handler), tmp);
    1709           0 :                 zend_stack_del_top(&EG(user_error_handlers));
    1710             :         }
    1711           2 :         RETURN_TRUE;
    1712             : }
    1713             : /* }}} */
    1714             : 
    1715             : /* {{{ proto string set_exception_handler(callable exception_handler)
    1716             :    Sets a user-defined exception handler function.  Returns the previously defined exception handler, or false on error */
    1717          19 : ZEND_FUNCTION(set_exception_handler)
    1718             : {
    1719             :         zval *exception_handler;
    1720          19 :         zend_string *exception_handler_name = NULL;
    1721             : 
    1722          19 :         if (zend_parse_parameters(ZEND_NUM_ARGS(), "z", &exception_handler) == FAILURE) {
    1723           2 :                 return;
    1724             :         }
    1725             : 
    1726          34 :         if (Z_TYPE_P(exception_handler) != IS_NULL) { /* NULL == unset */
    1727          16 :                 if (!zend_is_callable(exception_handler, 0, &exception_handler_name)) {
    1728           4 :                         zend_error(E_WARNING, "%s() expects the argument (%s) to be a valid callback",
    1729           4 :                                            get_active_function_name(), exception_handler_name?exception_handler_name->val:"unknown");
    1730           2 :                         zend_string_release(exception_handler_name);
    1731           2 :                         return;
    1732             :                 }
    1733          14 :                 zend_string_release(exception_handler_name);
    1734             :         }
    1735             : 
    1736          15 :         if (Z_TYPE(EG(user_exception_handler)) != IS_UNDEF) {
    1737           6 :                 RETVAL_ZVAL(&EG(user_exception_handler), 1, 0);
    1738             : 
    1739           3 :                 zend_stack_push(&EG(user_exception_handlers), &EG(user_exception_handler));
    1740             :         }
    1741             : 
    1742          30 :         if (Z_TYPE_P(exception_handler) == IS_NULL) { /* unset user-defined handler */
    1743           1 :                 ZVAL_UNDEF(&EG(user_exception_handler));
    1744           1 :                 return;
    1745             :         }
    1746             : 
    1747          14 :         ZVAL_DUP(&EG(user_exception_handler), exception_handler);
    1748             : }
    1749             : /* }}} */
    1750             : 
    1751             : /* {{{ proto void restore_exception_handler(void)
    1752             :    Restores the previously defined exception handler function */
    1753           1 : ZEND_FUNCTION(restore_exception_handler)
    1754             : {
    1755           1 :         if (Z_TYPE(EG(user_exception_handler)) != IS_UNDEF) {
    1756           1 :                 zval_ptr_dtor(&EG(user_exception_handler));
    1757             :         }
    1758           1 :         if (zend_stack_is_empty(&EG(user_exception_handlers))) {
    1759           0 :                 ZVAL_UNDEF(&EG(user_exception_handler));
    1760             :         } else {
    1761           1 :                 zval *tmp = zend_stack_top(&EG(user_exception_handlers));
    1762           1 :                 ZVAL_COPY_VALUE(&EG(user_exception_handler), tmp);
    1763           1 :                 zend_stack_del_top(&EG(user_exception_handlers));
    1764             :         }
    1765           1 :         RETURN_TRUE;
    1766             : }
    1767             : /* }}} */
    1768             : 
    1769        5104 : static int copy_class_or_interface_name(zval *el, int num_args, va_list args, zend_hash_key *hash_key) /* {{{ */
    1770             : {
    1771        5104 :         zend_class_entry *ce = (zend_class_entry *)Z_PTR_P(el);
    1772        5104 :         zval *array = va_arg(args, zval *);
    1773        5104 :         uint32_t mask = va_arg(args, uint32_t);
    1774        5104 :         uint32_t comply = va_arg(args, uint32_t);
    1775        5104 :         uint32_t comply_mask = (comply)? mask:0;
    1776             : 
    1777       10204 :         if ((hash_key->key && hash_key->key->val[0] != 0)
    1778        5100 :                 && (comply_mask == (ce->ce_flags & mask))) {
    1779        1795 :                 if (ce->refcount > 1 &&
    1780           2 :                     !same_name(hash_key->key, ce->name)) {
    1781           2 :                         add_next_index_str(array, zend_string_copy(hash_key->key));
    1782             :                 } else {
    1783        3582 :                         add_next_index_str(array, zend_string_copy(ce->name));
    1784             :                 }
    1785             :         }
    1786        5104 :         return ZEND_HASH_APPLY_KEEP;
    1787             : }
    1788             : /* }}} */
    1789             : 
    1790             : /* {{{ proto array get_declared_traits()
    1791             :    Returns an array of all declared traits. */
    1792          11 : ZEND_FUNCTION(get_declared_traits)
    1793             : {
    1794          11 :         uint32_t mask = ZEND_ACC_TRAIT;
    1795          11 :         uint32_t comply = 1;
    1796             : 
    1797          11 :         if (zend_parse_parameters_none() == FAILURE) {
    1798           1 :                 return;
    1799             :         }
    1800             : 
    1801          10 :         array_init(return_value);
    1802          10 :         zend_hash_apply_with_arguments(EG(class_table), copy_class_or_interface_name, 3, return_value, mask, comply);
    1803             : }
    1804             : /* }}} */
    1805             : 
    1806             : /* {{{ proto array get_declared_classes()
    1807             :    Returns an array of all declared classes. */
    1808          11 : ZEND_FUNCTION(get_declared_classes)
    1809             : {
    1810          11 :         uint32_t mask = ZEND_ACC_INTERFACE | ZEND_ACC_TRAIT;
    1811          11 :         uint32_t comply = 0;
    1812             : 
    1813          11 :         if (zend_parse_parameters_none() == FAILURE) {
    1814           1 :                 return;
    1815             :         }
    1816             : 
    1817          10 :         array_init(return_value);
    1818          10 :         zend_hash_apply_with_arguments(EG(class_table), copy_class_or_interface_name, 3, return_value, mask, comply);
    1819             : }
    1820             : /* }}} */
    1821             : 
    1822             : /* {{{ proto array get_declared_interfaces()
    1823             :    Returns an array of all declared interfaces. */
    1824          10 : ZEND_FUNCTION(get_declared_interfaces)
    1825             : {
    1826          10 :         uint32_t mask = ZEND_ACC_INTERFACE;
    1827          10 :         uint32_t comply = 1;
    1828             : 
    1829          10 :         if (zend_parse_parameters_none() == FAILURE) {
    1830           2 :                 return;
    1831             :         }
    1832             : 
    1833           8 :         array_init(return_value);
    1834           8 :         zend_hash_apply_with_arguments(EG(class_table), copy_class_or_interface_name, 3, return_value, mask, comply);
    1835             : }
    1836             : /* }}} */
    1837             : 
    1838        8557 : static int copy_function_name(zval *zv, int num_args, va_list args, zend_hash_key *hash_key) /* {{{ */
    1839             : {
    1840        8557 :         zend_function *func = Z_PTR_P(zv);
    1841        8557 :         zval *internal_ar = va_arg(args, zval *),
    1842        8557 :              *user_ar     = va_arg(args, zval *);
    1843             : 
    1844        8557 :         if (hash_key->key == NULL || hash_key->key->val[0] == 0) {
    1845           0 :                 return 0;
    1846             :         }
    1847             : 
    1848        8557 :         if (func->type == ZEND_INTERNAL_FUNCTION) {
    1849       17096 :                 add_next_index_str(internal_ar, zend_string_copy(hash_key->key));
    1850           9 :         } else if (func->type == ZEND_USER_FUNCTION) {
    1851          18 :                 add_next_index_str(user_ar, zend_string_copy(hash_key->key));
    1852             :         }
    1853             : 
    1854        8557 :         return 0;
    1855             : }
    1856             : /* }}} */
    1857             : 
    1858             : /* {{{ proto array get_defined_functions(void)
    1859             :    Returns an array of all defined functions */
    1860           6 : ZEND_FUNCTION(get_defined_functions)
    1861             : {
    1862             :         zval internal, user;
    1863             : 
    1864           6 :         if (zend_parse_parameters_none() == FAILURE) {
    1865           2 :                 return;
    1866             :         }
    1867             : 
    1868           4 :         array_init(&internal);
    1869           4 :         array_init(&user);
    1870           4 :         array_init(return_value);
    1871             : 
    1872           4 :         zend_hash_apply_with_arguments(EG(function_table), copy_function_name, 2, &internal, &user);
    1873             : 
    1874           4 :         zend_hash_str_add_new(Z_ARRVAL_P(return_value), "internal", sizeof("internal")-1, &internal);
    1875           4 :         zend_hash_str_add_new(Z_ARRVAL_P(return_value), "user", sizeof("user")-1, &user);
    1876             : }
    1877             : /* }}} */
    1878             : 
    1879             : /* {{{ proto array get_defined_vars(void)
    1880             :    Returns an associative array of names and values of all currently defined variable names (variables in the current scope) */
    1881          18 : ZEND_FUNCTION(get_defined_vars)
    1882             : {
    1883          18 :         zend_array *symbol_table = zend_rebuild_symbol_table();
    1884             : 
    1885          18 :         ZVAL_ARR(return_value, zend_array_dup(symbol_table));
    1886          18 : }
    1887             : /* }}} */
    1888             : 
    1889             : #define LAMBDA_TEMP_FUNCNAME    "__lambda_func"
    1890             : /* {{{ proto string create_function(string args, string code)
    1891             :    Creates an anonymous function, and returns its name (funny, eh?) */
    1892          55 : ZEND_FUNCTION(create_function)
    1893             : {
    1894             :     zend_string *function_name;
    1895             :         char *eval_code, *function_args, *function_code;
    1896             :         size_t eval_code_length, function_args_len, function_code_len;
    1897             :         int retval;
    1898             :         char *eval_name;
    1899             : 
    1900          55 :         if (zend_parse_parameters(ZEND_NUM_ARGS(), "ss", &function_args, &function_args_len, &function_code, &function_code_len) == FAILURE) {
    1901           0 :                 return;
    1902             :         }
    1903             : 
    1904          55 :         eval_code = (char *) emalloc(sizeof("function " LAMBDA_TEMP_FUNCNAME)
    1905             :                         +function_args_len
    1906             :                         +2      /* for the args parentheses */
    1907             :                         +2      /* for the curly braces */
    1908             :                         +function_code_len);
    1909             : 
    1910          55 :         eval_code_length = sizeof("function " LAMBDA_TEMP_FUNCNAME "(") - 1;
    1911          55 :         memcpy(eval_code, "function " LAMBDA_TEMP_FUNCNAME "(", eval_code_length);
    1912             : 
    1913          55 :         memcpy(eval_code + eval_code_length, function_args, function_args_len);
    1914          55 :         eval_code_length += function_args_len;
    1915             : 
    1916          55 :         eval_code[eval_code_length++] = ')';
    1917          55 :         eval_code[eval_code_length++] = '{';
    1918             : 
    1919          55 :         memcpy(eval_code + eval_code_length, function_code, function_code_len);
    1920          55 :         eval_code_length += function_code_len;
    1921             : 
    1922          55 :         eval_code[eval_code_length++] = '}';
    1923          55 :         eval_code[eval_code_length] = '\0';
    1924             : 
    1925          55 :         eval_name = zend_make_compiled_string_description("runtime-created function");
    1926          55 :         retval = zend_eval_stringl(eval_code, eval_code_length, NULL, eval_name);
    1927          55 :         efree(eval_code);
    1928          55 :         efree(eval_name);
    1929             : 
    1930          55 :         if (retval==SUCCESS) {
    1931             :                 zend_op_array *func;
    1932             :                 HashTable *static_variables;
    1933             : 
    1934         106 :                 func = zend_hash_str_find_ptr(EG(function_table), LAMBDA_TEMP_FUNCNAME, sizeof(LAMBDA_TEMP_FUNCNAME)-1);
    1935          53 :                 if (!func) {
    1936           0 :                         zend_error(E_ERROR, "Unexpected inconsistency in create_function()");
    1937           0 :                         RETURN_FALSE;
    1938             :                 }
    1939          53 :                 (*func->refcount)++;
    1940          53 :                 static_variables = func->static_variables;
    1941          53 :                 func->static_variables = NULL;
    1942          53 :                 zend_hash_str_del(EG(function_table), LAMBDA_TEMP_FUNCNAME, sizeof(LAMBDA_TEMP_FUNCNAME)-1);
    1943          53 :                 func->static_variables = static_variables;
    1944             : 
    1945          53 :                 function_name = zend_string_alloc(sizeof("0lambda_")+MAX_LENGTH_OF_LONG, 0);
    1946          53 :                 function_name->val[0] = '\0';
    1947             : 
    1948             :                 do {
    1949          53 :                         function_name->len = snprintf(function_name->val + 1, sizeof("lambda_")+MAX_LENGTH_OF_LONG, "lambda_%d", ++EG(lambda_count)) + 1;
    1950         106 :                 } while (zend_hash_add_ptr(EG(function_table), function_name, func) == NULL);
    1951          53 :                 RETURN_STR(function_name);
    1952             :         } else {
    1953           2 :                 zend_hash_str_del(EG(function_table), LAMBDA_TEMP_FUNCNAME, sizeof(LAMBDA_TEMP_FUNCNAME)-1);
    1954           2 :                 RETURN_FALSE;
    1955             :         }
    1956             : }
    1957             : /* }}} */
    1958             : 
    1959             : #if ZEND_DEBUG
    1960             : ZEND_FUNCTION(zend_test_func)
    1961             : {
    1962             :         zval *arg1, *arg2;
    1963             : 
    1964             :         zend_get_parameters(ZEND_NUM_ARGS(), 2, &arg1, &arg2);
    1965             : }
    1966             : 
    1967             : ZEND_FUNCTION(zend_test_func2)
    1968             : {
    1969             :         zval *arg1, *arg2;
    1970             : 
    1971             :         zend_get_parameters(ZEND_NUM_ARGS(), 2, &arg1, &arg2);
    1972             : }
    1973             : 
    1974             : 
    1975             : #ifdef ZTS
    1976             : ZEND_FUNCTION(zend_thread_id)
    1977             : {
    1978             :         RETURN_LONG((zend_long)tsrm_thread_id());
    1979             : }
    1980             : #endif
    1981             : #endif
    1982             : 
    1983             : /* {{{ proto string get_resource_type(resource res)
    1984             :    Get the resource type name for a given resource */
    1985          77 : ZEND_FUNCTION(get_resource_type)
    1986             : {
    1987             :         const char *resource_type;
    1988             :         zval *z_resource_type;
    1989             : 
    1990          77 :         if (zend_parse_parameters(ZEND_NUM_ARGS(), "r", &z_resource_type) == FAILURE) {
    1991          12 :                 return;
    1992             :         }
    1993             : 
    1994          65 :         resource_type = zend_rsrc_list_get_rsrc_type(Z_RES_P(z_resource_type));
    1995          65 :         if (resource_type) {
    1996          80 :                 RETURN_STRING(resource_type);
    1997             :         } else {
    1998          50 :                 RETURN_STRING("Unknown");
    1999             :         }
    2000             : }
    2001             : /* }}} */
    2002             : 
    2003             : /* {{{ proto array get_resources([string resouce_type])
    2004             :    Get an array with all active resources */
    2005           4 : ZEND_FUNCTION(get_resources)
    2006             : {
    2007           4 :         zend_string *type = NULL;
    2008             :         zend_string *key;
    2009             :         zend_ulong index;
    2010             :         zval *val;
    2011             : 
    2012           4 :         if (zend_parse_parameters(ZEND_NUM_ARGS(), "|S", &type) == FAILURE) {
    2013           0 :                 return;
    2014             :         }
    2015             : 
    2016           4 :         if (!type) {
    2017           4 :                 array_init(return_value);
    2018          68 :                 ZEND_HASH_FOREACH_KEY_VAL(&EG(regular_list), index, key, val) {
    2019          24 :                         if (!key) {
    2020             :                                 Z_ADDREF_P(val);
    2021          24 :                                 zend_hash_index_add_new(Z_ARRVAL_P(return_value), index, val);
    2022             :                         }
    2023             :                 } ZEND_HASH_FOREACH_END();
    2024           0 :         } else if (zend_string_equals_literal(type, "Unknown")) {
    2025           0 :                 array_init(return_value);
    2026           0 :                 ZEND_HASH_FOREACH_KEY_VAL(&EG(regular_list), index, key, val) {
    2027           0 :                         if (!key && Z_RES_TYPE_P(val) <= 0) {
    2028             :                                 Z_ADDREF_P(val);
    2029           0 :                                 zend_hash_index_add_new(Z_ARRVAL_P(return_value), index, val);
    2030             :                         }
    2031             :                 } ZEND_HASH_FOREACH_END();
    2032             :         } else {
    2033           0 :                 int id = zend_fetch_list_dtor_id(type->val);
    2034             : 
    2035           0 :                 if (id <= 0) {
    2036           0 :                         zend_error(E_WARNING, "get_resources():  Unknown resource type '%s'", type->val);
    2037           0 :                         RETURN_FALSE;
    2038             :                 }
    2039             : 
    2040           0 :                 array_init(return_value);
    2041           0 :                 ZEND_HASH_FOREACH_KEY_VAL(&EG(regular_list), index, key, val) {
    2042           0 :                         if (!key && Z_RES_TYPE_P(val) == id) {
    2043             :                                 Z_ADDREF_P(val);
    2044           0 :                                 zend_hash_index_add_new(Z_ARRVAL_P(return_value), index, val);
    2045             :                         }
    2046             :                 } ZEND_HASH_FOREACH_END();
    2047             :         }
    2048             : }
    2049             : /* }}} */
    2050             : 
    2051         284 : static int add_extension_info(zval *item, void *arg) /* {{{ */
    2052             : {
    2053         284 :         zval *name_array = (zval *)arg;
    2054         284 :         zend_module_entry *module = (zend_module_entry*)Z_PTR_P(item);
    2055         284 :         add_next_index_string(name_array, module->name);
    2056         284 :         return 0;
    2057             : }
    2058             : /* }}} */
    2059             : 
    2060           2 : static int add_zendext_info(zend_extension *ext, void *arg) /* {{{ */
    2061             : {
    2062           2 :         zval *name_array = (zval *)arg;
    2063           2 :         add_next_index_string(name_array, ext->name);
    2064           2 :         return 0;
    2065             : }
    2066             : /* }}} */
    2067             : 
    2068       26789 : static int add_constant_info(zval *item, void *arg) /* {{{ */
    2069             : {
    2070       26789 :         zval *name_array = (zval *)arg;
    2071       26789 :         zend_constant *constant = (zend_constant*)Z_PTR_P(item);
    2072             :         zval const_val;
    2073             : 
    2074       26789 :         if (!constant->name) {
    2075             :                 /* skip special constants */
    2076           1 :                 return 0;
    2077             :         }
    2078             : 
    2079       26788 :         ZVAL_DUP(&const_val, &constant->value);
    2080       26788 :         zend_hash_add_new(Z_ARRVAL_P(name_array), constant->name, &const_val);
    2081       26788 :         return 0;
    2082             : }
    2083             : /* }}} */
    2084             : 
    2085             : /* {{{ proto array get_loaded_extensions([bool zend_extensions]) U
    2086             :    Return an array containing names of loaded extensions */
    2087           7 : ZEND_FUNCTION(get_loaded_extensions)
    2088             : {
    2089           7 :         zend_bool zendext = 0;
    2090             : 
    2091           7 :         if (zend_parse_parameters(ZEND_NUM_ARGS(), "|b", &zendext) == FAILURE) {
    2092           1 :                 return;
    2093             :         }
    2094             : 
    2095           6 :         array_init(return_value);
    2096             : 
    2097           6 :         if (zendext) {
    2098           2 :                 zend_llist_apply_with_argument(&zend_extensions, (llist_apply_with_arg_func_t)add_zendext_info, return_value);
    2099             :         } else {
    2100           4 :                 zend_hash_apply_with_argument(&module_registry, add_extension_info, return_value);
    2101             :         }
    2102             : }
    2103             : /* }}} */
    2104             : 
    2105             : /* {{{ proto array get_defined_constants([bool categorize])
    2106             :    Return an array containing the names and values of all defined constants */
    2107          39 : ZEND_FUNCTION(get_defined_constants)
    2108             : {
    2109          39 :         zend_bool categorize = 0;
    2110             : 
    2111          39 :         if (zend_parse_parameters(ZEND_NUM_ARGS(), "|b", &categorize) == FAILURE) {
    2112           2 :                 return;
    2113             :         }
    2114             : 
    2115          37 :         array_init(return_value);
    2116             : 
    2117          37 :         if (categorize) {
    2118             :                 zend_constant *val;
    2119             :                 int module_number;
    2120             :                 zval *modules, const_val;
    2121             :                 char **module_names;
    2122             :                 zend_module_entry *module;
    2123          26 :                 int i = 1;
    2124             : 
    2125          26 :                 modules = ecalloc(zend_hash_num_elements(&module_registry) + 2, sizeof(zval));
    2126          26 :                 module_names = emalloc((zend_hash_num_elements(&module_registry) + 2) * sizeof(char *));
    2127             : 
    2128          26 :                 module_names[0] = "internal";
    2129        3718 :                 ZEND_HASH_FOREACH_PTR(&module_registry, module) {
    2130        1846 :                         module_names[module->module_number] = (char *)module->name;
    2131        1846 :                         i++;
    2132             :                 } ZEND_HASH_FOREACH_END();
    2133          26 :                 module_names[i] = "user";
    2134             : 
    2135      126650 :                 ZEND_HASH_FOREACH_PTR(EG(zend_constants), val) {
    2136       63312 :                         if (!val->name) {
    2137             :                                 /* skip special constants */
    2138           1 :                                 continue;
    2139             :                         }
    2140             : 
    2141       63311 :                         if (val->module_number == PHP_USER_CONSTANT) {
    2142           1 :                                 module_number = i;
    2143       63310 :                         } else if (val->module_number > i || val->module_number < 0) {
    2144             :                                 /* should not happen */
    2145           0 :                                 continue;
    2146             :                         } else {
    2147       63310 :                                 module_number = val->module_number;
    2148             :                         }
    2149             : 
    2150      126622 :                         if (Z_TYPE(modules[module_number]) == IS_UNDEF) {
    2151        1119 :                                 array_init(&modules[module_number]);
    2152        1119 :                                 add_assoc_zval(return_value, module_names[module_number], &modules[module_number]);
    2153             :                         }
    2154             : 
    2155       63311 :                         ZVAL_DUP(&const_val, &val->value);
    2156       63311 :                         zend_hash_add_new(Z_ARRVAL(modules[module_number]), val->name, &const_val);
    2157             :                 } ZEND_HASH_FOREACH_END();
    2158             : 
    2159          26 :                 efree(module_names);
    2160          26 :                 efree(modules);
    2161             :         } else {
    2162          11 :                 zend_hash_apply_with_argument(EG(zend_constants), add_constant_info, return_value);
    2163             :         }
    2164             : }
    2165             : /* }}} */
    2166             : 
    2167        2947 : static void debug_backtrace_get_args(zend_execute_data *call, zval *arg_array) /* {{{ */
    2168             : {
    2169        2947 :         uint32_t num_args = ZEND_CALL_NUM_ARGS(call);
    2170             : 
    2171        2947 :         array_init_size(arg_array, num_args);
    2172        2947 :         if (num_args) {
    2173        2472 :                 uint32_t i = 0;
    2174        2472 :                 zval *p = ZEND_CALL_ARG(call, 1);
    2175             : 
    2176        2472 :                 zend_hash_real_init(Z_ARRVAL_P(arg_array), 1);
    2177        2472 :                 ZEND_HASH_FILL_PACKED(Z_ARRVAL_P(arg_array)) {
    2178        2472 :                         if (call->func->type == ZEND_USER_FUNCTION) {
    2179         566 :                                 uint32_t first_extra_arg = call->func->op_array.num_args;
    2180             : 
    2181         566 :                                 if (ZEND_CALL_NUM_ARGS(call) > first_extra_arg) {
    2182         138 :                                         while (i < first_extra_arg) {
    2183          54 :                                                 if (Z_OPT_REFCOUNTED_P(p)) Z_ADDREF_P(p);
    2184          54 :                                                 ZEND_HASH_FILL_ADD(p);
    2185          54 :                                                 zend_hash_next_index_insert_new(Z_ARRVAL_P(arg_array), p);
    2186          54 :                                                 p++;
    2187          54 :                                                 i++;
    2188             :                                         }
    2189          42 :                                         p = ZEND_CALL_VAR_NUM(call, call->func->op_array.last_var + call->func->op_array.T);
    2190             :                                 }
    2191             :                         }
    2192             : 
    2193       10221 :                         while (i < num_args) {
    2194        5277 :                                 if (Z_OPT_REFCOUNTED_P(p)) Z_ADDREF_P(p);
    2195        5277 :                                 ZEND_HASH_FILL_ADD(p);
    2196        5277 :                                 p++;
    2197        5277 :                                 i++;
    2198             :                         }
    2199        2472 :                 } ZEND_HASH_FILL_END();
    2200             :         }
    2201        2947 : }
    2202             : /* }}} */
    2203             : 
    2204          42 : void debug_print_backtrace_args(zval *arg_array) /* {{{ */
    2205             : {
    2206             :         zval *tmp;
    2207          42 :         int i = 0;
    2208             : 
    2209         144 :         ZEND_HASH_FOREACH_VAL(Z_ARRVAL_P(arg_array), tmp) {
    2210          51 :                 if (i++) {
    2211          29 :                         ZEND_PUTS(", ");
    2212             :                 }
    2213          51 :                 zend_print_flat_zval_r(tmp);
    2214             :         } ZEND_HASH_FOREACH_END();
    2215          42 : }
    2216             : /* }}} */
    2217             : 
    2218             : /* {{{ proto void debug_print_backtrace([int options[, int limit]]) */
    2219          28 : ZEND_FUNCTION(debug_print_backtrace)
    2220             : {
    2221             :         zend_execute_data *call, *ptr, *skip;
    2222             :         zend_object *object;
    2223          28 :         int lineno, frameno = 0;
    2224             :         zend_function *func;
    2225             :         const char *function_name;
    2226             :         const char *filename;
    2227          28 :         zend_string *class_name = NULL;
    2228             :         char *call_type;
    2229          28 :         const char *include_filename = NULL;
    2230             :         zval arg_array;
    2231          28 :         int indent = 0;
    2232          28 :         zend_long options = 0;
    2233          28 :         zend_long limit = 0;
    2234             : 
    2235          28 :         if (zend_parse_parameters(ZEND_NUM_ARGS(), "|ll", &options, &limit) == FAILURE) {
    2236           0 :                 return;
    2237             :         }
    2238             : 
    2239          28 :         ZVAL_UNDEF(&arg_array);
    2240          28 :         ptr = EX(prev_execute_data);
    2241             : 
    2242             :         /* skip debug_backtrace() */
    2243          28 :         call = ptr;
    2244          28 :         ptr = ptr->prev_execute_data;
    2245             : 
    2246         115 :         while (ptr && (limit == 0 || frameno < limit)) {
    2247          59 :                 frameno++;
    2248          59 :                 class_name = NULL;
    2249          59 :                 call_type = NULL;
    2250          59 :                 ZVAL_UNDEF(&arg_array);
    2251             : 
    2252          59 :                 skip = ptr;
    2253             :                 /* skip internal handler */
    2254          78 :                 if ((!skip->func || !ZEND_USER_CODE(skip->func->common.type)) &&
    2255           4 :                     skip->prev_execute_data &&
    2256           4 :                     skip->prev_execute_data->func &&
    2257           4 :                     ZEND_USER_CODE(skip->prev_execute_data->func->common.type) &&
    2258           4 :                     skip->prev_execute_data->opline->opcode != ZEND_DO_FCALL &&
    2259           3 :                     skip->prev_execute_data->opline->opcode != ZEND_INCLUDE_OR_EVAL) {
    2260           1 :                         skip = skip->prev_execute_data;
    2261             :                 }
    2262             : 
    2263         115 :                 if (skip->func && ZEND_USER_CODE(skip->func->common.type)) {
    2264          56 :                         filename = skip->func->op_array.filename->val;
    2265          56 :                         if (skip->opline->opcode == ZEND_HANDLE_EXCEPTION) {
    2266           0 :                                 if (EG(opline_before_exception)) {
    2267           0 :                                         lineno = EG(opline_before_exception)->lineno;
    2268             :                                 } else {
    2269           0 :                                         lineno = skip->func->op_array.line_end;
    2270             :                                 }
    2271             :                         } else {
    2272          56 :                                 lineno = skip->opline->lineno;
    2273             :                         }
    2274             :                 } else {
    2275           3 :                         filename = NULL;
    2276           3 :                         lineno = 0;
    2277             :                 }
    2278             : 
    2279             :                 /* $this may be passed into regular internal functions */
    2280          59 :                 object = Z_OBJ(call->This);
    2281          75 :                 if (object &&
    2282             :                         call &&
    2283          15 :                     call->func->type == ZEND_INTERNAL_FUNCTION &&
    2284           1 :                     !call->func->common.scope) {
    2285           0 :                         object = NULL;
    2286             :                 }
    2287             : 
    2288          59 :                 if (call->func) {
    2289          57 :                         func = call->func;
    2290         193 :                         function_name = (func->common.scope &&
    2291          29 :                                          func->common.scope->trait_aliases) ?
    2292           6 :                                 zend_resolve_method_name(
    2293             :                                         (object ? object->ce : func->common.scope), func)->val :
    2294          51 :                                 (func->common.function_name ?
    2295          50 :                                         func->common.function_name->val : NULL);
    2296             :                 } else {
    2297           2 :                         func = NULL;
    2298           2 :                         function_name = NULL;
    2299             :                 }
    2300             : 
    2301          59 :                 if (function_name) {
    2302          56 :                         if (object) {
    2303          15 :                                 if (func->common.scope) {
    2304          15 :                                         class_name = func->common.scope->name;
    2305             :                                 } else {
    2306           0 :                                         class_name = object->ce->name;
    2307             :                                 }
    2308             : 
    2309          15 :                                 call_type = "->";
    2310          41 :                         } else if (func->common.scope) {
    2311          14 :                                 class_name = func->common.scope->name;
    2312          14 :                                 call_type = "::";
    2313             :                         } else {
    2314          27 :                                 class_name = NULL;
    2315          27 :                                 call_type = NULL;
    2316             :                         }
    2317          56 :                         if (func->type != ZEND_EVAL_CODE) {
    2318          56 :                                 if ((options & DEBUG_BACKTRACE_IGNORE_ARGS) == 0) {
    2319          42 :                                         debug_backtrace_get_args(call, &arg_array);
    2320             :                                 }
    2321             :                         }
    2322             :                 } else {
    2323             :                         /* i know this is kinda ugly, but i'm trying to avoid extra cycles in the main execution loop */
    2324           3 :                         zend_bool build_filename_arg = 1;
    2325             : 
    2326           3 :                         if (!ptr->func || !ZEND_USER_CODE(ptr->func->common.type) || ptr->opline->opcode != ZEND_INCLUDE_OR_EVAL) {
    2327             :                                 /* can happen when calling eval from a custom sapi */
    2328           0 :                                 function_name = "unknown";
    2329           0 :                                 build_filename_arg = 0;
    2330             :                         } else
    2331           3 :                         switch (ptr->opline->extended_value) {
    2332             :                                 case ZEND_EVAL:
    2333           1 :                                         function_name = "eval";
    2334           1 :                                         build_filename_arg = 0;
    2335           1 :                                         break;
    2336             :                                 case ZEND_INCLUDE:
    2337           2 :                                         function_name = "include";
    2338           2 :                                         break;
    2339             :                                 case ZEND_REQUIRE:
    2340           0 :                                         function_name = "require";
    2341           0 :                                         break;
    2342             :                                 case ZEND_INCLUDE_ONCE:
    2343           0 :                                         function_name = "include_once";
    2344           0 :                                         break;
    2345             :                                 case ZEND_REQUIRE_ONCE:
    2346           0 :                                         function_name = "require_once";
    2347           0 :                                         break;
    2348             :                                 default:
    2349             :                                         /* this can actually happen if you use debug_backtrace() in your error_handler and
    2350             :                                          * you're in the top-scope */
    2351           0 :                                         function_name = "unknown";
    2352           0 :                                         build_filename_arg = 0;
    2353             :                                         break;
    2354             :                         }
    2355             : 
    2356           3 :                         if (build_filename_arg && include_filename) {
    2357           0 :                                 array_init(&arg_array);
    2358           0 :                                 add_next_index_string(&arg_array, (char*)include_filename);
    2359             :                         }
    2360           3 :                         call_type = NULL;
    2361             :                 }
    2362          59 :                 zend_printf("#%-2d ", indent);
    2363          59 :                 if (class_name) {
    2364          29 :                         ZEND_PUTS(class_name->val);
    2365          29 :                         ZEND_PUTS(call_type);
    2366             :                 }
    2367          59 :                 zend_printf("%s(", function_name);
    2368          59 :                 if (Z_TYPE(arg_array) != IS_UNDEF) {
    2369          42 :                         debug_print_backtrace_args(&arg_array);
    2370          42 :                         zval_ptr_dtor(&arg_array);
    2371             :                 }
    2372          59 :                 if (filename) {
    2373          56 :                         zend_printf(") called at [%s:%d]\n", filename, lineno);
    2374             :                 } else {
    2375           3 :                         zend_execute_data *prev_call = skip;
    2376           3 :                         zend_execute_data *prev = skip->prev_execute_data;
    2377             : 
    2378           6 :                         while (prev) {
    2379           7 :                                 if (prev_call &&
    2380           3 :                                     prev_call->func &&
    2381           1 :                                         !ZEND_USER_CODE(prev_call->func->common.type)) {
    2382           1 :                                         prev = NULL;
    2383           1 :                                         break;
    2384             :                                 }
    2385           2 :                                 if (prev->func && ZEND_USER_CODE(prev->func->common.type)) {
    2386           2 :                                         zend_printf(") called at [%s:%d]\n", prev->func->op_array.filename->val, prev->opline->lineno);
    2387           2 :                                         break;
    2388             :                                 }
    2389           0 :                                 prev_call = prev;
    2390           0 :                                 prev = prev->prev_execute_data;
    2391             :                         }
    2392           3 :                         if (!prev) {
    2393           1 :                                 ZEND_PUTS(")\n");
    2394             :                         }
    2395             :                 }
    2396          59 :                 include_filename = filename;
    2397          59 :                 call = skip;
    2398          59 :                 ptr = skip->prev_execute_data;
    2399          59 :                 ++indent;
    2400             :         }
    2401             : }
    2402             : 
    2403             : /* }}} */
    2404             : 
    2405        1760 : ZEND_API void zend_fetch_debug_backtrace(zval *return_value, int skip_last, int options, int limit) /* {{{ */
    2406             : {
    2407             :         zend_execute_data *call, *ptr, *skip;
    2408             :         zend_object *object;
    2409        1760 :         int lineno, frameno = 0;
    2410             :         zend_function *func;
    2411             :         const char *function_name;
    2412             :         const char *filename;
    2413        1760 :         const char *include_filename = NULL;
    2414             :         zval stack_frame;
    2415             : 
    2416        1760 :         call = NULL;
    2417        1760 :         ptr = EG(current_execute_data);
    2418        1760 :         if (!ptr->func || !ZEND_USER_CODE(ptr->func->common.type)) {
    2419        1308 :                 call = ptr;
    2420        1308 :                 ptr = ptr->prev_execute_data;
    2421             :         }
    2422             : 
    2423        1760 :         if (ptr) {
    2424        1760 :                 if (skip_last) {
    2425             :                         /* skip debug_backtrace() */
    2426          47 :                         call = ptr;
    2427          47 :                         ptr = ptr->prev_execute_data;
    2428             :                 } else {
    2429             :                         /* skip "new Exception()" */
    2430        1713 :                         if (ptr->func && ZEND_USER_CODE(ptr->func->common.type) && (ptr->opline->opcode == ZEND_NEW)) {
    2431         413 :                                 call = ptr;
    2432         413 :                                 ptr = ptr->prev_execute_data;
    2433             :                         }
    2434             :                 }
    2435             :         }
    2436        1760 :         if (!call) {
    2437          37 :                 call = ptr;
    2438          37 :                 ptr = ptr->prev_execute_data;
    2439             :         }
    2440             : 
    2441        1760 :         array_init(return_value);
    2442             : 
    2443        6553 :         while (ptr && (limit == 0 || frameno < limit)) {
    2444        3033 :                 frameno++;
    2445        3033 :                 array_init(&stack_frame);
    2446             : 
    2447        3033 :                 skip = ptr;
    2448             :                 /* skip internal handler */
    2449        6653 :                 if ((!skip->func || !ZEND_USER_CODE(skip->func->common.type)) &&
    2450         951 :                     skip->prev_execute_data &&
    2451         941 :                     skip->prev_execute_data->func &&
    2452         930 :                     ZEND_USER_CODE(skip->prev_execute_data->func->common.type) &&
    2453         667 :                     skip->prev_execute_data->opline->opcode != ZEND_DO_FCALL &&
    2454         131 :                     skip->prev_execute_data->opline->opcode != ZEND_INCLUDE_OR_EVAL) {
    2455         128 :                         skip = skip->prev_execute_data;
    2456             :                 }
    2457             : 
    2458        5243 :                 if (skip->func && ZEND_USER_CODE(skip->func->common.type)) {
    2459        2210 :                         filename = skip->func->op_array.filename->val;
    2460        2210 :                         if (skip->opline->opcode == ZEND_HANDLE_EXCEPTION) {
    2461           2 :                                 if (EG(opline_before_exception)) {
    2462           2 :                                         lineno = EG(opline_before_exception)->lineno;
    2463             :                                 } else {
    2464           0 :                                         lineno = skip->func->op_array.line_end;
    2465             :                                 }
    2466             :                         } else {
    2467        2208 :                                 lineno = skip->opline->lineno;
    2468             :                         }
    2469        2210 :                         add_assoc_string_ex(&stack_frame, "file", sizeof("file")-1, (char*)filename);
    2470        2210 :                         add_assoc_long_ex(&stack_frame, "line", sizeof("line")-1, lineno);
    2471             : 
    2472             :                         /* try to fetch args only if an FCALL was just made - elsewise we're in the middle of a function
    2473             :                          * and debug_baktrace() might have been called by the error_handler. in this case we don't
    2474             :                          * want to pop anything of the argument-stack */
    2475             :                 } else {
    2476         823 :                         zend_execute_data *prev_call = skip;
    2477         823 :                         zend_execute_data *prev = skip->prev_execute_data;
    2478             : 
    2479        1646 :                         while (prev) {
    2480        4056 :                                 if (prev_call &&
    2481         813 :                                     prev_call->func &&
    2482         810 :                                         !ZEND_USER_CODE(prev_call->func->common.type) &&
    2483         810 :                                         !(prev_call->func->common.type == ZEND_INTERNAL_FUNCTION &&
    2484         810 :                                                 (prev_call->func->common.fn_flags & ZEND_ACC_CALL_VIA_HANDLER))) {
    2485             :                                         break;
    2486             :                                 }
    2487         267 :                                 if (prev->func && ZEND_USER_CODE(prev->func->common.type)) {
    2488         534 :                                         add_assoc_str_ex(&stack_frame, "file", sizeof("file")-1, zend_string_copy(prev->func->op_array.filename));
    2489         267 :                                         add_assoc_long_ex(&stack_frame, "line", sizeof("line")-1, prev->opline->lineno);
    2490         267 :                                         break;
    2491             :                                 }
    2492           0 :                                 prev_call = prev;
    2493           0 :                                 prev = prev->prev_execute_data;
    2494             :                         }
    2495         823 :                         filename = NULL;
    2496             :                 }
    2497             : 
    2498             :                 /* $this may be passed into regular internal functions */
    2499        3033 :                 object = call ? Z_OBJ(call->This) : NULL;
    2500        9316 :                 if (object &&
    2501        2204 :                     call->func &&
    2502        2202 :                     call->func->type == ZEND_INTERNAL_FUNCTION &&
    2503        1877 :                     !call->func->common.scope) {
    2504           3 :                         object = NULL;
    2505             :                 }
    2506             : 
    2507        6063 :                 if (call && call->func) {
    2508        3030 :                         func = call->func;
    2509       11349 :                         function_name = (func->common.scope &&
    2510        2374 :                                          func->common.scope->trait_aliases) ?
    2511           2 :                                 zend_resolve_method_name(
    2512             :                                         (object ? object->ce : func->common.scope), func)->val :
    2513        3028 :                                 (func->common.function_name ?
    2514        2915 :                                         func->common.function_name->val : NULL);
    2515             :                 } else {
    2516           3 :                         func = NULL;
    2517           3 :                         function_name = NULL;
    2518             :                 }
    2519             : 
    2520        3033 :                 if (function_name) {
    2521        2917 :                         add_assoc_string_ex(&stack_frame, "function", sizeof("function")-1, (char*)function_name);
    2522             : 
    2523        2917 :                         if (object) {
    2524        2199 :                                 if (func->common.scope) {
    2525        4398 :                                         add_assoc_str_ex(&stack_frame, "class", sizeof("class")-1, zend_string_copy(func->common.scope->name));
    2526             :                                 } else {
    2527           0 :                                         add_assoc_str_ex(&stack_frame, "class", sizeof("class")-1, zend_string_copy(object->ce->name));
    2528             : 
    2529             :                                 }
    2530        2199 :                                 if ((options & DEBUG_BACKTRACE_PROVIDE_OBJECT) != 0) {
    2531             :                                         zval zv;
    2532          26 :                                         ZVAL_OBJ(&zv, object);
    2533          26 :                                         add_assoc_zval_ex(&stack_frame, "object", sizeof("object")-1, &zv);
    2534             :                                         Z_ADDREF(zv);
    2535             :                                 }
    2536             : 
    2537        2199 :                                 add_assoc_string_ex(&stack_frame, "type", sizeof("type")-1, "->");
    2538         718 :                         } else if (func->common.scope) {
    2539         350 :                                 add_assoc_str_ex(&stack_frame, "class", sizeof("class")-1, zend_string_copy(func->common.scope->name));
    2540         175 :                                 add_assoc_string_ex(&stack_frame, "type", sizeof("type")-1, "::");
    2541             :                         }
    2542             : 
    2543        5822 :                         if ((options & DEBUG_BACKTRACE_IGNORE_ARGS) == 0 &&
    2544        2905 :                                 func->type != ZEND_EVAL_CODE) {
    2545             :                                 zval args;
    2546             : 
    2547        2905 :                                 debug_backtrace_get_args(call, &args);
    2548        2905 :                                 add_assoc_zval_ex(&stack_frame, "args", sizeof("args")-1, &args);
    2549             :                         }
    2550             :                 } else {
    2551             :                         /* i know this is kinda ugly, but i'm trying to avoid extra cycles in the main execution loop */
    2552         116 :                         zend_bool build_filename_arg = 1;
    2553             : 
    2554         116 :                         if (!ptr->func || !ZEND_USER_CODE(ptr->func->common.type) || ptr->opline->opcode != ZEND_INCLUDE_OR_EVAL) {
    2555             :                                 /* can happen when calling eval from a custom sapi */
    2556           0 :                                 function_name = "unknown";
    2557           0 :                                 build_filename_arg = 0;
    2558             :                         } else
    2559         116 :                         switch (ptr->opline->extended_value) {
    2560             :                                 case ZEND_EVAL:
    2561          14 :                                         function_name = "eval";
    2562          14 :                                         build_filename_arg = 0;
    2563          14 :                                         break;
    2564             :                                 case ZEND_INCLUDE:
    2565          97 :                                         function_name = "include";
    2566          97 :                                         break;
    2567             :                                 case ZEND_REQUIRE:
    2568           5 :                                         function_name = "require";
    2569           5 :                                         break;
    2570             :                                 case ZEND_INCLUDE_ONCE:
    2571           0 :                                         function_name = "include_once";
    2572           0 :                                         break;
    2573             :                                 case ZEND_REQUIRE_ONCE:
    2574           0 :                                         function_name = "require_once";
    2575           0 :                                         break;
    2576             :                                 default:
    2577             :                                         /* this can actually happen if you use debug_backtrace() in your error_handler and
    2578             :                                          * you're in the top-scope */
    2579           0 :                                         function_name = "unknown";
    2580           0 :                                         build_filename_arg = 0;
    2581             :                                         break;
    2582             :                         }
    2583             : 
    2584         116 :                         if (build_filename_arg && include_filename) {
    2585             :                                 zval arg_array;
    2586             : 
    2587          98 :                                 array_init(&arg_array);
    2588             : 
    2589             :                                 /* include_filename always points to the last filename of the last last called-function.
    2590             :                                    if we have called include in the frame above - this is the file we have included.
    2591             :                                  */
    2592             : 
    2593          98 :                                 add_next_index_string(&arg_array, (char*)include_filename);
    2594          98 :                                 add_assoc_zval_ex(&stack_frame, "args", sizeof("args")-1, &arg_array);
    2595             :                         }
    2596             : 
    2597         116 :                         add_assoc_string_ex(&stack_frame, "function", sizeof("function")-1, (char*)function_name);
    2598             :                 }
    2599             : 
    2600        3033 :                 zend_hash_next_index_insert_new(Z_ARRVAL_P(return_value), &stack_frame);
    2601             : 
    2602        3033 :                 include_filename = filename;
    2603             : 
    2604        3033 :                 call = skip;
    2605        3033 :                 ptr = skip->prev_execute_data;
    2606             :         }
    2607        1760 : }
    2608             : /* }}} */
    2609             : 
    2610             : /* {{{ proto array debug_backtrace([int options[, int limit]])
    2611             :    Return backtrace as array */
    2612          45 : ZEND_FUNCTION(debug_backtrace)
    2613             : {
    2614          45 :         zend_long options = DEBUG_BACKTRACE_PROVIDE_OBJECT;
    2615          45 :         zend_long limit = 0;
    2616             : 
    2617          45 :         if (zend_parse_parameters(ZEND_NUM_ARGS(), "|ll", &options, &limit) == FAILURE) {
    2618           0 :                 return;
    2619             :         }
    2620             : 
    2621          45 :         zend_fetch_debug_backtrace(return_value, 1, options, limit);
    2622             : }
    2623             : /* }}} */
    2624             : 
    2625             : /* {{{ proto bool extension_loaded(string extension_name)
    2626             :    Returns true if the named extension is loaded */
    2627       18818 : ZEND_FUNCTION(extension_loaded)
    2628             : {
    2629             :         zend_string *extension_name;
    2630             :         zend_string *lcname;
    2631             : 
    2632       18818 :         if (zend_parse_parameters(ZEND_NUM_ARGS(), "S", &extension_name) == FAILURE) {
    2633           0 :                 return;
    2634             :         }
    2635             : 
    2636       18818 :         lcname = zend_string_tolower(extension_name);
    2637       18818 :         if (zend_hash_exists(&module_registry, lcname)) {
    2638       18812 :                 RETVAL_TRUE;
    2639             :         } else {
    2640           6 :                 RETVAL_FALSE;
    2641             :         }
    2642             :         zend_string_release(lcname);
    2643             : }
    2644             : /* }}} */
    2645             : 
    2646             : /* {{{ proto array get_extension_funcs(string extension_name)
    2647             :    Returns an array with the names of functions belonging to the named extension */
    2648          34 : ZEND_FUNCTION(get_extension_funcs)
    2649             : {
    2650             :         zend_string *extension_name;
    2651             :         zend_string *lcname;
    2652             :         int array;
    2653             :         zend_module_entry *module;
    2654             :         zend_function *zif;
    2655             : 
    2656          34 :         if (zend_parse_parameters(ZEND_NUM_ARGS(), "S", &extension_name) == FAILURE) {
    2657           7 :                 return;
    2658             :         }
    2659          27 :         if (strncasecmp(extension_name->val, "zend", sizeof("zend"))) {
    2660          25 :                 lcname = zend_string_tolower(extension_name);
    2661             :         } else {
    2662           2 :                 lcname = zend_string_init("core", sizeof("core")-1, 0);
    2663             :         }
    2664          27 :         module = zend_hash_find_ptr(&module_registry, lcname);
    2665             :         zend_string_release(lcname);
    2666          27 :         if (!module) {
    2667          20 :                 RETURN_FALSE;
    2668             :         }
    2669             : 
    2670           7 :         if (module->functions) {
    2671             :                 /* avoid BC break, if functions list is empty, will return an empty array */
    2672           7 :                 array_init(return_value);
    2673           7 :                 array = 1;
    2674             :         } else {
    2675           0 :                 array = 0;
    2676             :         }
    2677             : 
    2678       29945 :         ZEND_HASH_FOREACH_PTR(CG(function_table), zif) {
    2679       29923 :                 if (zif->common.type == ZEND_INTERNAL_FUNCTION
    2680       29923 :                         && zif->internal_function.module == module) {
    2681        2381 :                         if (!array) {
    2682           0 :                                 array_init(return_value);
    2683           0 :                                 array = 1;
    2684             :                         }
    2685        4762 :                         add_next_index_str(return_value, zend_string_copy(zif->common.function_name));
    2686             :                 }
    2687             :         } ZEND_HASH_FOREACH_END();
    2688             : 
    2689           7 :         if (!array) {
    2690           0 :                 RETURN_FALSE;
    2691             :         }
    2692             : }
    2693             : /* }}} */
    2694             : 
    2695             : /*
    2696             :  * Local variables:
    2697             :  * tab-width: 4
    2698             :  * c-basic-offset: 4
    2699             :  * indent-tabs-mode: t
    2700             :  * End:
    2701             :  */

Generated by: LCOV version 1.10

Generated at Tue, 14 Apr 2015 11:48:38 +0000 (3 days ago)

Copyright © 2005-2015 The PHP Group
All rights reserved.