Skip to content

Commit 49bc3f5

Browse files
authored
Rollup merge of rust-lang#64063 - JohnTitor:fix-const-err, r=oli-obk
Fix const_err with `-(-0.0)` Fixes rust-lang#64059 r? @oli-obk
2 parents 05c6868 + 41deb83 commit 49bc3f5

14 files changed

+477
-53
lines changed

src/librustc_mir/transform/const_prop.rs

+9-4
Original file line numberDiff line numberDiff line change
@@ -405,13 +405,16 @@ impl<'mir, 'tcx> ConstPropagator<'mir, 'tcx> {
405405
}
406406

407407
let arg = self.eval_operand(arg, source_info)?;
408+
let oflo_check = self.tcx.sess.overflow_checks();
408409
let val = self.use_ecx(source_info, |this| {
409410
let prim = this.ecx.read_immediate(arg)?;
410411
match op {
411412
UnOp::Neg => {
412-
// Need to do overflow check here: For actual CTFE, MIR
413-
// generation emits code that does this before calling the op.
414-
if prim.to_bits()? == (1 << (prim.layout.size.bits() - 1)) {
413+
// We check overflow in debug mode already
414+
// so should only check in release mode.
415+
if !oflo_check
416+
&& prim.layout.ty.is_signed()
417+
&& prim.to_bits()? == (1 << (prim.layout.size.bits() - 1)) {
415418
throw_panic!(OverflowNeg)
416419
}
417420
}
@@ -485,7 +488,9 @@ impl<'mir, 'tcx> ConstPropagator<'mir, 'tcx> {
485488
Scalar::from_bool(overflow).into(),
486489
)
487490
} else {
488-
if overflow {
491+
// We check overflow in debug mode already
492+
// so should only check in release mode.
493+
if !self.tcx.sess.overflow_checks() && overflow {
489494
let err = err_panic!(Overflow(op)).into();
490495
let _: Option<()> = self.use_ecx(source_info, |_| Err(err));
491496
return None;

src/test/ui/consts/const-err2.rs

+2-1
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,7 @@
55

66
#![feature(rustc_attrs)]
77
#![allow(exceeding_bitshifts)]
8+
89
#![deny(const_err)]
910

1011
fn black_box<T>(_: T) {
@@ -21,7 +22,7 @@ fn main() {
2122
let d = 42u8 - (42u8 + 1);
2223
//~^ ERROR const_err
2324
let _e = [5u8][1];
24-
//~^ ERROR const_err
25+
//~^ ERROR index out of bounds
2526
black_box(a);
2627
black_box(b);
2728
black_box(c);

src/test/ui/consts/const-err2.stderr

+6-6
Original file line numberDiff line numberDiff line change
@@ -1,35 +1,35 @@
11
error: this expression will panic at runtime
2-
--> $DIR/const-err2.rs:15:13
2+
--> $DIR/const-err2.rs:16:13
33
|
44
LL | let a = -std::i8::MIN;
55
| ^^^^^^^^^^^^^ attempt to negate with overflow
66
|
77
note: lint level defined here
8-
--> $DIR/const-err2.rs:8:9
8+
--> $DIR/const-err2.rs:9:9
99
|
1010
LL | #![deny(const_err)]
1111
| ^^^^^^^^^
1212

1313
error: this expression will panic at runtime
14-
--> $DIR/const-err2.rs:17:13
14+
--> $DIR/const-err2.rs:18:13
1515
|
1616
LL | let b = 200u8 + 200u8 + 200u8;
1717
| ^^^^^^^^^^^^^ attempt to add with overflow
1818

1919
error: this expression will panic at runtime
20-
--> $DIR/const-err2.rs:19:13
20+
--> $DIR/const-err2.rs:20:13
2121
|
2222
LL | let c = 200u8 * 4;
2323
| ^^^^^^^^^ attempt to multiply with overflow
2424

2525
error: this expression will panic at runtime
26-
--> $DIR/const-err2.rs:21:13
26+
--> $DIR/const-err2.rs:22:13
2727
|
2828
LL | let d = 42u8 - (42u8 + 1);
2929
| ^^^^^^^^^^^^^^^^^ attempt to subtract with overflow
3030

3131
error: index out of bounds: the len is 1 but the index is 1
32-
--> $DIR/const-err2.rs:23:14
32+
--> $DIR/const-err2.rs:24:14
3333
|
3434
LL | let _e = [5u8][1];
3535
| ^^^^^^^^

src/test/ui/consts/const-err3.rs

+30
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,30 @@
1+
// needed because negating int::MIN will behave differently between
2+
// optimized compilation and unoptimized compilation and thus would
3+
// lead to different lints being emitted
4+
// compile-flags: -C overflow-checks=on -O
5+
6+
#![feature(rustc_attrs)]
7+
#![allow(exceeding_bitshifts)]
8+
9+
#![deny(const_err)]
10+
11+
fn black_box<T>(_: T) {
12+
unimplemented!()
13+
}
14+
15+
fn main() {
16+
let a = -std::i8::MIN;
17+
//~^ ERROR const_err
18+
let b = 200u8 + 200u8 + 200u8;
19+
//~^ ERROR const_err
20+
let c = 200u8 * 4;
21+
//~^ ERROR const_err
22+
let d = 42u8 - (42u8 + 1);
23+
//~^ ERROR const_err
24+
let _e = [5u8][1];
25+
//~^ ERROR const_err
26+
black_box(a);
27+
black_box(b);
28+
black_box(c);
29+
black_box(d);
30+
}

src/test/ui/consts/const-err3.stderr

+38
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,38 @@
1+
error: attempt to negate with overflow
2+
--> $DIR/const-err3.rs:16:13
3+
|
4+
LL | let a = -std::i8::MIN;
5+
| ^^^^^^^^^^^^^
6+
|
7+
note: lint level defined here
8+
--> $DIR/const-err3.rs:9:9
9+
|
10+
LL | #![deny(const_err)]
11+
| ^^^^^^^^^
12+
13+
error: attempt to add with overflow
14+
--> $DIR/const-err3.rs:18:13
15+
|
16+
LL | let b = 200u8 + 200u8 + 200u8;
17+
| ^^^^^^^^^^^^^
18+
19+
error: attempt to multiply with overflow
20+
--> $DIR/const-err3.rs:20:13
21+
|
22+
LL | let c = 200u8 * 4;
23+
| ^^^^^^^^^
24+
25+
error: attempt to subtract with overflow
26+
--> $DIR/const-err3.rs:22:13
27+
|
28+
LL | let d = 42u8 - (42u8 + 1);
29+
| ^^^^^^^^^^^^^^^^^
30+
31+
error: index out of bounds: the len is 1 but the index is 1
32+
--> $DIR/const-err3.rs:24:14
33+
|
34+
LL | let _e = [5u8][1];
35+
| ^^^^^^^^
36+
37+
error: aborting due to 5 previous errors
38+

src/test/ui/consts/const-eval/promoted_errors.rs

+1-1
Original file line numberDiff line numberDiff line change
@@ -5,7 +5,7 @@
55
fn main() {
66
println!("{}", 0u32 - 1);
77
let _x = 0u32 - 1;
8-
//~^ ERROR this expression will panic at runtime [const_err]
8+
//~^ ERROR const_err
99
println!("{}", 1/(1-1));
1010
//~^ ERROR attempt to divide by zero [const_err]
1111
//~| ERROR reaching this expression at runtime will panic or abort [const_err]
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,22 @@
1+
// compile-flags: -C overflow-checks=on -O
2+
3+
#![deny(const_err)]
4+
5+
fn main() {
6+
println!("{}", 0u32 - 1);
7+
//~^ ERROR attempt to subtract with overflow
8+
let _x = 0u32 - 1;
9+
//~^ ERROR attempt to subtract with overflow
10+
println!("{}", 1/(1-1));
11+
//~^ ERROR attempt to divide by zero [const_err]
12+
//~| ERROR reaching this expression at runtime will panic or abort [const_err]
13+
let _x = 1/(1-1);
14+
//~^ ERROR const_err
15+
//~| ERROR const_err
16+
println!("{}", 1/(false as u32));
17+
//~^ ERROR attempt to divide by zero [const_err]
18+
//~| ERROR reaching this expression at runtime will panic or abort [const_err]
19+
let _x = 1/(false as u32);
20+
//~^ ERROR const_err
21+
//~| ERROR const_err
22+
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,68 @@
1+
error: attempt to subtract with overflow
2+
--> $DIR/promoted_errors2.rs:6:20
3+
|
4+
LL | println!("{}", 0u32 - 1);
5+
| ^^^^^^^^
6+
|
7+
note: lint level defined here
8+
--> $DIR/promoted_errors2.rs:3:9
9+
|
10+
LL | #![deny(const_err)]
11+
| ^^^^^^^^^
12+
13+
error: attempt to subtract with overflow
14+
--> $DIR/promoted_errors2.rs:8:14
15+
|
16+
LL | let _x = 0u32 - 1;
17+
| ^^^^^^^^
18+
19+
error: attempt to divide by zero
20+
--> $DIR/promoted_errors2.rs:10:20
21+
|
22+
LL | println!("{}", 1/(1-1));
23+
| ^^^^^^^
24+
25+
error: reaching this expression at runtime will panic or abort
26+
--> $DIR/promoted_errors2.rs:10:20
27+
|
28+
LL | println!("{}", 1/(1-1));
29+
| ^^^^^^^ attempt to divide by zero
30+
31+
error: attempt to divide by zero
32+
--> $DIR/promoted_errors2.rs:13:14
33+
|
34+
LL | let _x = 1/(1-1);
35+
| ^^^^^^^
36+
37+
error: this expression will panic at runtime
38+
--> $DIR/promoted_errors2.rs:13:14
39+
|
40+
LL | let _x = 1/(1-1);
41+
| ^^^^^^^ attempt to divide by zero
42+
43+
error: attempt to divide by zero
44+
--> $DIR/promoted_errors2.rs:16:20
45+
|
46+
LL | println!("{}", 1/(false as u32));
47+
| ^^^^^^^^^^^^^^^^
48+
49+
error: reaching this expression at runtime will panic or abort
50+
--> $DIR/promoted_errors2.rs:16:20
51+
|
52+
LL | println!("{}", 1/(false as u32));
53+
| ^^^^^^^^^^^^^^^^ attempt to divide by zero
54+
55+
error: attempt to divide by zero
56+
--> $DIR/promoted_errors2.rs:19:14
57+
|
58+
LL | let _x = 1/(false as u32);
59+
| ^^^^^^^^^^^^^^^^
60+
61+
error: this expression will panic at runtime
62+
--> $DIR/promoted_errors2.rs:19:14
63+
|
64+
LL | let _x = 1/(false as u32);
65+
| ^^^^^^^^^^^^^^^^ attempt to divide by zero
66+
67+
error: aborting due to 10 previous errors
68+

src/test/ui/consts/issue-64059-2.rs

+6
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,6 @@
1+
// compile-flags: -C overflow-checks=on -O
2+
// run-pass
3+
4+
fn main() {
5+
let _ = -(-0.0);
6+
}

src/test/ui/consts/issue-64059.rs

+5
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,5 @@
1+
// run-pass
2+
3+
fn main() {
4+
let _ = -(-0.0);
5+
}

src/test/ui/issues/issue-8460-const.rs

+2
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,5 @@
1+
// compile-flags: -O
2+
13
#![deny(const_err)]
24

35
use std::{isize, i8, i16, i32, i64};

0 commit comments

Comments
 (0)