summary refs log tree commit diff stats
path: root/tcg/optimize.c
diff options
context:
space:
mode:
authorPeter Maydell <peter.maydell@linaro.org>2014-04-24 15:24:51 +0100
committerPeter Maydell <peter.maydell@linaro.org>2014-04-24 15:24:52 +0100
commitad600a4d49293f6b8eda7932f90e5aa5fa2021b0 (patch)
treed8c5b8685168c1fd1d8d35357c31fe20d0700efb /tcg/optimize.c
parentba3627ec384d6c68e87c466895a4d78422669e30 (diff)
parent02eb19d0ec19ac8fb1de1116999184663763eaa0 (diff)
downloadfocaccia-qemu-ad600a4d49293f6b8eda7932f90e5aa5fa2021b0.tar.gz
focaccia-qemu-ad600a4d49293f6b8eda7932f90e5aa5fa2021b0.zip
Merge remote-tracking branch 'remotes/rth/tags/tcg-next-20140422' into staging
Pull tcg 2014-04-22

# gpg: Signature made Tue 22 Apr 2014 22:00:04 BST using RSA key ID 4DD0279B
# gpg: Can't check signature: public key not found

* remotes/rth/tags/tcg-next-20140422:
  tcg: Use HOST_WORDS_BIGENDIAN
  tcg: Fix fallback from muls2_i64 to mulu2_i64
  tcg: Use tcg_gen_mulu2_i32 in tcg_gen_muls2_i32
  tcg: Relax requirement for mulu2_i32 on 32-bit hosts
  tcg-s390: Remove W constraint
  tcg-sparc: Use the type parameter to tcg_target_const_match
  tcg-ppc64: Use the type parameter to tcg_target_const_match
  tcg-aarch64: Remove w constraint
  tcg: Add TCGType parameter to tcg_target_const_match
  tcg: Fix out of range shift in deposit optimizations
  tci: Mask shift counts to avoid undefined behavior
  tcg: Mask shift quantities while folding
  tcg: Use "unspecified behavior" for shifts
  tcg: Fix warning (1 bit signed bitfield entry) and replace int by bool

Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
Diffstat (limited to 'tcg/optimize.c')
-rw-r--r--tcg/optimize.c45
1 files changed, 24 insertions, 21 deletions
diff --git a/tcg/optimize.c b/tcg/optimize.c
index 7777743e88..c447062ab1 100644
--- a/tcg/optimize.c
+++ b/tcg/optimize.c
@@ -220,34 +220,34 @@ static TCGArg do_constant_folding_2(TCGOpcode op, TCGArg x, TCGArg y)
         return x ^ y;
 
     case INDEX_op_shl_i32:
-        return (uint32_t)x << (uint32_t)y;
+        return (uint32_t)x << (y & 31);
 
     case INDEX_op_shl_i64:
-        return (uint64_t)x << (uint64_t)y;
+        return (uint64_t)x << (y & 63);
 
     case INDEX_op_shr_i32:
-        return (uint32_t)x >> (uint32_t)y;
+        return (uint32_t)x >> (y & 31);
 
     case INDEX_op_shr_i64:
-        return (uint64_t)x >> (uint64_t)y;
+        return (uint64_t)x >> (y & 63);
 
     case INDEX_op_sar_i32:
-        return (int32_t)x >> (int32_t)y;
+        return (int32_t)x >> (y & 31);
 
     case INDEX_op_sar_i64:
-        return (int64_t)x >> (int64_t)y;
+        return (int64_t)x >> (y & 63);
 
     case INDEX_op_rotr_i32:
-        return ror32(x, y);
+        return ror32(x, y & 31);
 
     case INDEX_op_rotr_i64:
-        return ror64(x, y);
+        return ror64(x, y & 63);
 
     case INDEX_op_rotl_i32:
-        return rol32(x, y);
+        return rol32(x, y & 31);
 
     case INDEX_op_rotl_i64:
-        return rol64(x, y);
+        return rol64(x, y & 63);
 
     CASE_OP_32_64(not):
         return ~x;
@@ -806,29 +806,34 @@ static TCGArg *tcg_constant_folding(TCGContext *s, uint16_t *tcg_opc_ptr,
 
         case INDEX_op_sar_i32:
             if (temps[args[2]].state == TCG_TEMP_CONST) {
-                mask = (int32_t)temps[args[1]].mask >> temps[args[2]].val;
+                tmp = temps[args[2]].val & 31;
+                mask = (int32_t)temps[args[1]].mask >> tmp;
             }
             break;
         case INDEX_op_sar_i64:
             if (temps[args[2]].state == TCG_TEMP_CONST) {
-                mask = (int64_t)temps[args[1]].mask >> temps[args[2]].val;
+                tmp = temps[args[2]].val & 63;
+                mask = (int64_t)temps[args[1]].mask >> tmp;
             }
             break;
 
         case INDEX_op_shr_i32:
             if (temps[args[2]].state == TCG_TEMP_CONST) {
-                mask = (uint32_t)temps[args[1]].mask >> temps[args[2]].val;
+                tmp = temps[args[2]].val & 31;
+                mask = (uint32_t)temps[args[1]].mask >> tmp;
             }
             break;
         case INDEX_op_shr_i64:
             if (temps[args[2]].state == TCG_TEMP_CONST) {
-                mask = (uint64_t)temps[args[1]].mask >> temps[args[2]].val;
+                tmp = temps[args[2]].val & 63;
+                mask = (uint64_t)temps[args[1]].mask >> tmp;
             }
             break;
 
         CASE_OP_32_64(shl):
             if (temps[args[2]].state == TCG_TEMP_CONST) {
-                mask = temps[args[1]].mask << temps[args[2]].val;
+                tmp = temps[args[2]].val & (TCG_TARGET_REG_BITS - 1);
+                mask = temps[args[1]].mask << tmp;
             }
             break;
 
@@ -838,9 +843,8 @@ static TCGArg *tcg_constant_folding(TCGContext *s, uint16_t *tcg_opc_ptr,
             break;
 
         CASE_OP_32_64(deposit):
-            tmp = ((1ull << args[4]) - 1);
-            mask = ((temps[args[1]].mask & ~(tmp << args[3]))
-                    | ((temps[args[2]].mask & tmp) << args[3]));
+            mask = deposit64(temps[args[1]].mask, args[3], args[4],
+                             temps[args[2]].mask);
             break;
 
         CASE_OP_32_64(or):
@@ -1055,9 +1059,8 @@ static TCGArg *tcg_constant_folding(TCGContext *s, uint16_t *tcg_opc_ptr,
             if (temps[args[1]].state == TCG_TEMP_CONST
                 && temps[args[2]].state == TCG_TEMP_CONST) {
                 s->gen_opc_buf[op_index] = op_to_movi(op);
-                tmp = ((1ull << args[4]) - 1);
-                tmp = (temps[args[1]].val & ~(tmp << args[3]))
-                      | ((temps[args[2]].val & tmp) << args[3]);
+                tmp = deposit64(temps[args[1]].val, args[3], args[4],
+                                temps[args[2]].val);
                 tcg_opt_gen_movi(gen_args, args[0], tmp);
                 gen_args += 2;
                 args += 5;