-
Notifications
You must be signed in to change notification settings - Fork 7.7k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Use correct fetch mode for object modification #5250
Conversation
Wow, it was really-really quick! :) |
I think we need to bite the bullet here and accept the SimpleXML breakage. The fact that you can do this kind of deep automatic intialization is undocumented (the documentation uses addChild and friends), and we have removed similar auto-vivification behavior for normal objects in PHP 8. |
For comparison:
gives on 7.4:
and on PHP 8.0:
It seems like the SimpleXML issue is completely analogous to this change. The only difference is that SimpleXML currently does not throw the warning, but we can't do anything about that at this time. |
@@ -1002,7 +1002,7 @@ ZEND_VM_HANDLER(28, ZEND_ASSIGN_OBJ_OP, VAR|UNUSED|THIS|CV, CONST|TMPVAR|CV, OP) | |||
zend_string *name, *tmp_name; | |||
|
|||
SAVE_OPLINE(); | |||
object = GET_OP1_OBJ_ZVAL_PTR_PTR_UNDEF(BP_VAR_RW); | |||
object = GET_OP1_OBJ_ZVAL_PTR_UNDEF(BP_VAR_R); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This may miss support for IS_INDIRECT.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I don't have strong opinion about this PR. Technically the patch is fine. On the other hand, it changes behavior, and I don't completely understand the reason. Should this help implementing read-only properties?
@@ -62,5 +64,16 @@ Warning: Trying to access array offset on value of type null in %s on line %d | |||
Warning: Trying to access array offset on value of type null in %s on line %d | |||
|
|||
Warning: Trying to get property 'foo' of non-object in %s on line %d | |||
|
|||
Warning: Undefined variable: arr in %s on line %d |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
It's going to be hard to explain why $a[2]->x = 2;
warns about undefined variable but $a[2][2] = 2;
does not.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
It may be hard to explain why arrays and objects have different semantics in the first place, but given that they do, this seems more consistent:
$a[0] = 42
where $a
is undefined is considered legal and does not throw any notices or errors. $a->x = 42
is considered illegal and throws a warning in PHP 7 and exception in PHP 8. In this case, the undefined variable notice indicates the "root cause" that needs to be fixed, while the "Attempt to assign property 'b' of non-object" is a followup error caused by it.
That's right. The basic problem is that
should both be allowed. The first case is automatically handled correctly, because the property is fetched for R. The second case is handled incorrectly, because the property is fetched for W. Workarounds for this are possible (allowing W/RW fetches in the first place, and then adding extra flags to the property assignment if it is "real"), but I think it is much cleaner to emit the correct fetch mode in the first place. We also have some existing issues in this area, but they are much less visible, because we have some "best effort" workarounds. For example, if you write something like this:
You get:
If you write:
You don't get a notice. The reason is that we have special-cased objects here to prevent a spurious warning if you write |
OK. I don't object against this. |
We already use r0 to hold the zval.
Previously,
$a->b
was treated as a write fetch.This is an updated version of #3865. The SimpleXML issue still exists.