https://bugs.kde.org/show_bug.cgi?id=509157

--- Comment #4 from Florian Krohm <[email protected]> ---
Looks like a bug in IR generation to me.

4.2.2. Integer Register-Register Operations of the ISA spec says:

SLL, SRL, and SRA perform logical left, logical right, and arithmetic right
shifts on the value in register
rs1 by the shift amount held in register rs2. In RV64I, only the low 6 bits of
rs2 are considered for the
shift amount.

guest_riscv64_toIR.c does  beginning on line 1551:

  case 0b001:
     expr = binop(Iop_Shl64, getIReg64(rs1),
                             unop(Iop_64to8, getIReg64(rs2)));
     break;

Thereby taking the lowest 8 and not 6 bits of the register as shift amount.
Should be something like:

    expr = binop(Iop_Shl64, getIReg64(rs1),   
                 unop(Iop_64to8, binop(Iop_And64, getIReg64(rs2),
mkU64(0x3F))));

As for the semantics of "shifting by a too large amount":
VEX semantics doesn't say anything specific about this because what happens in
that case
may be architecture dependent. 
Adding a comment to that effect:

If the value of the right operand is greater than or equal to the width of the
left operand, 
the behavior is undefined.

would be good.
So ideally, if an architecture defines a behaviour for too large shift amounts,
then it is the
job of IR generation to implement it in order to avoid the undefined behaviour
in the VEX IROp.
In practice that might not happen, though, because typically a shift insn in
the guest code
will be implemented by the same insn in the jitted code.

-- 
You are receiving this mail because:
You are watching all bug changes.

Reply via email to