Skip to content

Commit e5ff9f1

Browse files
committed
Sync from rust e1ec326
2 parents 343c532 + bb7b844 commit e5ff9f1

File tree

1 file changed

+10
-3
lines changed

1 file changed

+10
-3
lines changed

src/intrinsics/mod.rs

+10-3
Original file line numberDiff line numberDiff line change
@@ -713,14 +713,21 @@ fn codegen_regular_intrinsic_call<'tcx>(
713713
ret.write_cvalue(fx, val);
714714
};
715715

716-
ptr_offset_from, (v ptr, v base) {
716+
ptr_offset_from | ptr_offset_from_unsigned, (v ptr, v base) {
717717
let ty = substs.type_at(0);
718718
let isize_layout = fx.layout_of(fx.tcx.types.isize);
719719

720720
let pointee_size: u64 = fx.layout_of(ty).size.bytes();
721-
let diff = fx.bcx.ins().isub(ptr, base);
721+
let diff_bytes = fx.bcx.ins().isub(ptr, base);
722722
// FIXME this can be an exact division.
723-
let val = CValue::by_val(fx.bcx.ins().sdiv_imm(diff, pointee_size as i64), isize_layout);
723+
let diff = if intrinsic == sym::ptr_offset_from_unsigned {
724+
// Because diff_bytes ULE isize::MAX, this would be fine as signed,
725+
// but unsigned is slightly easier to codegen, so might as well.
726+
fx.bcx.ins().udiv_imm(diff_bytes, pointee_size as i64)
727+
} else {
728+
fx.bcx.ins().sdiv_imm(diff_bytes, pointee_size as i64)
729+
};
730+
let val = CValue::by_val(diff, isize_layout);
724731
ret.write_cvalue(fx, val);
725732
};
726733

0 commit comments

Comments
 (0)