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_execute.c (source / functions) Hit Total Coverage
Test: PHP Code Coverage Lines: 534 644 82.9 %
Date: 2014-08-17 Functions: 23 33 69.7 %
Legend: Lines: hit not hit

          Line data    Source code
       1             : /*
       2             :    +----------------------------------------------------------------------+
       3             :    | Zend Engine                                                          |
       4             :    +----------------------------------------------------------------------+
       5             :    | Copyright (c) 1998-2014 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             : #define ZEND_INTENSIVE_DEBUGGING 0
      23             : 
      24             : #include <stdio.h>
      25             : #include <signal.h>
      26             : 
      27             : #include "zend.h"
      28             : #include "zend_compile.h"
      29             : #include "zend_execute.h"
      30             : #include "zend_API.h"
      31             : #include "zend_ptr_stack.h"
      32             : #include "zend_constants.h"
      33             : #include "zend_extensions.h"
      34             : #include "zend_ini.h"
      35             : #include "zend_exceptions.h"
      36             : #include "zend_interfaces.h"
      37             : #include "zend_closures.h"
      38             : #include "zend_vm.h"
      39             : #include "zend_dtrace.h"
      40             : 
      41             : /* Virtual current working directory support */
      42             : #include "tsrm_virtual_cwd.h"
      43             : 
      44             : #define _CONST_CODE  0
      45             : #define _TMP_CODE    1
      46             : #define _VAR_CODE    2
      47             : #define _UNUSED_CODE 3
      48             : #define _CV_CODE     4
      49             : 
      50             : typedef int (*incdec_t)(zval *);
      51             : 
      52             : #define get_zval_ptr(op_type, node, Ts, should_free, type) _get_zval_ptr(op_type, node, Ts, should_free, type TSRMLS_CC)
      53             : #define get_zval_ptr_ptr(op_type, node, Ts, should_free, type) _get_zval_ptr_ptr(op_type, node, Ts, should_free, type TSRMLS_CC)
      54             : #define get_obj_zval_ptr(op_type, node, Ts, should_free, type) _get_obj_zval_ptr(op_type, node, Ts, should_free, type TSRMLS_CC)
      55             : #define get_obj_zval_ptr_ptr(op_type, node, Ts, should_free, type) _get_obj_zval_ptr_ptr(op_type, node, Ts, should_free, type TSRMLS_CC)
      56             : 
      57             : /* Prototypes */
      58             : static void zend_extension_statement_handler(const zend_extension *extension, zend_op_array *op_array TSRMLS_DC);
      59             : static void zend_extension_fcall_begin_handler(const zend_extension *extension, zend_op_array *op_array TSRMLS_DC);
      60             : static void zend_extension_fcall_end_handler(const zend_extension *extension, zend_op_array *op_array TSRMLS_DC);
      61             : 
      62             : #define RETURN_VALUE_USED(opline) (!((opline)->result_type & EXT_TYPE_UNUSED))
      63             : 
      64             : #define T(offset) (*(temp_variable *)((char *) Ts + offset))
      65             : #define CV(var)   CVs[var]
      66             : 
      67             : #define TEMP_VAR_STACK_LIMIT 2000
      68             : 
      69             : static zend_always_inline void zend_pzval_unlock_func(zval *z, zend_free_op *should_free, int unref TSRMLS_DC)
      70             : {
      71    33853304 :         if (!Z_DELREF_P(z)) {
      72             :                 Z_SET_REFCOUNT_P(z, 1);
      73             :                 Z_UNSET_ISREF_P(z);
      74    19034514 :                 should_free->var = z;
      75             : /*              should_free->is_var = 1; */
      76             :         } else {
      77    14818790 :                 should_free->var = 0;
      78    30088395 :                 if (unref && Z_ISREF_P(z) && Z_REFCOUNT_P(z) == 1) {
      79             :                         Z_UNSET_ISREF_P(z);
      80             :                 }
      81             :                 GC_ZVAL_CHECK_POSSIBLE_ROOT(z);
      82             :         }
      83             : }
      84             : 
      85             : static zend_always_inline void zend_pzval_unlock_free_func(zval *z TSRMLS_DC)
      86             : {
      87             :         if (!Z_DELREF_P(z)) {
      88             :                 if (z != &EG(uninitialized_zval)) {
      89             :                         GC_REMOVE_ZVAL_FROM_BUFFER(z);
      90             :                         zval_dtor(z);
      91             :                         efree(z);
      92             :                 }
      93             :         }
      94             : }
      95             : 
      96             : #undef zval_ptr_dtor
      97             : #define zval_ptr_dtor(pzv) i_zval_ptr_dtor(*(pzv)  ZEND_FILE_LINE_CC)
      98             : 
      99             : #define PZVAL_UNLOCK(z, f) zend_pzval_unlock_func(z, f, 1 TSRMLS_CC)
     100             : #define PZVAL_UNLOCK_EX(z, f, u) zend_pzval_unlock_func(z, f, u TSRMLS_CC)
     101             : #define PZVAL_UNLOCK_FREE(z) zend_pzval_unlock_free_func(z TSRMLS_CC)
     102             : #define PZVAL_LOCK(z) Z_ADDREF_P((z))
     103             : #define SELECTIVE_PZVAL_LOCK(pzv, opline)       if (RETURN_VALUE_USED(opline)) { PZVAL_LOCK(pzv); }
     104             : 
     105             : #define EXTRACT_ZVAL_PTR(t) do {                                                \
     106             :                 temp_variable *__t = (t);                                       \
     107             :                 if (__t->var.ptr_ptr) {                                              \
     108             :                         __t->var.ptr = *__t->var.ptr_ptr;         \
     109             :                         __t->var.ptr_ptr = &__t->var.ptr;             \
     110             :                         if (!PZVAL_IS_REF(__t->var.ptr) &&           \
     111             :                             Z_REFCOUNT_P(__t->var.ptr) > 2) {     \
     112             :                                 SEPARATE_ZVAL(__t->var.ptr_ptr);     \
     113             :                         }                                                                               \
     114             :                 }                                                                                       \
     115             :         } while (0)
     116             : 
     117             : #define AI_SET_PTR(t, val) do {                         \
     118             :                 temp_variable *__t = (t);                       \
     119             :                 __t->var.ptr = (val);                                \
     120             :                 __t->var.ptr_ptr = &__t->var.ptr;     \
     121             :         } while (0)
     122             : 
     123             : #define FREE_OP(should_free) \
     124             :         if (should_free.var) { \
     125             :                 if ((zend_uintptr_t)should_free.var & 1L) { \
     126             :                         zval_dtor((zval*)((zend_uintptr_t)should_free.var & ~1L)); \
     127             :                 } else { \
     128             :                         zval_ptr_dtor(&should_free.var); \
     129             :                 } \
     130             :         }
     131             : 
     132             : #define FREE_OP_IF_VAR(should_free) \
     133             :         if (should_free.var != NULL && (((zend_uintptr_t)should_free.var & 1L) == 0)) { \
     134             :                 zval_ptr_dtor(&should_free.var); \
     135             :         }
     136             : 
     137             : #define FREE_OP_VAR_PTR(should_free) \
     138             :         if (should_free.var) { \
     139             :                 zval_ptr_dtor(&should_free.var); \
     140             :         }
     141             : 
     142             : #define TMP_FREE(z) (zval*)(((zend_uintptr_t)(z)) | 1L)
     143             : 
     144             : #define IS_TMP_FREE(should_free) ((zend_uintptr_t)should_free.var & 1L)
     145             : 
     146             : #define MAKE_REAL_ZVAL_PTR(val) \
     147             :         do { \
     148             :                 zval *_tmp; \
     149             :                 ALLOC_ZVAL(_tmp); \
     150             :                 INIT_PZVAL_COPY(_tmp, (val)); \
     151             :                 (val) = _tmp; \
     152             :         } while (0)
     153             : 
     154             : /* End of zend_execute_locks.h */
     155             : 
     156             : #define CV_OF(i)     (EG(current_execute_data)->CVs[i])
     157             : #define CV_DEF_OF(i) (EG(active_op_array)->vars[i])
     158             : 
     159             : #define CTOR_CALL_BIT    0x1
     160             : #define CTOR_USED_BIT    0x2
     161             : 
     162             : #define IS_CTOR_CALL(ce) (((zend_uintptr_t)(ce)) & CTOR_CALL_BIT)
     163             : #define IS_CTOR_USED(ce) (((zend_uintptr_t)(ce)) & CTOR_USED_BIT)
     164             : 
     165             : #define ENCODE_CTOR(ce, used) \
     166             :         ((zend_class_entry*)(((zend_uintptr_t)(ce)) | CTOR_CALL_BIT | ((used) ? CTOR_USED_BIT : 0)))
     167             : #define DECODE_CTOR(ce) \
     168             :         ((zend_class_entry*)(((zend_uintptr_t)(ce)) & ~(CTOR_CALL_BIT|CTOR_USED_BIT)))
     169             : 
     170           0 : ZEND_API zval** zend_get_compiled_variable_value(const zend_execute_data *execute_data_ptr, zend_uint var)
     171             : {
     172           0 :         return execute_data_ptr->CVs[var];
     173             : }
     174             : 
     175             : static zend_always_inline zval *_get_zval_ptr_tmp(zend_uint var, const temp_variable *Ts, zend_free_op *should_free TSRMLS_DC)
     176             : {
     177    31899047 :         return should_free->var = &T(var).tmp_var;
     178             : }
     179             : 
     180             : static zend_always_inline zval *_get_zval_ptr_var(zend_uint var, const temp_variable *Ts, zend_free_op *should_free TSRMLS_DC)
     181             : {
     182    27564368 :         zval *ptr = T(var).var.ptr;
     183             : 
     184             :         PZVAL_UNLOCK(ptr, should_free);
     185    27564368 :         return ptr;
     186             : }
     187             : 
     188          10 : static zend_never_inline zval **_get_zval_cv_lookup(zval ***ptr, zend_uint var, int type TSRMLS_DC)
     189             : {
     190          10 :         zend_compiled_variable *cv = &CV_DEF_OF(var);
     191             : 
     192          20 :         if (!EG(active_symbol_table) ||
     193          10 :             zend_hash_quick_find(EG(active_symbol_table), cv->name, cv->name_len+1, cv->hash_value, (void **)ptr)==FAILURE) {
     194          10 :                 switch (type) {
     195             :                         case BP_VAR_R:
     196             :                         case BP_VAR_UNSET:
     197          10 :                                 zend_error(E_NOTICE, "Undefined variable: %s", cv->name);
     198             :                                 /* break missing intentionally */
     199             :                         case BP_VAR_IS:
     200          10 :                                 return &EG(uninitialized_zval_ptr);
     201             :                                 break;
     202             :                         case BP_VAR_RW:
     203           0 :                                 zend_error(E_NOTICE, "Undefined variable: %s", cv->name);
     204             :                                 /* break missing intentionally */
     205             :                         case BP_VAR_W:
     206             :                                 Z_ADDREF(EG(uninitialized_zval));
     207           0 :                                 if (!EG(active_symbol_table)) {
     208           0 :                                         *ptr = (zval**)EG(current_execute_data)->CVs + (EG(active_op_array)->last_var + var);
     209           0 :                                         **ptr = &EG(uninitialized_zval);
     210             :                                 } else {
     211           0 :                                         zend_hash_quick_update(EG(active_symbol_table), cv->name, cv->name_len+1, cv->hash_value, &EG(uninitialized_zval_ptr), sizeof(zval *), (void **)ptr);
     212             :                                 }
     213             :                                 break;
     214             :                 }
     215             :         }
     216           0 :         return *ptr;
     217             : }
     218             : 
     219       13270 : static zend_never_inline zval **_get_zval_cv_lookup_BP_VAR_R(zval ***ptr, zend_uint var TSRMLS_DC)
     220             : {
     221       13270 :         zend_compiled_variable *cv = &CV_DEF_OF(var);
     222             : 
     223       26503 :         if (!EG(active_symbol_table) ||
     224       13233 :             zend_hash_quick_find(EG(active_symbol_table), cv->name, cv->name_len+1, cv->hash_value, (void **)ptr)==FAILURE) {
     225         584 :                 zend_error(E_NOTICE, "Undefined variable: %s", cv->name);
     226         584 :                 return &EG(uninitialized_zval_ptr);
     227             :         }
     228       12686 :         return *ptr;
     229             : }
     230             : 
     231          40 : static zend_never_inline zval **_get_zval_cv_lookup_BP_VAR_UNSET(zval ***ptr, zend_uint var TSRMLS_DC)
     232             : {
     233          40 :         zend_compiled_variable *cv = &CV_DEF_OF(var);
     234             : 
     235          80 :         if (!EG(active_symbol_table) ||
     236          40 :             zend_hash_quick_find(EG(active_symbol_table), cv->name, cv->name_len+1, cv->hash_value, (void **)ptr)==FAILURE) {
     237           0 :                 zend_error(E_NOTICE, "Undefined variable: %s", cv->name);
     238           0 :                 return &EG(uninitialized_zval_ptr);
     239             :         }
     240          40 :         return *ptr;
     241             : }
     242             : 
     243          18 : static zend_never_inline zval **_get_zval_cv_lookup_BP_VAR_IS(zval ***ptr, zend_uint var TSRMLS_DC)
     244             : {
     245          18 :         zend_compiled_variable *cv = &CV_DEF_OF(var);
     246             : 
     247          36 :         if (!EG(active_symbol_table) ||
     248          18 :             zend_hash_quick_find(EG(active_symbol_table), cv->name, cv->name_len+1, cv->hash_value, (void **)ptr)==FAILURE) {
     249           3 :                 return &EG(uninitialized_zval_ptr);
     250             :         }
     251          15 :         return *ptr;
     252             : }
     253             : 
     254           5 : static zend_never_inline zval **_get_zval_cv_lookup_BP_VAR_RW(zval ***ptr, zend_uint var TSRMLS_DC)
     255             : {
     256           5 :         zend_compiled_variable *cv = &CV_DEF_OF(var);
     257             : 
     258           5 :         if (!EG(active_symbol_table)) {
     259             :                 Z_ADDREF(EG(uninitialized_zval));
     260           1 :                 *ptr = (zval**)EG(current_execute_data)->CVs + (EG(active_op_array)->last_var + var);
     261           1 :                 **ptr = &EG(uninitialized_zval);
     262           1 :                 zend_error(E_NOTICE, "Undefined variable: %s", cv->name);
     263           4 :         } else if (zend_hash_quick_find(EG(active_symbol_table), cv->name, cv->name_len+1, cv->hash_value, (void **)ptr)==FAILURE) {
     264             :                 Z_ADDREF(EG(uninitialized_zval));
     265           2 :                 zend_hash_quick_update(EG(active_symbol_table), cv->name, cv->name_len+1, cv->hash_value, &EG(uninitialized_zval_ptr), sizeof(zval *), (void **)ptr);
     266           2 :                 zend_error(E_NOTICE, "Undefined variable: %s", cv->name);
     267             :         }
     268           5 :         return *ptr;
     269             : }
     270             : 
     271     8101754 : static zend_never_inline zval **_get_zval_cv_lookup_BP_VAR_W(zval ***ptr, zend_uint var TSRMLS_DC)
     272             : {
     273     8101754 :         zend_compiled_variable *cv = &CV_DEF_OF(var);
     274             : 
     275     8101754 :         if (!EG(active_symbol_table)) {
     276             :                 Z_ADDREF(EG(uninitialized_zval));
     277     7452238 :                 *ptr = (zval**)EG(current_execute_data)->CVs + (EG(active_op_array)->last_var + var);
     278     7452238 :                 **ptr = &EG(uninitialized_zval);
     279      649516 :         } else if (zend_hash_quick_find(EG(active_symbol_table), cv->name, cv->name_len+1, cv->hash_value, (void **)ptr)==FAILURE) {
     280             :                 Z_ADDREF(EG(uninitialized_zval));
     281      648603 :                 zend_hash_quick_update(EG(active_symbol_table), cv->name, cv->name_len+1, cv->hash_value, &EG(uninitialized_zval_ptr), sizeof(zval *), (void **)ptr);
     282             :         }
     283     8101754 :         return *ptr;
     284             : }
     285             : 
     286             : static zend_always_inline zval *_get_zval_ptr_cv(zend_uint var, int type TSRMLS_DC)
     287             : {
     288     3115444 :         zval ***ptr = &CV_OF(var);
     289             : 
     290     3115444 :         if (UNEXPECTED(*ptr == NULL)) {
     291          10 :                 return *_get_zval_cv_lookup(ptr, var, type TSRMLS_CC);
     292             :         }
     293     3115434 :         return **ptr;
     294             : }
     295             : 
     296             : static zend_always_inline zval *_get_zval_ptr_cv_BP_VAR_R(zval ***CVs, zend_uint var TSRMLS_DC)
     297             : {
     298    53766892 :         zval ***ptr = &CV(var);
     299             : 
     300    53766892 :         if (UNEXPECTED(*ptr == NULL)) {
     301       13270 :                 return *_get_zval_cv_lookup_BP_VAR_R(ptr, var TSRMLS_CC);
     302             :         }
     303    53753622 :         return **ptr;
     304             : }
     305             : 
     306             : static zend_always_inline zval *_get_zval_ptr_cv_BP_VAR_UNSET(zval ***CVs, zend_uint var TSRMLS_DC)
     307             : {
     308             :         zval ***ptr = &CV(var);
     309             : 
     310             :         if (UNEXPECTED(*ptr == NULL)) {
     311             :                 return *_get_zval_cv_lookup_BP_VAR_UNSET(ptr, var TSRMLS_CC);
     312             :         }
     313             :         return **ptr;
     314             : }
     315             : 
     316             : static zend_always_inline zval *_get_zval_ptr_cv_BP_VAR_IS(zval ***CVs, zend_uint var TSRMLS_DC)
     317             : {
     318         867 :         zval ***ptr = &CV(var);
     319             : 
     320         867 :         if (UNEXPECTED(*ptr == NULL)) {
     321          14 :                 return *_get_zval_cv_lookup_BP_VAR_IS(ptr, var TSRMLS_CC);
     322             :         }
     323         853 :         return **ptr;
     324             : }
     325             : 
     326             : static zend_always_inline zval *_get_zval_ptr_cv_BP_VAR_RW(zval ***CVs, zend_uint var TSRMLS_DC)
     327             : {
     328             :         zval ***ptr = &CV(var);
     329             : 
     330             :         if (UNEXPECTED(*ptr == NULL)) {
     331             :                 return *_get_zval_cv_lookup_BP_VAR_RW(ptr, var TSRMLS_CC);
     332             :         }
     333             :         return **ptr;
     334             : }
     335             : 
     336             : static zend_always_inline zval *_get_zval_ptr_cv_BP_VAR_W(zval ***CVs, zend_uint var TSRMLS_DC)
     337             : {
     338             :         zval ***ptr = &CV(var);
     339             : 
     340             :         if (UNEXPECTED(*ptr == NULL)) {
     341             :                 return *_get_zval_cv_lookup_BP_VAR_W(ptr, var TSRMLS_CC);
     342             :         }
     343             :         return **ptr;
     344             : }
     345             : 
     346     4097419 : static inline zval *_get_zval_ptr(int op_type, const znode_op *node, const temp_variable *Ts, zend_free_op *should_free, int type TSRMLS_DC)
     347             : {
     348             : /*      should_free->is_var = 0; */
     349     4097419 :         switch (op_type) {
     350             :                 case IS_CONST:
     351      521386 :                         should_free->var = 0;
     352      521386 :                         return node->zv;
     353             :                         break;
     354             :                 case IS_TMP_VAR:
     355      237349 :                         should_free->var = TMP_FREE(&T(node->var).tmp_var);
     356      237349 :                         return &T(node->var).tmp_var;
     357             :                         break;
     358             :                 case IS_VAR:
     359      446480 :                         return _get_zval_ptr_var(node->var, Ts, should_free TSRMLS_CC);
     360             :                         break;
     361             :                 case IS_UNUSED:
     362           0 :                         should_free->var = 0;
     363           0 :                         return NULL;
     364             :                         break;
     365             :                 case IS_CV:
     366     3115444 :                         should_free->var = 0;
     367     6230888 :                         return _get_zval_ptr_cv(node->var, type TSRMLS_CC);
     368             :                         break;
     369             :                 EMPTY_SWITCH_DEFAULT_CASE()
     370             :         }
     371           0 :         return NULL;
     372             : }
     373             : 
     374             : static zend_always_inline zval **_get_zval_ptr_ptr_var(zend_uint var, const temp_variable *Ts, zend_free_op *should_free TSRMLS_DC)
     375             : {
     376     6288845 :         zval** ptr_ptr = T(var).var.ptr_ptr;
     377             : 
     378     6288845 :         if (EXPECTED(ptr_ptr != NULL)) {
     379     6288695 :                 PZVAL_UNLOCK(*ptr_ptr, should_free);
     380             :         } else {
     381             :                 /* string offset */
     382         150 :                 PZVAL_UNLOCK(T(var).str_offset.str, should_free);
     383             :         }
     384     6288845 :         return ptr_ptr;
     385             : }
     386             : 
     387             : static zend_always_inline zval **_get_zval_ptr_ptr_cv(zend_uint var, int type TSRMLS_DC)
     388             : {
     389           0 :         zval ***ptr = &CV_OF(var);
     390             : 
     391           0 :         if (UNEXPECTED(*ptr == NULL)) {
     392           0 :                 return _get_zval_cv_lookup(ptr, var, type TSRMLS_CC);
     393             :         }
     394           0 :         return *ptr;
     395             : }
     396             : 
     397             : static zend_always_inline zval **_get_zval_ptr_ptr_cv_BP_VAR_R(zval ***CVs, zend_uint var TSRMLS_DC)
     398             : {
     399         104 :         zval ***ptr = &CV(var);
     400             : 
     401         104 :         if (UNEXPECTED(*ptr == NULL)) {
     402           0 :                 return _get_zval_cv_lookup_BP_VAR_R(ptr, var TSRMLS_CC);
     403             :         }
     404         104 :         return *ptr;
     405             : }
     406             : 
     407             : static zend_always_inline zval **_get_zval_ptr_ptr_cv_BP_VAR_UNSET(zval ***CVs, zend_uint var TSRMLS_DC)
     408             : {
     409       21282 :         zval ***ptr = &CV(var);
     410             : 
     411       21282 :         if (UNEXPECTED(*ptr == NULL)) {
     412          40 :                 return _get_zval_cv_lookup_BP_VAR_UNSET(ptr, var TSRMLS_CC);
     413             :         }
     414       21242 :         return *ptr;
     415             : }
     416             : 
     417             : static zend_always_inline zval **_get_zval_ptr_ptr_cv_BP_VAR_IS(zval ***CVs, zend_uint var TSRMLS_DC)
     418             : {
     419      448493 :         zval ***ptr = &CV(var);
     420             : 
     421      448493 :         if (UNEXPECTED(*ptr == NULL)) {
     422           4 :                 return _get_zval_cv_lookup_BP_VAR_IS(ptr, var TSRMLS_CC);
     423             :         }
     424      448489 :         return *ptr;
     425             : }
     426             : 
     427             : static zend_always_inline zval **_get_zval_ptr_ptr_cv_BP_VAR_RW(zval ***CVs, zend_uint var TSRMLS_DC)
     428             : {
     429    10346488 :         zval ***ptr = &CV(var);
     430             : 
     431    10346488 :         if (UNEXPECTED(*ptr == NULL)) {
     432           5 :                 return _get_zval_cv_lookup_BP_VAR_RW(ptr, var TSRMLS_CC);
     433             :         }
     434    10346483 :         return *ptr;
     435             : }
     436             : 
     437             : static zend_always_inline zval **_get_zval_ptr_ptr_cv_BP_VAR_W(zval ***CVs, zend_uint var TSRMLS_DC)
     438             : {
     439    28609543 :         zval ***ptr = &CV(var);
     440             : 
     441    28609543 :         if (UNEXPECTED(*ptr == NULL)) {
     442     8101754 :                 return _get_zval_cv_lookup_BP_VAR_W(ptr, var TSRMLS_CC);
     443             :         }
     444    20507789 :         return *ptr;
     445             : }
     446             : 
     447           0 : static inline zval **_get_zval_ptr_ptr(int op_type, const znode_op *node, const temp_variable *Ts, zend_free_op *should_free, int type TSRMLS_DC)
     448             : {
     449           0 :         if (op_type == IS_CV) {
     450           0 :                 should_free->var = 0;
     451           0 :                 return _get_zval_ptr_ptr_cv(node->var, type TSRMLS_CC);
     452           0 :         } else if (op_type == IS_VAR) {
     453           0 :                 return _get_zval_ptr_ptr_var(node->var, Ts, should_free TSRMLS_CC);
     454             :         } else {
     455           0 :                 should_free->var = 0;
     456           0 :                 return NULL;
     457             :         }
     458             : }
     459             : 
     460             : static zend_always_inline zval *_get_obj_zval_ptr_unused(TSRMLS_D)
     461             : {
     462       31209 :         if (EXPECTED(EG(This) != NULL)) {
     463       31207 :                 return EG(This);
     464             :         } else {
     465           2 :                 zend_error_noreturn(E_ERROR, "Using $this when not in object context");
     466             :                 return NULL;
     467             :         }
     468             : }
     469             : 
     470             : static inline zval **_get_obj_zval_ptr_ptr(int op_type, const znode_op *op, const temp_variable *Ts, zend_free_op *should_free, int type TSRMLS_DC)
     471             : {
     472             :         if (op_type == IS_UNUSED) {
     473             :                 if (EXPECTED(EG(This) != NULL)) {
     474             :                         /* this should actually never be modified, _ptr_ptr is modified only when
     475             :                            the object is empty */
     476             :                         should_free->var = 0;
     477             :                         return &EG(This);
     478             :                 } else {
     479             :                         zend_error_noreturn(E_ERROR, "Using $this when not in object context");
     480             :                 }
     481             :         }
     482             :         return get_zval_ptr_ptr(op_type, op, Ts, should_free, type);
     483             : }
     484             : 
     485             : static zend_always_inline zval **_get_obj_zval_ptr_ptr_unused(TSRMLS_D)
     486             : {
     487      193986 :         if (EXPECTED(EG(This) != NULL)) {
     488      193984 :                 return &EG(This);
     489             :         } else {
     490           2 :                 zend_error_noreturn(E_ERROR, "Using $this when not in object context");
     491             :                 return NULL;
     492             :         }
     493             : }
     494             : 
     495             : static inline zval *_get_obj_zval_ptr(int op_type, znode_op *op, const temp_variable *Ts, zend_free_op *should_free, int type TSRMLS_DC)
     496             : {
     497             :         if (op_type == IS_UNUSED) {
     498             :                 if (EXPECTED(EG(This) != NULL)) {
     499             :                         should_free->var = 0;
     500             :                         return EG(This);
     501             :                 } else {
     502             :                         zend_error_noreturn(E_ERROR, "Using $this when not in object context");
     503             :                 }
     504             :         }
     505             :         return get_zval_ptr(op_type, op, Ts, should_free, type);
     506             : }
     507             : 
     508      920214 : static void zend_assign_to_variable_reference(zval **variable_ptr_ptr, zval **value_ptr_ptr TSRMLS_DC)
     509             : {
     510      920214 :         zval *variable_ptr = *variable_ptr_ptr;
     511      920214 :         zval *value_ptr = *value_ptr_ptr;
     512             : 
     513      920225 :         if (variable_ptr == &EG(error_zval) || value_ptr == &EG(error_zval)) {
     514          11 :                 variable_ptr_ptr = &EG(uninitialized_zval_ptr);
     515      920203 :         } else if (variable_ptr != value_ptr) {
     516      909248 :                 if (!PZVAL_IS_REF(value_ptr)) {
     517             :                         /* break it away */
     518             :                         Z_DELREF_P(value_ptr);
     519      621939 :                         if (Z_REFCOUNT_P(value_ptr)>0) {
     520          51 :                                 ALLOC_ZVAL(*value_ptr_ptr);
     521          51 :                                 ZVAL_COPY_VALUE(*value_ptr_ptr, value_ptr);
     522          51 :                                 value_ptr = *value_ptr_ptr;
     523             :                                 zendi_zval_copy_ctor(*value_ptr);
     524             :                         }
     525             :                         Z_SET_REFCOUNT_P(value_ptr, 1);
     526             :                         Z_SET_ISREF_P(value_ptr);
     527             :                 }
     528             : 
     529      909248 :                 *variable_ptr_ptr = value_ptr;
     530             :                 Z_ADDREF_P(value_ptr);
     531             : 
     532      909248 :                 zval_ptr_dtor(&variable_ptr);
     533       21910 :         } else if (!Z_ISREF_P(variable_ptr)) {
     534         848 :                 if (variable_ptr_ptr == value_ptr_ptr) {
     535        1348 :                         SEPARATE_ZVAL(variable_ptr_ptr);
     536         276 :                 } else if (variable_ptr==&EG(uninitialized_zval)
     537         276 :                         || Z_REFCOUNT_P(variable_ptr)>2) {
     538             :                         /* we need to separate */
     539         544 :                         Z_SET_REFCOUNT_P(variable_ptr, Z_REFCOUNT_P(variable_ptr) - 2);
     540         272 :                         ALLOC_ZVAL(*variable_ptr_ptr);
     541         272 :                         ZVAL_COPY_VALUE(*variable_ptr_ptr, variable_ptr);
     542         272 :                         zval_copy_ctor(*variable_ptr_ptr);
     543         272 :                         *value_ptr_ptr = *variable_ptr_ptr;
     544         272 :                         Z_SET_REFCOUNT_PP(variable_ptr_ptr, 2);
     545             :                 }
     546         848 :                 Z_SET_ISREF_PP(variable_ptr_ptr);
     547             :         }
     548      920214 : }
     549             : 
     550             : /* this should modify object only if it's empty */
     551        4350 : static inline void make_real_object(zval **object_ptr TSRMLS_DC)
     552             : {
     553       17393 :         if (Z_TYPE_PP(object_ptr) == IS_NULL
     554        8698 :                 || (Z_TYPE_PP(object_ptr) == IS_BOOL && Z_LVAL_PP(object_ptr) == 0)
     555        4345 :                 || (Z_TYPE_PP(object_ptr) == IS_STRING && Z_STRLEN_PP(object_ptr) == 0)
     556             :         ) {
     557          47 :                 SEPARATE_ZVAL_IF_NOT_REF(object_ptr);
     558          11 :                 zval_dtor(*object_ptr);
     559          11 :                 object_init(*object_ptr);
     560          11 :                 zend_error(E_WARNING, "Creating default object from empty value");
     561             :         }
     562        4350 : }
     563             : 
     564       88773 : ZEND_API char * zend_verify_arg_class_kind(const zend_arg_info *cur_arg_info, ulong fetch_type, const char **class_name, zend_class_entry **pce TSRMLS_DC)
     565             : {
     566       88773 :         *pce = zend_fetch_class(cur_arg_info->class_name, cur_arg_info->class_name_len, (fetch_type | ZEND_FETCH_CLASS_AUTO | ZEND_FETCH_CLASS_NO_AUTOLOAD) TSRMLS_CC);
     567             : 
     568       88773 :         *class_name = (*pce) ? (*pce)->name: cur_arg_info->class_name;
     569       88773 :         if (*pce && (*pce)->ce_flags & ZEND_ACC_INTERFACE) {
     570         658 :                 return "implement interface ";
     571             :         } else {
     572       88115 :                 return "be an instance of ";
     573             :         }
     574             : }
     575             : 
     576          59 : ZEND_API int zend_verify_arg_error(int error_type, const zend_function *zf, zend_uint arg_num, const char *need_msg, const char *need_kind, const char *given_msg, const char *given_kind TSRMLS_DC)
     577             : {
     578          59 :         zend_execute_data *ptr = EG(current_execute_data)->prev_execute_data;
     579          59 :         const char *fname = zf->common.function_name;
     580             :         char *fsep;
     581             :         const char *fclass;
     582             : 
     583          59 :         if (zf->common.scope) {
     584          23 :                 fsep =  "::";
     585          23 :                 fclass = zf->common.scope->name;
     586             :         } else {
     587          36 :                 fsep =  "";
     588          36 :                 fclass = "";
     589             :         }
     590             : 
     591          62 :         if (ptr && ptr->op_array) {
     592          20 :                 zend_error(error_type, "Argument %d passed to %s%s%s() must %s%s, %s%s given, called in %s on line %d and defined", arg_num, fclass, fsep, fname, need_msg, need_kind, given_msg, given_kind, ptr->op_array->filename, ptr->opline->lineno);
     593             :         } else {
     594          39 :                 zend_error(error_type, "Argument %d passed to %s%s%s() must %s%s, %s%s given", arg_num, fclass, fsep, fname, need_msg, need_kind, given_msg, given_kind);
     595             :         }
     596          33 :         return 0;
     597             : }
     598             : 
     599    37561204 : static inline int zend_verify_arg_type(zend_function *zf, zend_uint arg_num, zval *arg, ulong fetch_type TSRMLS_DC)
     600             : {
     601             :         zend_arg_info *cur_arg_info;
     602             :         char *need_msg;
     603             :         zend_class_entry *ce;
     604             : 
     605    75122408 :         if (!zf->common.arg_info
     606    37561204 :                 || arg_num>zf->common.num_args) {
     607      344932 :                 return 1;
     608             :         }
     609             : 
     610    37216272 :         cur_arg_info = &zf->common.arg_info[arg_num-1];
     611             : 
     612    37216272 :         if (cur_arg_info->class_name) {
     613             :                 const char *class_name;
     614             : 
     615       88813 :                 if (!arg) {
     616           2 :                         need_msg = zend_verify_arg_class_kind(cur_arg_info, fetch_type, &class_name, &ce TSRMLS_CC);
     617           2 :                         return zend_verify_arg_error(E_RECOVERABLE_ERROR, zf, arg_num, need_msg, class_name, "none", "" TSRMLS_CC);
     618             :                 }
     619       88811 :                 if (Z_TYPE_P(arg) == IS_OBJECT) {
     620       88754 :                         need_msg = zend_verify_arg_class_kind(cur_arg_info, fetch_type, &class_name, &ce TSRMLS_CC);
     621       88754 :                         if (!ce || !instanceof_function(Z_OBJCE_P(arg), ce TSRMLS_CC)) {
     622          27 :                                 return zend_verify_arg_error(E_RECOVERABLE_ERROR, zf, arg_num, need_msg, class_name, "instance of ", Z_OBJCE_P(arg)->name TSRMLS_CC);
     623             :                         }
     624          57 :                 } else if (Z_TYPE_P(arg) != IS_NULL || !cur_arg_info->allow_null) {
     625          17 :                         need_msg = zend_verify_arg_class_kind(cur_arg_info, fetch_type, &class_name, &ce TSRMLS_CC);
     626          17 :                         return zend_verify_arg_error(E_RECOVERABLE_ERROR, zf, arg_num, need_msg, class_name, zend_zval_type_name(arg), "" TSRMLS_CC);
     627             :                 }
     628    37127459 :         } else if (cur_arg_info->type_hint) {
     629         444 :                 switch(cur_arg_info->type_hint) {
     630             :                         case IS_ARRAY:
     631         435 :                                 if (!arg) {
     632           2 :                                         return zend_verify_arg_error(E_RECOVERABLE_ERROR, zf, arg_num, "be of the type array", "", "none", "" TSRMLS_CC);
     633             :                                 }
     634             : 
     635         433 :                                 if (Z_TYPE_P(arg) != IS_ARRAY && (Z_TYPE_P(arg) != IS_NULL || !cur_arg_info->allow_null)) {
     636          10 :                                         return zend_verify_arg_error(E_RECOVERABLE_ERROR, zf, arg_num, "be of the type array", "", zend_zval_type_name(arg), "" TSRMLS_CC);
     637             :                                 }
     638         423 :                                 break;
     639             : 
     640             :                         case IS_CALLABLE:
     641           9 :                                 if (!arg) {
     642           1 :                                         return zend_verify_arg_error(E_RECOVERABLE_ERROR, zf, arg_num, "be callable", "", "none", "" TSRMLS_CC);
     643             :                                 }
     644           8 :                                 if (!zend_is_callable(arg, IS_CALLABLE_CHECK_SILENT, NULL TSRMLS_CC) && (Z_TYPE_P(arg) != IS_NULL || !cur_arg_info->allow_null)) {
     645           0 :                                         return zend_verify_arg_error(E_RECOVERABLE_ERROR, zf, arg_num, "be callable", "", zend_zval_type_name(arg), "" TSRMLS_CC);
     646             :                                 }
     647           8 :                                 break;
     648             : 
     649             :                         default:
     650           0 :                                 zend_error(E_ERROR, "Unknown typehint");
     651             :                 }
     652             :         }
     653    37216213 :         return 1;
     654             : }
     655             : 
     656      114693 : static inline void zend_assign_to_object(zval **retval, zval **object_ptr, zval *property_name, int value_type, znode_op *value_op, const temp_variable *Ts, int opcode, const zend_literal *key TSRMLS_DC)
     657             : {
     658      114693 :         zval *object = *object_ptr;
     659             :         zend_free_op free_value;
     660      114693 :         zval *value = get_zval_ptr(value_type, value_op, Ts, &free_value, BP_VAR_R);
     661             : 
     662      114693 :         if (Z_TYPE_P(object) != IS_OBJECT) {
     663          27 :                 if (object == &EG(error_zval)) {
     664           0 :                         if (retval) {
     665           0 :                                 *retval = &EG(uninitialized_zval);
     666           0 :                                 PZVAL_LOCK(*retval);
     667             :                         }
     668           0 :                         FREE_OP(free_value);
     669           0 :                         return;
     670             :                 }
     671          65 :                 if (Z_TYPE_P(object) == IS_NULL ||
     672           9 :                     (Z_TYPE_P(object) == IS_BOOL && Z_LVAL_P(object) == 0) ||
     673           7 :                     (Z_TYPE_P(object) == IS_STRING && Z_STRLEN_P(object) == 0)) {
     674         103 :                         SEPARATE_ZVAL_IF_NOT_REF(object_ptr);
     675          23 :                         object = *object_ptr;
     676          23 :                         Z_ADDREF_P(object);
     677          23 :                         zend_error(E_WARNING, "Creating default object from empty value");
     678          46 :                         if (Z_REFCOUNT_P(object) == 1) {
     679             :                                 /* object was removed by error handler, nothing to assign to */
     680           1 :                                 zval_ptr_dtor(&object);
     681           1 :                                 if (retval) {
     682           1 :                                         *retval = &EG(uninitialized_zval);
     683           1 :                                         PZVAL_LOCK(*retval);
     684             :                                 }
     685           1 :                                 FREE_OP(free_value);
     686           1 :                                 return;
     687             :                         }
     688          22 :                         Z_DELREF_P(object);
     689          22 :                         zval_dtor(object);
     690          22 :                         object_init(object);
     691             :                 } else {
     692           4 :                         zend_error(E_WARNING, "Attempt to assign property of non-object");
     693           4 :                         if (retval) {
     694           0 :                                 *retval = &EG(uninitialized_zval);
     695           0 :                                 PZVAL_LOCK(*retval);
     696             :                         }
     697           4 :                         FREE_OP(free_value);
     698           4 :                         return;
     699             :                 }
     700             :         }
     701             : 
     702             :         /* separate our value if necessary */
     703      114688 :         if (value_type == IS_TMP_VAR) {
     704         647 :                 zval *orig_value = value;
     705             : 
     706         647 :                 ALLOC_ZVAL(value);
     707         647 :                 ZVAL_COPY_VALUE(value, orig_value);
     708         647 :                 Z_UNSET_ISREF_P(value);
     709         647 :                 Z_SET_REFCOUNT_P(value, 0);
     710      114041 :         } else if (value_type == IS_CONST) {
     711      100251 :                 zval *orig_value = value;
     712             : 
     713      100251 :                 ALLOC_ZVAL(value);
     714      100251 :                 ZVAL_COPY_VALUE(value, orig_value);
     715      100251 :                 Z_UNSET_ISREF_P(value);
     716      100251 :                 Z_SET_REFCOUNT_P(value, 0);
     717      100251 :                 zval_copy_ctor(value);
     718             :         }
     719             : 
     720             : 
     721      114688 :         Z_ADDREF_P(value);
     722      114688 :         if (opcode == ZEND_ASSIGN_OBJ) {
     723      113137 :                 if (!Z_OBJ_HT_P(object)->write_property) {
     724           0 :                         zend_error(E_WARNING, "Attempt to assign property of non-object");
     725           0 :                         if (retval) {
     726           0 :                                 *retval = &EG(uninitialized_zval);
     727             :                                 PZVAL_LOCK(&EG(uninitialized_zval));
     728             :                         }
     729           0 :                         if (value_type == IS_TMP_VAR) {
     730           0 :                                 FREE_ZVAL(value);
     731           0 :                         } else if (value_type == IS_CONST) {
     732           0 :                                 zval_ptr_dtor(&value);
     733             :                         }
     734           0 :                         FREE_OP(free_value);
     735           0 :                         return;
     736             :                 }
     737      113137 :                 Z_OBJ_HT_P(object)->write_property(object, property_name, value, key TSRMLS_CC);
     738             :         } else {
     739             :                 /* Note:  property_name in this case is really the array index! */
     740        1551 :                 if (!Z_OBJ_HT_P(object)->write_dimension) {
     741           0 :                         zend_error_noreturn(E_ERROR, "Cannot use object as array");
     742             :                 }
     743        1551 :                 Z_OBJ_HT_P(object)->write_dimension(object, property_name, value TSRMLS_CC);
     744             :         }
     745             : 
     746      114678 :         if (retval && !EG(exception)) {
     747          30 :                 *retval = value;
     748          30 :                 PZVAL_LOCK(value);
     749             :         }
     750      114678 :         zval_ptr_dtor(&value);
     751      114678 :         FREE_OP_IF_VAR(free_value);
     752             : }
     753             : 
     754         144 : static inline int zend_assign_to_string_offset(const temp_variable *T, const zval *value, int value_type TSRMLS_DC)
     755             : {
     756         144 :         if (Z_TYPE_P(T->str_offset.str) == IS_STRING) {
     757             : 
     758         144 :                 if (((int)T->str_offset.offset < 0)) {
     759           1 :                         zend_error(E_WARNING, "Illegal string offset:  %d", T->str_offset.offset);
     760           1 :                         return 0;
     761             :                 }
     762             : 
     763         143 :                 if (T->str_offset.offset >= Z_STRLEN_P(T->str_offset.str)) {
     764           4 :                         if (IS_INTERNED(Z_STRVAL_P(T->str_offset.str))) {
     765           1 :                                 char *tmp = (char *) emalloc(T->str_offset.offset+1+1);
     766             : 
     767           1 :                                 memcpy(tmp, Z_STRVAL_P(T->str_offset.str), Z_STRLEN_P(T->str_offset.str)+1);
     768           1 :                                 Z_STRVAL_P(T->str_offset.str) = tmp;
     769             :                         } else {
     770           2 :                                 Z_STRVAL_P(T->str_offset.str) = (char *) erealloc(Z_STRVAL_P(T->str_offset.str), T->str_offset.offset+1+1);
     771             :                         }
     772           3 :                         memset(Z_STRVAL_P(T->str_offset.str) + Z_STRLEN_P(T->str_offset.str),
     773             :                                ' ',
     774           3 :                                T->str_offset.offset - Z_STRLEN_P(T->str_offset.str));
     775           3 :                         Z_STRVAL_P(T->str_offset.str)[T->str_offset.offset+1] = 0;
     776           3 :                         Z_STRLEN_P(T->str_offset.str) = T->str_offset.offset+1;
     777         140 :                 } else if (IS_INTERNED(Z_STRVAL_P(T->str_offset.str))) {
     778           8 :                         char *tmp = (char *) emalloc(Z_STRLEN_P(T->str_offset.str) + 1);
     779             : 
     780           8 :                         memcpy(tmp, Z_STRVAL_P(T->str_offset.str), Z_STRLEN_P(T->str_offset.str) + 1);
     781           8 :                         Z_STRVAL_P(T->str_offset.str) = tmp;
     782             :                 }
     783             : 
     784         143 :                 if (Z_TYPE_P(value) != IS_STRING) {
     785             :                         zval tmp;
     786             : 
     787          11 :                         ZVAL_COPY_VALUE(&tmp, value);
     788          11 :                         if (value_type != IS_TMP_VAR) {
     789             :                                 zval_copy_ctor(&tmp);
     790             :                         }
     791          11 :                         convert_to_string(&tmp);
     792          11 :                         Z_STRVAL_P(T->str_offset.str)[T->str_offset.offset] = Z_STRVAL(tmp)[0];
     793          11 :                         STR_FREE(Z_STRVAL(tmp));
     794             :                 } else {
     795         132 :                         Z_STRVAL_P(T->str_offset.str)[T->str_offset.offset] = Z_STRVAL_P(value)[0];
     796         132 :                         if (value_type == IS_TMP_VAR) {
     797             :                                 /* we can safely free final_value here
     798             :                                  * because separation is done only
     799             :                                  * in case value_type == IS_VAR */
     800          10 :                                 STR_FREE(Z_STRVAL_P(value));
     801             :                         }
     802             :                 }
     803             :                 /*
     804             :                  * the value of an assignment to a string offset is undefined
     805             :                 T(result->u.var).var = &T->str_offset.str;
     806             :                 */
     807             :         }
     808         143 :         return 1;
     809             : }
     810             : 
     811             : 
     812     2943856 : static inline zval* zend_assign_tmp_to_variable(zval **variable_ptr_ptr, zval *value TSRMLS_DC)
     813             : {
     814     2943856 :         zval *variable_ptr = *variable_ptr_ptr;
     815             :         zval garbage;
     816             : 
     817     2943891 :         if (Z_TYPE_P(variable_ptr) == IS_OBJECT &&
     818          35 :             UNEXPECTED(Z_OBJ_HANDLER_P(variable_ptr, set) != NULL)) {
     819           0 :                 Z_OBJ_HANDLER_P(variable_ptr, set)(variable_ptr_ptr, value TSRMLS_CC);
     820           0 :                 return variable_ptr;
     821             :         }
     822             : 
     823     4134945 :         if (UNEXPECTED(Z_REFCOUNT_P(variable_ptr) > 1) &&
     824     1191089 :             EXPECTED(!PZVAL_IS_REF(variable_ptr))) {
     825             :             /* we need to split */
     826             :                 Z_DELREF_P(variable_ptr);
     827             :                 GC_ZVAL_CHECK_POSSIBLE_ROOT(variable_ptr);
     828     1188774 :                 ALLOC_ZVAL(variable_ptr);
     829     1188774 :                 INIT_PZVAL_COPY(variable_ptr, value);
     830     1188774 :                 *variable_ptr_ptr = variable_ptr;
     831     1188774 :                 return variable_ptr;
     832             :         } else {
     833     1755082 :                 if (EXPECTED(Z_TYPE_P(variable_ptr) <= IS_BOOL)) {
     834             :                         /* nothing to destroy */
     835      222933 :                         ZVAL_COPY_VALUE(variable_ptr, value);
     836             :                 } else {
     837     1532149 :                         ZVAL_COPY_VALUE(&garbage, variable_ptr);
     838     1532149 :                         ZVAL_COPY_VALUE(variable_ptr, value);
     839     1532149 :                         _zval_dtor_func(&garbage ZEND_FILE_LINE_CC);
     840             :                 }
     841     1755082 :                 return variable_ptr;
     842             :         }
     843             : }
     844             : 
     845     2900510 : static inline zval* zend_assign_const_to_variable(zval **variable_ptr_ptr, zval *value TSRMLS_DC)
     846             : {
     847     2900510 :         zval *variable_ptr = *variable_ptr_ptr;
     848             :         zval garbage;
     849             : 
     850     2910627 :         if (Z_TYPE_P(variable_ptr) == IS_OBJECT &&
     851       10117 :             UNEXPECTED(Z_OBJ_HANDLER_P(variable_ptr, set) != NULL)) {
     852           0 :                 Z_OBJ_HANDLER_P(variable_ptr, set)(variable_ptr_ptr, value TSRMLS_CC);
     853           0 :                 return variable_ptr;
     854             :         }
     855             : 
     856     3810229 :         if (UNEXPECTED(Z_REFCOUNT_P(variable_ptr) > 1) &&
     857      909719 :             EXPECTED(!PZVAL_IS_REF(variable_ptr))) {
     858             :                 /* we need to split */
     859             :                 Z_DELREF_P(variable_ptr);
     860             :                 GC_ZVAL_CHECK_POSSIBLE_ROOT(variable_ptr);
     861      908952 :                 ALLOC_ZVAL(variable_ptr);
     862      908952 :                 INIT_PZVAL_COPY(variable_ptr, value);
     863             :                 zval_copy_ctor(variable_ptr);
     864      908952 :                 *variable_ptr_ptr = variable_ptr;
     865      908952 :                 return variable_ptr;
     866             :         } else {
     867     1991558 :                 if (EXPECTED(Z_TYPE_P(variable_ptr) <= IS_BOOL)) {
     868             :                         /* nothing to destroy */
     869     1825747 :                         ZVAL_COPY_VALUE(variable_ptr, value);
     870             :                         zendi_zval_copy_ctor(*variable_ptr);
     871             :                 } else {
     872      165811 :                         ZVAL_COPY_VALUE(&garbage, variable_ptr);
     873      165811 :                         ZVAL_COPY_VALUE(variable_ptr, value);
     874             :                         zendi_zval_copy_ctor(*variable_ptr);
     875      165811 :                         _zval_dtor_func(&garbage ZEND_FILE_LINE_CC);
     876             :                 }
     877     1991554 :                 return variable_ptr;
     878             :         }
     879             : }
     880             : 
     881    13690622 : static inline zval* zend_assign_to_variable(zval **variable_ptr_ptr, zval *value TSRMLS_DC)
     882             : {
     883    13690622 :         zval *variable_ptr = *variable_ptr_ptr;
     884             :         zval garbage;
     885             : 
     886    14553940 :         if (Z_TYPE_P(variable_ptr) == IS_OBJECT &&
     887      863318 :             UNEXPECTED(Z_OBJ_HANDLER_P(variable_ptr, set) != NULL)) {
     888           0 :                 Z_OBJ_HANDLER_P(variable_ptr, set)(variable_ptr_ptr, value TSRMLS_CC);
     889           0 :                 return variable_ptr;
     890             :         }
     891             : 
     892    13690622 :         if (EXPECTED(!PZVAL_IS_REF(variable_ptr))) {
     893    13662271 :                 if (Z_REFCOUNT_P(variable_ptr)==1) {
     894     7463770 :                         if (UNEXPECTED(variable_ptr == value)) {
     895         169 :                                 return variable_ptr;
     896     7463601 :                         } else if (EXPECTED(!PZVAL_IS_REF(value))) {
     897             :                                 Z_ADDREF_P(value);
     898     7463449 :                                 *variable_ptr_ptr = value;
     899     7463449 :                                 if (EXPECTED(variable_ptr != &EG(uninitialized_zval))) {
     900     7463449 :                                         GC_REMOVE_ZVAL_FROM_BUFFER(variable_ptr);
     901             :                                         zval_dtor(variable_ptr);
     902     7463449 :                                         efree(variable_ptr);
     903             :                                 } else {
     904             :                                         Z_DELREF_P(variable_ptr);
     905             :                                 }
     906     7463449 :                                 return value;
     907             :                         } else {
     908         152 :                                 goto copy_value;
     909             :                         }
     910             :                 } else { /* we need to split */
     911             :                         Z_DELREF_P(variable_ptr);
     912             :                         GC_ZVAL_CHECK_POSSIBLE_ROOT(variable_ptr);
     913     6199804 :                         if (PZVAL_IS_REF(value) && Z_REFCOUNT_P(value) > 0) {
     914        1303 :                                 ALLOC_ZVAL(variable_ptr);
     915        1303 :                                 *variable_ptr_ptr = variable_ptr;
     916        1303 :                                 INIT_PZVAL_COPY(variable_ptr, value);
     917             :                                 zval_copy_ctor(variable_ptr);
     918        1303 :                                 return variable_ptr;
     919             :                         } else {
     920     6197198 :                                 *variable_ptr_ptr = value;
     921             :                                 Z_ADDREF_P(value);
     922             :                                 Z_UNSET_ISREF_P(value);
     923     6197198 :                                 return value;
     924             :                         }
     925             :                 }
     926             :         } else {
     927       28351 :                 if (EXPECTED(variable_ptr != value)) {
     928             : copy_value:
     929       28503 :                         if (EXPECTED(Z_TYPE_P(variable_ptr) <= IS_BOOL)) {
     930             :                                 /* nothing to destroy */
     931       13646 :                                 ZVAL_COPY_VALUE(variable_ptr, value);
     932             :                                 zendi_zval_copy_ctor(*variable_ptr);
     933             :                         } else {
     934       14857 :                                 ZVAL_COPY_VALUE(&garbage, variable_ptr);
     935       14857 :                                 ZVAL_COPY_VALUE(variable_ptr, value);
     936             :                                 zendi_zval_copy_ctor(*variable_ptr);
     937       14857 :                                 _zval_dtor_func(&garbage ZEND_FILE_LINE_CC);
     938             :                         }
     939             :                 }
     940       28503 :                 return variable_ptr;
     941             :         }
     942             : }
     943             : 
     944             : /* Utility Functions for Extensions */
     945           0 : static void zend_extension_statement_handler(const zend_extension *extension, zend_op_array *op_array TSRMLS_DC)
     946             : {
     947           0 :         if (extension->statement_handler) {
     948           0 :                 extension->statement_handler(op_array);
     949             :         }
     950           0 : }
     951             : 
     952             : 
     953           0 : static void zend_extension_fcall_begin_handler(const zend_extension *extension, zend_op_array *op_array TSRMLS_DC)
     954             : {
     955           0 :         if (extension->fcall_begin_handler) {
     956           0 :                 extension->fcall_begin_handler(op_array);
     957             :         }
     958           0 : }
     959             : 
     960             : 
     961           0 : static void zend_extension_fcall_end_handler(const zend_extension *extension, zend_op_array *op_array TSRMLS_DC)
     962             : {
     963           0 :         if (extension->fcall_end_handler) {
     964           0 :                 extension->fcall_end_handler(op_array);
     965             :         }
     966           0 : }
     967             : 
     968             : 
     969     1984081 : static inline HashTable *zend_get_target_symbol_table(int fetch_type TSRMLS_DC)
     970             : {
     971     1984081 :         switch (fetch_type) {
     972             :                 case ZEND_FETCH_LOCAL:
     973     1192445 :                         if (!EG(active_symbol_table)) {
     974       34213 :                                 zend_rebuild_symbol_table(TSRMLS_C);
     975             :                         }
     976     1192445 :                         return EG(active_symbol_table);
     977             :                         break;
     978             :                 case ZEND_FETCH_GLOBAL:
     979             :                 case ZEND_FETCH_GLOBAL_LOCK:
     980      790144 :                         return &EG(symbol_table);
     981             :                         break;
     982             :                 case ZEND_FETCH_STATIC:
     983        1492 :                         if (!EG(active_op_array)->static_variables) {
     984           0 :                                 ALLOC_HASHTABLE(EG(active_op_array)->static_variables);
     985           0 :                                 zend_hash_init(EG(active_op_array)->static_variables, 2, NULL, ZVAL_PTR_DTOR, 0);
     986             :                         }
     987        1492 :                         return EG(active_op_array)->static_variables;
     988             :                         break;
     989             :                 EMPTY_SWITCH_DEFAULT_CASE()
     990             :         }
     991           0 :         return NULL;
     992             : }
     993             : 
     994     8616352 : static inline zval **zend_fetch_dimension_address_inner(HashTable *ht, const zval *dim, int dim_type, int type TSRMLS_DC)
     995             : {
     996             :         zval **retval;
     997             :         char *offset_key;
     998             :         int offset_key_length;
     999             :         ulong hval;
    1000             : 
    1001     8616352 :         switch (dim->type) {
    1002             :                 case IS_NULL:
    1003          10 :                         offset_key = "";
    1004          10 :                         offset_key_length = 0;
    1005          10 :                         hval = zend_inline_hash_func("", 1);
    1006          10 :                         goto fetch_string_dim;
    1007             : 
    1008             :                 case IS_STRING:
    1009             : 
    1010     3829621 :                         offset_key = dim->value.str.val;
    1011     3829621 :                         offset_key_length = dim->value.str.len;
    1012             : 
    1013     3829621 :                         if (dim_type == IS_CONST) {
    1014      942866 :                                 hval = Z_HASH_P(dim);
    1015             :                         } else {
    1016     2886755 :                                 ZEND_HANDLE_NUMERIC_EX(offset_key, offset_key_length+1, hval, goto num_index);
    1017     2778339 :                                 if (IS_INTERNED(offset_key)) {
    1018       71669 :                                         hval = INTERNED_HASH(offset_key);
    1019             :                                 } else {
    1020     2635001 :                                         hval = zend_hash_func(offset_key, offset_key_length+1);
    1021             :                                 }
    1022             :                         }
    1023             : fetch_string_dim:
    1024     3649546 :                         if (zend_hash_quick_find(ht, offset_key, offset_key_length+1, hval, (void **) &retval) == FAILURE) {
    1025     1804709 :                                 switch (type) {
    1026             :                                         case BP_VAR_R:
    1027      114273 :                                                 zend_error(E_NOTICE, "Undefined index: %s", offset_key);
    1028             :                                                 /* break missing intentionally */
    1029             :                                         case BP_VAR_UNSET:
    1030             :                                         case BP_VAR_IS:
    1031      114273 :                                                 retval = &EG(uninitialized_zval_ptr);
    1032      114273 :                                                 break;
    1033             :                                         case BP_VAR_RW:
    1034           1 :                                                 zend_error(E_NOTICE,"Undefined index: %s", offset_key);
    1035             :                                                 /* break missing intentionally */
    1036             :                                         case BP_VAR_W: {
    1037     1690436 :                                                         zval *new_zval = &EG(uninitialized_zval);
    1038             : 
    1039     1690436 :                                                         Z_ADDREF_P(new_zval);
    1040     1690436 :                                                         zend_hash_quick_update(ht, offset_key, offset_key_length+1, hval, &new_zval, sizeof(zval *), (void **) &retval);
    1041             :                                                 }
    1042             :                                                 break;
    1043             :                                 }
    1044             :                         }
    1045     3649546 :                         break;
    1046             :                 case IS_DOUBLE:
    1047          98 :                         hval = zend_dval_to_lval(Z_DVAL_P(dim));
    1048          49 :                         goto num_index;
    1049             :                 case IS_RESOURCE:
    1050           3 :                         zend_error(E_STRICT, "Resource ID#%ld used as offset, casting to integer (%ld)", Z_LVAL_P(dim), Z_LVAL_P(dim));
    1051             :                         /* Fall Through */
    1052             :                 case IS_BOOL:
    1053             :                 case IS_LONG:
    1054     4786666 :                         hval = Z_LVAL_P(dim);
    1055             : num_index:
    1056     4966800 :                         if (zend_hash_index_find(ht, hval, (void **) &retval) == FAILURE) {
    1057      395583 :                                 switch (type) {
    1058             :                                         case BP_VAR_R:
    1059          16 :                                                 zend_error(E_NOTICE,"Undefined offset: %ld", hval);
    1060             :                                                 /* break missing intentionally */
    1061             :                                         case BP_VAR_UNSET:
    1062             :                                         case BP_VAR_IS:
    1063          18 :                                                 retval = &EG(uninitialized_zval_ptr);
    1064          18 :                                                 break;
    1065             :                                         case BP_VAR_RW:
    1066           6 :                                                 zend_error(E_NOTICE,"Undefined offset: %ld", hval);
    1067             :                                                 /* break missing intentionally */
    1068             :                                         case BP_VAR_W: {
    1069      395565 :                                                 zval *new_zval = &EG(uninitialized_zval);
    1070             : 
    1071      395565 :                                                 Z_ADDREF_P(new_zval);
    1072      395565 :                                                 zend_hash_index_update(ht, hval, &new_zval, sizeof(zval *), (void **) &retval);
    1073             :                                         }
    1074             :                                         break;
    1075             :                                 }
    1076             :                         }
    1077     4966800 :                         break;
    1078             : 
    1079             :                 default:
    1080           6 :                         zend_error(E_WARNING, "Illegal offset type");
    1081           6 :                         return (type == BP_VAR_W || type == BP_VAR_RW) ?
    1082             :                                 &EG(error_zval_ptr) : &EG(uninitialized_zval_ptr);
    1083             :         }
    1084     8616346 :         return retval;
    1085             : }
    1086             : 
    1087     4489181 : static void zend_fetch_dimension_address(temp_variable *result, zval **container_ptr, zval *dim, int dim_type, int type TSRMLS_DC)
    1088             : {
    1089     4489181 :         zval *container = *container_ptr;
    1090             :         zval **retval;
    1091             : 
    1092     4489181 :         switch (Z_TYPE_P(container)) {
    1093             : 
    1094             :                 case IS_ARRAY:
    1095     9563954 :                         if (type != BP_VAR_UNSET && Z_REFCOUNT_P(container)>1 && !PZVAL_IS_REF(container)) {
    1096      401832 :                                 SEPARATE_ZVAL(container_ptr);
    1097      100458 :                                 container = *container_ptr;
    1098             :                         }
    1099             : fetch_from_array:
    1100     4488959 :                         if (dim == NULL) {
    1101      664140 :                                 zval *new_zval = &EG(uninitialized_zval);
    1102             : 
    1103      664140 :                                 Z_ADDREF_P(new_zval);
    1104      664140 :                                 if (zend_hash_next_index_insert(Z_ARRVAL_P(container), &new_zval, sizeof(zval *), (void **) &retval) == FAILURE) {
    1105           1 :                                         zend_error(E_WARNING, "Cannot add element to the array as the next element is already occupied");
    1106           1 :                                         retval = &EG(error_zval_ptr);
    1107           1 :                                         Z_DELREF_P(new_zval);
    1108             :                                 }
    1109             :                         } else {
    1110     3824819 :                                 retval = zend_fetch_dimension_address_inner(Z_ARRVAL_P(container), dim, dim_type, type TSRMLS_CC);
    1111             :                         }
    1112     4488959 :                         result->var.ptr_ptr = retval;
    1113     4488959 :                         PZVAL_LOCK(*retval);
    1114     4488959 :                         return;
    1115             :                         break;
    1116             : 
    1117             :                 case IS_NULL:
    1118        1312 :                         if (container == &EG(error_zval)) {
    1119           1 :                                 result->var.ptr_ptr = &EG(error_zval_ptr);
    1120           1 :                                 PZVAL_LOCK(EG(error_zval_ptr));
    1121        1311 :                         } else if (type != BP_VAR_UNSET) {
    1122             : convert_to_array:
    1123        1322 :                                 if (!PZVAL_IS_REF(container)) {
    1124        5192 :                                         SEPARATE_ZVAL(container_ptr);
    1125        1319 :                                         container = *container_ptr;
    1126             :                                 }
    1127             :                                 zval_dtor(container);
    1128        1322 :                                 array_init(container);
    1129        1322 :                                 goto fetch_from_array;
    1130             :                         } else {
    1131             :                                 /* for read-mode only */
    1132           0 :                                 result->var.ptr_ptr = &EG(uninitialized_zval_ptr);
    1133           0 :                                 PZVAL_LOCK(EG(uninitialized_zval_ptr));
    1134             :                         }
    1135           1 :                         return;
    1136             :                         break;
    1137             : 
    1138             :                 case IS_STRING: {
    1139             :                                 zval tmp;
    1140             : 
    1141         155 :                                 if (type != BP_VAR_UNSET && Z_STRLEN_P(container)==0) {
    1142           4 :                                         goto convert_to_array;
    1143             :                                 }
    1144         151 :                                 if (dim == NULL) {
    1145           0 :                                         zend_error_noreturn(E_ERROR, "[] operator not supported for strings");
    1146             :                                 }
    1147             : 
    1148         151 :                                 if (type != BP_VAR_UNSET) {
    1149         460 :                                         SEPARATE_ZVAL_IF_NOT_REF(container_ptr);
    1150             :                                 }
    1151             : 
    1152         151 :                                 if (Z_TYPE_P(dim) != IS_LONG) {
    1153             : 
    1154          15 :                                         switch(Z_TYPE_P(dim)) {
    1155             :                                                 /* case IS_LONG: */
    1156             :                                                 case IS_STRING:
    1157          15 :                                                         if (IS_LONG == is_numeric_string(Z_STRVAL_P(dim), Z_STRLEN_P(dim), NULL, NULL, -1)) {
    1158           0 :                                                                 break;
    1159             :                                                         }
    1160          15 :                                                         if (type != BP_VAR_UNSET) {
    1161          14 :                                                                 zend_error(E_WARNING, "Illegal string offset '%s'", dim->value.str.val);
    1162             :                                                         }
    1163             : 
    1164          15 :                                                         break;
    1165             :                                                 case IS_DOUBLE:
    1166             :                                                 case IS_NULL:
    1167             :                                                 case IS_BOOL:
    1168           0 :                                                         zend_error(E_NOTICE, "String offset cast occurred");
    1169           0 :                                                         break;
    1170             :                                                 default:
    1171           0 :                                                         zend_error(E_WARNING, "Illegal offset type");
    1172             :                                                         break;
    1173             :                                         }
    1174             : 
    1175          15 :                                         tmp = *dim;
    1176             :                                         zval_copy_ctor(&tmp);
    1177          15 :                                         convert_to_long(&tmp);
    1178          15 :                                         dim = &tmp;
    1179             :                                 }
    1180         151 :                                 container = *container_ptr;
    1181         151 :                                 result->str_offset.str = container;
    1182             :                                 PZVAL_LOCK(container);
    1183         151 :                                 result->str_offset.offset = Z_LVAL_P(dim);
    1184         151 :                                 result->str_offset.ptr_ptr = NULL;
    1185         151 :                                 return;
    1186             :                         }
    1187             :                         break;
    1188             : 
    1189             :                 case IS_OBJECT:
    1190          51 :                         if (!Z_OBJ_HT_P(container)->read_dimension) {
    1191           0 :                                 zend_error_noreturn(E_ERROR, "Cannot use object as array");
    1192             :                         } else {
    1193             :                                 zval *overloaded_result;
    1194             : 
    1195          51 :                                 if (dim_type == IS_TMP_VAR) {
    1196           0 :                                         zval *orig = dim;
    1197           0 :                                         MAKE_REAL_ZVAL_PTR(dim);
    1198           0 :                                         ZVAL_NULL(orig);
    1199             :                                 }
    1200          51 :                                 overloaded_result = Z_OBJ_HT_P(container)->read_dimension(container, dim, type TSRMLS_CC);
    1201             : 
    1202          51 :                                 if (overloaded_result) {
    1203          96 :                                         if (!Z_ISREF_P(overloaded_result)) {
    1204          84 :                                                 if (Z_REFCOUNT_P(overloaded_result) > 0) {
    1205          11 :                                                         zval *tmp = overloaded_result;
    1206             : 
    1207          11 :                                                         ALLOC_ZVAL(overloaded_result);
    1208          11 :                                                         ZVAL_COPY_VALUE(overloaded_result, tmp);
    1209          11 :                                                         zval_copy_ctor(overloaded_result);
    1210          11 :                                                         Z_UNSET_ISREF_P(overloaded_result);
    1211          11 :                                                         Z_SET_REFCOUNT_P(overloaded_result, 0);
    1212             :                                                 }
    1213          42 :                                                 if (Z_TYPE_P(overloaded_result) != IS_OBJECT) {
    1214          11 :                                                         zend_class_entry *ce = Z_OBJCE_P(container);
    1215          11 :                                                         zend_error(E_NOTICE, "Indirect modification of overloaded element of %s has no effect", ce->name);
    1216             :                                                 }
    1217             :                                         }
    1218          48 :                                         retval = &overloaded_result;
    1219             :                                 } else {
    1220           3 :                                         retval = &EG(error_zval_ptr);
    1221             :                                 }
    1222          51 :                                 AI_SET_PTR(result, *retval);
    1223          51 :                                 PZVAL_LOCK(*retval);
    1224          51 :                                 if (dim_type == IS_TMP_VAR) {
    1225           0 :                                         zval_ptr_dtor(&dim);
    1226             :                                 }
    1227             :                         }
    1228          51 :                         return;
    1229             :                         break;
    1230             : 
    1231             :                 case IS_BOOL:
    1232          11 :                         if (type != BP_VAR_UNSET && Z_LVAL_P(container)==0) {
    1233           7 :                                 goto convert_to_array;
    1234             :                         }
    1235             :                         /* break missing intentionally */
    1236             : 
    1237             :                 default:
    1238          19 :                         if (type == BP_VAR_UNSET) {
    1239           0 :                                 zend_error(E_WARNING, "Cannot unset offset in a non-array variable");
    1240           0 :                                 AI_SET_PTR(result, &EG(uninitialized_zval));
    1241             :                                 PZVAL_LOCK(&EG(uninitialized_zval));
    1242             :                         } else {
    1243          19 :                                 zend_error(E_WARNING, "Cannot use a scalar value as an array");
    1244          19 :                                 result->var.ptr_ptr = &EG(error_zval_ptr);
    1245          19 :                                 PZVAL_LOCK(EG(error_zval_ptr));
    1246             :                         }
    1247             :                         break;
    1248             :         }
    1249             : }
    1250             : 
    1251     4824516 : static void zend_fetch_dimension_address_read(temp_variable *result, zval *container, zval *dim, int dim_type, int type TSRMLS_DC)
    1252             : {
    1253             :         zval **retval;
    1254             : 
    1255     4824516 :         switch (Z_TYPE_P(container)) {
    1256             : 
    1257             :                 case IS_ARRAY:
    1258     4791512 :                         retval = zend_fetch_dimension_address_inner(Z_ARRVAL_P(container), dim, dim_type, type TSRMLS_CC);
    1259     4791512 :                         AI_SET_PTR(result, *retval);
    1260     4791512 :                         PZVAL_LOCK(*retval);
    1261     4791512 :                         return;
    1262             : 
    1263             :                 case IS_NULL:
    1264          80 :                         AI_SET_PTR(result, &EG(uninitialized_zval));
    1265             :                         PZVAL_LOCK(&EG(uninitialized_zval));
    1266          80 :                         return;
    1267             : 
    1268             :                 case IS_STRING: {
    1269             :                                 zval tmp;
    1270             :                                 zval *ptr;
    1271             : 
    1272       32064 :                                 if (Z_TYPE_P(dim) != IS_LONG) {
    1273          44 :                                         switch(Z_TYPE_P(dim)) {
    1274             :                                                 /* case IS_LONG: */
    1275             :                                                 case IS_STRING:
    1276          28 :                                                         if (IS_LONG == is_numeric_string(Z_STRVAL_P(dim), Z_STRLEN_P(dim), NULL, NULL, -1)) {
    1277           1 :                                                                 break;
    1278             :                                                         }
    1279          27 :                                                         if (type != BP_VAR_IS) {
    1280          19 :                                                                 zend_error(E_WARNING, "Illegal string offset '%s'", dim->value.str.val);
    1281             :                                                         }
    1282          27 :                                                         break;
    1283             :                                                 case IS_DOUBLE:
    1284             :                                                 case IS_NULL:
    1285             :                                                 case IS_BOOL:
    1286          13 :                                                         if (type != BP_VAR_IS) {
    1287          11 :                                                                 zend_error(E_NOTICE, "String offset cast occurred");
    1288             :                                                         }
    1289          13 :                                                         break;
    1290             :                                                 default:
    1291           3 :                                                         zend_error(E_WARNING, "Illegal offset type");
    1292             :                                                         break;
    1293             :                                         }
    1294             : 
    1295          44 :                                         ZVAL_COPY_VALUE(&tmp, dim);
    1296             :                                         zval_copy_ctor(&tmp);
    1297          44 :                                         convert_to_long(&tmp);
    1298          44 :                                         dim = &tmp;
    1299             :                                 }
    1300             : 
    1301       32064 :                                 ALLOC_ZVAL(ptr);
    1302       32064 :                                 INIT_PZVAL(ptr);
    1303       32064 :                                 Z_TYPE_P(ptr) = IS_STRING;
    1304             : 
    1305       32104 :                                 if (Z_LVAL_P(dim) < 0 || Z_STRLEN_P(container) <= Z_LVAL_P(dim)) {
    1306          40 :                                         if (type != BP_VAR_IS) {
    1307          36 :                                                 zend_error(E_NOTICE, "Uninitialized string offset: %ld", Z_LVAL_P(dim));
    1308             :                                         }
    1309          40 :                                         Z_STRVAL_P(ptr) = STR_EMPTY_ALLOC();
    1310          40 :                                         Z_STRLEN_P(ptr) = 0;
    1311             :                                 } else {
    1312       32024 :                                         Z_STRVAL_P(ptr) = (char*)emalloc(2);
    1313       32024 :                                         Z_STRVAL_P(ptr)[0] = Z_STRVAL_P(container)[Z_LVAL_P(dim)];
    1314       32024 :                                         Z_STRVAL_P(ptr)[1] = 0;
    1315       32024 :                                         Z_STRLEN_P(ptr) = 1;
    1316             :                                 }
    1317       32064 :                                 AI_SET_PTR(result, ptr);
    1318       32064 :                                 return;
    1319             :                         }
    1320             :                         break;
    1321             : 
    1322             :                 case IS_OBJECT:
    1323         753 :                         if (!Z_OBJ_HT_P(container)->read_dimension) {
    1324           0 :                                 zend_error_noreturn(E_ERROR, "Cannot use object as array");
    1325             :                         } else {
    1326             :                                 zval *overloaded_result;
    1327             : 
    1328         753 :                                 if (dim_type == IS_TMP_VAR) {
    1329           6 :                                         zval *orig = dim;
    1330          12 :                                         MAKE_REAL_ZVAL_PTR(dim);
    1331           6 :                                         ZVAL_NULL(orig);
    1332             :                                 }
    1333         753 :                                 overloaded_result = Z_OBJ_HT_P(container)->read_dimension(container, dim, type TSRMLS_CC);
    1334             : 
    1335         749 :                                 if (overloaded_result) {
    1336         741 :                                         AI_SET_PTR(result, overloaded_result);
    1337             :                                         PZVAL_LOCK(overloaded_result);
    1338           8 :                                 } else if (result) {
    1339           8 :                                         AI_SET_PTR(result, &EG(uninitialized_zval));
    1340             :                                         PZVAL_LOCK(&EG(uninitialized_zval));
    1341             :                                 }
    1342         749 :                                 if (dim_type == IS_TMP_VAR) {
    1343           6 :                                         zval_ptr_dtor(&dim);
    1344             :                                 }
    1345             :                         }
    1346         749 :                         return;
    1347             : 
    1348             :                 default:
    1349         107 :                         AI_SET_PTR(result, &EG(uninitialized_zval));
    1350             :                         PZVAL_LOCK(&EG(uninitialized_zval));
    1351         107 :                         return;
    1352             :         }
    1353             : }
    1354             : 
    1355      175467 : static void zend_fetch_property_address(temp_variable *result, zval **container_ptr, zval *prop_ptr, const zend_literal *key, int type TSRMLS_DC)
    1356             : {
    1357      175467 :         zval *container = *container_ptr;;
    1358             : 
    1359      175467 :         if (Z_TYPE_P(container) != IS_OBJECT) {
    1360          44 :                 if (container == &EG(error_zval)) {
    1361           1 :                         result->var.ptr_ptr = &EG(error_zval_ptr);
    1362           1 :                         PZVAL_LOCK(EG(error_zval_ptr));
    1363           1 :                         return;
    1364             :                 }
    1365             : 
    1366             :                 /* this should modify object only if it's empty */
    1367         141 :                 if (type != BP_VAR_UNSET &&
    1368          43 :                     ((Z_TYPE_P(container) == IS_NULL ||
    1369           9 :                      (Z_TYPE_P(container) == IS_BOOL && Z_LVAL_P(container)==0) ||
    1370           9 :                      (Z_TYPE_P(container) == IS_STRING && Z_STRLEN_P(container)==0)))) {
    1371          37 :                         if (!PZVAL_IS_REF(container)) {
    1372         134 :                                 SEPARATE_ZVAL(container_ptr);
    1373          35 :                                 container = *container_ptr;
    1374             :                         }
    1375          37 :                         object_init(container);
    1376             :                 } else {
    1377           6 :                         zend_error(E_WARNING, "Attempt to modify property of non-object");
    1378           6 :                         result->var.ptr_ptr = &EG(error_zval_ptr);
    1379           6 :                         PZVAL_LOCK(EG(error_zval_ptr));
    1380           6 :                         return;
    1381             :                 }
    1382             :         }
    1383             : 
    1384      175460 :         if (Z_OBJ_HT_P(container)->get_property_ptr_ptr) {
    1385      175460 :                 zval **ptr_ptr = Z_OBJ_HT_P(container)->get_property_ptr_ptr(container, prop_ptr, key TSRMLS_CC);
    1386      175459 :                 if (NULL == ptr_ptr) {
    1387             :                         zval *ptr;
    1388             : 
    1389         162 :                         if (Z_OBJ_HT_P(container)->read_property &&
    1390          54 :                                 (ptr = Z_OBJ_HT_P(container)->read_property(container, prop_ptr, type, key TSRMLS_CC)) != NULL) {
    1391          54 :                                 AI_SET_PTR(result, ptr);
    1392             :                                 PZVAL_LOCK(ptr);
    1393             :                         } else {
    1394           0 :                                 zend_error_noreturn(E_ERROR, "Cannot access undefined property for object with overloaded property access");
    1395             :                         }
    1396             :                 } else {
    1397      175405 :                         result->var.ptr_ptr = ptr_ptr;
    1398      175405 :                         PZVAL_LOCK(*ptr_ptr);
    1399             :                 }
    1400           0 :         } else if (Z_OBJ_HT_P(container)->read_property) {
    1401           0 :                 zval *ptr = Z_OBJ_HT_P(container)->read_property(container, prop_ptr, type, key TSRMLS_CC);
    1402             : 
    1403           0 :                 AI_SET_PTR(result, ptr);
    1404             :                 PZVAL_LOCK(ptr);
    1405             :         } else {
    1406           0 :                 zend_error(E_WARNING, "This object doesn't support property references");
    1407           0 :                 result->var.ptr_ptr = &EG(error_zval_ptr);
    1408           0 :                 PZVAL_LOCK(EG(error_zval_ptr));
    1409             :         }
    1410             : }
    1411             : 
    1412       75919 : static inline zend_brk_cont_element* zend_brk_cont(int nest_levels, int array_offset, const zend_op_array *op_array, const temp_variable *Ts TSRMLS_DC)
    1413             : {
    1414       75919 :         int original_nest_levels = nest_levels;
    1415             :         zend_brk_cont_element *jmp_to;
    1416             : 
    1417             :         do {
    1418       76076 :                 if (array_offset==-1) {
    1419           0 :                         zend_error_noreturn(E_ERROR, "Cannot break/continue %d level%s", original_nest_levels, (original_nest_levels == 1) ? "" : "s");
    1420             :                 }
    1421       76076 :                 jmp_to = &op_array->brk_cont_array[array_offset];
    1422       76076 :                 if (nest_levels>1) {
    1423         157 :                         zend_op *brk_opline = &op_array->opcodes[jmp_to->brk];
    1424             : 
    1425         157 :                         switch (brk_opline->opcode) {
    1426             :                                 case ZEND_SWITCH_FREE:
    1427           2 :                                         if (!(brk_opline->extended_value & EXT_TYPE_FREE_ON_RETURN)) {
    1428           0 :                                                 zval_ptr_dtor(&T(brk_opline->op1.var).var.ptr);
    1429             :                                         }
    1430           2 :                                         break;
    1431             :                                 case ZEND_FREE:
    1432           0 :                                         if (!(brk_opline->extended_value & EXT_TYPE_FREE_ON_RETURN)) {
    1433           0 :                                                 zendi_zval_dtor(T(brk_opline->op1.var).tmp_var);
    1434             :                                         }
    1435             :                                         break;
    1436             :                         }
    1437             :                 }
    1438       76076 :                 array_offset = jmp_to->parent;
    1439       76076 :         } while (--nest_levels > 0);
    1440       75919 :         return jmp_to;
    1441             : }
    1442             : 
    1443             : #if ZEND_INTENSIVE_DEBUGGING
    1444             : 
    1445             : #define CHECK_SYMBOL_TABLES()                                                                                                           \
    1446             :         zend_hash_apply(&EG(symbol_table), (apply_func_t) zend_check_symbol TSRMLS_CC);     \
    1447             :         if (&EG(symbol_table)!=EG(active_symbol_table)) {                                                           \
    1448             :                 zend_hash_apply(EG(active_symbol_table), (apply_func_t) zend_check_symbol TSRMLS_CC);   \
    1449             :         }
    1450             : 
    1451             : static int zend_check_symbol(zval **pz TSRMLS_DC)
    1452             : {
    1453             :         if (Z_TYPE_PP(pz) > 9) {
    1454             :                 fprintf(stderr, "Warning!  %x has invalid type!\n", *pz);
    1455             : /* See http://support.microsoft.com/kb/190351 */
    1456             : #ifdef PHP_WIN32
    1457             :                 fflush(stderr);
    1458             : #endif
    1459             :         } else if (Z_TYPE_PP(pz) == IS_ARRAY) {
    1460             :                 zend_hash_apply(Z_ARRVAL_PP(pz), (apply_func_t) zend_check_symbol TSRMLS_CC);
    1461             :         } else if (Z_TYPE_PP(pz) == IS_OBJECT) {
    1462             : 
    1463             :                 /* OBJ-TBI - doesn't support new object model! */
    1464             :                 zend_hash_apply(Z_OBJPROP_PP(pz), (apply_func_t) zend_check_symbol TSRMLS_CC);
    1465             :         }
    1466             : 
    1467             :         return 0;
    1468             : }
    1469             : 
    1470             : 
    1471             : #else
    1472             : #define CHECK_SYMBOL_TABLES()
    1473             : #endif
    1474             : 
    1475             : ZEND_API opcode_handler_t *zend_opcode_handlers;
    1476             : 
    1477           0 : ZEND_API void execute_internal(zend_execute_data *execute_data_ptr, int return_value_used TSRMLS_DC)
    1478             : {
    1479           0 :         zval **return_value_ptr = &(*(temp_variable *)((char *) execute_data_ptr->Ts + execute_data_ptr->opline->result.var)).var.ptr;
    1480           0 :         ((zend_internal_function *) execute_data_ptr->function_state.function)->handler(execute_data_ptr->opline->extended_value, *return_value_ptr, (execute_data_ptr->function_state.function->common.fn_flags & ZEND_ACC_RETURN_REFERENCE)?return_value_ptr:NULL, execute_data_ptr->object, return_value_used TSRMLS_CC);
    1481           0 : }
    1482             : 
    1483             : #define ZEND_VM_NEXT_OPCODE() \
    1484             :         CHECK_SYMBOL_TABLES() \
    1485             :         ZEND_VM_INC_OPCODE(); \
    1486             :         ZEND_VM_CONTINUE()
    1487             : 
    1488             : #define ZEND_VM_SET_OPCODE(new_op) \
    1489             :         CHECK_SYMBOL_TABLES() \
    1490             :         OPLINE = new_op
    1491             : 
    1492             : #define ZEND_VM_JMP(new_op) \
    1493             :         if (EXPECTED(!EG(exception))) { \
    1494             :                 ZEND_VM_SET_OPCODE(new_op); \
    1495             :         } else { \
    1496             :                 LOAD_OPLINE(); \
    1497             :         } \
    1498             :         ZEND_VM_CONTINUE()
    1499             : 
    1500             : #define ZEND_VM_INC_OPCODE() \
    1501             :         OPLINE++
    1502             : 
    1503             : #ifdef __GNUC__
    1504             : # define ZEND_VM_GUARD(name) __asm__("#" #name)
    1505             : #else
    1506             : # define ZEND_VM_GUARD(name)
    1507             : #endif
    1508             : 
    1509             : #include "zend_vm_execute.h"
    1510             : 
    1511           0 : ZEND_API int zend_set_user_opcode_handler(zend_uchar opcode, user_opcode_handler_t handler)
    1512             : {
    1513           0 :         if (opcode != ZEND_USER_OPCODE) {
    1514           0 :                 if (handler == NULL) {
    1515             :                         /* restore the original handler */                      
    1516           0 :                         zend_user_opcodes[opcode] = opcode;
    1517             :                 } else {
    1518           0 :                         zend_user_opcodes[opcode] = ZEND_USER_OPCODE;
    1519             :                 }
    1520           0 :                 zend_user_opcode_handlers[opcode] = handler;
    1521           0 :                 return SUCCESS;
    1522             :         }
    1523           0 :         return FAILURE;
    1524             : }
    1525             : 
    1526           0 : ZEND_API user_opcode_handler_t zend_get_user_opcode_handler(zend_uchar opcode)
    1527             : {
    1528           0 :         return zend_user_opcode_handlers[opcode];
    1529             : }
    1530             : 
    1531           0 : ZEND_API zval *zend_get_zval_ptr(int op_type, const znode_op *node, const temp_variable *Ts, zend_free_op *should_free, int type TSRMLS_DC) {
    1532           0 :         return get_zval_ptr(op_type, node, Ts, should_free, type);
    1533             : }
    1534             : 
    1535           0 : ZEND_API zval **zend_get_zval_ptr_ptr(int op_type, const znode_op *node, const temp_variable *Ts, zend_free_op *should_free, int type TSRMLS_DC) {
    1536           0 :         return get_zval_ptr_ptr(op_type, node, Ts, should_free, type);
    1537             : }
    1538             : 
    1539             : /*
    1540             :  * Local variables:
    1541             :  * tab-width: 4
    1542             :  * c-basic-offset: 4
    1543             :  * indent-tabs-mode: t
    1544             :  * End:
    1545             :  */

Generated by: LCOV version 1.10

Generated at Sun, 17 Aug 2014 15:21:45 +0000 (4 days ago)

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