diff options
| author | bors <bors@rust-lang.org> | 2023-09-12 05:38:25 +0000 |
|---|---|---|
| committer | bors <bors@rust-lang.org> | 2023-09-12 05:38:25 +0000 |
| commit | ea488f786442aeed98ad8158d50a7017c415dec4 (patch) | |
| tree | 74180c12ca0b1d828dfdde86adfe37739c39eb51 /tests | |
| parent | 3bf9c5a00a29e6294fbc603cbdcb351175d9d5bf (diff) | |
| parent | 1916a4a5244b8f788170f0ec0444b9e0f6772b54 (diff) | |
| download | rust-ea488f786442aeed98ad8158d50a7017c415dec4.tar.gz rust-ea488f786442aeed98ad8158d50a7017c415dec4.zip | |
Auto merge of #3059 - rust-lang:rustup-2023-09-12, r=RalfJung
Automatic sync from rustc
Diffstat (limited to 'tests')
333 files changed, 5765 insertions, 406 deletions
diff --git a/tests/codegen/debuginfo-inline-callsite-location.rs b/tests/codegen/debuginfo-inline-callsite-location.rs new file mode 100644 index 00000000000..b1475ee7931 --- /dev/null +++ b/tests/codegen/debuginfo-inline-callsite-location.rs @@ -0,0 +1,28 @@ +// compile-flags: -g -O + +// Check that each inline call site for the same function uses the same "sub-program" so that LLVM +// can correctly merge the debug info if it merges the inlined code (e.g., for merging of tail +// calls to panic. + +// CHECK: tail call void @_ZN4core9panicking5panic17h{{([0-9a-z]{16})}}E +// CHECK-SAME: !dbg ![[#first_dbg:]] +// CHECK: tail call void @_ZN4core9panicking5panic17h{{([0-9a-z]{16})}}E +// CHECK-SAME: !dbg ![[#second_dbg:]] + +// CHECK-DAG: ![[#func_dbg:]] = distinct !DISubprogram(name: "unwrap<i32>" +// CHECK-DAG: ![[#first_scope:]] = distinct !DILexicalBlock(scope: ![[#func_dbg]], +// CHECK: ![[#second_scope:]] = distinct !DILexicalBlock(scope: ![[#func_dbg]], +// CHECK: ![[#first_dbg]] = !DILocation(line: [[#]] +// CHECK-SAME: scope: ![[#first_scope]], inlinedAt: ![[#]]) +// CHECK: ![[#second_dbg]] = !DILocation(line: [[#]] +// CHECK-SAME: scope: ![[#second_scope]], inlinedAt: ![[#]]) + +#![crate_type = "lib"] + +#[no_mangle] +extern "C" fn add_numbers(x: &Option<i32>, y: &Option<i32>) -> i32 { + let x1 = x.unwrap(); + let y1 = y.unwrap(); + + x1 + y1 +} diff --git a/tests/codegen/issues/issue-115385-llvm-jump-threading.rs b/tests/codegen/issues/issue-115385-llvm-jump-threading.rs new file mode 100644 index 00000000000..142e3596d96 --- /dev/null +++ b/tests/codegen/issues/issue-115385-llvm-jump-threading.rs @@ -0,0 +1,46 @@ +// compile-flags: -O -Ccodegen-units=1 + +#![crate_type = "lib"] + +#[repr(i64)] +pub enum Boolean { + False = 0, + True = 1, +} + +impl Clone for Boolean { + fn clone(&self) -> Self { + *self + } +} + +impl Copy for Boolean {} + +extern "C" { + fn set_value(foo: *mut i64); + fn bar(); +} + +pub fn foo(x: bool) { + let mut foo = core::mem::MaybeUninit::<i64>::uninit(); + unsafe { + set_value(foo.as_mut_ptr()); + } + + if x { + let l1 = unsafe { *foo.as_mut_ptr().cast::<Boolean>() }; + if matches!(l1, Boolean::False) { + unsafe { + *foo.as_mut_ptr() = 0; + } + } + } + + let l2 = unsafe { *foo.as_mut_ptr() }; + if l2 == 2 { + // CHECK: call void @bar + unsafe { + bar(); + } + } +} diff --git a/tests/codegen/repr/transparent.rs b/tests/codegen/repr/transparent.rs index b140fc719da..c5974248bb3 100644 --- a/tests/codegen/repr/transparent.rs +++ b/tests/codegen/repr/transparent.rs @@ -43,7 +43,6 @@ pub extern "C" fn test_WithZst(_: WithZst) -> WithZst { loop {} } #[repr(transparent)] pub struct WithZeroSizedArray(*const f32, [i8; 0]); -// Apparently we use i32* when newtype-unwrapping f32 pointers. Whatever. // CHECK: define{{.*}}ptr @test_WithZeroSizedArray(ptr noundef %_1) #[no_mangle] pub extern "C" fn test_WithZeroSizedArray(_: WithZeroSizedArray) -> WithZeroSizedArray { loop {} } diff --git a/tests/codegen/sanitizer/address-sanitizer-globals-tracking.rs b/tests/codegen/sanitizer/address-sanitizer-globals-tracking.rs new file mode 100644 index 00000000000..a70ef7751b6 --- /dev/null +++ b/tests/codegen/sanitizer/address-sanitizer-globals-tracking.rs @@ -0,0 +1,43 @@ +// Verifies that AddressSanitizer symbols show up as expected in LLVM IR with `-Zsanitizer`. +// This is a regression test for https://github.com/rust-lang/rust/issues/113404 +// +// Notes about the `compile-flags` below: +// +// * The original issue only reproed with LTO - this is why this angle has +// extra test coverage via different `revisions` +// * To observe the failure/repro at LLVM-IR level we need to use `staticlib` +// which necessitates `-C prefer-dynamic=false` - without the latter flag, +// we would have run into "cannot prefer dynamic linking when performing LTO". +// +// The test is restricted to `only-linux`, because the sanitizer-related instrumentation is target +// specific. In particular, `___asan_globals_registered` is only used in the +// `InstrumentGlobalsELF` and `InstrumentGlobalsMachO` code paths. The `only-linux` filter is +// narrower than really needed (i.e. narrower than ELF-or-MachO), but this seems ok - having a +// linux-only regression test should be sufficient here. +// +// needs-sanitizer-address +// only-linux +// +// revisions:ASAN ASAN-FAT-LTO +//[ASAN] compile-flags: -Zsanitizer=address +//[ASAN-FAT-LTO] compile-flags: -Zsanitizer=address -Cprefer-dynamic=false -Clto=fat + +#![crate_type="staticlib"] + +// The test below mimics `CACHED_POW10` from `library/core/src/num/flt2dec/strategy/grisu.rs` which +// (because of incorrect handling of `___asan_globals_registered` during LTO) was incorrectly +// reported as an ODR violation in https://crbug.com/1459233#c1. Before this bug was fixed, +// `___asan_globals_registered` would show up as `internal global i64` rather than `common hidden +// global i64`. (The test expectations ignore the exact type because on `arm-android` the type +// is `i32` rather than `i64`.) +// +// CHECK: @___asan_globals_registered = common hidden global +// CHECK: @__start_asan_globals = extern_weak hidden global +// CHECK: @__stop_asan_globals = extern_weak hidden global +#[no_mangle] +pub static CACHED_POW10: [(u64, i16, i16); 4] = [ + (0xe61acf033d1a45df, -1087, -308), + (0xab70fe17c79ac6ca, -1060, -300), + (0xff77b1fcbebcdc4f, -1034, -292), + (0xbe5691ef416bd60c, -1007, -284), +]; diff --git a/tests/mir-opt/building/async_await.b-{closure#0}.generator_resume.0.mir b/tests/mir-opt/building/async_await.b-{closure#0}.generator_resume.0.mir index 80ac92d59f3..b06666c9dd7 100644 --- a/tests/mir-opt/building/async_await.b-{closure#0}.generator_resume.0.mir +++ b/tests/mir-opt/building/async_await.b-{closure#0}.generator_resume.0.mir @@ -2,7 +2,14 @@ /* generator_layout = GeneratorLayout { field_tys: { _0: GeneratorSavedTy { - ty: impl std::future::Future<Output = ()>, + ty: Alias( + Opaque, + AliasTy { + args: [ + ], + def_id: DefId(0:7 ~ async_await[ccf8]::a::{opaque#0}), + }, + ), source_info: SourceInfo { span: $DIR/async_await.rs:15:9: 15:14 (#8), scope: scope[0], @@ -10,7 +17,14 @@ ignore_for_traits: false, }, _1: GeneratorSavedTy { - ty: impl std::future::Future<Output = ()>, + ty: Alias( + Opaque, + AliasTy { + args: [ + ], + def_id: DefId(0:7 ~ async_await[ccf8]::a::{opaque#0}), + }, + ), source_info: SourceInfo { span: $DIR/async_await.rs:16:9: 16:14 (#10), scope: scope[0], diff --git a/tests/mir-opt/const_debuginfo.main.ConstDebugInfo.diff b/tests/mir-opt/const_debuginfo.main.ConstDebugInfo.diff index 255ec94816c..ed47baa67da 100644 --- a/tests/mir-opt/const_debuginfo.main.ConstDebugInfo.diff +++ b/tests/mir-opt/const_debuginfo.main.ConstDebugInfo.diff @@ -33,14 +33,22 @@ let _15: bool; let _16: u32; scope 6 { - debug f => (bool, bool, u32){ .0 => _14, .1 => _15, .2 => _16, }; +- debug ((f: (bool, bool, u32)).0: bool) => _14; +- debug ((f: (bool, bool, u32)).1: bool) => _15; +- debug ((f: (bool, bool, u32)).2: u32) => _16; ++ debug ((f: (bool, bool, u32)).0: bool) => const true; ++ debug ((f: (bool, bool, u32)).1: bool) => const false; ++ debug ((f: (bool, bool, u32)).2: u32) => const 123_u32; let _10: std::option::Option<u16>; scope 7 { debug o => _10; let _17: u32; let _18: u32; scope 8 { - debug p => Point{ .0 => _17, .1 => _18, }; +- debug ((p: Point).0: u32) => _17; +- debug ((p: Point).1: u32) => _18; ++ debug ((p: Point).0: u32) => const 32_u32; ++ debug ((p: Point).1: u32) => const 32_u32; let _11: u32; scope 9 { - debug a => _11; diff --git a/tests/mir-opt/const_prop/bad_op_unsafe_oob_for_slices.main.ConstProp.32bit.panic-abort.diff b/tests/mir-opt/const_prop/bad_op_unsafe_oob_for_slices.main.ConstProp.32bit.panic-abort.diff index 55c774d555d..e443c8991f9 100644 --- a/tests/mir-opt/const_prop/bad_op_unsafe_oob_for_slices.main.ConstProp.32bit.panic-abort.diff +++ b/tests/mir-opt/const_prop/bad_op_unsafe_oob_for_slices.main.ConstProp.32bit.panic-abort.diff @@ -34,11 +34,11 @@ StorageLive(_5); StorageLive(_6); _6 = const 3_usize; - _7 = const 3_usize; + _7 = Len((*_1)); - _8 = Lt(_6, _7); - assert(move _8, "index out of bounds: the length is {} but the index is {}", move _7, _6) -> [success: bb1, unwind unreachable]; -+ _8 = const false; -+ assert(const false, "index out of bounds: the length is {} but the index is {}", const 3_usize, const 3_usize) -> [success: bb1, unwind unreachable]; ++ _8 = Lt(const 3_usize, _7); ++ assert(move _8, "index out of bounds: the length is {} but the index is {}", move _7, const 3_usize) -> [success: bb1, unwind unreachable]; } bb1: { diff --git a/tests/mir-opt/const_prop/bad_op_unsafe_oob_for_slices.main.ConstProp.32bit.panic-unwind.diff b/tests/mir-opt/const_prop/bad_op_unsafe_oob_for_slices.main.ConstProp.32bit.panic-unwind.diff index dcab570ea77..592f43f4739 100644 --- a/tests/mir-opt/const_prop/bad_op_unsafe_oob_for_slices.main.ConstProp.32bit.panic-unwind.diff +++ b/tests/mir-opt/const_prop/bad_op_unsafe_oob_for_slices.main.ConstProp.32bit.panic-unwind.diff @@ -34,11 +34,11 @@ StorageLive(_5); StorageLive(_6); _6 = const 3_usize; - _7 = const 3_usize; + _7 = Len((*_1)); - _8 = Lt(_6, _7); - assert(move _8, "index out of bounds: the length is {} but the index is {}", move _7, _6) -> [success: bb1, unwind continue]; -+ _8 = const false; -+ assert(const false, "index out of bounds: the length is {} but the index is {}", const 3_usize, const 3_usize) -> [success: bb1, unwind continue]; ++ _8 = Lt(const 3_usize, _7); ++ assert(move _8, "index out of bounds: the length is {} but the index is {}", move _7, const 3_usize) -> [success: bb1, unwind continue]; } bb1: { diff --git a/tests/mir-opt/const_prop/bad_op_unsafe_oob_for_slices.main.ConstProp.64bit.panic-abort.diff b/tests/mir-opt/const_prop/bad_op_unsafe_oob_for_slices.main.ConstProp.64bit.panic-abort.diff index 55c774d555d..e443c8991f9 100644 --- a/tests/mir-opt/const_prop/bad_op_unsafe_oob_for_slices.main.ConstProp.64bit.panic-abort.diff +++ b/tests/mir-opt/const_prop/bad_op_unsafe_oob_for_slices.main.ConstProp.64bit.panic-abort.diff @@ -34,11 +34,11 @@ StorageLive(_5); StorageLive(_6); _6 = const 3_usize; - _7 = const 3_usize; + _7 = Len((*_1)); - _8 = Lt(_6, _7); - assert(move _8, "index out of bounds: the length is {} but the index is {}", move _7, _6) -> [success: bb1, unwind unreachable]; -+ _8 = const false; -+ assert(const false, "index out of bounds: the length is {} but the index is {}", const 3_usize, const 3_usize) -> [success: bb1, unwind unreachable]; ++ _8 = Lt(const 3_usize, _7); ++ assert(move _8, "index out of bounds: the length is {} but the index is {}", move _7, const 3_usize) -> [success: bb1, unwind unreachable]; } bb1: { diff --git a/tests/mir-opt/const_prop/bad_op_unsafe_oob_for_slices.main.ConstProp.64bit.panic-unwind.diff b/tests/mir-opt/const_prop/bad_op_unsafe_oob_for_slices.main.ConstProp.64bit.panic-unwind.diff index dcab570ea77..592f43f4739 100644 --- a/tests/mir-opt/const_prop/bad_op_unsafe_oob_for_slices.main.ConstProp.64bit.panic-unwind.diff +++ b/tests/mir-opt/const_prop/bad_op_unsafe_oob_for_slices.main.ConstProp.64bit.panic-unwind.diff @@ -34,11 +34,11 @@ StorageLive(_5); StorageLive(_6); _6 = const 3_usize; - _7 = const 3_usize; + _7 = Len((*_1)); - _8 = Lt(_6, _7); - assert(move _8, "index out of bounds: the length is {} but the index is {}", move _7, _6) -> [success: bb1, unwind continue]; -+ _8 = const false; -+ assert(const false, "index out of bounds: the length is {} but the index is {}", const 3_usize, const 3_usize) -> [success: bb1, unwind continue]; ++ _8 = Lt(const 3_usize, _7); ++ assert(move _8, "index out of bounds: the length is {} but the index is {}", move _7, const 3_usize) -> [success: bb1, unwind continue]; } bb1: { diff --git a/tests/mir-opt/const_prop/bad_op_unsafe_oob_for_slices.rs b/tests/mir-opt/const_prop/bad_op_unsafe_oob_for_slices.rs index 7931c4f02ae..d6b1a93f304 100644 --- a/tests/mir-opt/const_prop/bad_op_unsafe_oob_for_slices.rs +++ b/tests/mir-opt/const_prop/bad_op_unsafe_oob_for_slices.rs @@ -1,8 +1,7 @@ // unit-test: ConstProp // EMIT_MIR_FOR_EACH_PANIC_STRATEGY -// compile-flags: -Zmir-enable-passes=+NormalizeArrayLen - // EMIT_MIR_FOR_EACH_BIT_WIDTH + // EMIT_MIR bad_op_unsafe_oob_for_slices.main.ConstProp.diff #[allow(unconditional_panic)] fn main() { diff --git a/tests/mir-opt/const_prop/large_array_index.rs b/tests/mir-opt/const_prop/large_array_index.rs index 6c03fe9d9c2..d226bd54671 100644 --- a/tests/mir-opt/const_prop/large_array_index.rs +++ b/tests/mir-opt/const_prop/large_array_index.rs @@ -1,6 +1,5 @@ // unit-test: ConstProp // EMIT_MIR_FOR_EACH_PANIC_STRATEGY -// compile-flags: -Zmir-enable-passes=+NormalizeArrayLen // EMIT_MIR_FOR_EACH_BIT_WIDTH // EMIT_MIR large_array_index.main.ConstProp.diff diff --git a/tests/mir-opt/const_prop/repeat.rs b/tests/mir-opt/const_prop/repeat.rs index 21dba84af37..fb8b825ee36 100644 --- a/tests/mir-opt/const_prop/repeat.rs +++ b/tests/mir-opt/const_prop/repeat.rs @@ -1,6 +1,5 @@ // unit-test: ConstProp // EMIT_MIR_FOR_EACH_PANIC_STRATEGY -// compile-flags: -Zmir-enable-passes=+NormalizeArrayLen // EMIT_MIR_FOR_EACH_BIT_WIDTH // EMIT_MIR repeat.main.ConstProp.diff diff --git a/tests/mir-opt/dataflow-const-prop/array_index.main.DataflowConstProp.32bit.panic-abort.diff b/tests/mir-opt/dataflow-const-prop/array_index.main.DataflowConstProp.32bit.panic-abort.diff new file mode 100644 index 00000000000..212ddc5b154 --- /dev/null +++ b/tests/mir-opt/dataflow-const-prop/array_index.main.DataflowConstProp.32bit.panic-abort.diff @@ -0,0 +1,39 @@ +- // MIR for `main` before DataflowConstProp ++ // MIR for `main` after DataflowConstProp + + fn main() -> () { + let mut _0: (); + let _1: u32; + let mut _2: [u32; 4]; + let _3: usize; + let mut _4: usize; + let mut _5: bool; + scope 1 { + debug x => _1; + } + + bb0: { + StorageLive(_1); + StorageLive(_2); + _2 = [const 0_u32, const 1_u32, const 2_u32, const 3_u32]; + StorageLive(_3); + _3 = const 2_usize; +- _4 = Len(_2); +- _5 = Lt(_3, _4); +- assert(move _5, "index out of bounds: the length is {} but the index is {}", move _4, _3) -> [success: bb1, unwind unreachable]; ++ _4 = const 4_usize; ++ _5 = const true; ++ assert(const true, "index out of bounds: the length is {} but the index is {}", const 4_usize, const 2_usize) -> [success: bb1, unwind unreachable]; + } + + bb1: { +- _1 = _2[_3]; ++ _1 = _2[2 of 3]; + StorageDead(_3); + StorageDead(_2); + _0 = const (); + StorageDead(_1); + return; + } + } + diff --git a/tests/mir-opt/dataflow-const-prop/array_index.main.DataflowConstProp.32bit.panic-unwind.diff b/tests/mir-opt/dataflow-const-prop/array_index.main.DataflowConstProp.32bit.panic-unwind.diff new file mode 100644 index 00000000000..5c53d4f4461 --- /dev/null +++ b/tests/mir-opt/dataflow-const-prop/array_index.main.DataflowConstProp.32bit.panic-unwind.diff @@ -0,0 +1,39 @@ +- // MIR for `main` before DataflowConstProp ++ // MIR for `main` after DataflowConstProp + + fn main() -> () { + let mut _0: (); + let _1: u32; + let mut _2: [u32; 4]; + let _3: usize; + let mut _4: usize; + let mut _5: bool; + scope 1 { + debug x => _1; + } + + bb0: { + StorageLive(_1); + StorageLive(_2); + _2 = [const 0_u32, const 1_u32, const 2_u32, const 3_u32]; + StorageLive(_3); + _3 = const 2_usize; +- _4 = Len(_2); +- _5 = Lt(_3, _4); +- assert(move _5, "index out of bounds: the length is {} but the index is {}", move _4, _3) -> [success: bb1, unwind continue]; ++ _4 = const 4_usize; ++ _5 = const true; ++ assert(const true, "index out of bounds: the length is {} but the index is {}", const 4_usize, const 2_usize) -> [success: bb1, unwind continue]; + } + + bb1: { +- _1 = _2[_3]; ++ _1 = _2[2 of 3]; + StorageDead(_3); + StorageDead(_2); + _0 = const (); + StorageDead(_1); + return; + } + } + diff --git a/tests/mir-opt/dataflow-const-prop/array_index.main.DataflowConstProp.64bit.panic-abort.diff b/tests/mir-opt/dataflow-const-prop/array_index.main.DataflowConstProp.64bit.panic-abort.diff new file mode 100644 index 00000000000..212ddc5b154 --- /dev/null +++ b/tests/mir-opt/dataflow-const-prop/array_index.main.DataflowConstProp.64bit.panic-abort.diff @@ -0,0 +1,39 @@ +- // MIR for `main` before DataflowConstProp ++ // MIR for `main` after DataflowConstProp + + fn main() -> () { + let mut _0: (); + let _1: u32; + let mut _2: [u32; 4]; + let _3: usize; + let mut _4: usize; + let mut _5: bool; + scope 1 { + debug x => _1; + } + + bb0: { + StorageLive(_1); + StorageLive(_2); + _2 = [const 0_u32, const 1_u32, const 2_u32, const 3_u32]; + StorageLive(_3); + _3 = const 2_usize; +- _4 = Len(_2); +- _5 = Lt(_3, _4); +- assert(move _5, "index out of bounds: the length is {} but the index is {}", move _4, _3) -> [success: bb1, unwind unreachable]; ++ _4 = const 4_usize; ++ _5 = const true; ++ assert(const true, "index out of bounds: the length is {} but the index is {}", const 4_usize, const 2_usize) -> [success: bb1, unwind unreachable]; + } + + bb1: { +- _1 = _2[_3]; ++ _1 = _2[2 of 3]; + StorageDead(_3); + StorageDead(_2); + _0 = const (); + StorageDead(_1); + return; + } + } + diff --git a/tests/mir-opt/dataflow-const-prop/array_index.main.DataflowConstProp.64bit.panic-unwind.diff b/tests/mir-opt/dataflow-const-prop/array_index.main.DataflowConstProp.64bit.panic-unwind.diff new file mode 100644 index 00000000000..5c53d4f4461 --- /dev/null +++ b/tests/mir-opt/dataflow-const-prop/array_index.main.DataflowConstProp.64bit.panic-unwind.diff @@ -0,0 +1,39 @@ +- // MIR for `main` before DataflowConstProp ++ // MIR for `main` after DataflowConstProp + + fn main() -> () { + let mut _0: (); + let _1: u32; + let mut _2: [u32; 4]; + let _3: usize; + let mut _4: usize; + let mut _5: bool; + scope 1 { + debug x => _1; + } + + bb0: { + StorageLive(_1); + StorageLive(_2); + _2 = [const 0_u32, const 1_u32, const 2_u32, const 3_u32]; + StorageLive(_3); + _3 = const 2_usize; +- _4 = Len(_2); +- _5 = Lt(_3, _4); +- assert(move _5, "index out of bounds: the length is {} but the index is {}", move _4, _3) -> [success: bb1, unwind continue]; ++ _4 = const 4_usize; ++ _5 = const true; ++ assert(const true, "index out of bounds: the length is {} but the index is {}", const 4_usize, const 2_usize) -> [success: bb1, unwind continue]; + } + + bb1: { +- _1 = _2[_3]; ++ _1 = _2[2 of 3]; + StorageDead(_3); + StorageDead(_2); + _0 = const (); + StorageDead(_1); + return; + } + } + diff --git a/tests/mir-opt/dataflow-const-prop/array_index.rs b/tests/mir-opt/dataflow-const-prop/array_index.rs new file mode 100644 index 00000000000..ddb3646ca9b --- /dev/null +++ b/tests/mir-opt/dataflow-const-prop/array_index.rs @@ -0,0 +1,8 @@ +// EMIT_MIR_FOR_EACH_PANIC_STRATEGY +// unit-test: DataflowConstProp +// EMIT_MIR_FOR_EACH_BIT_WIDTH + +// EMIT_MIR array_index.main.DataflowConstProp.diff +fn main() { + let x: u32 = [0, 1, 2, 3][2]; +} diff --git a/tests/mir-opt/dataflow-const-prop/boolean_identities.rs b/tests/mir-opt/dataflow-const-prop/boolean_identities.rs new file mode 100644 index 00000000000..9e911e85b88 --- /dev/null +++ b/tests/mir-opt/dataflow-const-prop/boolean_identities.rs @@ -0,0 +1,10 @@ +// unit-test: DataflowConstProp + +// EMIT_MIR boolean_identities.test.DataflowConstProp.diff +pub fn test(x: bool, y: bool) -> bool { + (y | true) & (x & false) +} + +fn main() { + test(true, false); +} diff --git a/tests/mir-opt/dataflow-const-prop/boolean_identities.test.DataflowConstProp.diff b/tests/mir-opt/dataflow-const-prop/boolean_identities.test.DataflowConstProp.diff new file mode 100644 index 00000000000..5440c38ce4b --- /dev/null +++ b/tests/mir-opt/dataflow-const-prop/boolean_identities.test.DataflowConstProp.diff @@ -0,0 +1,33 @@ +- // MIR for `test` before DataflowConstProp ++ // MIR for `test` after DataflowConstProp + + fn test(_1: bool, _2: bool) -> bool { + debug x => _1; + debug y => _2; + let mut _0: bool; + let mut _3: bool; + let mut _4: bool; + let mut _5: bool; + let mut _6: bool; + + bb0: { + StorageLive(_3); + StorageLive(_4); + _4 = _2; +- _3 = BitOr(move _4, const true); ++ _3 = const true; + StorageDead(_4); + StorageLive(_5); + StorageLive(_6); + _6 = _1; +- _5 = BitAnd(move _6, const false); ++ _5 = const false; + StorageDead(_6); +- _0 = BitAnd(move _3, move _5); ++ _0 = const false; + StorageDead(_5); + StorageDead(_3); + return; + } + } + diff --git a/tests/mir-opt/dataflow-const-prop/large_array_index.main.DataflowConstProp.32bit.panic-abort.diff b/tests/mir-opt/dataflow-const-prop/large_array_index.main.DataflowConstProp.32bit.panic-abort.diff new file mode 100644 index 00000000000..6c612d46725 --- /dev/null +++ b/tests/mir-opt/dataflow-const-prop/large_array_index.main.DataflowConstProp.32bit.panic-abort.diff @@ -0,0 +1,39 @@ +- // MIR for `main` before DataflowConstProp ++ // MIR for `main` after DataflowConstProp + + fn main() -> () { + let mut _0: (); + let _1: u8; + let mut _2: [u8; 5000]; + let _3: usize; + let mut _4: usize; + let mut _5: bool; + scope 1 { + debug x => _1; + } + + bb0: { + StorageLive(_1); + StorageLive(_2); + _2 = [const 0_u8; 5000]; + StorageLive(_3); + _3 = const 2_usize; +- _4 = Len(_2); +- _5 = Lt(_3, _4); +- assert(move _5, "index out of bounds: the length is {} but the index is {}", move _4, _3) -> [success: bb1, unwind unreachable]; ++ _4 = const 5000_usize; ++ _5 = const true; ++ assert(const true, "index out of bounds: the length is {} but the index is {}", const 5000_usize, const 2_usize) -> [success: bb1, unwind unreachable]; + } + + bb1: { +- _1 = _2[_3]; ++ _1 = _2[2 of 3]; + StorageDead(_3); + StorageDead(_2); + _0 = const (); + StorageDead(_1); + return; + } + } + diff --git a/tests/mir-opt/dataflow-const-prop/large_array_index.main.DataflowConstProp.32bit.panic-unwind.diff b/tests/mir-opt/dataflow-const-prop/large_array_index.main.DataflowConstProp.32bit.panic-unwind.diff new file mode 100644 index 00000000000..87024da2628 --- /dev/null +++ b/tests/mir-opt/dataflow-const-prop/large_array_index.main.DataflowConstProp.32bit.panic-unwind.diff @@ -0,0 +1,39 @@ +- // MIR for `main` before DataflowConstProp ++ // MIR for `main` after DataflowConstProp + + fn main() -> () { + let mut _0: (); + let _1: u8; + let mut _2: [u8; 5000]; + let _3: usize; + let mut _4: usize; + let mut _5: bool; + scope 1 { + debug x => _1; + } + + bb0: { + StorageLive(_1); + StorageLive(_2); + _2 = [const 0_u8; 5000]; + StorageLive(_3); + _3 = const 2_usize; +- _4 = Len(_2); +- _5 = Lt(_3, _4); +- assert(move _5, "index out of bounds: the length is {} but the index is {}", move _4, _3) -> [success: bb1, unwind continue]; ++ _4 = const 5000_usize; ++ _5 = const true; ++ assert(const true, "index out of bounds: the length is {} but the index is {}", const 5000_usize, const 2_usize) -> [success: bb1, unwind continue]; + } + + bb1: { +- _1 = _2[_3]; ++ _1 = _2[2 of 3]; + StorageDead(_3); + StorageDead(_2); + _0 = const (); + StorageDead(_1); + return; + } + } + diff --git a/tests/mir-opt/dataflow-const-prop/large_array_index.main.DataflowConstProp.64bit.panic-abort.diff b/tests/mir-opt/dataflow-const-prop/large_array_index.main.DataflowConstProp.64bit.panic-abort.diff new file mode 100644 index 00000000000..6c612d46725 --- /dev/null +++ b/tests/mir-opt/dataflow-const-prop/large_array_index.main.DataflowConstProp.64bit.panic-abort.diff @@ -0,0 +1,39 @@ +- // MIR for `main` before DataflowConstProp ++ // MIR for `main` after DataflowConstProp + + fn main() -> () { + let mut _0: (); + let _1: u8; + let mut _2: [u8; 5000]; + let _3: usize; + let mut _4: usize; + let mut _5: bool; + scope 1 { + debug x => _1; + } + + bb0: { + StorageLive(_1); + StorageLive(_2); + _2 = [const 0_u8; 5000]; + StorageLive(_3); + _3 = const 2_usize; +- _4 = Len(_2); +- _5 = Lt(_3, _4); +- assert(move _5, "index out of bounds: the length is {} but the index is {}", move _4, _3) -> [success: bb1, unwind unreachable]; ++ _4 = const 5000_usize; ++ _5 = const true; ++ assert(const true, "index out of bounds: the length is {} but the index is {}", const 5000_usize, const 2_usize) -> [success: bb1, unwind unreachable]; + } + + bb1: { +- _1 = _2[_3]; ++ _1 = _2[2 of 3]; + StorageDead(_3); + StorageDead(_2); + _0 = const (); + StorageDead(_1); + return; + } + } + diff --git a/tests/mir-opt/dataflow-const-prop/large_array_index.main.DataflowConstProp.64bit.panic-unwind.diff b/tests/mir-opt/dataflow-const-prop/large_array_index.main.DataflowConstProp.64bit.panic-unwind.diff new file mode 100644 index 00000000000..87024da2628 --- /dev/null +++ b/tests/mir-opt/dataflow-const-prop/large_array_index.main.DataflowConstProp.64bit.panic-unwind.diff @@ -0,0 +1,39 @@ +- // MIR for `main` before DataflowConstProp ++ // MIR for `main` after DataflowConstProp + + fn main() -> () { + let mut _0: (); + let _1: u8; + let mut _2: [u8; 5000]; + let _3: usize; + let mut _4: usize; + let mut _5: bool; + scope 1 { + debug x => _1; + } + + bb0: { + StorageLive(_1); + StorageLive(_2); + _2 = [const 0_u8; 5000]; + StorageLive(_3); + _3 = const 2_usize; +- _4 = Len(_2); +- _5 = Lt(_3, _4); +- assert(move _5, "index out of bounds: the length is {} but the index is {}", move _4, _3) -> [success: bb1, unwind continue]; ++ _4 = const 5000_usize; ++ _5 = const true; ++ assert(const true, "index out of bounds: the length is {} but the index is {}", const 5000_usize, const 2_usize) -> [success: bb1, unwind continue]; + } + + bb1: { +- _1 = _2[_3]; ++ _1 = _2[2 of 3]; + StorageDead(_3); + StorageDead(_2); + _0 = const (); + StorageDead(_1); + return; + } + } + diff --git a/tests/mir-opt/dataflow-const-prop/large_array_index.rs b/tests/mir-opt/dataflow-const-prop/large_array_index.rs new file mode 100644 index 00000000000..af13c7d1020 --- /dev/null +++ b/tests/mir-opt/dataflow-const-prop/large_array_index.rs @@ -0,0 +1,9 @@ +// unit-test: DataflowConstProp +// EMIT_MIR_FOR_EACH_PANIC_STRATEGY +// EMIT_MIR_FOR_EACH_BIT_WIDTH + +// EMIT_MIR large_array_index.main.DataflowConstProp.diff +fn main() { + // check that we don't propagate this, because it's too large + let x: u8 = [0_u8; 5000][2]; +} diff --git a/tests/mir-opt/dataflow-const-prop/mult_by_zero.rs b/tests/mir-opt/dataflow-const-prop/mult_by_zero.rs new file mode 100644 index 00000000000..dbea1480445 --- /dev/null +++ b/tests/mir-opt/dataflow-const-prop/mult_by_zero.rs @@ -0,0 +1,10 @@ +// unit-test: DataflowConstProp + +// EMIT_MIR mult_by_zero.test.DataflowConstProp.diff +fn test(x : i32) -> i32 { + x * 0 +} + +fn main() { + test(10); +} diff --git a/tests/mir-opt/dataflow-const-prop/mult_by_zero.test.DataflowConstProp.diff b/tests/mir-opt/dataflow-const-prop/mult_by_zero.test.DataflowConstProp.diff new file mode 100644 index 00000000000..91bc10a562f --- /dev/null +++ b/tests/mir-opt/dataflow-const-prop/mult_by_zero.test.DataflowConstProp.diff @@ -0,0 +1,18 @@ +- // MIR for `test` before DataflowConstProp ++ // MIR for `test` after DataflowConstProp + + fn test(_1: i32) -> i32 { + debug x => _1; + let mut _0: i32; + let mut _2: i32; + + bb0: { + StorageLive(_2); + _2 = _1; +- _0 = Mul(move _2, const 0_i32); ++ _0 = const 0_i32; + StorageDead(_2); + return; + } + } + diff --git a/tests/mir-opt/dataflow-const-prop/offset_of.concrete.DataflowConstProp.panic-abort.diff b/tests/mir-opt/dataflow-const-prop/offset_of.concrete.DataflowConstProp.panic-abort.diff new file mode 100644 index 00000000000..c61414b6541 --- /dev/null +++ b/tests/mir-opt/dataflow-const-prop/offset_of.concrete.DataflowConstProp.panic-abort.diff @@ -0,0 +1,76 @@ +- // MIR for `concrete` before DataflowConstProp ++ // MIR for `concrete` after DataflowConstProp + + fn concrete() -> () { + let mut _0: (); + let _1: usize; + let mut _2: usize; + let mut _4: usize; + let mut _6: usize; + let mut _8: usize; + scope 1 { + debug x => _1; + let _3: usize; + scope 2 { + debug y => _3; + let _5: usize; + scope 3 { + debug z0 => _5; + let _7: usize; + scope 4 { + debug z1 => _7; + } + } + } + } + + bb0: { + StorageLive(_1); + StorageLive(_2); +- _2 = OffsetOf(Alpha, [0]); +- _1 = must_use::<usize>(move _2) -> [return: bb1, unwind unreachable]; ++ _2 = const 4_usize; ++ _1 = must_use::<usize>(const 4_usize) -> [return: bb1, unwind unreachable]; + } + + bb1: { + StorageDead(_2); + StorageLive(_3); + StorageLive(_4); +- _4 = OffsetOf(Alpha, [1]); +- _3 = must_use::<usize>(move _4) -> [return: bb2, unwind unreachable]; ++ _4 = const 0_usize; ++ _3 = must_use::<usize>(const 0_usize) -> [return: bb2, unwind unreachable]; + } + + bb2: { + StorageDead(_4); + StorageLive(_5); + StorageLive(_6); +- _6 = OffsetOf(Alpha, [2, 0]); +- _5 = must_use::<usize>(move _6) -> [return: bb3, unwind unreachable]; ++ _6 = const 2_usize; ++ _5 = must_use::<usize>(const 2_usize) -> [return: bb3, unwind unreachable]; + } + + bb3: { + StorageDead(_6); + StorageLive(_7); + StorageLive(_8); +- _8 = OffsetOf(Alpha, [2, 1]); +- _7 = must_use::<usize>(move _8) -> [return: bb4, unwind unreachable]; ++ _8 = const 3_usize; ++ _7 = must_use::<usize>(const 3_usize) -> [return: bb4, unwind unreachable]; + } + + bb4: { + StorageDead(_8); + _0 = const (); + StorageDead(_7); + StorageDead(_5); + StorageDead(_3); + StorageDead(_1); + return; + } + } + diff --git a/tests/mir-opt/dataflow-const-prop/offset_of.concrete.DataflowConstProp.panic-unwind.diff b/tests/mir-opt/dataflow-const-prop/offset_of.concrete.DataflowConstProp.panic-unwind.diff new file mode 100644 index 00000000000..0c3939a3456 --- /dev/null +++ b/tests/mir-opt/dataflow-const-prop/offset_of.concrete.DataflowConstProp.panic-unwind.diff @@ -0,0 +1,76 @@ +- // MIR for `concrete` before DataflowConstProp ++ // MIR for `concrete` after DataflowConstProp + + fn concrete() -> () { + let mut _0: (); + let _1: usize; + let mut _2: usize; + let mut _4: usize; + let mut _6: usize; + let mut _8: usize; + scope 1 { + debug x => _1; + let _3: usize; + scope 2 { + debug y => _3; + let _5: usize; + scope 3 { + debug z0 => _5; + let _7: usize; + scope 4 { + debug z1 => _7; + } + } + } + } + + bb0: { + StorageLive(_1); + StorageLive(_2); +- _2 = OffsetOf(Alpha, [0]); +- _1 = must_use::<usize>(move _2) -> [return: bb1, unwind continue]; ++ _2 = const 4_usize; ++ _1 = must_use::<usize>(const 4_usize) -> [return: bb1, unwind continue]; + } + + bb1: { + StorageDead(_2); + StorageLive(_3); + StorageLive(_4); +- _4 = OffsetOf(Alpha, [1]); +- _3 = must_use::<usize>(move _4) -> [return: bb2, unwind continue]; ++ _4 = const 0_usize; ++ _3 = must_use::<usize>(const 0_usize) -> [return: bb2, unwind continue]; + } + + bb2: { + StorageDead(_4); + StorageLive(_5); + StorageLive(_6); +- _6 = OffsetOf(Alpha, [2, 0]); +- _5 = must_use::<usize>(move _6) -> [return: bb3, unwind continue]; ++ _6 = const 2_usize; ++ _5 = must_use::<usize>(const 2_usize) -> [return: bb3, unwind continue]; + } + + bb3: { + StorageDead(_6); + StorageLive(_7); + StorageLive(_8); +- _8 = OffsetOf(Alpha, [2, 1]); +- _7 = must_use::<usize>(move _8) -> [return: bb4, unwind continue]; ++ _8 = const 3_usize; ++ _7 = must_use::<usize>(const 3_usize) -> [return: bb4, unwind continue]; + } + + bb4: { + StorageDead(_8); + _0 = const (); + StorageDead(_7); + StorageDead(_5); + StorageDead(_3); + StorageDead(_1); + return; + } + } + diff --git a/tests/mir-opt/dataflow-const-prop/offset_of.generic.DataflowConstProp.panic-abort.diff b/tests/mir-opt/dataflow-const-prop/offset_of.generic.DataflowConstProp.panic-abort.diff new file mode 100644 index 00000000000..d54d4687060 --- /dev/null +++ b/tests/mir-opt/dataflow-const-prop/offset_of.generic.DataflowConstProp.panic-abort.diff @@ -0,0 +1,72 @@ +- // MIR for `generic` before DataflowConstProp ++ // MIR for `generic` after DataflowConstProp + + fn generic() -> () { + let mut _0: (); + let _1: usize; + let mut _2: usize; + let mut _4: usize; + let mut _6: usize; + let mut _8: usize; + scope 1 { + debug gx => _1; + let _3: usize; + scope 2 { + debug gy => _3; + let _5: usize; + scope 3 { + debug dx => _5; + let _7: usize; + scope 4 { + debug dy => _7; + } + } + } + } + + bb0: { + StorageLive(_1); + StorageLive(_2); + _2 = OffsetOf(Gamma<T>, [0]); + _1 = must_use::<usize>(move _2) -> [return: bb1, unwind unreachable]; + } + + bb1: { + StorageDead(_2); + StorageLive(_3); + StorageLive(_4); + _4 = OffsetOf(Gamma<T>, [1]); + _3 = must_use::<usize>(move _4) -> [return: bb2, unwind unreachable]; + } + + bb2: { + StorageDead(_4); + StorageLive(_5); + StorageLive(_6); +- _6 = OffsetOf(Delta<T>, [1]); +- _5 = must_use::<usize>(move _6) -> [return: bb3, unwind unreachable]; ++ _6 = const 0_usize; ++ _5 = must_use::<usize>(const 0_usize) -> [return: bb3, unwind unreachable]; + } + + bb3: { + StorageDead(_6); + StorageLive(_7); + StorageLive(_8); +- _8 = OffsetOf(Delta<T>, [2]); +- _7 = must_use::<usize>(move _8) -> [return: bb4, unwind unreachable]; ++ _8 = const 2_usize; ++ _7 = must_use::<usize>(const 2_usize) -> [return: bb4, unwind unreachable]; + } + + bb4: { + StorageDead(_8); + _0 = const (); + StorageDead(_7); + StorageDead(_5); + StorageDead(_3); + StorageDead(_1); + return; + } + } + diff --git a/tests/mir-opt/dataflow-const-prop/offset_of.generic.DataflowConstProp.panic-unwind.diff b/tests/mir-opt/dataflow-const-prop/offset_of.generic.DataflowConstProp.panic-unwind.diff new file mode 100644 index 00000000000..6032a2274ef --- /dev/null +++ b/tests/mir-opt/dataflow-const-prop/offset_of.generic.DataflowConstProp.panic-unwind.diff @@ -0,0 +1,72 @@ +- // MIR for `generic` before DataflowConstProp ++ // MIR for `generic` after DataflowConstProp + + fn generic() -> () { + let mut _0: (); + let _1: usize; + let mut _2: usize; + let mut _4: usize; + let mut _6: usize; + let mut _8: usize; + scope 1 { + debug gx => _1; + let _3: usize; + scope 2 { + debug gy => _3; + let _5: usize; + scope 3 { + debug dx => _5; + let _7: usize; + scope 4 { + debug dy => _7; + } + } + } + } + + bb0: { + StorageLive(_1); + StorageLive(_2); + _2 = OffsetOf(Gamma<T>, [0]); + _1 = must_use::<usize>(move _2) -> [return: bb1, unwind continue]; + } + + bb1: { + StorageDead(_2); + StorageLive(_3); + StorageLive(_4); + _4 = OffsetOf(Gamma<T>, [1]); + _3 = must_use::<usize>(move _4) -> [return: bb2, unwind continue]; + } + + bb2: { + StorageDead(_4); + StorageLive(_5); + StorageLive(_6); +- _6 = OffsetOf(Delta<T>, [1]); +- _5 = must_use::<usize>(move _6) -> [return: bb3, unwind continue]; ++ _6 = const 0_usize; ++ _5 = must_use::<usize>(const 0_usize) -> [return: bb3, unwind continue]; + } + + bb3: { + StorageDead(_6); + StorageLive(_7); + StorageLive(_8); +- _8 = OffsetOf(Delta<T>, [2]); +- _7 = must_use::<usize>(move _8) -> [return: bb4, unwind continue]; ++ _8 = const 2_usize; ++ _7 = must_use::<usize>(const 2_usize) -> [return: bb4, unwind continue]; + } + + bb4: { + StorageDead(_8); + _0 = const (); + StorageDead(_7); + StorageDead(_5); + StorageDead(_3); + StorageDead(_1); + return; + } + } + diff --git a/tests/mir-opt/dataflow-const-prop/offset_of.rs b/tests/mir-opt/dataflow-const-prop/offset_of.rs new file mode 100644 index 00000000000..ccc90790e52 --- /dev/null +++ b/tests/mir-opt/dataflow-const-prop/offset_of.rs @@ -0,0 +1,49 @@ +// unit-test: DataflowConstProp +// EMIT_MIR_FOR_EACH_PANIC_STRATEGY + +#![feature(offset_of)] + +use std::marker::PhantomData; +use std::mem::offset_of; + +struct Alpha { + x: u8, + y: u16, + z: Beta, +} + +struct Beta(u8, u8); + +struct Gamma<T> { + x: u8, + y: u16, + _t: T, +} + +#[repr(C)] +struct Delta<T> { + _phantom: PhantomData<T>, + x: u8, + y: u16, +} + +// EMIT_MIR offset_of.concrete.DataflowConstProp.diff +fn concrete() { + let x = offset_of!(Alpha, x); + let y = offset_of!(Alpha, y); + let z0 = offset_of!(Alpha, z.0); + let z1 = offset_of!(Alpha, z.1); +} + +// EMIT_MIR offset_of.generic.DataflowConstProp.diff +fn generic<T>() { + let gx = offset_of!(Gamma<T>, x); + let gy = offset_of!(Gamma<T>, y); + let dx = offset_of!(Delta<T>, x); + let dy = offset_of!(Delta<T>, y); +} + +fn main() { + concrete(); + generic::<()>(); +} diff --git a/tests/mir-opt/dataflow-const-prop/repeat.main.DataflowConstProp.32bit.panic-abort.diff b/tests/mir-opt/dataflow-const-prop/repeat.main.DataflowConstProp.32bit.panic-abort.diff new file mode 100644 index 00000000000..a18ef6c9db7 --- /dev/null +++ b/tests/mir-opt/dataflow-const-prop/repeat.main.DataflowConstProp.32bit.panic-abort.diff @@ -0,0 +1,43 @@ +- // MIR for `main` before DataflowConstProp ++ // MIR for `main` after DataflowConstProp + + fn main() -> () { + let mut _0: (); + let _1: u32; + let mut _2: u32; + let mut _3: [u32; 8]; + let _4: usize; + let mut _5: usize; + let mut _6: bool; + scope 1 { + debug x => _1; + } + + bb0: { + StorageLive(_1); + StorageLive(_2); + StorageLive(_3); + _3 = [const 42_u32; 8]; + StorageLive(_4); + _4 = const 2_usize; +- _5 = Len(_3); +- _6 = Lt(_4, _5); +- assert(move _6, "index out of bounds: the length is {} but the index is {}", move _5, _4) -> [success: bb1, unwind unreachable]; ++ _5 = const 8_usize; ++ _6 = const true; ++ assert(const true, "index out of bounds: the length is {} but the index is {}", const 8_usize, const 2_usize) -> [success: bb1, unwind unreachable]; + } + + bb1: { +- _2 = _3[_4]; ++ _2 = _3[2 of 3]; + _1 = Add(move _2, const 0_u32); + StorageDead(_2); + StorageDead(_4); + StorageDead(_3); + _0 = const (); + StorageDead(_1); + return; + } + } + diff --git a/tests/mir-opt/dataflow-const-prop/repeat.main.DataflowConstProp.32bit.panic-unwind.diff b/tests/mir-opt/dataflow-const-prop/repeat.main.DataflowConstProp.32bit.panic-unwind.diff new file mode 100644 index 00000000000..3356ef98b14 --- /dev/null +++ b/tests/mir-opt/dataflow-const-prop/repeat.main.DataflowConstProp.32bit.panic-unwind.diff @@ -0,0 +1,43 @@ +- // MIR for `main` before DataflowConstProp ++ // MIR for `main` after DataflowConstProp + + fn main() -> () { + let mut _0: (); + let _1: u32; + let mut _2: u32; + let mut _3: [u32; 8]; + let _4: usize; + let mut _5: usize; + let mut _6: bool; + scope 1 { + debug x => _1; + } + + bb0: { + StorageLive(_1); + StorageLive(_2); + StorageLive(_3); + _3 = [const 42_u32; 8]; + StorageLive(_4); + _4 = const 2_usize; +- _5 = Len(_3); +- _6 = Lt(_4, _5); +- assert(move _6, "index out of bounds: the length is {} but the index is {}", move _5, _4) -> [success: bb1, unwind continue]; ++ _5 = const 8_usize; ++ _6 = const true; ++ assert(const true, "index out of bounds: the length is {} but the index is {}", const 8_usize, const 2_usize) -> [success: bb1, unwind continue]; + } + + bb1: { +- _2 = _3[_4]; ++ _2 = _3[2 of 3]; + _1 = Add(move _2, const 0_u32); + StorageDead(_2); + StorageDead(_4); + StorageDead(_3); + _0 = const (); + StorageDead(_1); + return; + } + } + diff --git a/tests/mir-opt/dataflow-const-prop/repeat.main.DataflowConstProp.64bit.panic-abort.diff b/tests/mir-opt/dataflow-const-prop/repeat.main.DataflowConstProp.64bit.panic-abort.diff new file mode 100644 index 00000000000..a18ef6c9db7 --- /dev/null +++ b/tests/mir-opt/dataflow-const-prop/repeat.main.DataflowConstProp.64bit.panic-abort.diff @@ -0,0 +1,43 @@ +- // MIR for `main` before DataflowConstProp ++ // MIR for `main` after DataflowConstProp + + fn main() -> () { + let mut _0: (); + let _1: u32; + let mut _2: u32; + let mut _3: [u32; 8]; + let _4: usize; + let mut _5: usize; + let mut _6: bool; + scope 1 { + debug x => _1; + } + + bb0: { + StorageLive(_1); + StorageLive(_2); + StorageLive(_3); + _3 = [const 42_u32; 8]; + StorageLive(_4); + _4 = const 2_usize; +- _5 = Len(_3); +- _6 = Lt(_4, _5); +- assert(move _6, "index out of bounds: the length is {} but the index is {}", move _5, _4) -> [success: bb1, unwind unreachable]; ++ _5 = const 8_usize; ++ _6 = const true; ++ assert(const true, "index out of bounds: the length is {} but the index is {}", const 8_usize, const 2_usize) -> [success: bb1, unwind unreachable]; + } + + bb1: { +- _2 = _3[_4]; ++ _2 = _3[2 of 3]; + _1 = Add(move _2, const 0_u32); + StorageDead(_2); + StorageDead(_4); + StorageDead(_3); + _0 = const (); + StorageDead(_1); + return; + } + } + diff --git a/tests/mir-opt/dataflow-const-prop/repeat.main.DataflowConstProp.64bit.panic-unwind.diff b/tests/mir-opt/dataflow-const-prop/repeat.main.DataflowConstProp.64bit.panic-unwind.diff new file mode 100644 index 00000000000..3356ef98b14 --- /dev/null +++ b/tests/mir-opt/dataflow-const-prop/repeat.main.DataflowConstProp.64bit.panic-unwind.diff @@ -0,0 +1,43 @@ +- // MIR for `main` before DataflowConstProp ++ // MIR for `main` after DataflowConstProp + + fn main() -> () { + let mut _0: (); + let _1: u32; + let mut _2: u32; + let mut _3: [u32; 8]; + let _4: usize; + let mut _5: usize; + let mut _6: bool; + scope 1 { + debug x => _1; + } + + bb0: { + StorageLive(_1); + StorageLive(_2); + StorageLive(_3); + _3 = [const 42_u32; 8]; + StorageLive(_4); + _4 = const 2_usize; +- _5 = Len(_3); +- _6 = Lt(_4, _5); +- assert(move _6, "index out of bounds: the length is {} but the index is {}", move _5, _4) -> [success: bb1, unwind continue]; ++ _5 = const 8_usize; ++ _6 = const true; ++ assert(const true, "index out of bounds: the length is {} but the index is {}", const 8_usize, const 2_usize) -> [success: bb1, unwind continue]; + } + + bb1: { +- _2 = _3[_4]; ++ _2 = _3[2 of 3]; + _1 = Add(move _2, const 0_u32); + StorageDead(_2); + StorageDead(_4); + StorageDead(_3); + _0 = const (); + StorageDead(_1); + return; + } + } + diff --git a/tests/mir-opt/dataflow-const-prop/repeat.rs b/tests/mir-opt/dataflow-const-prop/repeat.rs new file mode 100644 index 00000000000..9fa353e44c5 --- /dev/null +++ b/tests/mir-opt/dataflow-const-prop/repeat.rs @@ -0,0 +1,8 @@ +// unit-test: DataflowConstProp +// EMIT_MIR_FOR_EACH_PANIC_STRATEGY +// EMIT_MIR_FOR_EACH_BIT_WIDTH + +// EMIT_MIR repeat.main.DataflowConstProp.diff +fn main() { + let x: u32 = [42; 8][2] + 0; +} diff --git a/tests/mir-opt/dataflow-const-prop/slice_len.main.DataflowConstProp.32bit.panic-abort.diff b/tests/mir-opt/dataflow-const-prop/slice_len.main.DataflowConstProp.32bit.panic-abort.diff new file mode 100644 index 00000000000..be55d259dcf --- /dev/null +++ b/tests/mir-opt/dataflow-const-prop/slice_len.main.DataflowConstProp.32bit.panic-abort.diff @@ -0,0 +1,76 @@ +- // MIR for `main` before DataflowConstProp ++ // MIR for `main` after DataflowConstProp + + fn main() -> () { + let mut _0: (); + let _1: u32; + let mut _2: &[u32]; + let mut _3: &[u32; 3]; + let _4: &[u32; 3]; + let _5: [u32; 3]; + let _6: usize; + let mut _7: usize; + let mut _8: bool; + let mut _10: &[u32]; + let _11: usize; + let mut _12: usize; + let mut _13: bool; + let mut _14: &[u32; 3]; + scope 1 { + debug local => _1; + let _9: u32; + scope 2 { + debug constant => _9; + } + } + + bb0: { + StorageLive(_1); + StorageLive(_2); + StorageLive(_3); + StorageLive(_4); + _14 = const _; + _4 = _14; + _3 = _4; + _2 = move _3 as &[u32] (PointerCoercion(Unsize)); + StorageDead(_3); + StorageLive(_6); + _6 = const 1_usize; +- _7 = Len((*_2)); +- _8 = Lt(_6, _7); +- assert(move _8, "index out of bounds: the length is {} but the index is {}", move _7, _6) -> [success: bb1, unwind unreachable]; ++ _7 = const 3_usize; ++ _8 = const true; ++ assert(const true, "index out of bounds: the length is {} but the index is {}", const 3_usize, const 1_usize) -> [success: bb1, unwind unreachable]; + } + + bb1: { +- _1 = (*_2)[_6]; ++ _1 = (*_2)[1 of 2]; + StorageDead(_6); + StorageDead(_4); + StorageDead(_2); + StorageLive(_9); + StorageLive(_10); + _10 = const _; + StorageLive(_11); + _11 = const 1_usize; + _12 = Len((*_10)); +- _13 = Lt(_11, _12); +- assert(move _13, "index out of bounds: the length is {} but the index is {}", move _12, _11) -> [success: bb2, unwind unreachable]; ++ _13 = Lt(const 1_usize, _12); ++ assert(move _13, "index out of bounds: the length is {} but the index is {}", move _12, const 1_usize) -> [success: bb2, unwind unreachable]; + } + + bb2: { +- _9 = (*_10)[_11]; ++ _9 = (*_10)[1 of 2]; + StorageDead(_11); + StorageDead(_10); + _0 = const (); + StorageDead(_9); + StorageDead(_1); + return; + } + } + diff --git a/tests/mir-opt/dataflow-const-prop/slice_len.main.DataflowConstProp.32bit.panic-unwind.diff b/tests/mir-opt/dataflow-const-prop/slice_len.main.DataflowConstProp.32bit.panic-unwind.diff new file mode 100644 index 00000000000..f9a6c509ac8 --- /dev/null +++ b/tests/mir-opt/dataflow-const-prop/slice_len.main.DataflowConstProp.32bit.panic-unwind.diff @@ -0,0 +1,76 @@ +- // MIR for `main` before DataflowConstProp ++ // MIR for `main` after DataflowConstProp + + fn main() -> () { + let mut _0: (); + let _1: u32; + let mut _2: &[u32]; + let mut _3: &[u32; 3]; + let _4: &[u32; 3]; + let _5: [u32; 3]; + let _6: usize; + let mut _7: usize; + let mut _8: bool; + let mut _10: &[u32]; + let _11: usize; + let mut _12: usize; + let mut _13: bool; + let mut _14: &[u32; 3]; + scope 1 { + debug local => _1; + let _9: u32; + scope 2 { + debug constant => _9; + } + } + + bb0: { + StorageLive(_1); + StorageLive(_2); + StorageLive(_3); + StorageLive(_4); + _14 = const _; + _4 = _14; + _3 = _4; + _2 = move _3 as &[u32] (PointerCoercion(Unsize)); + StorageDead(_3); + StorageLive(_6); + _6 = const 1_usize; +- _7 = Len((*_2)); +- _8 = Lt(_6, _7); +- assert(move _8, "index out of bounds: the length is {} but the index is {}", move _7, _6) -> [success: bb1, unwind continue]; ++ _7 = const 3_usize; ++ _8 = const true; ++ assert(const true, "index out of bounds: the length is {} but the index is {}", const 3_usize, const 1_usize) -> [success: bb1, unwind continue]; + } + + bb1: { +- _1 = (*_2)[_6]; ++ _1 = (*_2)[1 of 2]; + StorageDead(_6); + StorageDead(_4); + StorageDead(_2); + StorageLive(_9); + StorageLive(_10); + _10 = const _; + StorageLive(_11); + _11 = const 1_usize; + _12 = Len((*_10)); +- _13 = Lt(_11, _12); +- assert(move _13, "index out of bounds: the length is {} but the index is {}", move _12, _11) -> [success: bb2, unwind continue]; ++ _13 = Lt(const 1_usize, _12); ++ assert(move _13, "index out of bounds: the length is {} but the index is {}", move _12, const 1_usize) -> [success: bb2, unwind continue]; + } + + bb2: { +- _9 = (*_10)[_11]; ++ _9 = (*_10)[1 of 2]; + StorageDead(_11); + StorageDead(_10); + _0 = const (); + StorageDead(_9); + StorageDead(_1); + return; + } + } + diff --git a/tests/mir-opt/dataflow-const-prop/slice_len.main.DataflowConstProp.64bit.panic-abort.diff b/tests/mir-opt/dataflow-const-prop/slice_len.main.DataflowConstProp.64bit.panic-abort.diff new file mode 100644 index 00000000000..be55d259dcf --- /dev/null +++ b/tests/mir-opt/dataflow-const-prop/slice_len.main.DataflowConstProp.64bit.panic-abort.diff @@ -0,0 +1,76 @@ +- // MIR for `main` before DataflowConstProp ++ // MIR for `main` after DataflowConstProp + + fn main() -> () { + let mut _0: (); + let _1: u32; + let mut _2: &[u32]; + let mut _3: &[u32; 3]; + let _4: &[u32; 3]; + let _5: [u32; 3]; + let _6: usize; + let mut _7: usize; + let mut _8: bool; + let mut _10: &[u32]; + let _11: usize; + let mut _12: usize; + let mut _13: bool; + let mut _14: &[u32; 3]; + scope 1 { + debug local => _1; + let _9: u32; + scope 2 { + debug constant => _9; + } + } + + bb0: { + StorageLive(_1); + StorageLive(_2); + StorageLive(_3); + StorageLive(_4); + _14 = const _; + _4 = _14; + _3 = _4; + _2 = move _3 as &[u32] (PointerCoercion(Unsize)); + StorageDead(_3); + StorageLive(_6); + _6 = const 1_usize; +- _7 = Len((*_2)); +- _8 = Lt(_6, _7); +- assert(move _8, "index out of bounds: the length is {} but the index is {}", move _7, _6) -> [success: bb1, unwind unreachable]; ++ _7 = const 3_usize; ++ _8 = const true; ++ assert(const true, "index out of bounds: the length is {} but the index is {}", const 3_usize, const 1_usize) -> [success: bb1, unwind unreachable]; + } + + bb1: { +- _1 = (*_2)[_6]; ++ _1 = (*_2)[1 of 2]; + StorageDead(_6); + StorageDead(_4); + StorageDead(_2); + StorageLive(_9); + StorageLive(_10); + _10 = const _; + StorageLive(_11); + _11 = const 1_usize; + _12 = Len((*_10)); +- _13 = Lt(_11, _12); +- assert(move _13, "index out of bounds: the length is {} but the index is {}", move _12, _11) -> [success: bb2, unwind unreachable]; ++ _13 = Lt(const 1_usize, _12); ++ assert(move _13, "index out of bounds: the length is {} but the index is {}", move _12, const 1_usize) -> [success: bb2, unwind unreachable]; + } + + bb2: { +- _9 = (*_10)[_11]; ++ _9 = (*_10)[1 of 2]; + StorageDead(_11); + StorageDead(_10); + _0 = const (); + StorageDead(_9); + StorageDead(_1); + return; + } + } + diff --git a/tests/mir-opt/dataflow-const-prop/slice_len.main.DataflowConstProp.64bit.panic-unwind.diff b/tests/mir-opt/dataflow-const-prop/slice_len.main.DataflowConstProp.64bit.panic-unwind.diff new file mode 100644 index 00000000000..f9a6c509ac8 --- /dev/null +++ b/tests/mir-opt/dataflow-const-prop/slice_len.main.DataflowConstProp.64bit.panic-unwind.diff @@ -0,0 +1,76 @@ +- // MIR for `main` before DataflowConstProp ++ // MIR for `main` after DataflowConstProp + + fn main() -> () { + let mut _0: (); + let _1: u32; + let mut _2: &[u32]; + let mut _3: &[u32; 3]; + let _4: &[u32; 3]; + let _5: [u32; 3]; + let _6: usize; + let mut _7: usize; + let mut _8: bool; + let mut _10: &[u32]; + let _11: usize; + let mut _12: usize; + let mut _13: bool; + let mut _14: &[u32; 3]; + scope 1 { + debug local => _1; + let _9: u32; + scope 2 { + debug constant => _9; + } + } + + bb0: { + StorageLive(_1); + StorageLive(_2); + StorageLive(_3); + StorageLive(_4); + _14 = const _; + _4 = _14; + _3 = _4; + _2 = move _3 as &[u32] (PointerCoercion(Unsize)); + StorageDead(_3); + StorageLive(_6); + _6 = const 1_usize; +- _7 = Len((*_2)); +- _8 = Lt(_6, _7); +- assert(move _8, "index out of bounds: the length is {} but the index is {}", move _7, _6) -> [success: bb1, unwind continue]; ++ _7 = const 3_usize; ++ _8 = const true; ++ assert(const true, "index out of bounds: the length is {} but the index is {}", const 3_usize, const 1_usize) -> [success: bb1, unwind continue]; + } + + bb1: { +- _1 = (*_2)[_6]; ++ _1 = (*_2)[1 of 2]; + StorageDead(_6); + StorageDead(_4); + StorageDead(_2); + StorageLive(_9); + StorageLive(_10); + _10 = const _; + StorageLive(_11); + _11 = const 1_usize; + _12 = Len((*_10)); +- _13 = Lt(_11, _12); +- assert(move _13, "index out of bounds: the length is {} but the index is {}", move _12, _11) -> [success: bb2, unwind continue]; ++ _13 = Lt(const 1_usize, _12); ++ assert(move _13, "index out of bounds: the length is {} but the index is {}", move _12, const 1_usize) -> [success: bb2, unwind continue]; + } + + bb2: { +- _9 = (*_10)[_11]; ++ _9 = (*_10)[1 of 2]; + StorageDead(_11); + StorageDead(_10); + _0 = const (); + StorageDead(_9); + StorageDead(_1); + return; + } + } + diff --git a/tests/mir-opt/dataflow-const-prop/slice_len.rs b/tests/mir-opt/dataflow-const-prop/slice_len.rs new file mode 100644 index 00000000000..41367e48497 --- /dev/null +++ b/tests/mir-opt/dataflow-const-prop/slice_len.rs @@ -0,0 +1,12 @@ +// EMIT_MIR_FOR_EACH_PANIC_STRATEGY +// unit-test: DataflowConstProp +// compile-flags: -Zmir-enable-passes=+InstSimplify +// EMIT_MIR_FOR_EACH_BIT_WIDTH + +// EMIT_MIR slice_len.main.DataflowConstProp.diff +fn main() { + let local = (&[1u32, 2, 3] as &[u32])[1]; + + const SLICE: &[u32] = &[1, 2, 3]; + let constant = SLICE[1]; +} diff --git a/tests/mir-opt/dataflow-const-prop/transmute.from_char.DataflowConstProp.32bit.diff b/tests/mir-opt/dataflow-const-prop/transmute.from_char.DataflowConstProp.32bit.diff new file mode 100644 index 00000000000..52f096ac0e4 --- /dev/null +++ b/tests/mir-opt/dataflow-const-prop/transmute.from_char.DataflowConstProp.32bit.diff @@ -0,0 +1,15 @@ +- // MIR for `from_char` before DataflowConstProp ++ // MIR for `from_char` after DataflowConstProp + + fn from_char() -> i32 { + let mut _0: i32; + scope 1 { + } + + bb0: { +- _0 = const 'R' as i32 (Transmute); ++ _0 = const 82_i32; + return; + } + } + diff --git a/tests/mir-opt/dataflow-const-prop/transmute.from_char.DataflowConstProp.64bit.diff b/tests/mir-opt/dataflow-const-prop/transmute.from_char.DataflowConstProp.64bit.diff new file mode 100644 index 00000000000..52f096ac0e4 --- /dev/null +++ b/tests/mir-opt/dataflow-const-prop/transmute.from_char.DataflowConstProp.64bit.diff @@ -0,0 +1,15 @@ +- // MIR for `from_char` before DataflowConstProp ++ // MIR for `from_char` after DataflowConstProp + + fn from_char() -> i32 { + let mut _0: i32; + scope 1 { + } + + bb0: { +- _0 = const 'R' as i32 (Transmute); ++ _0 = const 82_i32; + return; + } + } + diff --git a/tests/mir-opt/dataflow-const-prop/transmute.invalid_bool.DataflowConstProp.32bit.diff b/tests/mir-opt/dataflow-const-prop/transmute.invalid_bool.DataflowConstProp.32bit.diff new file mode 100644 index 00000000000..3972eb209a1 --- /dev/null +++ b/tests/mir-opt/dataflow-const-prop/transmute.invalid_bool.DataflowConstProp.32bit.diff @@ -0,0 +1,15 @@ +- // MIR for `invalid_bool` before DataflowConstProp ++ // MIR for `invalid_bool` after DataflowConstProp + + fn invalid_bool() -> bool { + let mut _0: bool; + scope 1 { + } + + bb0: { +- _0 = const -1_i8 as bool (Transmute); ++ _0 = const {transmute(0xff): bool}; + return; + } + } + diff --git a/tests/mir-opt/dataflow-const-prop/transmute.invalid_bool.DataflowConstProp.64bit.diff b/tests/mir-opt/dataflow-const-prop/transmute.invalid_bool.DataflowConstProp.64bit.diff new file mode 100644 index 00000000000..3972eb209a1 --- /dev/null +++ b/tests/mir-opt/dataflow-const-prop/transmute.invalid_bool.DataflowConstProp.64bit.diff @@ -0,0 +1,15 @@ +- // MIR for `invalid_bool` before DataflowConstProp ++ // MIR for `invalid_bool` after DataflowConstProp + + fn invalid_bool() -> bool { + let mut _0: bool; + scope 1 { + } + + bb0: { +- _0 = const -1_i8 as bool (Transmute); ++ _0 = const {transmute(0xff): bool}; + return; + } + } + diff --git a/tests/mir-opt/dataflow-const-prop/transmute.invalid_char.DataflowConstProp.32bit.diff b/tests/mir-opt/dataflow-const-prop/transmute.invalid_char.DataflowConstProp.32bit.diff new file mode 100644 index 00000000000..837dabde42a --- /dev/null +++ b/tests/mir-opt/dataflow-const-prop/transmute.invalid_char.DataflowConstProp.32bit.diff @@ -0,0 +1,15 @@ +- // MIR for `invalid_char` before DataflowConstProp ++ // MIR for `invalid_char` after DataflowConstProp + + fn invalid_char() -> char { + let mut _0: char; + scope 1 { + } + + bb0: { +- _0 = const _ as char (Transmute); ++ _0 = const {transmute(0x7fffffff): char}; + return; + } + } + diff --git a/tests/mir-opt/dataflow-const-prop/transmute.invalid_char.DataflowConstProp.64bit.diff b/tests/mir-opt/dataflow-const-prop/transmute.invalid_char.DataflowConstProp.64bit.diff new file mode 100644 index 00000000000..837dabde42a --- /dev/null +++ b/tests/mir-opt/dataflow-const-prop/transmute.invalid_char.DataflowConstProp.64bit.diff @@ -0,0 +1,15 @@ +- // MIR for `invalid_char` before DataflowConstProp ++ // MIR for `invalid_char` after DataflowConstProp + + fn invalid_char() -> char { + let mut _0: char; + scope 1 { + } + + bb0: { +- _0 = const _ as char (Transmute); ++ _0 = const {transmute(0x7fffffff): char}; + return; + } + } + diff --git a/tests/mir-opt/dataflow-const-prop/transmute.less_as_i8.DataflowConstProp.32bit.diff b/tests/mir-opt/dataflow-const-prop/transmute.less_as_i8.DataflowConstProp.32bit.diff new file mode 100644 index 00000000000..6091e169e8e --- /dev/null +++ b/tests/mir-opt/dataflow-const-prop/transmute.less_as_i8.DataflowConstProp.32bit.diff @@ -0,0 +1,18 @@ +- // MIR for `less_as_i8` before DataflowConstProp ++ // MIR for `less_as_i8` after DataflowConstProp + + fn less_as_i8() -> i8 { + let mut _0: i8; + let mut _1: std::cmp::Ordering; + scope 1 { + } + + bb0: { + StorageLive(_1); + _1 = Less; + _0 = move _1 as i8 (Transmute); + StorageDead(_1); + return; + } + } + diff --git a/tests/mir-opt/dataflow-const-prop/transmute.less_as_i8.DataflowConstProp.64bit.diff b/tests/mir-opt/dataflow-const-prop/transmute.less_as_i8.DataflowConstProp.64bit.diff new file mode 100644 index 00000000000..6091e169e8e --- /dev/null +++ b/tests/mir-opt/dataflow-const-prop/transmute.less_as_i8.DataflowConstProp.64bit.diff @@ -0,0 +1,18 @@ +- // MIR for `less_as_i8` before DataflowConstProp ++ // MIR for `less_as_i8` after DataflowConstProp + + fn less_as_i8() -> i8 { + let mut _0: i8; + let mut _1: std::cmp::Ordering; + scope 1 { + } + + bb0: { + StorageLive(_1); + _1 = Less; + _0 = move _1 as i8 (Transmute); + StorageDead(_1); + return; + } + } + diff --git a/tests/mir-opt/dataflow-const-prop/transmute.rs b/tests/mir-opt/dataflow-const-prop/transmute.rs new file mode 100644 index 00000000000..c25e33ab0b6 --- /dev/null +++ b/tests/mir-opt/dataflow-const-prop/transmute.rs @@ -0,0 +1,63 @@ +// unit-test: DataflowConstProp +// compile-flags: -O --crate-type=lib +// ignore-endian-big +// EMIT_MIR_FOR_EACH_BIT_WIDTH + +use std::mem::transmute; + +// EMIT_MIR transmute.less_as_i8.DataflowConstProp.diff +pub fn less_as_i8() -> i8 { + unsafe { transmute(std::cmp::Ordering::Less) } +} + +// EMIT_MIR transmute.from_char.DataflowConstProp.diff +pub fn from_char() -> i32 { + unsafe { transmute('R') } +} + +// EMIT_MIR transmute.valid_char.DataflowConstProp.diff +pub fn valid_char() -> char { + unsafe { transmute(0x52_u32) } +} + +// EMIT_MIR transmute.invalid_char.DataflowConstProp.diff +pub unsafe fn invalid_char() -> char { + unsafe { transmute(i32::MAX) } +} + +// EMIT_MIR transmute.invalid_bool.DataflowConstProp.diff +pub unsafe fn invalid_bool() -> bool { + unsafe { transmute(-1_i8) } +} + +// EMIT_MIR transmute.undef_union_as_integer.DataflowConstProp.diff +pub unsafe fn undef_union_as_integer() -> u32 { + union Union32 { value: u32, unit: () } + unsafe { transmute(Union32 { unit: () }) } +} + +// EMIT_MIR transmute.unreachable_direct.DataflowConstProp.diff +pub unsafe fn unreachable_direct() -> ! { + let x: Never = unsafe { transmute(()) }; + match x {} +} + +// EMIT_MIR transmute.unreachable_ref.DataflowConstProp.diff +pub unsafe fn unreachable_ref() -> ! { + let x: &Never = unsafe { transmute(1_usize) }; + match *x {} +} + +// EMIT_MIR transmute.unreachable_mut.DataflowConstProp.diff +pub unsafe fn unreachable_mut() -> ! { + let x: &mut Never = unsafe { transmute(1_usize) }; + match *x {} +} + +// EMIT_MIR transmute.unreachable_box.DataflowConstProp.diff +pub unsafe fn unreachable_box() -> ! { + let x: Box<Never> = unsafe { transmute(1_usize) }; + match *x {} +} + +enum Never {} diff --git a/tests/mir-opt/dataflow-const-prop/transmute.undef_union_as_integer.DataflowConstProp.32bit.diff b/tests/mir-opt/dataflow-const-prop/transmute.undef_union_as_integer.DataflowConstProp.32bit.diff new file mode 100644 index 00000000000..fc0634b1f8f --- /dev/null +++ b/tests/mir-opt/dataflow-const-prop/transmute.undef_union_as_integer.DataflowConstProp.32bit.diff @@ -0,0 +1,22 @@ +- // MIR for `undef_union_as_integer` before DataflowConstProp ++ // MIR for `undef_union_as_integer` after DataflowConstProp + + fn undef_union_as_integer() -> u32 { + let mut _0: u32; + let mut _1: undef_union_as_integer::Union32; + let mut _2: (); + scope 1 { + } + + bb0: { + StorageLive(_1); + StorageLive(_2); + _2 = (); + _1 = Union32 { value: move _2 }; + StorageDead(_2); + _0 = move _1 as u32 (Transmute); + StorageDead(_1); + return; + } + } + diff --git a/tests/mir-opt/dataflow-const-prop/transmute.undef_union_as_integer.DataflowConstProp.64bit.diff b/tests/mir-opt/dataflow-const-prop/transmute.undef_union_as_integer.DataflowConstProp.64bit.diff new file mode 100644 index 00000000000..fc0634b1f8f --- /dev/null +++ b/tests/mir-opt/dataflow-const-prop/transmute.undef_union_as_integer.DataflowConstProp.64bit.diff @@ -0,0 +1,22 @@ +- // MIR for `undef_union_as_integer` before DataflowConstProp ++ // MIR for `undef_union_as_integer` after DataflowConstProp + + fn undef_union_as_integer() -> u32 { + let mut _0: u32; + let mut _1: undef_union_as_integer::Union32; + let mut _2: (); + scope 1 { + } + + bb0: { + StorageLive(_1); + StorageLive(_2); + _2 = (); + _1 = Union32 { value: move _2 }; + StorageDead(_2); + _0 = move _1 as u32 (Transmute); + StorageDead(_1); + return; + } + } + diff --git a/tests/mir-opt/dataflow-const-prop/transmute.unreachable_box.DataflowConstProp.32bit.diff b/tests/mir-opt/dataflow-const-prop/transmute.unreachable_box.DataflowConstProp.32bit.diff new file mode 100644 index 00000000000..d0c298ba233 --- /dev/null +++ b/tests/mir-opt/dataflow-const-prop/transmute.unreachable_box.DataflowConstProp.32bit.diff @@ -0,0 +1,20 @@ +- // MIR for `unreachable_box` before DataflowConstProp ++ // MIR for `unreachable_box` after DataflowConstProp + + fn unreachable_box() -> ! { + let mut _0: !; + let _1: std::boxed::Box<Never>; + scope 1 { + debug x => _1; + } + scope 2 { + } + + bb0: { + StorageLive(_1); +- _1 = const 1_usize as std::boxed::Box<Never> (Transmute); ++ _1 = const Box::<Never>(Unique::<Never> {{ pointer: NonNull::<Never> {{ pointer: {0x1 as *const Never} }}, _marker: PhantomData::<Never> }}, std::alloc::Global); + unreachable; + } + } + diff --git a/tests/mir-opt/dataflow-const-prop/transmute.unreachable_box.DataflowConstProp.64bit.diff b/tests/mir-opt/dataflow-const-prop/transmute.unreachable_box.DataflowConstProp.64bit.diff new file mode 100644 index 00000000000..d0c298ba233 --- /dev/null +++ b/tests/mir-opt/dataflow-const-prop/transmute.unreachable_box.DataflowConstProp.64bit.diff @@ -0,0 +1,20 @@ +- // MIR for `unreachable_box` before DataflowConstProp ++ // MIR for `unreachable_box` after DataflowConstProp + + fn unreachable_box() -> ! { + let mut _0: !; + let _1: std::boxed::Box<Never>; + scope 1 { + debug x => _1; + } + scope 2 { + } + + bb0: { + StorageLive(_1); +- _1 = const 1_usize as std::boxed::Box<Never> (Transmute); ++ _1 = const Box::<Never>(Unique::<Never> {{ pointer: NonNull::<Never> {{ pointer: {0x1 as *const Never} }}, _marker: PhantomData::<Never> }}, std::alloc::Global); + unreachable; + } + } + diff --git a/tests/mir-opt/dataflow-const-prop/transmute.unreachable_direct.DataflowConstProp.32bit.diff b/tests/mir-opt/dataflow-const-prop/transmute.unreachable_direct.DataflowConstProp.32bit.diff new file mode 100644 index 00000000000..acbb5cd1bc7 --- /dev/null +++ b/tests/mir-opt/dataflow-const-prop/transmute.unreachable_direct.DataflowConstProp.32bit.diff @@ -0,0 +1,22 @@ +- // MIR for `unreachable_direct` before DataflowConstProp ++ // MIR for `unreachable_direct` after DataflowConstProp + + fn unreachable_direct() -> ! { + let mut _0: !; + let _1: Never; + let mut _2: (); + scope 1 { + debug x => _1; + } + scope 2 { + } + + bb0: { + StorageLive(_1); + StorageLive(_2); + _2 = (); + _1 = move _2 as Never (Transmute); + unreachable; + } + } + diff --git a/tests/mir-opt/dataflow-const-prop/transmute.unreachable_direct.DataflowConstProp.64bit.diff b/tests/mir-opt/dataflow-const-prop/transmute.unreachable_direct.DataflowConstProp.64bit.diff new file mode 100644 index 00000000000..acbb5cd1bc7 --- /dev/null +++ b/tests/mir-opt/dataflow-const-prop/transmute.unreachable_direct.DataflowConstProp.64bit.diff @@ -0,0 +1,22 @@ +- // MIR for `unreachable_direct` before DataflowConstProp ++ // MIR for `unreachable_direct` after DataflowConstProp + + fn unreachable_direct() -> ! { + let mut _0: !; + let _1: Never; + let mut _2: (); + scope 1 { + debug x => _1; + } + scope 2 { + } + + bb0: { + StorageLive(_1); + StorageLive(_2); + _2 = (); + _1 = move _2 as Never (Transmute); + unreachable; + } + } + diff --git a/tests/mir-opt/dataflow-const-prop/transmute.unreachable_mut.DataflowConstProp.32bit.diff b/tests/mir-opt/dataflow-const-prop/transmute.unreachable_mut.DataflowConstProp.32bit.diff new file mode 100644 index 00000000000..2ffaeea72db --- /dev/null +++ b/tests/mir-opt/dataflow-const-prop/transmute.unreachable_mut.DataflowConstProp.32bit.diff @@ -0,0 +1,24 @@ +- // MIR for `unreachable_mut` before DataflowConstProp ++ // MIR for `unreachable_mut` after DataflowConstProp + + fn unreachable_mut() -> ! { + let mut _0: !; + let _1: &mut Never; + let mut _2: &mut Never; + scope 1 { + debug x => _1; + } + scope 2 { + } + + bb0: { + StorageLive(_1); + StorageLive(_2); +- _2 = const 1_usize as &mut Never (Transmute); ++ _2 = const {0x1 as &mut Never}; + _1 = &mut (*_2); + StorageDead(_2); + unreachable; + } + } + diff --git a/tests/mir-opt/dataflow-const-prop/transmute.unreachable_mut.DataflowConstProp.64bit.diff b/tests/mir-opt/dataflow-const-prop/transmute.unreachable_mut.DataflowConstProp.64bit.diff new file mode 100644 index 00000000000..2ffaeea72db --- /dev/null +++ b/tests/mir-opt/dataflow-const-prop/transmute.unreachable_mut.DataflowConstProp.64bit.diff @@ -0,0 +1,24 @@ +- // MIR for `unreachable_mut` before DataflowConstProp ++ // MIR for `unreachable_mut` after DataflowConstProp + + fn unreachable_mut() -> ! { + let mut _0: !; + let _1: &mut Never; + let mut _2: &mut Never; + scope 1 { + debug x => _1; + } + scope 2 { + } + + bb0: { + StorageLive(_1); + StorageLive(_2); +- _2 = const 1_usize as &mut Never (Transmute); ++ _2 = const {0x1 as &mut Never}; + _1 = &mut (*_2); + StorageDead(_2); + unreachable; + } + } + diff --git a/tests/mir-opt/dataflow-const-prop/transmute.unreachable_ref.DataflowConstProp.32bit.diff b/tests/mir-opt/dataflow-const-prop/transmute.unreachable_ref.DataflowConstProp.32bit.diff new file mode 100644 index 00000000000..31fcaafc5bc --- /dev/null +++ b/tests/mir-opt/dataflow-const-prop/transmute.unreachable_ref.DataflowConstProp.32bit.diff @@ -0,0 +1,20 @@ +- // MIR for `unreachable_ref` before DataflowConstProp ++ // MIR for `unreachable_ref` after DataflowConstProp + + fn unreachable_ref() -> ! { + let mut _0: !; + let _1: &Never; + scope 1 { + debug x => _1; + } + scope 2 { + } + + bb0: { + StorageLive(_1); +- _1 = const 1_usize as &Never (Transmute); ++ _1 = const {0x1 as &Never}; + unreachable; + } + } + diff --git a/tests/mir-opt/dataflow-const-prop/transmute.unreachable_ref.DataflowConstProp.64bit.diff b/tests/mir-opt/dataflow-const-prop/transmute.unreachable_ref.DataflowConstProp.64bit.diff new file mode 100644 index 00000000000..31fcaafc5bc --- /dev/null +++ b/tests/mir-opt/dataflow-const-prop/transmute.unreachable_ref.DataflowConstProp.64bit.diff @@ -0,0 +1,20 @@ +- // MIR for `unreachable_ref` before DataflowConstProp ++ // MIR for `unreachable_ref` after DataflowConstProp + + fn unreachable_ref() -> ! { + let mut _0: !; + let _1: &Never; + scope 1 { + debug x => _1; + } + scope 2 { + } + + bb0: { + StorageLive(_1); +- _1 = const 1_usize as &Never (Transmute); ++ _1 = const {0x1 as &Never}; + unreachable; + } + } + diff --git a/tests/mir-opt/dataflow-const-prop/transmute.valid_char.DataflowConstProp.32bit.diff b/tests/mir-opt/dataflow-const-prop/transmute.valid_char.DataflowConstProp.32bit.diff new file mode 100644 index 00000000000..402ef754a64 --- /dev/null +++ b/tests/mir-opt/dataflow-const-prop/transmute.valid_char.DataflowConstProp.32bit.diff @@ -0,0 +1,15 @@ +- // MIR for `valid_char` before DataflowConstProp ++ // MIR for `valid_char` after DataflowConstProp + + fn valid_char() -> char { + let mut _0: char; + scope 1 { + } + + bb0: { +- _0 = const 82_u32 as char (Transmute); ++ _0 = const 'R'; + return; + } + } + diff --git a/tests/mir-opt/dataflow-const-prop/transmute.valid_char.DataflowConstProp.64bit.diff b/tests/mir-opt/dataflow-const-prop/transmute.valid_char.DataflowConstProp.64bit.diff new file mode 100644 index 00000000000..402ef754a64 --- /dev/null +++ b/tests/mir-opt/dataflow-const-prop/transmute.valid_char.DataflowConstProp.64bit.diff @@ -0,0 +1,15 @@ +- // MIR for `valid_char` before DataflowConstProp ++ // MIR for `valid_char` after DataflowConstProp + + fn valid_char() -> char { + let mut _0: char; + scope 1 { + } + + bb0: { +- _0 = const 82_u32 as char (Transmute); ++ _0 = const 'R'; + return; + } + } + diff --git a/tests/mir-opt/funky_arms.rs b/tests/mir-opt/funky_arms.rs index 6b4f4c80560..79fd9457ce1 100644 --- a/tests/mir-opt/funky_arms.rs +++ b/tests/mir-opt/funky_arms.rs @@ -9,7 +9,7 @@ use core::num::flt2dec; use std::fmt::{Formatter, Result}; // EMIT_MIR funky_arms.float_to_exponential_common.ConstProp.diff -fn float_to_exponential_common<T>(fmt: &mut Formatter<'_>, num: &T, upper: bool) -> Result +pub fn float_to_exponential_common<T>(fmt: &mut Formatter<'_>, num: &T, upper: bool) -> Result where T: flt2dec::DecodableFloat, { diff --git a/tests/mir-opt/generator_drop_cleanup.main-{closure#0}.generator_drop.0.panic-abort.mir b/tests/mir-opt/generator_drop_cleanup.main-{closure#0}.generator_drop.0.panic-abort.mir index 958078b9706..acbb7904985 100644 --- a/tests/mir-opt/generator_drop_cleanup.main-{closure#0}.generator_drop.0.panic-abort.mir +++ b/tests/mir-opt/generator_drop_cleanup.main-{closure#0}.generator_drop.0.panic-abort.mir @@ -2,7 +2,11 @@ /* generator_layout = GeneratorLayout { field_tys: { _0: GeneratorSavedTy { - ty: std::string::String, + ty: Adt( + std::string::String, + [ + ], + ), source_info: SourceInfo { span: $DIR/generator_drop_cleanup.rs:11:13: 11:15 (#0), scope: scope[0], diff --git a/tests/mir-opt/generator_drop_cleanup.main-{closure#0}.generator_drop.0.panic-unwind.mir b/tests/mir-opt/generator_drop_cleanup.main-{closure#0}.generator_drop.0.panic-unwind.mir index 7e050e585b1..c17d4421542 100644 --- a/tests/mir-opt/generator_drop_cleanup.main-{closure#0}.generator_drop.0.panic-unwind.mir +++ b/tests/mir-opt/generator_drop_cleanup.main-{closure#0}.generator_drop.0.panic-unwind.mir @@ -2,7 +2,11 @@ /* generator_layout = GeneratorLayout { field_tys: { _0: GeneratorSavedTy { - ty: std::string::String, + ty: Adt( + std::string::String, + [ + ], + ), source_info: SourceInfo { span: $DIR/generator_drop_cleanup.rs:11:13: 11:15 (#0), scope: scope[0], diff --git a/tests/mir-opt/generator_tiny.main-{closure#0}.generator_resume.0.mir b/tests/mir-opt/generator_tiny.main-{closure#0}.generator_resume.0.mir index 13d703b908c..e33f5f59de1 100644 --- a/tests/mir-opt/generator_tiny.main-{closure#0}.generator_resume.0.mir +++ b/tests/mir-opt/generator_tiny.main-{closure#0}.generator_resume.0.mir @@ -2,7 +2,11 @@ /* generator_layout = GeneratorLayout { field_tys: { _0: GeneratorSavedTy { - ty: HasDrop, + ty: Adt( + HasDrop, + [ + ], + ), source_info: SourceInfo { span: $DIR/generator_tiny.rs:20:13: 20:15 (#0), scope: scope[0], diff --git a/tests/mir-opt/issue_76432.test.SimplifyComparisonIntegral.panic-abort.diff b/tests/mir-opt/issue_76432.test.SimplifyComparisonIntegral.panic-abort.diff index f61632728ba..9d8f272abea 100644 --- a/tests/mir-opt/issue_76432.test.SimplifyComparisonIntegral.panic-abort.diff +++ b/tests/mir-opt/issue_76432.test.SimplifyComparisonIntegral.panic-abort.diff @@ -33,12 +33,10 @@ _3 = &_4; _2 = move _3 as &[T] (PointerCoercion(Unsize)); StorageDead(_3); - _8 = Len((*_2)); + _8 = const 3_usize; _9 = const 3_usize; -- _10 = Eq(move _8, const 3_usize); -- switchInt(move _10) -> [0: bb1, otherwise: bb2]; -+ nop; -+ switchInt(move _8) -> [3: bb2, otherwise: bb1]; + _10 = const true; + goto -> bb2; } bb1: { diff --git a/tests/mir-opt/issue_76432.test.SimplifyComparisonIntegral.panic-unwind.diff b/tests/mir-opt/issue_76432.test.SimplifyComparisonIntegral.panic-unwind.diff index f6c337be10f..738b0b1b3e5 100644 --- a/tests/mir-opt/issue_76432.test.SimplifyComparisonIntegral.panic-unwind.diff +++ b/tests/mir-opt/issue_76432.test.SimplifyComparisonIntegral.panic-unwind.diff @@ -33,12 +33,10 @@ _3 = &_4; _2 = move _3 as &[T] (PointerCoercion(Unsize)); StorageDead(_3); - _8 = Len((*_2)); + _8 = const 3_usize; _9 = const 3_usize; -- _10 = Eq(move _8, const 3_usize); -- switchInt(move _10) -> [0: bb1, otherwise: bb2]; -+ nop; -+ switchInt(move _8) -> [3: bb2, otherwise: bb1]; + _10 = const true; + goto -> bb2; } bb1: { diff --git a/tests/mir-opt/issue_99325.main.built.after.mir b/tests/mir-opt/issue_99325.main.built.after.32bit.mir index f12179a8905..b6a673b6355 100644 --- a/tests/mir-opt/issue_99325.main.built.after.mir +++ b/tests/mir-opt/issue_99325.main.built.after.32bit.mir @@ -1,8 +1,8 @@ // MIR for `main` after built | User Type Annotations -| 0: user_ty: Canonical { value: TypeOf(DefId(0:3 ~ issue_99325[22bb]::function_with_bytes), UserArgs { args: [Const { ty: &'static [u8; 4], kind: Branch([Leaf(0x41), Leaf(0x41), Leaf(0x41), Leaf(0x41)]) }], user_self_ty: None }), max_universe: U0, variables: [] }, span: $DIR/issue_99325.rs:10:16: 10:46, inferred_ty: fn() -> &'static [u8] {function_with_bytes::<&*b"AAAA">} -| 1: user_ty: Canonical { value: TypeOf(DefId(0:3 ~ issue_99325[22bb]::function_with_bytes), UserArgs { args: [Const { ty: &'static [u8; 4], kind: UnevaluatedConst { def: DefId(0:8 ~ issue_99325[22bb]::main::{constant#1}), args: [] } }], user_self_ty: None }), max_universe: U0, variables: [] }, span: $DIR/issue_99325.rs:11:16: 11:68, inferred_ty: fn() -> &'static [u8] {function_with_bytes::<&*b"AAAA">} +| 0: user_ty: Canonical { value: TypeOf(DefId(0:3 ~ issue_99325[22bb]::function_with_bytes), UserArgs { args: [Const { ty: &ReStatic [u8; Const { ty: usize, kind: Leaf(0x00000004) }], kind: Branch([Leaf(0x41), Leaf(0x41), Leaf(0x41), Leaf(0x41)]) }], user_self_ty: None }), max_universe: U0, variables: [] }, span: $DIR/issue_99325.rs:12:16: 12:46, inferred_ty: fn() -> &'static [u8] {function_with_bytes::<&*b"AAAA">} +| 1: user_ty: Canonical { value: TypeOf(DefId(0:3 ~ issue_99325[22bb]::function_with_bytes), UserArgs { args: [Const { ty: &ReStatic [u8; Const { ty: usize, kind: Leaf(0x00000004) }], kind: UnevaluatedConst { def: DefId(0:8 ~ issue_99325[22bb]::main::{constant#1}), args: [] } }], user_self_ty: None }), max_universe: U0, variables: [] }, span: $DIR/issue_99325.rs:13:16: 13:68, inferred_ty: fn() -> &'static [u8] {function_with_bytes::<&*b"AAAA">} | fn main() -> () { let mut _0: (); diff --git a/tests/mir-opt/issue_99325.main.built.after.64bit.mir b/tests/mir-opt/issue_99325.main.built.after.64bit.mir new file mode 100644 index 00000000000..9d112cfa20a --- /dev/null +++ b/tests/mir-opt/issue_99325.main.built.after.64bit.mir @@ -0,0 +1,276 @@ +// MIR for `main` after built + +| User Type Annotations +| 0: user_ty: Canonical { value: TypeOf(DefId(0:3 ~ issue_99325[22bb]::function_with_bytes), UserArgs { args: [Const { ty: &ReStatic [u8; Const { ty: usize, kind: Leaf(0x0000000000000004) }], kind: Branch([Leaf(0x41), Leaf(0x41), Leaf(0x41), Leaf(0x41)]) }], user_self_ty: None }), max_universe: U0, variables: [] }, span: $DIR/issue_99325.rs:12:16: 12:46, inferred_ty: fn() -> &'static [u8] {function_with_bytes::<&*b"AAAA">} +| 1: user_ty: Canonical { value: TypeOf(DefId(0:3 ~ issue_99325[22bb]::function_with_bytes), UserArgs { args: [Const { ty: &ReStatic [u8; Const { ty: usize, kind: Leaf(0x0000000000000004) }], kind: UnevaluatedConst { def: DefId(0:8 ~ issue_99325[22bb]::main::{constant#1}), args: [] } }], user_self_ty: None }), max_universe: U0, variables: [] }, span: $DIR/issue_99325.rs:13:16: 13:68, inferred_ty: fn() -> &'static [u8] {function_with_bytes::<&*b"AAAA">} +| +fn main() -> () { + let mut _0: (); + let _1: (); + let mut _2: (&&[u8], &&[u8; 4]); + let mut _3: &&[u8]; + let _4: &[u8]; + let mut _5: &&[u8; 4]; + let _6: &[u8; 4]; + let _7: [u8; 4]; + let _8: &&[u8]; + let _9: &&[u8; 4]; + let mut _10: bool; + let mut _11: &&[u8]; + let mut _12: &&[u8; 4]; + let mut _13: !; + let _15: !; + let mut _16: core::panicking::AssertKind; + let mut _17: &&[u8]; + let _18: &&[u8]; + let mut _19: &&[u8; 4]; + let _20: &&[u8; 4]; + let mut _21: std::option::Option<std::fmt::Arguments<'_>>; + let _22: (); + let mut _23: (&&[u8], &&[u8; 4]); + let mut _24: &&[u8]; + let _25: &[u8]; + let mut _26: &&[u8; 4]; + let _27: &[u8; 4]; + let _28: &&[u8]; + let _29: &&[u8; 4]; + let mut _30: bool; + let mut _31: &&[u8]; + let mut _32: &&[u8; 4]; + let mut _33: !; + let _35: !; + let mut _36: core::panicking::AssertKind; + let mut _37: &&[u8]; + let _38: &&[u8]; + let mut _39: &&[u8; 4]; + let _40: &&[u8; 4]; + let mut _41: std::option::Option<std::fmt::Arguments<'_>>; + scope 1 { + debug left_val => _8; + debug right_val => _9; + let _14: core::panicking::AssertKind; + scope 2 { + debug kind => _14; + } + } + scope 3 { + debug left_val => _28; + debug right_val => _29; + let _34: core::panicking::AssertKind; + scope 4 { + debug kind => _34; + } + } + + bb0: { + StorageLive(_1); + StorageLive(_2); + StorageLive(_3); + StorageLive(_4); + _4 = function_with_bytes::<&*b"AAAA">() -> [return: bb1, unwind: bb21]; + } + + bb1: { + _3 = &_4; + StorageLive(_5); + StorageLive(_6); + StorageLive(_7); + _7 = [const 65_u8, const 65_u8, const 65_u8, const 65_u8]; + _6 = &_7; + _5 = &_6; + _2 = (move _3, move _5); + StorageDead(_5); + StorageDead(_3); + FakeRead(ForMatchedPlace(None), _2); + StorageLive(_8); + _8 = (_2.0: &&[u8]); + StorageLive(_9); + _9 = (_2.1: &&[u8; 4]); + StorageLive(_10); + StorageLive(_11); + _11 = &(*_8); + StorageLive(_12); + _12 = &(*_9); + _10 = <&[u8] as PartialEq<&[u8; 4]>>::eq(move _11, move _12) -> [return: bb2, unwind: bb21]; + } + + bb2: { + switchInt(move _10) -> [0: bb4, otherwise: bb3]; + } + + bb3: { + StorageDead(_12); + StorageDead(_11); + goto -> bb8; + } + + bb4: { + goto -> bb5; + } + + bb5: { + StorageDead(_12); + StorageDead(_11); + StorageLive(_14); + _14 = core::panicking::AssertKind::Eq; + FakeRead(ForLet(None), _14); + StorageLive(_15); + StorageLive(_16); + _16 = move _14; + StorageLive(_17); + StorageLive(_18); + _18 = &(*_8); + _17 = &(*_18); + StorageLive(_19); + StorageLive(_20); + _20 = &(*_9); + _19 = &(*_20); + StorageLive(_21); + _21 = Option::<Arguments<'_>>::None; + _15 = core::panicking::assert_failed::<&[u8], &[u8; 4]>(move _16, move _17, move _19, move _21) -> bb21; + } + + bb6: { + StorageDead(_21); + StorageDead(_19); + StorageDead(_17); + StorageDead(_16); + StorageDead(_20); + StorageDead(_18); + StorageDead(_15); + StorageDead(_14); + unreachable; + } + + bb7: { + goto -> bb9; + } + + bb8: { + _1 = const (); + goto -> bb9; + } + + bb9: { + StorageDead(_10); + StorageDead(_9); + StorageDead(_8); + goto -> bb10; + } + + bb10: { + StorageDead(_7); + StorageDead(_6); + StorageDead(_4); + StorageDead(_2); + StorageDead(_1); + StorageLive(_22); + StorageLive(_23); + StorageLive(_24); + StorageLive(_25); + _25 = function_with_bytes::<&*b"AAAA">() -> [return: bb11, unwind: bb21]; + } + + bb11: { + _24 = &_25; + StorageLive(_26); + StorageLive(_27); + _27 = const b"AAAA"; + _26 = &_27; + _23 = (move _24, move _26); + StorageDead(_26); + StorageDead(_24); + FakeRead(ForMatchedPlace(None), _23); + StorageLive(_28); + _28 = (_23.0: &&[u8]); + StorageLive(_29); + _29 = (_23.1: &&[u8; 4]); + StorageLive(_30); + StorageLive(_31); + _31 = &(*_28); + StorageLive(_32); + _32 = &(*_29); + _30 = <&[u8] as PartialEq<&[u8; 4]>>::eq(move _31, move _32) -> [return: bb12, unwind: bb21]; + } + + bb12: { + switchInt(move _30) -> [0: bb14, otherwise: bb13]; + } + + bb13: { + StorageDead(_32); + StorageDead(_31); + goto -> bb18; + } + + bb14: { + goto -> bb15; + } + + bb15: { + StorageDead(_32); + StorageDead(_31); + StorageLive(_34); + _34 = core::panicking::AssertKind::Eq; + FakeRead(ForLet(None), _34); + StorageLive(_35); + StorageLive(_36); + _36 = move _34; + StorageLive(_37); + StorageLive(_38); + _38 = &(*_28); + _37 = &(*_38); + StorageLive(_39); + StorageLive(_40); + _40 = &(*_29); + _39 = &(*_40); + StorageLive(_41); + _41 = Option::<Arguments<'_>>::None; + _35 = core::panicking::assert_failed::<&[u8], &[u8; 4]>(move _36, move _37, move _39, move _41) -> bb21; + } + + bb16: { + StorageDead(_41); + StorageDead(_39); + StorageDead(_37); + StorageDead(_36); + StorageDead(_40); + StorageDead(_38); + StorageDead(_35); + StorageDead(_34); + unreachable; + } + + bb17: { + goto -> bb19; + } + + bb18: { + _22 = const (); + goto -> bb19; + } + + bb19: { + StorageDead(_30); + StorageDead(_29); + StorageDead(_28); + goto -> bb20; + } + + bb20: { + StorageDead(_27); + StorageDead(_25); + StorageDead(_23); + StorageDead(_22); + _0 = const (); + return; + } + + bb21 (cleanup): { + resume; + } +} + +alloc4 (size: 4, align: 1) { + 41 41 41 41 │ AAAA +} diff --git a/tests/mir-opt/issue_99325.rs b/tests/mir-opt/issue_99325.rs index fe819cddb2c..3603228a502 100644 --- a/tests/mir-opt/issue_99325.rs +++ b/tests/mir-opt/issue_99325.rs @@ -1,3 +1,5 @@ +// EMIT_MIR_FOR_EACH_BIT_WIDTH + #![feature(adt_const_params)] #![allow(incomplete_features)] diff --git a/tests/mir-opt/pre-codegen/slice_index.slice_get_unchecked_mut_range.PreCodegen.after.panic-abort.mir b/tests/mir-opt/pre-codegen/slice_index.slice_get_unchecked_mut_range.PreCodegen.after.panic-abort.mir index 8dd2cd7900f..2fd669aeeb6 100644 --- a/tests/mir-opt/pre-codegen/slice_index.slice_get_unchecked_mut_range.PreCodegen.after.panic-abort.mir +++ b/tests/mir-opt/pre-codegen/slice_index.slice_get_unchecked_mut_range.PreCodegen.after.panic-abort.mir @@ -8,19 +8,22 @@ fn slice_get_unchecked_mut_range(_1: &mut [u32], _2: std::ops::Range<usize>) -> let mut _4: usize; scope 1 (inlined core::slice::<impl [u32]>::get_unchecked_mut::<std::ops::Range<usize>>) { debug self => _1; - debug index => std::ops::Range<usize>{ .0 => _3, .1 => _4, }; + debug ((index: std::ops::Range<usize>).0: usize) => _3; + debug ((index: std::ops::Range<usize>).1: usize) => _4; let mut _5: *mut [u32]; let mut _13: *mut [u32]; scope 2 { scope 3 (inlined <std::ops::Range<usize> as SliceIndex<[u32]>>::get_unchecked_mut) { - debug self => std::ops::Range<usize>{ .0 => _3, .1 => _4, }; + debug ((self: std::ops::Range<usize>).0: usize) => _3; + debug ((self: std::ops::Range<usize>).1: usize) => _4; debug slice => _5; let mut _7: *mut u32; let mut _8: *mut u32; let _15: usize; let _16: usize; scope 4 { - debug this => std::ops::Range<usize>{ .0 => _15, .1 => _16, }; + debug ((this: std::ops::Range<usize>).0: usize) => _15; + debug ((this: std::ops::Range<usize>).1: usize) => _16; scope 5 { let _6: usize; scope 6 { @@ -53,7 +56,8 @@ fn slice_get_unchecked_mut_range(_1: &mut [u32], _2: std::ops::Range<usize>) -> } } scope 7 (inlined <std::ops::Range<usize> as SliceIndex<[T]>>::get_unchecked_mut::runtime::<u32>) { - debug this => std::ops::Range<usize>{ .0 => _15, .1 => _16, }; + debug ((this: std::ops::Range<usize>).0: usize) => _15; + debug ((this: std::ops::Range<usize>).1: usize) => _16; debug slice => _5; scope 8 (inlined ptr::mut_ptr::<impl *mut [u32]>::len) { debug self => _5; diff --git a/tests/mir-opt/pre-codegen/slice_index.slice_get_unchecked_mut_range.PreCodegen.after.panic-unwind.mir b/tests/mir-opt/pre-codegen/slice_index.slice_get_unchecked_mut_range.PreCodegen.after.panic-unwind.mir index 8dd2cd7900f..2fd669aeeb6 100644 --- a/tests/mir-opt/pre-codegen/slice_index.slice_get_unchecked_mut_range.PreCodegen.after.panic-unwind.mir +++ b/tests/mir-opt/pre-codegen/slice_index.slice_get_unchecked_mut_range.PreCodegen.after.panic-unwind.mir @@ -8,19 +8,22 @@ fn slice_get_unchecked_mut_range(_1: &mut [u32], _2: std::ops::Range<usize>) -> let mut _4: usize; scope 1 (inlined core::slice::<impl [u32]>::get_unchecked_mut::<std::ops::Range<usize>>) { debug self => _1; - debug index => std::ops::Range<usize>{ .0 => _3, .1 => _4, }; + debug ((index: std::ops::Range<usize>).0: usize) => _3; + debug ((index: std::ops::Range<usize>).1: usize) => _4; let mut _5: *mut [u32]; let mut _13: *mut [u32]; scope 2 { scope 3 (inlined <std::ops::Range<usize> as SliceIndex<[u32]>>::get_unchecked_mut) { - debug self => std::ops::Range<usize>{ .0 => _3, .1 => _4, }; + debug ((self: std::ops::Range<usize>).0: usize) => _3; + debug ((self: std::ops::Range<usize>).1: usize) => _4; debug slice => _5; let mut _7: *mut u32; let mut _8: *mut u32; let _15: usize; let _16: usize; scope 4 { - debug this => std::ops::Range<usize>{ .0 => _15, .1 => _16, }; + debug ((this: std::ops::Range<usize>).0: usize) => _15; + debug ((this: std::ops::Range<usize>).1: usize) => _16; scope 5 { let _6: usize; scope 6 { @@ -53,7 +56,8 @@ fn slice_get_unchecked_mut_range(_1: &mut [u32], _2: std::ops::Range<usize>) -> } } scope 7 (inlined <std::ops::Range<usize> as SliceIndex<[T]>>::get_unchecked_mut::runtime::<u32>) { - debug this => std::ops::Range<usize>{ .0 => _15, .1 => _16, }; + debug ((this: std::ops::Range<usize>).0: usize) => _15; + debug ((this: std::ops::Range<usize>).1: usize) => _16; debug slice => _5; scope 8 (inlined ptr::mut_ptr::<impl *mut [u32]>::len) { debug self => _5; diff --git a/tests/mir-opt/sroa/lifetimes.foo.ScalarReplacementOfAggregates.diff b/tests/mir-opt/sroa/lifetimes.foo.ScalarReplacementOfAggregates.diff index bb14b909a95..b020d1baafa 100644 --- a/tests/mir-opt/sroa/lifetimes.foo.ScalarReplacementOfAggregates.diff +++ b/tests/mir-opt/sroa/lifetimes.foo.ScalarReplacementOfAggregates.diff @@ -33,7 +33,8 @@ + let _32: u32; scope 1 { - debug foo => _1; -+ debug foo => Foo<T>{ .0 => _31, .1 => _32, }; ++ debug ((foo: Foo<T>).0: std::result::Result<std::boxed::Box<dyn std::fmt::Display>, <T as Err>::Err>) => _31; ++ debug ((foo: Foo<T>).1: u32) => _32; let _5: std::result::Result<std::boxed::Box<dyn std::fmt::Display>, <T as Err>::Err>; scope 2 { debug x => _5; diff --git a/tests/mir-opt/sroa/structs.constant.ScalarReplacementOfAggregates.diff b/tests/mir-opt/sroa/structs.constant.ScalarReplacementOfAggregates.diff index 7ee0431692c..1330f9b3ac8 100644 --- a/tests/mir-opt/sroa/structs.constant.ScalarReplacementOfAggregates.diff +++ b/tests/mir-opt/sroa/structs.constant.ScalarReplacementOfAggregates.diff @@ -8,7 +8,8 @@ + let _5: u8; scope 1 { - debug y => _1; -+ debug y => (usize, u8){ .0 => _4, .1 => _5, }; ++ debug ((y: (usize, u8)).0: usize) => _4; ++ debug ((y: (usize, u8)).1: u8) => _5; let _2: usize; scope 2 { debug t => _2; diff --git a/tests/mir-opt/sroa/structs.copies.ScalarReplacementOfAggregates.diff b/tests/mir-opt/sroa/structs.copies.ScalarReplacementOfAggregates.diff index 0a1de891aee..3621338635e 100644 --- a/tests/mir-opt/sroa/structs.copies.ScalarReplacementOfAggregates.diff +++ b/tests/mir-opt/sroa/structs.copies.ScalarReplacementOfAggregates.diff @@ -11,7 +11,10 @@ + let _14: std::option::Option<isize>; scope 1 { - debug y => _2; -+ debug y => Foo{ .0 => _11, .1 => _12, .2 => _13, .3 => _14, }; ++ debug ((y: Foo).0: u8) => _11; ++ debug ((y: Foo).1: ()) => _12; ++ debug ((y: Foo).2: &str) => _13; ++ debug ((y: Foo).3: std::option::Option<isize>) => _14; let _3: u8; scope 2 { debug t => _3; @@ -25,7 +28,10 @@ + let _10: std::option::Option<isize>; scope 4 { - debug z => _5; -+ debug z => Foo{ .0 => _7, .1 => _8, .2 => _9, .3 => _10, }; ++ debug ((z: Foo).0: u8) => _7; ++ debug ((z: Foo).1: ()) => _8; ++ debug ((z: Foo).2: &str) => _9; ++ debug ((z: Foo).3: std::option::Option<isize>) => _10; let _6: (); scope 5 { debug a => _6; diff --git a/tests/mir-opt/sroa/structs.ref_copies.ScalarReplacementOfAggregates.diff b/tests/mir-opt/sroa/structs.ref_copies.ScalarReplacementOfAggregates.diff index d7c57c293c4..304bf2fb1a7 100644 --- a/tests/mir-opt/sroa/structs.ref_copies.ScalarReplacementOfAggregates.diff +++ b/tests/mir-opt/sroa/structs.ref_copies.ScalarReplacementOfAggregates.diff @@ -11,7 +11,10 @@ + let _8: std::option::Option<isize>; scope 1 { - debug y => _2; -+ debug y => Foo{ .0 => _5, .1 => _6, .2 => _7, .3 => _8, }; ++ debug ((y: Foo).0: u8) => _5; ++ debug ((y: Foo).1: ()) => _6; ++ debug ((y: Foo).2: &str) => _7; ++ debug ((y: Foo).3: std::option::Option<isize>) => _8; let _3: u8; scope 2 { debug t => _3; diff --git a/tests/run-make-fulldeps/issue-19371/foo.rs b/tests/run-make-fulldeps/issue-19371/foo.rs index 68132638759..1c9d33dcc8e 100644 --- a/tests/run-make-fulldeps/issue-19371/foo.rs +++ b/tests/run-make-fulldeps/issue-19371/foo.rs @@ -61,6 +61,7 @@ fn compile(code: String, output: PathBuf, sysroot: PathBuf) { override_queries: None, make_codegen_backend: None, registry: rustc_driver::diagnostics_registry(), + expanded_args: Default::default(), }; interface::run_compiler(config, |compiler| { diff --git a/tests/run-make-fulldeps/obtain-borrowck/driver.rs b/tests/run-make-fulldeps/obtain-borrowck/driver.rs index 04c551cf4bb..b59a65a713f 100644 --- a/tests/run-make-fulldeps/obtain-borrowck/driver.rs +++ b/tests/run-make-fulldeps/obtain-borrowck/driver.rs @@ -27,7 +27,7 @@ use rustc_interface::{Config, Queries}; use rustc_middle::query::queries::mir_borrowck::ProvidedValue; use rustc_middle::query::{ExternProviders, Providers}; use rustc_middle::ty::TyCtxt; -use rustc_session::{Session, EarlyErrorHandler}; +use rustc_session::Session; use std::cell::RefCell; use std::collections::HashMap; use std::thread_local; @@ -58,7 +58,6 @@ impl rustc_driver::Callbacks for CompilerCalls { // the result. fn after_analysis<'tcx>( &mut self, - _handler: &EarlyErrorHandler, compiler: &Compiler, queries: &'tcx Queries<'tcx>, ) -> Compilation { diff --git a/tests/run-make/compressed-debuginfo/Makefile b/tests/run-make/compressed-debuginfo/Makefile new file mode 100644 index 00000000000..f9e4927d008 --- /dev/null +++ b/tests/run-make/compressed-debuginfo/Makefile @@ -0,0 +1,15 @@ +# ignore-cross-compile +include ../tools.mk + +# only-linux +# min-llvm-version: 16.0 +# +# This tests debuginfo-compression. + +all: zlib zstandard + +zlib: + test "`$(RUSTC) --crate-name=foo --crate-type=lib --emit=obj -C debuginfo=full -Z debuginfo-compression=zlib foo.rs 2>&1 | sed 's/.*unknown.*zlib.*/missing/' | head -n 1`" = missing || readelf -t $(TMPDIR)/foo.o | grep -q ZLIB + +zstandard: + test "`$(RUSTC) --crate-name=foo --crate-type=lib --emit=obj -C debuginfo=full -Z debuginfo-compression=zstd foo.rs 2>&1 | sed 's/.*unknown.*zstd.*/missing/' | head -n 1`" = missing || readelf -t $(TMPDIR)/foo.o | grep -q ZST diff --git a/tests/run-make/compressed-debuginfo/foo.rs b/tests/run-make/compressed-debuginfo/foo.rs new file mode 100644 index 00000000000..185ce22450c --- /dev/null +++ b/tests/run-make/compressed-debuginfo/foo.rs @@ -0,0 +1,3 @@ +pub fn foo() -> i32 { + 42 +} diff --git a/tests/run-make/lto-linkage-used-attr/Makefile b/tests/run-make/lto-linkage-used-attr/Makefile new file mode 100644 index 00000000000..e78b83890ed --- /dev/null +++ b/tests/run-make/lto-linkage-used-attr/Makefile @@ -0,0 +1,9 @@ +include ../tools.mk + +# Verify that the impl_* symbols are preserved. #108030 +# only-x86_64-unknown-linux-gnu +# min-llvm-version: 17 + +all: + $(RUSTC) -Cdebuginfo=0 -Copt-level=3 lib.rs + $(RUSTC) -Clto=fat -Cdebuginfo=0 -Copt-level=3 main.rs diff --git a/tests/run-make/lto-linkage-used-attr/lib.rs b/tests/run-make/lto-linkage-used-attr/lib.rs new file mode 100644 index 00000000000..0a92ea9cd22 --- /dev/null +++ b/tests/run-make/lto-linkage-used-attr/lib.rs @@ -0,0 +1,50 @@ +#![crate_type = "rlib"] +#![crate_type = "cdylib"] + +#[macro_export] +macro_rules! asm_func { + ($name:expr, $body:expr $(, $($args:tt)*)?) => { + core::arch::global_asm!( + concat!( + ".p2align 4\n", + ".hidden ", $name, "\n", + ".global ", $name, "\n", + ".type ", $name, ",@function\n", + $name, ":\n", + $body, + ".size ", $name, ",.-", $name, + ) + $(, $($args)*)? + ); + }; +} + +macro_rules! libcall_trampoline { + ($libcall:ident ; $libcall_impl:ident) => { + asm_func!( + stringify!($libcall), + concat!( + " + .cfi_startproc simple + .cfi_def_cfa_offset 0 + jmp {} + .cfi_endproc + ", + ), + sym $libcall_impl + ); + }; +} + +pub mod trampolines { + extern "C" { + pub fn table_fill_funcref(); + pub fn table_fill_externref(); + } + + unsafe extern "C" fn impl_table_fill_funcref() {} + unsafe extern "C" fn impl_table_fill_externref() {} + + libcall_trampoline!(table_fill_funcref ; impl_table_fill_funcref); + libcall_trampoline!(table_fill_externref ; impl_table_fill_externref); +} diff --git a/tests/run-make/lto-linkage-used-attr/main.rs b/tests/run-make/lto-linkage-used-attr/main.rs new file mode 100644 index 00000000000..256b02e5b0b --- /dev/null +++ b/tests/run-make/lto-linkage-used-attr/main.rs @@ -0,0 +1,10 @@ +extern crate lib; + +use lib::trampolines::*; + +fn main() { + unsafe { + table_fill_externref(); + table_fill_funcref(); + } +} diff --git a/tests/run-make/pdb-buildinfo-cl-cmd/Makefile b/tests/run-make/pdb-buildinfo-cl-cmd/Makefile new file mode 100644 index 00000000000..a7be301a5b0 --- /dev/null +++ b/tests/run-make/pdb-buildinfo-cl-cmd/Makefile @@ -0,0 +1,16 @@ +include ../tools.mk + +# only-windows-msvc + +# tests if the pdb contains the following information in the LF_BUILDINFO: +# 1. the commandline args to compile it (cmd) +# 2. full path to the compiler (cl) + +# we just do a stringsearch on the pdb, as these need to show up at least once, as the LF_BUILDINFO is created for each cgu +# actual parsing would be better, but this is a simple and good enough solution for now + +all: + $(RUSTC_ORIGINAL) main.rs -g --crate-name my_crate_name --crate-type bin -C metadata=dc9ef878b0a48666 --out-dir $(TMPDIR) + cat '$(TMPDIR)/my_crate_name.pdb' | grep -F '$(RUSTC_ORIGINAL)' +# using a file containing the string so I don't have problems with escaping quotes and spaces + cat '$(TMPDIR)/my_crate_name.pdb' | grep -f 'stringlist.txt' diff --git a/tests/run-make/pdb-buildinfo-cl-cmd/main.rs b/tests/run-make/pdb-buildinfo-cl-cmd/main.rs new file mode 100644 index 00000000000..f79c691f085 --- /dev/null +++ b/tests/run-make/pdb-buildinfo-cl-cmd/main.rs @@ -0,0 +1,2 @@ +fn main() { +} diff --git a/tests/run-make/pdb-buildinfo-cl-cmd/stringlist.txt b/tests/run-make/pdb-buildinfo-cl-cmd/stringlist.txt new file mode 100644 index 00000000000..634e9f19e89 --- /dev/null +++ b/tests/run-make/pdb-buildinfo-cl-cmd/stringlist.txt @@ -0,0 +1 @@ +"main.rs" "-g" "--crate-name" "my_crate_name" "--crate-type" "bin" "-C" "metadata=dc9ef878b0a48666" "--out-dir" \ No newline at end of file diff --git a/tests/run-make/print-cfg/Makefile b/tests/run-make/print-cfg/Makefile index 654c303b3e2..6b153e5b54e 100644 --- a/tests/run-make/print-cfg/Makefile +++ b/tests/run-make/print-cfg/Makefile @@ -13,19 +13,19 @@ all: default output_to_file output_to_file: # Backend-independent, printed by rustc_driver_impl/src/lib.rs - $(RUSTC) --target x86_64-pc-windows-gnu --print cfg=$(TMPDIR)/cfg.txt -Z unstable-options + $(RUSTC) --target x86_64-pc-windows-gnu --print cfg=$(TMPDIR)/cfg.txt $(CGREP) windows < $(TMPDIR)/cfg.txt # Printed from CodegenBackend trait impl in rustc_codegen_llvm/src/lib.rs - $(RUSTC) --print relocation-models=$(TMPDIR)/relocation-models.txt -Z unstable-options + $(RUSTC) --print relocation-models=$(TMPDIR)/relocation-models.txt $(CGREP) dynamic-no-pic < $(TMPDIR)/relocation-models.txt # Printed by compiler/rustc_codegen_llvm/src/llvm_util.rs - $(RUSTC) --target wasm32-unknown-unknown --print target-features=$(TMPDIR)/target-features.txt -Z unstable-options + $(RUSTC) --target wasm32-unknown-unknown --print target-features=$(TMPDIR)/target-features.txt $(CGREP) reference-types < $(TMPDIR)/target-features.txt # Printed by C++ code in rustc_llvm/llvm-wrapper/PassWrapper.cpp - $(RUSTC) --target wasm32-unknown-unknown --print target-cpus=$(TMPDIR)/target-cpus.txt -Z unstable-options + $(RUSTC) --target wasm32-unknown-unknown --print target-cpus=$(TMPDIR)/target-cpus.txt $(CGREP) generic < $(TMPDIR)/target-cpus.txt ifdef IS_WINDOWS diff --git a/tests/rustdoc-gui/help-page.goml b/tests/rustdoc-gui/help-page.goml index 6e880302f28..84c20355500 100644 --- a/tests/rustdoc-gui/help-page.goml +++ b/tests/rustdoc-gui/help-page.goml @@ -33,21 +33,21 @@ define-function: ( call-function: ("check-colors", { "theme": "ayu", - "color": "rgb(197, 197, 197)", - "background": "rgb(49, 69, 89)", - "box_shadow": "rgb(92, 103, 115)", + "color": "#c5c5c5", + "background": "#314559", + "box_shadow": "#5c6773", }) call-function: ("check-colors", { "theme": "dark", - "color": "rgb(0, 0, 0)", - "background": "rgb(250, 251, 252)", - "box_shadow": "rgb(198, 203, 209)", + "color": "#000", + "background": "#fafbfc", + "box_shadow": "#c6cbd1", }) call-function: ("check-colors", { "theme": "light", - "color": "rgb(0, 0, 0)", - "background": "rgb(250, 251, 252)", - "box_shadow": "rgb(198, 203, 209)", + "color": "#000", + "background": "#fafbfc", + "box_shadow": "#c6cbd1", }) // This test ensures that opening the help popover without switching pages works. diff --git a/tests/rustdoc-gui/search-no-result.goml b/tests/rustdoc-gui/search-no-result.goml index 46d1856b4d6..e7c64791256 100644 --- a/tests/rustdoc-gui/search-no-result.goml +++ b/tests/rustdoc-gui/search-no-result.goml @@ -21,16 +21,16 @@ define-function: ( call-function: ("check-no-result", { "theme": "ayu", - "link": "rgb(57, 175, 215)", - "link_hover": "rgb(57, 175, 215)", + "link": "#39afd7", + "link_hover": "#39afd7", }) call-function: ("check-no-result", { "theme": "dark", - "link": "rgb(210, 153, 29)", - "link_hover": "rgb(210, 153, 29)", + "link": "#d2991d", + "link_hover": "#d2991d", }) call-function: ("check-no-result", { "theme": "light", - "link": "rgb(56, 115, 173)", - "link_hover": "rgb(56, 115, 173)", + "link": "#3873ad", + "link_hover": "#3873ad", }) diff --git a/tests/rustdoc/auxiliary/cross_crate_generic_typedef.rs b/tests/rustdoc/auxiliary/cross_crate_generic_typedef.rs new file mode 100644 index 00000000000..f4e020b3b95 --- /dev/null +++ b/tests/rustdoc/auxiliary/cross_crate_generic_typedef.rs @@ -0,0 +1,5 @@ +pub struct InlineOne<A> { + pub inline: A +} + +pub type InlineU64 = InlineOne<u64>; diff --git a/tests/rustdoc/const-generics/const-generic-defaults.rs b/tests/rustdoc/const-generics/const-generic-defaults.rs index f781c6a62f2..7a0a794112d 100644 --- a/tests/rustdoc/const-generics/const-generic-defaults.rs +++ b/tests/rustdoc/const-generics/const-generic-defaults.rs @@ -1,5 +1,5 @@ #![crate_name = "foo"] // @has foo/struct.Foo.html '//pre[@class="rust item-decl"]' \ -// 'pub struct Foo<const M: usize = 10, const N: usize = M, T = i32>(_);' +// 'pub struct Foo<const M: usize = 10, const N: usize = M, T = i32>(' pub struct Foo<const M: usize = 10, const N: usize = M, T = i32>(T); diff --git a/tests/rustdoc/const-generics/const-generics-docs.rs b/tests/rustdoc/const-generics/const-generics-docs.rs index 828486a41d4..70a9518f05b 100644 --- a/tests/rustdoc/const-generics/const-generics-docs.rs +++ b/tests/rustdoc/const-generics/const-generics-docs.rs @@ -33,7 +33,7 @@ impl<const N: usize> Trait<N> for [u8; N] {} // @has foo/struct.Foo.html '//pre[@class="rust item-decl"]' \ // 'pub struct Foo<const N: usize> where u8: Trait<N>' pub struct Foo<const N: usize> where u8: Trait<N>; -// @has foo/struct.Bar.html '//pre[@class="rust item-decl"]' 'pub struct Bar<T, const N: usize>(_)' +// @has foo/struct.Bar.html '//pre[@class="rust item-decl"]' 'pub struct Bar<T, const N: usize>(' pub struct Bar<T, const N: usize>([T; N]); // @has foo/struct.Foo.html '//*[@id="impl-Foo%3CM%3E"]/h3[@class="code-header"]' 'impl<const M: usize> Foo<M>where u8: Trait<M>' @@ -92,7 +92,7 @@ macro_rules! define_me { } // @has foo/struct.Foz.html '//pre[@class="rust item-decl"]' \ -// 'pub struct Foz<const N: usize>(_);' +// 'pub struct Foz<const N: usize>(/* private fields */);' define_me!(Foz<N>); trait Q { diff --git a/tests/rustdoc/issue-32077-type-alias-impls.rs b/tests/rustdoc/issue-32077-type-alias-impls.rs new file mode 100644 index 00000000000..ac486c36ad0 --- /dev/null +++ b/tests/rustdoc/issue-32077-type-alias-impls.rs @@ -0,0 +1,66 @@ +// Regression test for <https://github.com/rust-lang/rust/issues/32077>. + +#![crate_name = "foo"] + +pub struct GenericStruct<T>(T); + +impl<T> GenericStruct<T> { + pub fn on_gen(arg: T) {} +} + +impl GenericStruct<u32> { + pub fn on_u32(arg: u32) {} +} + +pub trait Foo {} +pub trait Bar {} + +impl<T> Foo for GenericStruct<T> {} +impl Bar for GenericStruct<u32> {} + +// @has 'foo/type.TypedefStruct.html' +// We check that "Aliased type" is also present as a title in the sidebar. +// @has - '//*[@class="sidebar-elems"]//h3/a[@href="#aliased-type"]' 'Aliased type' +// We check that we have the implementation of the type alias itself. +// @has - '//*[@id="impl-TypedefStruct"]/h3' 'impl TypedefStruct' +// @has - '//*[@id="method.on_alias"]/h4' 'pub fn on_alias()' +// @has - '//*[@id="impl-GenericStruct%3CT%3E"]/h3' 'impl<T> GenericStruct<T>' +// @has - '//*[@id="method.on_gen"]/h4' 'pub fn on_gen(arg: T)' +// @has - '//*[@id="impl-Foo-for-GenericStruct%3CT%3E"]/h3' 'impl<T> Foo for GenericStruct<T>' +// This trait implementation doesn't match the type alias parameters so shouldn't appear in docs. +// @!has - '//h3' 'impl Bar for GenericStruct<u32> {}' +// Same goes for the `Deref` impl. +// @!has - '//h2' 'Methods from Deref<Target = u32>' +// @count - '//nav[@class="sidebar"]//a' 'on_alias' 1 +// @count - '//nav[@class="sidebar"]//a' 'on_gen' 1 +// @count - '//nav[@class="sidebar"]//a' 'Foo' 1 +// @!has - '//nav[@class="sidebar"]//a' 'Bar' +// @!has - '//nav[@class="sidebar"]//a' 'on_u32' +pub type TypedefStruct = GenericStruct<u8>; + +impl TypedefStruct { + pub fn on_alias() {} +} + +impl std::ops::Deref for GenericStruct<u32> { + type Target = u32; + + fn deref(&self) -> &Self::Target { + &self.0 + } +} + +pub struct Wrap<T>(GenericStruct<T>); + +// @has 'foo/type.Alias.html' +// @has - '//h2' 'Methods from Deref<Target = u32>' +// @has - '//*[@id="impl-Deref-for-Wrap%3CT%3E"]/h3' 'impl<T> Deref for Wrap<T>' +pub type Alias = Wrap<u32>; + +impl<T> std::ops::Deref for Wrap<T> { + type Target = GenericStruct<T>; + + fn deref(&self) -> &Self::Target { + &self.0 + } +} diff --git a/tests/rustdoc/issue-88600.rs b/tests/rustdoc/issue-88600.rs index db0d102b741..f89af472f6e 100644 --- a/tests/rustdoc/issue-88600.rs +++ b/tests/rustdoc/issue-88600.rs @@ -8,10 +8,10 @@ pub struct S; // @has issue_88600/enum.FooEnum.html pub enum FooEnum { - // @has - '//*[@id="variant.HiddenTupleItem"]//h3' 'HiddenTupleItem(_)' + // @has - '//*[@id="variant.HiddenTupleItem"]//h3' 'HiddenTupleItem(/* private fields */)' // @count - '//*[@id="variant.HiddenTupleItem.field.0"]' 0 HiddenTupleItem(#[doc(hidden)] H), - // @has - '//*[@id="variant.MultipleHidden"]//h3' 'MultipleHidden(_, _)' + // @has - '//*[@id="variant.MultipleHidden"]//h3' 'MultipleHidden(/* private fields */)' // @count - '//*[@id="variant.MultipleHidden.field.0"]' 0 // @count - '//*[@id="variant.MultipleHidden.field.1"]' 0 MultipleHidden(#[doc(hidden)] H, #[doc(hidden)] H), diff --git a/tests/rustdoc/private-fields-tuple-struct.rs b/tests/rustdoc/private-fields-tuple-struct.rs new file mode 100644 index 00000000000..c6989dd8cdf --- /dev/null +++ b/tests/rustdoc/private-fields-tuple-struct.rs @@ -0,0 +1,15 @@ +// This test checks the diplay of "/* private fields */" sentence in tuple structs. +#![crate_name = "foo"] + +// @has 'foo/struct.A.html' '//*[@class="rust item-decl"]/code' 'pub struct A(pub u8, _);' +pub struct A(pub u8, u8); +// @has 'foo/struct.B.html' '//*[@class="rust item-decl"]/code' 'pub struct B(_, pub u8);' +pub struct B(u8, pub u8); +// @has 'foo/struct.C.html' '//*[@class="rust item-decl"]/code' 'pub struct C(_, pub u8, _);' +pub struct C(u8, pub u8, u8); +// @has 'foo/struct.D.html' '//*[@class="rust item-decl"]/code' 'pub struct D(pub u8, _, pub u8);' +pub struct D(pub u8, u8, pub u8); +// @has 'foo/struct.E.html' '//*[@class="rust item-decl"]/code' 'pub struct E(/* private fields */);' +pub struct E(u8); +// @has 'foo/struct.F.html' '//*[@class="rust item-decl"]/code' 'pub struct F(/* private fields */);' +pub struct F(u8, u8); diff --git a/tests/rustdoc/typedef-inner-variants-lazy_type_alias.rs b/tests/rustdoc/typedef-inner-variants-lazy_type_alias.rs new file mode 100644 index 00000000000..ff84352d716 --- /dev/null +++ b/tests/rustdoc/typedef-inner-variants-lazy_type_alias.rs @@ -0,0 +1,34 @@ +#![crate_name = "inner_types_lazy"] + +#![feature(lazy_type_alias)] +#![allow(incomplete_features)] + +// @has 'inner_types_lazy/struct.Pair.html' +pub struct Pair<A, B> { + pub first: A, + pub second: B, +} + +// @has 'inner_types_lazy/type.ReversedTypesPair.html' +// @count - '//*[@id="aliased-type"]' 1 +// @count - '//*[@id="variants"]' 0 +// @count - '//*[@id="fields"]' 1 +// @count - '//span[@class="where fmt-newline"]' 0 +pub type ReversedTypesPair<Q, R> = Pair<R, Q>; + +// @has 'inner_types_lazy/type.ReadWrite.html' +// @count - '//*[@id="aliased-type"]' 1 +// @count - '//*[@id="variants"]' 0 +// @count - '//*[@id="fields"]' 1 +// @count - '//span[@class="where fmt-newline"]' 2 +pub type ReadWrite<R, W> = Pair<R, W> +where + R: std::io::Read, + W: std::io::Write; + +// @has 'inner_types_lazy/type.VecPair.html' +// @count - '//*[@id="aliased-type"]' 1 +// @count - '//*[@id="variants"]' 0 +// @count - '//*[@id="fields"]' 1 +// @count - '//span[@class="where fmt-newline"]' 0 +pub type VecPair<U, V> = Pair<Vec<U>, Vec<V>>; diff --git a/tests/rustdoc/typedef-inner-variants.rs b/tests/rustdoc/typedef-inner-variants.rs new file mode 100644 index 00000000000..b734714fd64 --- /dev/null +++ b/tests/rustdoc/typedef-inner-variants.rs @@ -0,0 +1,119 @@ +// This test checks different combinations of structs, enums, and unions +// for the "Show Aliased Type" feature on type definition. + +#![crate_name = "inner_variants"] + +// aux-build:cross_crate_generic_typedef.rs +extern crate cross_crate_generic_typedef; + +pub struct Adt; +pub struct Ty; +pub struct TyCtxt; + +pub trait Interner { + type Adt; + type Ty; +} + +impl Interner for TyCtxt { + type Adt = Adt; + type Ty = Ty; +} + +// @has 'inner_variants/type.AliasTy.html' +// @count - '//*[@id="variants"]' 0 +// @count - '//*[@id="fields"]' 0 +pub type AliasTy = Ty; + +// @has 'inner_variants/enum.IrTyKind.html' +pub enum IrTyKind<A, I: Interner> { + /// Doc comment for AdtKind + AdtKind(I::Adt), + /// and another one for TyKind + TyKind(I::Adt, <I as Interner>::Ty), + // no comment + StructKind { a: A, }, + #[doc(hidden)] + Unspecified, +} + +// @has 'inner_variants/type.NearlyTyKind.html' +// @count - '//*[@id="aliased-type"]' 1 +// @count - '//*[@id="variants"]' 1 +// @count - '//*[@id="fields"]' 0 +pub type NearlyTyKind<A> = IrTyKind<A, TyCtxt>; + +// @has 'inner_variants/type.TyKind.html' +// @count - '//*[@id="aliased-type"]' 1 +// @count - '//*[@id="variants"]' 1 +// @count - '//*[@id="fields"]' 0 +// @count - '//*[@class="variant"]' 3 +// @matches - '//pre[@class="rust item-decl"]//code' "enum TyKind" +// @has - '//pre[@class="rust item-decl"]//code/a[1]' "Adt" +// @has - '//pre[@class="rust item-decl"]//code/a[2]' "Adt" +// @has - '//pre[@class="rust item-decl"]//code/a[3]' "Ty" +// @has - '//pre[@class="rust item-decl"]//code/a[4]' "i64" +pub type TyKind = IrTyKind<i64, TyCtxt>; + +// @has 'inner_variants/union.OneOr.html' +pub union OneOr<A: Copy> { + pub one: i64, + pub or: A, +} + +// @has 'inner_variants/type.OneOrF64.html' +// @count - '//*[@id="aliased-type"]' 1 +// @count - '//*[@id="variants"]' 0 +// @count - '//*[@id="fields"]' 1 +// @count - '//*[@class="structfield small-section-header"]' 2 +// @matches - '//pre[@class="rust item-decl"]//code' "union OneOrF64" +pub type OneOrF64 = OneOr<f64>; + +// @has 'inner_variants/struct.One.html' +pub struct One<T> { + pub val: T, + #[doc(hidden)] + pub __hidden: T, + __private: T, +} + +// @has 'inner_variants/type.OneU64.html' +// @count - '//*[@id="aliased-type"]' 1 +// @count - '//*[@id="variants"]' 0 +// @count - '//*[@id="fields"]' 1 +// @count - '//*[@class="structfield small-section-header"]' 1 +// @matches - '//pre[@class="rust item-decl"]//code' "struct OneU64" +// @matches - '//pre[@class="rust item-decl"]//code' "pub val" +pub type OneU64 = One<u64>; + +// @has 'inner_variants/struct.OnceA.html' +pub struct OnceA<'a, A> { + pub a: &'a A, +} + +// @has 'inner_variants/type.Once.html' +// @count - '//*[@id="aliased-type"]' 1 +// @count - '//*[@id="variants"]' 0 +// @count - '//*[@id="fields"]' 1 +// @matches - '//pre[@class="rust item-decl"]//code' "struct Once<'a>" +// @matches - '//pre[@class="rust item-decl"]//code' "&'a" +pub type Once<'a> = OnceA<'a, i64>; + +// @has 'inner_variants/struct.HighlyGenericStruct.html' +pub struct HighlyGenericStruct<A, B, C, D> { + pub z: (A, B, C, D) +} + +// @has 'inner_variants/type.HighlyGenericAABB.html' +// @count - '//*[@id="aliased-type"]' 1 +// @count - '//*[@id="variants"]' 0 +// @count - '//*[@id="fields"]' 1 +// @matches - '//pre[@class="rust item-decl"]//code' "struct HighlyGenericAABB<A, B>" +// @matches - '//pre[@class="rust item-decl"]//code' "pub z" +pub type HighlyGenericAABB<A, B> = HighlyGenericStruct<A, A, B, B>; + +// @has 'inner_variants/type.InlineU64.html' +// @count - '//*[@id="aliased-type"]' 1 +// @count - '//*[@id="variants"]' 0 +// @count - '//*[@id="fields"]' 1 +pub use cross_crate_generic_typedef::InlineU64; diff --git a/tests/rustdoc/where.SWhere_Simd_item-decl.html b/tests/rustdoc/where.SWhere_Simd_item-decl.html index 3e72ba2b74f..46708b9e4e9 100644 --- a/tests/rustdoc/where.SWhere_Simd_item-decl.html +++ b/tests/rustdoc/where.SWhere_Simd_item-decl.html @@ -1,3 +1,3 @@ -<pre class="rust item-decl"><code>pub struct Simd<T>(_) +<pre class="rust item-decl"><code>pub struct Simd<T>(/* private fields */) <span class="where">where T: <a class="trait" href="trait.MyTrait.html" title="trait foo::MyTrait">MyTrait</a></span>;</code></pre> diff --git a/tests/rustdoc/where.alpha_trait_decl.html b/tests/rustdoc/where.alpha_trait_decl.html index a7700055c9a..0c0b2d1ceca 100644 --- a/tests/rustdoc/where.alpha_trait_decl.html +++ b/tests/rustdoc/where.alpha_trait_decl.html @@ -1,3 +1,3 @@ -<code>pub struct Alpha<A>(_) +<code>pub struct Alpha<A>(/* private fields */) <span class="where">where A: <a class="trait" href="trait.MyTrait.html" title="trait foo::MyTrait">MyTrait</a></span>;</code> \ No newline at end of file diff --git a/tests/rustdoc/where.rs b/tests/rustdoc/where.rs index 2aa9c8b5461..aea02c14039 100644 --- a/tests/rustdoc/where.rs +++ b/tests/rustdoc/where.rs @@ -4,7 +4,7 @@ use std::io::Lines; pub trait MyTrait { fn dummy(&self) { } } -// @has foo/struct.Alpha.html '//pre' "pub struct Alpha<A>(_) where A: MyTrait" +// @has foo/struct.Alpha.html '//pre' "pub struct Alpha<A>(/* private fields */) where A: MyTrait" // @snapshot alpha_trait_decl - '//*[@class="rust item-decl"]/code' pub struct Alpha<A>(A) where A: MyTrait; // @has foo/trait.Bravo.html '//pre' "pub trait Bravo<B>where B: MyTrait" diff --git a/tests/ui-fulldeps/plugin/lint-tool-cmdline-allow.stderr b/tests/ui-fulldeps/plugin/lint-tool-cmdline-allow.stderr index b060e3a3e38..0e661795999 100644 --- a/tests/ui-fulldeps/plugin/lint-tool-cmdline-allow.stderr +++ b/tests/ui-fulldeps/plugin/lint-tool-cmdline-allow.stderr @@ -1,9 +1,12 @@ -warning: lint name `test_lint` is deprecated and does not have an effect anymore. Use: clippy::test_lint +warning: lint name `test_lint` is deprecated and may not have an effect in the future. | + = help: change it to clippy::test_lint = note: requested on the command line with `-A test_lint` + = note: `#[warn(renamed_and_removed_lints)]` on by default -warning: lint name `test_lint` is deprecated and does not have an effect anymore. Use: clippy::test_lint +warning: lint name `test_lint` is deprecated and may not have an effect in the future. | + = help: change it to clippy::test_lint = note: requested on the command line with `-A test_lint` warning: item is named 'lintme' @@ -22,8 +25,9 @@ LL | #![plugin(lint_tool_test)] | = note: `#[warn(deprecated)]` on by default -warning: lint name `test_lint` is deprecated and does not have an effect anymore. Use: clippy::test_lint +warning: lint name `test_lint` is deprecated and may not have an effect in the future. | + = help: change it to clippy::test_lint = note: requested on the command line with `-A test_lint` warning: 5 warnings emitted diff --git a/tests/ui-fulldeps/stable-mir/crate-info.rs b/tests/ui-fulldeps/stable-mir/crate-info.rs index 182f97373ea..a11720c4b55 100644 --- a/tests/ui-fulldeps/stable-mir/crate-info.rs +++ b/tests/ui-fulldeps/stable-mir/crate-info.rs @@ -8,6 +8,7 @@ #![feature(rustc_private)] #![feature(assert_matches)] +#![feature(control_flow_enum)] extern crate rustc_hir; extern crate rustc_middle; @@ -15,7 +16,10 @@ extern crate rustc_smir; use rustc_hir::def::DefKind; use rustc_middle::ty::TyCtxt; -use rustc_smir::{rustc_internal, stable_mir}; +use rustc_smir::{ + rustc_internal, + stable_mir::{self, fold::Foldable}, +}; use std::assert_matches::assert_matches; use std::io::Write; use std::ops::ControlFlow; @@ -110,6 +114,50 @@ fn test_stable_mir(tcx: TyCtxt<'_>) -> ControlFlow<()> { other => panic!("{other:?}"), } + let monomorphic = get_item(tcx, &items, (DefKind::Fn, "monomorphic")).unwrap(); + for block in monomorphic.body().blocks { + match &block.terminator { + stable_mir::mir::Terminator::Call { func, .. } => match func { + stable_mir::mir::Operand::Constant(c) => match &c.literal.literal { + stable_mir::ty::ConstantKind::Allocated(alloc) => { + assert!(alloc.bytes.is_empty()); + match c.literal.ty.kind() { + stable_mir::ty::TyKind::RigidTy(stable_mir::ty::RigidTy::FnDef( + def, + mut args, + )) => { + let func = def.body(); + match func.locals[1] + .fold(&mut args) + .continue_value() + .unwrap() + .kind() + { + stable_mir::ty::TyKind::RigidTy( + stable_mir::ty::RigidTy::Uint(_), + ) => {} + stable_mir::ty::TyKind::RigidTy( + stable_mir::ty::RigidTy::Tuple(_), + ) => {} + other => panic!("{other:?}"), + } + } + other => panic!("{other:?}"), + } + } + other => panic!("{other:?}"), + }, + other => panic!("{other:?}"), + }, + stable_mir::mir::Terminator::Return => {} + other => panic!("{other:?}"), + } + } + + let foo_const = get_item(tcx, &items, (DefKind::Const, "FOO")).unwrap(); + // Ensure we don't panic trying to get the body of a constant. + foo_const.body(); + ControlFlow::Continue(()) } @@ -147,6 +195,18 @@ fn generate_input(path: &str) -> std::io::Result<()> { write!( file, r#" + pub const FOO: u32 = 1 + 2; + + fn generic<T, const U: usize>(t: T) -> [(); U] {{ + _ = t; + [(); U] + }} + + pub fn monomorphic() {{ + generic::<(), 5>(()); + generic::<u32, 0>(45); + }} + mod foo {{ pub fn bar(i: i32) -> i64 {{ i as i64 diff --git a/tests/ui/abi/compatibility.rs b/tests/ui/abi/compatibility.rs new file mode 100644 index 00000000000..bfe0a5cf81d --- /dev/null +++ b/tests/ui/abi/compatibility.rs @@ -0,0 +1,144 @@ +// check-pass +#![feature(rustc_attrs, transparent_unions)] +#![allow(unused, improper_ctypes_definitions)] +use std::marker::PhantomData; +use std::mem::ManuallyDrop; +use std::num::NonZeroI32; +use std::ptr::NonNull; + +macro_rules! assert_abi_compatible { + ($name:ident, $t1:ty, $t2:ty) => { + mod $name { + use super::*; + // Test argument and return value, `Rust` and `C` ABIs. + #[rustc_abi(assert_eq)] + type TestRust = (fn($t1) -> $t1, fn($t2) -> $t2); + #[rustc_abi(assert_eq)] + type TestC = (extern "C" fn($t1) -> $t1, extern "C" fn($t2) -> $t2); + } + }; +} + +#[derive(Copy, Clone)] +struct Zst; + +#[repr(C)] +struct ReprC1<T>(T); +#[repr(C)] +struct ReprC2Int<T>(i32, T); +#[repr(C)] +struct ReprC2Float<T>(f32, T); +#[repr(C)] +struct ReprC4<T>(T, Vec<i32>, Zst, T); +#[repr(C)] +struct ReprC4Mixed<T>(T, f32, i32, T); +#[repr(C)] +enum ReprCEnum<T> { + Variant1, + Variant2(T), +} +#[repr(C)] +union ReprCUnion<T> { + nothing: (), + something: ManuallyDrop<T>, +} + +macro_rules! test_abi_compatible { + ($name:ident, $t1:ty, $t2:ty) => { + mod $name { + use super::*; + assert_abi_compatible!(plain, $t1, $t2); + // We also do some tests with differences in fields of `repr(C)` types. + assert_abi_compatible!(repr_c_1, ReprC1<$t1>, ReprC1<$t2>); + assert_abi_compatible!(repr_c_2_int, ReprC2Int<$t1>, ReprC2Int<$t2>); + assert_abi_compatible!(repr_c_2_float, ReprC2Float<$t1>, ReprC2Float<$t2>); + assert_abi_compatible!(repr_c_4, ReprC4<$t1>, ReprC4<$t2>); + assert_abi_compatible!(repr_c_4mixed, ReprC4Mixed<$t1>, ReprC4Mixed<$t2>); + assert_abi_compatible!(repr_c_enum, ReprCEnum<$t1>, ReprCEnum<$t2>); + assert_abi_compatible!(repr_c_union, ReprCUnion<$t1>, ReprCUnion<$t2>); + } + }; +} + +// Compatibility of pointers is probably de-facto guaranteed, +// but that does not seem to be documented. +test_abi_compatible!(ptr_mut, *const i32, *mut i32); +test_abi_compatible!(ptr_pointee, *const i32, *const Vec<i32>); +test_abi_compatible!(ref_mut, &i32, &mut i32); +test_abi_compatible!(ref_ptr, &i32, *const i32); +test_abi_compatible!(box_ptr, Box<i32>, *const i32); +test_abi_compatible!(nonnull_ptr, NonNull<i32>, *const i32); +test_abi_compatible!(fn_fn, fn(), fn(i32) -> i32); + +// Some further guarantees we will likely (have to) make. +test_abi_compatible!(zst_unit, Zst, ()); +test_abi_compatible!(zst_array, Zst, [u8; 0]); +test_abi_compatible!(nonzero_int, NonZeroI32, i32); + +// `repr(transparent)` compatibility. +#[repr(transparent)] +struct Wrapper1<T>(T); +#[repr(transparent)] +struct Wrapper2<T>((), Zst, T); +#[repr(transparent)] +struct Wrapper3<T>(T, [u8; 0], PhantomData<u64>); +#[repr(transparent)] +union WrapperUnion<T> { + nothing: (), + something: ManuallyDrop<T>, +} + +macro_rules! test_transparent { + ($name:ident, $t:ty) => { + mod $name { + use super::*; + test_abi_compatible!(wrap1, $t, Wrapper1<$t>); + test_abi_compatible!(wrap2, $t, Wrapper2<$t>); + test_abi_compatible!(wrap3, $t, Wrapper3<$t>); + test_abi_compatible!(wrap4, $t, WrapperUnion<$t>); + } + }; +} + +test_transparent!(simple, i32); +test_transparent!(reference, &'static i32); +test_transparent!(zst, Zst); +test_transparent!(unit, ()); +test_transparent!(pair, (i32, f32)); // mixing in some floats since they often get special treatment +test_transparent!(triple, (i8, i16, f32)); // chosen to fit into 64bit +test_transparent!(triple_f32, (f32, f32, f32)); // homogeneous case +test_transparent!(triple_f64, (f64, f64, f64)); +test_transparent!(tuple, (i32, f32, i64, f64)); +test_transparent!(empty_array, [u32; 0]); +test_transparent!(empty_1zst_array, [u8; 0]); +test_transparent!(small_array, [i32; 2]); // chosen to fit into 64bit +test_transparent!(large_array, [i32; 16]); +test_transparent!(enum_, Option<i32>); +test_transparent!(enum_niched, Option<&'static i32>); + +// RFC 3391 <https://rust-lang.github.io/rfcs/3391-result_ffi_guarantees.html>. +macro_rules! test_nonnull { + ($name:ident, $t:ty) => { + mod $name { + use super::*; + test_abi_compatible!(option, Option<$t>, $t); + test_abi_compatible!(result_err_unit, Result<$t, ()>, $t); + test_abi_compatible!(result_ok_unit, Result<(), $t>, $t); + test_abi_compatible!(result_err_zst, Result<$t, Zst>, $t); + test_abi_compatible!(result_ok_zst, Result<Zst, $t>, $t); + test_abi_compatible!(result_err_arr, Result<$t, [i8; 0]>, $t); + test_abi_compatible!(result_ok_arr, Result<[i8; 0], $t>, $t); + } + } +} + +test_nonnull!(ref_, &i32); +test_nonnull!(mut_, &mut i32); +test_nonnull!(ref_unsized, &[i32]); +test_nonnull!(mut_unsized, &mut [i32]); +test_nonnull!(fn_, fn()); +test_nonnull!(nonnull, NonNull<i32>); +test_nonnull!(nonnull_unsized, NonNull<dyn std::fmt::Debug>); +test_nonnull!(non_zero, NonZeroI32); + +fn main() {} diff --git a/tests/ui/abi/debug.rs b/tests/ui/abi/debug.rs index 13464be275e..ac37d7b6bff 100644 --- a/tests/ui/abi/debug.rs +++ b/tests/ui/abi/debug.rs @@ -4,20 +4,51 @@ // normalize-stderr-test "(valid_range): 0\.\.=(4294967295|18446744073709551615)" -> "$1: $$FULL" // This pattern is prepared for when we account for alignment in the niche. // normalize-stderr-test "(valid_range): [1-9]\.\.=(429496729[0-9]|1844674407370955161[0-9])" -> "$1: $$NON_NULL" +// normalize-stderr-test "Leaf\(0x0*20\)" -> "Leaf(0x0...20)" // Some attributes are only computed for release builds: // compile-flags: -O #![feature(rustc_attrs)] #![crate_type = "lib"] +struct S(u16); + #[rustc_abi(debug)] fn test(_x: u8) -> bool { true } //~ ERROR: fn_abi +#[rustc_abi(debug)] +type TestFnPtr = fn(bool) -> u8; //~ ERROR: fn_abi #[rustc_abi(debug)] fn test_generic<T>(_x: *const T) { } //~ ERROR: fn_abi -struct S(u16); +#[rustc_abi(debug)] +const C: () = (); //~ ERROR: can only be applied to + +impl S { + #[rustc_abi(debug)] + const C: () = (); //~ ERROR: can only be applied to +} + impl S { #[rustc_abi(debug)] fn assoc_test(&self) { } //~ ERROR: fn_abi } + +#[rustc_abi(assert_eq)] +type TestAbiEq = (fn(bool), fn(bool)); + +#[rustc_abi(assert_eq)] +type TestAbiNe = (fn(u8), fn(u32)); //~ ERROR: ABIs are not compatible + +#[rustc_abi(assert_eq)] +type TestAbiNeLarger = (fn([u8; 32]), fn([u32; 32])); //~ ERROR: ABIs are not compatible + +#[rustc_abi(assert_eq)] +type TestAbiNeFloat = (fn(f32), fn(u32)); //~ ERROR: ABIs are not compatible + +// Sign matters on some targets (such as s390x), so let's make sure we never accept this. +#[rustc_abi(assert_eq)] +type TestAbiNeSign = (fn(i32), fn(u32)); //~ ERROR: ABIs are not compatible + +#[rustc_abi(assert_eq)] +type TestAbiEqNonsense = (fn((str, str)), fn((str, str))); //~ ERROR: cannot be known at compilation time diff --git a/tests/ui/abi/debug.stderr b/tests/ui/abi/debug.stderr index 4f4ee3de4b8..f56f5c525ab 100644 --- a/tests/ui/abi/debug.stderr +++ b/tests/ui/abi/debug.stderr @@ -1,4 +1,4 @@ -error: fn_abi_of_instance(test) = FnAbi { +error: fn_abi_of(test) = FnAbi { args: [ ArgAbi { layout: TyAndLayout { @@ -87,16 +87,110 @@ error: fn_abi_of_instance(test) = FnAbi { conv: Rust, can_unwind: $SOME_BOOL, } - --> $DIR/debug.rs:13:1 + --> $DIR/debug.rs:16:1 | LL | fn test(_x: u8) -> bool { true } | ^^^^^^^^^^^^^^^^^^^^^^^ -error: fn_abi_of_instance(test_generic) = FnAbi { +error: fn_abi_of(TestFnPtr) = FnAbi { args: [ ArgAbi { layout: TyAndLayout { - ty: *const T, + ty: bool, + layout: Layout { + size: Size(1 bytes), + align: AbiAndPrefAlign { + abi: $SOME_ALIGN, + pref: $SOME_ALIGN, + }, + abi: Scalar( + Initialized { + value: Int( + I8, + false, + ), + valid_range: 0..=1, + }, + ), + fields: Primitive, + largest_niche: Some( + Niche { + offset: Size(0 bytes), + value: Int( + I8, + false, + ), + valid_range: 0..=1, + }, + ), + variants: Single { + index: 0, + }, + max_repr_align: None, + unadjusted_abi_align: $SOME_ALIGN, + }, + }, + mode: Direct( + ArgAttributes { + regular: NoUndef, + arg_ext: Zext, + pointee_size: Size(0 bytes), + pointee_align: None, + }, + ), + }, + ], + ret: ArgAbi { + layout: TyAndLayout { + ty: u8, + layout: Layout { + size: Size(1 bytes), + align: AbiAndPrefAlign { + abi: $SOME_ALIGN, + pref: $SOME_ALIGN, + }, + abi: Scalar( + Initialized { + value: Int( + I8, + false, + ), + valid_range: 0..=255, + }, + ), + fields: Primitive, + largest_niche: None, + variants: Single { + index: 0, + }, + max_repr_align: None, + unadjusted_abi_align: $SOME_ALIGN, + }, + }, + mode: Direct( + ArgAttributes { + regular: NoUndef, + arg_ext: None, + pointee_size: Size(0 bytes), + pointee_align: None, + }, + ), + }, + c_variadic: false, + fixed_count: 1, + conv: Rust, + can_unwind: $SOME_BOOL, + } + --> $DIR/debug.rs:19:1 + | +LL | type TestFnPtr = fn(bool) -> u8; + | ^^^^^^^^^^^^^^ + +error: fn_abi_of(test_generic) = FnAbi { + args: [ + ArgAbi { + layout: TyAndLayout { + ty: *const T/#0, layout: Layout { size: $SOME_SIZE, align: AbiAndPrefAlign { @@ -163,16 +257,620 @@ error: fn_abi_of_instance(test_generic) = FnAbi { conv: Rust, can_unwind: $SOME_BOOL, } - --> $DIR/debug.rs:17:1 + --> $DIR/debug.rs:22:1 | LL | fn test_generic<T>(_x: *const T) { } | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ -error: fn_abi_of_instance(assoc_test) = FnAbi { +error: `#[rustc_abi]` can only be applied to function items, type aliases, and associated functions + --> $DIR/debug.rs:25:1 + | +LL | const C: () = (); + | ^^^^^^^^^^^ + +error: ABIs are not compatible + left ABI = FnAbi { + args: [ + ArgAbi { + layout: TyAndLayout { + ty: u8, + layout: Layout { + size: Size(1 bytes), + align: AbiAndPrefAlign { + abi: $SOME_ALIGN, + pref: $SOME_ALIGN, + }, + abi: Scalar( + Initialized { + value: Int( + I8, + false, + ), + valid_range: 0..=255, + }, + ), + fields: Primitive, + largest_niche: None, + variants: Single { + index: 0, + }, + max_repr_align: None, + unadjusted_abi_align: $SOME_ALIGN, + }, + }, + mode: Direct( + ArgAttributes { + regular: NoUndef, + arg_ext: None, + pointee_size: Size(0 bytes), + pointee_align: None, + }, + ), + }, + ], + ret: ArgAbi { + layout: TyAndLayout { + ty: (), + layout: Layout { + size: Size(0 bytes), + align: AbiAndPrefAlign { + abi: $SOME_ALIGN, + pref: $SOME_ALIGN, + }, + abi: Aggregate { + sized: true, + }, + fields: Arbitrary { + offsets: [], + memory_index: [], + }, + largest_niche: None, + variants: Single { + index: 0, + }, + max_repr_align: None, + unadjusted_abi_align: $SOME_ALIGN, + }, + }, + mode: Ignore, + }, + c_variadic: false, + fixed_count: 1, + conv: Rust, + can_unwind: $SOME_BOOL, + } + right ABI = FnAbi { + args: [ + ArgAbi { + layout: TyAndLayout { + ty: u32, + layout: Layout { + size: $SOME_SIZE, + align: AbiAndPrefAlign { + abi: $SOME_ALIGN, + pref: $SOME_ALIGN, + }, + abi: Scalar( + Initialized { + value: Int( + I32, + false, + ), + valid_range: $FULL, + }, + ), + fields: Primitive, + largest_niche: None, + variants: Single { + index: 0, + }, + max_repr_align: None, + unadjusted_abi_align: $SOME_ALIGN, + }, + }, + mode: Direct( + ArgAttributes { + regular: NoUndef, + arg_ext: None, + pointee_size: Size(0 bytes), + pointee_align: None, + }, + ), + }, + ], + ret: ArgAbi { + layout: TyAndLayout { + ty: (), + layout: Layout { + size: Size(0 bytes), + align: AbiAndPrefAlign { + abi: $SOME_ALIGN, + pref: $SOME_ALIGN, + }, + abi: Aggregate { + sized: true, + }, + fields: Arbitrary { + offsets: [], + memory_index: [], + }, + largest_niche: None, + variants: Single { + index: 0, + }, + max_repr_align: None, + unadjusted_abi_align: $SOME_ALIGN, + }, + }, + mode: Ignore, + }, + c_variadic: false, + fixed_count: 1, + conv: Rust, + can_unwind: $SOME_BOOL, + } + --> $DIR/debug.rs:41:1 + | +LL | type TestAbiNe = (fn(u8), fn(u32)); + | ^^^^^^^^^^^^^^ + +error: ABIs are not compatible + left ABI = FnAbi { + args: [ + ArgAbi { + layout: TyAndLayout { + ty: [u8; Const { ty: usize, kind: Leaf(0x0...20) }], + layout: Layout { + size: Size(32 bytes), + align: AbiAndPrefAlign { + abi: $SOME_ALIGN, + pref: $SOME_ALIGN, + }, + abi: Aggregate { + sized: true, + }, + fields: Array { + stride: Size(1 bytes), + count: 32, + }, + largest_niche: None, + variants: Single { + index: 0, + }, + max_repr_align: None, + unadjusted_abi_align: $SOME_ALIGN, + }, + }, + mode: Indirect { + attrs: ArgAttributes { + regular: NoAlias | NoCapture | NonNull | NoUndef, + arg_ext: None, + pointee_size: Size(32 bytes), + pointee_align: Some( + Align(1 bytes), + ), + }, + extra_attrs: None, + on_stack: false, + }, + }, + ], + ret: ArgAbi { + layout: TyAndLayout { + ty: (), + layout: Layout { + size: Size(0 bytes), + align: AbiAndPrefAlign { + abi: $SOME_ALIGN, + pref: $SOME_ALIGN, + }, + abi: Aggregate { + sized: true, + }, + fields: Arbitrary { + offsets: [], + memory_index: [], + }, + largest_niche: None, + variants: Single { + index: 0, + }, + max_repr_align: None, + unadjusted_abi_align: $SOME_ALIGN, + }, + }, + mode: Ignore, + }, + c_variadic: false, + fixed_count: 1, + conv: Rust, + can_unwind: $SOME_BOOL, + } + right ABI = FnAbi { + args: [ + ArgAbi { + layout: TyAndLayout { + ty: [u32; Const { ty: usize, kind: Leaf(0x0...20) }], + layout: Layout { + size: Size(128 bytes), + align: AbiAndPrefAlign { + abi: $SOME_ALIGN, + pref: $SOME_ALIGN, + }, + abi: Aggregate { + sized: true, + }, + fields: Array { + stride: Size(4 bytes), + count: 32, + }, + largest_niche: None, + variants: Single { + index: 0, + }, + max_repr_align: None, + unadjusted_abi_align: $SOME_ALIGN, + }, + }, + mode: Indirect { + attrs: ArgAttributes { + regular: NoAlias | NoCapture | NonNull | NoUndef, + arg_ext: None, + pointee_size: Size(128 bytes), + pointee_align: Some( + Align(4 bytes), + ), + }, + extra_attrs: None, + on_stack: false, + }, + }, + ], + ret: ArgAbi { + layout: TyAndLayout { + ty: (), + layout: Layout { + size: Size(0 bytes), + align: AbiAndPrefAlign { + abi: $SOME_ALIGN, + pref: $SOME_ALIGN, + }, + abi: Aggregate { + sized: true, + }, + fields: Arbitrary { + offsets: [], + memory_index: [], + }, + largest_niche: None, + variants: Single { + index: 0, + }, + max_repr_align: None, + unadjusted_abi_align: $SOME_ALIGN, + }, + }, + mode: Ignore, + }, + c_variadic: false, + fixed_count: 1, + conv: Rust, + can_unwind: $SOME_BOOL, + } + --> $DIR/debug.rs:44:1 + | +LL | type TestAbiNeLarger = (fn([u8; 32]), fn([u32; 32])); + | ^^^^^^^^^^^^^^^^^^^^ + +error: ABIs are not compatible + left ABI = FnAbi { + args: [ + ArgAbi { + layout: TyAndLayout { + ty: f32, + layout: Layout { + size: $SOME_SIZE, + align: AbiAndPrefAlign { + abi: $SOME_ALIGN, + pref: $SOME_ALIGN, + }, + abi: Scalar( + Initialized { + value: F32, + valid_range: $FULL, + }, + ), + fields: Primitive, + largest_niche: None, + variants: Single { + index: 0, + }, + max_repr_align: None, + unadjusted_abi_align: $SOME_ALIGN, + }, + }, + mode: Direct( + ArgAttributes { + regular: NoUndef, + arg_ext: None, + pointee_size: Size(0 bytes), + pointee_align: None, + }, + ), + }, + ], + ret: ArgAbi { + layout: TyAndLayout { + ty: (), + layout: Layout { + size: Size(0 bytes), + align: AbiAndPrefAlign { + abi: $SOME_ALIGN, + pref: $SOME_ALIGN, + }, + abi: Aggregate { + sized: true, + }, + fields: Arbitrary { + offsets: [], + memory_index: [], + }, + largest_niche: None, + variants: Single { + index: 0, + }, + max_repr_align: None, + unadjusted_abi_align: $SOME_ALIGN, + }, + }, + mode: Ignore, + }, + c_variadic: false, + fixed_count: 1, + conv: Rust, + can_unwind: $SOME_BOOL, + } + right ABI = FnAbi { + args: [ + ArgAbi { + layout: TyAndLayout { + ty: u32, + layout: Layout { + size: $SOME_SIZE, + align: AbiAndPrefAlign { + abi: $SOME_ALIGN, + pref: $SOME_ALIGN, + }, + abi: Scalar( + Initialized { + value: Int( + I32, + false, + ), + valid_range: $FULL, + }, + ), + fields: Primitive, + largest_niche: None, + variants: Single { + index: 0, + }, + max_repr_align: None, + unadjusted_abi_align: $SOME_ALIGN, + }, + }, + mode: Direct( + ArgAttributes { + regular: NoUndef, + arg_ext: None, + pointee_size: Size(0 bytes), + pointee_align: None, + }, + ), + }, + ], + ret: ArgAbi { + layout: TyAndLayout { + ty: (), + layout: Layout { + size: Size(0 bytes), + align: AbiAndPrefAlign { + abi: $SOME_ALIGN, + pref: $SOME_ALIGN, + }, + abi: Aggregate { + sized: true, + }, + fields: Arbitrary { + offsets: [], + memory_index: [], + }, + largest_niche: None, + variants: Single { + index: 0, + }, + max_repr_align: None, + unadjusted_abi_align: $SOME_ALIGN, + }, + }, + mode: Ignore, + }, + c_variadic: false, + fixed_count: 1, + conv: Rust, + can_unwind: $SOME_BOOL, + } + --> $DIR/debug.rs:47:1 + | +LL | type TestAbiNeFloat = (fn(f32), fn(u32)); + | ^^^^^^^^^^^^^^^^^^^ + +error: ABIs are not compatible + left ABI = FnAbi { + args: [ + ArgAbi { + layout: TyAndLayout { + ty: i32, + layout: Layout { + size: $SOME_SIZE, + align: AbiAndPrefAlign { + abi: $SOME_ALIGN, + pref: $SOME_ALIGN, + }, + abi: Scalar( + Initialized { + value: Int( + I32, + true, + ), + valid_range: $FULL, + }, + ), + fields: Primitive, + largest_niche: None, + variants: Single { + index: 0, + }, + max_repr_align: None, + unadjusted_abi_align: $SOME_ALIGN, + }, + }, + mode: Direct( + ArgAttributes { + regular: NoUndef, + arg_ext: None, + pointee_size: Size(0 bytes), + pointee_align: None, + }, + ), + }, + ], + ret: ArgAbi { + layout: TyAndLayout { + ty: (), + layout: Layout { + size: Size(0 bytes), + align: AbiAndPrefAlign { + abi: $SOME_ALIGN, + pref: $SOME_ALIGN, + }, + abi: Aggregate { + sized: true, + }, + fields: Arbitrary { + offsets: [], + memory_index: [], + }, + largest_niche: None, + variants: Single { + index: 0, + }, + max_repr_align: None, + unadjusted_abi_align: $SOME_ALIGN, + }, + }, + mode: Ignore, + }, + c_variadic: false, + fixed_count: 1, + conv: Rust, + can_unwind: $SOME_BOOL, + } + right ABI = FnAbi { + args: [ + ArgAbi { + layout: TyAndLayout { + ty: u32, + layout: Layout { + size: $SOME_SIZE, + align: AbiAndPrefAlign { + abi: $SOME_ALIGN, + pref: $SOME_ALIGN, + }, + abi: Scalar( + Initialized { + value: Int( + I32, + false, + ), + valid_range: $FULL, + }, + ), + fields: Primitive, + largest_niche: None, + variants: Single { + index: 0, + }, + max_repr_align: None, + unadjusted_abi_align: $SOME_ALIGN, + }, + }, + mode: Direct( + ArgAttributes { + regular: NoUndef, + arg_ext: None, + pointee_size: Size(0 bytes), + pointee_align: None, + }, + ), + }, + ], + ret: ArgAbi { + layout: TyAndLayout { + ty: (), + layout: Layout { + size: Size(0 bytes), + align: AbiAndPrefAlign { + abi: $SOME_ALIGN, + pref: $SOME_ALIGN, + }, + abi: Aggregate { + sized: true, + }, + fields: Arbitrary { + offsets: [], + memory_index: [], + }, + largest_niche: None, + variants: Single { + index: 0, + }, + max_repr_align: None, + unadjusted_abi_align: $SOME_ALIGN, + }, + }, + mode: Ignore, + }, + c_variadic: false, + fixed_count: 1, + conv: Rust, + can_unwind: $SOME_BOOL, + } + --> $DIR/debug.rs:51:1 + | +LL | type TestAbiNeSign = (fn(i32), fn(u32)); + | ^^^^^^^^^^^^^^^^^^ + +error[E0277]: the size for values of type `str` cannot be known at compilation time + --> $DIR/debug.rs:54:46 + | +LL | type TestAbiEqNonsense = (fn((str, str)), fn((str, str))); + | ^^^^^^^^^^ doesn't have a size known at compile-time + | + = help: the trait `Sized` is not implemented for `str` + = note: only the last element of a tuple may have a dynamically sized type + +error: `#[rustc_abi]` can only be applied to function items, type aliases, and associated functions + --> $DIR/debug.rs:29:5 + | +LL | const C: () = (); + | ^^^^^^^^^^^ + +error: fn_abi_of(assoc_test) = FnAbi { args: [ ArgAbi { layout: TyAndLayout { - ty: &S, + ty: &ReErased Adt(S, []), layout: Layout { size: $SOME_SIZE, align: AbiAndPrefAlign { @@ -251,10 +949,11 @@ error: fn_abi_of_instance(assoc_test) = FnAbi { conv: Rust, can_unwind: $SOME_BOOL, } - --> $DIR/debug.rs:22:5 + --> $DIR/debug.rs:34:5 | LL | fn assoc_test(&self) { } | ^^^^^^^^^^^^^^^^^^^^ -error: aborting due to 3 previous errors +error: aborting due to 11 previous errors +For more information about this error, try `rustc --explain E0277`. diff --git a/tests/ui/associated-consts/associated-const-array-len.stderr b/tests/ui/associated-consts/associated-const-array-len.stderr index 0e0dec35b53..e3db45810fd 100644 --- a/tests/ui/associated-consts/associated-const-array-len.stderr +++ b/tests/ui/associated-consts/associated-const-array-len.stderr @@ -3,6 +3,12 @@ error[E0277]: the trait bound `i32: Foo` is not satisfied | LL | const X: [i32; <i32 as Foo>::ID] = [0, 1, 2]; | ^^^ the trait `Foo` is not implemented for `i32` + | +help: this trait has no implementations, consider adding one + --> $DIR/associated-const-array-len.rs:1:1 + | +LL | trait Foo { + | ^^^^^^^^^ error: aborting due to previous error diff --git a/tests/ui/associated-consts/issue-105330.stderr b/tests/ui/associated-consts/issue-105330.stderr index e9fe3a5e514..927422fa8dc 100644 --- a/tests/ui/associated-consts/issue-105330.stderr +++ b/tests/ui/associated-consts/issue-105330.stderr @@ -51,6 +51,11 @@ error[E0277]: the trait bound `Demo: TraitWAssocConst` is not satisfied LL | foo::<Demo>()(); | ^^^^ the trait `TraitWAssocConst` is not implemented for `Demo` | +help: this trait has no implementations, consider adding one + --> $DIR/issue-105330.rs:1:1 + | +LL | pub trait TraitWAssocConst { + | ^^^^^^^^^^^^^^^^^^^^^^^^^^ note: required by a bound in `foo` --> $DIR/issue-105330.rs:11:11 | @@ -87,6 +92,11 @@ error[E0277]: the trait bound `Demo: TraitWAssocConst` is not satisfied LL | foo::<Demo>(); | ^^^^ the trait `TraitWAssocConst` is not implemented for `Demo` | +help: this trait has no implementations, consider adding one + --> $DIR/issue-105330.rs:1:1 + | +LL | pub trait TraitWAssocConst { + | ^^^^^^^^^^^^^^^^^^^^^^^^^^ note: required by a bound in `foo` --> $DIR/issue-105330.rs:11:11 | diff --git a/tests/ui/associated-type-bounds/return-type-notation/basic.without.stderr b/tests/ui/associated-type-bounds/return-type-notation/basic.without.stderr index c2da4f57696..edce1045e24 100644 --- a/tests/ui/associated-type-bounds/return-type-notation/basic.without.stderr +++ b/tests/ui/associated-type-bounds/return-type-notation/basic.without.stderr @@ -13,12 +13,12 @@ error: future cannot be sent between threads safely LL | is_send(foo::<T>()); | ^^^^^^^^^^ future returned by `foo` is not `Send` | - = help: within `impl Future<Output = Result<(), ()>>`, the trait `Send` is not implemented for `impl Future<Output = Result<(), ()>>` + = help: within `impl Future<Output = Result<(), ()>>`, the trait `Send` is not implemented for `impl Future<Output = Result<(), ()>> { <T as Foo>::method() }` note: future is not `Send` as it awaits another future which is not `Send` --> $DIR/basic.rs:13:5 | LL | T::method().await?; - | ^^^^^^^^^^^ await occurs here on type `impl Future<Output = Result<(), ()>>`, which is not `Send` + | ^^^^^^^^^^^ await occurs here on type `impl Future<Output = Result<(), ()>> { <T as Foo>::method() }`, which is not `Send` note: required by a bound in `is_send` --> $DIR/basic.rs:17:20 | diff --git a/tests/ui/associated-types/associated-types-ICE-when-projecting-out-of-err.stderr b/tests/ui/associated-types/associated-types-ICE-when-projecting-out-of-err.stderr index 8c3463a2832..fbc4ccd4cf4 100644 --- a/tests/ui/associated-types/associated-types-ICE-when-projecting-out-of-err.stderr +++ b/tests/ui/associated-types/associated-types-ICE-when-projecting-out-of-err.stderr @@ -3,6 +3,12 @@ error[E0277]: the trait bound `(): Add<A>` is not satisfied | LL | r = r + a; | ^ the trait `Add<A>` is not implemented for `()` + | +help: this trait has no implementations, consider adding one + --> $DIR/associated-types-ICE-when-projecting-out-of-err.rs:15:1 + | +LL | trait Add<RHS=Self> { + | ^^^^^^^^^^^^^^^^^^^ error: aborting due to previous error diff --git a/tests/ui/associated-types/associated-types-no-suitable-supertrait.stderr b/tests/ui/associated-types/associated-types-no-suitable-supertrait.stderr index bd3ee2abd2c..b3f2e16ba0d 100644 --- a/tests/ui/associated-types/associated-types-no-suitable-supertrait.stderr +++ b/tests/ui/associated-types/associated-types-no-suitable-supertrait.stderr @@ -3,6 +3,12 @@ error[E0277]: the trait bound `(T, U): Get` is not satisfied | LL | fn uhoh<U:Get>(&self, foo: U, bar: <(T, U) as Get>::Value) {} | ^^^^^^^^^^^^^^^^^^^^^^ the trait `Get` is not implemented for `(T, U)` + | +help: this trait has no implementations, consider adding one + --> $DIR/associated-types-no-suitable-supertrait.rs:12:1 + | +LL | trait Get { + | ^^^^^^^^^ error[E0277]: the trait bound `Self: Get` is not satisfied --> $DIR/associated-types-no-suitable-supertrait.rs:17:40 diff --git a/tests/ui/associated-types/defaults-suitability.stderr b/tests/ui/associated-types/defaults-suitability.stderr index 4b2094691f8..0a8ad0f89e2 100644 --- a/tests/ui/associated-types/defaults-suitability.stderr +++ b/tests/ui/associated-types/defaults-suitability.stderr @@ -58,6 +58,11 @@ error[E0277]: the trait bound `(): Foo<Self>` is not satisfied LL | type Assoc: Foo<Self> = (); | ^^ the trait `Foo<Self>` is not implemented for `()` | +help: this trait has no implementations, consider adding one + --> $DIR/defaults-suitability.rs:27:1 + | +LL | trait Foo<T> { + | ^^^^^^^^^^^^ note: required by a bound in `Bar::Assoc` --> $DIR/defaults-suitability.rs:34:17 | diff --git a/tests/ui/associated-types/issue-23595-2.stderr b/tests/ui/associated-types/issue-23595-2.stderr index dded673f6ee..73effa9f955 100644 --- a/tests/ui/associated-types/issue-23595-2.stderr +++ b/tests/ui/associated-types/issue-23595-2.stderr @@ -2,7 +2,7 @@ error[E0220]: associated type `anything_here_kills_it` not found for `Self` --> $DIR/issue-23595-2.rs:6:22 | LL | type B = C<Self::anything_here_kills_it>; - | ^^^^^^^^^^^^^^^^^^^^^^ associated type `anything_here_kills_it` not found + | ^^^^^^^^^^^^^^^^^^^^^^ help: `Self` has the following associated type: `B` error: aborting due to previous error diff --git a/tests/ui/associated-types/issue-59324.stderr b/tests/ui/associated-types/issue-59324.stderr index a84b599b52b..266e22d4726 100644 --- a/tests/ui/associated-types/issue-59324.stderr +++ b/tests/ui/associated-types/issue-59324.stderr @@ -48,6 +48,12 @@ error[E0277]: the trait bound `(): Foo` is not satisfied | LL | fn with_factory<H>(factory: dyn ThriftService<()>) {} | ^^^^^^^^^^^^^^^^^^^^^ the trait `Foo` is not implemented for `()` + | +help: this trait has no implementations, consider adding one + --> $DIR/issue-59324.rs:3:1 + | +LL | pub trait Foo: NotFoo { + | ^^^^^^^^^^^^^^^^^^^^^ error[E0277]: the trait bound `Bug: Foo` is not satisfied --> $DIR/issue-59324.rs:19:10 diff --git a/tests/ui/associated-types/issue-64855.stderr b/tests/ui/associated-types/issue-64855.stderr index 6ad795c1117..f1016f0e3a1 100644 --- a/tests/ui/associated-types/issue-64855.stderr +++ b/tests/ui/associated-types/issue-64855.stderr @@ -3,6 +3,12 @@ error[E0277]: the trait bound `Bar<T>: Foo` is not satisfied | LL | pub struct Bar<T>(<Self as Foo>::Type) where Self: ; | ^^^^^^^^^^^^^^^^^^^ the trait `Foo` is not implemented for `Bar<T>` + | +help: this trait has no implementations, consider adding one + --> $DIR/issue-64855.rs:1:1 + | +LL | pub trait Foo { + | ^^^^^^^^^^^^^ error: aborting due to previous error diff --git a/tests/ui/associated-types/issue-85103-layout-debug.rs b/tests/ui/associated-types/issue-85103-layout-debug.rs new file mode 100644 index 00000000000..77c9876ffa5 --- /dev/null +++ b/tests/ui/associated-types/issue-85103-layout-debug.rs @@ -0,0 +1,9 @@ +#![feature(rustc_attrs)] + +use std::borrow::Cow; + +#[rustc_layout(debug)] +type Edges<'a, E> = Cow<'a, [E]>; +//~^ the trait bound `[E]: ToOwned` is not satisfied + +fn main() {} diff --git a/tests/ui/associated-types/issue-85103-layout-debug.stderr b/tests/ui/associated-types/issue-85103-layout-debug.stderr new file mode 100644 index 00000000000..0bdea10ba47 --- /dev/null +++ b/tests/ui/associated-types/issue-85103-layout-debug.stderr @@ -0,0 +1,16 @@ +error[E0277]: the trait bound `[E]: ToOwned` is not satisfied + --> $DIR/issue-85103-layout-debug.rs:6:21 + | +LL | type Edges<'a, E> = Cow<'a, [E]>; + | ^^^^^^^^^^^^ the trait `ToOwned` is not implemented for `[E]` + | +note: required by a bound in `Cow` + --> $SRC_DIR/alloc/src/borrow.rs:LL:COL +help: consider introducing a `where` clause, but there might be an alternative better way to express this requirement + | +LL | type Edges<'a, E> where [E]: ToOwned = Cow<'a, [E]>; + | ++++++++++++++++++ + +error: aborting due to previous error + +For more information about this error, try `rustc --explain E0277`. diff --git a/tests/ui/associated-types/issue-85103.rs b/tests/ui/associated-types/issue-85103.rs deleted file mode 100644 index 9c6a419e9f7..00000000000 --- a/tests/ui/associated-types/issue-85103.rs +++ /dev/null @@ -1,9 +0,0 @@ -#![feature(rustc_attrs)] - -use std::borrow::Cow; - -#[rustc_layout(debug)] -type Edges<'a, E> = Cow<'a, [E]>; -//~^ 6:1: 6:18: unable to determine layout for `<[E] as ToOwned>::Owned` because `<[E] as ToOwned>::Owned` cannot be normalized - -fn main() {} diff --git a/tests/ui/associated-types/issue-85103.stderr b/tests/ui/associated-types/issue-85103.stderr deleted file mode 100644 index 17f7148074c..00000000000 --- a/tests/ui/associated-types/issue-85103.stderr +++ /dev/null @@ -1,8 +0,0 @@ -error: unable to determine layout for `<[E] as ToOwned>::Owned` because `<[E] as ToOwned>::Owned` cannot be normalized - --> $DIR/issue-85103.rs:6:1 - | -LL | type Edges<'a, E> = Cow<'a, [E]>; - | ^^^^^^^^^^^^^^^^^ - -error: aborting due to previous error - diff --git a/tests/ui/associated-types/point-at-type-on-obligation-failure-2.stderr b/tests/ui/associated-types/point-at-type-on-obligation-failure-2.stderr index 3b4689e08cc..056d9201b4a 100644 --- a/tests/ui/associated-types/point-at-type-on-obligation-failure-2.stderr +++ b/tests/ui/associated-types/point-at-type-on-obligation-failure-2.stderr @@ -4,6 +4,11 @@ error[E0277]: the trait bound `bool: Bar` is not satisfied LL | type Assoc = bool; | ^^^^ the trait `Bar` is not implemented for `bool` | +help: this trait has no implementations, consider adding one + --> $DIR/point-at-type-on-obligation-failure-2.rs:1:1 + | +LL | trait Bar {} + | ^^^^^^^^^ note: required by a bound in `Foo::Assoc` --> $DIR/point-at-type-on-obligation-failure-2.rs:4:17 | @@ -16,6 +21,11 @@ error[E0277]: the trait bound `bool: Bar` is not satisfied LL | type Assoc = bool; | ^^^^ the trait `Bar` is not implemented for `bool` | +help: this trait has no implementations, consider adding one + --> $DIR/point-at-type-on-obligation-failure-2.rs:1:1 + | +LL | trait Bar {} + | ^^^^^^^^^ note: required by a bound in `Baz::Assoc` --> $DIR/point-at-type-on-obligation-failure-2.rs:13:18 | @@ -31,6 +41,11 @@ error[E0277]: the trait bound `bool: Bar` is not satisfied LL | type Assoc = bool; | ^^^^ the trait `Bar` is not implemented for `bool` | +help: this trait has no implementations, consider adding one + --> $DIR/point-at-type-on-obligation-failure-2.rs:1:1 + | +LL | trait Bar {} + | ^^^^^^^^^ note: required by a bound in `Bat::Assoc` --> $DIR/point-at-type-on-obligation-failure-2.rs:24:27 | diff --git a/tests/ui/async-await/async-is-unwindsafe.stderr b/tests/ui/async-await/async-is-unwindsafe.stderr index 5d29325c827..c855e902ba9 100644 --- a/tests/ui/async-await/async-is-unwindsafe.stderr +++ b/tests/ui/async-await/async-is-unwindsafe.stderr @@ -15,7 +15,7 @@ LL | | }); | within this `[async block@$DIR/async-is-unwindsafe.rs:12:19: 29:6]` | = help: within `[async block@$DIR/async-is-unwindsafe.rs:12:19: 29:6]`, the trait `UnwindSafe` is not implemented for `&mut Context<'_>` - = note: `UnwindSafe` is implemented for `&std::task::Context<'_>`, but not for `&mut std::task::Context<'_>` + = note: `UnwindSafe` is implemented for `&Context<'_>`, but not for `&mut Context<'_>` note: future does not implement `UnwindSafe` as this value is used across an await --> $DIR/async-is-unwindsafe.rs:25:18 | diff --git a/tests/ui/async-await/in-trait/async-example-desugared-extra.rs b/tests/ui/async-await/in-trait/async-example-desugared-extra.rs index 81e1e59a362..3505690f1ec 100644 --- a/tests/ui/async-await/in-trait/async-example-desugared-extra.rs +++ b/tests/ui/async-await/in-trait/async-example-desugared-extra.rs @@ -2,14 +2,14 @@ // edition: 2021 #![feature(async_fn_in_trait)] -#![feature(return_position_impl_trait_in_trait)] +#![feature(return_position_impl_trait_in_trait, lint_reasons)] #![allow(incomplete_features)] use std::future::Future; use std::pin::Pin; use std::task::Poll; -trait MyTrait { +pub trait MyTrait { async fn foo(&self) -> i32; } @@ -27,8 +27,7 @@ impl Future for MyFuture { } impl MyTrait for i32 { - // FIXME: this should eventually require `#[refine]` to compile, because it also provides - // `Clone`. + #[expect(refining_impl_trait)] fn foo(&self) -> impl Future<Output = i32> + Clone { MyFuture(*self) } diff --git a/tests/ui/async-await/in-trait/async-example-desugared.rs b/tests/ui/async-await/in-trait/async-example-desugared.rs index fb92ec78674..0a5023176fe 100644 --- a/tests/ui/async-await/in-trait/async-example-desugared.rs +++ b/tests/ui/async-await/in-trait/async-example-desugared.rs @@ -12,7 +12,7 @@ trait MyTrait { } impl MyTrait for i32 { - fn foo(&self) -> impl Future<Output = i32> + '_ { + fn foo(&self) -> impl Future<Output = i32> { async { *self } } } diff --git a/tests/ui/async-await/return-type-notation/normalizing-self-auto-trait-issue-109924.current.stderr b/tests/ui/async-await/return-type-notation/normalizing-self-auto-trait-issue-109924.current.stderr new file mode 100644 index 00000000000..3b63ec45804 --- /dev/null +++ b/tests/ui/async-await/return-type-notation/normalizing-self-auto-trait-issue-109924.current.stderr @@ -0,0 +1,27 @@ +warning: the feature `return_type_notation` is incomplete and may not be safe to use and/or cause compiler crashes + --> $DIR/normalizing-self-auto-trait-issue-109924.rs:8:12 + | +LL | #![feature(return_type_notation)] + | ^^^^^^^^^^^^^^^^^^^^ + | + = note: see issue #109417 <https://github.com/rust-lang/rust/issues/109417> for more information + = note: `#[warn(incomplete_features)]` on by default + +error[E0277]: `impl Future<Output = ()> { <_ as Foo>::bar() }` cannot be sent between threads safely + --> $DIR/normalizing-self-auto-trait-issue-109924.rs:23:11 + | +LL | build(Bar); + | ----- ^^^ `impl Future<Output = ()> { <_ as Foo>::bar() }` cannot be sent between threads safely + | | + | required by a bound introduced by this call + | + = help: the trait `for<'a> Send` is not implemented for `impl Future<Output = ()> { <_ as Foo>::bar() }` +note: required by a bound in `build` + --> $DIR/normalizing-self-auto-trait-issue-109924.rs:20:39 + | +LL | fn build<T>(_: T) where T: Foo<bar(): Send> {} + | ^^^^ required by this bound in `build` + +error: aborting due to previous error; 1 warning emitted + +For more information about this error, try `rustc --explain E0277`. diff --git a/tests/ui/async-await/return-type-notation/normalizing-self-auto-trait-issue-109924.next.stderr b/tests/ui/async-await/return-type-notation/normalizing-self-auto-trait-issue-109924.next.stderr new file mode 100644 index 00000000000..6fab7178767 --- /dev/null +++ b/tests/ui/async-await/return-type-notation/normalizing-self-auto-trait-issue-109924.next.stderr @@ -0,0 +1,11 @@ +warning: the feature `return_type_notation` is incomplete and may not be safe to use and/or cause compiler crashes + --> $DIR/normalizing-self-auto-trait-issue-109924.rs:8:12 + | +LL | #![feature(return_type_notation)] + | ^^^^^^^^^^^^^^^^^^^^ + | + = note: see issue #109417 <https://github.com/rust-lang/rust/issues/109417> for more information + = note: `#[warn(incomplete_features)]` on by default + +warning: 1 warning emitted + diff --git a/tests/ui/async-await/return-type-notation/normalizing-self-auto-trait-issue-109924.rs b/tests/ui/async-await/return-type-notation/normalizing-self-auto-trait-issue-109924.rs new file mode 100644 index 00000000000..b2cd9707db9 --- /dev/null +++ b/tests/ui/async-await/return-type-notation/normalizing-self-auto-trait-issue-109924.rs @@ -0,0 +1,24 @@ +// revisions: current next +//[current] known-bug: #109924 +//[next] check-pass +//[next] compile-flags: -Ztrait-solver=next +// edition:2021 + +#![feature(async_fn_in_trait)] +#![feature(return_type_notation)] +//[next]~^ WARN the feature `return_type_notation` is incomplete + +trait Foo { + async fn bar(&self); +} + +struct Bar; +impl Foo for Bar { + async fn bar(&self) {} +} + +fn build<T>(_: T) where T: Foo<bar(): Send> {} + +fn main() { + build(Bar); +} diff --git a/tests/ui/borrowck/issue-114374-invalid-help-fmt-args.rs b/tests/ui/borrowck/issue-114374-invalid-help-fmt-args.rs new file mode 100644 index 00000000000..4a6c2f9ed06 --- /dev/null +++ b/tests/ui/borrowck/issue-114374-invalid-help-fmt-args.rs @@ -0,0 +1,16 @@ +#![allow(dead_code)] + +fn bar<'a>(_: std::fmt::Arguments<'a>) {} +fn main() { + let x = format_args!("a {} {} {}.", 1, format_args!("b{}!", 2), 3); + //~^ ERROR temporary value dropped while borrowed + + bar(x); + + let foo = format_args!("{}", "hi"); + //~^ ERROR temporary value dropped while borrowed + bar(foo); + + let foo = format_args!("hi"); // no placeholder in arguments, so no error + bar(foo); +} diff --git a/tests/ui/borrowck/issue-114374-invalid-help-fmt-args.stderr b/tests/ui/borrowck/issue-114374-invalid-help-fmt-args.stderr new file mode 100644 index 00000000000..8221505b100 --- /dev/null +++ b/tests/ui/borrowck/issue-114374-invalid-help-fmt-args.stderr @@ -0,0 +1,33 @@ +error[E0716]: temporary value dropped while borrowed + --> $DIR/issue-114374-invalid-help-fmt-args.rs:5:13 + | +LL | let x = format_args!("a {} {} {}.", 1, format_args!("b{}!", 2), 3); + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^- temporary value is freed at the end of this statement + | | + | creates a temporary value which is freed while still in use +... +LL | bar(x); + | - borrow later used here + | + = note: the result of `format_args!` can only be assigned directly if no placeholders in it's arguments are used + = note: to learn more, visit <https://doc.rust-lang.org/std/macro.format_args.html> + = note: this error originates in the macro `format_args` (in Nightly builds, run with -Z macro-backtrace for more info) + +error[E0716]: temporary value dropped while borrowed + --> $DIR/issue-114374-invalid-help-fmt-args.rs:10:15 + | +LL | let foo = format_args!("{}", "hi"); + | ^^^^^^^^^^^^^^^^^^^^^^^^- temporary value is freed at the end of this statement + | | + | creates a temporary value which is freed while still in use +LL | +LL | bar(foo); + | --- borrow later used here + | + = note: the result of `format_args!` can only be assigned directly if no placeholders in it's arguments are used + = note: to learn more, visit <https://doc.rust-lang.org/std/macro.format_args.html> + = note: this error originates in the macro `format_args` (in Nightly builds, run with -Z macro-backtrace for more info) + +error: aborting due to 2 previous errors + +For more information about this error, try `rustc --explain E0716`. diff --git a/tests/ui/borrowck/issue-115259-suggest-iter-mut.fixed b/tests/ui/borrowck/issue-115259-suggest-iter-mut.fixed new file mode 100644 index 00000000000..4653fe7375d --- /dev/null +++ b/tests/ui/borrowck/issue-115259-suggest-iter-mut.fixed @@ -0,0 +1,20 @@ +// run-rustfix +#![allow(unused_mut)] +#![allow(dead_code)] + +pub trait Layer { + fn process(&mut self) -> u32; +} + +pub struct State { + layers: Vec<Box<dyn Layer>>, +} + +impl State { + pub fn process(&mut self) -> u32 { + self.layers.iter_mut().fold(0, |result, mut layer| result + layer.process()) + //~^ ERROR cannot borrow `**layer` as mutable, as it is behind a `&` reference + } +} + +fn main() {} diff --git a/tests/ui/borrowck/issue-115259-suggest-iter-mut.rs b/tests/ui/borrowck/issue-115259-suggest-iter-mut.rs new file mode 100644 index 00000000000..e0f6ab1321f --- /dev/null +++ b/tests/ui/borrowck/issue-115259-suggest-iter-mut.rs @@ -0,0 +1,20 @@ +// run-rustfix +#![allow(unused_mut)] +#![allow(dead_code)] + +pub trait Layer { + fn process(&mut self) -> u32; +} + +pub struct State { + layers: Vec<Box<dyn Layer>>, +} + +impl State { + pub fn process(&mut self) -> u32 { + self.layers.iter().fold(0, |result, mut layer| result + layer.process()) + //~^ ERROR cannot borrow `**layer` as mutable, as it is behind a `&` reference + } +} + +fn main() {} diff --git a/tests/ui/borrowck/issue-115259-suggest-iter-mut.stderr b/tests/ui/borrowck/issue-115259-suggest-iter-mut.stderr new file mode 100644 index 00000000000..7e0fc2cf298 --- /dev/null +++ b/tests/ui/borrowck/issue-115259-suggest-iter-mut.stderr @@ -0,0 +1,16 @@ +error[E0596]: cannot borrow `**layer` as mutable, as it is behind a `&` reference + --> $DIR/issue-115259-suggest-iter-mut.rs:15:65 + | +LL | self.layers.iter().fold(0, |result, mut layer| result + layer.process()) + | --------- ^^^^^ `layer` is a `&` reference, so the data it refers to cannot be borrowed as mutable + | | + | consider changing this binding's type to be: `&mut Box<dyn Layer>` + | +help: you may want to use `iter_mut` here + | +LL | self.layers.iter_mut().fold(0, |result, mut layer| result + layer.process()) + | ~~~~~~~~ + +error: aborting due to previous error + +For more information about this error, try `rustc --explain E0596`. diff --git a/tests/ui/borrowck/issue-62387-suggest-iter-mut-2.fixed b/tests/ui/borrowck/issue-62387-suggest-iter-mut-2.fixed new file mode 100644 index 00000000000..f02374d8e11 --- /dev/null +++ b/tests/ui/borrowck/issue-62387-suggest-iter-mut-2.fixed @@ -0,0 +1,36 @@ +// run-rustfix +#![allow(unused_mut)] +#![allow(dead_code)] +use std::path::PathBuf; + +#[derive(Clone)] +struct Container { + things: Vec<PathBuf>, +} + +impl Container { + fn things(&mut self) -> &[PathBuf] { + &self.things + } +} + +// contains containers +struct ContainerContainer { + contained: Vec<Container>, +} + +impl ContainerContainer { + fn contained(&self) -> &[Container] { + &self.contained + } + + fn all_the_things(&mut self) -> &[PathBuf] { + let mut vec = self.contained.clone(); + let _a = + vec.iter_mut().flat_map(|container| container.things()).cloned().collect::<Vec<PathBuf>>(); + //~^ ERROR cannot borrow `*container` as mutable, as it is behind a `&` reference + unimplemented!(); + } +} + +fn main() {} diff --git a/tests/ui/borrowck/issue-62387-suggest-iter-mut-2.rs b/tests/ui/borrowck/issue-62387-suggest-iter-mut-2.rs new file mode 100644 index 00000000000..2d0b837a946 --- /dev/null +++ b/tests/ui/borrowck/issue-62387-suggest-iter-mut-2.rs @@ -0,0 +1,36 @@ +// run-rustfix +#![allow(unused_mut)] +#![allow(dead_code)] +use std::path::PathBuf; + +#[derive(Clone)] +struct Container { + things: Vec<PathBuf>, +} + +impl Container { + fn things(&mut self) -> &[PathBuf] { + &self.things + } +} + +// contains containers +struct ContainerContainer { + contained: Vec<Container>, +} + +impl ContainerContainer { + fn contained(&self) -> &[Container] { + &self.contained + } + + fn all_the_things(&mut self) -> &[PathBuf] { + let mut vec = self.contained.clone(); + let _a = + vec.iter().flat_map(|container| container.things()).cloned().collect::<Vec<PathBuf>>(); + //~^ ERROR cannot borrow `*container` as mutable, as it is behind a `&` reference + unimplemented!(); + } +} + +fn main() {} diff --git a/tests/ui/borrowck/issue-62387-suggest-iter-mut-2.stderr b/tests/ui/borrowck/issue-62387-suggest-iter-mut-2.stderr new file mode 100644 index 00000000000..19f194100a1 --- /dev/null +++ b/tests/ui/borrowck/issue-62387-suggest-iter-mut-2.stderr @@ -0,0 +1,16 @@ +error[E0596]: cannot borrow `*container` as mutable, as it is behind a `&` reference + --> $DIR/issue-62387-suggest-iter-mut-2.rs:30:45 + | +LL | vec.iter().flat_map(|container| container.things()).cloned().collect::<Vec<PathBuf>>(); + | --------- ^^^^^^^^^ `container` is a `&` reference, so the data it refers to cannot be borrowed as mutable + | | + | consider changing this binding's type to be: `&mut Container` + | +help: you may want to use `iter_mut` here + | +LL | vec.iter_mut().flat_map(|container| container.things()).cloned().collect::<Vec<PathBuf>>(); + | ~~~~~~~~ + +error: aborting due to previous error + +For more information about this error, try `rustc --explain E0596`. diff --git a/tests/ui/borrowck/issue-62387-suggest-iter-mut.fixed b/tests/ui/borrowck/issue-62387-suggest-iter-mut.fixed new file mode 100644 index 00000000000..8bf2625de6d --- /dev/null +++ b/tests/ui/borrowck/issue-62387-suggest-iter-mut.fixed @@ -0,0 +1,30 @@ +// run-rustfix +#![allow(unused_mut)] +#![allow(dead_code)] + +#[derive(Debug)] +struct A { + a: i32, +} + +impl A { + fn double(&mut self) { + self.a += self.a + } +} + +fn baz() { + let mut v = [A { a: 4 }]; + v.iter_mut().for_each(|a| a.double()); + //~^ ERROR cannot borrow `*a` as mutable, as it is behind a `&` reference + println!("{:?}", v); +} + +fn bar() { + let mut v = [A { a: 4 }]; + v.iter_mut().rev().rev().for_each(|a| a.double()); + //~^ ERROR cannot borrow `*a` as mutable, as it is behind a `&` reference + println!("{:?}", v); +} + +fn main() {} diff --git a/tests/ui/borrowck/issue-62387-suggest-iter-mut.rs b/tests/ui/borrowck/issue-62387-suggest-iter-mut.rs new file mode 100644 index 00000000000..39bc30bf294 --- /dev/null +++ b/tests/ui/borrowck/issue-62387-suggest-iter-mut.rs @@ -0,0 +1,30 @@ +// run-rustfix +#![allow(unused_mut)] +#![allow(dead_code)] + +#[derive(Debug)] +struct A { + a: i32, +} + +impl A { + fn double(&mut self) { + self.a += self.a + } +} + +fn baz() { + let mut v = [A { a: 4 }]; + v.iter().for_each(|a| a.double()); + //~^ ERROR cannot borrow `*a` as mutable, as it is behind a `&` reference + println!("{:?}", v); +} + +fn bar() { + let mut v = [A { a: 4 }]; + v.iter().rev().rev().for_each(|a| a.double()); + //~^ ERROR cannot borrow `*a` as mutable, as it is behind a `&` reference + println!("{:?}", v); +} + +fn main() {} diff --git a/tests/ui/borrowck/issue-62387-suggest-iter-mut.stderr b/tests/ui/borrowck/issue-62387-suggest-iter-mut.stderr new file mode 100644 index 00000000000..fd58e433020 --- /dev/null +++ b/tests/ui/borrowck/issue-62387-suggest-iter-mut.stderr @@ -0,0 +1,29 @@ +error[E0596]: cannot borrow `*a` as mutable, as it is behind a `&` reference + --> $DIR/issue-62387-suggest-iter-mut.rs:18:27 + | +LL | v.iter().for_each(|a| a.double()); + | - ^ `a` is a `&` reference, so the data it refers to cannot be borrowed as mutable + | | + | consider changing this binding's type to be: `&mut A` + | +help: you may want to use `iter_mut` here + | +LL | v.iter_mut().for_each(|a| a.double()); + | ~~~~~~~~ + +error[E0596]: cannot borrow `*a` as mutable, as it is behind a `&` reference + --> $DIR/issue-62387-suggest-iter-mut.rs:25:39 + | +LL | v.iter().rev().rev().for_each(|a| a.double()); + | - ^ `a` is a `&` reference, so the data it refers to cannot be borrowed as mutable + | | + | consider changing this binding's type to be: `&mut A` + | +help: you may want to use `iter_mut` here + | +LL | v.iter_mut().rev().rev().for_each(|a| a.double()); + | ~~~~~~~~ + +error: aborting due to 2 previous errors + +For more information about this error, try `rustc --explain E0596`. diff --git a/tests/ui/coherence/coherence-unsafe-trait-object-impl.stderr b/tests/ui/coherence/coherence-unsafe-trait-object-impl.stderr index 2e2dac288a1..a3a37fd2775 100644 --- a/tests/ui/coherence/coherence-unsafe-trait-object-impl.stderr +++ b/tests/ui/coherence/coherence-unsafe-trait-object-impl.stderr @@ -6,6 +6,11 @@ LL | takes_t(t); | | | required by a bound introduced by this call | +help: this trait has no implementations, consider adding one + --> $DIR/coherence-unsafe-trait-object-impl.rs:6:1 + | +LL | trait Trait: Sized { + | ^^^^^^^^^^^^^^^^^^ note: required by a bound in `takes_t` --> $DIR/coherence-unsafe-trait-object-impl.rs:10:15 | diff --git a/tests/ui/const-generics/dont-evaluate-array-len-on-err-1.stderr b/tests/ui/const-generics/dont-evaluate-array-len-on-err-1.stderr index cb51d9b1ea5..b3a27566026 100644 --- a/tests/ui/const-generics/dont-evaluate-array-len-on-err-1.stderr +++ b/tests/ui/const-generics/dont-evaluate-array-len-on-err-1.stderr @@ -3,6 +3,12 @@ error[E0277]: the trait bound `[Adt; std::mem::size_of::<Self::Assoc>()]: Foo` i | LL | <[Adt; std::mem::size_of::<Self::Assoc>()] as Foo>::bar() | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ the trait `Foo` is not implemented for `[Adt; std::mem::size_of::<Self::Assoc>()]` + | +help: this trait has no implementations, consider adding one + --> $DIR/dont-evaluate-array-len-on-err-1.rs:9:1 + | +LL | trait Foo { + | ^^^^^^^^^ error: aborting due to previous error diff --git a/tests/ui/const-generics/early/const-param-from-outer-fn.rs b/tests/ui/const-generics/early/const-param-from-outer-fn.rs index c3b418ee3f8..ee57f3c4fc3 100644 --- a/tests/ui/const-generics/early/const-param-from-outer-fn.rs +++ b/tests/ui/const-generics/early/const-param-from-outer-fn.rs @@ -1,6 +1,6 @@ fn foo<const X: u32>() { fn bar() -> u32 { - X //~ ERROR can't use generic parameters from outer function + X //~ ERROR can't use generic parameters from outer item } } diff --git a/tests/ui/const-generics/early/const-param-from-outer-fn.stderr b/tests/ui/const-generics/early/const-param-from-outer-fn.stderr index e3bf38b702e..826f2657905 100644 --- a/tests/ui/const-generics/early/const-param-from-outer-fn.stderr +++ b/tests/ui/const-generics/early/const-param-from-outer-fn.stderr @@ -1,12 +1,12 @@ -error[E0401]: can't use generic parameters from outer function +error[E0401]: can't use generic parameters from outer item --> $DIR/const-param-from-outer-fn.rs:3:9 | LL | fn foo<const X: u32>() { - | - const parameter from outer function + | - const parameter from outer item LL | fn bar() -> u32 { - | - help: try using a local generic parameter instead: `<X>` + | - help: try introducing a local generic parameter here: `<X>` LL | X - | ^ use of generic parameter from outer function + | ^ use of generic parameter from outer item error: aborting due to previous error diff --git a/tests/ui/const-generics/generic_const_exprs/issue-85848.stderr b/tests/ui/const-generics/generic_const_exprs/issue-85848.stderr index e50ac671eca..9391b1c1a17 100644 --- a/tests/ui/const-generics/generic_const_exprs/issue-85848.stderr +++ b/tests/ui/const-generics/generic_const_exprs/issue-85848.stderr @@ -6,7 +6,11 @@ LL | writes_to_specific_path(&cap); | | | required by a bound introduced by this call | - = help: the trait `Delegates<U>` is implemented for `T` +help: this trait has no implementations, consider adding one + --> $DIR/issue-85848.rs:4:1 + | +LL | trait _Contains<T> { + | ^^^^^^^^^^^^^^^^^^ note: required for `&C` to implement `Contains<(), true>` --> $DIR/issue-85848.rs:21:12 | diff --git a/tests/ui/const-generics/issues/issue-86530.stderr b/tests/ui/const-generics/issues/issue-86530.stderr index 620ed4f0fb2..d02808f7c56 100644 --- a/tests/ui/const-generics/issues/issue-86530.stderr +++ b/tests/ui/const-generics/issues/issue-86530.stderr @@ -6,6 +6,11 @@ LL | z(" "); | | | required by a bound introduced by this call | +help: this trait has no implementations, consider adding one + --> $DIR/issue-86530.rs:4:1 + | +LL | pub trait X { + | ^^^^^^^^^^^ note: required by a bound in `z` --> $DIR/issue-86530.rs:10:8 | diff --git a/tests/ui/consts/drop-maybe_uninit.rs b/tests/ui/consts/drop-maybe_uninit.rs new file mode 100644 index 00000000000..2fdeae5f185 --- /dev/null +++ b/tests/ui/consts/drop-maybe_uninit.rs @@ -0,0 +1,17 @@ +// build-pass + +pub const fn f<T, const N: usize>(_: [std::mem::MaybeUninit<T>; N]) {} + +pub struct Blubb<T>(*const T); + +pub const fn g<T, const N: usize>(_: [Blubb<T>; N]) {} + +pub struct Blorb<const N: usize>([String; N]); + +pub const fn h(_: Blorb<0>) {} + +pub struct Wrap(Blorb<0>); + +pub const fn i(_: Wrap) {} + +fn main() {} diff --git a/tests/ui/cross/cross-fn-cache-hole.stderr b/tests/ui/cross/cross-fn-cache-hole.stderr index 7e15562b081..79d1713934b 100644 --- a/tests/ui/cross/cross-fn-cache-hole.stderr +++ b/tests/ui/cross/cross-fn-cache-hole.stderr @@ -4,6 +4,11 @@ error[E0277]: the trait bound `i32: Bar<u32>` is not satisfied LL | where i32: Foo<u32, A> | ^^^^^^^^^^^^^^^^ the trait `Bar<u32>` is not implemented for `i32` | +help: this trait has no implementations, consider adding one + --> $DIR/cross-fn-cache-hole.rs:11:1 + | +LL | trait Bar<X> { } + | ^^^^^^^^^^^^ = help: see issue #48214 = help: add `#![feature(trivial_bounds)]` to the crate attributes to enable diff --git a/tests/ui/drop-bounds/drop-bounds-impl-drop.rs b/tests/ui/drop-bounds/drop-bounds-impl-drop.rs index 063efc7b31a..15aebdf1bc9 100644 --- a/tests/ui/drop-bounds/drop-bounds-impl-drop.rs +++ b/tests/ui/drop-bounds/drop-bounds-impl-drop.rs @@ -2,13 +2,13 @@ #![deny(drop_bounds)] // As a special exemption, `impl Drop` in the return position raises no error. // This allows a convenient way to return an unnamed drop guard. -fn voldemort_type() -> impl Drop { - struct Voldemort; - impl Drop for Voldemort { +fn unnameable_type() -> impl Drop { + struct Unnameable; + impl Drop for Unnameable { fn drop(&mut self) {} } - Voldemort + Unnameable } fn main() { - let _ = voldemort_type(); + let _ = unnameable_type(); } diff --git a/tests/ui/dst/dst-bad-coerce1.stderr b/tests/ui/dst/dst-bad-coerce1.stderr index 2c75518c298..455d15e935f 100644 --- a/tests/ui/dst/dst-bad-coerce1.stderr +++ b/tests/ui/dst/dst-bad-coerce1.stderr @@ -15,6 +15,11 @@ error[E0277]: the trait bound `Foo: Bar` is not satisfied LL | let f3: &Fat<dyn Bar> = f2; | ^^ the trait `Bar` is not implemented for `Foo` | +help: this trait has no implementations, consider adding one + --> $DIR/dst-bad-coerce1.rs:10:1 + | +LL | trait Bar { fn bar(&self) {} } + | ^^^^^^^^^ = note: required for the cast from `&Fat<Foo>` to `&Fat<dyn Bar>` error[E0308]: mismatched types @@ -34,6 +39,11 @@ error[E0277]: the trait bound `Foo: Bar` is not satisfied LL | let f3: &(dyn Bar,) = f2; | ^^ the trait `Bar` is not implemented for `Foo` | +help: this trait has no implementations, consider adding one + --> $DIR/dst-bad-coerce1.rs:10:1 + | +LL | trait Bar { fn bar(&self) {} } + | ^^^^^^^^^ = note: required for the cast from `&(Foo,)` to `&(dyn Bar,)` error: aborting due to 4 previous errors diff --git a/tests/ui/dyn-star/error.stderr b/tests/ui/dyn-star/error.stderr index ae54b9ca707..e039bb6f1c8 100644 --- a/tests/ui/dyn-star/error.stderr +++ b/tests/ui/dyn-star/error.stderr @@ -3,6 +3,12 @@ error[E0277]: the trait bound `{integer}: Foo` is not satisfied | LL | let dyn_i: dyn* Foo = i; | ^ the trait `Foo` is not implemented for `{integer}` + | +help: this trait has no implementations, consider adding one + --> $DIR/error.rs:6:1 + | +LL | trait Foo {} + | ^^^^^^^^^ error: aborting due to previous error diff --git a/tests/ui/error-codes/E0220.stderr b/tests/ui/error-codes/E0220.stderr index 11763ce788d..e03eadacae4 100644 --- a/tests/ui/error-codes/E0220.stderr +++ b/tests/ui/error-codes/E0220.stderr @@ -2,7 +2,7 @@ error[E0220]: associated type `F` not found for `Trait` --> $DIR/E0220.rs:5:22 | LL | type Foo = dyn Trait<F=i32>; - | ^ associated type `F` not found + | ^ help: `Trait` has the following associated type: `Bar` error[E0191]: the value of the associated type `Bar` (from trait `Trait`) must be specified --> $DIR/E0220.rs:5:16 diff --git a/tests/ui/error-codes/E0277.stderr b/tests/ui/error-codes/E0277.stderr index 440e43dff81..0b0d2b09720 100644 --- a/tests/ui/error-codes/E0277.stderr +++ b/tests/ui/error-codes/E0277.stderr @@ -21,6 +21,11 @@ LL | some_func(5i32); | | | required by a bound introduced by this call | +help: this trait has no implementations, consider adding one + --> $DIR/E0277.rs:3:1 + | +LL | trait Foo { + | ^^^^^^^^^ note: required by a bound in `some_func` --> $DIR/E0277.rs:7:17 | diff --git a/tests/ui/error-codes/E0401.stderr b/tests/ui/error-codes/E0401.stderr index fa4b91cacef..928c8d11d20 100644 --- a/tests/ui/error-codes/E0401.stderr +++ b/tests/ui/error-codes/E0401.stderr @@ -1,26 +1,26 @@ -error[E0401]: can't use generic parameters from outer function +error[E0401]: can't use generic parameters from outer item --> $DIR/E0401.rs:4:39 | LL | fn foo<T>(x: T) { - | - type parameter from outer function + | - type parameter from outer item LL | fn bfnr<U, V: Baz<U>, W: Fn()>(y: T) { - | - ^ use of generic parameter from outer function + | - ^ use of generic parameter from outer item | | - | help: try using a local generic parameter instead: `T,` + | help: try introducing a local generic parameter here: `T,` -error[E0401]: can't use generic parameters from outer function +error[E0401]: can't use generic parameters from outer item --> $DIR/E0401.rs:9:16 | LL | fn foo<T>(x: T) { - | - type parameter from outer function + | - type parameter from outer item ... LL | fn baz<U, - | - help: try using a local generic parameter instead: `T,` + | - help: try introducing a local generic parameter here: `T,` ... LL | (y: T) { - | ^ use of generic parameter from outer function + | ^ use of generic parameter from outer item -error[E0401]: can't use generic parameters from outer function +error[E0401]: can't use generic parameters from outer item --> $DIR/E0401.rs:24:25 | LL | impl<T> Iterator for A<T> { @@ -29,8 +29,8 @@ LL | impl<T> Iterator for A<T> { LL | fn helper(sel: &Self) -> u8 { | ^^^^ | | - | use of generic parameter from outer function - | use a type here instead + | use of generic parameter from outer item + | refer to the type directly here instead error[E0282]: type annotations needed --> $DIR/E0401.rs:11:5 diff --git a/tests/ui/error-codes/E0602.rs b/tests/ui/error-codes/E0602.rs index 8fadce526d9..77d28838a10 100644 --- a/tests/ui/error-codes/E0602.rs +++ b/tests/ui/error-codes/E0602.rs @@ -1,6 +1,8 @@ // compile-flags:-D bogus +// check-pass // error-pattern:E0602 // error-pattern:requested on the command line with `-D bogus` +// error-pattern:`#[warn(unknown_lints)]` on by default fn main() {} diff --git a/tests/ui/error-codes/E0602.stderr b/tests/ui/error-codes/E0602.stderr index 2b372263345..60ecec7cdd7 100644 --- a/tests/ui/error-codes/E0602.stderr +++ b/tests/ui/error-codes/E0602.stderr @@ -1,11 +1,16 @@ -error[E0602]: unknown lint: `bogus` +warning[E0602]: unknown lint: `bogus` | = note: requested on the command line with `-D bogus` + = note: `#[warn(unknown_lints)]` on by default -error[E0602]: unknown lint: `bogus` +warning[E0602]: unknown lint: `bogus` | = note: requested on the command line with `-D bogus` -error: aborting due to 2 previous errors +warning[E0602]: unknown lint: `bogus` + | + = note: requested on the command line with `-D bogus` + +warning: 3 warnings emitted For more information about this error, try `rustc --explain E0602`. diff --git a/tests/ui/feature-gates/print-with-path.cfg.stderr b/tests/ui/feature-gates/print-with-path.cfg.stderr deleted file mode 100644 index a6c51baa320..00000000000 --- a/tests/ui/feature-gates/print-with-path.cfg.stderr +++ /dev/null @@ -1,2 +0,0 @@ -error: the `-Z unstable-options` flag must also be passed to enable the path print option - diff --git a/tests/ui/feature-gates/print-with-path.rs b/tests/ui/feature-gates/print-with-path.rs deleted file mode 100644 index f929c14c218..00000000000 --- a/tests/ui/feature-gates/print-with-path.rs +++ /dev/null @@ -1,7 +0,0 @@ -// check-fail -// revisions: cfg target-features target-cpus -// [cfg]compile-flags: --print cfg=cfg.txt -// [target-cpus]compile-flags: --print target-cpu=target_cpu.txt -// [target-features]compile-flags: --print target-features=target_features.txt - -fn main() {} diff --git a/tests/ui/feature-gates/print-with-path.target-cpus.stderr b/tests/ui/feature-gates/print-with-path.target-cpus.stderr deleted file mode 100644 index a6c51baa320..00000000000 --- a/tests/ui/feature-gates/print-with-path.target-cpus.stderr +++ /dev/null @@ -1,2 +0,0 @@ -error: the `-Z unstable-options` flag must also be passed to enable the path print option - diff --git a/tests/ui/feature-gates/print-with-path.target-features.stderr b/tests/ui/feature-gates/print-with-path.target-features.stderr deleted file mode 100644 index a6c51baa320..00000000000 --- a/tests/ui/feature-gates/print-with-path.target-features.stderr +++ /dev/null @@ -1,2 +0,0 @@ -error: the `-Z unstable-options` flag must also be passed to enable the path print option - diff --git a/tests/ui/fn/keyword-order.stderr b/tests/ui/fn/keyword-order.stderr index d3b140c8528..97d8f91b1ee 100644 --- a/tests/ui/fn/keyword-order.stderr +++ b/tests/ui/fn/keyword-order.stderr @@ -11,6 +11,8 @@ error: expected item, found keyword `pub` | LL | default pub const async unsafe extern fn err() {} | ^^^ expected item + | + = note: for a full list of items that can appear in modules, see <https://doc.rust-lang.org/reference/items.html> error: aborting due to 2 previous errors diff --git a/tests/ui/generic-associated-types/issue-101020.stderr b/tests/ui/generic-associated-types/issue-101020.stderr index 5c8db617c17..91967fb8509 100644 --- a/tests/ui/generic-associated-types/issue-101020.stderr +++ b/tests/ui/generic-associated-types/issue-101020.stderr @@ -4,6 +4,11 @@ error[E0277]: the trait bound `for<'a> &'a mut (): Foo<&'a mut ()>` is not satis LL | (&mut EmptyIter).consume(()); | ^^^^^^^ the trait `for<'a> Foo<&'a mut ()>` is not implemented for `&'a mut ()` | +help: this trait has no implementations, consider adding one + --> $DIR/issue-101020.rs:28:1 + | +LL | trait Foo<T> {} + | ^^^^^^^^^^^^ note: required for `&'a mut ()` to implement `for<'a> FuncInput<'a, &'a mut ()>` --> $DIR/issue-101020.rs:27:20 | diff --git a/tests/ui/generics/issue-94432-garbage-ice.rs b/tests/ui/generics/issue-94432-garbage-ice.rs index d0709e2d2a4..4ddb3a7e9f8 100644 --- a/tests/ui/generics/issue-94432-garbage-ice.rs +++ b/tests/ui/generics/issue-94432-garbage-ice.rs @@ -4,7 +4,7 @@ fn�a<e>(){fn�p(){e}} //~ ERROR unknown start of token: \u{fffd} //~^ ERROR unknown start of token: \u{fffd} -//~^^ ERROR can't use generic parameters from outer function [E0401] +//~^^ ERROR can't use generic parameters from outer item [E0401] //~^^^ WARN type parameter `e` should have an upper camel case name fn main(){} diff --git a/tests/ui/generics/issue-98432.rs b/tests/ui/generics/issue-98432.rs index 780c50d6ffa..c31dea76c09 100644 --- a/tests/ui/generics/issue-98432.rs +++ b/tests/ui/generics/issue-98432.rs @@ -2,7 +2,7 @@ struct Struct<T>(T); impl<T> Struct<T> { const CONST: fn() = || { - struct _Obligation where T:; //~ ERROR can't use generic parameters from outer function + struct _Obligation where T:; //~ ERROR can't use generic parameters from outer item }; } diff --git a/tests/ui/generics/issue-98432.stderr b/tests/ui/generics/issue-98432.stderr index c7b5c33618d..0736d94106e 100644 --- a/tests/ui/generics/issue-98432.stderr +++ b/tests/ui/generics/issue-98432.stderr @@ -1,13 +1,13 @@ -error[E0401]: can't use generic parameters from outer function +error[E0401]: can't use generic parameters from outer item --> $DIR/issue-98432.rs:5:34 | LL | impl<T> Struct<T> { - | - type parameter from outer function + | - type parameter from outer item LL | const CONST: fn() = || { LL | struct _Obligation where T:; - | - ^ use of generic parameter from outer function + | - ^ use of generic parameter from outer item | | - | help: try using a local generic parameter instead: `<T>` + | help: try introducing a local generic parameter here: `<T>` error: aborting due to previous error diff --git a/tests/ui/higher-ranked/trait-bounds/normalize-under-binder/issue-89118.stderr b/tests/ui/higher-ranked/trait-bounds/normalize-under-binder/issue-89118.stderr index edef6ccd34e..7fe803550bd 100644 --- a/tests/ui/higher-ranked/trait-bounds/normalize-under-binder/issue-89118.stderr +++ b/tests/ui/higher-ranked/trait-bounds/normalize-under-binder/issue-89118.stderr @@ -4,6 +4,11 @@ error[E0277]: the trait bound `for<'a> &'a (): BufferMut` is not satisfied LL | C: StackContext, | ^^^^^^^^^^^^ the trait `for<'a> BufferMut` is not implemented for `&'a ()` | +help: this trait has no implementations, consider adding one + --> $DIR/issue-89118.rs:1:1 + | +LL | trait BufferMut {} + | ^^^^^^^^^^^^^^^ note: required for `Ctx<()>` to implement `for<'a> BufferUdpStateContext<&'a ()>` --> $DIR/issue-89118.rs:5:23 | @@ -26,6 +31,11 @@ error[E0277]: the trait bound `for<'a> &'a (): BufferMut` is not satisfied LL | impl<C> EthernetWorker<C> {} | ^^^^^^^^^^^^^^^^^ the trait `for<'a> BufferMut` is not implemented for `&'a ()` | +help: this trait has no implementations, consider adding one + --> $DIR/issue-89118.rs:1:1 + | +LL | trait BufferMut {} + | ^^^^^^^^^^^^^^^ note: required for `Ctx<()>` to implement `for<'a> BufferUdpStateContext<&'a ()>` --> $DIR/issue-89118.rs:5:23 | @@ -48,6 +58,11 @@ error[E0277]: the trait bound `for<'a> &'a (): BufferMut` is not satisfied LL | type Handler = Ctx<C::Dispatcher>; | ^^^^^^^^^^^^^^^^^^ the trait `for<'a> BufferMut` is not implemented for `&'a ()` | +help: this trait has no implementations, consider adding one + --> $DIR/issue-89118.rs:1:1 + | +LL | trait BufferMut {} + | ^^^^^^^^^^^^^^^ note: required for `Ctx<()>` to implement `for<'a> BufferUdpStateContext<&'a ()>` --> $DIR/issue-89118.rs:5:23 | diff --git a/tests/ui/impl-trait/async_scope_creep.rs b/tests/ui/impl-trait/async_scope_creep.rs index 7a9d64d339f..9a8831a299e 100644 --- a/tests/ui/impl-trait/async_scope_creep.rs +++ b/tests/ui/impl-trait/async_scope_creep.rs @@ -1,6 +1,7 @@ #![feature(type_alias_impl_trait)] // edition:2021 -// check-pass +//[rpit] check-pass +// revisions: tait rpit struct Pending {} @@ -12,15 +13,23 @@ impl AsyncRead for i32 {} type PendingReader<'a> = impl AsyncRead + 'a; -type OpeningReadFuture<'a> = - impl std::future::Future<Output = Result<PendingReader<'a>, CantOpen>>; +#[cfg(tait)] +type OpeningReadFuture<'a> = impl std::future::Future<Output = Result<PendingReader<'a>, CantOpen>>; impl Pending { async fn read(&mut self) -> Result<impl AsyncRead + '_, CantOpen> { Ok(42) } + #[cfg(tait)] fn read_fut(&mut self) -> OpeningReadFuture<'_> { + self.read() //[tait]~ ERROR: cannot satisfy `impl AsyncRead + 'a == PendingReader<'a>` + } + + #[cfg(rpit)] + fn read_fut( + &mut self, + ) -> impl std::future::Future<Output = Result<PendingReader<'_>, CantOpen>> { self.read() } } diff --git a/tests/ui/impl-trait/async_scope_creep.tait.stderr b/tests/ui/impl-trait/async_scope_creep.tait.stderr new file mode 100644 index 00000000000..165096a0574 --- /dev/null +++ b/tests/ui/impl-trait/async_scope_creep.tait.stderr @@ -0,0 +1,9 @@ +error[E0284]: type annotations needed: cannot satisfy `impl AsyncRead + 'a == PendingReader<'a>` + --> $DIR/async_scope_creep.rs:26:9 + | +LL | self.read() + | ^^^^^^^^^^^ cannot satisfy `impl AsyncRead + 'a == PendingReader<'a>` + +error: aborting due to previous error + +For more information about this error, try `rustc --explain E0284`. diff --git a/tests/ui/impl-trait/in-trait/auxiliary/rpitit.rs b/tests/ui/impl-trait/in-trait/auxiliary/rpitit.rs index cfc2193f633..6e99402113a 100644 --- a/tests/ui/impl-trait/in-trait/auxiliary/rpitit.rs +++ b/tests/ui/impl-trait/in-trait/auxiliary/rpitit.rs @@ -1,4 +1,4 @@ -#![feature(return_position_impl_trait_in_trait)] +#![feature(return_position_impl_trait_in_trait, lint_reasons)] use std::ops::Deref; @@ -8,6 +8,7 @@ pub trait Foo { pub struct Foreign; impl Foo for Foreign { + #[expect(refining_impl_trait)] fn bar(self) -> &'static () { &() } diff --git a/tests/ui/impl-trait/in-trait/bad-item-bound-within-rpitit.rs b/tests/ui/impl-trait/in-trait/bad-item-bound-within-rpitit.rs index ff7ad4bf389..fbbbb8585d1 100644 --- a/tests/ui/impl-trait/in-trait/bad-item-bound-within-rpitit.rs +++ b/tests/ui/impl-trait/in-trait/bad-item-bound-within-rpitit.rs @@ -2,7 +2,7 @@ #![feature(return_position_impl_trait_in_trait)] -trait Iterable { +pub trait Iterable { type Item<'a> where Self: 'a; @@ -17,6 +17,7 @@ impl<'a, I: 'a + Iterable> Iterable for &'a I { //~^ ERROR impl has stricter requirements than trait fn iter(&self) -> impl 'a + Iterator<Item = I::Item<'a>> { + //~^ WARN impl trait in impl method signature does not match trait method signature (*self).iter() } } diff --git a/tests/ui/impl-trait/in-trait/bad-item-bound-within-rpitit.stderr b/tests/ui/impl-trait/in-trait/bad-item-bound-within-rpitit.stderr index 106b8a7c804..a5fb338ea4e 100644 --- a/tests/ui/impl-trait/in-trait/bad-item-bound-within-rpitit.stderr +++ b/tests/ui/impl-trait/in-trait/bad-item-bound-within-rpitit.stderr @@ -12,6 +12,22 @@ help: copy the `where` clause predicates from the trait LL | where Self: 'b; | ~~~~~~~~~~~~~~ -error: aborting due to previous error +warning: impl trait in impl method signature does not match trait method signature + --> $DIR/bad-item-bound-within-rpitit.rs:19:28 + | +LL | fn iter(&self) -> impl '_ + Iterator<Item = Self::Item<'_>>; + | ----------------------------------------- return type from trait method defined here +... +LL | fn iter(&self) -> impl 'a + Iterator<Item = I::Item<'a>> { + | ^^ this bound is stronger than that defined on the trait + | + = note: add `#[allow(refining_impl_trait)]` if it is intended for this to be part of the public API of this crate + = note: `#[warn(refining_impl_trait)]` on by default +help: replace the return type so that it matches the trait + | +LL | fn iter(&self) -> impl Iterator<Item = <Self as Iterable>::Item<'_>> + '_ { + | ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + +error: aborting due to previous error; 1 warning emitted For more information about this error, try `rustc --explain E0276`. diff --git a/tests/ui/impl-trait/in-trait/deep-match-works.rs b/tests/ui/impl-trait/in-trait/deep-match-works.rs index 78cff97c616..fc290f11f9d 100644 --- a/tests/ui/impl-trait/in-trait/deep-match-works.rs +++ b/tests/ui/impl-trait/in-trait/deep-match-works.rs @@ -1,15 +1,16 @@ // check-pass -#![feature(return_position_impl_trait_in_trait)] +#![feature(return_position_impl_trait_in_trait, lint_reasons)] #![allow(incomplete_features)] -struct Wrapper<T>(T); +pub struct Wrapper<T>(T); -trait Foo { +pub trait Foo { fn bar() -> Wrapper<impl Sized>; } impl Foo for () { + #[expect(refining_impl_trait)] fn bar() -> Wrapper<i32> { Wrapper(0) } diff --git a/tests/ui/impl-trait/in-trait/foreign.rs b/tests/ui/impl-trait/in-trait/foreign.rs index b0c93a02935..6285d7786d5 100644 --- a/tests/ui/impl-trait/in-trait/foreign.rs +++ b/tests/ui/impl-trait/in-trait/foreign.rs @@ -1,14 +1,25 @@ // check-pass // aux-build: rpitit.rs +#![feature(lint_reasons)] + extern crate rpitit; use rpitit::{Foo, Foreign}; use std::sync::Arc; // Implement an RPITIT from another crate. -struct Local; +pub struct Local; impl Foo for Local { + #[expect(refining_impl_trait)] + fn bar(self) -> Arc<String> { + Arc::new(String::new()) + } +} + +struct LocalIgnoreRefining; +impl Foo for LocalIgnoreRefining { + #[deny(refining_impl_trait)] fn bar(self) -> Arc<String> { Arc::new(String::new()) } @@ -23,4 +34,5 @@ fn main() { let &() = Foreign.bar(); let x: Arc<String> = Local.bar(); + let x: Arc<String> = LocalIgnoreRefining.bar(); } diff --git a/tests/ui/impl-trait/in-trait/issue-102571.rs b/tests/ui/impl-trait/in-trait/issue-102571.rs index 61c91e64417..ccb53031c44 100644 --- a/tests/ui/impl-trait/in-trait/issue-102571.rs +++ b/tests/ui/impl-trait/in-trait/issue-102571.rs @@ -8,14 +8,6 @@ trait Foo { fn bar(self) -> impl Deref<Target = impl Display + ?Sized>; } -struct A; - -impl Foo for A { - fn bar(self) -> &'static str { - "Hello, world" - } -} - fn foo<T: Foo>(t: T) { let () = t.bar(); //~^ ERROR mismatched types diff --git a/tests/ui/impl-trait/in-trait/issue-102571.stderr b/tests/ui/impl-trait/in-trait/issue-102571.stderr index 87219941d91..594b9ae9cd6 100644 --- a/tests/ui/impl-trait/in-trait/issue-102571.stderr +++ b/tests/ui/impl-trait/in-trait/issue-102571.stderr @@ -1,5 +1,5 @@ error[E0308]: mismatched types - --> $DIR/issue-102571.rs:20:9 + --> $DIR/issue-102571.rs:12:9 | LL | let () = t.bar(); | ^^ ------- this expression has type `impl Deref<Target = impl std::fmt::Display + ?Sized>` diff --git a/tests/ui/impl-trait/in-trait/nested-rpitit.rs b/tests/ui/impl-trait/in-trait/nested-rpitit.rs index 65285e3a3cc..58ba1acaf14 100644 --- a/tests/ui/impl-trait/in-trait/nested-rpitit.rs +++ b/tests/ui/impl-trait/in-trait/nested-rpitit.rs @@ -1,26 +1,28 @@ // check-pass -#![feature(return_position_impl_trait_in_trait)] +#![feature(return_position_impl_trait_in_trait, lint_reasons)] #![allow(incomplete_features)] use std::fmt::Display; use std::ops::Deref; -trait Foo { +pub trait Foo { fn bar(self) -> impl Deref<Target = impl Display + ?Sized>; } -struct A; +pub struct A; impl Foo for A { + #[expect(refining_impl_trait)] fn bar(self) -> &'static str { "Hello, world" } } -struct B; +pub struct B; impl Foo for B { + #[expect(refining_impl_trait)] fn bar(self) -> Box<i32> { Box::new(42) } diff --git a/tests/ui/impl-trait/in-trait/object-safety.rs b/tests/ui/impl-trait/in-trait/object-safety.rs index 9a231e59b09..d1c9fba4e99 100644 --- a/tests/ui/impl-trait/in-trait/object-safety.rs +++ b/tests/ui/impl-trait/in-trait/object-safety.rs @@ -8,7 +8,7 @@ trait Foo { } impl Foo for u32 { - fn baz(&self) -> u32 { + fn baz(&self) -> impl Debug { 32 } } diff --git a/tests/ui/impl-trait/in-trait/refine.rs b/tests/ui/impl-trait/in-trait/refine.rs new file mode 100644 index 00000000000..a91f9b3e722 --- /dev/null +++ b/tests/ui/impl-trait/in-trait/refine.rs @@ -0,0 +1,48 @@ +#![feature(return_position_impl_trait_in_trait, async_fn_in_trait)] +#![deny(refining_impl_trait)] + +pub trait Foo { + fn bar() -> impl Sized; +} + +pub struct A; +impl Foo for A { + fn bar() -> impl Copy {} + //~^ ERROR impl method signature does not match trait method signature +} + +pub struct B; +impl Foo for B { + fn bar() {} + //~^ ERROR impl method signature does not match trait method signature +} + +pub struct C; +impl Foo for C { + fn bar() -> () {} + //~^ ERROR impl method signature does not match trait method signature +} + +struct Private; +impl Foo for Private { + fn bar() -> () {} +} + +pub trait Arg<A> { + fn bar() -> impl Sized; +} +impl Arg<Private> for A { + fn bar() -> () {} +} + +pub trait Late { + fn bar<'a>(&'a self) -> impl Sized + 'a; +} + +pub struct D; +impl Late for D { + fn bar(&self) -> impl Copy + '_ {} + //~^ ERROR impl method signature does not match trait method signature +} + +fn main() {} diff --git a/tests/ui/impl-trait/in-trait/refine.stderr b/tests/ui/impl-trait/in-trait/refine.stderr new file mode 100644 index 00000000000..29aa08e25bb --- /dev/null +++ b/tests/ui/impl-trait/in-trait/refine.stderr @@ -0,0 +1,67 @@ +error: impl trait in impl method signature does not match trait method signature + --> $DIR/refine.rs:10:22 + | +LL | fn bar() -> impl Sized; + | ---------- return type from trait method defined here +... +LL | fn bar() -> impl Copy {} + | ^^^^ this bound is stronger than that defined on the trait + | + = note: add `#[allow(refining_impl_trait)]` if it is intended for this to be part of the public API of this crate +note: the lint level is defined here + --> $DIR/refine.rs:2:9 + | +LL | #![deny(refining_impl_trait)] + | ^^^^^^^^^^^^^^^^^^^ +help: replace the return type so that it matches the trait + | +LL | fn bar() -> impl Sized {} + | ~~~~~~~~~~ + +error: impl trait in impl method signature does not match trait method signature + --> $DIR/refine.rs:16:5 + | +LL | fn bar() -> impl Sized; + | ---------- return type from trait method defined here +... +LL | fn bar() {} + | ^^^^^^^^ + | + = note: add `#[allow(refining_impl_trait)]` if it is intended for this to be part of the public API of this crate +help: replace the return type so that it matches the trait + | +LL | fn bar() -> impl Sized {} + | +++++++++++++ + +error: impl trait in impl method signature does not match trait method signature + --> $DIR/refine.rs:22:17 + | +LL | fn bar() -> impl Sized; + | ---------- return type from trait method defined here +... +LL | fn bar() -> () {} + | ^^ + | + = note: add `#[allow(refining_impl_trait)]` if it is intended for this to be part of the public API of this crate +help: replace the return type so that it matches the trait + | +LL | fn bar() -> impl Sized {} + | ~~~~~~~~~~ + +error: impl trait in impl method signature does not match trait method signature + --> $DIR/refine.rs:44:27 + | +LL | fn bar<'a>(&'a self) -> impl Sized + 'a; + | --------------- return type from trait method defined here +... +LL | fn bar(&self) -> impl Copy + '_ {} + | ^^^^ this bound is stronger than that defined on the trait + | + = note: add `#[allow(refining_impl_trait)]` if it is intended for this to be part of the public API of this crate +help: replace the return type so that it matches the trait + | +LL | fn bar(&self) -> impl Sized + '_ {} + | ~~~~~~~~~~~~~~~ + +error: aborting due to 4 previous errors + diff --git a/tests/ui/impl-trait/in-trait/reveal.rs b/tests/ui/impl-trait/in-trait/reveal.rs index d6ede1cc495..b1b46d75b8f 100644 --- a/tests/ui/impl-trait/in-trait/reveal.rs +++ b/tests/ui/impl-trait/in-trait/reveal.rs @@ -1,13 +1,14 @@ // check-pass -#![feature(return_position_impl_trait_in_trait)] +#![feature(return_position_impl_trait_in_trait, lint_reasons)] #![allow(incomplete_features)] -trait Foo { +pub trait Foo { fn f() -> Box<impl Sized>; } impl Foo for () { + #[expect(refining_impl_trait)] fn f() -> Box<String> { Box::new(String::new()) } diff --git a/tests/ui/impl-trait/in-trait/rpitit-shadowed-by-missing-adt.rs b/tests/ui/impl-trait/in-trait/rpitit-shadowed-by-missing-adt.rs index 7682884f879..44a2b430344 100644 --- a/tests/ui/impl-trait/in-trait/rpitit-shadowed-by-missing-adt.rs +++ b/tests/ui/impl-trait/in-trait/rpitit-shadowed-by-missing-adt.rs @@ -1,6 +1,6 @@ // issue: 113903 -#![feature(return_position_impl_trait_in_trait)] +#![feature(return_position_impl_trait_in_trait, lint_reasons)] use std::ops::Deref; @@ -10,6 +10,7 @@ pub trait Tr { } impl Tr for () { + #[expect(refining_impl_trait)] fn w() -> &'static () { &() } diff --git a/tests/ui/impl-trait/in-trait/signature-mismatch.failure.stderr b/tests/ui/impl-trait/in-trait/signature-mismatch.failure.stderr index 186580f5756..468cf12f1bc 100644 --- a/tests/ui/impl-trait/in-trait/signature-mismatch.failure.stderr +++ b/tests/ui/impl-trait/in-trait/signature-mismatch.failure.stderr @@ -1,5 +1,5 @@ error[E0623]: lifetime mismatch - --> $DIR/signature-mismatch.rs:77:10 + --> $DIR/signature-mismatch.rs:79:10 | LL | &'a self, | -------- this parameter and the return type are declared with different lifetimes... diff --git a/tests/ui/impl-trait/in-trait/signature-mismatch.rs b/tests/ui/impl-trait/in-trait/signature-mismatch.rs index c84a3b8f46b..685c0f06e88 100644 --- a/tests/ui/impl-trait/in-trait/signature-mismatch.rs +++ b/tests/ui/impl-trait/in-trait/signature-mismatch.rs @@ -2,18 +2,17 @@ // revisions: success failure //[success] check-pass -#![feature(return_position_impl_trait_in_trait)] -#![allow(incomplete_features)] +#![feature(return_position_impl_trait_in_trait, lint_reasons)] use std::future::Future; -trait Captures<'a> {} +pub trait Captures<'a> {} impl<T> Captures<'_> for T {} -trait Captures2<'a, 'b> {} +pub trait Captures2<'a, 'b> {} impl<T> Captures2<'_, '_> for T {} -trait AsyncTrait { +pub trait AsyncTrait { #[cfg(success)] fn async_fn(&self, buff: &[u8]) -> impl Future<Output = Vec<u8>>; @@ -45,6 +44,7 @@ impl AsyncTrait for Struct { // Does not capture more lifetimes that trait def'n, since trait def'n // implicitly captures all in-scope lifetimes. #[cfg(success)] + #[expect(refining_impl_trait)] fn async_fn<'a>(&self, buff: &'a [u8]) -> impl Future<Output = Vec<u8>> + 'a { async move { buff.to_vec() } } @@ -52,6 +52,7 @@ impl AsyncTrait for Struct { // Does not capture more lifetimes that trait def'n, since trait def'n // implicitly captures all in-scope lifetimes. #[cfg(success)] + #[expect(refining_impl_trait)] fn async_fn_early<'a: 'a>(&self, buff: &'a [u8]) -> impl Future<Output = Vec<u8>> + 'a { async move { buff.to_vec() } } @@ -59,6 +60,7 @@ impl AsyncTrait for Struct { // Does not capture more lifetimes that trait def'n, since trait def'n // implicitly captures all in-scope lifetimes. #[cfg(success)] + #[expect(refining_impl_trait)] fn async_fn_multiple<'a, 'b>( &'a self, buff: &'b [u8], diff --git a/tests/ui/impl-trait/in-trait/specialization-substs-remap.rs b/tests/ui/impl-trait/in-trait/specialization-substs-remap.rs index c9ee877db8e..41fc285883a 100644 --- a/tests/ui/impl-trait/in-trait/specialization-substs-remap.rs +++ b/tests/ui/impl-trait/in-trait/specialization-substs-remap.rs @@ -1,10 +1,10 @@ // check-pass #![feature(specialization)] -#![feature(return_position_impl_trait_in_trait)] +#![feature(return_position_impl_trait_in_trait, lint_reasons)] #![allow(incomplete_features)] -trait Foo { +pub trait Foo { fn bar(&self) -> impl Sized; } @@ -12,6 +12,7 @@ impl<U> Foo for U where U: Copy, { + #[expect(refining_impl_trait)] fn bar(&self) -> U { *self } diff --git a/tests/ui/impl-trait/in-trait/success.rs b/tests/ui/impl-trait/in-trait/success.rs index 4cbe682b46f..7d415ea17a4 100644 --- a/tests/ui/impl-trait/in-trait/success.rs +++ b/tests/ui/impl-trait/in-trait/success.rs @@ -1,29 +1,32 @@ // check-pass -#![feature(return_position_impl_trait_in_trait)] +#![feature(return_position_impl_trait_in_trait, lint_reasons)] #![allow(incomplete_features)] use std::fmt::Display; -trait Foo { +pub trait Foo { fn bar(&self) -> impl Display; } impl Foo for i32 { + #[expect(refining_impl_trait)] fn bar(&self) -> i32 { *self } } impl Foo for &'static str { + #[expect(refining_impl_trait)] fn bar(&self) -> &'static str { *self } } -struct Yay; +pub struct Yay; impl Foo for Yay { + #[expect(refining_impl_trait)] fn bar(&self) -> String { String::from(":^)") } diff --git a/tests/ui/inner-static-type-parameter.rs b/tests/ui/inner-static-type-parameter.rs index c08ccd29d80..a1994e7529c 100644 --- a/tests/ui/inner-static-type-parameter.rs +++ b/tests/ui/inner-static-type-parameter.rs @@ -4,7 +4,7 @@ enum Bar<T> { What } //~ ERROR parameter `T` is never used fn foo<T>() { static a: Bar<T> = Bar::What; -//~^ ERROR can't use generic parameters from outer function +//~^ ERROR can't use generic parameters from outer item } fn main() { diff --git a/tests/ui/inner-static-type-parameter.stderr b/tests/ui/inner-static-type-parameter.stderr index e4e449e4159..ff6558e494b 100644 --- a/tests/ui/inner-static-type-parameter.stderr +++ b/tests/ui/inner-static-type-parameter.stderr @@ -1,10 +1,10 @@ -error[E0401]: can't use generic parameters from outer function +error[E0401]: can't use generic parameters from outer item --> $DIR/inner-static-type-parameter.rs:6:19 | LL | fn foo<T>() { - | - type parameter from outer function + | - type parameter from outer item LL | static a: Bar<T> = Bar::What; - | ^ use of generic parameter from outer function + | ^ use of generic parameter from outer item error[E0392]: parameter `T` is never used --> $DIR/inner-static-type-parameter.rs:3:10 diff --git a/tests/ui/issues/issue-18611.stderr b/tests/ui/issues/issue-18611.stderr index bd18d46223e..784b9b984e9 100644 --- a/tests/ui/issues/issue-18611.stderr +++ b/tests/ui/issues/issue-18611.stderr @@ -3,6 +3,12 @@ error[E0277]: the trait bound `isize: HasState` is not satisfied | LL | fn add_state(op: <isize as HasState>::State) { | ^^^^^^^^^^^^^^^^^^^^^^^^^^ the trait `HasState` is not implemented for `isize` + | +help: this trait has no implementations, consider adding one + --> $DIR/issue-18611.rs:5:1 + | +LL | trait HasState { + | ^^^^^^^^^^^^^^ error: aborting due to previous error diff --git a/tests/ui/issues/issue-25076.stderr b/tests/ui/issues/issue-25076.stderr index 159cc484c5d..065bf7def42 100644 --- a/tests/ui/issues/issue-25076.stderr +++ b/tests/ui/issues/issue-25076.stderr @@ -6,6 +6,11 @@ LL | do_fold(bot(), ()); | | | required by a bound introduced by this call | +help: this trait has no implementations, consider adding one + --> $DIR/issue-25076.rs:3:1 + | +LL | trait InOut<T> { type Out; } + | ^^^^^^^^^^^^^^ note: required by a bound in `do_fold` --> $DIR/issue-25076.rs:5:18 | diff --git a/tests/ui/issues/issue-3214.rs b/tests/ui/issues/issue-3214.rs index e3c07bb3f72..b2c27f5be95 100644 --- a/tests/ui/issues/issue-3214.rs +++ b/tests/ui/issues/issue-3214.rs @@ -1,6 +1,6 @@ fn foo<T>() { struct Foo { - x: T, //~ ERROR can't use generic parameters from outer function + x: T, //~ ERROR can't use generic parameters from outer item } impl<T> Drop for Foo<T> { diff --git a/tests/ui/issues/issue-3214.stderr b/tests/ui/issues/issue-3214.stderr index 7a2d772f0a1..5b57c1baf90 100644 --- a/tests/ui/issues/issue-3214.stderr +++ b/tests/ui/issues/issue-3214.stderr @@ -1,12 +1,12 @@ -error[E0401]: can't use generic parameters from outer function +error[E0401]: can't use generic parameters from outer item --> $DIR/issue-3214.rs:3:12 | LL | fn foo<T>() { - | - type parameter from outer function + | - type parameter from outer item LL | struct Foo { - | - help: try using a local generic parameter instead: `<T>` + | - help: try introducing a local generic parameter here: `<T>` LL | x: T, - | ^ use of generic parameter from outer function + | ^ use of generic parameter from outer item error[E0107]: struct takes 0 generic arguments but 1 generic argument was supplied --> $DIR/issue-3214.rs:6:22 diff --git a/tests/ui/issues/issue-35570.stderr b/tests/ui/issues/issue-35570.stderr index 2697d46bdb2..197e80ac097 100644 --- a/tests/ui/issues/issue-35570.stderr +++ b/tests/ui/issues/issue-35570.stderr @@ -3,6 +3,12 @@ error[E0277]: the trait bound `for<'a> (): Trait2<'a>` is not satisfied | LL | fn _ice(param: Box<dyn for <'a> Trait1<<() as Trait2<'a>>::Ty>>) { | ^^^^^^^^^^^^^^^^^^^^^^ the trait `for<'a> Trait2<'a>` is not implemented for `()` + | +help: this trait has no implementations, consider adding one + --> $DIR/issue-35570.rs:4:1 + | +LL | trait Trait2<'a> { + | ^^^^^^^^^^^^^^^^ error: aborting due to previous error diff --git a/tests/ui/issues/issue-5997-enum.rs b/tests/ui/issues/issue-5997-enum.rs index 3ff4e036c60..0b1857ae3df 100644 --- a/tests/ui/issues/issue-5997-enum.rs +++ b/tests/ui/issues/issue-5997-enum.rs @@ -1,6 +1,6 @@ fn f<Z>() -> bool { enum E { V(Z) } - //~^ ERROR can't use generic parameters from outer function + //~^ ERROR can't use generic parameters from outer item true } diff --git a/tests/ui/issues/issue-5997-enum.stderr b/tests/ui/issues/issue-5997-enum.stderr index 3a79215d3ae..d07258ea7a2 100644 --- a/tests/ui/issues/issue-5997-enum.stderr +++ b/tests/ui/issues/issue-5997-enum.stderr @@ -1,12 +1,12 @@ -error[E0401]: can't use generic parameters from outer function +error[E0401]: can't use generic parameters from outer item --> $DIR/issue-5997-enum.rs:2:16 | LL | fn f<Z>() -> bool { - | - type parameter from outer function + | - type parameter from outer item LL | enum E { V(Z) } - | - ^ use of generic parameter from outer function + | - ^ use of generic parameter from outer item | | - | help: try using a local generic parameter instead: `<Z>` + | help: try introducing a local generic parameter here: `<Z>` error: aborting due to previous error diff --git a/tests/ui/issues/issue-5997-struct.rs b/tests/ui/issues/issue-5997-struct.rs index 6cf510b0a9d..19d994b0dfb 100644 --- a/tests/ui/issues/issue-5997-struct.rs +++ b/tests/ui/issues/issue-5997-struct.rs @@ -1,5 +1,5 @@ fn f<T>() -> bool { - struct S(T); //~ ERROR can't use generic parameters from outer function + struct S(T); //~ ERROR can't use generic parameters from outer item true } diff --git a/tests/ui/issues/issue-5997-struct.stderr b/tests/ui/issues/issue-5997-struct.stderr index d2e97f76771..83229e02c6c 100644 --- a/tests/ui/issues/issue-5997-struct.stderr +++ b/tests/ui/issues/issue-5997-struct.stderr @@ -1,12 +1,12 @@ -error[E0401]: can't use generic parameters from outer function +error[E0401]: can't use generic parameters from outer item --> $DIR/issue-5997-struct.rs:2:14 | LL | fn f<T>() -> bool { - | - type parameter from outer function + | - type parameter from outer item LL | struct S(T); - | -^ use of generic parameter from outer function + | -^ use of generic parameter from outer item | | - | help: try using a local generic parameter instead: `<T>` + | help: try introducing a local generic parameter here: `<T>` error: aborting due to previous error diff --git a/tests/ui/issues/issue-60218.stderr b/tests/ui/issues/issue-60218.stderr index 563690c9a5d..ae3c4d12025 100644 --- a/tests/ui/issues/issue-60218.stderr +++ b/tests/ui/issues/issue-60218.stderr @@ -6,6 +6,11 @@ LL | trigger_error(vec![], |x: &u32| x) | | | required by a bound introduced by this call | +help: this trait has no implementations, consider adding one + --> $DIR/issue-60218.rs:7:1 + | +LL | pub trait Foo {} + | ^^^^^^^^^^^^^ note: required by a bound in `trigger_error` --> $DIR/issue-60218.rs:13:72 | diff --git a/tests/ui/issues/issue-66353.stderr b/tests/ui/issues/issue-66353.stderr index 71530f58220..7ab7547b42d 100644 --- a/tests/ui/issues/issue-66353.stderr +++ b/tests/ui/issues/issue-66353.stderr @@ -3,6 +3,12 @@ error[E0277]: the trait bound `(): _A` is not satisfied | LL | _Func::< <() as _A>::AssocT >::func(()); | ^^ the trait `_A` is not implemented for `()` + | +help: this trait has no implementations, consider adding one + --> $DIR/issue-66353.rs:7:1 + | +LL | trait _A { + | ^^^^^^^^ error[E0277]: the trait bound `(): _Func<_>` is not satisfied --> $DIR/issue-66353.rs:12:41 @@ -11,6 +17,12 @@ LL | _Func::< <() as _A>::AssocT >::func(()); | ----------------------------------- ^^ the trait `_Func<_>` is not implemented for `()` | | | required by a bound introduced by this call + | +help: this trait has no implementations, consider adding one + --> $DIR/issue-66353.rs:3:1 + | +LL | trait _Func<T> { + | ^^^^^^^^^^^^^^ error: aborting due to 2 previous errors diff --git a/tests/ui/layout/debug.rs b/tests/ui/layout/debug.rs index b74a8d3b917..65f2f3b89af 100644 --- a/tests/ui/layout/debug.rs +++ b/tests/ui/layout/debug.rs @@ -17,6 +17,9 @@ type Test = Result<i32, i32>; //~ ERROR: layout_of #[rustc_layout(debug)] type T = impl std::fmt::Debug; //~ ERROR: layout_of +fn f() -> T { + 0i32 +} #[rustc_layout(debug)] pub union V { //~ ERROR: layout_of @@ -63,6 +66,13 @@ union P5 { zst: [u16; 0], byte: u8 } //~ ERROR: layout_of #[rustc_layout(debug)] type X = std::mem::MaybeUninit<u8>; //~ ERROR: layout_of -fn f() -> T { - 0i32 +#[rustc_layout(debug)] +const C: () = (); //~ ERROR: can only be applied to + +impl S { + #[rustc_layout(debug)] + const C: () = (); //~ ERROR: can only be applied to } + +#[rustc_layout(debug)] +type Impossible = (str, str); //~ ERROR: cannot be known at compilation time diff --git a/tests/ui/layout/debug.stderr b/tests/ui/layout/debug.stderr index c20a0198ccb..5162a771b4d 100644 --- a/tests/ui/layout/debug.stderr +++ b/tests/ui/layout/debug.stderr @@ -162,7 +162,7 @@ error: layout_of(U) = Layout { LL | union U { f1: (i32, i32), f3: i32 } | ^^^^^^^ -error: layout_of(std::result::Result<i32, i32>) = Layout { +error: layout_of(Result<i32, i32>) = Layout { size: Size(8 bytes), align: AbiAndPrefAlign { abi: Align(4 bytes), @@ -344,7 +344,7 @@ error: layout_of(V) = Layout { max_repr_align: None, unadjusted_abi_align: Align(2 bytes), } - --> $DIR/debug.rs:22:1 + --> $DIR/debug.rs:25:1 | LL | pub union V { | ^^^^^^^^^^^ @@ -368,7 +368,7 @@ error: layout_of(W) = Layout { max_repr_align: None, unadjusted_abi_align: Align(2 bytes), } - --> $DIR/debug.rs:28:1 + --> $DIR/debug.rs:31:1 | LL | pub union W { | ^^^^^^^^^^^ @@ -392,7 +392,7 @@ error: layout_of(Y) = Layout { max_repr_align: None, unadjusted_abi_align: Align(2 bytes), } - --> $DIR/debug.rs:34:1 + --> $DIR/debug.rs:37:1 | LL | pub union Y { | ^^^^^^^^^^^ @@ -416,7 +416,7 @@ error: layout_of(P1) = Layout { max_repr_align: None, unadjusted_abi_align: Align(1 bytes), } - --> $DIR/debug.rs:41:1 + --> $DIR/debug.rs:44:1 | LL | union P1 { x: u32 } | ^^^^^^^^ @@ -440,7 +440,7 @@ error: layout_of(P2) = Layout { max_repr_align: None, unadjusted_abi_align: Align(1 bytes), } - --> $DIR/debug.rs:45:1 + --> $DIR/debug.rs:48:1 | LL | union P2 { x: (u32, u32) } | ^^^^^^^^ @@ -464,7 +464,7 @@ error: layout_of(P3) = Layout { max_repr_align: None, unadjusted_abi_align: Align(1 bytes), } - --> $DIR/debug.rs:53:1 + --> $DIR/debug.rs:56:1 | LL | union P3 { x: F32x4 } | ^^^^^^^^ @@ -488,7 +488,7 @@ error: layout_of(P4) = Layout { max_repr_align: None, unadjusted_abi_align: Align(1 bytes), } - --> $DIR/debug.rs:57:1 + --> $DIR/debug.rs:60:1 | LL | union P4 { x: E } | ^^^^^^^^ @@ -517,12 +517,12 @@ error: layout_of(P5) = Layout { max_repr_align: None, unadjusted_abi_align: Align(1 bytes), } - --> $DIR/debug.rs:61:1 + --> $DIR/debug.rs:64:1 | LL | union P5 { zst: [u16; 0], byte: u8 } | ^^^^^^^^ -error: layout_of(std::mem::MaybeUninit<u8>) = Layout { +error: layout_of(MaybeUninit<u8>) = Layout { size: Size(1 bytes), align: AbiAndPrefAlign { abi: Align(1 bytes), @@ -546,10 +546,32 @@ error: layout_of(std::mem::MaybeUninit<u8>) = Layout { max_repr_align: None, unadjusted_abi_align: Align(1 bytes), } - --> $DIR/debug.rs:64:1 + --> $DIR/debug.rs:67:1 | LL | type X = std::mem::MaybeUninit<u8>; | ^^^^^^ -error: aborting due to 14 previous errors +error: `#[rustc_layout]` can only be applied to `struct`/`enum`/`union` declarations and type aliases + --> $DIR/debug.rs:70:1 + | +LL | const C: () = (); + | ^^^^^^^^^^^ + +error[E0277]: the size for values of type `str` cannot be known at compilation time + --> $DIR/debug.rs:78:19 + | +LL | type Impossible = (str, str); + | ^^^^^^^^^^ doesn't have a size known at compile-time + | + = help: the trait `Sized` is not implemented for `str` + = note: only the last element of a tuple may have a dynamically sized type + +error: `#[rustc_layout]` can only be applied to `struct`/`enum`/`union` declarations and type aliases + --> $DIR/debug.rs:74:5 + | +LL | const C: () = (); + | ^^^^^^^^^^^ + +error: aborting due to 17 previous errors +For more information about this error, try `rustc --explain E0277`. diff --git a/tests/ui/layout/homogeneous-aggr-transparent.rs b/tests/ui/layout/homogeneous-aggr-transparent.rs new file mode 100644 index 00000000000..9703d2bf294 --- /dev/null +++ b/tests/ui/layout/homogeneous-aggr-transparent.rs @@ -0,0 +1,44 @@ +#![feature(rustc_attrs)] +#![feature(transparent_unions)] +use std::marker::PhantomData; + +// Regression test for #115664. We want to ensure that `repr(transparent)` wrappers do not affect +// the result of `homogeneous_aggregate`. + +type Tuple = (f32, f32, f32); + +struct Zst; + +#[repr(transparent)] +struct Wrapper1<T>(T); +#[repr(transparent)] +struct Wrapper2<T>((), Zst, T); +#[repr(transparent)] +struct Wrapper3<T>(T, [u8; 0], PhantomData<u64>); +#[repr(transparent)] +union WrapperUnion<T: Copy> { + nothing: (), + something: T, +} + +#[rustc_layout(homogeneous_aggregate)] +pub type Test0 = Tuple; +//~^ ERROR homogeneous_aggregate: Ok(Homogeneous(Reg { kind: Float, size: Size(4 bytes) })) + +#[rustc_layout(homogeneous_aggregate)] +pub type Test1 = Wrapper1<Tuple>; +//~^ ERROR homogeneous_aggregate: Ok(Homogeneous(Reg { kind: Float, size: Size(4 bytes) })) + +#[rustc_layout(homogeneous_aggregate)] +pub type Test2 = Wrapper2<Tuple>; +//~^ ERROR homogeneous_aggregate: Ok(Homogeneous(Reg { kind: Float, size: Size(4 bytes) })) + +#[rustc_layout(homogeneous_aggregate)] +pub type Test3 = Wrapper3<Tuple>; +//~^ ERROR homogeneous_aggregate: Ok(Homogeneous(Reg { kind: Float, size: Size(4 bytes) })) + +#[rustc_layout(homogeneous_aggregate)] +pub type Test4 = WrapperUnion<Tuple>; +//~^ ERROR homogeneous_aggregate: Ok(Homogeneous(Reg { kind: Float, size: Size(4 bytes) })) + +fn main() {} diff --git a/tests/ui/layout/homogeneous-aggr-transparent.stderr b/tests/ui/layout/homogeneous-aggr-transparent.stderr new file mode 100644 index 00000000000..99eb703ac82 --- /dev/null +++ b/tests/ui/layout/homogeneous-aggr-transparent.stderr @@ -0,0 +1,32 @@ +error: homogeneous_aggregate: Ok(Homogeneous(Reg { kind: Float, size: Size(4 bytes) })) + --> $DIR/homogeneous-aggr-transparent.rs:25:1 + | +LL | pub type Test0 = Tuple; + | ^^^^^^^^^^^^^^ + +error: homogeneous_aggregate: Ok(Homogeneous(Reg { kind: Float, size: Size(4 bytes) })) + --> $DIR/homogeneous-aggr-transparent.rs:29:1 + | +LL | pub type Test1 = Wrapper1<Tuple>; + | ^^^^^^^^^^^^^^ + +error: homogeneous_aggregate: Ok(Homogeneous(Reg { kind: Float, size: Size(4 bytes) })) + --> $DIR/homogeneous-aggr-transparent.rs:33:1 + | +LL | pub type Test2 = Wrapper2<Tuple>; + | ^^^^^^^^^^^^^^ + +error: homogeneous_aggregate: Ok(Homogeneous(Reg { kind: Float, size: Size(4 bytes) })) + --> $DIR/homogeneous-aggr-transparent.rs:37:1 + | +LL | pub type Test3 = Wrapper3<Tuple>; + | ^^^^^^^^^^^^^^ + +error: homogeneous_aggregate: Ok(Homogeneous(Reg { kind: Float, size: Size(4 bytes) })) + --> $DIR/homogeneous-aggr-transparent.rs:41:1 + | +LL | pub type Test4 = WrapperUnion<Tuple>; + | ^^^^^^^^^^^^^^ + +error: aborting due to 5 previous errors + diff --git a/tests/ui/layout/zero-sized-array-enum-niche.stderr b/tests/ui/layout/zero-sized-array-enum-niche.stderr index df9f1cc8d10..8161f97dde0 100644 --- a/tests/ui/layout/zero-sized-array-enum-niche.stderr +++ b/tests/ui/layout/zero-sized-array-enum-niche.stderr @@ -1,4 +1,4 @@ -error: layout_of(std::result::Result<[u32; 0], bool>) = Layout { +error: layout_of(Result<[u32; 0], bool>) = Layout { size: Size(4 bytes), align: AbiAndPrefAlign { abi: Align(4 bytes), @@ -232,7 +232,7 @@ error: layout_of(MultipleAlignments) = Layout { LL | enum MultipleAlignments { | ^^^^^^^^^^^^^^^^^^^^^^^ -error: layout_of(std::result::Result<[u32; 0], Packed<std::num::NonZeroU16>>) = Layout { +error: layout_of(Result<[u32; 0], Packed<NonZeroU16>>) = Layout { size: Size(4 bytes), align: AbiAndPrefAlign { abi: Align(4 bytes), @@ -337,7 +337,7 @@ error: layout_of(std::result::Result<[u32; 0], Packed<std::num::NonZeroU16>>) = LL | type NicheLosesToTagged = Result<[u32; 0], Packed<std::num::NonZeroU16>>; | ^^^^^^^^^^^^^^^^^^^^^^^ -error: layout_of(std::result::Result<[u32; 0], Packed<U16IsZero>>) = Layout { +error: layout_of(Result<[u32; 0], Packed<U16IsZero>>) = Layout { size: Size(4 bytes), align: AbiAndPrefAlign { abi: Align(4 bytes), diff --git a/tests/ui/lifetimes/issue-95023.stderr b/tests/ui/lifetimes/issue-95023.stderr index 5b93eff8614..6361d8ad30b 100644 --- a/tests/ui/lifetimes/issue-95023.stderr +++ b/tests/ui/lifetimes/issue-95023.stderr @@ -36,7 +36,7 @@ error[E0220]: associated type `B` not found for `Self` --> $DIR/issue-95023.rs:6:44 | LL | fn foo<const N: usize>(&self) -> Self::B<{N}>; - | ^ associated type `B` not found + | ^ help: `Self` has the following associated type: `Output` error: aborting due to 5 previous errors diff --git a/tests/ui/lifetimes/lifetime-elision-return-type-trait.stderr b/tests/ui/lifetimes/lifetime-elision-return-type-trait.stderr index ef1127c59ac..421ab3fcf4e 100644 --- a/tests/ui/lifetimes/lifetime-elision-return-type-trait.stderr +++ b/tests/ui/lifetimes/lifetime-elision-return-type-trait.stderr @@ -3,6 +3,12 @@ error[E0277]: the trait bound `Result<(), _>: Future` is not satisfied | LL | fn foo() -> impl Future<Item=(), Error=Box<dyn Error>> { | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ the trait `Future` is not implemented for `Result<(), _>` + | +help: this trait has no implementations, consider adding one + --> $DIR/lifetime-elision-return-type-trait.rs:1:1 + | +LL | trait Future { + | ^^^^^^^^^^^^ error: aborting due to previous error diff --git a/tests/ui/linkage-attr/common-linkage-non-zero-init.rs b/tests/ui/linkage-attr/common-linkage-non-zero-init.rs new file mode 100644 index 00000000000..ce8d9848e42 --- /dev/null +++ b/tests/ui/linkage-attr/common-linkage-non-zero-init.rs @@ -0,0 +1,14 @@ +// build-fail +// failure-status: 101 +// known-bug: #109681 + +// This test verifies that we continue to hit the LLVM error for common linkage with non-zero +// initializers, since it generates invalid LLVM IR. +// Linkages are internal features marked as perma-unstable, so we don't need to fix the issue +// for now. +#![crate_type="lib"] +#![feature(linkage)] + +#[linkage = "common"] +#[no_mangle] +pub static TEST: bool = true; diff --git a/tests/ui/linkage-attr/common-linkage-non-zero-init.stderr b/tests/ui/linkage-attr/common-linkage-non-zero-init.stderr new file mode 100644 index 00000000000..667bb3ec130 --- /dev/null +++ b/tests/ui/linkage-attr/common-linkage-non-zero-init.stderr @@ -0,0 +1,3 @@ +'common' global must have a zero initializer! +ptr @TEST +LLVM ERROR: Broken module found, compilation aborted! diff --git a/tests/ui/lint/cli-unknown-force-warn.rs b/tests/ui/lint/cli-unknown-force-warn.rs index f3dea87a6b6..a9e4e4a6017 100644 --- a/tests/ui/lint/cli-unknown-force-warn.rs +++ b/tests/ui/lint/cli-unknown-force-warn.rs @@ -1,7 +1,11 @@ // Checks that rustc correctly errors when passed an invalid lint with // `--force-warn`. This is a regression test for issue #86958. -// + +// check-pass // compile-flags: --force-warn foo-qux + // error-pattern: unknown lint: `foo_qux` +// error-pattern: requested on the command line with `--force-warn foo_qux` +// error-pattern: `#[warn(unknown_lints)]` on by default fn main() {} diff --git a/tests/ui/lint/cli-unknown-force-warn.stderr b/tests/ui/lint/cli-unknown-force-warn.stderr index 9ce9f405aee..2ee718a8c8e 100644 --- a/tests/ui/lint/cli-unknown-force-warn.stderr +++ b/tests/ui/lint/cli-unknown-force-warn.stderr @@ -1,11 +1,16 @@ -error[E0602]: unknown lint: `foo_qux` +warning[E0602]: unknown lint: `foo_qux` | = note: requested on the command line with `--force-warn foo_qux` + = note: `#[warn(unknown_lints)]` on by default -error[E0602]: unknown lint: `foo_qux` +warning[E0602]: unknown lint: `foo_qux` | = note: requested on the command line with `--force-warn foo_qux` -error: aborting due to 2 previous errors +warning[E0602]: unknown lint: `foo_qux` + | + = note: requested on the command line with `--force-warn foo_qux` + +warning: 3 warnings emitted For more information about this error, try `rustc --explain E0602`. diff --git a/tests/ui/lint/lint-ctypes-94223.rs b/tests/ui/lint/lint-ctypes-94223.rs index 70dd2a71f26..ac24f61b0ac 100644 --- a/tests/ui/lint/lint-ctypes-94223.rs +++ b/tests/ui/lint/lint-ctypes-94223.rs @@ -24,6 +24,13 @@ enum BadUnion { type Foo = extern "C" fn([u8]); //~^ ERROR `extern` fn uses type `[u8]`, which is not FFI-safe +pub trait FooTrait { + type FooType; +} + +pub type Foo2<T> = extern "C" fn(Option<&<T as FooTrait>::FooType>); +//~^ ERROR `extern` fn uses type `Option<&<T as FooTrait>::FooType>`, which is not FFI-safe + pub struct FfiUnsafe; #[allow(improper_ctypes_definitions)] diff --git a/tests/ui/lint/lint-ctypes-94223.stderr b/tests/ui/lint/lint-ctypes-94223.stderr index 49e64ed5140..bd127cf6004 100644 --- a/tests/ui/lint/lint-ctypes-94223.stderr +++ b/tests/ui/lint/lint-ctypes-94223.stderr @@ -66,8 +66,17 @@ LL | type Foo = extern "C" fn([u8]); = help: consider using a raw pointer instead = note: slices have no C equivalent +error: `extern` fn uses type `Option<&<T as FooTrait>::FooType>`, which is not FFI-safe + --> $DIR/lint-ctypes-94223.rs:31:20 + | +LL | pub type Foo2<T> = extern "C" fn(Option<&<T as FooTrait>::FooType>); + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ not FFI-safe + | + = help: consider adding a `#[repr(C)]`, `#[repr(transparent)]`, or integer `#[repr(...)]` attribute to this enum + = note: enum has no representation hint + error: `extern` fn uses type `FfiUnsafe`, which is not FFI-safe - --> $DIR/lint-ctypes-94223.rs:34:17 + --> $DIR/lint-ctypes-94223.rs:41:17 | LL | pub static BAD: extern "C" fn(FfiUnsafe) = f; | ^^^^^^^^^^^^^^^^^^^^^^^^ not FFI-safe @@ -75,13 +84,13 @@ LL | pub static BAD: extern "C" fn(FfiUnsafe) = f; = help: consider adding a `#[repr(C)]` or `#[repr(transparent)]` attribute to this struct = note: this struct has unspecified layout note: the type is defined here - --> $DIR/lint-ctypes-94223.rs:27:1 + --> $DIR/lint-ctypes-94223.rs:34:1 | LL | pub struct FfiUnsafe; | ^^^^^^^^^^^^^^^^^^^^ error: `extern` fn uses type `FfiUnsafe`, which is not FFI-safe - --> $DIR/lint-ctypes-94223.rs:37:30 + --> $DIR/lint-ctypes-94223.rs:44:30 | LL | pub static BAD_TWICE: Result<extern "C" fn(FfiUnsafe), extern "C" fn(FfiUnsafe)> = Ok(f); | ^^^^^^^^^^^^^^^^^^^^^^^^ not FFI-safe @@ -89,13 +98,13 @@ LL | pub static BAD_TWICE: Result<extern "C" fn(FfiUnsafe), extern "C" fn(FfiUns = help: consider adding a `#[repr(C)]` or `#[repr(transparent)]` attribute to this struct = note: this struct has unspecified layout note: the type is defined here - --> $DIR/lint-ctypes-94223.rs:27:1 + --> $DIR/lint-ctypes-94223.rs:34:1 | LL | pub struct FfiUnsafe; | ^^^^^^^^^^^^^^^^^^^^ error: `extern` fn uses type `FfiUnsafe`, which is not FFI-safe - --> $DIR/lint-ctypes-94223.rs:37:56 + --> $DIR/lint-ctypes-94223.rs:44:56 | LL | pub static BAD_TWICE: Result<extern "C" fn(FfiUnsafe), extern "C" fn(FfiUnsafe)> = Ok(f); | ^^^^^^^^^^^^^^^^^^^^^^^^ not FFI-safe @@ -103,13 +112,13 @@ LL | pub static BAD_TWICE: Result<extern "C" fn(FfiUnsafe), extern "C" fn(FfiUns = help: consider adding a `#[repr(C)]` or `#[repr(transparent)]` attribute to this struct = note: this struct has unspecified layout note: the type is defined here - --> $DIR/lint-ctypes-94223.rs:27:1 + --> $DIR/lint-ctypes-94223.rs:34:1 | LL | pub struct FfiUnsafe; | ^^^^^^^^^^^^^^^^^^^^ error: `extern` fn uses type `FfiUnsafe`, which is not FFI-safe - --> $DIR/lint-ctypes-94223.rs:41:22 + --> $DIR/lint-ctypes-94223.rs:48:22 | LL | pub const BAD_CONST: extern "C" fn(FfiUnsafe) = f; | ^^^^^^^^^^^^^^^^^^^^^^^^ not FFI-safe @@ -117,10 +126,10 @@ LL | pub const BAD_CONST: extern "C" fn(FfiUnsafe) = f; = help: consider adding a `#[repr(C)]` or `#[repr(transparent)]` attribute to this struct = note: this struct has unspecified layout note: the type is defined here - --> $DIR/lint-ctypes-94223.rs:27:1 + --> $DIR/lint-ctypes-94223.rs:34:1 | LL | pub struct FfiUnsafe; | ^^^^^^^^^^^^^^^^^^^^ -error: aborting due to 11 previous errors +error: aborting due to 12 previous errors diff --git a/tests/ui/lint/lint-ctypes-option-nonnull-unsized.rs b/tests/ui/lint/lint-ctypes-option-nonnull-unsized.rs new file mode 100644 index 00000000000..ca08eb23a57 --- /dev/null +++ b/tests/ui/lint/lint-ctypes-option-nonnull-unsized.rs @@ -0,0 +1,8 @@ +#![deny(improper_ctypes_definitions)] + +extern "C" fn foo<T: ?Sized + 'static>() -> Option<&'static T> { + //~^ ERROR `extern` fn uses type `Option<&T>`, which is not FFI-safe + None +} + +fn main() {} diff --git a/tests/ui/lint/lint-ctypes-option-nonnull-unsized.stderr b/tests/ui/lint/lint-ctypes-option-nonnull-unsized.stderr new file mode 100644 index 00000000000..f59fb3cc750 --- /dev/null +++ b/tests/ui/lint/lint-ctypes-option-nonnull-unsized.stderr @@ -0,0 +1,16 @@ +error: `extern` fn uses type `Option<&T>`, which is not FFI-safe + --> $DIR/lint-ctypes-option-nonnull-unsized.rs:3:45 + | +LL | extern "C" fn foo<T: ?Sized + 'static>() -> Option<&'static T> { + | ^^^^^^^^^^^^^^^^^^ not FFI-safe + | + = help: consider adding a `#[repr(C)]`, `#[repr(transparent)]`, or integer `#[repr(...)]` attribute to this enum + = note: enum has no representation hint +note: the lint level is defined here + --> $DIR/lint-ctypes-option-nonnull-unsized.rs:1:9 + | +LL | #![deny(improper_ctypes_definitions)] + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^ + +error: aborting due to previous error + diff --git a/tests/ui/lint/lint-removed-cmdline-deny.rs b/tests/ui/lint/lint-removed-cmdline-deny.rs new file mode 100644 index 00000000000..8cf91cf60eb --- /dev/null +++ b/tests/ui/lint/lint-removed-cmdline-deny.rs @@ -0,0 +1,13 @@ +// The raw_pointer_derived lint warns about its removal +// cc #30346 + +// compile-flags:-D renamed-and-removed-lints -D raw_pointer_derive + +// error-pattern:lint `raw_pointer_derive` has been removed +// error-pattern:requested on the command line with `-D raw_pointer_derive` +// error-pattern:requested on the command line with `-D renamed-and-removed-lints` + +#![warn(unused)] + +#[deny(warnings)] +fn main() { let unused = (); } diff --git a/tests/ui/lint/lint-removed-cmdline-deny.stderr b/tests/ui/lint/lint-removed-cmdline-deny.stderr new file mode 100644 index 00000000000..80c85d01e53 --- /dev/null +++ b/tests/ui/lint/lint-removed-cmdline-deny.stderr @@ -0,0 +1,28 @@ +error: lint `raw_pointer_derive` has been removed: using derive with raw pointers is ok + | + = note: requested on the command line with `-D raw_pointer_derive` + = note: requested on the command line with `-D renamed-and-removed-lints` + +error: lint `raw_pointer_derive` has been removed: using derive with raw pointers is ok + | + = note: requested on the command line with `-D raw_pointer_derive` + +error: lint `raw_pointer_derive` has been removed: using derive with raw pointers is ok + | + = note: requested on the command line with `-D raw_pointer_derive` + +error: unused variable: `unused` + --> $DIR/lint-removed-cmdline-deny.rs:13:17 + | +LL | fn main() { let unused = (); } + | ^^^^^^ help: if this is intentional, prefix it with an underscore: `_unused` + | +note: the lint level is defined here + --> $DIR/lint-removed-cmdline-deny.rs:12:8 + | +LL | #[deny(warnings)] + | ^^^^^^^^ + = note: `#[deny(unused_variables)]` implied by `#[deny(warnings)]` + +error: aborting due to 4 previous errors + diff --git a/tests/ui/lint/lint-removed-cmdline.rs b/tests/ui/lint/lint-removed-cmdline.rs index 462beabb945..34373df3a9c 100644 --- a/tests/ui/lint/lint-removed-cmdline.rs +++ b/tests/ui/lint/lint-removed-cmdline.rs @@ -4,6 +4,7 @@ // compile-flags:-D raw_pointer_derive // error-pattern:lint `raw_pointer_derive` has been removed +// error-pattern:`#[warn(renamed_and_removed_lints)]` on by default // error-pattern:requested on the command line with `-D raw_pointer_derive` #![warn(unused)] diff --git a/tests/ui/lint/lint-removed-cmdline.stderr b/tests/ui/lint/lint-removed-cmdline.stderr index 9be532ef234..ebfae34ade9 100644 --- a/tests/ui/lint/lint-removed-cmdline.stderr +++ b/tests/ui/lint/lint-removed-cmdline.stderr @@ -1,6 +1,7 @@ warning: lint `raw_pointer_derive` has been removed: using derive with raw pointers is ok | = note: requested on the command line with `-D raw_pointer_derive` + = note: `#[warn(renamed_and_removed_lints)]` on by default warning: lint `raw_pointer_derive` has been removed: using derive with raw pointers is ok | @@ -11,13 +12,13 @@ warning: lint `raw_pointer_derive` has been removed: using derive with raw point = note: requested on the command line with `-D raw_pointer_derive` error: unused variable: `unused` - --> $DIR/lint-removed-cmdline.rs:12:17 + --> $DIR/lint-removed-cmdline.rs:13:17 | LL | fn main() { let unused = (); } | ^^^^^^ help: if this is intentional, prefix it with an underscore: `_unused` | note: the lint level is defined here - --> $DIR/lint-removed-cmdline.rs:11:8 + --> $DIR/lint-removed-cmdline.rs:12:8 | LL | #[deny(warnings)] | ^^^^^^^^ diff --git a/tests/ui/lint/lint-renamed-cmdline-deny.rs b/tests/ui/lint/lint-renamed-cmdline-deny.rs new file mode 100644 index 00000000000..01629aaca80 --- /dev/null +++ b/tests/ui/lint/lint-renamed-cmdline-deny.rs @@ -0,0 +1,10 @@ +// compile-flags:-D renamed-and-removed-lints -D bare_trait_object + +// error-pattern:lint `bare_trait_object` has been renamed to `bare_trait_objects` +// error-pattern:use the new name `bare_trait_objects` +// error-pattern:requested on the command line with `-D bare_trait_object` +// error-pattern:requested on the command line with `-D renamed-and-removed-lints` +// error-pattern:unused + +#[deny(unused)] +fn main() { let unused = (); } diff --git a/tests/ui/lint/lint-renamed-cmdline-deny.stderr b/tests/ui/lint/lint-renamed-cmdline-deny.stderr new file mode 100644 index 00000000000..df22ef60daf --- /dev/null +++ b/tests/ui/lint/lint-renamed-cmdline-deny.stderr @@ -0,0 +1,31 @@ +error: lint `bare_trait_object` has been renamed to `bare_trait_objects` + | + = help: use the new name `bare_trait_objects` + = note: requested on the command line with `-D bare_trait_object` + = note: requested on the command line with `-D renamed-and-removed-lints` + +error: lint `bare_trait_object` has been renamed to `bare_trait_objects` + | + = help: use the new name `bare_trait_objects` + = note: requested on the command line with `-D bare_trait_object` + +error: lint `bare_trait_object` has been renamed to `bare_trait_objects` + | + = help: use the new name `bare_trait_objects` + = note: requested on the command line with `-D bare_trait_object` + +error: unused variable: `unused` + --> $DIR/lint-renamed-cmdline-deny.rs:10:17 + | +LL | fn main() { let unused = (); } + | ^^^^^^ help: if this is intentional, prefix it with an underscore: `_unused` + | +note: the lint level is defined here + --> $DIR/lint-renamed-cmdline-deny.rs:9:8 + | +LL | #[deny(unused)] + | ^^^^^^ + = note: `#[deny(unused_variables)]` implied by `#[deny(unused)]` + +error: aborting due to 4 previous errors + diff --git a/tests/ui/lint/lint-renamed-cmdline.rs b/tests/ui/lint/lint-renamed-cmdline.rs index c873771e308..fba7c33311d 100644 --- a/tests/ui/lint/lint-renamed-cmdline.rs +++ b/tests/ui/lint/lint-renamed-cmdline.rs @@ -2,6 +2,7 @@ // error-pattern:lint `bare_trait_object` has been renamed to `bare_trait_objects` // error-pattern:requested on the command line with `-D bare_trait_object` +// error-pattern:`#[warn(renamed_and_removed_lints)]` on by default // error-pattern:unused #[deny(unused)] diff --git a/tests/ui/lint/lint-renamed-cmdline.stderr b/tests/ui/lint/lint-renamed-cmdline.stderr index 8dfd61ac927..a41284003ed 100644 --- a/tests/ui/lint/lint-renamed-cmdline.stderr +++ b/tests/ui/lint/lint-renamed-cmdline.stderr @@ -1,23 +1,27 @@ warning: lint `bare_trait_object` has been renamed to `bare_trait_objects` | + = help: use the new name `bare_trait_objects` = note: requested on the command line with `-D bare_trait_object` + = note: `#[warn(renamed_and_removed_lints)]` on by default warning: lint `bare_trait_object` has been renamed to `bare_trait_objects` | + = help: use the new name `bare_trait_objects` = note: requested on the command line with `-D bare_trait_object` warning: lint `bare_trait_object` has been renamed to `bare_trait_objects` | + = help: use the new name `bare_trait_objects` = note: requested on the command line with `-D bare_trait_object` error: unused variable: `unused` - --> $DIR/lint-renamed-cmdline.rs:8:17 + --> $DIR/lint-renamed-cmdline.rs:9:17 | LL | fn main() { let unused = (); } | ^^^^^^ help: if this is intentional, prefix it with an underscore: `_unused` | note: the lint level is defined here - --> $DIR/lint-renamed-cmdline.rs:7:8 + --> $DIR/lint-renamed-cmdline.rs:8:8 | LL | #[deny(unused)] | ^^^^^^ diff --git a/tests/ui/lint/lint-unexported-no-mangle.stderr b/tests/ui/lint/lint-unexported-no-mangle.stderr index a11ee769c7c..85852782222 100644 --- a/tests/ui/lint/lint-unexported-no-mangle.stderr +++ b/tests/ui/lint/lint-unexported-no-mangle.stderr @@ -1,6 +1,7 @@ warning: lint `private_no_mangle_fns` has been removed: no longer a warning, `#[no_mangle]` functions always exported | = note: requested on the command line with `-F private_no_mangle_fns` + = note: `#[warn(renamed_and_removed_lints)]` on by default warning: lint `private_no_mangle_statics` has been removed: no longer a warning, `#[no_mangle]` statics always exported | diff --git a/tests/ui/lint/lint-unknown-lint-cmdline-allow.rs b/tests/ui/lint/lint-unknown-lint-cmdline-allow.rs new file mode 100644 index 00000000000..c7f8d434c04 --- /dev/null +++ b/tests/ui/lint/lint-unknown-lint-cmdline-allow.rs @@ -0,0 +1,4 @@ +// check-pass +// compile-flags:-A unknown-lints -D bogus -D dead_cod + +fn main() { } diff --git a/tests/ui/lint/lint-unknown-lint-cmdline-deny.rs b/tests/ui/lint/lint-unknown-lint-cmdline-deny.rs new file mode 100644 index 00000000000..31bc2047356 --- /dev/null +++ b/tests/ui/lint/lint-unknown-lint-cmdline-deny.rs @@ -0,0 +1,9 @@ +// compile-flags:-D unknown-lints -D bogus -D dead_cod + +// error-pattern:unknown lint: `bogus` +// error-pattern:requested on the command line with `-D bogus` +// error-pattern:requested on the command line with `-D dead_cod` +// error-pattern:requested on the command line with `-D unknown-lints` +// error-pattern:did you mean: `dead_code` + +fn main() { } diff --git a/tests/ui/lint/lint-unknown-lint-cmdline-deny.stderr b/tests/ui/lint/lint-unknown-lint-cmdline-deny.stderr new file mode 100644 index 00000000000..677b5edc894 --- /dev/null +++ b/tests/ui/lint/lint-unknown-lint-cmdline-deny.stderr @@ -0,0 +1,31 @@ +error[E0602]: unknown lint: `bogus` + | + = note: requested on the command line with `-D bogus` + = note: requested on the command line with `-D unknown-lints` + +error[E0602]: unknown lint: `dead_cod` + | + = help: did you mean: `dead_code` + = note: requested on the command line with `-D dead_cod` + +error[E0602]: unknown lint: `bogus` + | + = note: requested on the command line with `-D bogus` + +error[E0602]: unknown lint: `dead_cod` + | + = help: did you mean: `dead_code` + = note: requested on the command line with `-D dead_cod` + +error[E0602]: unknown lint: `bogus` + | + = note: requested on the command line with `-D bogus` + +error[E0602]: unknown lint: `dead_cod` + | + = help: did you mean: `dead_code` + = note: requested on the command line with `-D dead_cod` + +error: aborting due to 6 previous errors + +For more information about this error, try `rustc --explain E0602`. diff --git a/tests/ui/lint/lint-unknown-lint-cmdline.rs b/tests/ui/lint/lint-unknown-lint-cmdline.rs index 7f3f55fbad0..81539cb6dc1 100644 --- a/tests/ui/lint/lint-unknown-lint-cmdline.rs +++ b/tests/ui/lint/lint-unknown-lint-cmdline.rs @@ -1,7 +1,9 @@ +// check-pass // compile-flags:-D bogus -D dead_cod // error-pattern:unknown lint: `bogus` // error-pattern:requested on the command line with `-D bogus` +// error-pattern:`#[warn(unknown_lints)]` on by default // error-pattern:unknown lint: `dead_cod` // error-pattern:requested on the command line with `-D dead_cod` // error-pattern:did you mean: `dead_code` diff --git a/tests/ui/lint/lint-unknown-lint-cmdline.stderr b/tests/ui/lint/lint-unknown-lint-cmdline.stderr index 3855d552792..10db76ac4f1 100644 --- a/tests/ui/lint/lint-unknown-lint-cmdline.stderr +++ b/tests/ui/lint/lint-unknown-lint-cmdline.stderr @@ -1,21 +1,31 @@ -error[E0602]: unknown lint: `bogus` +warning[E0602]: unknown lint: `bogus` | = note: requested on the command line with `-D bogus` + = note: `#[warn(unknown_lints)]` on by default -error[E0602]: unknown lint: `dead_cod` +warning[E0602]: unknown lint: `dead_cod` | = help: did you mean: `dead_code` = note: requested on the command line with `-D dead_cod` -error[E0602]: unknown lint: `bogus` +warning[E0602]: unknown lint: `bogus` | = note: requested on the command line with `-D bogus` -error[E0602]: unknown lint: `dead_cod` +warning[E0602]: unknown lint: `dead_cod` | = help: did you mean: `dead_code` = note: requested on the command line with `-D dead_cod` -error: aborting due to 4 previous errors +warning[E0602]: unknown lint: `bogus` + | + = note: requested on the command line with `-D bogus` + +warning[E0602]: unknown lint: `dead_cod` + | + = help: did you mean: `dead_code` + = note: requested on the command line with `-D dead_cod` + +warning: 6 warnings emitted For more information about this error, try `rustc --explain E0602`. diff --git a/tests/ui/lint/reference_casting.rs b/tests/ui/lint/reference_casting.rs index 92d985948ec..7745d4ef4c3 100644 --- a/tests/ui/lint/reference_casting.rs +++ b/tests/ui/lint/reference_casting.rs @@ -36,6 +36,10 @@ unsafe fn ref_to_mut() { //~^ ERROR casting `&T` to `&mut T` is undefined behavior let _num = &mut *std::mem::transmute::<_, *mut i32>(num); //~^ ERROR casting `&T` to `&mut T` is undefined behavior + let _num = &mut *std::cell::UnsafeCell::raw_get( + //~^ ERROR casting `&T` to `&mut T` is undefined behavior + num as *const i32 as *const std::cell::UnsafeCell<i32> + ); let deferred = num as *const i32 as *mut i32; let _num = &mut *deferred; @@ -50,6 +54,16 @@ unsafe fn ref_to_mut() { &mut *((this as *const _) as *mut _) //~^ ERROR casting `&T` to `&mut T` is undefined behavior } + + fn as_mut<T>(x: &T) -> &mut T { + unsafe { &mut *std::cell::UnsafeCell::raw_get(x as *const _ as *const _) } + //~^ ERROR casting `&T` to `&mut T` is undefined behavior + } + + fn as_mut_i32(x: &i32) -> &mut i32 { + unsafe { &mut *std::cell::UnsafeCell::raw_get(x as *const _ as *const _) } + //~^ ERROR casting `&T` to `&mut T` is undefined behavior + } } unsafe fn assign_to_ref() { @@ -111,6 +125,20 @@ unsafe fn no_warn() { let mut value = 3; let value: *const i32 = &mut value; *(value as *const i16 as *mut i16) = 42; + + fn safe_as_mut<T>(x: &std::cell::UnsafeCell<T>) -> &mut T { + unsafe { &mut *std::cell::UnsafeCell::raw_get(x as *const _ as *const _) } + } + + fn cell_as_mut(x: &std::cell::Cell<i32>) -> &mut i32 { + unsafe { &mut *std::cell::UnsafeCell::raw_get(x as *const _ as *const _) } + } + + #[repr(transparent)] + struct DoesContainUnsafeCell(std::cell::UnsafeCell<i32>); + fn safe_as_mut2(x: &DoesContainUnsafeCell) -> &mut DoesContainUnsafeCell { + unsafe { &mut *std::cell::UnsafeCell::raw_get(x as *const _ as *const _) } + } } fn main() {} diff --git a/tests/ui/lint/reference_casting.stderr b/tests/ui/lint/reference_casting.stderr index 47b95460ec3..1189942c809 100644 --- a/tests/ui/lint/reference_casting.stderr +++ b/tests/ui/lint/reference_casting.stderr @@ -80,7 +80,19 @@ LL | let _num = &mut *std::mem::transmute::<_, *mut i32>(num); = note: for more information, visit <https://doc.rust-lang.org/book/ch15-05-interior-mutability.html> error: casting `&T` to `&mut T` is undefined behavior, even if the reference is unused, consider instead using an `UnsafeCell` - --> $DIR/reference_casting.rs:41:16 + --> $DIR/reference_casting.rs:39:16 + | +LL | let _num = &mut *std::cell::UnsafeCell::raw_get( + | ________________^ +LL | | +LL | | num as *const i32 as *const std::cell::UnsafeCell<i32> +LL | | ); + | |_____^ + | + = note: for more information, visit <https://doc.rust-lang.org/book/ch15-05-interior-mutability.html> + +error: casting `&T` to `&mut T` is undefined behavior, even if the reference is unused, consider instead using an `UnsafeCell` + --> $DIR/reference_casting.rs:45:16 | LL | let deferred = num as *const i32 as *mut i32; | ----------------------------- casting happend here @@ -90,7 +102,7 @@ LL | let _num = &mut *deferred; = note: for more information, visit <https://doc.rust-lang.org/book/ch15-05-interior-mutability.html> error: casting `&T` to `&mut T` is undefined behavior, even if the reference is unused, consider instead using an `UnsafeCell` - --> $DIR/reference_casting.rs:44:16 + --> $DIR/reference_casting.rs:48:16 | LL | let deferred = (std::ptr::from_ref(num) as *const i32 as *const i32).cast_mut() as *mut i32; | ---------------------------------------------------------------------------- casting happend here @@ -100,7 +112,7 @@ LL | let _num = &mut *deferred; = note: for more information, visit <https://doc.rust-lang.org/book/ch15-05-interior-mutability.html> error: casting `&T` to `&mut T` is undefined behavior, even if the reference is unused, consider instead using an `UnsafeCell` - --> $DIR/reference_casting.rs:46:16 + --> $DIR/reference_casting.rs:50:16 | LL | let _num = &mut *(num as *const _ as usize as *mut i32); | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ @@ -108,15 +120,31 @@ LL | let _num = &mut *(num as *const _ as usize as *mut i32); = note: for more information, visit <https://doc.rust-lang.org/book/ch15-05-interior-mutability.html> error: casting `&T` to `&mut T` is undefined behavior, even if the reference is unused, consider instead using an `UnsafeCell` - --> $DIR/reference_casting.rs:50:9 + --> $DIR/reference_casting.rs:54:9 | LL | &mut *((this as *const _) as *mut _) | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ | = note: for more information, visit <https://doc.rust-lang.org/book/ch15-05-interior-mutability.html> +error: casting `&T` to `&mut T` is undefined behavior, even if the reference is unused, consider instead using an `UnsafeCell` + --> $DIR/reference_casting.rs:59:18 + | +LL | unsafe { &mut *std::cell::UnsafeCell::raw_get(x as *const _ as *const _) } + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + | + = note: for more information, visit <https://doc.rust-lang.org/book/ch15-05-interior-mutability.html> + +error: casting `&T` to `&mut T` is undefined behavior, even if the reference is unused, consider instead using an `UnsafeCell` + --> $DIR/reference_casting.rs:64:18 + | +LL | unsafe { &mut *std::cell::UnsafeCell::raw_get(x as *const _ as *const _) } + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + | + = note: for more information, visit <https://doc.rust-lang.org/book/ch15-05-interior-mutability.html> + error: assigning to `&T` is undefined behavior, consider using an `UnsafeCell` - --> $DIR/reference_casting.rs:60:5 + --> $DIR/reference_casting.rs:74:5 | LL | *(a as *const _ as *mut _) = String::from("Replaced"); | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ @@ -124,7 +152,7 @@ LL | *(a as *const _ as *mut _) = String::from("Replaced"); = note: for more information, visit <https://doc.rust-lang.org/book/ch15-05-interior-mutability.html> error: assigning to `&T` is undefined behavior, consider using an `UnsafeCell` - --> $DIR/reference_casting.rs:62:5 + --> $DIR/reference_casting.rs:76:5 | LL | *(a as *const _ as *mut String) += " world"; | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ @@ -132,7 +160,7 @@ LL | *(a as *const _ as *mut String) += " world"; = note: for more information, visit <https://doc.rust-lang.org/book/ch15-05-interior-mutability.html> error: assigning to `&T` is undefined behavior, consider using an `UnsafeCell` - --> $DIR/reference_casting.rs:64:5 + --> $DIR/reference_casting.rs:78:5 | LL | *std::ptr::from_ref(num).cast_mut() += 1; | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ @@ -140,7 +168,7 @@ LL | *std::ptr::from_ref(num).cast_mut() += 1; = note: for more information, visit <https://doc.rust-lang.org/book/ch15-05-interior-mutability.html> error: assigning to `&T` is undefined behavior, consider using an `UnsafeCell` - --> $DIR/reference_casting.rs:66:5 + --> $DIR/reference_casting.rs:80:5 | LL | *std::ptr::from_ref({ num }).cast_mut() += 1; | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ @@ -148,7 +176,7 @@ LL | *std::ptr::from_ref({ num }).cast_mut() += 1; = note: for more information, visit <https://doc.rust-lang.org/book/ch15-05-interior-mutability.html> error: assigning to `&T` is undefined behavior, consider using an `UnsafeCell` - --> $DIR/reference_casting.rs:68:5 + --> $DIR/reference_casting.rs:82:5 | LL | *{ std::ptr::from_ref(num) }.cast_mut() += 1; | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ @@ -156,7 +184,7 @@ LL | *{ std::ptr::from_ref(num) }.cast_mut() += 1; = note: for more information, visit <https://doc.rust-lang.org/book/ch15-05-interior-mutability.html> error: assigning to `&T` is undefined behavior, consider using an `UnsafeCell` - --> $DIR/reference_casting.rs:70:5 + --> $DIR/reference_casting.rs:84:5 | LL | *(std::ptr::from_ref({ num }) as *mut i32) += 1; | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ @@ -164,7 +192,7 @@ LL | *(std::ptr::from_ref({ num }) as *mut i32) += 1; = note: for more information, visit <https://doc.rust-lang.org/book/ch15-05-interior-mutability.html> error: assigning to `&T` is undefined behavior, consider using an `UnsafeCell` - --> $DIR/reference_casting.rs:72:5 + --> $DIR/reference_casting.rs:86:5 | LL | *std::mem::transmute::<_, *mut i32>(num) += 1; | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ @@ -172,7 +200,7 @@ LL | *std::mem::transmute::<_, *mut i32>(num) += 1; = note: for more information, visit <https://doc.rust-lang.org/book/ch15-05-interior-mutability.html> error: assigning to `&T` is undefined behavior, consider using an `UnsafeCell` - --> $DIR/reference_casting.rs:74:5 + --> $DIR/reference_casting.rs:88:5 | LL | / std::ptr::write( LL | | @@ -184,7 +212,7 @@ LL | | ); = note: for more information, visit <https://doc.rust-lang.org/book/ch15-05-interior-mutability.html> error: assigning to `&T` is undefined behavior, consider using an `UnsafeCell` - --> $DIR/reference_casting.rs:81:5 + --> $DIR/reference_casting.rs:95:5 | LL | let value = num as *const i32 as *mut i32; | ----------------------------- casting happend here @@ -194,7 +222,7 @@ LL | *value = 1; = note: for more information, visit <https://doc.rust-lang.org/book/ch15-05-interior-mutability.html> error: assigning to `&T` is undefined behavior, consider using an `UnsafeCell` - --> $DIR/reference_casting.rs:83:5 + --> $DIR/reference_casting.rs:97:5 | LL | *(num as *const i32).cast::<i32>().cast_mut() = 2; | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ @@ -202,7 +230,7 @@ LL | *(num as *const i32).cast::<i32>().cast_mut() = 2; = note: for more information, visit <https://doc.rust-lang.org/book/ch15-05-interior-mutability.html> error: assigning to `&T` is undefined behavior, consider using an `UnsafeCell` - --> $DIR/reference_casting.rs:85:5 + --> $DIR/reference_casting.rs:99:5 | LL | *(num as *const _ as usize as *mut i32) = 2; | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ @@ -210,7 +238,7 @@ LL | *(num as *const _ as usize as *mut i32) = 2; = note: for more information, visit <https://doc.rust-lang.org/book/ch15-05-interior-mutability.html> error: assigning to `&T` is undefined behavior, consider using an `UnsafeCell` - --> $DIR/reference_casting.rs:87:5 + --> $DIR/reference_casting.rs:101:5 | LL | let value = num as *const i32 as *mut i32; | ----------------------------- casting happend here @@ -221,7 +249,7 @@ LL | std::ptr::write(value, 2); = note: for more information, visit <https://doc.rust-lang.org/book/ch15-05-interior-mutability.html> error: assigning to `&T` is undefined behavior, consider using an `UnsafeCell` - --> $DIR/reference_casting.rs:89:5 + --> $DIR/reference_casting.rs:103:5 | LL | let value = num as *const i32 as *mut i32; | ----------------------------- casting happend here @@ -232,7 +260,7 @@ LL | std::ptr::write_unaligned(value, 2); = note: for more information, visit <https://doc.rust-lang.org/book/ch15-05-interior-mutability.html> error: assigning to `&T` is undefined behavior, consider using an `UnsafeCell` - --> $DIR/reference_casting.rs:91:5 + --> $DIR/reference_casting.rs:105:5 | LL | let value = num as *const i32 as *mut i32; | ----------------------------- casting happend here @@ -243,12 +271,12 @@ LL | std::ptr::write_volatile(value, 2); = note: for more information, visit <https://doc.rust-lang.org/book/ch15-05-interior-mutability.html> error: assigning to `&T` is undefined behavior, consider using an `UnsafeCell` - --> $DIR/reference_casting.rs:95:9 + --> $DIR/reference_casting.rs:109:9 | LL | *(this as *const _ as *mut _) = a; | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ | = note: for more information, visit <https://doc.rust-lang.org/book/ch15-05-interior-mutability.html> -error: aborting due to 29 previous errors +error: aborting due to 32 previous errors diff --git a/tests/ui/namespace/namespace-mix.stderr b/tests/ui/namespace/namespace-mix.stderr index 3ac5e96c574..4eff08ead42 100644 --- a/tests/ui/namespace/namespace-mix.stderr +++ b/tests/ui/namespace/namespace-mix.stderr @@ -114,6 +114,11 @@ LL | check(m1::S{}); | | | required by a bound introduced by this call | +help: this trait has no implementations, consider adding one + --> $DIR/namespace-mix.rs:20:1 + | +LL | trait Impossible {} + | ^^^^^^^^^^^^^^^^ note: required by a bound in `check` --> $DIR/namespace-mix.rs:21:13 | @@ -128,6 +133,11 @@ LL | check(m2::S{}); | | | required by a bound introduced by this call | +help: this trait has no implementations, consider adding one + --> $DIR/namespace-mix.rs:20:1 + | +LL | trait Impossible {} + | ^^^^^^^^^^^^^^^^ note: required by a bound in `check` --> $DIR/namespace-mix.rs:21:13 | @@ -142,6 +152,11 @@ LL | check(m2::S); | | | required by a bound introduced by this call | +help: this trait has no implementations, consider adding one + --> $DIR/namespace-mix.rs:20:1 + | +LL | trait Impossible {} + | ^^^^^^^^^^^^^^^^ note: required by a bound in `check` --> $DIR/namespace-mix.rs:21:13 | @@ -156,6 +171,11 @@ LL | check(xm1::S{}); | | | required by a bound introduced by this call | +help: this trait has no implementations, consider adding one + --> $DIR/namespace-mix.rs:20:1 + | +LL | trait Impossible {} + | ^^^^^^^^^^^^^^^^ note: required by a bound in `check` --> $DIR/namespace-mix.rs:21:13 | @@ -170,6 +190,11 @@ LL | check(xm2::S{}); | | | required by a bound introduced by this call | +help: this trait has no implementations, consider adding one + --> $DIR/namespace-mix.rs:20:1 + | +LL | trait Impossible {} + | ^^^^^^^^^^^^^^^^ note: required by a bound in `check` --> $DIR/namespace-mix.rs:21:13 | @@ -184,6 +209,11 @@ LL | check(xm2::S); | | | required by a bound introduced by this call | +help: this trait has no implementations, consider adding one + --> $DIR/namespace-mix.rs:20:1 + | +LL | trait Impossible {} + | ^^^^^^^^^^^^^^^^ note: required by a bound in `check` --> $DIR/namespace-mix.rs:21:13 | @@ -198,6 +228,11 @@ LL | check(m3::TS{}); | | | required by a bound introduced by this call | +help: this trait has no implementations, consider adding one + --> $DIR/namespace-mix.rs:20:1 + | +LL | trait Impossible {} + | ^^^^^^^^^^^^^^^^ note: required by a bound in `check` --> $DIR/namespace-mix.rs:21:13 | @@ -212,6 +247,11 @@ LL | check(m3::TS); | | | required by a bound introduced by this call | +help: this trait has no implementations, consider adding one + --> $DIR/namespace-mix.rs:20:1 + | +LL | trait Impossible {} + | ^^^^^^^^^^^^^^^^ note: required by a bound in `check` --> $DIR/namespace-mix.rs:21:13 | @@ -226,6 +266,11 @@ LL | check(m4::TS{}); | | | required by a bound introduced by this call | +help: this trait has no implementations, consider adding one + --> $DIR/namespace-mix.rs:20:1 + | +LL | trait Impossible {} + | ^^^^^^^^^^^^^^^^ note: required by a bound in `check` --> $DIR/namespace-mix.rs:21:13 | @@ -240,6 +285,11 @@ LL | check(m4::TS); | | | required by a bound introduced by this call | +help: this trait has no implementations, consider adding one + --> $DIR/namespace-mix.rs:20:1 + | +LL | trait Impossible {} + | ^^^^^^^^^^^^^^^^ note: required by a bound in `check` --> $DIR/namespace-mix.rs:21:13 | @@ -254,6 +304,11 @@ LL | check(xm3::TS{}); | | | required by a bound introduced by this call | +help: this trait has no implementations, consider adding one + --> $DIR/namespace-mix.rs:20:1 + | +LL | trait Impossible {} + | ^^^^^^^^^^^^^^^^ note: required by a bound in `check` --> $DIR/namespace-mix.rs:21:13 | @@ -268,6 +323,11 @@ LL | check(xm3::TS); | | | required by a bound introduced by this call | +help: this trait has no implementations, consider adding one + --> $DIR/namespace-mix.rs:20:1 + | +LL | trait Impossible {} + | ^^^^^^^^^^^^^^^^ note: required by a bound in `check` --> $DIR/namespace-mix.rs:21:13 | @@ -282,6 +342,11 @@ LL | check(xm4::TS{}); | | | required by a bound introduced by this call | +help: this trait has no implementations, consider adding one + --> $DIR/namespace-mix.rs:20:1 + | +LL | trait Impossible {} + | ^^^^^^^^^^^^^^^^ note: required by a bound in `check` --> $DIR/namespace-mix.rs:21:13 | @@ -296,6 +361,11 @@ LL | check(xm4::TS); | | | required by a bound introduced by this call | +help: this trait has no implementations, consider adding one + --> $DIR/namespace-mix.rs:20:1 + | +LL | trait Impossible {} + | ^^^^^^^^^^^^^^^^ note: required by a bound in `check` --> $DIR/namespace-mix.rs:21:13 | @@ -310,6 +380,11 @@ LL | check(m5::US{}); | | | required by a bound introduced by this call | +help: this trait has no implementations, consider adding one + --> $DIR/namespace-mix.rs:20:1 + | +LL | trait Impossible {} + | ^^^^^^^^^^^^^^^^ note: required by a bound in `check` --> $DIR/namespace-mix.rs:21:13 | @@ -324,6 +399,11 @@ LL | check(m5::US); | | | required by a bound introduced by this call | +help: this trait has no implementations, consider adding one + --> $DIR/namespace-mix.rs:20:1 + | +LL | trait Impossible {} + | ^^^^^^^^^^^^^^^^ note: required by a bound in `check` --> $DIR/namespace-mix.rs:21:13 | @@ -338,6 +418,11 @@ LL | check(m6::US{}); | | | required by a bound introduced by this call | +help: this trait has no implementations, consider adding one + --> $DIR/namespace-mix.rs:20:1 + | +LL | trait Impossible {} + | ^^^^^^^^^^^^^^^^ note: required by a bound in `check` --> $DIR/namespace-mix.rs:21:13 | @@ -352,6 +437,11 @@ LL | check(m6::US); | | | required by a bound introduced by this call | +help: this trait has no implementations, consider adding one + --> $DIR/namespace-mix.rs:20:1 + | +LL | trait Impossible {} + | ^^^^^^^^^^^^^^^^ note: required by a bound in `check` --> $DIR/namespace-mix.rs:21:13 | @@ -366,6 +456,11 @@ LL | check(xm5::US{}); | | | required by a bound introduced by this call | +help: this trait has no implementations, consider adding one + --> $DIR/namespace-mix.rs:20:1 + | +LL | trait Impossible {} + | ^^^^^^^^^^^^^^^^ note: required by a bound in `check` --> $DIR/namespace-mix.rs:21:13 | @@ -380,6 +475,11 @@ LL | check(xm5::US); | | | required by a bound introduced by this call | +help: this trait has no implementations, consider adding one + --> $DIR/namespace-mix.rs:20:1 + | +LL | trait Impossible {} + | ^^^^^^^^^^^^^^^^ note: required by a bound in `check` --> $DIR/namespace-mix.rs:21:13 | @@ -394,6 +494,11 @@ LL | check(xm6::US{}); | | | required by a bound introduced by this call | +help: this trait has no implementations, consider adding one + --> $DIR/namespace-mix.rs:20:1 + | +LL | trait Impossible {} + | ^^^^^^^^^^^^^^^^ note: required by a bound in `check` --> $DIR/namespace-mix.rs:21:13 | @@ -408,6 +513,11 @@ LL | check(xm6::US); | | | required by a bound introduced by this call | +help: this trait has no implementations, consider adding one + --> $DIR/namespace-mix.rs:20:1 + | +LL | trait Impossible {} + | ^^^^^^^^^^^^^^^^ note: required by a bound in `check` --> $DIR/namespace-mix.rs:21:13 | @@ -422,6 +532,11 @@ LL | check(m7::V{}); | | | required by a bound introduced by this call | +help: this trait has no implementations, consider adding one + --> $DIR/namespace-mix.rs:20:1 + | +LL | trait Impossible {} + | ^^^^^^^^^^^^^^^^ note: required by a bound in `check` --> $DIR/namespace-mix.rs:21:13 | @@ -436,6 +551,11 @@ LL | check(m8::V{}); | | | required by a bound introduced by this call | +help: this trait has no implementations, consider adding one + --> $DIR/namespace-mix.rs:20:1 + | +LL | trait Impossible {} + | ^^^^^^^^^^^^^^^^ note: required by a bound in `check` --> $DIR/namespace-mix.rs:21:13 | @@ -450,6 +570,11 @@ LL | check(m8::V); | | | required by a bound introduced by this call | +help: this trait has no implementations, consider adding one + --> $DIR/namespace-mix.rs:20:1 + | +LL | trait Impossible {} + | ^^^^^^^^^^^^^^^^ note: required by a bound in `check` --> $DIR/namespace-mix.rs:21:13 | @@ -464,6 +589,11 @@ LL | check(xm7::V{}); | | | required by a bound introduced by this call | +help: this trait has no implementations, consider adding one + --> $DIR/namespace-mix.rs:20:1 + | +LL | trait Impossible {} + | ^^^^^^^^^^^^^^^^ note: required by a bound in `check` --> $DIR/namespace-mix.rs:21:13 | @@ -478,6 +608,11 @@ LL | check(xm8::V{}); | | | required by a bound introduced by this call | +help: this trait has no implementations, consider adding one + --> $DIR/namespace-mix.rs:20:1 + | +LL | trait Impossible {} + | ^^^^^^^^^^^^^^^^ note: required by a bound in `check` --> $DIR/namespace-mix.rs:21:13 | @@ -492,6 +627,11 @@ LL | check(xm8::V); | | | required by a bound introduced by this call | +help: this trait has no implementations, consider adding one + --> $DIR/namespace-mix.rs:20:1 + | +LL | trait Impossible {} + | ^^^^^^^^^^^^^^^^ note: required by a bound in `check` --> $DIR/namespace-mix.rs:21:13 | @@ -506,6 +646,11 @@ LL | check(m9::TV{}); | | | required by a bound introduced by this call | +help: this trait has no implementations, consider adding one + --> $DIR/namespace-mix.rs:20:1 + | +LL | trait Impossible {} + | ^^^^^^^^^^^^^^^^ note: required by a bound in `check` --> $DIR/namespace-mix.rs:21:13 | @@ -520,6 +665,11 @@ LL | check(m9::TV); | | | required by a bound introduced by this call | +help: this trait has no implementations, consider adding one + --> $DIR/namespace-mix.rs:20:1 + | +LL | trait Impossible {} + | ^^^^^^^^^^^^^^^^ note: required by a bound in `check` --> $DIR/namespace-mix.rs:21:13 | @@ -534,6 +684,11 @@ LL | check(mA::TV{}); | | | required by a bound introduced by this call | +help: this trait has no implementations, consider adding one + --> $DIR/namespace-mix.rs:20:1 + | +LL | trait Impossible {} + | ^^^^^^^^^^^^^^^^ note: required by a bound in `check` --> $DIR/namespace-mix.rs:21:13 | @@ -548,6 +703,11 @@ LL | check(mA::TV); | | | required by a bound introduced by this call | +help: this trait has no implementations, consider adding one + --> $DIR/namespace-mix.rs:20:1 + | +LL | trait Impossible {} + | ^^^^^^^^^^^^^^^^ note: required by a bound in `check` --> $DIR/namespace-mix.rs:21:13 | @@ -562,6 +722,11 @@ LL | check(xm9::TV{}); | | | required by a bound introduced by this call | +help: this trait has no implementations, consider adding one + --> $DIR/namespace-mix.rs:20:1 + | +LL | trait Impossible {} + | ^^^^^^^^^^^^^^^^ note: required by a bound in `check` --> $DIR/namespace-mix.rs:21:13 | @@ -576,6 +741,11 @@ LL | check(xm9::TV); | | | required by a bound introduced by this call | +help: this trait has no implementations, consider adding one + --> $DIR/namespace-mix.rs:20:1 + | +LL | trait Impossible {} + | ^^^^^^^^^^^^^^^^ note: required by a bound in `check` --> $DIR/namespace-mix.rs:21:13 | @@ -590,6 +760,11 @@ LL | check(xmA::TV{}); | | | required by a bound introduced by this call | +help: this trait has no implementations, consider adding one + --> $DIR/namespace-mix.rs:20:1 + | +LL | trait Impossible {} + | ^^^^^^^^^^^^^^^^ note: required by a bound in `check` --> $DIR/namespace-mix.rs:21:13 | @@ -604,6 +779,11 @@ LL | check(xmA::TV); | | | required by a bound introduced by this call | +help: this trait has no implementations, consider adding one + --> $DIR/namespace-mix.rs:20:1 + | +LL | trait Impossible {} + | ^^^^^^^^^^^^^^^^ note: required by a bound in `check` --> $DIR/namespace-mix.rs:21:13 | @@ -618,6 +798,11 @@ LL | check(mB::UV{}); | | | required by a bound introduced by this call | +help: this trait has no implementations, consider adding one + --> $DIR/namespace-mix.rs:20:1 + | +LL | trait Impossible {} + | ^^^^^^^^^^^^^^^^ note: required by a bound in `check` --> $DIR/namespace-mix.rs:21:13 | @@ -632,6 +817,11 @@ LL | check(mB::UV); | | | required by a bound introduced by this call | +help: this trait has no implementations, consider adding one + --> $DIR/namespace-mix.rs:20:1 + | +LL | trait Impossible {} + | ^^^^^^^^^^^^^^^^ note: required by a bound in `check` --> $DIR/namespace-mix.rs:21:13 | @@ -646,6 +836,11 @@ LL | check(mC::UV{}); | | | required by a bound introduced by this call | +help: this trait has no implementations, consider adding one + --> $DIR/namespace-mix.rs:20:1 + | +LL | trait Impossible {} + | ^^^^^^^^^^^^^^^^ note: required by a bound in `check` --> $DIR/namespace-mix.rs:21:13 | @@ -660,6 +855,11 @@ LL | check(mC::UV); | | | required by a bound introduced by this call | +help: this trait has no implementations, consider adding one + --> $DIR/namespace-mix.rs:20:1 + | +LL | trait Impossible {} + | ^^^^^^^^^^^^^^^^ note: required by a bound in `check` --> $DIR/namespace-mix.rs:21:13 | @@ -674,6 +874,11 @@ LL | check(xmB::UV{}); | | | required by a bound introduced by this call | +help: this trait has no implementations, consider adding one + --> $DIR/namespace-mix.rs:20:1 + | +LL | trait Impossible {} + | ^^^^^^^^^^^^^^^^ note: required by a bound in `check` --> $DIR/namespace-mix.rs:21:13 | @@ -688,6 +893,11 @@ LL | check(xmB::UV); | | | required by a bound introduced by this call | +help: this trait has no implementations, consider adding one + --> $DIR/namespace-mix.rs:20:1 + | +LL | trait Impossible {} + | ^^^^^^^^^^^^^^^^ note: required by a bound in `check` --> $DIR/namespace-mix.rs:21:13 | @@ -702,6 +912,11 @@ LL | check(xmC::UV{}); | | | required by a bound introduced by this call | +help: this trait has no implementations, consider adding one + --> $DIR/namespace-mix.rs:20:1 + | +LL | trait Impossible {} + | ^^^^^^^^^^^^^^^^ note: required by a bound in `check` --> $DIR/namespace-mix.rs:21:13 | @@ -716,6 +931,11 @@ LL | check(xmC::UV); | | | required by a bound introduced by this call | +help: this trait has no implementations, consider adding one + --> $DIR/namespace-mix.rs:20:1 + | +LL | trait Impossible {} + | ^^^^^^^^^^^^^^^^ note: required by a bound in `check` --> $DIR/namespace-mix.rs:21:13 | diff --git a/tests/ui/nested-ty-params.rs b/tests/ui/nested-ty-params.rs index 85413acdb14..25bac1ba24b 100644 --- a/tests/ui/nested-ty-params.rs +++ b/tests/ui/nested-ty-params.rs @@ -1,4 +1,4 @@ -// error-pattern:can't use generic parameters from outer function +// error-pattern:can't use generic parameters from outer item fn hd<U>(v: Vec<U> ) -> U { fn hd1(w: [U]) -> U { return w[0]; } diff --git a/tests/ui/nested-ty-params.stderr b/tests/ui/nested-ty-params.stderr index 8f4746f5ec3..a9cdec66719 100644 --- a/tests/ui/nested-ty-params.stderr +++ b/tests/ui/nested-ty-params.stderr @@ -1,22 +1,22 @@ -error[E0401]: can't use generic parameters from outer function +error[E0401]: can't use generic parameters from outer item --> $DIR/nested-ty-params.rs:3:16 | LL | fn hd<U>(v: Vec<U> ) -> U { - | - type parameter from outer function + | - type parameter from outer item LL | fn hd1(w: [U]) -> U { return w[0]; } - | - ^ use of generic parameter from outer function + | - ^ use of generic parameter from outer item | | - | help: try using a local generic parameter instead: `<U>` + | help: try introducing a local generic parameter here: `<U>` -error[E0401]: can't use generic parameters from outer function +error[E0401]: can't use generic parameters from outer item --> $DIR/nested-ty-params.rs:3:23 | LL | fn hd<U>(v: Vec<U> ) -> U { - | - type parameter from outer function + | - type parameter from outer item LL | fn hd1(w: [U]) -> U { return w[0]; } - | - ^ use of generic parameter from outer function + | - ^ use of generic parameter from outer item | | - | help: try using a local generic parameter instead: `<U>` + | help: try introducing a local generic parameter here: `<U>` error: aborting due to 2 previous errors diff --git a/tests/ui/never_type/feature-gate-never_type_fallback.stderr b/tests/ui/never_type/feature-gate-never_type_fallback.stderr index 2db1cc4b776..56aafbb4ce8 100644 --- a/tests/ui/never_type/feature-gate-never_type_fallback.stderr +++ b/tests/ui/never_type/feature-gate-never_type_fallback.stderr @@ -8,6 +8,11 @@ LL | foo(panic!()) | | this tail expression is of type `()` | required by a bound introduced by this call | +help: this trait has no implementations, consider adding one + --> $DIR/feature-gate-never_type_fallback.rs:7:1 + | +LL | trait T {} + | ^^^^^^^ note: required by a bound in `foo` --> $DIR/feature-gate-never_type_fallback.rs:13:16 | diff --git a/tests/ui/never_type/impl_trait_fallback3.stderr b/tests/ui/never_type/impl_trait_fallback3.stderr index 5d5d216fb9b..821d141569e 100644 --- a/tests/ui/never_type/impl_trait_fallback3.stderr +++ b/tests/ui/never_type/impl_trait_fallback3.stderr @@ -3,6 +3,12 @@ error[E0277]: the trait bound `(): T` is not satisfied | LL | fn a() -> Foo { | ^^^ the trait `T` is not implemented for `()` + | +help: this trait has no implementations, consider adding one + --> $DIR/impl_trait_fallback3.rs:5:1 + | +LL | trait T { + | ^^^^^^^ error: aborting due to previous error diff --git a/tests/ui/never_type/impl_trait_fallback4.stderr b/tests/ui/never_type/impl_trait_fallback4.stderr index f2e216e9044..67421ba8da7 100644 --- a/tests/ui/never_type/impl_trait_fallback4.stderr +++ b/tests/ui/never_type/impl_trait_fallback4.stderr @@ -3,6 +3,12 @@ error[E0277]: the trait bound `(): T` is not satisfied | LL | fn foo() -> impl T { | ^^^^^^ the trait `T` is not implemented for `()` + | +help: this trait has no implementations, consider adding one + --> $DIR/impl_trait_fallback4.rs:3:1 + | +LL | trait T { + | ^^^^^^^ error: aborting due to previous error diff --git a/tests/ui/on-unimplemented/on-trait.stderr b/tests/ui/on-unimplemented/on-trait.stderr index 4b040f1ac5a..4847a1a5a61 100644 --- a/tests/ui/on-unimplemented/on-trait.stderr +++ b/tests/ui/on-unimplemented/on-trait.stderr @@ -5,6 +5,11 @@ LL | let y: Option<Vec<u8>> = collect(x.iter()); // this should give approxi | ^^^^^^^ a collection of type `Option<Vec<u8>>` cannot be built from an iterator over elements of type `&u8` | = help: the trait `MyFromIterator<&u8>` is not implemented for `Option<Vec<u8>>` +help: this trait has no implementations, consider adding one + --> $DIR/on-trait.rs:17:1 + | +LL | trait MyFromIterator<A> { + | ^^^^^^^^^^^^^^^^^^^^^^^ note: required by a bound in `collect` --> $DIR/on-trait.rs:22:39 | @@ -18,6 +23,11 @@ LL | let x: String = foobar(); | ^^^^^^ test error `String` with `u8` `_` `u32` in `Foo` | = help: the trait `Foo<u8, _, u32>` is not implemented for `String` +help: this trait has no implementations, consider adding one + --> $DIR/on-trait.rs:7:3 + | +LL | pub trait Foo<Bar, Baz, Quux> {} + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ note: required by a bound in `foobar` --> $DIR/on-trait.rs:12:24 | diff --git a/tests/ui/on-unimplemented/parent-label.stderr b/tests/ui/on-unimplemented/parent-label.stderr index 8cd7412fd9d..101a41512d2 100644 --- a/tests/ui/on-unimplemented/parent-label.stderr +++ b/tests/ui/on-unimplemented/parent-label.stderr @@ -8,6 +8,11 @@ LL | f(Foo {}); | | | required by a bound introduced by this call | +help: this trait has no implementations, consider adding one + --> $DIR/parent-label.rs:6:1 + | +LL | trait Trait {} + | ^^^^^^^^^^^ note: required by a bound in `f` --> $DIR/parent-label.rs:10:9 | @@ -24,6 +29,11 @@ LL | f(Foo {}); | | | required by a bound introduced by this call | +help: this trait has no implementations, consider adding one + --> $DIR/parent-label.rs:6:1 + | +LL | trait Trait {} + | ^^^^^^^^^^^ note: required by a bound in `f` --> $DIR/parent-label.rs:10:9 | @@ -41,6 +51,11 @@ LL | f(Foo {}); | | | required by a bound introduced by this call | +help: this trait has no implementations, consider adding one + --> $DIR/parent-label.rs:6:1 + | +LL | trait Trait {} + | ^^^^^^^^^^^ note: required by a bound in `f` --> $DIR/parent-label.rs:10:9 | @@ -58,6 +73,11 @@ LL | f(Foo {}); | | | required by a bound introduced by this call | +help: this trait has no implementations, consider adding one + --> $DIR/parent-label.rs:6:1 + | +LL | trait Trait {} + | ^^^^^^^^^^^ note: required by a bound in `f` --> $DIR/parent-label.rs:10:9 | diff --git a/tests/ui/parser/default-unmatched.stderr b/tests/ui/parser/default-unmatched.stderr index 331e003f63c..de142411d69 100644 --- a/tests/ui/parser/default-unmatched.stderr +++ b/tests/ui/parser/default-unmatched.stderr @@ -11,6 +11,8 @@ error: expected item, found reserved keyword `do` | LL | default do | ^^ expected item + | + = note: for a full list of items that can appear in modules, see <https://doc.rust-lang.org/reference/items.html> error: aborting due to 2 previous errors diff --git a/tests/ui/parser/impl-parsing.stderr b/tests/ui/parser/impl-parsing.stderr index 755addf1452..a57cc075ccc 100644 --- a/tests/ui/parser/impl-parsing.stderr +++ b/tests/ui/parser/impl-parsing.stderr @@ -35,6 +35,8 @@ error: expected item, found keyword `unsafe` | LL | default unsafe FAIL | ^^^^^^ expected item + | + = note: for a full list of items that can appear in modules, see <https://doc.rust-lang.org/reference/items.html> error: aborting due to 6 previous errors diff --git a/tests/ui/parser/issue-101477-enum.stderr b/tests/ui/parser/issue-101477-enum.stderr index 1edca391e8f..94130671f1c 100644 --- a/tests/ui/parser/issue-101477-enum.stderr +++ b/tests/ui/parser/issue-101477-enum.stderr @@ -11,6 +11,8 @@ error: expected item, found `==` | LL | B == 2 | ^^ expected item + | + = note: for a full list of items that can appear in modules, see <https://doc.rust-lang.org/reference/items.html> error: aborting due to 2 previous errors diff --git a/tests/ui/parser/issues/issue-113110-non-item-at-module-root.rs b/tests/ui/parser/issues/issue-113110-non-item-at-module-root.rs new file mode 100644 index 00000000000..3b6f4304369 --- /dev/null +++ b/tests/ui/parser/issues/issue-113110-non-item-at-module-root.rs @@ -0,0 +1 @@ + 5 //~ ERROR expected item, found `5` diff --git a/tests/ui/parser/issues/issue-113110-non-item-at-module-root.stderr b/tests/ui/parser/issues/issue-113110-non-item-at-module-root.stderr new file mode 100644 index 00000000000..0789c4548a0 --- /dev/null +++ b/tests/ui/parser/issues/issue-113110-non-item-at-module-root.stderr @@ -0,0 +1,10 @@ +error: expected item, found `5` + --> $DIR/issue-113110-non-item-at-module-root.rs:1:2 + | +LL | 5 + | ^ expected item + | + = note: for a full list of items that can appear in modules, see <https://doc.rust-lang.org/reference/items.html> + +error: aborting due to previous error + diff --git a/tests/ui/parser/issues/issue-17904-2.stderr b/tests/ui/parser/issues/issue-17904-2.stderr index 9c7fdf6ccb4..7185a5e5752 100644 --- a/tests/ui/parser/issues/issue-17904-2.stderr +++ b/tests/ui/parser/issues/issue-17904-2.stderr @@ -3,6 +3,8 @@ error: expected item, found keyword `where` | LL | struct Bar<T> { x: T } where T: Copy | ^^^^^ expected item + | + = note: for a full list of items that can appear in modules, see <https://doc.rust-lang.org/reference/items.html> error: aborting due to previous error diff --git a/tests/ui/parser/issues/issue-43196.stderr b/tests/ui/parser/issues/issue-43196.stderr index 4f7ed5cc6fd..15bbb158cd1 100644 --- a/tests/ui/parser/issues/issue-43196.stderr +++ b/tests/ui/parser/issues/issue-43196.stderr @@ -11,6 +11,8 @@ error: expected item, found `|` | LL | | | ^ expected item + | + = note: for a full list of items that can appear in modules, see <https://doc.rust-lang.org/reference/items.html> error: aborting due to 2 previous errors diff --git a/tests/ui/parser/issues/issue-62913.stderr b/tests/ui/parser/issues/issue-62913.stderr index 6f385e8dc17..c33e4683728 100644 --- a/tests/ui/parser/issues/issue-62913.stderr +++ b/tests/ui/parser/issues/issue-62913.stderr @@ -17,6 +17,8 @@ error: expected item, found `"\u\"` | LL | "\u\" | ^^^^^^ expected item + | + = note: for a full list of items that can appear in modules, see <https://doc.rust-lang.org/reference/items.html> error: aborting due to 3 previous errors diff --git a/tests/ui/parser/issues/issue-68890.stderr b/tests/ui/parser/issues/issue-68890.stderr index 2a3bf6b41f0..0d7b53a67c5 100644 --- a/tests/ui/parser/issues/issue-68890.stderr +++ b/tests/ui/parser/issues/issue-68890.stderr @@ -15,6 +15,8 @@ error: expected item, found `)` | LL | enum e{A((?'a a+?+l))} | ^ expected item + | + = note: for a full list of items that can appear in modules, see <https://doc.rust-lang.org/reference/items.html> error: aborting due to 3 previous errors diff --git a/tests/ui/parser/shebang/shebang-doc-comment.stderr b/tests/ui/parser/shebang/shebang-doc-comment.stderr index 2227d45ec5a..a36b2a2f72b 100644 --- a/tests/ui/parser/shebang/shebang-doc-comment.stderr +++ b/tests/ui/parser/shebang/shebang-doc-comment.stderr @@ -3,6 +3,8 @@ error: expected item, found `[` | LL | [allow(unused_variables)] | ^ expected item + | + = note: for a full list of items that can appear in modules, see <https://doc.rust-lang.org/reference/items.html> error: aborting due to previous error diff --git a/tests/ui/parser/virtual-structs.stderr b/tests/ui/parser/virtual-structs.stderr index a5211d83f84..268fc105796 100644 --- a/tests/ui/parser/virtual-structs.stderr +++ b/tests/ui/parser/virtual-structs.stderr @@ -3,6 +3,8 @@ error: expected item, found reserved keyword `virtual` | LL | virtual struct SuperStruct { | ^^^^^^^ expected item + | + = note: for a full list of items that can appear in modules, see <https://doc.rust-lang.org/reference/items.html> error: aborting due to previous error diff --git a/tests/ui/pattern/issue-114896.rs b/tests/ui/pattern/issue-114896.rs new file mode 100644 index 00000000000..cde37f658d6 --- /dev/null +++ b/tests/ui/pattern/issue-114896.rs @@ -0,0 +1,7 @@ +fn main() { + fn x(a: &char) { + let &b = a; + b.make_ascii_uppercase(); +//~^ cannot borrow `b` as mutable, as it is not declared as mutable + } +} diff --git a/tests/ui/pattern/issue-114896.stderr b/tests/ui/pattern/issue-114896.stderr new file mode 100644 index 00000000000..ffeb7bc1365 --- /dev/null +++ b/tests/ui/pattern/issue-114896.stderr @@ -0,0 +1,11 @@ +error[E0596]: cannot borrow `b` as mutable, as it is not declared as mutable + --> $DIR/issue-114896.rs:4:9 + | +LL | let &b = a; + | -- help: consider changing this to be mutable: `&(mut b)` +LL | b.make_ascii_uppercase(); + | ^ cannot borrow as mutable + +error: aborting due to previous error + +For more information about this error, try `rustc --explain E0596`. diff --git a/tests/ui/privacy/private-bounds-locally-allowed.rs b/tests/ui/privacy/private-bounds-locally-allowed.rs new file mode 100644 index 00000000000..96a007a64f6 --- /dev/null +++ b/tests/ui/privacy/private-bounds-locally-allowed.rs @@ -0,0 +1,7 @@ +// check-pass +// compile-flags: --crate-type=lib + +#[allow(private_bounds)] +pub trait Foo: FooImpl {} + +trait FooImpl {} diff --git a/tests/ui/privacy/unnameable_types.rs b/tests/ui/privacy/unnameable_types.rs index e35aaec5b3b..c6c5561c3c4 100644 --- a/tests/ui/privacy/unnameable_types.rs +++ b/tests/ui/privacy/unnameable_types.rs @@ -20,10 +20,10 @@ mod m { } } -pub trait Voldemort<T> {} +pub trait Unnameable<T> {} -impl Voldemort<m::PubStruct> for i32 {} -impl Voldemort<m::PubE> for i32 {} -impl<T> Voldemort<T> for u32 where T: m::PubTr {} +impl Unnameable<m::PubStruct> for i32 {} +impl Unnameable<m::PubE> for i32 {} +impl<T> Unnameable<T> for u32 where T: m::PubTr {} fn main() {} diff --git a/tests/ui/proc-macro/bad-projection.stderr b/tests/ui/proc-macro/bad-projection.stderr index 8a8246376fe..8716defa17a 100644 --- a/tests/ui/proc-macro/bad-projection.stderr +++ b/tests/ui/proc-macro/bad-projection.stderr @@ -3,6 +3,12 @@ error[E0277]: the trait bound `(): Project` is not satisfied | LL | pub fn uwu() -> <() as Project>::Assoc {} | ^^^^^^^^^^^^^^^^^^^^^^ the trait `Project` is not implemented for `()` + | +help: this trait has no implementations, consider adding one + --> $DIR/bad-projection.rs:9:1 + | +LL | trait Project { + | ^^^^^^^^^^^^^ error: aborting due to previous error diff --git a/tests/ui/pub/pub-restricted-error-fn.stderr b/tests/ui/pub/pub-restricted-error-fn.stderr index 0511a821a7a..ca5d8e1b58e 100644 --- a/tests/ui/pub/pub-restricted-error-fn.stderr +++ b/tests/ui/pub/pub-restricted-error-fn.stderr @@ -11,6 +11,8 @@ error: expected item, found `(` | LL | pub(crate) () fn foo() {} | ^ expected item + | + = note: for a full list of items that can appear in modules, see <https://doc.rust-lang.org/reference/items.html> error: aborting due to 2 previous errors diff --git a/tests/ui/resolve/bad-type-env-capture.stderr b/tests/ui/resolve/bad-type-env-capture.stderr index b6282c2d070..941b6b7a68c 100644 --- a/tests/ui/resolve/bad-type-env-capture.stderr +++ b/tests/ui/resolve/bad-type-env-capture.stderr @@ -1,12 +1,12 @@ -error[E0401]: can't use generic parameters from outer function +error[E0401]: can't use generic parameters from outer item --> $DIR/bad-type-env-capture.rs:2:15 | LL | fn foo<T>() { - | - type parameter from outer function + | - type parameter from outer item LL | fn bar(b: T) { } - | - ^ use of generic parameter from outer function + | - ^ use of generic parameter from outer item | | - | help: try using a local generic parameter instead: `<T>` + | help: try introducing a local generic parameter here: `<T>` error: aborting due to previous error diff --git a/tests/ui/resolve/generic-params-from-outer-item-in-const-item.default.stderr b/tests/ui/resolve/generic-params-from-outer-item-in-const-item.default.stderr new file mode 100644 index 00000000000..4f853829279 --- /dev/null +++ b/tests/ui/resolve/generic-params-from-outer-item-in-const-item.default.stderr @@ -0,0 +1,28 @@ +error[E0401]: can't use generic parameters from outer item + --> $DIR/generic-params-from-outer-item-in-const-item.rs:12:20 + | +LL | fn outer<T: Tr>() { // outer function + | - type parameter from outer item +LL | const K: u32 = T::C; + | ^^^^ use of generic parameter from outer item + +error[E0401]: can't use generic parameters from outer item + --> $DIR/generic-params-from-outer-item-in-const-item.rs:19:24 + | +LL | impl<T> Tr for T { // outer impl block + | - type parameter from outer item +LL | const C: u32 = { +LL | const I: u32 = T::C; + | ^^^^ use of generic parameter from outer item + +error[E0401]: can't use generic parameters from outer item + --> $DIR/generic-params-from-outer-item-in-const-item.rs:27:20 + | +LL | struct S<T: Tr>(U32<{ // outer struct + | - type parameter from outer item +LL | const _: u32 = T::C; + | ^^^^ use of generic parameter from outer item + +error: aborting due to 3 previous errors + +For more information about this error, try `rustc --explain E0401`. diff --git a/tests/ui/resolve/generic-params-from-outer-item-in-const-item.generic_const_items.stderr b/tests/ui/resolve/generic-params-from-outer-item-in-const-item.generic_const_items.stderr new file mode 100644 index 00000000000..1cb55842bc6 --- /dev/null +++ b/tests/ui/resolve/generic-params-from-outer-item-in-const-item.generic_const_items.stderr @@ -0,0 +1,34 @@ +error[E0401]: can't use generic parameters from outer item + --> $DIR/generic-params-from-outer-item-in-const-item.rs:12:20 + | +LL | fn outer<T: Tr>() { // outer function + | - type parameter from outer item +LL | const K: u32 = T::C; + | - ^^^^ use of generic parameter from outer item + | | + | help: try introducing a local generic parameter here: `<T>` + +error[E0401]: can't use generic parameters from outer item + --> $DIR/generic-params-from-outer-item-in-const-item.rs:19:24 + | +LL | impl<T> Tr for T { // outer impl block + | - type parameter from outer item +LL | const C: u32 = { +LL | const I: u32 = T::C; + | - ^^^^ use of generic parameter from outer item + | | + | help: try introducing a local generic parameter here: `<T>` + +error[E0401]: can't use generic parameters from outer item + --> $DIR/generic-params-from-outer-item-in-const-item.rs:27:20 + | +LL | struct S<T: Tr>(U32<{ // outer struct + | - type parameter from outer item +LL | const _: u32 = T::C; + | - ^^^^ use of generic parameter from outer item + | | + | help: try introducing a local generic parameter here: `<T>` + +error: aborting due to 3 previous errors + +For more information about this error, try `rustc --explain E0401`. diff --git a/tests/ui/resolve/generic-params-from-outer-item-in-const-item.rs b/tests/ui/resolve/generic-params-from-outer-item-in-const-item.rs new file mode 100644 index 00000000000..e5647d72cba --- /dev/null +++ b/tests/ui/resolve/generic-params-from-outer-item-in-const-item.rs @@ -0,0 +1,39 @@ +// Regression test for issue #115720. +// If a const item contains generic params from an outer items, only suggest +// turning the const item generic if the feature `generic_const_items` is enabled. + +// revisions: default generic_const_items + +#![cfg_attr(generic_const_items, feature(generic_const_items))] +#![feature(generic_const_exprs)] // only used for the test case "outer struct" +#![allow(incomplete_features)] + +fn outer<T: Tr>() { // outer function + const K: u32 = T::C; + //~^ ERROR can't use generic parameters from outer item + //[generic_const_items]~| HELP try introducing a local generic parameter here +} + +impl<T> Tr for T { // outer impl block + const C: u32 = { + const I: u32 = T::C; + //~^ ERROR can't use generic parameters from outer item + //[generic_const_items]~| HELP try introducing a local generic parameter here + I + }; +} + +struct S<T: Tr>(U32<{ // outer struct + const _: u32 = T::C; + //~^ ERROR can't use generic parameters from outer item + //[generic_const_items]~| HELP try introducing a local generic parameter here + 0 +}>); + +trait Tr { + const C: u32; +} + +struct U32<const N: u32>; + +fn main() {} diff --git a/tests/ui/resolve/issue-12796.rs b/tests/ui/resolve/issue-12796.rs index 942d6b9a568..de3e73437f0 100644 --- a/tests/ui/resolve/issue-12796.rs +++ b/tests/ui/resolve/issue-12796.rs @@ -1,7 +1,7 @@ trait Trait { fn outer(&self) { fn inner(_: &Self) { - //~^ ERROR can't use generic parameters from outer function + //~^ ERROR can't use generic parameters from outer item } } } diff --git a/tests/ui/resolve/issue-12796.stderr b/tests/ui/resolve/issue-12796.stderr index a01fd2d6542..ef59d00360b 100644 --- a/tests/ui/resolve/issue-12796.stderr +++ b/tests/ui/resolve/issue-12796.stderr @@ -1,10 +1,10 @@ -error[E0401]: can't use generic parameters from outer function +error[E0401]: can't use generic parameters from outer item --> $DIR/issue-12796.rs:3:22 | LL | fn inner(_: &Self) { | ^^^^ | | - | use of generic parameter from outer function + | use of generic parameter from outer item | can't use `Self` here error: aborting due to previous error diff --git a/tests/ui/resolve/issue-3021-c.rs b/tests/ui/resolve/issue-3021-c.rs index 94ed1fdf781..bd21d124423 100644 --- a/tests/ui/resolve/issue-3021-c.rs +++ b/tests/ui/resolve/issue-3021-c.rs @@ -1,8 +1,8 @@ fn siphash<T>() { trait U { - fn g(&self, x: T) -> T; //~ ERROR can't use generic parameters from outer function - //~^ ERROR can't use generic parameters from outer function + fn g(&self, x: T) -> T; //~ ERROR can't use generic parameters from outer item + //~^ ERROR can't use generic parameters from outer item } } diff --git a/tests/ui/resolve/issue-3021-c.stderr b/tests/ui/resolve/issue-3021-c.stderr index 5176efc3a6b..537bbaf7b6a 100644 --- a/tests/ui/resolve/issue-3021-c.stderr +++ b/tests/ui/resolve/issue-3021-c.stderr @@ -1,24 +1,24 @@ -error[E0401]: can't use generic parameters from outer function +error[E0401]: can't use generic parameters from outer item --> $DIR/issue-3021-c.rs:4:24 | LL | fn siphash<T>() { - | - type parameter from outer function + | - type parameter from outer item LL | LL | trait U { - | - help: try using a local generic parameter instead: `<T>` + | - help: try introducing a local generic parameter here: `<T>` LL | fn g(&self, x: T) -> T; - | ^ use of generic parameter from outer function + | ^ use of generic parameter from outer item -error[E0401]: can't use generic parameters from outer function +error[E0401]: can't use generic parameters from outer item --> $DIR/issue-3021-c.rs:4:30 | LL | fn siphash<T>() { - | - type parameter from outer function + | - type parameter from outer item LL | LL | trait U { - | - help: try using a local generic parameter instead: `<T>` + | - help: try introducing a local generic parameter here: `<T>` LL | fn g(&self, x: T) -> T; - | ^ use of generic parameter from outer function + | ^ use of generic parameter from outer item error: aborting due to 2 previous errors diff --git a/tests/ui/resolve/issue-65025-extern-static-parent-generics.rs b/tests/ui/resolve/issue-65025-extern-static-parent-generics.rs index ce45f630e48..4fa3f12d024 100644 --- a/tests/ui/resolve/issue-65025-extern-static-parent-generics.rs +++ b/tests/ui/resolve/issue-65025-extern-static-parent-generics.rs @@ -1,7 +1,7 @@ unsafe fn foo<A>() { extern "C" { static baz: *const A; - //~^ ERROR can't use generic parameters from outer function + //~^ ERROR can't use generic parameters from outer item } let bar: *const u64 = core::mem::transmute(&baz); diff --git a/tests/ui/resolve/issue-65025-extern-static-parent-generics.stderr b/tests/ui/resolve/issue-65025-extern-static-parent-generics.stderr index 6bbf76dd1fb..3e9c3fd11b7 100644 --- a/tests/ui/resolve/issue-65025-extern-static-parent-generics.stderr +++ b/tests/ui/resolve/issue-65025-extern-static-parent-generics.stderr @@ -1,11 +1,11 @@ -error[E0401]: can't use generic parameters from outer function +error[E0401]: can't use generic parameters from outer item --> $DIR/issue-65025-extern-static-parent-generics.rs:3:28 | LL | unsafe fn foo<A>() { - | - type parameter from outer function + | - type parameter from outer item LL | extern "C" { LL | static baz: *const A; - | ^ use of generic parameter from outer function + | ^ use of generic parameter from outer item error: aborting due to previous error diff --git a/tests/ui/resolve/issue-65035-static-with-parent-generics.rs b/tests/ui/resolve/issue-65035-static-with-parent-generics.rs index f96c04841dd..bc99584a8d2 100644 --- a/tests/ui/resolve/issue-65035-static-with-parent-generics.rs +++ b/tests/ui/resolve/issue-65035-static-with-parent-generics.rs @@ -1,26 +1,26 @@ fn f<T>() { extern "C" { static a: *const T; - //~^ ERROR can't use generic parameters from outer function + //~^ ERROR can't use generic parameters from outer item } } fn g<T: Default>() { static a: *const T = Default::default(); - //~^ ERROR can't use generic parameters from outer function + //~^ ERROR can't use generic parameters from outer item } fn h<const N: usize>() { extern "C" { static a: [u8; N]; - //~^ ERROR can't use generic parameters from outer function + //~^ ERROR can't use generic parameters from outer item } } fn i<const N: usize>() { static a: [u8; N] = [0; N]; - //~^ ERROR can't use generic parameters from outer function - //~| ERROR can't use generic parameters from outer function + //~^ ERROR can't use generic parameters from outer item + //~| ERROR can't use generic parameters from outer item } fn main() {} diff --git a/tests/ui/resolve/issue-65035-static-with-parent-generics.stderr b/tests/ui/resolve/issue-65035-static-with-parent-generics.stderr index 7ed572f80b8..f1fe1a6002c 100644 --- a/tests/ui/resolve/issue-65035-static-with-parent-generics.stderr +++ b/tests/ui/resolve/issue-65035-static-with-parent-generics.stderr @@ -1,44 +1,44 @@ -error[E0401]: can't use generic parameters from outer function +error[E0401]: can't use generic parameters from outer item --> $DIR/issue-65035-static-with-parent-generics.rs:3:26 | LL | fn f<T>() { - | - type parameter from outer function + | - type parameter from outer item LL | extern "C" { LL | static a: *const T; - | ^ use of generic parameter from outer function + | ^ use of generic parameter from outer item -error[E0401]: can't use generic parameters from outer function +error[E0401]: can't use generic parameters from outer item --> $DIR/issue-65035-static-with-parent-generics.rs:9:22 | LL | fn g<T: Default>() { - | - type parameter from outer function + | - type parameter from outer item LL | static a: *const T = Default::default(); - | ^ use of generic parameter from outer function + | ^ use of generic parameter from outer item -error[E0401]: can't use generic parameters from outer function +error[E0401]: can't use generic parameters from outer item --> $DIR/issue-65035-static-with-parent-generics.rs:15:24 | LL | fn h<const N: usize>() { - | - const parameter from outer function + | - const parameter from outer item LL | extern "C" { LL | static a: [u8; N]; - | ^ use of generic parameter from outer function + | ^ use of generic parameter from outer item -error[E0401]: can't use generic parameters from outer function +error[E0401]: can't use generic parameters from outer item --> $DIR/issue-65035-static-with-parent-generics.rs:21:20 | LL | fn i<const N: usize>() { - | - const parameter from outer function + | - const parameter from outer item LL | static a: [u8; N] = [0; N]; - | ^ use of generic parameter from outer function + | ^ use of generic parameter from outer item -error[E0401]: can't use generic parameters from outer function +error[E0401]: can't use generic parameters from outer item --> $DIR/issue-65035-static-with-parent-generics.rs:21:29 | LL | fn i<const N: usize>() { - | - const parameter from outer function + | - const parameter from outer item LL | static a: [u8; N] = [0; N]; - | ^ use of generic parameter from outer function + | ^ use of generic parameter from outer item error: aborting due to 5 previous errors diff --git a/tests/ui/resolve/resolve-type-param-in-item-in-trait.rs b/tests/ui/resolve/resolve-type-param-in-item-in-trait.rs index c77a66524f7..2d5f34c62a6 100644 --- a/tests/ui/resolve/resolve-type-param-in-item-in-trait.rs +++ b/tests/ui/resolve/resolve-type-param-in-item-in-trait.rs @@ -6,7 +6,7 @@ trait TraitA<A> { fn outer(&self) { enum Foo<B> { Variance(A) - //~^ ERROR can't use generic parameters from outer function + //~^ ERROR can't use generic parameters from outer item } } } @@ -14,21 +14,21 @@ trait TraitA<A> { trait TraitB<A> { fn outer(&self) { struct Foo<B>(A); - //~^ ERROR can't use generic parameters from outer function + //~^ ERROR can't use generic parameters from outer item } } trait TraitC<A> { fn outer(&self) { struct Foo<B> { a: A } - //~^ ERROR can't use generic parameters from outer function + //~^ ERROR can't use generic parameters from outer item } } trait TraitD<A> { fn outer(&self) { fn foo<B>(a: A) { } - //~^ ERROR can't use generic parameters from outer function + //~^ ERROR can't use generic parameters from outer item } } diff --git a/tests/ui/resolve/resolve-type-param-in-item-in-trait.stderr b/tests/ui/resolve/resolve-type-param-in-item-in-trait.stderr index 0a6d1cc3bcd..1ab56fdc504 100644 --- a/tests/ui/resolve/resolve-type-param-in-item-in-trait.stderr +++ b/tests/ui/resolve/resolve-type-param-in-item-in-trait.stderr @@ -1,46 +1,46 @@ -error[E0401]: can't use generic parameters from outer function +error[E0401]: can't use generic parameters from outer item --> $DIR/resolve-type-param-in-item-in-trait.rs:8:22 | LL | trait TraitA<A> { - | - type parameter from outer function + | - type parameter from outer item LL | fn outer(&self) { LL | enum Foo<B> { - | - help: try using a local generic parameter instead: `A,` + | - help: try introducing a local generic parameter here: `A,` LL | Variance(A) - | ^ use of generic parameter from outer function + | ^ use of generic parameter from outer item -error[E0401]: can't use generic parameters from outer function +error[E0401]: can't use generic parameters from outer item --> $DIR/resolve-type-param-in-item-in-trait.rs:16:23 | LL | trait TraitB<A> { - | - type parameter from outer function + | - type parameter from outer item LL | fn outer(&self) { LL | struct Foo<B>(A); - | - ^ use of generic parameter from outer function + | - ^ use of generic parameter from outer item | | - | help: try using a local generic parameter instead: `A,` + | help: try introducing a local generic parameter here: `A,` -error[E0401]: can't use generic parameters from outer function +error[E0401]: can't use generic parameters from outer item --> $DIR/resolve-type-param-in-item-in-trait.rs:23:28 | LL | trait TraitC<A> { - | - type parameter from outer function + | - type parameter from outer item LL | fn outer(&self) { LL | struct Foo<B> { a: A } - | - ^ use of generic parameter from outer function + | - ^ use of generic parameter from outer item | | - | help: try using a local generic parameter instead: `A,` + | help: try introducing a local generic parameter here: `A,` -error[E0401]: can't use generic parameters from outer function +error[E0401]: can't use generic parameters from outer item --> $DIR/resolve-type-param-in-item-in-trait.rs:30:22 | LL | trait TraitD<A> { - | - type parameter from outer function + | - type parameter from outer item LL | fn outer(&self) { LL | fn foo<B>(a: A) { } - | - ^ use of generic parameter from outer function + | - ^ use of generic parameter from outer item | | - | help: try using a local generic parameter instead: `A,` + | help: try introducing a local generic parameter here: `A,` error: aborting due to 4 previous errors diff --git a/tests/ui/resolve/suggest-import-without-clobbering-attrs.fixed b/tests/ui/resolve/suggest-import-without-clobbering-attrs.fixed new file mode 100644 index 00000000000..fc68884fe9c --- /dev/null +++ b/tests/ui/resolve/suggest-import-without-clobbering-attrs.fixed @@ -0,0 +1,16 @@ +// run-rustfix +// compile-flags: --cfg=whatever -Aunused + +use y::z; +#[cfg(whatever)] +use y::Whatever; + +mod y { + pub(crate) fn z() {} + pub(crate) struct Whatever; +} + +fn main() { + z(); + //~^ ERROR cannot find function `z` in this scope +} diff --git a/tests/ui/resolve/suggest-import-without-clobbering-attrs.rs b/tests/ui/resolve/suggest-import-without-clobbering-attrs.rs new file mode 100644 index 00000000000..38a1095703b --- /dev/null +++ b/tests/ui/resolve/suggest-import-without-clobbering-attrs.rs @@ -0,0 +1,15 @@ +// run-rustfix +// compile-flags: --cfg=whatever -Aunused + +#[cfg(whatever)] +use y::Whatever; + +mod y { + pub(crate) fn z() {} + pub(crate) struct Whatever; +} + +fn main() { + z(); + //~^ ERROR cannot find function `z` in this scope +} diff --git a/tests/ui/resolve/suggest-import-without-clobbering-attrs.stderr b/tests/ui/resolve/suggest-import-without-clobbering-attrs.stderr new file mode 100644 index 00000000000..d3574851d5c --- /dev/null +++ b/tests/ui/resolve/suggest-import-without-clobbering-attrs.stderr @@ -0,0 +1,14 @@ +error[E0425]: cannot find function `z` in this scope + --> $DIR/suggest-import-without-clobbering-attrs.rs:13:5 + | +LL | z(); + | ^ not found in this scope + | +help: consider importing this function + | +LL + use y::z; + | + +error: aborting due to previous error + +For more information about this error, try `rustc --explain E0425`. diff --git a/tests/ui/resolve/use-self-in-inner-fn.rs b/tests/ui/resolve/use-self-in-inner-fn.rs index eccb315feb1..f4dfa4c40ab 100644 --- a/tests/ui/resolve/use-self-in-inner-fn.rs +++ b/tests/ui/resolve/use-self-in-inner-fn.rs @@ -4,9 +4,9 @@ impl A { //~^ NOTE `Self` type implicitly declared here, by this `impl` fn banana(&mut self) { fn peach(this: &Self) { - //~^ ERROR can't use generic parameters from outer function - //~| NOTE use of generic parameter from outer function - //~| NOTE use a type here instead + //~^ ERROR can't use generic parameters from outer item + //~| NOTE use of generic parameter from outer item + //~| NOTE refer to the type directly here instead } } } diff --git a/tests/ui/resolve/use-self-in-inner-fn.stderr b/tests/ui/resolve/use-self-in-inner-fn.stderr index 96609349924..832aaacaf49 100644 --- a/tests/ui/resolve/use-self-in-inner-fn.stderr +++ b/tests/ui/resolve/use-self-in-inner-fn.stderr @@ -1,4 +1,4 @@ -error[E0401]: can't use generic parameters from outer function +error[E0401]: can't use generic parameters from outer item --> $DIR/use-self-in-inner-fn.rs:6:25 | LL | impl A { @@ -7,8 +7,8 @@ LL | impl A { LL | fn peach(this: &Self) { | ^^^^ | | - | use of generic parameter from outer function - | use a type here instead + | use of generic parameter from outer item + | refer to the type directly here instead error: aborting due to previous error diff --git a/tests/ui/rfcs/rfc-2632-const-trait-impl/effects/fallback.rs b/tests/ui/rfcs/rfc-2632-const-trait-impl/effects/fallback.rs new file mode 100644 index 00000000000..855bbb2e992 --- /dev/null +++ b/tests/ui/rfcs/rfc-2632-const-trait-impl/effects/fallback.rs @@ -0,0 +1,9 @@ +// check-pass + +#![feature(const_trait_impl, effects)] + +pub const fn owo() {} + +fn main() { + let _ = owo; +} diff --git a/tests/ui/sanitize/cfg.rs b/tests/ui/sanitize/cfg.rs index c0f08a6d1e5..523de1ceaee 100644 --- a/tests/ui/sanitize/cfg.rs +++ b/tests/ui/sanitize/cfg.rs @@ -2,19 +2,19 @@ // the `#[cfg(sanitize = "option")]` attribute is configured. // needs-sanitizer-support -// needs-sanitizer-address -// needs-sanitizer-cfi -// needs-sanitizer-kcfi -// needs-sanitizer-leak -// needs-sanitizer-memory -// needs-sanitizer-thread // check-pass -// revisions: address leak memory thread +// revisions: address cfi kcfi leak memory thread +//[address]needs-sanitizer-address //[address]compile-flags: -Zsanitizer=address --cfg address -//[cfi]compile-flags: -Zsanitizer=cfi --cfg cfi +//[cfi]needs-sanitizer-cfi +//[cfi]compile-flags: -Zsanitizer=cfi --cfg cfi -Clto +//[kcfi]needs-sanitizer-kcfi //[kcfi]compile-flags: -Zsanitizer=kcfi --cfg kcfi +//[leak]needs-sanitizer-leak //[leak]compile-flags: -Zsanitizer=leak --cfg leak +//[memory]needs-sanitizer-memory //[memory]compile-flags: -Zsanitizer=memory --cfg memory +//[thread]needs-sanitizer-thread //[thread]compile-flags: -Zsanitizer=thread --cfg thread #![feature(cfg_sanitize)] diff --git a/tests/ui/span/issue-29595.stderr b/tests/ui/span/issue-29595.stderr index 92445e40731..7d603cdbfe5 100644 --- a/tests/ui/span/issue-29595.stderr +++ b/tests/ui/span/issue-29595.stderr @@ -3,6 +3,12 @@ error[E0277]: the trait bound `u8: Tr` is not satisfied | LL | let a: u8 = Tr::C; | ^^^^^ the trait `Tr` is not implemented for `u8` + | +help: this trait has no implementations, consider adding one + --> $DIR/issue-29595.rs:1:1 + | +LL | trait Tr { + | ^^^^^^^^ error: aborting due to previous error diff --git a/tests/ui/specialization/issue-38091.stderr b/tests/ui/specialization/issue-38091.stderr index f2210a40719..4d840482b46 100644 --- a/tests/ui/specialization/issue-38091.stderr +++ b/tests/ui/specialization/issue-38091.stderr @@ -14,6 +14,11 @@ error[E0277]: the trait bound `(): Valid` is not satisfied LL | default type Ty = (); | ^^ the trait `Valid` is not implemented for `()` | +help: this trait has no implementations, consider adding one + --> $DIR/issue-38091.rs:20:1 + | +LL | trait Valid {} + | ^^^^^^^^^^^ note: required by a bound in `Iterate::Ty` --> $DIR/issue-38091.rs:5:14 | diff --git a/tests/ui/suggestions/issue-89333.stderr b/tests/ui/suggestions/issue-89333.stderr index f73f1147d5d..4739f11ddad 100644 --- a/tests/ui/suggestions/issue-89333.stderr +++ b/tests/ui/suggestions/issue-89333.stderr @@ -4,6 +4,11 @@ error[E0277]: the trait bound `for<'a> &'a _: Trait` is not satisfied LL | test(&|| 0); | ^^^^ the trait `for<'a> Trait` is not implemented for `&'a _` | +help: this trait has no implementations, consider adding one + --> $DIR/issue-89333.rs:9:1 + | +LL | trait Trait {} + | ^^^^^^^^^^^ note: required by a bound in `test` --> $DIR/issue-89333.rs:11:55 | diff --git a/tests/ui/thir-print/thir-flat-const-variant.stdout b/tests/ui/thir-print/thir-flat-const-variant.stdout index 7bddc925996..af7f2b67152 100644 --- a/tests/ui/thir-print/thir-flat-const-variant.stdout +++ b/tests/ui/thir-print/thir-flat-const-variant.stdout @@ -1,7 +1,11 @@ DefId(0:8 ~ thir_flat_const_variant[1f54]::{impl#0}::BAR1): Thir { body_type: Const( - Foo, + Adt( + Foo, + [ + ], + ), ), arms: [], blocks: [], @@ -46,7 +50,11 @@ Thir { base: None, }, ), - ty: Foo, + ty: Adt( + Foo, + [ + ], + ), temp_lifetime: Some( Node(3), ), @@ -60,7 +68,11 @@ Thir { ), value: e2, }, - ty: Foo, + ty: Adt( + Foo, + [ + ], + ), temp_lifetime: Some( Node(3), ), @@ -72,7 +84,11 @@ Thir { lint_level: Inherited, value: e3, }, - ty: Foo, + ty: Adt( + Foo, + [ + ], + ), temp_lifetime: Some( Node(3), ), @@ -86,7 +102,11 @@ Thir { DefId(0:9 ~ thir_flat_const_variant[1f54]::{impl#0}::BAR2): Thir { body_type: Const( - Foo, + Adt( + Foo, + [ + ], + ), ), arms: [], blocks: [], @@ -131,7 +151,11 @@ Thir { base: None, }, ), - ty: Foo, + ty: Adt( + Foo, + [ + ], + ), temp_lifetime: Some( Node(3), ), @@ -145,7 +169,11 @@ Thir { ), value: e2, }, - ty: Foo, + ty: Adt( + Foo, + [ + ], + ), temp_lifetime: Some( Node(3), ), @@ -157,7 +185,11 @@ Thir { lint_level: Inherited, value: e3, }, - ty: Foo, + ty: Adt( + Foo, + [ + ], + ), temp_lifetime: Some( Node(3), ), @@ -171,7 +203,11 @@ Thir { DefId(0:10 ~ thir_flat_const_variant[1f54]::{impl#0}::BAR3): Thir { body_type: Const( - Foo, + Adt( + Foo, + [ + ], + ), ), arms: [], blocks: [], @@ -216,7 +252,11 @@ Thir { base: None, }, ), - ty: Foo, + ty: Adt( + Foo, + [ + ], + ), temp_lifetime: Some( Node(3), ), @@ -230,7 +270,11 @@ Thir { ), value: e2, }, - ty: Foo, + ty: Adt( + Foo, + [ + ], + ), temp_lifetime: Some( Node(3), ), @@ -242,7 +286,11 @@ Thir { lint_level: Inherited, value: e3, }, - ty: Foo, + ty: Adt( + Foo, + [ + ], + ), temp_lifetime: Some( Node(3), ), @@ -256,7 +304,11 @@ Thir { DefId(0:11 ~ thir_flat_const_variant[1f54]::{impl#0}::BAR4): Thir { body_type: Const( - Foo, + Adt( + Foo, + [ + ], + ), ), arms: [], blocks: [], @@ -301,7 +353,11 @@ Thir { base: None, }, ), - ty: Foo, + ty: Adt( + Foo, + [ + ], + ), temp_lifetime: Some( Node(3), ), @@ -315,7 +371,11 @@ Thir { ), value: e2, }, - ty: Foo, + ty: Adt( + Foo, + [ + ], + ), temp_lifetime: Some( Node(3), ), @@ -327,7 +387,11 @@ Thir { lint_level: Inherited, value: e3, }, - ty: Foo, + ty: Adt( + Foo, + [ + ], + ), temp_lifetime: Some( Node(3), ), diff --git a/tests/ui/thir-print/thir-tree-match.stdout b/tests/ui/thir-print/thir-tree-match.stdout index 3fc130f0176..0e21b98307b 100644 --- a/tests/ui/thir-print/thir-tree-match.stdout +++ b/tests/ui/thir-print/thir-tree-match.stdout @@ -1,13 +1,13 @@ DefId(0:16 ~ thir_tree_match[fcf8]::has_match): params: [ Param { - ty: Foo + ty: Adt(Foo, []) ty_span: Some($DIR/thir-tree-match.rs:15:19: 15:22 (#0)) self_kind: None hir_id: Some(HirId(DefId(0:16 ~ thir_tree_match[fcf8]::has_match).1)) param: Some( Pat: { - ty: Foo + ty: Adt(Foo, []) span: $DIR/thir-tree-match.rs:15:14: 15:17 (#0) kind: PatKind { Binding { @@ -15,7 +15,7 @@ params: [ name: "foo" mode: ByValue var: LocalVarId(HirId(DefId(0:16 ~ thir_tree_match[fcf8]::has_match).2)) - ty: Foo + ty: Adt(Foo, []) is_primary: true subpattern: None } @@ -73,7 +73,7 @@ body: Match { scrutinee: Expr { - ty: Foo + ty: Adt(Foo, []) temp_lifetime: Some(Node(26)) span: $DIR/thir-tree-match.rs:16:11: 16:14 (#0) kind: @@ -82,7 +82,7 @@ body: lint_level: Explicit(HirId(DefId(0:16 ~ thir_tree_match[fcf8]::has_match).4)) value: Expr { - ty: Foo + ty: Adt(Foo, []) temp_lifetime: Some(Node(26)) span: $DIR/thir-tree-match.rs:16:11: 16:14 (#0) kind: @@ -96,7 +96,7 @@ body: Arm { pattern: Pat: { - ty: Foo + ty: Adt(Foo, []) span: $DIR/thir-tree-match.rs:17:9: 17:32 (#0) kind: PatKind { Variant { @@ -110,7 +110,7 @@ body: variant_index: 0 subpatterns: [ Pat: { - ty: Bar + ty: Adt(Bar, []) span: $DIR/thir-tree-match.rs:17:21: 17:31 (#0) kind: PatKind { Variant { @@ -169,7 +169,7 @@ body: Arm { pattern: Pat: { - ty: Foo + ty: Adt(Foo, []) span: $DIR/thir-tree-match.rs:18:9: 18:23 (#0) kind: PatKind { Variant { @@ -183,7 +183,7 @@ body: variant_index: 0 subpatterns: [ Pat: { - ty: Bar + ty: Adt(Bar, []) span: $DIR/thir-tree-match.rs:18:21: 18:22 (#0) kind: PatKind { Wild @@ -232,7 +232,7 @@ body: Arm { pattern: Pat: { - ty: Foo + ty: Adt(Foo, []) span: $DIR/thir-tree-match.rs:19:9: 19:20 (#0) kind: PatKind { Variant { diff --git a/tests/ui/trait-bounds/issue-82038.rs b/tests/ui/trait-bounds/issue-82038.rs new file mode 100644 index 00000000000..11de714faf0 --- /dev/null +++ b/tests/ui/trait-bounds/issue-82038.rs @@ -0,0 +1,9 @@ +// Failed bound `bool: Foo` must not point at the `Self: Clone` line + +trait Foo { + fn my_method() where Self: Clone; +} + +fn main() { + <bool as Foo>::my_method(); //~ERROR [E0277] +} diff --git a/tests/ui/trait-bounds/issue-82038.stderr b/tests/ui/trait-bounds/issue-82038.stderr new file mode 100644 index 00000000000..30bb4a0a850 --- /dev/null +++ b/tests/ui/trait-bounds/issue-82038.stderr @@ -0,0 +1,15 @@ +error[E0277]: the trait bound `bool: Foo` is not satisfied + --> $DIR/issue-82038.rs:8:6 + | +LL | <bool as Foo>::my_method(); + | ^^^^ the trait `Foo` is not implemented for `bool` + | +help: this trait has no implementations, consider adding one + --> $DIR/issue-82038.rs:3:1 + | +LL | trait Foo { + | ^^^^^^^^^ + +error: aborting due to previous error + +For more information about this error, try `rustc --explain E0277`. diff --git a/tests/ui/traits/bound/on-structs-and-enums-in-fns.stderr b/tests/ui/traits/bound/on-structs-and-enums-in-fns.stderr index 61237a63e32..530264b344a 100644 --- a/tests/ui/traits/bound/on-structs-and-enums-in-fns.stderr +++ b/tests/ui/traits/bound/on-structs-and-enums-in-fns.stderr @@ -4,6 +4,11 @@ error[E0277]: the trait bound `u32: Trait` is not satisfied LL | fn explode(x: Foo<u32>) {} | ^^^^^^^^ the trait `Trait` is not implemented for `u32` | +help: this trait has no implementations, consider adding one + --> $DIR/on-structs-and-enums-in-fns.rs:1:1 + | +LL | trait Trait {} + | ^^^^^^^^^^^ note: required by a bound in `Foo` --> $DIR/on-structs-and-enums-in-fns.rs:3:14 | @@ -16,6 +21,11 @@ error[E0277]: the trait bound `f32: Trait` is not satisfied LL | fn kaboom(y: Bar<f32>) {} | ^^^^^^^^ the trait `Trait` is not implemented for `f32` | +help: this trait has no implementations, consider adding one + --> $DIR/on-structs-and-enums-in-fns.rs:1:1 + | +LL | trait Trait {} + | ^^^^^^^^^^^ note: required by a bound in `Bar` --> $DIR/on-structs-and-enums-in-fns.rs:7:12 | diff --git a/tests/ui/traits/bound/on-structs-and-enums-in-impls.stderr b/tests/ui/traits/bound/on-structs-and-enums-in-impls.stderr index 8a43742260b..372bbabbd86 100644 --- a/tests/ui/traits/bound/on-structs-and-enums-in-impls.stderr +++ b/tests/ui/traits/bound/on-structs-and-enums-in-impls.stderr @@ -4,6 +4,11 @@ error[E0277]: the trait bound `u16: Trait` is not satisfied LL | impl PolyTrait<Foo<u16>> for Struct { | ^^^^^^^^^^^^^^^^^^^ the trait `Trait` is not implemented for `u16` | +help: this trait has no implementations, consider adding one + --> $DIR/on-structs-and-enums-in-impls.rs:1:1 + | +LL | trait Trait {} + | ^^^^^^^^^^^ note: required by a bound in `Foo` --> $DIR/on-structs-and-enums-in-impls.rs:3:14 | diff --git a/tests/ui/traits/bound/on-structs-and-enums-locals.stderr b/tests/ui/traits/bound/on-structs-and-enums-locals.stderr index 20bbe69c059..01cf76c62d5 100644 --- a/tests/ui/traits/bound/on-structs-and-enums-locals.stderr +++ b/tests/ui/traits/bound/on-structs-and-enums-locals.stderr @@ -4,6 +4,11 @@ error[E0277]: the trait bound `usize: Trait` is not satisfied LL | let baz: Foo<usize> = loop { }; | ^^^^^^^^^^ the trait `Trait` is not implemented for `usize` | +help: this trait has no implementations, consider adding one + --> $DIR/on-structs-and-enums-locals.rs:1:1 + | +LL | trait Trait { + | ^^^^^^^^^^^ note: required by a bound in `Foo` --> $DIR/on-structs-and-enums-locals.rs:5:14 | @@ -16,6 +21,11 @@ error[E0277]: the trait bound `{integer}: Trait` is not satisfied LL | x: 3 | ^ the trait `Trait` is not implemented for `{integer}` | +help: this trait has no implementations, consider adding one + --> $DIR/on-structs-and-enums-locals.rs:1:1 + | +LL | trait Trait { + | ^^^^^^^^^^^ note: required by a bound in `Foo` --> $DIR/on-structs-and-enums-locals.rs:5:14 | diff --git a/tests/ui/traits/bound/on-structs-and-enums-static.stderr b/tests/ui/traits/bound/on-structs-and-enums-static.stderr index fda734e8571..fa14aff684d 100644 --- a/tests/ui/traits/bound/on-structs-and-enums-static.stderr +++ b/tests/ui/traits/bound/on-structs-and-enums-static.stderr @@ -4,6 +4,11 @@ error[E0277]: the trait bound `usize: Trait` is not satisfied LL | static X: Foo<usize> = Foo { | ^^^^^^^^^^ the trait `Trait` is not implemented for `usize` | +help: this trait has no implementations, consider adding one + --> $DIR/on-structs-and-enums-static.rs:1:1 + | +LL | trait Trait { + | ^^^^^^^^^^^ note: required by a bound in `Foo` --> $DIR/on-structs-and-enums-static.rs:5:14 | diff --git a/tests/ui/traits/bound/on-structs-and-enums.stderr b/tests/ui/traits/bound/on-structs-and-enums.stderr index fe05b86344b..606f764852f 100644 --- a/tests/ui/traits/bound/on-structs-and-enums.stderr +++ b/tests/ui/traits/bound/on-structs-and-enums.stderr @@ -20,6 +20,11 @@ error[E0277]: the trait bound `isize: Trait` is not satisfied LL | a: Foo<isize>, | ^^^^^^^^^^ the trait `Trait` is not implemented for `isize` | +help: this trait has no implementations, consider adding one + --> $DIR/on-structs-and-enums.rs:1:1 + | +LL | trait Trait {} + | ^^^^^^^^^^^ note: required by a bound in `Foo` --> $DIR/on-structs-and-enums.rs:3:14 | @@ -32,6 +37,11 @@ error[E0277]: the trait bound `usize: Trait` is not satisfied LL | Quux(Bar<usize>), | ^^^^^^^^^^ the trait `Trait` is not implemented for `usize` | +help: this trait has no implementations, consider adding one + --> $DIR/on-structs-and-enums.rs:1:1 + | +LL | trait Trait {} + | ^^^^^^^^^^^ note: required by a bound in `Bar` --> $DIR/on-structs-and-enums.rs:7:12 | @@ -76,6 +86,11 @@ error[E0277]: the trait bound `i32: Trait` is not satisfied LL | Foo<i32>, | ^^^^^^^^ the trait `Trait` is not implemented for `i32` | +help: this trait has no implementations, consider adding one + --> $DIR/on-structs-and-enums.rs:1:1 + | +LL | trait Trait {} + | ^^^^^^^^^^^ note: required by a bound in `Foo` --> $DIR/on-structs-and-enums.rs:3:14 | @@ -88,6 +103,11 @@ error[E0277]: the trait bound `u8: Trait` is not satisfied LL | DictionaryLike { field: Bar<u8> }, | ^^^^^^^ the trait `Trait` is not implemented for `u8` | +help: this trait has no implementations, consider adding one + --> $DIR/on-structs-and-enums.rs:1:1 + | +LL | trait Trait {} + | ^^^^^^^^^^^ note: required by a bound in `Bar` --> $DIR/on-structs-and-enums.rs:7:12 | diff --git a/tests/ui/traits/deny-builtin-object-impl.current.stderr b/tests/ui/traits/deny-builtin-object-impl.current.stderr index 5c1987426f7..8ca3d3a057f 100644 --- a/tests/ui/traits/deny-builtin-object-impl.current.stderr +++ b/tests/ui/traits/deny-builtin-object-impl.current.stderr @@ -4,6 +4,11 @@ error[E0277]: the trait bound `dyn NotObject: NotObject` is not satisfied LL | test_not_object::<dyn NotObject>(); | ^^^^^^^^^^^^^ the trait `NotObject` is not implemented for `dyn NotObject` | +help: this trait has no implementations, consider adding one + --> $DIR/deny-builtin-object-impl.rs:10:1 + | +LL | trait NotObject {} + | ^^^^^^^^^^^^^^^ note: required by a bound in `test_not_object` --> $DIR/deny-builtin-object-impl.rs:14:23 | diff --git a/tests/ui/traits/deny-builtin-object-impl.next.stderr b/tests/ui/traits/deny-builtin-object-impl.next.stderr index 5c1987426f7..8ca3d3a057f 100644 --- a/tests/ui/traits/deny-builtin-object-impl.next.stderr +++ b/tests/ui/traits/deny-builtin-object-impl.next.stderr @@ -4,6 +4,11 @@ error[E0277]: the trait bound `dyn NotObject: NotObject` is not satisfied LL | test_not_object::<dyn NotObject>(); | ^^^^^^^^^^^^^ the trait `NotObject` is not implemented for `dyn NotObject` | +help: this trait has no implementations, consider adding one + --> $DIR/deny-builtin-object-impl.rs:10:1 + | +LL | trait NotObject {} + | ^^^^^^^^^^^^^^^ note: required by a bound in `test_not_object` --> $DIR/deny-builtin-object-impl.rs:14:23 | diff --git a/tests/ui/traits/dont-autoderef-ty-with-escaping-var.stderr b/tests/ui/traits/dont-autoderef-ty-with-escaping-var.stderr index 263c59ee327..a5d0e6ab095 100644 --- a/tests/ui/traits/dont-autoderef-ty-with-escaping-var.stderr +++ b/tests/ui/traits/dont-autoderef-ty-with-escaping-var.stderr @@ -10,6 +10,11 @@ error[E0277]: the trait bound `for<'a> &'a mut Vec<&'a u32>: Foo<'static, i32>` LL | <i32 as RefFoo<i32>>::ref_foo(unknown); | ^^^ the trait `for<'a> Foo<'static, i32>` is not implemented for `&'a mut Vec<&'a u32>` | +help: this trait has no implementations, consider adding one + --> $DIR/dont-autoderef-ty-with-escaping-var.rs:3:1 + | +LL | trait Foo<'x, T> {} + | ^^^^^^^^^^^^^^^^ note: required for `i32` to implement `RefFoo<i32>` --> $DIR/dont-autoderef-ty-with-escaping-var.rs:9:9 | diff --git a/tests/ui/traits/impl-bounds-checking.stderr b/tests/ui/traits/impl-bounds-checking.stderr index 1f969efe114..bfa8213abe7 100644 --- a/tests/ui/traits/impl-bounds-checking.stderr +++ b/tests/ui/traits/impl-bounds-checking.stderr @@ -4,6 +4,11 @@ error[E0277]: the trait bound `isize: Clone2` is not satisfied LL | impl Getter<isize> for isize { | ^^^^^ the trait `Clone2` is not implemented for `isize` | +help: this trait has no implementations, consider adding one + --> $DIR/impl-bounds-checking.rs:1:1 + | +LL | pub trait Clone2 { + | ^^^^^^^^^^^^^^^^ note: required by a bound in `Getter` --> $DIR/impl-bounds-checking.rs:6:17 | diff --git a/tests/ui/traits/new-solver/projection-discr-kind.stderr b/tests/ui/traits/new-solver/projection-discr-kind.stderr index 03e28f993e2..e14953f19ff 100644 --- a/tests/ui/traits/new-solver/projection-discr-kind.stderr +++ b/tests/ui/traits/new-solver/projection-discr-kind.stderr @@ -6,6 +6,11 @@ LL | needs_bar(std::mem::discriminant(&x)); | | | required by a bound introduced by this call | +help: this trait has no implementations, consider adding one + --> $DIR/projection-discr-kind.rs:10:1 + | +LL | trait Bar {} + | ^^^^^^^^^ note: required by a bound in `needs_bar` --> $DIR/projection-discr-kind.rs:11:22 | diff --git a/tests/ui/traits/non_lifetime_binders/fail.stderr b/tests/ui/traits/non_lifetime_binders/fail.stderr index 7bd02550fb3..240bcef7df5 100644 --- a/tests/ui/traits/non_lifetime_binders/fail.stderr +++ b/tests/ui/traits/non_lifetime_binders/fail.stderr @@ -13,6 +13,11 @@ error[E0277]: the trait bound `T: Trait` is not satisfied LL | fail(); | ^^^^ the trait `Trait` is not implemented for `T` | +help: this trait has no implementations, consider adding one + --> $DIR/fail.rs:6:1 + | +LL | trait Trait {} + | ^^^^^^^^^^^ note: required by a bound in `fail` --> $DIR/fail.rs:10:15 | diff --git a/tests/ui/traits/object-does-not-impl-trait.stderr b/tests/ui/traits/object-does-not-impl-trait.stderr index f1dd508a467..81d67255a0b 100644 --- a/tests/ui/traits/object-does-not-impl-trait.stderr +++ b/tests/ui/traits/object-does-not-impl-trait.stderr @@ -6,6 +6,11 @@ LL | fn take_object(f: Box<dyn Foo>) { take_foo(f); } | | | required by a bound introduced by this call | +help: this trait has no implementations, consider adding one + --> $DIR/object-does-not-impl-trait.rs:4:1 + | +LL | trait Foo {} + | ^^^^^^^^^ note: required by a bound in `take_foo` --> $DIR/object-does-not-impl-trait.rs:5:15 | diff --git a/tests/ui/traits/object/enforce-supertrait-projection.rs b/tests/ui/traits/object/enforce-supertrait-projection.rs index 2c9b41eea2a..0ea944ec2df 100644 --- a/tests/ui/traits/object/enforce-supertrait-projection.rs +++ b/tests/ui/traits/object/enforce-supertrait-projection.rs @@ -7,7 +7,7 @@ trait Trait: SuperTrait<A = <Self as SuperTrait>::B> {} fn transmute<A, B>(x: A) -> B { foo::<A, B, dyn Trait<A = A, B = B>>(x) - //~^ ERROR type mismatch resolving `<dyn Trait<B = B, A = A> as SuperTrait>::A == B` + //~^ ERROR type mismatch resolving `<dyn Trait<A = A, B = B> as SuperTrait>::A == B` } fn foo<A, B, T: ?Sized>(x: T::A) -> B diff --git a/tests/ui/traits/object/enforce-supertrait-projection.stderr b/tests/ui/traits/object/enforce-supertrait-projection.stderr index 848b4e69a4b..2fb94d34896 100644 --- a/tests/ui/traits/object/enforce-supertrait-projection.stderr +++ b/tests/ui/traits/object/enforce-supertrait-projection.stderr @@ -1,4 +1,4 @@ -error[E0271]: type mismatch resolving `<dyn Trait<B = B, A = A> as SuperTrait>::A == B` +error[E0271]: type mismatch resolving `<dyn Trait<A = A, B = B> as SuperTrait>::A == B` --> $DIR/enforce-supertrait-projection.rs:9:17 | LL | fn transmute<A, B>(x: A) -> B { diff --git a/tests/ui/traits/suggest-dereferences/dont-suggest-unsize-deref.rs b/tests/ui/traits/suggest-dereferences/dont-suggest-unsize-deref.rs new file mode 100644 index 00000000000..c6f9e345618 --- /dev/null +++ b/tests/ui/traits/suggest-dereferences/dont-suggest-unsize-deref.rs @@ -0,0 +1,15 @@ +fn use_iterator<I>(itr: I) +where + I: IntoIterator<Item = i32>, +{ +} + +fn pass_iterator<I>(i: &dyn IntoIterator<Item = i32, IntoIter = I>) +where + I: Iterator<Item = i32>, +{ + use_iterator(i); + //~^ ERROR `&dyn IntoIterator<IntoIter = I, Item = i32>` is not an iterator +} + +fn main() {} diff --git a/tests/ui/traits/suggest-dereferences/dont-suggest-unsize-deref.stderr b/tests/ui/traits/suggest-dereferences/dont-suggest-unsize-deref.stderr new file mode 100644 index 00000000000..bd0e7ca2c02 --- /dev/null +++ b/tests/ui/traits/suggest-dereferences/dont-suggest-unsize-deref.stderr @@ -0,0 +1,22 @@ +error[E0277]: `&dyn IntoIterator<IntoIter = I, Item = i32>` is not an iterator + --> $DIR/dont-suggest-unsize-deref.rs:11:18 + | +LL | use_iterator(i); + | ------------ ^ `&dyn IntoIterator<IntoIter = I, Item = i32>` is not an iterator + | | + | required by a bound introduced by this call + | + = help: the trait `Iterator` is not implemented for `&dyn IntoIterator<IntoIter = I, Item = i32>` + = note: required for `&dyn IntoIterator<IntoIter = I, Item = i32>` to implement `IntoIterator` +note: required by a bound in `use_iterator` + --> $DIR/dont-suggest-unsize-deref.rs:3:8 + | +LL | fn use_iterator<I>(itr: I) + | ------------ required by a bound in this function +LL | where +LL | I: IntoIterator<Item = i32>, + | ^^^^^^^^^^^^^^^^^^^^^^^^ required by this bound in `use_iterator` + +error: aborting due to previous error + +For more information about this error, try `rustc --explain E0277`. diff --git a/tests/ui/traits/suggest-deferences/issue-39029.fixed b/tests/ui/traits/suggest-dereferences/issue-39029.fixed index a1abf668b8b..a1abf668b8b 100644 --- a/tests/ui/traits/suggest-deferences/issue-39029.fixed +++ b/tests/ui/traits/suggest-dereferences/issue-39029.fixed diff --git a/tests/ui/traits/suggest-deferences/issue-39029.rs b/tests/ui/traits/suggest-dereferences/issue-39029.rs index 90d097105ed..90d097105ed 100644 --- a/tests/ui/traits/suggest-deferences/issue-39029.rs +++ b/tests/ui/traits/suggest-dereferences/issue-39029.rs diff --git a/tests/ui/traits/suggest-deferences/issue-39029.stderr b/tests/ui/traits/suggest-dereferences/issue-39029.stderr index 49105de3d69..49105de3d69 100644 --- a/tests/ui/traits/suggest-deferences/issue-39029.stderr +++ b/tests/ui/traits/suggest-dereferences/issue-39029.stderr diff --git a/tests/ui/traits/suggest-deferences/issue-62530.fixed b/tests/ui/traits/suggest-dereferences/issue-62530.fixed index 406caaa007f..406caaa007f 100644 --- a/tests/ui/traits/suggest-deferences/issue-62530.fixed +++ b/tests/ui/traits/suggest-dereferences/issue-62530.fixed diff --git a/tests/ui/traits/suggest-deferences/issue-62530.rs b/tests/ui/traits/suggest-dereferences/issue-62530.rs index 53846be7306..53846be7306 100644 --- a/tests/ui/traits/suggest-deferences/issue-62530.rs +++ b/tests/ui/traits/suggest-dereferences/issue-62530.rs diff --git a/tests/ui/traits/suggest-deferences/issue-62530.stderr b/tests/ui/traits/suggest-dereferences/issue-62530.stderr index e47ae0b65af..e47ae0b65af 100644 --- a/tests/ui/traits/suggest-deferences/issue-62530.stderr +++ b/tests/ui/traits/suggest-dereferences/issue-62530.stderr diff --git a/tests/ui/traits/suggest-deferences/multiple-0.fixed b/tests/ui/traits/suggest-dereferences/multiple-0.fixed index b7160b75c60..b7160b75c60 100644 --- a/tests/ui/traits/suggest-deferences/multiple-0.fixed +++ b/tests/ui/traits/suggest-dereferences/multiple-0.fixed diff --git a/tests/ui/traits/suggest-deferences/multiple-0.rs b/tests/ui/traits/suggest-dereferences/multiple-0.rs index 9ac55177ffa..9ac55177ffa 100644 --- a/tests/ui/traits/suggest-deferences/multiple-0.rs +++ b/tests/ui/traits/suggest-dereferences/multiple-0.rs diff --git a/tests/ui/traits/suggest-deferences/multiple-0.stderr b/tests/ui/traits/suggest-dereferences/multiple-0.stderr index 6a4d4b8d521..6a4d4b8d521 100644 --- a/tests/ui/traits/suggest-deferences/multiple-0.stderr +++ b/tests/ui/traits/suggest-dereferences/multiple-0.stderr diff --git a/tests/ui/traits/suggest-deferences/multiple-1.rs b/tests/ui/traits/suggest-dereferences/multiple-1.rs index 91c6c7924a4..91c6c7924a4 100644 --- a/tests/ui/traits/suggest-deferences/multiple-1.rs +++ b/tests/ui/traits/suggest-dereferences/multiple-1.rs diff --git a/tests/ui/traits/suggest-deferences/multiple-1.stderr b/tests/ui/traits/suggest-dereferences/multiple-1.stderr index 6e12321c233..6e12321c233 100644 --- a/tests/ui/traits/suggest-deferences/multiple-1.stderr +++ b/tests/ui/traits/suggest-dereferences/multiple-1.stderr diff --git a/tests/ui/traits/suggest-deferences/root-obligation.fixed b/tests/ui/traits/suggest-dereferences/root-obligation.fixed index 7a8433f9057..7a8433f9057 100644 --- a/tests/ui/traits/suggest-deferences/root-obligation.fixed +++ b/tests/ui/traits/suggest-dereferences/root-obligation.fixed diff --git a/tests/ui/traits/suggest-deferences/root-obligation.rs b/tests/ui/traits/suggest-dereferences/root-obligation.rs index 51bac2107e3..51bac2107e3 100644 --- a/tests/ui/traits/suggest-deferences/root-obligation.rs +++ b/tests/ui/traits/suggest-dereferences/root-obligation.rs diff --git a/tests/ui/traits/suggest-deferences/root-obligation.stderr b/tests/ui/traits/suggest-dereferences/root-obligation.stderr index 1363fb8c47a..1363fb8c47a 100644 --- a/tests/ui/traits/suggest-deferences/root-obligation.stderr +++ b/tests/ui/traits/suggest-dereferences/root-obligation.stderr diff --git a/tests/ui/traits/suggest-deferences/suggest-dereferencing-receiver-argument.fixed b/tests/ui/traits/suggest-dereferences/suggest-dereferencing-receiver-argument.fixed index ea3d1bf853a..ea3d1bf853a 100644 --- a/tests/ui/traits/suggest-deferences/suggest-dereferencing-receiver-argument.fixed +++ b/tests/ui/traits/suggest-dereferences/suggest-dereferencing-receiver-argument.fixed diff --git a/tests/ui/traits/suggest-deferences/suggest-dereferencing-receiver-argument.rs b/tests/ui/traits/suggest-dereferences/suggest-dereferencing-receiver-argument.rs index 9eda68027b2..9eda68027b2 100644 --- a/tests/ui/traits/suggest-deferences/suggest-dereferencing-receiver-argument.rs +++ b/tests/ui/traits/suggest-dereferences/suggest-dereferencing-receiver-argument.rs diff --git a/tests/ui/traits/suggest-deferences/suggest-dereferencing-receiver-argument.stderr b/tests/ui/traits/suggest-dereferences/suggest-dereferencing-receiver-argument.stderr index ede31a2c7bc..ede31a2c7bc 100644 --- a/tests/ui/traits/suggest-deferences/suggest-dereferencing-receiver-argument.stderr +++ b/tests/ui/traits/suggest-dereferences/suggest-dereferencing-receiver-argument.stderr diff --git a/tests/ui/traits/vtable-res-trait-param.stderr b/tests/ui/traits/vtable-res-trait-param.stderr index 2b3e3de9b1a..4cfceefb24c 100644 --- a/tests/ui/traits/vtable-res-trait-param.stderr +++ b/tests/ui/traits/vtable-res-trait-param.stderr @@ -6,6 +6,11 @@ LL | b.gimme_an_a(y) | | | required by a bound introduced by this call | +help: this trait has no implementations, consider adding one + --> $DIR/vtable-res-trait-param.rs:1:1 + | +LL | trait TraitA { + | ^^^^^^^^^^^^ note: required by a bound in `TraitB::gimme_an_a` --> $DIR/vtable-res-trait-param.rs:6:21 | diff --git a/tests/ui/trivial-bounds/trivial-bounds-leak.stderr b/tests/ui/trivial-bounds/trivial-bounds-leak.stderr index 02c5d5d2484..be472a50769 100644 --- a/tests/ui/trivial-bounds/trivial-bounds-leak.stderr +++ b/tests/ui/trivial-bounds/trivial-bounds-leak.stderr @@ -27,6 +27,12 @@ LL | Foo::test(&4i32); | --------- ^^^^^ the trait `Foo` is not implemented for `i32` | | | required by a bound introduced by this call + | +help: this trait has no implementations, consider adding one + --> $DIR/trivial-bounds-leak.rs:4:1 + | +LL | pub trait Foo { + | ^^^^^^^^^^^^^ error[E0277]: the trait bound `i32: Foo` is not satisfied --> $DIR/trivial-bounds-leak.rs:26:22 @@ -36,6 +42,11 @@ LL | generic_function(5i32); | | | required by a bound introduced by this call | +help: this trait has no implementations, consider adding one + --> $DIR/trivial-bounds-leak.rs:4:1 + | +LL | pub trait Foo { + | ^^^^^^^^^^^^^ note: required by a bound in `generic_function` --> $DIR/trivial-bounds-leak.rs:29:24 | diff --git a/tests/ui/type-alias-impl-trait/rpit_tait_equality_in_canonical_query.rs b/tests/ui/type-alias-impl-trait/rpit_tait_equality_in_canonical_query.rs new file mode 100644 index 00000000000..eefe333da45 --- /dev/null +++ b/tests/ui/type-alias-impl-trait/rpit_tait_equality_in_canonical_query.rs @@ -0,0 +1,25 @@ +//! This tries to prove the APIT's bounds in a canonical query, +//! which doesn't know anything about the defining scope of either +//! opaque type and thus makes a random choice as to which opaque type +//! becomes the hidden type of the other. When we leave the canonical +//! query, we attempt to actually check the defining anchor, but now we +//! have a situation where the RPIT gets constrained outside its anchor. + +// revisions: current next +//[next] compile-flags: -Ztrait-solver=next +// check-pass + +#![feature(type_alias_impl_trait)] + +type Opaque = impl Sized; + +fn get_rpit() -> impl Clone {} + +fn query(_: impl FnOnce() -> Opaque) {} + +fn test() -> Opaque { + query(get_rpit); + get_rpit() +} + +fn main() {} diff --git a/tests/ui/type/type-arg-out-of-scope.rs b/tests/ui/type/type-arg-out-of-scope.rs index 02aad007707..c36f9904e5d 100644 --- a/tests/ui/type/type-arg-out-of-scope.rs +++ b/tests/ui/type/type-arg-out-of-scope.rs @@ -1,4 +1,4 @@ -// error-pattern:can't use generic parameters from outer function +// error-pattern:can't use generic parameters from outer item fn foo<T>(x: T) { fn bar(f: Box<dyn FnMut(T) -> T>) { } } diff --git a/tests/ui/type/type-arg-out-of-scope.stderr b/tests/ui/type/type-arg-out-of-scope.stderr index 7f18b4510f4..8665001e243 100644 --- a/tests/ui/type/type-arg-out-of-scope.stderr +++ b/tests/ui/type/type-arg-out-of-scope.stderr @@ -1,22 +1,22 @@ -error[E0401]: can't use generic parameters from outer function +error[E0401]: can't use generic parameters from outer item --> $DIR/type-arg-out-of-scope.rs:3:29 | LL | fn foo<T>(x: T) { - | - type parameter from outer function + | - type parameter from outer item LL | fn bar(f: Box<dyn FnMut(T) -> T>) { } - | - ^ use of generic parameter from outer function + | - ^ use of generic parameter from outer item | | - | help: try using a local generic parameter instead: `<T>` + | help: try introducing a local generic parameter here: `<T>` -error[E0401]: can't use generic parameters from outer function +error[E0401]: can't use generic parameters from outer item --> $DIR/type-arg-out-of-scope.rs:3:35 | LL | fn foo<T>(x: T) { - | - type parameter from outer function + | - type parameter from outer item LL | fn bar(f: Box<dyn FnMut(T) -> T>) { } - | - ^ use of generic parameter from outer function + | - ^ use of generic parameter from outer item | | - | help: try using a local generic parameter instead: `<T>` + | help: try introducing a local generic parameter here: `<T>` error: aborting due to 2 previous errors diff --git a/tests/ui/union/projection-as-union-type-error-2.stderr b/tests/ui/union/projection-as-union-type-error-2.stderr index bab226f271d..21f4ea103ad 100644 --- a/tests/ui/union/projection-as-union-type-error-2.stderr +++ b/tests/ui/union/projection-as-union-type-error-2.stderr @@ -4,6 +4,11 @@ error[E0277]: the trait bound `u8: NotImplemented` is not satisfied LL | a: <Foo as Identity>::Identity, | ^^^^^^^^^^^^^^^^^^^^^^^^^^^ the trait `NotImplemented` is not implemented for `u8` | +help: this trait has no implementations, consider adding one + --> $DIR/projection-as-union-type-error-2.rs:9:1 + | +LL | trait NotImplemented {} + | ^^^^^^^^^^^^^^^^^^^^ note: required for `u8` to implement `Identity` --> $DIR/projection-as-union-type-error-2.rs:11:25 | diff --git a/tests/ui/union/projection-as-union-type-error.stderr b/tests/ui/union/projection-as-union-type-error.stderr index e4fbe9603ad..2b0241caf98 100644 --- a/tests/ui/union/projection-as-union-type-error.stderr +++ b/tests/ui/union/projection-as-union-type-error.stderr @@ -3,6 +3,12 @@ error[E0277]: the trait bound `u8: Identity` is not satisfied | LL | a: <Foo as Identity>::Identity, | ^^^^^^^^^^^^^^^^^^^^^^^^^^^ the trait `Identity` is not implemented for `u8` + | +help: this trait has no implementations, consider adding one + --> $DIR/projection-as-union-type-error.rs:6:1 + | +LL | pub trait Identity { + | ^^^^^^^^^^^^^^^^^^ error: aborting due to previous error diff --git a/tests/ui/unsafe/issue-115348-false-positive-warning-of-unnecessary-unsafe.rs b/tests/ui/unsafe/issue-115348-false-positive-warning-of-unnecessary-unsafe.rs new file mode 100644 index 00000000000..68559338d49 --- /dev/null +++ b/tests/ui/unsafe/issue-115348-false-positive-warning-of-unnecessary-unsafe.rs @@ -0,0 +1,16 @@ +// Regression test for #115348. + +unsafe fn uwu() {} + +// Tests that the false-positive warning "unnecessary `unsafe` block" +// should not be reported, when the error "non-exhaustive patterns" +// appears. + +fn foo(x: Option<u32>) { + match x { + //~^ ERROR non-exhaustive patterns: `None` not covered + Some(_) => unsafe { uwu() }, + } +} + +fn main() {} diff --git a/tests/ui/unsafe/issue-115348-false-positive-warning-of-unnecessary-unsafe.stderr b/tests/ui/unsafe/issue-115348-false-positive-warning-of-unnecessary-unsafe.stderr new file mode 100644 index 00000000000..7384899b978 --- /dev/null +++ b/tests/ui/unsafe/issue-115348-false-positive-warning-of-unnecessary-unsafe.stderr @@ -0,0 +1,21 @@ +error[E0004]: non-exhaustive patterns: `None` not covered + --> $DIR/issue-115348-false-positive-warning-of-unnecessary-unsafe.rs:10:11 + | +LL | match x { + | ^ pattern `None` not covered + | +note: `Option<u32>` defined here + --> $SRC_DIR/core/src/option.rs:LL:COL + ::: $SRC_DIR/core/src/option.rs:LL:COL + | + = note: not covered + = note: the matched value is of type `Option<u32>` +help: ensure that all possible cases are being handled by adding a match arm with a wildcard pattern or an explicit pattern as shown + | +LL ~ Some(_) => unsafe { uwu() }, +LL ~ None => todo!(), + | + +error: aborting due to previous error + +For more information about this error, try `rustc --explain E0004`. diff --git a/tests/ui/unsized/issue-115203.rs b/tests/ui/unsized/issue-115203.rs new file mode 100644 index 00000000000..5fe7bd64288 --- /dev/null +++ b/tests/ui/unsized/issue-115203.rs @@ -0,0 +1,11 @@ +// compile-flags: --emit link + +fn main() { + let a: [i32; 0] = []; + match [a[..]] { + //~^ ERROR cannot move a value of type `[i32] + //~| ERROR cannot move out of type `[i32]`, a non-copy slice + [[]] => (), + _ => (), + } +} diff --git a/tests/ui/unsized/issue-115203.stderr b/tests/ui/unsized/issue-115203.stderr new file mode 100644 index 00000000000..3ee734988c5 --- /dev/null +++ b/tests/ui/unsized/issue-115203.stderr @@ -0,0 +1,19 @@ +error[E0161]: cannot move a value of type `[i32]` + --> $DIR/issue-115203.rs:5:12 + | +LL | match [a[..]] { + | ^^^^^ the size of `[i32]` cannot be statically determined + +error[E0508]: cannot move out of type `[i32]`, a non-copy slice + --> $DIR/issue-115203.rs:5:12 + | +LL | match [a[..]] { + | ^^^^^ + | | + | cannot move out of here + | move occurs because value has type `[i32]`, which does not implement the `Copy` trait + +error: aborting due to 2 previous errors + +Some errors have detailed explanations: E0161, E0508. +For more information about an error, try `rustc --explain E0161`. diff --git a/tests/ui/unsized/issue-75707.stderr b/tests/ui/unsized/issue-75707.stderr index 97618ed05ed..aa7f9c78fa8 100644 --- a/tests/ui/unsized/issue-75707.stderr +++ b/tests/ui/unsized/issue-75707.stderr @@ -4,6 +4,11 @@ error[E0277]: the trait bound `MyCall: Callback` is not satisfied LL | f::<dyn Processing<Call = MyCall>>(); | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ the trait `Callback` is not implemented for `MyCall` | +help: this trait has no implementations, consider adding one + --> $DIR/issue-75707.rs:1:1 + | +LL | pub trait Callback { + | ^^^^^^^^^^^^^^^^^^ note: required by a bound in `f` --> $DIR/issue-75707.rs:9:9 | diff --git a/tests/ui/wf/hir-wf-canonicalized.stderr b/tests/ui/wf/hir-wf-canonicalized.stderr index 9fd0f9c81eb..21122e37da5 100644 --- a/tests/ui/wf/hir-wf-canonicalized.stderr +++ b/tests/ui/wf/hir-wf-canonicalized.stderr @@ -3,12 +3,24 @@ error[E0277]: the trait bound `Bar<'a, T>: Foo` is not satisfied | LL | callback: Box<dyn Callback<dyn Callback<Bar<'a, T>>>>, | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ the trait `Foo` is not implemented for `Bar<'a, T>` + | +help: this trait has no implementations, consider adding one + --> $DIR/hir-wf-canonicalized.rs:3:1 + | +LL | trait Foo { + | ^^^^^^^^^ error[E0277]: the trait bound `(dyn Callback<Bar<'a, T>, for<'b, 'c, 'd> Output = ()> + 'static): Foo` is not satisfied --> $DIR/hir-wf-canonicalized.rs:10:15 | LL | callback: Box<dyn Callback<dyn Callback<Bar<'a, T>>>>, | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ the trait `Foo` is not implemented for `(dyn Callback<Bar<'a, T>, for<'b, 'c, 'd> Output = ()> + 'static)` + | +help: this trait has no implementations, consider adding one + --> $DIR/hir-wf-canonicalized.rs:3:1 + | +LL | trait Foo { + | ^^^^^^^^^ error[E0277]: the size for values of type `(dyn Callback<Bar<'a, T>, for<'b, 'c, 'd> Output = ()> + 'static)` cannot be known at compilation time --> $DIR/hir-wf-canonicalized.rs:10:15 diff --git a/tests/ui/wf/issue-95665.stderr b/tests/ui/wf/issue-95665.stderr index b1cda59a916..f80cd41a4c2 100644 --- a/tests/ui/wf/issue-95665.stderr +++ b/tests/ui/wf/issue-95665.stderr @@ -4,6 +4,11 @@ error[E0277]: the trait bound `u8: Trait` is not satisfied LL | static VAR: Struct<u8>; | ^^^^^^^^^^ the trait `Trait` is not implemented for `u8` | +help: this trait has no implementations, consider adding one + --> $DIR/issue-95665.rs:4:1 + | +LL | pub trait Trait: {} + | ^^^^^^^^^^^^^^^ note: required by a bound in `Struct` --> $DIR/issue-95665.rs:6:22 | diff --git a/tests/ui/wf/wf-complex-assoc-type.stderr b/tests/ui/wf/wf-complex-assoc-type.stderr index ef613e3132d..6a623bec815 100644 --- a/tests/ui/wf/wf-complex-assoc-type.stderr +++ b/tests/ui/wf/wf-complex-assoc-type.stderr @@ -4,6 +4,11 @@ error[E0277]: the trait bound `bool: MyTrait` is not satisfied LL | type MyItem = Option<((AssertMyTrait<bool>, u8))>; | ^^^^^^^^^^^^^^^^^^^ the trait `MyTrait` is not implemented for `bool` | +help: this trait has no implementations, consider adding one + --> $DIR/wf-complex-assoc-type.rs:1:1 + | +LL | trait MyTrait {} + | ^^^^^^^^^^^^^ note: required by a bound in `AssertMyTrait` --> $DIR/wf-complex-assoc-type.rs:2:25 | diff --git a/tests/ui/wf/wf-foreign-fn-decl-ret.stderr b/tests/ui/wf/wf-foreign-fn-decl-ret.stderr index b03023b5fd1..0e93601043a 100644 --- a/tests/ui/wf/wf-foreign-fn-decl-ret.stderr +++ b/tests/ui/wf/wf-foreign-fn-decl-ret.stderr @@ -3,6 +3,12 @@ error[E0277]: the trait bound `(): Foo` is not satisfied | LL | pub fn lint_me() -> <() as Foo>::Assoc; | ^^^^^^^^^^^^^^^^^^ the trait `Foo` is not implemented for `()` + | +help: this trait has no implementations, consider adding one + --> $DIR/wf-foreign-fn-decl-ret.rs:6:1 + | +LL | pub trait Foo { + | ^^^^^^^^^^^^^ error[E0277]: the trait bound `u32: Unsatisfied` is not satisfied --> $DIR/wf-foreign-fn-decl-ret.rs:14:32 @@ -10,6 +16,11 @@ error[E0277]: the trait bound `u32: Unsatisfied` is not satisfied LL | pub fn lint_me_aswell() -> Bar<u32>; | ^^^^^^^^ the trait `Unsatisfied` is not implemented for `u32` | +help: this trait has no implementations, consider adding one + --> $DIR/wf-foreign-fn-decl-ret.rs:1:1 + | +LL | pub trait Unsatisfied {} + | ^^^^^^^^^^^^^^^^^^^^^ note: required by a bound in `Bar` --> $DIR/wf-foreign-fn-decl-ret.rs:4:19 | diff --git a/tests/ui/wf/wf-packed-on-proj-of-type-as-unimpl-trait.stderr b/tests/ui/wf/wf-packed-on-proj-of-type-as-unimpl-trait.stderr index e460cdcd3f3..52f46562c37 100644 --- a/tests/ui/wf/wf-packed-on-proj-of-type-as-unimpl-trait.stderr +++ b/tests/ui/wf/wf-packed-on-proj-of-type-as-unimpl-trait.stderr @@ -3,6 +3,12 @@ error[E0277]: the trait bound `DefaultAllocator: Allocator` is not satisfied | LL | struct Foo(Matrix<<DefaultAllocator as Allocator>::Buffer>); | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ the trait `Allocator` is not implemented for `DefaultAllocator` + | +help: this trait has no implementations, consider adding one + --> $DIR/wf-packed-on-proj-of-type-as-unimpl-trait.rs:23:1 + | +LL | pub trait Allocator { type Buffer; } + | ^^^^^^^^^^^^^^^^^^^ error: aborting due to previous error diff --git a/tests/ui/where-clauses/higher-ranked-fn-type.quiet.stderr b/tests/ui/where-clauses/higher-ranked-fn-type.quiet.stderr index 191a8ca8ebc..29b36f44a4d 100644 --- a/tests/ui/where-clauses/higher-ranked-fn-type.quiet.stderr +++ b/tests/ui/where-clauses/higher-ranked-fn-type.quiet.stderr @@ -4,6 +4,11 @@ error[E0277]: the trait bound `for<'b> fn(&'b ()): Foo` is not satisfied LL | called() | ^^^^^^ the trait `for<'b> Foo` is not implemented for `fn(&'b ())` | +help: this trait has no implementations, consider adding one + --> $DIR/higher-ranked-fn-type.rs:6:1 + | +LL | trait Foo { + | ^^^^^^^^^ note: required by a bound in `called` --> $DIR/higher-ranked-fn-type.rs:12:25 | diff --git a/tests/ui/where-clauses/higher-ranked-fn-type.verbose.stderr b/tests/ui/where-clauses/higher-ranked-fn-type.verbose.stderr index ce409f627be..54afeaa7eda 100644 --- a/tests/ui/where-clauses/higher-ranked-fn-type.verbose.stderr +++ b/tests/ui/where-clauses/higher-ranked-fn-type.verbose.stderr @@ -4,6 +4,11 @@ error[E0277]: the trait bound `for<Region(BrNamed(DefId(0:6 ~ higher_ranked_fn_t LL | called() | ^^^^^^ the trait `for<Region(BrNamed(DefId(0:6 ~ higher_ranked_fn_type[9e51]::called::'b), 'b))> Foo` is not implemented for `fn(&ReLateBound(DebruijnIndex(1), BoundRegion { var: 0, kind: BrNamed(DefId(0:6 ~ higher_ranked_fn_type[9e51]::called::'b), 'b) }) ())` | +help: this trait has no implementations, consider adding one + --> $DIR/higher-ranked-fn-type.rs:6:1 + | +LL | trait Foo { + | ^^^^^^^^^ note: required by a bound in `called` --> $DIR/higher-ranked-fn-type.rs:12:25 | diff --git a/tests/ui/where-clauses/where-clause-method-substituion.stderr b/tests/ui/where-clauses/where-clause-method-substituion.stderr index 8c47ed6d431..2f3b615a13b 100644 --- a/tests/ui/where-clauses/where-clause-method-substituion.stderr +++ b/tests/ui/where-clauses/where-clause-method-substituion.stderr @@ -4,6 +4,11 @@ error[E0277]: the trait bound `X: Foo<X>` is not satisfied LL | 1.method::<X>(); | ^ the trait `Foo<X>` is not implemented for `X` | +help: this trait has no implementations, consider adding one + --> $DIR/where-clause-method-substituion.rs:1:1 + | +LL | trait Foo<T> { + | ^^^^^^^^^^^^ note: required by a bound in `Bar::method` --> $DIR/where-clause-method-substituion.rs:6:34 | |
