diff options
author | Dmitry Stogov <dmitry@zend.com> | 2021-03-17 23:00:22 +0300 |
---|---|---|
committer | Dmitry Stogov <dmitry@zend.com> | 2021-03-17 23:00:22 +0300 |
commit | eb8f5e43475e44f8746a2357ed8c3cd60b426eb0 (patch) | |
tree | cdc5d351e1a73fda54e3b1498f3d541468ae0a59 | |
parent | d628d7e0156a44df3027f7013188577dfa438d64 (diff) | |
parent | 7e494d92258b0150e228bae82021a92b64e415b8 (diff) | |
download | php-git-eb8f5e43475e44f8746a2357ed8c3cd60b426eb0.tar.gz |
Merge branch 'PHP-8.0'
* PHP-8.0:
Fixed bug #80861 (erronous array key overflow in 2D array with JIT)
-rw-r--r-- | ext/opcache/jit/zend_jit_x86.dasc | 2 | ||||
-rw-r--r-- | ext/opcache/tests/jit/bug80861.phpt | 111 |
2 files changed, 112 insertions, 1 deletions
diff --git a/ext/opcache/jit/zend_jit_x86.dasc b/ext/opcache/jit/zend_jit_x86.dasc index 8bad99f95f..ccf3a173de 100644 --- a/ext/opcache/jit/zend_jit_x86.dasc +++ b/ext/opcache/jit/zend_jit_x86.dasc @@ -15514,7 +15514,7 @@ static zend_regset zend_jit_get_scratch_regset(const zend_op *opline, const zend op2_info = OP2_INFO(); if (opline->op1_type == IS_CV && !(op2_info & MAY_BE_UNDEF) - && !(op1_info & (MAY_BE_STRING|MAY_BE_ARRAY|MAY_BE_RESOURCE|MAY_BE_REF))) { + && !(op1_info & (MAY_BE_STRING|MAY_BE_ARRAY|MAY_BE_OBJECT|MAY_BE_RESOURCE|MAY_BE_REF))) { if ((op2_info & (MAY_BE_ANY|MAY_BE_REF)) == MAY_BE_DOUBLE) { regset = ZEND_REGSET(ZREG_XMM0); } else if ((op2_info & (MAY_BE_ANY|MAY_BE_REF)) == MAY_BE_LONG) { diff --git a/ext/opcache/tests/jit/bug80861.phpt b/ext/opcache/tests/jit/bug80861.phpt new file mode 100644 index 0000000000..3ae93d66d7 --- /dev/null +++ b/ext/opcache/tests/jit/bug80861.phpt @@ -0,0 +1,111 @@ +--TEST-- +Bug #80839: PHP problem with JIT +--INI-- +opcache.enable=1 +opcache.enable_cli=1 +opcache.jit_buffer_size=1M +opcache.jit=tracing +--SKIPIF-- +<?php require_once('skipif.inc'); ?> +--FILE-- +<?php +declare(strict_types=1); + +// -------------------------------------------------------------------- +class Node +{ + public $column = null; + public $left = null; + public $right = null; + public $up = null; + public $down = null; + + public static function joinLR(Node $a, Node $b): void + { + $a->right = $b; + $b->left = $a; + } + + public static function joinDU(Node $a, Node $b): void + { + $a->up = $b; + $b->down = $a; + } +} + +// -------------------------------------------------------------------- +class Column extends Node +{ + public function __construct() + { + $this->column = $this; + $this->up = $this; + $this->down = $this; + } +} + +// -------------------------------------------------------------------- +class Matrix +{ + public $head = null; + + public function __construct() + { + $this->head = new Node(); + Node::joinLR($this->head, $this->head); + } + + // $from is array[][] of bool + public static function fromArray(array $from): Matrix + { + $m = new Matrix(); + $rowCount = count($from); + if ($rowCount == 0) { + return $m; + } + $columnCount = count($from[0]); + if ($columnCount == 0) { + return $m; + } + // we generate 2D double linked circular list of nodes from the input 2D bool array + // might be not relevant for the bug + $c = new Column(); + Node::joinLR($m->head, $c); + for ($j = 1; $j < $columnCount; $j++) { + $nextCol = new Column(); + Node::joinLR($c, $nextCol); + $c = $c->right; + } + Node::joinLR($c, $m->head); + $c = $m->head->right; + error_log("These are the array bounds: $rowCount * $columnCount"); + for ($j = 0; $j < $columnCount; $j++) { + $prev = $c; + for ($i = 0; $i < $rowCount; $i++) { + // next line generates the warnings despite $i and $j is within bounds + if ($from[$i][$j]) { + $node = new Node(); + $node->column = $c; + Node::joinDU($node, $prev); + Node::joinLR($node, $node); + $prev = $node; + // ... code to generate $m excluded + } + } + Node::joinDU($c, $prev); + $c = $c->right; + } + return $m; + } +} + +// -------------------------------------------------------------------- +// simple driver code - fills up a 2D bool matrix and calls the static matrix constructing function above +for ($y = 0; $y < 10; $y++) { + for ($x = 0; $x < 10; $x++) { + $a[$y][$x] = true; + } +} +$m = Matrix::fromArray($a); +--EXPECT-- +These are the array bounds: 10 * 10 |