Skip to content

Instantly share code, notes, and snippets.

@laruence
Last active August 29, 2015 14:26
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save laruence/c18e97cc85f53e0200c0 to your computer and use it in GitHub Desktop.
Save laruence/c18e97cc85f53e0200c0 to your computer and use it in GitHub Desktop.
bug70207
diff --git a/ext/opcache/Optimizer/optimize_temp_vars_5.c b/ext/opcache/Optimizer/optimize_temp_vars_5.c
index 0e96ee8..1b23d8b 100644
--- a/ext/opcache/Optimizer/optimize_temp_vars_5.c
+++ b/ext/opcache/Optimizer/optimize_temp_vars_5.c
@@ -99,6 +99,38 @@ void optimize_temporary_variables(zend_op_array *op_array, zend_optimizer_ctx *c
num--;
zend_bitset_incl(taken_T, var + num);
}
+ } else if ((opline->opcode == ZEND_RETURN ||
+ opline->opcode == ZEND_RETURN_BY_REF ||
+ opline->opcode == ZEND_FREE ||
+ opline->opcode == ZEND_FE_FREE)) {
+ /* TODO: is it possible we find out the gap between FAST_CALL
+ * jmp dest opline and FAST_RET, then only don't reuse
+ * temporary vars in that gap. but for the costs, I fix this
+ * in a simple way. */
+ int conflict = 0;
+ zend_op *curr = opline;
+ while (--curr >= end) {
+ if (curr->opcode == ZEND_FAST_CALL) {
+ conflict = 1;
+ break;
+ } else if (curr->opcode != ZEND_FREE &&
+ curr->opcode != ZEND_FE_FREE &&
+ curr->opcode != ZEND_VERIFY_RETURN_TYPE &&
+ curr->opcode != ZEND_DISCARD_EXCEPTION) {
+ break;
+ }
+ }
+ if (conflict) {
+ i = ++max;
+ zend_bitset_incl(taken_T, i);
+ map_T[currT] = i;
+ zend_bitset_incl(valid_T, currT);
+ } else if (!zend_bitset_in(valid_T, currT)) {
+ GET_AVAILABLE_T();
+ map_T[currT] = i;
+ zend_bitset_incl(valid_T, currT);
+ }
+ ZEND_OP1(opline).var = NUM_VAR(map_T[currT] + offset);
} else {
if (!zend_bitset_in(valid_T, currT)) {
GET_AVAILABLE_T();
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment