Skip to content

Make ASSIGN, ASSIGN_OP, INC and DEC opcodes to return IS_TMP_VAR instead of IS_VAR #5158

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

Closed
wants to merge 2 commits into from

Conversation

dstogov
Copy link
Member

@dstogov dstogov commented Feb 6, 2020

This helps to avoid unnecessary IS_REFERENCE checks.
This changes some notices "Only variables should be passed by reference" to exception "Cannot pass parameter %d by reference".

Also, for consistency, compile-time fatal error "Only variables can be passed by reference" was converted to exception "Cannot pass parameter %d by reference"

@dstogov dstogov requested a review from nikic February 6, 2020 20:53
@nikic
Copy link
Member

nikic commented Feb 6, 2020

Looks fine to me. Please add an UPGRADING note about the notice->exception change.

There's also an unrelated change to ext/zip/tests/oo_namelocate.zip in here.

@nikic
Copy link
Member

nikic commented Feb 6, 2020

As this further reduces the number of IS_VAR uses, I wonder if we can make it so that the majority of opcodes no longer need to accept IS_VAR at all... for example, one of the few remaining ones if DO_FCALL. We could add a flag to it to dereference the result. Then most uses would set that flag and get back an IS_TMP_VAR. Only the few cases where we are in a reference context would not set and get IS_VAR. This way we should be able to make sure that opcodes used in a read context only ever get IS_TMP_VAR (or IS_CV/IS_CONST of course).

Not sure if this really makes sense though...

@dstogov
Copy link
Member Author

dstogov commented Feb 7, 2020

Looks fine to me. Please add an UPGRADING note about the notice->exception change.

I will do.

There's also an unrelated change to ext/zip/tests/oo_namelocate.zip in here.

Yeah, already noticed. Seems, Remi added it by mistake.

@dstogov
Copy link
Member Author

dstogov commented Feb 7, 2020

As this further reduces the number of IS_VAR uses, I wonder if we can make it so that the majority of opcodes no longer need to accept IS_VAR at all... for example, one of the few remaining ones if DO_FCALL. We could add a flag to it to dereference the result. Then most uses would set that flag and get back an IS_TMP_VAR. Only the few cases where we are in a reference context would not set and get IS_VAR. This way we should be able to make sure that opcodes used in a read context only ever get IS_TMP_VAR (or IS_CV/IS_CONST of course).

Not sure if this really makes sense though...

We have to keep IS_VAR results, in cases where IS_REFERENCE is possible (or expected) e.g. DO_FCALL, ASSIGN_REF. We probably may use IS_TMP_VAR for most of DO_UCALL/DO_ICALL.
anyway, I won't do it right now. May be I don't understand your suggestion completely...

One other related idea - change the remaining "Only variables should be passed by reference" notices into exceptions "Cannot pass parameter %d by reference".

@nikic
Copy link
Member

nikic commented Feb 7, 2020

We have to keep IS_VAR results, in cases where IS_REFERENCE is possible (or expected) e.g. DO_FCALL, ASSIGN_REF. We probably may use IS_TMP_VAR for most of DO_UCALL/DO_ICALL.
anyway, I won't do it right now. May be I don't understand your suggestion completely...

The idea is to allow both IS_VAR and IS_TMP_VAR result types for the remaining opcodes. Whether IS_VAR or IS_TMP_VAR is used would depend on whether the opcode is in W or R context. Then the opcode would be responsible itself for performing a dereference if the result type is IS_TMP_VAR.

That is, we move responsibility for performing the dereference from the user opcode to the producer opcode. This did not make sense before, as there were many opcodes that could produce references, but now this might make more sense.

One other related idea - change the remaining "Only variables should be passed by reference" notices into exceptions "Cannot pass parameter %d by reference".

Yes, this probably makes sense, to avoid breakages when things switch between IS_VAR <-> IS_TMP_VAR.

@dstogov
Copy link
Member Author

dstogov commented Feb 7, 2020

We have to keep IS_VAR results, in cases where IS_REFERENCE is possible (or expected) e.g. DO_FCALL, ASSIGN_REF. We probably may use IS_TMP_VAR for most of DO_UCALL/DO_ICALL.
anyway, I won't do it right now. May be I don't understand your suggestion completely...

The idea is to allow both IS_VAR and IS_TMP_VAR result types for the remaining opcodes. Whether IS_VAR or IS_TMP_VAR is used would depend on whether the opcode is in W or R context. Then the opcode would be responsible itself for performing a dereference if the result type is IS_TMP_VAR.

That is, we move responsibility for performing the dereference from the user opcode to the producer opcode. This did not make sense before, as there were many opcodes that could produce references, but now this might make more sense.

Go it, but not sure if this makes sense, because we will always check for IS_REFERENCE in that opcodes. Now we check only on use, and most opcodes optimized to check the most probable type first. Anyway, it makes sense to think a bit more.

One other related idea - change the remaining "Only variables should be passed by reference" notices into exceptions "Cannot pass parameter %d by reference".

Yes, this probably makes sense, to avoid breakages when things switch between IS_VAR <-> IS_TMP_VAR.

I'll prepare a separate PR later.

…ead of IS_VAR.

This helps to avoid unnecessary IS_REFERENCE checks.
This changes some notices "Only variables should be passed by reference" to exception "Cannot pass parameter %d by reference".

Also, for consistency, compile-time fatal error "Only variables can be passed by reference" was converted to exception "Cannot pass parameter %d by reference"
Actually, all assignments (ZEND_ASSIGN, ZEND_ASSIGN_DIM, ZEND_ASSIGN_OBJ,
ZEND_ASSIGN_STATIC_PROP), all compound assignments (ZEND_ASSIGN_OP,
ZEND_ASSIGN_DIM_OP, ZEND_ASSIGN_OBJ_OP, ZEND_ASSIGN_STATIC_PROP_OP) and all
pre increments/decremets (ZEND_PRE_INC, ZEND_PRE_DEC, ZEND_PRE_INC_OBJ
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

decremets -> decrements

@dstogov
Copy link
Member Author

dstogov commented Feb 7, 2020

Merged as 64b40f6

@dstogov dstogov closed this Feb 7, 2020
@carusogabriel carusogabriel added this to the PHP 8.0 milestone May 29, 2020
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

3 participants