Add some extra folding rules. Fixes #268513.
(Florian Krohm <britzel@acm.org>)
git-svn-id: svn://svn.valgrind.org/vex/trunk@2120 8f6e269a-dfd6-0310-a8e1-e2731360e62c
diff --git a/priv/ir_opt.c b/priv/ir_opt.c
index 7d26d4d..504105b 100644
--- a/priv/ir_opt.c
+++ b/priv/ir_opt.c
@@ -962,7 +962,7 @@
UInt i;
vassert(value != 0ULL); /* no defined semantics for arg==0 */
for (i = 0; i < 64; ++i) {
- if (value & (((ULong)1) << (63 - i))) return i;
+ if (0ULL != (value & (((ULong)1) << (63 - i)))) return i;
}
vassert(0);
/*NOTREACHED*/
@@ -974,7 +974,7 @@
UInt i;
vassert(value != 0); /* no defined semantics for arg==0 */
for (i = 0; i < 32; ++i) {
- if (value & (((UInt)1) << (31 - i))) return i;
+ if (0 != (value & (((UInt)1) << (31 - i)))) return i;
}
vassert(0);
/*NOTREACHED*/
@@ -1035,6 +1035,13 @@
e2 = IRExpr_Const(IRConst_U32((UInt)s32));
break;
}
+ case Iop_16Sto32: {
+ /* signed */ Int s32 = e->Iex.Unop.arg->Iex.Const.con->Ico.U16;
+ s32 <<= 16;
+ s32 >>= 16;
+ e2 = IRExpr_Const(IRConst_U32( (UInt)s32) );
+ break;
+ }
case Iop_8Uto64:
e2 = IRExpr_Const(IRConst_U64(
0xFFULL & e->Iex.Unop.arg->Iex.Const.con->Ico.U8));
@@ -1047,6 +1054,17 @@
e2 = IRExpr_Const(IRConst_U32(
0xFF & e->Iex.Unop.arg->Iex.Const.con->Ico.U8));
break;
+ case Iop_8Sto16: {
+ /* signed */ Short s16 = e->Iex.Unop.arg->Iex.Const.con->Ico.U8;
+ s16 <<= 8;
+ s16 >>= 8;
+ e2 = IRExpr_Const(IRConst_U16( (UShort)s16) );
+ break;
+ }
+ case Iop_8Uto16:
+ e2 = IRExpr_Const(IRConst_U16(
+ 0xFF & e->Iex.Unop.arg->Iex.Const.con->Ico.U8));
+ break;
case Iop_16Uto32:
e2 = IRExpr_Const(IRConst_U32(
0xFFFF & e->Iex.Unop.arg->Iex.Const.con->Ico.U16));
@@ -1121,6 +1139,13 @@
0xFFFFFFFFULL
& e->Iex.Unop.arg->Iex.Const.con->Ico.U32));
break;
+ case Iop_16Sto64: {
+ /* signed */ Long s64 = e->Iex.Unop.arg->Iex.Const.con->Ico.U16;
+ s64 <<= 48;
+ s64 >>= 48;
+ e2 = IRExpr_Const(IRConst_U64((ULong)s64));
+ break;
+ }
case Iop_32Sto64: {
/* signed */ Long s64 = e->Iex.Unop.arg->Iex.Const.con->Ico.U32;
s64 <<= 32;
@@ -1128,6 +1153,21 @@
e2 = IRExpr_Const(IRConst_U64((ULong)s64));
break;
}
+
+ case Iop_16to8: {
+ UShort w16 = e->Iex.Unop.arg->Iex.Const.con->Ico.U16;
+ w16 &= 0xFF;
+ e2 = IRExpr_Const(IRConst_U8( (UChar)w16 ));
+ break;
+ }
+ case Iop_16HIto8: {
+ UShort w16 = e->Iex.Unop.arg->Iex.Const.con->Ico.U16;
+ w16 >>= 8;
+ w16 &= 0xFF;
+ e2 = IRExpr_Const(IRConst_U8( (UChar)w16 ));
+ break;
+ }
+
case Iop_CmpNEZ8:
e2 = IRExpr_Const(IRConst_U1(toBool(
0 !=
@@ -1254,6 +1294,11 @@
(e->Iex.Binop.arg1->Iex.Const.con->Ico.U8
& e->Iex.Binop.arg2->Iex.Const.con->Ico.U8))));
break;
+ case Iop_And16:
+ e2 = IRExpr_Const(IRConst_U16(toUShort(
+ (e->Iex.Binop.arg1->Iex.Const.con->Ico.U16
+ & e->Iex.Binop.arg2->Iex.Const.con->Ico.U16))));
+ break;
case Iop_And32:
e2 = IRExpr_Const(IRConst_U32(
(e->Iex.Binop.arg1->Iex.Const.con->Ico.U32
@@ -1439,6 +1484,11 @@
((UInt)(e->Iex.Binop.arg1->Iex.Const.con->Ico.U32)
<= (UInt)(e->Iex.Binop.arg2->Iex.Const.con->Ico.U32)))));
break;
+ case Iop_CmpLE64U:
+ e2 = IRExpr_Const(IRConst_U1(toBool(
+ ((ULong)(e->Iex.Binop.arg1->Iex.Const.con->Ico.U64)
+ <= (ULong)(e->Iex.Binop.arg2->Iex.Const.con->Ico.U64)))));
+ break;
/* -- CmpLES -- */
case Iop_CmpLE32S:
@@ -1446,6 +1496,11 @@
((Int)(e->Iex.Binop.arg1->Iex.Const.con->Ico.U32)
<= (Int)(e->Iex.Binop.arg2->Iex.Const.con->Ico.U32)))));
break;
+ case Iop_CmpLE64S:
+ e2 = IRExpr_Const(IRConst_U1(toBool(
+ ((Long)(e->Iex.Binop.arg1->Iex.Const.con->Ico.U64)
+ <= (Long)(e->Iex.Binop.arg2->Iex.Const.con->Ico.U64)))));
+ break;
/* -- CmpLTS -- */
case Iop_CmpLT32S:
@@ -1453,6 +1508,11 @@
((Int)(e->Iex.Binop.arg1->Iex.Const.con->Ico.U32)
< (Int)(e->Iex.Binop.arg2->Iex.Const.con->Ico.U32)))));
break;
+ case Iop_CmpLT64S:
+ e2 = IRExpr_Const(IRConst_U1(toBool(
+ ((Long)(e->Iex.Binop.arg1->Iex.Const.con->Ico.U64)
+ < (Long)(e->Iex.Binop.arg2->Iex.Const.con->Ico.U64)))));
+ break;
/* -- CmpLTU -- */
case Iop_CmpLT32U:
@@ -1460,6 +1520,11 @@
((UInt)(e->Iex.Binop.arg1->Iex.Const.con->Ico.U32)
< (UInt)(e->Iex.Binop.arg2->Iex.Const.con->Ico.U32)))));
break;
+ case Iop_CmpLT64U:
+ e2 = IRExpr_Const(IRConst_U1(toBool(
+ ((ULong)(e->Iex.Binop.arg1->Iex.Const.con->Ico.U64)
+ < (ULong)(e->Iex.Binop.arg2->Iex.Const.con->Ico.U64)))));
+ break;
/* -- CmpORD -- */
case Iop_CmpORD32S: {