Skip to content

Commit 676e737

Browse files
committed
Fix other typos & add test script
1 parent 580d6fe commit 676e737

File tree

2 files changed

+136
-6
lines changed

2 files changed

+136
-6
lines changed

ext/opcache/Optimizer/optimize_func_calls.c

Lines changed: 6 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -81,7 +81,7 @@ static void optimize_func_calls(zend_op_array *op_array, zend_persistent_script
8181
case ZEND_FETCH_OBJ_FUNC_ARG:
8282
case ZEND_FETCH_DIM_FUNC_ARG:
8383
if (call_stack[call - 1].func) {
84-
if (ARG_SHOULD_BE_SENT_BY_REF(call_stack[call].func, (opline->extended_value & ZEND_FETCH_ARG_MASK))) {
84+
if (ARG_SHOULD_BE_SENT_BY_REF(call_stack[call - 1].func, (opline->extended_value & ZEND_FETCH_ARG_MASK))) {
8585
opline->extended_value = 0;
8686
opline->opcode -= 9;
8787
} else {
@@ -92,25 +92,25 @@ static void optimize_func_calls(zend_op_array *op_array, zend_persistent_script
9292
break;
9393
case ZEND_SEND_VAL:
9494
if (opline->extended_value == ZEND_DO_FCALL_BY_NAME && call_stack[call - 1].func) {
95-
if (ARG_MUST_BE_SENT_BY_REF(call_stack[call].func, opline->op2.num)) {
95+
if (ARG_MUST_BE_SENT_BY_REF(call_stack[call - 1].func, opline->op2.num)) {
9696
/* We won't convert it into_DO_FCALL to emit error at run-time */
97-
call_stack[call].opline = NULL;
97+
call_stack[call - 1].opline = NULL;
9898
} else {
9999
opline->extended_value = ZEND_DO_FCALL;
100100
}
101101
}
102102
break;
103103
case ZEND_SEND_VAR:
104104
if (opline->extended_value == ZEND_DO_FCALL_BY_NAME && call_stack[call - 1].func) {
105-
if (ARG_SHOULD_BE_SENT_BY_REF(call_stack[call].func, opline->op2.num)) {
105+
if (ARG_SHOULD_BE_SENT_BY_REF(call_stack[call - 1].func, opline->op2.num)) {
106106
opline->opcode = ZEND_SEND_REF;
107107
}
108108
opline->extended_value = ZEND_DO_FCALL;
109109
}
110110
break;
111111
case ZEND_SEND_VAR_NO_REF:
112112
if (!(opline->extended_value & ZEND_ARG_COMPILE_TIME_BOUND) && call_stack[call - 1].func) {
113-
if (ARG_SHOULD_BE_SENT_BY_REF(call_stack[call].func, opline->op2.num)) {
113+
if (ARG_SHOULD_BE_SENT_BY_REF(call_stack[call - 1].func, opline->op2.num)) {
114114
opline->extended_value |= ZEND_ARG_COMPILE_TIME_BOUND | ZEND_ARG_SEND_BY_REF;
115115
} else if (opline->extended_value) {
116116
opline->extended_value |= ZEND_ARG_COMPILE_TIME_BOUND;
@@ -123,7 +123,7 @@ static void optimize_func_calls(zend_op_array *op_array, zend_persistent_script
123123
case ZEND_SEND_REF:
124124
if (opline->extended_value == ZEND_DO_FCALL_BY_NAME && call_stack[call - 1].func) {
125125
/* We won't handle run-time pass by reference */
126-
call_stack[call].opline = NULL;
126+
call_stack[call - 1].opline = NULL;
127127
}
128128
break;
129129

Lines changed: 130 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,130 @@
1+
--TEST--
2+
Test with optimization of function calls
3+
--INI--
4+
opcache.enable=1
5+
opcache.enable_cli=1
6+
opcache.optimization_level=-1
7+
--SKIPIF--
8+
<?php require_once('skipif.inc'); ?>
9+
--FILE--
10+
<?php
11+
12+
class A {
13+
public $obj;
14+
public function test($a) {
15+
}
16+
}
17+
18+
function a(&$b) {
19+
$b = "changed";
20+
return "done";
21+
}
22+
23+
$a = "a";
24+
$b = "b";
25+
$c = "c";
26+
$f = "a";
27+
28+
/*
29+
* INIT_FCALL_BY_NAME
30+
* SEND_VAR
31+
* DO_FCALL
32+
* DO_FCALL_BY_NAME
33+
*/
34+
foo(a($a));
35+
var_dump($a);
36+
$a = "a";
37+
38+
/*
39+
* INIT_FCALL_BY_NAME
40+
* INIT_FCALL_BY_NAME -- un-optimizable
41+
* DO_FCALL_BY_NAME -- un-optimizable
42+
* DO_FCALL_BY_NAME
43+
*/
44+
foo($f($a));
45+
var_dump($a);
46+
47+
/*
48+
* INIT_FCALL_BY_NAME
49+
* ZEND_NEW
50+
* DO_FCALL_BY_NAME
51+
* DO_FCALL_BY_NAME
52+
*/
53+
foo(new A());
54+
55+
/*
56+
* INIT_FCALL_BY_NAME
57+
* FETCH_OBJ_FUNC_ARG
58+
* ZEND_SEND_VAR
59+
* DO_FCALL_BY_NAME
60+
*/
61+
foo((new A)->obj);
62+
$obj = new A;
63+
ref($obj->obj);
64+
var_dump($obj->obj);
65+
66+
ref(retarray()[0]);
67+
68+
$a = "a";
69+
foo(a($a), $a, ref($b, $c), $obj);
70+
var_dump($a);
71+
var_dump($b);
72+
73+
/*
74+
* INIT_FCALL_BY_NAME
75+
* SEND_VAL
76+
* DO_FCALL_BY_NAME
77+
*/
78+
ref("xxx");
79+
80+
function retarray() {
81+
return array("retarray");
82+
}
83+
84+
function foo($a) {
85+
print_r(func_get_args());
86+
}
87+
88+
function ref(&$b) {
89+
$b = "changed";
90+
return "ref";
91+
}
92+
--EXPECTF--
93+
Array
94+
(
95+
[0] => done
96+
)
97+
string(7) "changed"
98+
Array
99+
(
100+
[0] => done
101+
)
102+
string(7) "changed"
103+
Array
104+
(
105+
[0] => A Object
106+
(
107+
[obj] =>
108+
)
109+
110+
)
111+
Array
112+
(
113+
[0] =>
114+
)
115+
string(7) "changed"
116+
Array
117+
(
118+
[0] => done
119+
[1] => changed
120+
[2] => ref
121+
[3] => A Object
122+
(
123+
[obj] => changed
124+
)
125+
126+
)
127+
string(7) "changed"
128+
string(7) "changed"
129+
130+
Fatal error: Cannot pass parameter 1 by reference in %soptimize_func_calls.php on line %d

0 commit comments

Comments
 (0)