bug #39738 [VarDumper] fix mutating $GLOBALS while cloning it (nicolas-grekas)

This PR was merged into the 4.4 branch.

Discussion
----------

[VarDumper] fix mutating $GLOBALS while cloning it

| Q             | A
| ------------- | ---
| Branch?       | 4.4
| Bug fix?      | yes
| New feature?  | no
| Deprecations? | no
| Tickets       | Fix #39679
| License       | MIT
| Doc PR        | -

Also preparing for https://wiki.php.net/rfc/restrict_globals_usage

Commits
-------

384b0adf38 [VarDumper] fix mutating $GLOBALS while cloning it
This commit is contained in:
Nicolas Grekas 2021-01-07 14:07:47 +01:00
commit d223a5ed40
3 changed files with 22 additions and 14 deletions

View File

@ -335,7 +335,7 @@ class Data implements \ArrayAccess, \Countable, \IteratorAggregate
}
$cursor->hardRefTo = $refs[$r];
$cursor->hardRefHandle = $this->useRefHandles & $item->handle;
$cursor->hardRefCount = $item->refCount;
$cursor->hardRefCount = 0 < $item->handle ? $item->refCount : 0;
}
$cursor->attr = $item->attr;
$type = $item->class ?: \gettype($item->value);

View File

@ -159,13 +159,19 @@ class VarCloner extends AbstractCloner
if (Stub::ARRAY_ASSOC === $stub->class) {
// Copies of $GLOBALS have very strange behavior,
// let's detect them with some black magic
$a[$gid] = true;
// Happens with copies of $GLOBALS
if (isset($v[$gid])) {
if (\PHP_VERSION_ID < 80100 && ($a[$gid] = true) && isset($v[$gid])) {
unset($v[$gid]);
$a = [];
foreach ($v as $gk => &$gv) {
if ($v === $gv) {
unset($v);
$v = new Stub();
$v->value = [$v->cut = \count($gv), Stub::TYPE_ARRAY => 0];
$v->handle = -1;
$gv = &$hardRefs[spl_object_id($v)];
$gv = $v;
}
$a[$gk] = &$gv;
}
unset($gv);

View File

@ -439,6 +439,7 @@ EOTXT
/**
* @runInSeparateProcess
* @preserveGlobalState disabled
* @requires PHP < 8.1
*/
public function testSpecialVars56()
{
@ -453,11 +454,11 @@ array:3 [
]
]
1 => array:1 [
"GLOBALS" => &2 array:1 [
"GLOBALS" => &2 array:1 [&2]
]
"GLOBALS" => & array:1 [ …1]
]
2 => &3 array:1 [
"GLOBALS" => &3 array:1 [&3]
]
2 => &2 array:1 [&2]
]
EOTXT
,
@ -468,6 +469,7 @@ EOTXT
/**
* @runInSeparateProcess
* @preserveGlobalState disabled
* @requires PHP < 8.1
*/
public function testGlobals()
{
@ -490,11 +492,11 @@ EOTXT
<<<'EOTXT'
array:2 [
1 => array:1 [
"GLOBALS" => &1 array:1 [
"GLOBALS" => &1 array:1 [&1]
]
"GLOBALS" => & array:1 [ …1]
]
2 => &2 array:1 [
"GLOBALS" => &2 array:1 [&2]
]
2 => &1 array:1 [&1]
]
EOTXT
@ -584,6 +586,6 @@ EOTXT
return $var;
};
return [$var(), $GLOBALS, &$GLOBALS];
return eval('return [$var(), $GLOBALS, &$GLOBALS];');
}
}