@@ -2191,6 +2191,25 @@ static uint32_t zend_fetch_prop_type(const zend_script *script, zend_property_in
21912191 return MAY_BE_ANY | MAY_BE_ARRAY_KEY_ANY | MAY_BE_ARRAY_OF_ANY | MAY_BE_ARRAY_OF_REF | MAY_BE_RC1 | MAY_BE_RCN ;
21922192}
21932193
2194+ static zend_bool result_may_be_separated (zend_ssa * ssa , zend_ssa_op * ssa_op )
2195+ {
2196+ int tmp_var = ssa_op -> result_def ;
2197+
2198+ if (ssa -> vars [tmp_var ].use_chain >= 0
2199+ && !ssa -> vars [tmp_var ].phi_use_chain ) {
2200+ zend_ssa_op * use_op = & ssa -> ops [ssa -> vars [tmp_var ].use_chain ];
2201+
2202+ /* TODO: analize instructions between ssa_op and use_op */
2203+ if (use_op == ssa_op + 1 ) {
2204+ if ((use_op -> op1_use == tmp_var && use_op -> op1_use_chain < 0 )
2205+ || (use_op -> op2_use == tmp_var && use_op -> op2_use_chain < 0 )) {
2206+ return 0 ;
2207+ }
2208+ }
2209+ }
2210+ return 1 ;
2211+ }
2212+
21942213static zend_always_inline int _zend_update_type_info (
21952214 const zend_op_array * op_array ,
21962215 zend_ssa * ssa ,
@@ -3307,11 +3326,11 @@ static zend_always_inline int _zend_update_type_info(
33073326 if (prop_info ) {
33083327 /* FETCH_OBJ_R/IS for plain property increments reference counter,
33093328 so it can't be 1 */
3310- if (ce && !ce -> create_object ) {
3329+ if (ce && !ce -> create_object && ! result_may_be_separated ( ssa , ssa_op ) ) {
33113330 tmp &= ~MAY_BE_RC1 ;
33123331 }
33133332 } else {
3314- if (ce && !ce -> create_object && !ce -> __get ) {
3333+ if (ce && !ce -> create_object && !ce -> __get && ! result_may_be_separated ( ssa , ssa_op ) ) {
33153334 tmp &= ~MAY_BE_RC1 ;
33163335 }
33173336 }
@@ -3336,7 +3355,7 @@ static zend_always_inline int _zend_update_type_info(
33363355 zend_fetch_static_prop_info (script , op_array , ssa , opline ), & ce );
33373356 if (opline -> result_type != IS_TMP_VAR ) {
33383357 tmp |= MAY_BE_REF | MAY_BE_INDIRECT ;
3339- } else {
3358+ } else if (! result_may_be_separated ( ssa , ssa_op )) {
33403359 tmp &= ~MAY_BE_RC1 ;
33413360 }
33423361 UPDATE_SSA_TYPE (tmp , ssa_op -> result_def );
0 commit comments