@@ -3815,22 +3815,23 @@ static DisasJumpType op_risbg(DisasContext *s, DisasOps *o)
pmask = 0xffffffff00000000ull;
break;
case 0x51: /* risblg */
- i3 &= 31;
- i4 &= 31;
+ i3 = (i3 & 31) + 32;
+ i4 = (i4 & 31) + 32;
pmask = 0x00000000ffffffffull;
break;
default:
g_assert_not_reached();
}
- /* MASK is the set of bits to be inserted from R2.
- Take care for I3/I4 wraparound. */
- mask = pmask >> i3;
+ /* MASK is the set of bits to be inserted from R2. */
if (i3 <= i4) {
- mask ^= pmask >> i4 >> 1;
+ /* [0...i3---i4...63] */
+ mask = (-1ull >> i3) & (-1ull << (63 - i4));
} else {
- mask |= ~(pmask >> i4 >> 1);
+ /* [0---i4...i3---63] */
+ mask = (-1ull >> i3) | (-1ull << (63 - i4));
}
+ /* For RISBLG/RISBHG, the wrapping is limited to the high/low doubleword. */
mask &= pmask;
/* IMASK is the set of bits to be kept from R1. In the case of the high/low
@@ -3843,9 +3844,6 @@ static DisasJumpType op_risbg(DisasContext *s, DisasOps *o)
len = i4 - i3 + 1;
pos = 63 - i4;
rot = i5 & 63;
- if (s->fields.op2 == 0x5d) {
- pos += 32;
- }
/* In some cases we can implement this with extract. */
if (imask == 0 && pos == 0 && len > 0 && len <= rot) {