]> granicus.if.org Git - php/commitdiff
Improved specialization (IS_CONST can't be IS_OBJECT)
authorDmitry Stogov <dmitry@php.net>
Wed, 8 Apr 2009 13:19:34 +0000 (13:19 +0000)
committerDmitry Stogov <dmitry@php.net>
Wed, 8 Apr 2009 13:19:34 +0000 (13:19 +0000)
Zend/zend_vm_def.h
Zend/zend_vm_execute.h

index 24c51f39f6ccc031d41e4774d03ffb464a9ef1c9..b4ee7be7cbbfe50683d0a39b302b7c5ce971b4c1 100644 (file)
@@ -899,7 +899,8 @@ ZEND_VM_HANDLER(40, ZEND_ECHO, CONST|TMP|VAR|CV, ANY)
        zval z_copy;
        zval *z = GET_OP1_ZVAL_PTR(BP_VAR_R);
 
-       if (Z_TYPE_P(z) == IS_OBJECT && Z_OBJ_HT_P(z)->get_method != NULL &&
+       if (OP1_TYPE != IS_CONST &&
+           Z_TYPE_P(z) == IS_OBJECT && Z_OBJ_HT_P(z)->get_method != NULL &&
                zend_std_cast_object_tostring(z, &z_copy, IS_STRING TSRMLS_CC) == SUCCESS) {
                zend_print_variable(&z_copy);
                zval_dtor(&z_copy);
@@ -1892,31 +1893,26 @@ ZEND_VM_HANDLER(56, ZEND_ADD_VAR, TMP|UNUSED, TMP|VAR|CV)
 ZEND_VM_HANDLER(109, ZEND_FETCH_CLASS, ANY, CONST|TMP|VAR|UNUSED|CV)
 {
        zend_op *opline = EX(opline);
-       zval *class_name;
-       zend_free_op free_op2;
 
 
        if (OP2_TYPE == IS_UNUSED) {
                EX_T(opline->result.u.var).class_entry = zend_fetch_class(NULL, 0, opline->extended_value TSRMLS_CC);
                ZEND_VM_NEXT_OPCODE();
-       }
-
-       class_name = GET_OP2_ZVAL_PTR(BP_VAR_R);
+       } else {
+               zend_free_op free_op2;
+               zval *class_name = GET_OP2_ZVAL_PTR(BP_VAR_R);
 
-       switch (Z_TYPE_P(class_name)) {
-               case IS_OBJECT:
+               if (OP2_TYPE != IS_CONST && Z_TYPE_P(class_name) == IS_OBJECT) {
                        EX_T(opline->result.u.var).class_entry = Z_OBJCE_P(class_name);
-                       break;
-               case IS_STRING:
+               } else if (Z_TYPE_P(class_name) == IS_STRING) {
                        EX_T(opline->result.u.var).class_entry = zend_fetch_class(Z_STRVAL_P(class_name), Z_STRLEN_P(class_name), opline->extended_value TSRMLS_CC);
-                       break;
-               default:
+               } else {
                        zend_error_noreturn(E_ERROR, "Class name must be a valid object or a string");
-                       break;
-       }
+               }
 
-       FREE_OP2();
-       ZEND_VM_NEXT_OPCODE();
+               FREE_OP2();
+               ZEND_VM_NEXT_OPCODE();
+       }
 }
 
 ZEND_VM_HANDLER(112, ZEND_INIT_METHOD_CALL, TMP|VAR|UNUSED|CV, CONST|TMP|VAR|CV)
@@ -2090,7 +2086,8 @@ ZEND_VM_HANDLER(59, ZEND_INIT_FCALL_BY_NAME, ANY, CONST|TMP|VAR|CV)
        } else {
                function_name = GET_OP2_ZVAL_PTR(BP_VAR_R);
 
-               if (Z_TYPE_P(function_name) == IS_OBJECT &&
+               if (OP2_TYPE != IS_CONST &&
+                   Z_TYPE_P(function_name) == IS_OBJECT &&
                        Z_OBJ_HANDLER_P(function_name, get_closure) &&
                        Z_OBJ_HANDLER_P(function_name, get_closure)(function_name, &EX(called_scope), &EX(fbc), &EX(object) TSRMLS_CC) == SUCCESS) {
                        if (EX(object)) {
@@ -2524,7 +2521,7 @@ ZEND_VM_HANDLER(108, ZEND_THROW, CONST|TMP|VAR|CV, ANY)
 
        value = GET_OP1_ZVAL_PTR(BP_VAR_R);
 
-       if (Z_TYPE_P(value) != IS_OBJECT) {
+       if (OP1_TYPE == IS_CONST || Z_TYPE_P(value) != IS_OBJECT) {
                zend_error_noreturn(E_ERROR, "Can only throw objects");
        }
        zend_exception_save(TSRMLS_C);
@@ -2936,7 +2933,9 @@ ZEND_VM_HANDLER(110, ZEND_CLONE, CONST|TMP|VAR|UNUSED|CV, ANY)
        zend_function *clone;
        zend_object_clone_obj_t clone_call;
 
-       if (!obj || Z_TYPE_P(obj) != IS_OBJECT) {
+       if (OP1_TYPE == IS_CONST ||
+           (OP1_TYPE == IS_VAR && !obj) ||
+           Z_TYPE_P(obj) != IS_OBJECT) {
                zend_error_noreturn(E_ERROR, "__clone method called on non-object");
        }
 
index fe902cb2445701c19fc3e0ea9c78fdbd96c7e6f6..bf3419ffc1121727f73ebb70a6c3e763f6251791 100644 (file)
@@ -709,30 +709,25 @@ static int ZEND_FASTCALL  ZEND_USER_OPCODE_SPEC_HANDLER(ZEND_OPCODE_HANDLER_ARGS
 static int ZEND_FASTCALL  ZEND_FETCH_CLASS_SPEC_CONST_HANDLER(ZEND_OPCODE_HANDLER_ARGS)
 {
        zend_op *opline = EX(opline);
-       zval *class_name;
-
 
 
        if (IS_CONST == IS_UNUSED) {
                EX_T(opline->result.u.var).class_entry = zend_fetch_class(NULL, 0, opline->extended_value TSRMLS_CC);
                ZEND_VM_NEXT_OPCODE();
-       }
+       } else {
 
-       class_name = &opline->op2.u.constant;
+               zval *class_name = &opline->op2.u.constant;
 
-       switch (Z_TYPE_P(class_name)) {
-               case IS_OBJECT:
+               if (IS_CONST != IS_CONST && Z_TYPE_P(class_name) == IS_OBJECT) {
                        EX_T(opline->result.u.var).class_entry = Z_OBJCE_P(class_name);
-                       break;
-               case IS_STRING:
+               } else if (Z_TYPE_P(class_name) == IS_STRING) {
                        EX_T(opline->result.u.var).class_entry = zend_fetch_class(Z_STRVAL_P(class_name), Z_STRLEN_P(class_name), opline->extended_value TSRMLS_CC);
-                       break;
-               default:
+               } else {
                        zend_error_noreturn(E_ERROR, "Class name must be a valid object or a string");
-                       break;
-       }
+               }
 
-       ZEND_VM_NEXT_OPCODE();
+               ZEND_VM_NEXT_OPCODE();
+       }
 }
 
 static int ZEND_FASTCALL  ZEND_INIT_FCALL_BY_NAME_SPEC_CONST_HANDLER(ZEND_OPCODE_HANDLER_ARGS)
@@ -752,7 +747,8 @@ static int ZEND_FASTCALL  ZEND_INIT_FCALL_BY_NAME_SPEC_CONST_HANDLER(ZEND_OPCODE
        } else {
                function_name = &opline->op2.u.constant;
 
-               if (Z_TYPE_P(function_name) == IS_OBJECT &&
+               if (IS_CONST != IS_CONST &&
+                   Z_TYPE_P(function_name) == IS_OBJECT &&
                        Z_OBJ_HANDLER_P(function_name, get_closure) &&
                        Z_OBJ_HANDLER_P(function_name, get_closure)(function_name, &EX(called_scope), &EX(fbc), &EX(object) TSRMLS_CC) == SUCCESS) {
                        if (EX(object)) {
@@ -905,31 +901,26 @@ static int ZEND_FASTCALL  ZEND_ADD_INTERFACE_SPEC_CONST_HANDLER(ZEND_OPCODE_HAND
 static int ZEND_FASTCALL  ZEND_FETCH_CLASS_SPEC_TMP_HANDLER(ZEND_OPCODE_HANDLER_ARGS)
 {
        zend_op *opline = EX(opline);
-       zval *class_name;
-       zend_free_op free_op2;
 
 
        if (IS_TMP_VAR == IS_UNUSED) {
                EX_T(opline->result.u.var).class_entry = zend_fetch_class(NULL, 0, opline->extended_value TSRMLS_CC);
                ZEND_VM_NEXT_OPCODE();
-       }
-
-       class_name = _get_zval_ptr_tmp(&opline->op2, EX(Ts), &free_op2 TSRMLS_CC);
+       } else {
+               zend_free_op free_op2;
+               zval *class_name = _get_zval_ptr_tmp(&opline->op2, EX(Ts), &free_op2 TSRMLS_CC);
 
-       switch (Z_TYPE_P(class_name)) {
-               case IS_OBJECT:
+               if (IS_TMP_VAR != IS_CONST && Z_TYPE_P(class_name) == IS_OBJECT) {
                        EX_T(opline->result.u.var).class_entry = Z_OBJCE_P(class_name);
-                       break;
-               case IS_STRING:
+               } else if (Z_TYPE_P(class_name) == IS_STRING) {
                        EX_T(opline->result.u.var).class_entry = zend_fetch_class(Z_STRVAL_P(class_name), Z_STRLEN_P(class_name), opline->extended_value TSRMLS_CC);
-                       break;
-               default:
+               } else {
                        zend_error_noreturn(E_ERROR, "Class name must be a valid object or a string");
-                       break;
-       }
+               }
 
-       zval_dtor(free_op2.var);
-       ZEND_VM_NEXT_OPCODE();
+               zval_dtor(free_op2.var);
+               ZEND_VM_NEXT_OPCODE();
+       }
 }
 
 static int ZEND_FASTCALL  ZEND_INIT_FCALL_BY_NAME_SPEC_TMP_HANDLER(ZEND_OPCODE_HANDLER_ARGS)
@@ -949,7 +940,8 @@ static int ZEND_FASTCALL  ZEND_INIT_FCALL_BY_NAME_SPEC_TMP_HANDLER(ZEND_OPCODE_H
        } else {
                function_name = _get_zval_ptr_tmp(&opline->op2, EX(Ts), &free_op2 TSRMLS_CC);
 
-               if (Z_TYPE_P(function_name) == IS_OBJECT &&
+               if (IS_TMP_VAR != IS_CONST &&
+                   Z_TYPE_P(function_name) == IS_OBJECT &&
                        Z_OBJ_HANDLER_P(function_name, get_closure) &&
                        Z_OBJ_HANDLER_P(function_name, get_closure)(function_name, &EX(called_scope), &EX(fbc), &EX(object) TSRMLS_CC) == SUCCESS) {
                        if (EX(object)) {
@@ -1010,31 +1002,26 @@ static int ZEND_FASTCALL  ZEND_CONT_SPEC_TMP_HANDLER(ZEND_OPCODE_HANDLER_ARGS)
 static int ZEND_FASTCALL  ZEND_FETCH_CLASS_SPEC_VAR_HANDLER(ZEND_OPCODE_HANDLER_ARGS)
 {
        zend_op *opline = EX(opline);
-       zval *class_name;
-       zend_free_op free_op2;
 
 
        if (IS_VAR == IS_UNUSED) {
                EX_T(opline->result.u.var).class_entry = zend_fetch_class(NULL, 0, opline->extended_value TSRMLS_CC);
                ZEND_VM_NEXT_OPCODE();
-       }
-
-       class_name = _get_zval_ptr_var(&opline->op2, EX(Ts), &free_op2 TSRMLS_CC);
+       } else {
+               zend_free_op free_op2;
+               zval *class_name = _get_zval_ptr_var(&opline->op2, EX(Ts), &free_op2 TSRMLS_CC);
 
-       switch (Z_TYPE_P(class_name)) {
-               case IS_OBJECT:
+               if (IS_VAR != IS_CONST && Z_TYPE_P(class_name) == IS_OBJECT) {
                        EX_T(opline->result.u.var).class_entry = Z_OBJCE_P(class_name);
-                       break;
-               case IS_STRING:
+               } else if (Z_TYPE_P(class_name) == IS_STRING) {
                        EX_T(opline->result.u.var).class_entry = zend_fetch_class(Z_STRVAL_P(class_name), Z_STRLEN_P(class_name), opline->extended_value TSRMLS_CC);
-                       break;
-               default:
+               } else {
                        zend_error_noreturn(E_ERROR, "Class name must be a valid object or a string");
-                       break;
-       }
+               }
 
-       if (free_op2.var) {zval_ptr_dtor(&free_op2.var);};
-       ZEND_VM_NEXT_OPCODE();
+               if (free_op2.var) {zval_ptr_dtor(&free_op2.var);};
+               ZEND_VM_NEXT_OPCODE();
+       }
 }
 
 static int ZEND_FASTCALL  ZEND_INIT_FCALL_BY_NAME_SPEC_VAR_HANDLER(ZEND_OPCODE_HANDLER_ARGS)
@@ -1054,7 +1041,8 @@ static int ZEND_FASTCALL  ZEND_INIT_FCALL_BY_NAME_SPEC_VAR_HANDLER(ZEND_OPCODE_H
        } else {
                function_name = _get_zval_ptr_var(&opline->op2, EX(Ts), &free_op2 TSRMLS_CC);
 
-               if (Z_TYPE_P(function_name) == IS_OBJECT &&
+               if (IS_VAR != IS_CONST &&
+                   Z_TYPE_P(function_name) == IS_OBJECT &&
                        Z_OBJ_HANDLER_P(function_name, get_closure) &&
                        Z_OBJ_HANDLER_P(function_name, get_closure)(function_name, &EX(called_scope), &EX(fbc), &EX(object) TSRMLS_CC) == SUCCESS) {
                        if (EX(object)) {
@@ -1115,59 +1103,49 @@ static int ZEND_FASTCALL  ZEND_CONT_SPEC_VAR_HANDLER(ZEND_OPCODE_HANDLER_ARGS)
 static int ZEND_FASTCALL  ZEND_FETCH_CLASS_SPEC_UNUSED_HANDLER(ZEND_OPCODE_HANDLER_ARGS)
 {
        zend_op *opline = EX(opline);
-       zval *class_name;
-
 
 
        if (IS_UNUSED == IS_UNUSED) {
                EX_T(opline->result.u.var).class_entry = zend_fetch_class(NULL, 0, opline->extended_value TSRMLS_CC);
                ZEND_VM_NEXT_OPCODE();
-       }
+       } else {
 
-       class_name = NULL;
+               zval *class_name = NULL;
 
-       switch (Z_TYPE_P(class_name)) {
-               case IS_OBJECT:
+               if (IS_UNUSED != IS_CONST && Z_TYPE_P(class_name) == IS_OBJECT) {
                        EX_T(opline->result.u.var).class_entry = Z_OBJCE_P(class_name);
-                       break;
-               case IS_STRING:
+               } else if (Z_TYPE_P(class_name) == IS_STRING) {
                        EX_T(opline->result.u.var).class_entry = zend_fetch_class(Z_STRVAL_P(class_name), Z_STRLEN_P(class_name), opline->extended_value TSRMLS_CC);
-                       break;
-               default:
+               } else {
                        zend_error_noreturn(E_ERROR, "Class name must be a valid object or a string");
-                       break;
-       }
+               }
 
-       ZEND_VM_NEXT_OPCODE();
+               ZEND_VM_NEXT_OPCODE();
+       }
 }
 
 static int ZEND_FASTCALL  ZEND_FETCH_CLASS_SPEC_CV_HANDLER(ZEND_OPCODE_HANDLER_ARGS)
 {
        zend_op *opline = EX(opline);
-       zval *class_name;
-
 
 
        if (IS_CV == IS_UNUSED) {
                EX_T(opline->result.u.var).class_entry = zend_fetch_class(NULL, 0, opline->extended_value TSRMLS_CC);
                ZEND_VM_NEXT_OPCODE();
-       }
+       } else {
 
-       class_name = _get_zval_ptr_cv(&opline->op2, EX(Ts), BP_VAR_R TSRMLS_CC);
+               zval *class_name = _get_zval_ptr_cv(&opline->op2, EX(Ts), BP_VAR_R TSRMLS_CC);
 
-       switch (Z_TYPE_P(class_name)) {
-               case IS_OBJECT:
+               if (IS_CV != IS_CONST && Z_TYPE_P(class_name) == IS_OBJECT) {
                        EX_T(opline->result.u.var).class_entry = Z_OBJCE_P(class_name);
-                       break;
-               case IS_STRING:
+               } else if (Z_TYPE_P(class_name) == IS_STRING) {
                        EX_T(opline->result.u.var).class_entry = zend_fetch_class(Z_STRVAL_P(class_name), Z_STRLEN_P(class_name), opline->extended_value TSRMLS_CC);
-                       break;
-               default:
+               } else {
                        zend_error_noreturn(E_ERROR, "Class name must be a valid object or a string");
-                       break;
-       }
+               }
 
-       ZEND_VM_NEXT_OPCODE();
+               ZEND_VM_NEXT_OPCODE();
+       }
 }
 
 static int ZEND_FASTCALL  ZEND_INIT_FCALL_BY_NAME_SPEC_CV_HANDLER(ZEND_OPCODE_HANDLER_ARGS)
@@ -1187,7 +1165,8 @@ static int ZEND_FASTCALL  ZEND_INIT_FCALL_BY_NAME_SPEC_CV_HANDLER(ZEND_OPCODE_HA
        } else {
                function_name = _get_zval_ptr_cv(&opline->op2, EX(Ts), BP_VAR_R TSRMLS_CC);
 
-               if (Z_TYPE_P(function_name) == IS_OBJECT &&
+               if (IS_CV != IS_CONST &&
+                   Z_TYPE_P(function_name) == IS_OBJECT &&
                        Z_OBJ_HANDLER_P(function_name, get_closure) &&
                        Z_OBJ_HANDLER_P(function_name, get_closure)(function_name, &EX(called_scope), &EX(fbc), &EX(object) TSRMLS_CC) == SUCCESS) {
                        if (EX(object)) {
@@ -1312,7 +1291,8 @@ static int ZEND_FASTCALL  ZEND_ECHO_SPEC_CONST_HANDLER(ZEND_OPCODE_HANDLER_ARGS)
        zval z_copy;
        zval *z = &opline->op1.u.constant;
 
-       if (Z_TYPE_P(z) == IS_OBJECT && Z_OBJ_HT_P(z)->get_method != NULL &&
+       if (IS_CONST != IS_CONST &&
+           Z_TYPE_P(z) == IS_OBJECT && Z_OBJ_HT_P(z)->get_method != NULL &&
                zend_std_cast_object_tostring(z, &z_copy, IS_STRING TSRMLS_CC) == SUCCESS) {
                zend_print_variable(&z_copy);
                zval_dtor(&z_copy);
@@ -1704,7 +1684,7 @@ static int ZEND_FASTCALL  ZEND_THROW_SPEC_CONST_HANDLER(ZEND_OPCODE_HANDLER_ARGS
 
        value = &opline->op1.u.constant;
 
-       if (Z_TYPE_P(value) != IS_OBJECT) {
+       if (IS_CONST == IS_CONST || Z_TYPE_P(value) != IS_OBJECT) {
                zend_error_noreturn(E_ERROR, "Can only throw objects");
        }
        zend_exception_save(TSRMLS_C);
@@ -1767,7 +1747,9 @@ static int ZEND_FASTCALL  ZEND_CLONE_SPEC_CONST_HANDLER(ZEND_OPCODE_HANDLER_ARGS
        zend_function *clone;
        zend_object_clone_obj_t clone_call;
 
-       if (!obj || Z_TYPE_P(obj) != IS_OBJECT) {
+       if (IS_CONST == IS_CONST ||
+           (IS_CONST == IS_VAR && !obj) ||
+           Z_TYPE_P(obj) != IS_OBJECT) {
                zend_error_noreturn(E_ERROR, "__clone method called on non-object");
        }
 
@@ -4589,7 +4571,8 @@ static int ZEND_FASTCALL  ZEND_ECHO_SPEC_TMP_HANDLER(ZEND_OPCODE_HANDLER_ARGS)
        zval z_copy;
        zval *z = _get_zval_ptr_tmp(&opline->op1, EX(Ts), &free_op1 TSRMLS_CC);
 
-       if (Z_TYPE_P(z) == IS_OBJECT && Z_OBJ_HT_P(z)->get_method != NULL &&
+       if (IS_TMP_VAR != IS_CONST &&
+           Z_TYPE_P(z) == IS_OBJECT && Z_OBJ_HT_P(z)->get_method != NULL &&
                zend_std_cast_object_tostring(z, &z_copy, IS_STRING TSRMLS_CC) == SUCCESS) {
                zend_print_variable(&z_copy);
                zval_dtor(&z_copy);
@@ -4972,7 +4955,7 @@ static int ZEND_FASTCALL  ZEND_THROW_SPEC_TMP_HANDLER(ZEND_OPCODE_HANDLER_ARGS)
 
        value = _get_zval_ptr_tmp(&opline->op1, EX(Ts), &free_op1 TSRMLS_CC);
 
-       if (Z_TYPE_P(value) != IS_OBJECT) {
+       if (IS_TMP_VAR == IS_CONST || Z_TYPE_P(value) != IS_OBJECT) {
                zend_error_noreturn(E_ERROR, "Can only throw objects");
        }
        zend_exception_save(TSRMLS_C);
@@ -5036,7 +5019,9 @@ static int ZEND_FASTCALL  ZEND_CLONE_SPEC_TMP_HANDLER(ZEND_OPCODE_HANDLER_ARGS)
        zend_function *clone;
        zend_object_clone_obj_t clone_call;
 
-       if (!obj || Z_TYPE_P(obj) != IS_OBJECT) {
+       if (IS_TMP_VAR == IS_CONST ||
+           (IS_TMP_VAR == IS_VAR && !obj) ||
+           Z_TYPE_P(obj) != IS_OBJECT) {
                zend_error_noreturn(E_ERROR, "__clone method called on non-object");
        }
 
@@ -7832,7 +7817,8 @@ static int ZEND_FASTCALL  ZEND_ECHO_SPEC_VAR_HANDLER(ZEND_OPCODE_HANDLER_ARGS)
        zval z_copy;
        zval *z = _get_zval_ptr_var(&opline->op1, EX(Ts), &free_op1 TSRMLS_CC);
 
-       if (Z_TYPE_P(z) == IS_OBJECT && Z_OBJ_HT_P(z)->get_method != NULL &&
+       if (IS_VAR != IS_CONST &&
+           Z_TYPE_P(z) == IS_OBJECT && Z_OBJ_HT_P(z)->get_method != NULL &&
                zend_std_cast_object_tostring(z, &z_copy, IS_STRING TSRMLS_CC) == SUCCESS) {
                zend_print_variable(&z_copy);
                zval_dtor(&z_copy);
@@ -8209,7 +8195,7 @@ static int ZEND_FASTCALL  ZEND_THROW_SPEC_VAR_HANDLER(ZEND_OPCODE_HANDLER_ARGS)
 
        value = _get_zval_ptr_var(&opline->op1, EX(Ts), &free_op1 TSRMLS_CC);
 
-       if (Z_TYPE_P(value) != IS_OBJECT) {
+       if (IS_VAR == IS_CONST || Z_TYPE_P(value) != IS_OBJECT) {
                zend_error_noreturn(E_ERROR, "Can only throw objects");
        }
        zend_exception_save(TSRMLS_C);
@@ -8388,7 +8374,9 @@ static int ZEND_FASTCALL  ZEND_CLONE_SPEC_VAR_HANDLER(ZEND_OPCODE_HANDLER_ARGS)
        zend_function *clone;
        zend_object_clone_obj_t clone_call;
 
-       if (!obj || Z_TYPE_P(obj) != IS_OBJECT) {
+       if (IS_VAR == IS_CONST ||
+           (IS_VAR == IS_VAR && !obj) ||
+           Z_TYPE_P(obj) != IS_OBJECT) {
                zend_error_noreturn(E_ERROR, "__clone method called on non-object");
        }
 
@@ -16922,7 +16910,9 @@ static int ZEND_FASTCALL  ZEND_CLONE_SPEC_UNUSED_HANDLER(ZEND_OPCODE_HANDLER_ARG
        zend_function *clone;
        zend_object_clone_obj_t clone_call;
 
-       if (!obj || Z_TYPE_P(obj) != IS_OBJECT) {
+       if (IS_UNUSED == IS_CONST ||
+           (IS_UNUSED == IS_VAR && !obj) ||
+           Z_TYPE_P(obj) != IS_OBJECT) {
                zend_error_noreturn(E_ERROR, "__clone method called on non-object");
        }
 
@@ -21736,7 +21726,8 @@ static int ZEND_FASTCALL  ZEND_ECHO_SPEC_CV_HANDLER(ZEND_OPCODE_HANDLER_ARGS)
        zval z_copy;
        zval *z = _get_zval_ptr_cv(&opline->op1, EX(Ts), BP_VAR_R TSRMLS_CC);
 
-       if (Z_TYPE_P(z) == IS_OBJECT && Z_OBJ_HT_P(z)->get_method != NULL &&
+       if (IS_CV != IS_CONST &&
+           Z_TYPE_P(z) == IS_OBJECT && Z_OBJ_HT_P(z)->get_method != NULL &&
                zend_std_cast_object_tostring(z, &z_copy, IS_STRING TSRMLS_CC) == SUCCESS) {
                zend_print_variable(&z_copy);
                zval_dtor(&z_copy);
@@ -22112,7 +22103,7 @@ static int ZEND_FASTCALL  ZEND_THROW_SPEC_CV_HANDLER(ZEND_OPCODE_HANDLER_ARGS)
 
        value = _get_zval_ptr_cv(&opline->op1, EX(Ts), BP_VAR_R TSRMLS_CC);
 
-       if (Z_TYPE_P(value) != IS_OBJECT) {
+       if (IS_CV == IS_CONST || Z_TYPE_P(value) != IS_OBJECT) {
                zend_error_noreturn(E_ERROR, "Can only throw objects");
        }
        zend_exception_save(TSRMLS_C);
@@ -22281,7 +22272,9 @@ static int ZEND_FASTCALL  ZEND_CLONE_SPEC_CV_HANDLER(ZEND_OPCODE_HANDLER_ARGS)
        zend_function *clone;
        zend_object_clone_obj_t clone_call;
 
-       if (!obj || Z_TYPE_P(obj) != IS_OBJECT) {
+       if (IS_CV == IS_CONST ||
+           (IS_CV == IS_VAR && !obj) ||
+           Z_TYPE_P(obj) != IS_OBJECT) {
                zend_error_noreturn(E_ERROR, "__clone method called on non-object");
        }