]> granicus.if.org Git - php/commitdiff
Fixed register allocation
authorDmitry Stogov <dmitry@zend.com>
Tue, 28 May 2019 09:39:13 +0000 (12:39 +0300)
committerDmitry Stogov <dmitry@zend.com>
Tue, 28 May 2019 09:39:13 +0000 (12:39 +0300)
ext/opcache/jit/zend_jit_x86.dasc
ext/opcache/tests/jit/reg_alloc_003.phpt [new file with mode: 0644]

index 1d6ea01c0d06253299d7a4ea45d87b6e15542ca4..1cd59ffc860744ecad15e01cbf6755904b5e39cd 100644 (file)
@@ -748,18 +748,23 @@ static void* dasm_labels[zend_lb_MAX];
 ||     if (Z_MODE(addr) == IS_CONST_ZVAL) {
 |      .if X64
 ||             if (!IS_SIGNED_32BIT(Z_LVAL_P(Z_ZV(addr)))) {
-|                      mov64 r1, Z_LVAL_P(Z_ZV(addr))
-|                      long_ins reg, r1
+||                             if (reg != ZREG_R0) {
+|                                      mov64 r0, Z_LVAL_P(Z_ZV(addr))
+|                              long_ins Ra(reg), r0
+||                             } else {
+|                                      mov64 r1, Z_LVAL_P(Z_ZV(addr))
+|                              long_ins Ra(reg), r1
+||                             }
 ||             } else {
-|                      long_ins reg, Z_LVAL_P(Z_ZV(addr))
+|                      long_ins Ra(reg), Z_LVAL_P(Z_ZV(addr))
 ||             }
 |      .else
-|              long_ins reg, Z_LVAL_P(Z_ZV(addr))
+|              long_ins Ra(reg), Z_LVAL_P(Z_ZV(addr))
 |      .endif
 ||     } else if (Z_MODE(addr) == IS_MEM_ZVAL) {
-|      long_ins reg, aword [Ra(Z_REG(addr))+Z_OFFSET(addr)]
+|      long_ins Ra(reg), aword [Ra(Z_REG(addr))+Z_OFFSET(addr)]
 ||     } else if (Z_MODE(addr) == IS_REG) {
-|      long_ins reg, Ra(Z_REG(addr))
+|      long_ins Ra(reg), Ra(Z_REG(addr))
 ||     } else {
 ||             ZEND_ASSERT(0);
 ||     }
@@ -3261,7 +3266,7 @@ static int zend_jit_math_long_long(dasm_State    **Dst,
                if (same_ops && opline->opcode != ZEND_DIV) {
                        |       LONG_MATH_REG opline->opcode, Ra(result_reg), Ra(result_reg)
                } else {
-                       |       LONG_MATH opline->opcode, Ra(result_reg), op2_addr
+                       |       LONG_MATH opline->opcode, result_reg, op2_addr
                }
        }
        if ((res_info & MAY_BE_DOUBLE) && zend_may_overflow(opline, op_array, ssa)) {
@@ -3967,7 +3972,7 @@ static int zend_jit_long_math_helper(dasm_State    **Dst,
                |       LONG_MATH_REG opcode, Ra(result_reg), Ra(result_reg)
        } else {
                |       GET_ZVAL_LVAL result_reg, op1_addr
-               |       LONG_MATH opcode, Ra(result_reg), op2_addr
+               |       LONG_MATH opcode, result_reg, op2_addr
        }
 
        |       SET_ZVAL_LVAL res_addr, Ra(result_reg)
@@ -5324,13 +5329,13 @@ static int zend_jit_cmp_long_long(dasm_State **Dst, const zend_op *opline, int b
                if (Z_MODE(op2_addr) == IS_CONST_ZVAL && Z_LVAL_P(Z_ZV(op2_addr)) == 0) {
                        |       test Ra(Z_REG(op1_addr)), Ra(Z_REG(op1_addr))
                } else {
-                       |       LONG_OP cmp, Ra(Z_REG(op1_addr)), op2_addr
+                       |       LONG_OP cmp, Z_REG(op1_addr), op2_addr
                }
        } else if (Z_MODE(op2_addr) == IS_REG) {
                if (Z_MODE(op1_addr) == IS_CONST_ZVAL && Z_LVAL_P(Z_ZV(op1_addr)) == 0) {
                        |       test Ra(Z_REG(op2_addr)), Ra(Z_REG(op2_addr))
                } else {
-                       |       LONG_OP cmp, Ra(Z_REG(op2_addr)), op1_addr
+                       |       LONG_OP cmp, Z_REG(op2_addr), op1_addr
                }
                swap = 1;
        } else if (Z_MODE(op1_addr) == IS_CONST_ZVAL && Z_MODE(op2_addr) != IS_CONST_ZVAL) {
@@ -5343,7 +5348,7 @@ static int zend_jit_cmp_long_long(dasm_State **Dst, const zend_op *opline, int b
                if (Z_MODE(op2_addr) == IS_CONST_ZVAL && Z_LVAL_P(Z_ZV(op2_addr)) == 0) {
                        |       test r0, r0
                } else {
-                       |       LONG_OP cmp, r0, op2_addr
+                       |       LONG_OP cmp, ZREG_R0, op2_addr
                }
        }
        if (((opline+1)->opcode == ZEND_JMPZ_EX ||
diff --git a/ext/opcache/tests/jit/reg_alloc_003.phpt b/ext/opcache/tests/jit/reg_alloc_003.phpt
new file mode 100644 (file)
index 0000000..57f3bd4
--- /dev/null
@@ -0,0 +1,23 @@
+--TEST--
+Register Alloction 003: Reuse temporay register
+--INI--
+opcache.enable=1
+opcache.enable_cli=1
+opcache.file_update_protection=0
+opcache.jit_buffer_size=1M
+opcache.protect_memory=1
+--SKIPIF--
+<?php require_once('../skipif.inc'); ?>
+--FILE--
+<?php
+function test($char_code) {
+    if ($char_code == !($char_code & 0xffffff80)) {
+        return "correct";
+    } else {
+        return "wrong";
+    }
+}
+echo test(65), "\n";
+?>
+--EXPECT--
+correct