return icon;
};
+ auto NewZeroExtendNode = [&](var_types type, GenTree* op1, var_types castToType) -> GenTree* {
+ assert(varTypeIsIntegral(type));
+ assert(!varTypeIsSmall(type));
+ assert(!varTypeIsUnsigned(type));
+ assert(varTypeIsUnsigned(castToType));
+
+ GenTreeCast* cast = gtNewCastNode(TYP_INT, op1, false, castToType);
+ if (fgGlobalMorph)
+ {
+ fgMorphTreeDone(cast);
+ }
+
+ if (type == TYP_LONG)
+ {
+ cast = gtNewCastNode(TYP_LONG, cast, true, TYP_LONG);
+ if (fgGlobalMorph)
+ {
+ fgMorphTreeDone(cast);
+ }
+ }
+
+ return cast;
+ };
+
// Here `op` is the non-constant operand, `cons` is the constant operand
// and `val` is the constant value.
goto DONE_FOLD;
}
}
+ else if (val == 0xFF)
+ {
+ op = NewZeroExtendNode(tree->TypeGet(), op, TYP_UBYTE);
+ goto DONE_FOLD;
+ }
+ else if (val == 0xFFFF)
+ {
+ op = NewZeroExtendNode(tree->TypeGet(), op, TYP_USHORT);
+ goto DONE_FOLD;
+ }
+ else if ((val == 0xFFFFFFFF) && varTypeIsLong(tree))
+ {
+ op = NewZeroExtendNode(tree->TypeGet(), op, TYP_UINT);
+ goto DONE_FOLD;
+ }
else
{
/* The GTF_BOOLEAN flag is set for nodes that are part
static class IntRemainder
{
static int _fieldValue = 123;
+ static uint _fieldValueUnsigned = 123;
[MethodImpl(MethodImplOptions.NoInlining)]
static int Int32_RemainderByOne()
return value % 1;
}
+ [MethodImpl(MethodImplOptions.NoInlining)]
+ static byte Byte_RemainderByMaxValuePlusOne(uint value)
+ {
+ // X64-NOT: and {{[a-z]+}}
+
+ // X64: movzx {{[a-z]+}}, {{[a-z]+}}
+
+ return (byte)(value % (Byte.MaxValue + 1));
+ }
+
+ [MethodImpl(MethodImplOptions.NoInlining)]
+ static ushort UInt16_RemainderByMaxValuePlusOne(uint value)
+ {
+ // X64-NOT: and {{[a-z]+}}
+
+ // X64: movzx {{[a-z]+}}, {{[a-z]+}}
+
+ return (ushort)(value % (UInt16.MaxValue + 1));
+ }
+
+ [MethodImpl(MethodImplOptions.NoInlining)]
+ static uint Byte_RemainderByMaxValuePlusOne_Return_UInt32(uint value)
+ {
+ // X64-NOT: and {{[a-z]+}}
+
+ // X64: movzx {{[a-z]+}}, {{[a-z]+}}
+
+ return (value % (Byte.MaxValue + 1));
+ }
+
+ [MethodImpl(MethodImplOptions.NoInlining)]
+ static uint UInt16_RemainderByMaxValuePlusOne_Return_UInt32(uint value)
+ {
+ // X64-NOT: and {{[a-z]+}}
+
+ // X64: movzx {{[a-z]+}}, {{[a-z]+}}
+
+ return (value % (UInt16.MaxValue + 1));
+ }
+
+ [MethodImpl(MethodImplOptions.NoInlining)]
+ static byte Byte_RemainderByMaxValuePlusOne_WithField()
+ {
+ // X64-NOT: and {{[a-z]+}}
+
+ // X64: movzx {{[a-z]+}}, {{[a-z]+}}
+
+ return (byte)(_fieldValueUnsigned % (Byte.MaxValue + 1));
+ }
+
static int Main()
{
if (Int32_RemainderByOne() != 0)
if (Int32_RemainderByOneWithValue(-123) != 0)
return 0;
+ if (Byte_RemainderByMaxValuePlusOne(68000) != 160)
+ return 0;
+
+ if (UInt16_RemainderByMaxValuePlusOne(68000) != 2464)
+ return 0;
+
+ if (Byte_RemainderByMaxValuePlusOne_Return_UInt32(68000) != 160)
+ return 0;
+
+ if (UInt16_RemainderByMaxValuePlusOne_Return_UInt32(68000) != 2464)
+ return 0;
+
+ if (Byte_RemainderByMaxValuePlusOne_WithField() != 123)
+ return 0;
+
return 100;
}
}