Skip to content

Commit 4ab8f59

Browse files
committed
Report the range of uninit bytes in CTFE errors
1 parent f191420 commit 4ab8f59

18 files changed

+40
-29
lines changed

compiler/rustc_const_eval/src/interpret/operand.rs

Lines changed: 10 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -7,7 +7,7 @@ use either::{Either, Left, Right};
77
use rustc_abi as abi;
88
use rustc_abi::{BackendRepr, HasDataLayout, Size};
99
use rustc_hir::def::Namespace;
10-
use rustc_middle::mir::interpret::ScalarSizeMismatch;
10+
use rustc_middle::mir::interpret::{BadBytesAccess, ScalarSizeMismatch};
1111
use rustc_middle::ty::layout::{HasTyCtxt, HasTypingEnv, TyAndLayout};
1212
use rustc_middle::ty::print::{FmtPrinter, PrettyPrinter};
1313
use rustc_middle::ty::{ConstInt, ScalarInt, Ty, TyCtxt};
@@ -663,7 +663,15 @@ impl<'tcx, M: Machine<'tcx>> InterpCx<'tcx, M> {
663663
}
664664
let imm = self.read_immediate_raw(op)?.right().unwrap();
665665
if matches!(*imm, Immediate::Uninit) {
666-
throw_ub!(InvalidUninitBytes(None));
666+
throw_ub!(InvalidUninitBytes(match op.to_op(self)?.as_mplace_or_imm() {
667+
Left(mplace) => mplace.ptr().provenance.and_then(|prov| {
668+
let start = mplace.ptr().into_parts().1;
669+
let size = op.layout().size;
670+
let range = alloc_range(start, size);
671+
Some((prov.get_alloc_id()?, BadBytesAccess { access: range, bad: range }))
672+
}),
673+
Right(_) => None,
674+
}))
667675
}
668676
interp_ok(imm)
669677
}

compiler/rustc_const_eval/src/interpret/validity.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -397,7 +397,7 @@ impl<'rt, 'tcx, M: Machine<'tcx>> ValidityVisitor<'rt, 'tcx, M> {
397397
interp_ok(try_validation!(
398398
self.ecx.read_immediate(val),
399399
self.path,
400-
Ub(InvalidUninitBytes(None)) =>
400+
Ub(InvalidUninitBytes(_)) =>
401401
Uninit { expected },
402402
// The `Unsup` cases can only occur during CTFE
403403
Unsup(ReadPointerAsInt(_)) =>

compiler/rustc_middle/src/mir/interpret/allocation.rs

Lines changed: 5 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -700,8 +700,11 @@ impl<Prov: Provenance, Extra, Bytes: AllocBytes> Allocation<Prov, Extra, Bytes>
700700
read_provenance: bool,
701701
) -> AllocResult<Scalar<Prov>> {
702702
// First and foremost, if anything is uninit, bail.
703-
if self.init_mask.is_range_initialized(range).is_err() {
704-
return Err(AllocError::InvalidUninitBytes(None));
703+
if let Err(bad) = self.init_mask.is_range_initialized(range) {
704+
return Err(AllocError::InvalidUninitBytes(Some(BadBytesAccess {
705+
access: range,
706+
bad,
707+
})));
705708
}
706709

707710
// Get the integer part of the result. We HAVE TO check provenance before returning this!

tests/ui/const-generics/min_const_generics/invalid-patterns.32bit.stderr

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
error[E0080]: using uninitialized data, but this operation requires initialized memory
1+
error[E0080]: reading memory at ALLOC0[0x0..0x4], but memory is uninitialized at [0x1..0x4], and this operation requires initialized memory
22
--> $DIR/invalid-patterns.rs:40:32
33
|
44
LL | get_flag::<false, { unsafe { char_raw.character } }>();
@@ -26,7 +26,7 @@ LL | get_flag::<{ unsafe { bool_raw.boolean } }, { unsafe { char_raw.character
2626
42 │ B
2727
}
2828

29-
error[E0080]: using uninitialized data, but this operation requires initialized memory
29+
error[E0080]: reading memory at ALLOC1[0x0..0x4], but memory is uninitialized at [0x1..0x4], and this operation requires initialized memory
3030
--> $DIR/invalid-patterns.rs:44:58
3131
|
3232
LL | get_flag::<{ unsafe { bool_raw.boolean } }, { unsafe { char_raw.character } }>();

tests/ui/const-generics/min_const_generics/invalid-patterns.64bit.stderr

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
error[E0080]: using uninitialized data, but this operation requires initialized memory
1+
error[E0080]: reading memory at ALLOC0[0x0..0x4], but memory is uninitialized at [0x1..0x4], and this operation requires initialized memory
22
--> $DIR/invalid-patterns.rs:40:32
33
|
44
LL | get_flag::<false, { unsafe { char_raw.character } }>();
@@ -26,7 +26,7 @@ LL | get_flag::<{ unsafe { bool_raw.boolean } }, { unsafe { char_raw.character
2626
42 │ B
2727
}
2828

29-
error[E0080]: using uninitialized data, but this operation requires initialized memory
29+
error[E0080]: reading memory at ALLOC1[0x0..0x4], but memory is uninitialized at [0x1..0x4], and this operation requires initialized memory
3030
--> $DIR/invalid-patterns.rs:44:58
3131
|
3232
LL | get_flag::<{ unsafe { bool_raw.boolean } }, { unsafe { char_raw.character } }>();

tests/ui/consts/const-err-enum-discriminant.stderr

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
error[E0080]: using uninitialized data, but this operation requires initialized memory
1+
error[E0080]: reading memory at ALLOC0[0x0..0x8], but memory is uninitialized at [0x0..0x8], and this operation requires initialized memory
22
--> $DIR/const-err-enum-discriminant.rs:8:21
33
|
44
LL | Boo = [unsafe { Foo { b: () }.a }; 4][3],

tests/ui/consts/const-eval/const-pointer-values-in-various-types.64bit.stderr

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -43,7 +43,7 @@ LL | const I32_REF_U64_UNION: u64 = unsafe { Nonsense { int_32_ref: &3 }.uin
4343
= help: this code performed an operation that depends on the underlying bytes representing a pointer
4444
= help: the absolute address of a pointer is not known at compile-time, so such operations are not supported
4545

46-
error[E0080]: using uninitialized data, but this operation requires initialized memory
46+
error[E0080]: reading memory at ALLOC0[0x0..0x10], but memory is uninitialized at [0x8..0x10], and this operation requires initialized memory
4747
--> $DIR/const-pointer-values-in-various-types.rs:42:47
4848
|
4949
LL | const I32_REF_U128_UNION: u128 = unsafe { Nonsense { int_32_ref: &3 }.uint_128 };
@@ -85,7 +85,7 @@ LL | const I32_REF_I64_UNION: i64 = unsafe { Nonsense { int_32_ref: &3 }.int
8585
= help: this code performed an operation that depends on the underlying bytes representing a pointer
8686
= help: the absolute address of a pointer is not known at compile-time, so such operations are not supported
8787

88-
error[E0080]: using uninitialized data, but this operation requires initialized memory
88+
error[E0080]: reading memory at ALLOC1[0x0..0x10], but memory is uninitialized at [0x8..0x10], and this operation requires initialized memory
8989
--> $DIR/const-pointer-values-in-various-types.rs:57:47
9090
|
9191
LL | const I32_REF_I128_UNION: i128 = unsafe { Nonsense { int_32_ref: &3 }.int_128 };

tests/ui/consts/const-eval/ub-enum-overwrite.stderr

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
error[E0080]: using uninitialized data, but this operation requires initialized memory
1+
error[E0080]: reading memory at ALLOC0[0x1..0x2], but memory is uninitialized at [0x1..0x2], and this operation requires initialized memory
22
--> $DIR/ub-enum-overwrite.rs:11:14
33
|
44
LL | unsafe { *p }

tests/ui/consts/const-eval/ub-enum.stderr

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -56,7 +56,7 @@ LL | const BAD_ENUM2_WRAPPED: Wrap<Enum2> = unsafe { mem::transmute(&0) };
5656
= help: this code performed an operation that depends on the underlying bytes representing a pointer
5757
= help: the absolute address of a pointer is not known at compile-time, so such operations are not supported
5858

59-
error[E0080]: using uninitialized data, but this operation requires initialized memory
59+
error[E0080]: reading memory at ALLOC0[0x0..0x8], but memory is uninitialized at [0x0..0x8], and this operation requires initialized memory
6060
--> $DIR/ub-enum.rs:61:41
6161
|
6262
LL | const BAD_ENUM2_UNDEF: Enum2 = unsafe { MaybeUninit { uninit: () }.init };

tests/ui/consts/const-eval/ub-nonnull.stderr

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -37,7 +37,7 @@ LL | const NULL_USIZE: NonZero<usize> = unsafe { mem::transmute(0usize) };
3737
HEX_DUMP
3838
}
3939

40-
error[E0080]: using uninitialized data, but this operation requires initialized memory
40+
error[E0080]: reading memory at ALLOC2[0x0..0x1], but memory is uninitialized at [0x0..0x1], and this operation requires initialized memory
4141
--> $DIR/ub-nonnull.rs:36:38
4242
|
4343
LL | const UNINIT: NonZero<u8> = unsafe { MaybeUninit { uninit: () }.init };

tests/ui/consts/const-eval/ub-ref-ptr.stderr

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -103,7 +103,7 @@ LL | const USIZE_AS_BOX: Box<u8> = unsafe { mem::transmute(1337usize) };
103103
HEX_DUMP
104104
}
105105

106-
error[E0080]: using uninitialized data, but this operation requires initialized memory
106+
error[E0080]: reading memory at ALLOC3[0x0..0x8], but memory is uninitialized at [0x0..0x8], and this operation requires initialized memory
107107
--> $DIR/ub-ref-ptr.rs:48:41
108108
|
109109
LL | const UNINIT_PTR: *const i32 = unsafe { MaybeUninit { uninit: () }.init };
@@ -120,7 +120,7 @@ LL | const NULL_FN_PTR: fn() = unsafe { mem::transmute(0usize) };
120120
HEX_DUMP
121121
}
122122

123-
error[E0080]: using uninitialized data, but this operation requires initialized memory
123+
error[E0080]: reading memory at ALLOC4[0x0..0x8], but memory is uninitialized at [0x0..0x8], and this operation requires initialized memory
124124
--> $DIR/ub-ref-ptr.rs:53:38
125125
|
126126
LL | const UNINIT_FN_PTR: fn() = unsafe { MaybeUninit { uninit: () }.init };

tests/ui/consts/const-eval/ub-wide-ptr.stderr

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -71,7 +71,7 @@ LL | const MYSTR_NO_INIT: &MyStr = unsafe { mem::transmute::<&[_], _>(&[MaybeUni
7171
HEX_DUMP
7272
}
7373

74-
error[E0080]: using uninitialized data, but this operation requires initialized memory
74+
error[E0080]: reading memory at ALLOC32[0x0..0x8], but memory is uninitialized at [0x4..0x8], and this operation requires initialized memory
7575
--> $DIR/ub-wide-ptr.rs:63:1
7676
|
7777
LL | const SLICE_LENGTH_UNINIT: &[u8] = unsafe {
@@ -179,7 +179,7 @@ note: erroneous constant encountered
179179
LL | const MYSLICE_SUFFIX_BAD: &MySliceBool = &MySlice(true, [unsafe { mem::transmute(3u8) }]);
180180
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
181181

182-
error[E0080]: using uninitialized data, but this operation requires initialized memory
182+
error[E0080]: reading memory at ALLOC33[0x0..0x8], but memory is uninitialized at [0x4..0x8], and this operation requires initialized memory
183183
--> $DIR/ub-wide-ptr.rs:101:1
184184
|
185185
LL | const RAW_SLICE_LENGTH_UNINIT: *const [u8] = unsafe {

tests/ui/consts/const-eval/union-const-eval-field.stderr

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
error[E0080]: using uninitialized data, but this operation requires initialized memory
1+
error[E0080]: reading memory at ALLOC0[0x0..0x8], but memory is uninitialized at [0x4..0x8], and this operation requires initialized memory
22
--> $DIR/union-const-eval-field.rs:28:37
33
|
44
LL | const FIELD3: Field3 = unsafe { UNION.field3 };

tests/ui/consts/const-eval/union-ice.stderr

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,16 +1,16 @@
1-
error[E0080]: using uninitialized data, but this operation requires initialized memory
1+
error[E0080]: reading memory at ALLOC0[0x0..0x8], but memory is uninitialized at [0x4..0x8], and this operation requires initialized memory
22
--> $DIR/union-ice.rs:14:33
33
|
44
LL | const FIELD3: Field3 = unsafe { UNION.field3 };
55
| ^^^^^^^^^^^^ evaluation of `FIELD3` failed here
66

7-
error[E0080]: using uninitialized data, but this operation requires initialized memory
7+
error[E0080]: reading memory at ALLOC1[0x0..0x8], but memory is uninitialized at [0x4..0x8], and this operation requires initialized memory
88
--> $DIR/union-ice.rs:19:17
99
|
1010
LL | b: unsafe { UNION.field3 },
1111
| ^^^^^^^^^^^^ evaluation of `FIELD_PATH` failed here
1212

13-
error[E0080]: using uninitialized data, but this operation requires initialized memory
13+
error[E0080]: reading memory at ALLOC2[0x0..0x8], but memory is uninitialized at [0x4..0x8], and this operation requires initialized memory
1414
--> $DIR/union-ice.rs:31:18
1515
|
1616
LL | unsafe { UNION.field3 },

tests/ui/consts/const-eval/union-ub.32bit.stderr

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -9,7 +9,7 @@ LL | const BAD_BOOL: bool = unsafe { DummyUnion { u8: 42 }.bool };
99
2a │ *
1010
}
1111

12-
error[E0080]: using uninitialized data, but this operation requires initialized memory
12+
error[E0080]: reading memory at ALLOC0[0x0..0x1], but memory is uninitialized at [0x0..0x1], and this operation requires initialized memory
1313
--> $DIR/union-ub.rs:35:36
1414
|
1515
LL | const UNINIT_BOOL: bool = unsafe { DummyUnion { unit: () }.bool };

tests/ui/consts/const-eval/union-ub.64bit.stderr

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -9,7 +9,7 @@ LL | const BAD_BOOL: bool = unsafe { DummyUnion { u8: 42 }.bool };
99
2a │ *
1010
}
1111

12-
error[E0080]: using uninitialized data, but this operation requires initialized memory
12+
error[E0080]: reading memory at ALLOC0[0x0..0x1], but memory is uninitialized at [0x0..0x1], and this operation requires initialized memory
1313
--> $DIR/union-ub.rs:35:36
1414
|
1515
LL | const UNINIT_BOOL: bool = unsafe { DummyUnion { unit: () }.bool };

tests/ui/type/pattern_types/validity.rs

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -11,7 +11,7 @@ const BAD: pattern_type!(u32 is 1..) = unsafe { std::mem::transmute(0) };
1111
//~^ ERROR: constructing invalid value: encountered 0
1212

1313
const BAD_UNINIT: pattern_type!(u32 is 1..) =
14-
//~^ ERROR: using uninitialized data, but this operation requires initialized memory
14+
//~^ ERROR: this operation requires initialized memory
1515
unsafe { std::mem::transmute(std::mem::MaybeUninit::<u32>::uninit()) };
1616

1717
const BAD_PTR: pattern_type!(usize is 1..) = unsafe { std::mem::transmute(&42) };
@@ -27,7 +27,7 @@ const BAD_FOO: Foo = Foo(Bar(unsafe { std::mem::transmute(0) }));
2727
//~^ ERROR: constructing invalid value at .0.0: encountered 0
2828

2929
const CHAR_UNINIT: pattern_type!(char is 'A'..'Z') =
30-
//~^ ERROR: using uninitialized data, but this operation requires initialized memory
30+
//~^ ERROR: this operation requires initialized memory
3131
unsafe { std::mem::transmute(std::mem::MaybeUninit::<u32>::uninit()) };
3232

3333
const CHAR_OOB_PAT: pattern_type!(char is 'A'..'Z') = unsafe { std::mem::transmute('a') };

tests/ui/type/pattern_types/validity.stderr

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -9,7 +9,7 @@ LL | const BAD: pattern_type!(u32 is 1..) = unsafe { std::mem::transmute(0) };
99
HEX_DUMP
1010
}
1111

12-
error[E0080]: using uninitialized data, but this operation requires initialized memory
12+
error[E0080]: reading memory at ALLOC0[0x0..0x4], but memory is uninitialized at [0x0..0x4], and this operation requires initialized memory
1313
--> $DIR/validity.rs:13:1
1414
|
1515
LL | const BAD_UNINIT: pattern_type!(u32 is 1..) =
@@ -46,7 +46,7 @@ LL | const BAD_FOO: Foo = Foo(Bar(unsafe { std::mem::transmute(0) }));
4646
HEX_DUMP
4747
}
4848

49-
error[E0080]: using uninitialized data, but this operation requires initialized memory
49+
error[E0080]: reading memory at ALLOC1[0x0..0x4], but memory is uninitialized at [0x0..0x4], and this operation requires initialized memory
5050
--> $DIR/validity.rs:29:1
5151
|
5252
LL | const CHAR_UNINIT: pattern_type!(char is 'A'..'Z') =

0 commit comments

Comments
 (0)