This silences some reports about the equivalence to array_merge()'s
issue. However, this is different as no packed fill is used in this
code, so it doesn't have the same bug that array_merge() had.
Closes GH-21449.
* PHP-8.5:
Update NEWS with info about security issues
Fix GHSA-www2-q4fc-65wf
Fix GHSA-h96m-rvf9-jgm2
Fix GHSA-8xr5-qppj-gvwj: PDO quoting result null deref
Fix GH-20584: Information Leak of Memory
* PHP-8.4:
Update NEWS with info about security issues
Fix GHSA-www2-q4fc-65wf
Fix GHSA-h96m-rvf9-jgm2
Fix GHSA-8xr5-qppj-gvwj: PDO quoting result null deref
Fix GH-20584: Information Leak of Memory
* PHP-8.3:
Update NEWS with info about security issues
Fix GHSA-www2-q4fc-65wf
Fix GHSA-h96m-rvf9-jgm2
Fix GHSA-8xr5-qppj-gvwj: PDO quoting result null deref
Fix GH-20584: Information Leak of Memory
* PHP-8.2:
Update NEWS with info about security issues
Fix GHSA-www2-q4fc-65wf
Fix GHSA-h96m-rvf9-jgm2
Fix GHSA-8xr5-qppj-gvwj: PDO quoting result null deref
Fix GH-20584: Information Leak of Memory
* PHP-8.1:
Update NEWS with info about security issues
Fix GHSA-www2-q4fc-65wf
Fix GHSA-h96m-rvf9-jgm2
Fix GHSA-8xr5-qppj-gvwj: PDO quoting result null deref
Fix GH-20584: Information Leak of Memory
Consolidate userland functions to rely on a single implementation
Split get_comparison functions into a reverse and a normal one
Use bool type when applicable
Packed arrays are likely common in this case, as with array_shift which
already has a similar optimization.
For the following benchmark:
```php
<?php
for ($i = 0; $i < 10000000; $i++) {
$a = [0, 1, 2, 3, 4, 5];
array_unshift($a, -3, -2, -1);
}
```
On an i7-4790:
```
Benchmark 1: ./sapi/cli/php x.php
Time (mean ± σ): 753.8 ms ± 23.8 ms [User: 749.8 ms, System: 2.1 ms]
Range (min … max): 734.3 ms … 818.6 ms 10 runs
Benchmark 2: ./sapi/cli/php_old x.php
Time (mean ± σ): 972.5 ms ± 5.0 ms [User: 968.8 ms, System: 1.4 ms]
Range (min … max): 967.8 ms … 984.3 ms 10 runs
Summary
./sapi/cli/php x.php ran
1.29 ± 0.04 times faster than ./sapi/cli/php_old x.php
```
We never need to use refcounted copies for arguments because the copy to
the call frame already increments the refcount.
For the following benchmark:
```php
$a = range(0, 10);
for ($i = 0; $i < 1000000; $i++)
array_walk($a, fn ($val, $idx, $arg) => $val + $arg, 2);
```
On an i7-4790:
```
Benchmark 1: ./sapi/cli/php x.php
Time (mean ± σ): 593.0 ms ± 5.4 ms [User: 589.8 ms, System: 1.7 ms]
Range (min … max): 583.3 ms … 600.9 ms 10 runs
Benchmark 2: ./sapi/cli/php_old x.php
Time (mean ± σ): 637.8 ms ± 4.6 ms [User: 633.9 ms, System: 2.2 ms]
Range (min … max): 633.4 ms … 649.2 ms 10 runs
Summary
./sapi/cli/php x.php ran
1.08 ± 0.01 times faster than ./sapi/cli/php_old x.php
```
On an i7-1185G7:
```
Benchmark 1: ./sapi/cli/php x.php
Time (mean ± σ): 362.3 ms ± 2.0 ms [User: 359.9 ms, System: 1.9 ms]
Range (min … max): 359.6 ms … 367.1 ms 10 runs
Benchmark 2: ./sapi/cli/php_old x.php
Time (mean ± σ): 385.5 ms ± 1.8 ms [User: 383.2 ms, System: 1.9 ms]
Range (min … max): 381.5 ms … 387.2 ms 10 runs
Summary
./sapi/cli/php x.php ran
1.06 ± 0.01 times faster than ./sapi/cli/php_old x.php
```
Move the refcount update outside of the loop.
For the following benchmark:
```php
$r = range(0, 1000);
$v = new stdClass();
for ($i = 0; $i < 100000; $i++) {
array_fill_keys($r, $v);
}
```
On an i7-4790:
```
Benchmark 1: ./sapi/cli/php_old ../x.php
Time (mean ± σ): 507.5 ms ± 4.8 ms [User: 505.1 ms, System: 1.2 ms]
Range (min … max): 501.2 ms … 518.4 ms 10 runs
Benchmark 2: ./sapi/cli/php ../x.php
Time (mean ± σ): 479.8 ms ± 3.1 ms [User: 476.8 ms, System: 1.8 ms]
Range (min … max): 475.0 ms … 486.7 ms 10 runs
Summary
./sapi/cli/php ../x.php ran
1.06 ± 0.01 times faster than ./sapi/cli/php_old ../x.php
```
On an i7-1185G7:
```
Benchmark 1: ./sapi/cli/php x.php
Time (mean ± σ): 343.9 ms ± 3.1 ms [User: 341.1 ms, System: 2.3 ms]
Range (min … max): 337.9 ms … 347.8 ms 10 runs
Benchmark 2: ./sapi/cli/php_old x.php
Time (mean ± σ): 357.8 ms ± 2.3 ms [User: 355.7 ms, System: 1.6 ms]
Range (min … max): 355.0 ms … 362.6 ms 10 runs
Summary
./sapi/cli/php x.php ran
1.04 ± 0.01 times faster than ./sapi/cli/php_old x.php
```
The reason this happens is because the array_unique operation happens in-place
because the input array is RC1.
At one point during comparison an exception is thrown which will capture the
arguments in the backtrace, which will increment the refcount of the RC1 array
to 2. Then a modification happens after the throw on the RC2 array causing the
assertion failure.
We shouldn't try continue work after an exception happened during the sort.
Closes GH-20059.