fix modulo logic

This commit is contained in:
Ralf Jung 2018-08-14 12:16:29 +02:00
parent 2b40d39c1e
commit 04b925135d
2 changed files with 4 additions and 3 deletions

View file

@ -197,14 +197,15 @@ impl<'a, 'mir, 'tcx> EvalContextExt<'tcx> for EvalContext<'a, 'mir, 'tcx, super:
}
Rem if !signed => {
// Doing modulo a multiple of the alignment is allowed
// Doing modulo a divisor of the alignment is allowed.
// (Intuition: Modulo a divisor leaks less information.)
let ptr_base_align = self.memory.get(left.alloc_id)?.align.abi();
let right = right as u64;
let ptr_size = self.memory.pointer_size().bytes() as u8;
if right == 1 {
// modulo 1 is always 0
(Scalar::Bits { bits: 0, size: ptr_size }, false)
} else if right % ptr_base_align == 0 {
} else if ptr_base_align % right == 0 {
// the base address would be cancelled out by the modulo operation, so we can
// just take the modulo of the offset
(Scalar::Bits { bits: (left.offset.bytes() % right) as u128, size: ptr_size }, false)

View file

@ -1,5 +1,5 @@
fn main() {
let val = 13usize;
let addr = &val as *const _ as usize;
let _ = addr % 2; //~ ERROR access part of a pointer value as raw bytes
let _ = addr % 16; //~ ERROR access part of a pointer value as raw bytes
}