Skip to content

Optimize false === is_string($x) in opcache #4909

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

Open
wants to merge 1 commit into
base: master
Choose a base branch
from

Conversation

TysonAndre
Copy link
Contributor

@TysonAndre TysonAndre commented Nov 14, 2019

This optimization acts on opcodes that are guaranteed to return booleans.
(It's based on the below case for ZEND_BOOL and ZEND_BOOL_NOT)
Code such as return is_string($this->prop) === false; will benefit from it when
opcache is enabled.

A contrived example of a worst-case scenario is below.

// Before this PR: Took 0.459 seconds
// After this PR: Takes 0.362 seconds
loop_is_float(0, 20000000);
function loop_is_float($a, $b) {
  $values = [];
  for ($i = $a; $i < $b; $i++) {
      $values[false === is_float($i)] = true;
  }
  return $values;
}

This PR uses bit operations,
so that this optimization will also work for false !== is_string($x)
and any future combinations generated for ZEND_TYPE_CHECK.

Similar to GH-4906 (can be merged independently)

EDIT: Fixed, that should have been a logical xor, not a binary xor

@TysonAndre TysonAndre force-pushed the optimize-identical-bool branch from 471bbed to 378e10b Compare November 14, 2019 00:38
@TysonAndre
Copy link
Contributor Author

The build is passing - the only issue in php.php-src was the runner for MacOS getting cancelled.

This optimization acts on opcodes that are guaranteed to return booleans.
(It's based on the below case for ZEND_BOOL and ZEND_BOOL_NOT)
Code such as `return is_string($this->prop) === false;` will benefit from it when
opcache is enabled.

A contrived example of a worst-case scenario is below.

```php
// Before this PR: Took 0.459 seconds
// After this PR: Takes 0.362 seconds
loop_is_float(0, 20000000);
function loop_is_float($a, $b) {
  $values = [];
  for ($i = $a; $i < $b; $i++) {
      $values[false === is_float($i)] = true;
  }
  return $values;
}
```

This PR uses bit operations,
so that this optimization will also work for `false !== is_string($x)`
and any future combinations generated for ZEND_TYPE_CHECK.

Similar to phpGH-4906 (can be merged independently)
@TysonAndre TysonAndre force-pushed the optimize-identical-bool branch from 46d6262 to 80ceda5 Compare June 2, 2021 13:07
@Girgias Girgias requested a review from nikic June 2, 2021 13:12
@ramsey
Copy link
Member

ramsey commented May 31, 2022

This needs a review, please! If approved, I'd like to get it merge to master for 8.2.

@ramsey ramsey added this to the PHP 8.2 milestone May 31, 2022
@adoy adoy removed this from the PHP 8.2 milestone Feb 16, 2023
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment