diff options
Diffstat (limited to 'tests')
109 files changed, 1486 insertions, 211 deletions
diff --git a/tests/codegen/function-arguments.rs b/tests/codegen/function-arguments.rs index 96dfde18683..d6f019016a5 100644 --- a/tests/codegen/function-arguments.rs +++ b/tests/codegen/function-arguments.rs @@ -1,6 +1,7 @@ // compile-flags: -O -C no-prepopulate-passes #![crate_type = "lib"] +#![feature(dyn_star)] use std::mem::MaybeUninit; use std::num::NonZeroU64; @@ -279,3 +280,11 @@ pub fn enum_id_1(x: Option<Result<u16, u16>>) -> Option<Result<u16, u16>> { pub fn enum_id_2(x: Option<u8>) -> Option<u8> { x } + +// CHECK: { {{\{\}\*|ptr}}, {{.+}} } @dyn_star({{\{\}\*|ptr}} noundef %x.0, {{.+}} noalias noundef readonly align {{.*}} dereferenceable({{.*}}) %x.1) +// Expect an ABI something like `{ {}*, [3 x i64]* }`, but that's hard to match on generically, +// so do like the `trait_box` test and just match on `{{.+}}` for the vtable. +#[no_mangle] +pub fn dyn_star(x: dyn* Drop) -> dyn* Drop { + x +} diff --git a/tests/codegen/inherit_overflow.rs b/tests/codegen/inherit_overflow.rs new file mode 100644 index 00000000000..0b0b890b2c9 --- /dev/null +++ b/tests/codegen/inherit_overflow.rs @@ -0,0 +1,14 @@ +// compile-flags: -Zmir-enable-passes=+Inline,+ConstProp --crate-type lib +// revisions: ASSERT NOASSERT +//[ASSERT] compile-flags: -Coverflow-checks=on +//[NOASSERT] compile-flags: -Coverflow-checks=off + +// CHECK-LABEL: define{{.*}} @assertion +// ASSERT: call void @_ZN4core9panicking5panic17h +// NOASSERT: ret i8 0 +#[no_mangle] +pub fn assertion() -> u8 { + // Optimized MIR will replace this `CheckedBinaryOp` by `const (0, true)`. + // Verify that codegen does or does not emit the panic. + <u8 as std::ops::Add>::add(255, 1) +} diff --git a/tests/mir-opt/const_prop/bad_op_div_by_zero.main.ConstProp.diff b/tests/mir-opt/const_prop/bad_op_div_by_zero.main.ConstProp.diff index bea32a67ef4..900061a484b 100644 --- a/tests/mir-opt/const_prop/bad_op_div_by_zero.main.ConstProp.diff +++ b/tests/mir-opt/const_prop/bad_op_div_by_zero.main.ConstProp.diff @@ -24,9 +24,10 @@ StorageLive(_3); // scope 1 at $DIR/bad_op_div_by_zero.rs:+2:18: +2:19 - _3 = _1; // scope 1 at $DIR/bad_op_div_by_zero.rs:+2:18: +2:19 - _4 = Eq(_3, const 0_i32); // scope 1 at $DIR/bad_op_div_by_zero.rs:+2:14: +2:19 +- assert(!move _4, "attempt to divide `{}` by zero", const 1_i32) -> bb1; // scope 1 at $DIR/bad_op_div_by_zero.rs:+2:14: +2:19 + _3 = const 0_i32; // scope 1 at $DIR/bad_op_div_by_zero.rs:+2:18: +2:19 + _4 = const true; // scope 1 at $DIR/bad_op_div_by_zero.rs:+2:14: +2:19 - assert(!move _4, "attempt to divide `{}` by zero", const 1_i32) -> bb1; // scope 1 at $DIR/bad_op_div_by_zero.rs:+2:14: +2:19 ++ assert(!const true, "attempt to divide `{}` by zero", const 1_i32) -> bb1; // scope 1 at $DIR/bad_op_div_by_zero.rs:+2:14: +2:19 } bb1: { diff --git a/tests/mir-opt/const_prop/inherit_overflow.main.ConstProp.diff b/tests/mir-opt/const_prop/inherit_overflow.main.ConstProp.diff new file mode 100644 index 00000000000..d03c23a3fb5 --- /dev/null +++ b/tests/mir-opt/const_prop/inherit_overflow.main.ConstProp.diff @@ -0,0 +1,39 @@ +- // MIR for `main` before ConstProp ++ // MIR for `main` after ConstProp + + fn main() -> () { + let mut _0: (); // return place in scope 0 at $DIR/inherit_overflow.rs:+0:11: +0:11 + let mut _1: u8; // in scope 0 at $DIR/inherit_overflow.rs:+3:13: +3:47 + let mut _2: u8; // in scope 0 at $DIR/inherit_overflow.rs:+3:13: +3:47 + let mut _3: u8; // in scope 0 at $DIR/inherit_overflow.rs:+3:13: +3:47 + scope 1 { + } + scope 2 (inlined <u8 as Add>::add) { // at $DIR/inherit_overflow.rs:8:13: 8:47 + debug self => _2; // in scope 2 at $SRC_DIR/core/src/ops/arith.rs:LL:COL + debug other => _3; // in scope 2 at $SRC_DIR/core/src/ops/arith.rs:LL:COL + let mut _4: (u8, bool); // in scope 2 at $SRC_DIR/core/src/ops/arith.rs:LL:COL + } + + bb0: { + StorageLive(_1); // scope 0 at $DIR/inherit_overflow.rs:+3:13: +3:47 + StorageLive(_2); // scope 0 at $DIR/inherit_overflow.rs:+3:13: +3:47 + _2 = const u8::MAX; // scope 0 at $DIR/inherit_overflow.rs:+3:13: +3:47 + StorageLive(_3); // scope 0 at $DIR/inherit_overflow.rs:+3:13: +3:47 + _3 = const 1_u8; // scope 0 at $DIR/inherit_overflow.rs:+3:13: +3:47 +- _4 = CheckedAdd(_2, _3); // scope 2 at $SRC_DIR/core/src/ops/arith.rs:LL:COL +- assert(!move (_4.1: bool), "attempt to compute `{} + {}`, which would overflow", _2, _3) -> bb1; // scope 2 at $SRC_DIR/core/src/ops/arith.rs:LL:COL ++ _4 = const (0_u8, true); // scope 2 at $SRC_DIR/core/src/ops/arith.rs:LL:COL ++ assert(!const true, "attempt to compute `{} + {}`, which would overflow", _2, _3) -> bb1; // scope 2 at $SRC_DIR/core/src/ops/arith.rs:LL:COL + } + + bb1: { +- _1 = move (_4.0: u8); // scope 2 at $SRC_DIR/core/src/ops/arith.rs:LL:COL ++ _1 = const 0_u8; // scope 2 at $SRC_DIR/core/src/ops/arith.rs:LL:COL + StorageDead(_3); // scope 0 at $DIR/inherit_overflow.rs:+3:13: +3:47 + StorageDead(_2); // scope 0 at $DIR/inherit_overflow.rs:+3:13: +3:47 + StorageDead(_1); // scope 0 at $DIR/inherit_overflow.rs:+3:47: +3:48 + _0 = const (); // scope 0 at $DIR/inherit_overflow.rs:+0:11: +4:2 + return; // scope 0 at $DIR/inherit_overflow.rs:+4:2: +4:2 + } + } + diff --git a/tests/mir-opt/const_prop/inherit_overflow.rs b/tests/mir-opt/const_prop/inherit_overflow.rs new file mode 100644 index 00000000000..541a8c5c3af --- /dev/null +++ b/tests/mir-opt/const_prop/inherit_overflow.rs @@ -0,0 +1,9 @@ +// unit-test: ConstProp +// compile-flags: -Zmir-enable-passes=+Inline + +// EMIT_MIR inherit_overflow.main.ConstProp.diff +fn main() { + // After inlining, this will contain a `CheckedBinaryOp`. + // Propagating the overflow is ok as codegen will just skip emitting the panic. + let _ = <u8 as std::ops::Add>::add(255, 1); +} diff --git a/tests/mir-opt/dataflow-const-prop/checked.main.DataflowConstProp.diff b/tests/mir-opt/dataflow-const-prop/checked.main.DataflowConstProp.diff index a4ebd0c8c18..944afed8f46 100644 --- a/tests/mir-opt/dataflow-const-prop/checked.main.DataflowConstProp.diff +++ b/tests/mir-opt/dataflow-const-prop/checked.main.DataflowConstProp.diff @@ -61,7 +61,7 @@ - assert(!move (_10.1: bool), "attempt to compute `{} + {}`, which would overflow", move _9, const 1_i32) -> bb2; // scope 4 at $DIR/checked.rs:+6:13: +6:18 + _9 = const i32::MAX; // scope 4 at $DIR/checked.rs:+6:13: +6:14 + _10 = CheckedAdd(const i32::MAX, const 1_i32); // scope 4 at $DIR/checked.rs:+6:13: +6:18 -+ assert(!move (_10.1: bool), "attempt to compute `{} + {}`, which would overflow", const i32::MAX, const 1_i32) -> bb2; // scope 4 at $DIR/checked.rs:+6:13: +6:18 ++ assert(!const true, "attempt to compute `{} + {}`, which would overflow", const i32::MAX, const 1_i32) -> bb2; // scope 4 at $DIR/checked.rs:+6:13: +6:18 } bb2: { diff --git a/tests/mir-opt/dataflow-const-prop/inherit_overflow.main.DataflowConstProp.diff b/tests/mir-opt/dataflow-const-prop/inherit_overflow.main.DataflowConstProp.diff index 33122f465fe..29781e9ce18 100644 --- a/tests/mir-opt/dataflow-const-prop/inherit_overflow.main.DataflowConstProp.diff +++ b/tests/mir-opt/dataflow-const-prop/inherit_overflow.main.DataflowConstProp.diff @@ -5,26 +5,34 @@ let mut _0: (); // return place in scope 0 at $DIR/inherit_overflow.rs:+0:11: +0:11 let mut _1: u8; // in scope 0 at $DIR/inherit_overflow.rs:+3:13: +3:47 let mut _2: u8; // in scope 0 at $DIR/inherit_overflow.rs:+3:13: +3:47 + let mut _3: u8; // in scope 0 at $DIR/inherit_overflow.rs:+3:13: +3:47 scope 1 { } - scope 2 (inlined <u8 as Add>::add) { // at $DIR/inherit_overflow.rs:7:13: 7:47 - debug self => _1; // in scope 2 at $SRC_DIR/core/src/ops/arith.rs:LL:COL - debug other => _2; // in scope 2 at $SRC_DIR/core/src/ops/arith.rs:LL:COL - let mut _3: (u8, bool); // in scope 2 at $SRC_DIR/core/src/ops/arith.rs:LL:COL + scope 2 (inlined <u8 as Add>::add) { // at $DIR/inherit_overflow.rs:8:13: 8:47 + debug self => _2; // in scope 2 at $SRC_DIR/core/src/ops/arith.rs:LL:COL + debug other => _3; // in scope 2 at $SRC_DIR/core/src/ops/arith.rs:LL:COL + let mut _4: (u8, bool); // in scope 2 at $SRC_DIR/core/src/ops/arith.rs:LL:COL } bb0: { StorageLive(_1); // scope 0 at $DIR/inherit_overflow.rs:+3:13: +3:47 - _1 = const u8::MAX; // scope 0 at $DIR/inherit_overflow.rs:+3:13: +3:47 StorageLive(_2); // scope 0 at $DIR/inherit_overflow.rs:+3:13: +3:47 - _2 = const 1_u8; // scope 0 at $DIR/inherit_overflow.rs:+3:13: +3:47 - _3 = CheckedAdd(const u8::MAX, const 1_u8); // scope 2 at $SRC_DIR/core/src/ops/arith.rs:LL:COL - assert(!move (_3.1: bool), "attempt to compute `{} + {}`, which would overflow", const u8::MAX, const 1_u8) -> bb1; // scope 2 at $SRC_DIR/core/src/ops/arith.rs:LL:COL + _2 = const u8::MAX; // scope 0 at $DIR/inherit_overflow.rs:+3:13: +3:47 + StorageLive(_3); // scope 0 at $DIR/inherit_overflow.rs:+3:13: +3:47 + _3 = const 1_u8; // scope 0 at $DIR/inherit_overflow.rs:+3:13: +3:47 +- _4 = CheckedAdd(_2, _3); // scope 2 at $SRC_DIR/core/src/ops/arith.rs:LL:COL +- assert(!move (_4.1: bool), "attempt to compute `{} + {}`, which would overflow", _2, _3) -> bb1; // scope 2 at $SRC_DIR/core/src/ops/arith.rs:LL:COL ++ _4 = CheckedAdd(const u8::MAX, const 1_u8); // scope 2 at $SRC_DIR/core/src/ops/arith.rs:LL:COL ++ assert(!const true, "attempt to compute `{} + {}`, which would overflow", const u8::MAX, const 1_u8) -> bb1; // scope 2 at $SRC_DIR/core/src/ops/arith.rs:LL:COL } bb1: { +- _1 = move (_4.0: u8); // scope 2 at $SRC_DIR/core/src/ops/arith.rs:LL:COL ++ _1 = const 0_u8; // scope 2 at $SRC_DIR/core/src/ops/arith.rs:LL:COL + StorageDead(_3); // scope 0 at $DIR/inherit_overflow.rs:+3:13: +3:47 StorageDead(_2); // scope 0 at $DIR/inherit_overflow.rs:+3:13: +3:47 - StorageDead(_1); // scope 0 at $DIR/inherit_overflow.rs:+3:13: +3:47 + StorageDead(_1); // scope 0 at $DIR/inherit_overflow.rs:+3:47: +3:48 + _0 = const (); // scope 0 at $DIR/inherit_overflow.rs:+0:11: +4:2 return; // scope 0 at $DIR/inherit_overflow.rs:+4:2: +4:2 } } diff --git a/tests/mir-opt/dataflow-const-prop/inherit_overflow.rs b/tests/mir-opt/dataflow-const-prop/inherit_overflow.rs index 2f2d9d0102d..f4aba60f0c8 100644 --- a/tests/mir-opt/dataflow-const-prop/inherit_overflow.rs +++ b/tests/mir-opt/dataflow-const-prop/inherit_overflow.rs @@ -1,8 +1,9 @@ -// compile-flags: -Zunsound-mir-opts +// unit-test: DataflowConstProp +// compile-flags: -Zmir-enable-passes=+Inline // EMIT_MIR inherit_overflow.main.DataflowConstProp.diff fn main() { - // After inlining, this will contain a `CheckedBinaryOp`. The overflow - // must be ignored by the constant propagation to avoid triggering a panic. + // After inlining, this will contain a `CheckedBinaryOp`. + // Propagating the overflow is ok as codegen will just skip emitting the panic. let _ = <u8 as std::ops::Add>::add(255, 1); } diff --git a/tests/mir-opt/lower_intrinsics.rs b/tests/mir-opt/lower_intrinsics.rs index 66dae0e46b9..7147be43ca5 100644 --- a/tests/mir-opt/lower_intrinsics.rs +++ b/tests/mir-opt/lower_intrinsics.rs @@ -72,3 +72,10 @@ pub fn assume() { std::intrinsics::assume(true); } } + +// EMIT_MIR lower_intrinsics.with_overflow.LowerIntrinsics.diff +pub fn with_overflow(a: i32, b: i32) { + let _x = core::intrinsics::add_with_overflow(a, b); + let _y = core::intrinsics::sub_with_overflow(a, b); + let _z = core::intrinsics::mul_with_overflow(a, b); +} diff --git a/tests/mir-opt/lower_intrinsics.with_overflow.LowerIntrinsics.diff b/tests/mir-opt/lower_intrinsics.with_overflow.LowerIntrinsics.diff new file mode 100644 index 00000000000..9870a70dec5 --- /dev/null +++ b/tests/mir-opt/lower_intrinsics.with_overflow.LowerIntrinsics.diff @@ -0,0 +1,83 @@ +- // MIR for `with_overflow` before LowerIntrinsics ++ // MIR for `with_overflow` after LowerIntrinsics + + fn with_overflow(_1: i32, _2: i32) -> () { + debug a => _1; // in scope 0 at $DIR/lower_intrinsics.rs:+0:22: +0:23 + debug b => _2; // in scope 0 at $DIR/lower_intrinsics.rs:+0:30: +0:31 + let mut _0: (); // return place in scope 0 at $DIR/lower_intrinsics.rs:+0:38: +0:38 + let _3: (i32, bool); // in scope 0 at $DIR/lower_intrinsics.rs:+1:9: +1:11 + let mut _4: i32; // in scope 0 at $DIR/lower_intrinsics.rs:+1:50: +1:51 + let mut _5: i32; // in scope 0 at $DIR/lower_intrinsics.rs:+1:53: +1:54 + let mut _7: i32; // in scope 0 at $DIR/lower_intrinsics.rs:+2:50: +2:51 + let mut _8: i32; // in scope 0 at $DIR/lower_intrinsics.rs:+2:53: +2:54 + let mut _10: i32; // in scope 0 at $DIR/lower_intrinsics.rs:+3:50: +3:51 + let mut _11: i32; // in scope 0 at $DIR/lower_intrinsics.rs:+3:53: +3:54 + scope 1 { + debug _x => _3; // in scope 1 at $DIR/lower_intrinsics.rs:+1:9: +1:11 + let _6: (i32, bool); // in scope 1 at $DIR/lower_intrinsics.rs:+2:9: +2:11 + scope 2 { + debug _y => _6; // in scope 2 at $DIR/lower_intrinsics.rs:+2:9: +2:11 + let _9: (i32, bool); // in scope 2 at $DIR/lower_intrinsics.rs:+3:9: +3:11 + scope 3 { + debug _z => _9; // in scope 3 at $DIR/lower_intrinsics.rs:+3:9: +3:11 + } + } + } + + bb0: { + StorageLive(_3); // scope 0 at $DIR/lower_intrinsics.rs:+1:9: +1:11 + StorageLive(_4); // scope 0 at $DIR/lower_intrinsics.rs:+1:50: +1:51 + _4 = _1; // scope 0 at $DIR/lower_intrinsics.rs:+1:50: +1:51 + StorageLive(_5); // scope 0 at $DIR/lower_intrinsics.rs:+1:53: +1:54 + _5 = _2; // scope 0 at $DIR/lower_intrinsics.rs:+1:53: +1:54 +- _3 = add_with_overflow::<i32>(move _4, move _5) -> bb1; // scope 0 at $DIR/lower_intrinsics.rs:+1:14: +1:55 +- // mir::Constant +- // + span: $DIR/lower_intrinsics.rs:78:14: 78:49 +- // + literal: Const { ty: extern "rust-intrinsic" fn(i32, i32) -> (i32, bool) {add_with_overflow::<i32>}, val: Value(<ZST>) } ++ _3 = CheckedAdd(move _4, move _5); // scope 0 at $DIR/lower_intrinsics.rs:+1:14: +1:55 ++ goto -> bb1; // scope 0 at $DIR/lower_intrinsics.rs:+1:14: +1:55 + } + + bb1: { + StorageDead(_5); // scope 0 at $DIR/lower_intrinsics.rs:+1:54: +1:55 + StorageDead(_4); // scope 0 at $DIR/lower_intrinsics.rs:+1:54: +1:55 + StorageLive(_6); // scope 1 at $DIR/lower_intrinsics.rs:+2:9: +2:11 + StorageLive(_7); // scope 1 at $DIR/lower_intrinsics.rs:+2:50: +2:51 + _7 = _1; // scope 1 at $DIR/lower_intrinsics.rs:+2:50: +2:51 + StorageLive(_8); // scope 1 at $DIR/lower_intrinsics.rs:+2:53: +2:54 + _8 = _2; // scope 1 at $DIR/lower_intrinsics.rs:+2:53: +2:54 +- _6 = sub_with_overflow::<i32>(move _7, move _8) -> bb2; // scope 1 at $DIR/lower_intrinsics.rs:+2:14: +2:55 +- // mir::Constant +- // + span: $DIR/lower_intrinsics.rs:79:14: 79:49 +- // + literal: Const { ty: extern "rust-intrinsic" fn(i32, i32) -> (i32, bool) {sub_with_overflow::<i32>}, val: Value(<ZST>) } ++ _6 = CheckedSub(move _7, move _8); // scope 1 at $DIR/lower_intrinsics.rs:+2:14: +2:55 ++ goto -> bb2; // scope 1 at $DIR/lower_intrinsics.rs:+2:14: +2:55 + } + + bb2: { + StorageDead(_8); // scope 1 at $DIR/lower_intrinsics.rs:+2:54: +2:55 + StorageDead(_7); // scope 1 at $DIR/lower_intrinsics.rs:+2:54: +2:55 + StorageLive(_9); // scope 2 at $DIR/lower_intrinsics.rs:+3:9: +3:11 + StorageLive(_10); // scope 2 at $DIR/lower_intrinsics.rs:+3:50: +3:51 + _10 = _1; // scope 2 at $DIR/lower_intrinsics.rs:+3:50: +3:51 + StorageLive(_11); // scope 2 at $DIR/lower_intrinsics.rs:+3:53: +3:54 + _11 = _2; // scope 2 at $DIR/lower_intrinsics.rs:+3:53: +3:54 +- _9 = mul_with_overflow::<i32>(move _10, move _11) -> bb3; // scope 2 at $DIR/lower_intrinsics.rs:+3:14: +3:55 +- // mir::Constant +- // + span: $DIR/lower_intrinsics.rs:80:14: 80:49 +- // + literal: Const { ty: extern "rust-intrinsic" fn(i32, i32) -> (i32, bool) {mul_with_overflow::<i32>}, val: Value(<ZST>) } ++ _9 = CheckedMul(move _10, move _11); // scope 2 at $DIR/lower_intrinsics.rs:+3:14: +3:55 ++ goto -> bb3; // scope 2 at $DIR/lower_intrinsics.rs:+3:14: +3:55 + } + + bb3: { + StorageDead(_11); // scope 2 at $DIR/lower_intrinsics.rs:+3:54: +3:55 + StorageDead(_10); // scope 2 at $DIR/lower_intrinsics.rs:+3:54: +3:55 + _0 = const (); // scope 0 at $DIR/lower_intrinsics.rs:+0:38: +4:2 + StorageDead(_9); // scope 2 at $DIR/lower_intrinsics.rs:+4:1: +4:2 + StorageDead(_6); // scope 1 at $DIR/lower_intrinsics.rs:+4:1: +4:2 + StorageDead(_3); // scope 0 at $DIR/lower_intrinsics.rs:+4:1: +4:2 + return; // scope 0 at $DIR/lower_intrinsics.rs:+4:2: +4:2 + } + } + diff --git a/tests/rustdoc-gui/huge-collection-of-constants.goml b/tests/rustdoc-gui/huge-collection-of-constants.goml index 3ccd33f1ccd..636382a9169 100644 --- a/tests/rustdoc-gui/huge-collection-of-constants.goml +++ b/tests/rustdoc-gui/huge-collection-of-constants.goml @@ -3,7 +3,7 @@ goto: "file://" + |DOC_PATH| + "/test_docs/huge_amount_of_consts/index.html" compare-elements-position-near-false: ( - "//*[@class='item-table']//div[last()-1]", - "//*[@class='item-table']//div[last()-3]", + "//ul[@class='item-table']/li[last()-1]", + "//ul[@class='item-table']/li[last()-3]", {"y": 12}, ) diff --git a/tests/rustdoc-gui/item-summary-table.goml b/tests/rustdoc-gui/item-summary-table.goml index 2a92e9da52c..7a219bd54c3 100644 --- a/tests/rustdoc-gui/item-summary-table.goml +++ b/tests/rustdoc-gui/item-summary-table.goml @@ -1,6 +1,6 @@ // This test ensures that <table> elements aren't display in items summary. goto: "file://" + |DOC_PATH| + "/lib2/summary_table/index.html" // We check that we picked the right item first. -assert-text: (".item-table .item-left", "Foo") +assert-text: (".item-table .item-name", "Foo") // Then we check that its summary is empty. -assert-false: ".item-table .item-right" +assert-false: ".item-table .desc" diff --git a/tests/rustdoc-gui/label-next-to-symbol.goml b/tests/rustdoc-gui/label-next-to-symbol.goml index 3f4f65890b4..412e475dcc9 100644 --- a/tests/rustdoc-gui/label-next-to-symbol.goml +++ b/tests/rustdoc-gui/label-next-to-symbol.goml @@ -9,31 +9,31 @@ assert: (".stab.portability") // make sure that deprecated and portability have the right colors assert-css: ( - ".item-table .item-left .stab.deprecated", + ".item-table .item-name .stab.deprecated", { "background-color": "rgb(255, 245, 214)" }, ) assert-css: ( - ".item-table .item-left .stab.portability", + ".item-table .item-name .stab.portability", { "background-color": "rgb(255, 245, 214)" }, ) // table like view -assert-css: (".item-right.docblock-short", { "padding-left": "0px" }) +assert-css: (".desc.docblock-short", { "padding-left": "0px" }) compare-elements-position-near: ( - "//*[@class='item-left']//a[text()='replaced_function']", - ".item-left .stab.deprecated", + "//*[@class='item-name']//a[text()='replaced_function']", + ".item-name .stab.deprecated", {"y": 2}, ) compare-elements-position: ( - ".item-left .stab.deprecated", - ".item-left .stab.portability", + ".item-name .stab.deprecated", + ".item-name .stab.portability", ("y"), ) // Ensure no wrap compare-elements-position: ( - "//*[@class='item-left']//a[text()='replaced_function']/..", - "//*[@class='item-right docblock-short'][text()='a thing with a label']", + "//*[@class='item-name']//a[text()='replaced_function']/..", + "//*[@class='desc docblock-short'][text()='a thing with a label']", ("y"), ) @@ -41,26 +41,26 @@ compare-elements-position: ( // Mobile view size: (600, 600) // staggered layout with 2em spacing -assert-css: (".item-right.docblock-short", { "padding-left": "32px" }) +assert-css: (".desc.docblock-short", { "padding-left": "32px" }) compare-elements-position-near: ( - "//*[@class='item-left']//a[text()='replaced_function']", - ".item-left .stab.deprecated", + "//*[@class='item-name']//a[text()='replaced_function']", + ".item-name .stab.deprecated", {"y": 2}, ) compare-elements-position: ( - ".item-left .stab.deprecated", - ".item-left .stab.portability", + ".item-name .stab.deprecated", + ".item-name .stab.portability", ("y"), ) // Ensure wrap compare-elements-position-false: ( - "//*[@class='item-left']//a[text()='replaced_function']/..", - "//*[@class='item-right docblock-short'][text()='a thing with a label']", + "//*[@class='item-name']//a[text()='replaced_function']/..", + "//*[@class='desc docblock-short'][text()='a thing with a label']", ("y"), ) compare-elements-position-false: ( - ".item-left .stab.deprecated", - "//*[@class='item-right docblock-short'][text()='a thing with a label']", + ".item-name .stab.deprecated", + "//*[@class='desc docblock-short'][text()='a thing with a label']", ("y"), ) diff --git a/tests/rustdoc-gui/module-items-font.goml b/tests/rustdoc-gui/module-items-font.goml index 5940962a8dd..23823f8b6c7 100644 --- a/tests/rustdoc-gui/module-items-font.goml +++ b/tests/rustdoc-gui/module-items-font.goml @@ -1,7 +1,7 @@ // This test checks that the correct font is used on module items (in index.html pages). goto: "file://" + |DOC_PATH| + "/test_docs/index.html" assert-css: ( - ".item-table .item-left > a", + ".item-table .item-name > a", {"font-family": '"Fira Sans", Arial, NanumBarunGothic, sans-serif'}, ALL, ) @@ -13,55 +13,55 @@ assert-css: ( // modules assert-css: ( - "#modules + .item-table .item-left a", + "#modules + .item-table .item-name a", {"font-family": '"Fira Sans", Arial, NanumBarunGothic, sans-serif'}, ) assert-css: ( - "#modules + .item-table .item-right.docblock-short", + "#modules + .item-table .desc.docblock-short", {"font-family": '"Source Serif 4", NanumBarunGothic, serif'}, ) // structs assert-css: ( - "#structs + .item-table .item-left a", + "#structs + .item-table .item-name a", {"font-family": '"Fira Sans", Arial, NanumBarunGothic, sans-serif'}, ) assert-css: ( - "#structs + .item-table .item-right.docblock-short", + "#structs + .item-table .desc.docblock-short", {"font-family": '"Source Serif 4", NanumBarunGothic, serif'}, ) // enums assert-css: ( - "#enums + .item-table .item-left a", + "#enums + .item-table .item-name a", {"font-family": '"Fira Sans", Arial, NanumBarunGothic, sans-serif'}, ) assert-css: ( - "#enums + .item-table .item-right.docblock-short", + "#enums + .item-table .desc.docblock-short", {"font-family": '"Source Serif 4", NanumBarunGothic, serif'}, ) // traits assert-css: ( - "#traits + .item-table .item-left a", + "#traits + .item-table .item-name a", {"font-family": '"Fira Sans", Arial, NanumBarunGothic, sans-serif'}, ) assert-css: ( - "#traits + .item-table .item-right.docblock-short", + "#traits + .item-table .desc.docblock-short", {"font-family": '"Source Serif 4", NanumBarunGothic, serif'}, ) // functions assert-css: ( - "#functions + .item-table .item-left a", + "#functions + .item-table .item-name a", {"font-family": '"Fira Sans", Arial, NanumBarunGothic, sans-serif'}, ) assert-css: ( - "#functions + .item-table .item-right.docblock-short", + "#functions + .item-table .desc.docblock-short", {"font-family": '"Source Serif 4", NanumBarunGothic, serif'}, ) // keywords assert-css: ( - "#keywords + .item-table .item-left a", + "#keywords + .item-table .item-name a", {"font-family": '"Fira Sans", Arial, NanumBarunGothic, sans-serif'}, ) assert-css: ( - "#keywords + .item-table .item-right.docblock-short", + "#keywords + .item-table .desc.docblock-short", {"font-family": '"Source Serif 4", NanumBarunGothic, serif'}, ) diff --git a/tests/rustdoc-gui/sidebar.goml b/tests/rustdoc-gui/sidebar.goml index 9c742be0587..a6d51709019 100644 --- a/tests/rustdoc-gui/sidebar.goml +++ b/tests/rustdoc-gui/sidebar.goml @@ -70,8 +70,8 @@ assert-text: (".sidebar-elems section ul > li:nth-child(8)", "Functions") assert-text: (".sidebar-elems section ul > li:nth-child(9)", "Type Definitions") assert-text: (".sidebar-elems section ul > li:nth-child(10)", "Unions") assert-text: (".sidebar-elems section ul > li:nth-child(11)", "Keywords") -assert-text: ("#structs + .item-table .item-left > a", "Foo") -click: "#structs + .item-table .item-left > a" +assert-text: ("#structs + .item-table .item-name > a", "Foo") +click: "#structs + .item-table .item-name > a" // PAGE: struct.Foo.html assert-count: (".sidebar .location", 1) @@ -103,8 +103,8 @@ assert-text: (".sidebar-elems > section ul.block > li:nth-child(2)", "Structs") assert-text: (".sidebar-elems > section ul.block > li:nth-child(3)", "Traits") assert-text: (".sidebar-elems > section ul.block > li:nth-child(4)", "Functions") assert-text: (".sidebar-elems > section ul.block > li:nth-child(5)", "Type Definitions") -assert-text: ("#functions + .item-table .item-left > a", "foobar") -click: "#functions + .item-table .item-left > a" +assert-text: ("#functions + .item-table .item-name > a", "foobar") +click: "#functions + .item-table .item-name > a" // PAGE: fn.foobar.html // In items containing no items (like functions or constants) and in modules, we have no @@ -127,7 +127,7 @@ assert-text: (".sidebar > .location", "Module sub_sub_module") // We check that we don't have the crate list. assert-false: ".sidebar-elems .crate" assert-text: (".sidebar-elems > section ul > li:nth-child(1)", "Functions") -assert-text: ("#functions + .item-table .item-left > a", "foo") +assert-text: ("#functions + .item-table .item-name > a", "foo") // Links to trait implementations in the sidebar should not wrap even if they are long. goto: "file://" + |DOC_PATH| + "/lib2/struct.HasALongTraitWithParams.html" diff --git a/tests/rustdoc-gui/unsafe-fn.goml b/tests/rustdoc-gui/unsafe-fn.goml index 3ecb25c82a4..9d2577178c0 100644 --- a/tests/rustdoc-gui/unsafe-fn.goml +++ b/tests/rustdoc-gui/unsafe-fn.goml @@ -19,7 +19,7 @@ define-function: ( local-storage: {"rustdoc-theme": |theme|, "rustdoc-use-system-theme": "false"} // We reload the page so the local storage settings are being used. reload: - assert-css: (".item-left sup", {"color": |color|}) + assert-css: (".item-name sup", {"color": |color|}) }, ) diff --git a/tests/rustdoc-js-std/reference-shrink.js b/tests/rustdoc-js-std/reference-shrink.js new file mode 100644 index 00000000000..f90be6d1bfd --- /dev/null +++ b/tests/rustdoc-js-std/reference-shrink.js @@ -0,0 +1,8 @@ +// exact-check + +const QUERY = 'reference::shrink'; + +const EXPECTED = { + // avoid including the method that's not going to be in the HTML + 'others': [], +}; diff --git a/tests/rustdoc-json/reexport/same_name_different_types.rs b/tests/rustdoc-json/reexport/same_name_different_types.rs new file mode 100644 index 00000000000..2314a4eb909 --- /dev/null +++ b/tests/rustdoc-json/reexport/same_name_different_types.rs @@ -0,0 +1,25 @@ +// Regression test for <https://github.com/rust-lang/rust/issues/107677>. + +#![feature(no_core)] +#![no_core] + +pub mod nested { + // @set foo_struct = "$.index[*][?(@.docs == 'Foo the struct')].id" + + /// Foo the struct + pub struct Foo {} + + // @set foo_fn = "$.index[*][?(@.docs == 'Foo the function')].id" + + #[allow(non_snake_case)] + /// Foo the function + pub fn Foo() {} +} + +// @ismany "$.index[*][?(@.inner.name == 'Foo' && @.kind == 'import')].inner.id" $foo_fn $foo_struct +// @ismany "$.index[*][?(@.inner.name == 'Bar' && @.kind == 'import')].inner.id" $foo_fn $foo_struct + +// @count "$.index[*][?(@.inner.name == 'Foo' && @.kind == 'import')]" 2 +pub use nested::Foo; +// @count "$.index[*][?(@.inner.name == 'Bar' && @.kind == 'import')]" 2 +pub use Foo as Bar; diff --git a/tests/rustdoc-ui/bounded-hr-lifetime.stderr b/tests/rustdoc-ui/bounded-hr-lifetime.stderr index d8fcd6cb4b1..580f70c9742 100644 --- a/tests/rustdoc-ui/bounded-hr-lifetime.stderr +++ b/tests/rustdoc-ui/bounded-hr-lifetime.stderr @@ -4,7 +4,5 @@ error: lifetime bounds cannot be used in this context LL | for<'a: 'b + 'c> &'a (): std::fmt::Debug, | ^^ ^^ -error: Compilation failed, aborting rustdoc - -error: aborting due to 2 previous errors +error: aborting due to previous error diff --git a/tests/rustdoc-ui/check-fail.rs b/tests/rustdoc-ui/check-fail.rs index c5e1759ee2d..02632b4ce7d 100644 --- a/tests/rustdoc-ui/check-fail.rs +++ b/tests/rustdoc-ui/check-fail.rs @@ -2,6 +2,7 @@ #![feature(rustdoc_missing_doc_code_examples)] #![deny(missing_docs)] +#![deny(rustdoc::missing_doc_code_examples)] #![deny(rustdoc::all)] //! ```rust,testharness diff --git a/tests/rustdoc-ui/check-fail.stderr b/tests/rustdoc-ui/check-fail.stderr index d8aeccbfc31..f05e457af64 100644 --- a/tests/rustdoc-ui/check-fail.stderr +++ b/tests/rustdoc-ui/check-fail.stderr @@ -1,5 +1,5 @@ error: missing documentation for a function - --> $DIR/check-fail.rs:12:1 + --> $DIR/check-fail.rs:13:1 | LL | pub fn foo() {} | ^^^^^^^^^^^^ @@ -11,7 +11,7 @@ LL | #![deny(missing_docs)] | ^^^^^^^^^^^^ error: missing code example in this documentation - --> $DIR/check-fail.rs:12:1 + --> $DIR/check-fail.rs:13:1 | LL | pub fn foo() {} | ^^^^^^^^^^^^^^^ @@ -19,12 +19,11 @@ LL | pub fn foo() {} note: the lint level is defined here --> $DIR/check-fail.rs:5:9 | -LL | #![deny(rustdoc::all)] - | ^^^^^^^^^^^^ - = note: `#[deny(rustdoc::missing_doc_code_examples)]` implied by `#[deny(rustdoc::all)]` +LL | #![deny(rustdoc::missing_doc_code_examples)] + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ error: unknown attribute `testharness`. Did you mean `test_harness`? - --> $DIR/check-fail.rs:7:1 + --> $DIR/check-fail.rs:8:1 | LL | / //! ```rust,testharness LL | | @@ -33,10 +32,15 @@ LL | | //! ``` | |_______^ | = help: the code block will either not be tested if not marked as a rust one or the code will be wrapped inside a main function +note: the lint level is defined here + --> $DIR/check-fail.rs:6:9 + | +LL | #![deny(rustdoc::all)] + | ^^^^^^^^^^^^ = note: `#[deny(rustdoc::invalid_codeblock_attributes)]` implied by `#[deny(rustdoc::all)]` error: unknown attribute `testharness`. Did you mean `test_harness`? - --> $DIR/check-fail.rs:16:1 + --> $DIR/check-fail.rs:17:1 | LL | / /// hello LL | | diff --git a/tests/rustdoc-ui/check.rs b/tests/rustdoc-ui/check.rs index f70b0336151..e389a81bb33 100644 --- a/tests/rustdoc-ui/check.rs +++ b/tests/rustdoc-ui/check.rs @@ -7,6 +7,7 @@ //~^^ WARN #![warn(missing_docs)] +#![warn(rustdoc::missing_doc_code_examples)] #![warn(rustdoc::all)] pub fn foo() {} diff --git a/tests/rustdoc-ui/check.stderr b/tests/rustdoc-ui/check.stderr index d379f33f2bd..c5ed5d0c3ef 100644 --- a/tests/rustdoc-ui/check.stderr +++ b/tests/rustdoc-ui/check.stderr @@ -17,7 +17,7 @@ LL | #![warn(missing_docs)] | ^^^^^^^^^^^^ warning: missing documentation for a function - --> $DIR/check.rs:12:1 + --> $DIR/check.rs:13:1 | LL | pub fn foo() {} | ^^^^^^^^^^^^ @@ -27,7 +27,7 @@ warning: no documentation found for this crate's top-level module = help: The following guide may be of use: https://doc.rust-lang.org/$CHANNEL/rustdoc/how-to-write-documentation.html note: the lint level is defined here - --> $DIR/check.rs:10:9 + --> $DIR/check.rs:11:9 | LL | #![warn(rustdoc::all)] | ^^^^^^^^^^^^ @@ -45,10 +45,14 @@ LL | | LL | | pub fn foo() {} | |_______________^ | - = note: `#[warn(rustdoc::missing_doc_code_examples)]` implied by `#[warn(rustdoc::all)]` +note: the lint level is defined here + --> $DIR/check.rs:10:9 + | +LL | #![warn(rustdoc::missing_doc_code_examples)] + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ warning: missing code example in this documentation - --> $DIR/check.rs:12:1 + --> $DIR/check.rs:13:1 | LL | pub fn foo() {} | ^^^^^^^^^^^^^^^ diff --git a/tests/rustdoc-ui/feature-gate-doc_cfg_hide.stderr b/tests/rustdoc-ui/feature-gate-doc_cfg_hide.stderr index ba42c7bbb05..0864159c8e2 100644 --- a/tests/rustdoc-ui/feature-gate-doc_cfg_hide.stderr +++ b/tests/rustdoc-ui/feature-gate-doc_cfg_hide.stderr @@ -7,8 +7,6 @@ LL | #![doc(cfg_hide(test))] = note: see issue #43781 <https://github.com/rust-lang/rust/issues/43781> for more information = help: add `#![feature(doc_cfg_hide)]` to the crate attributes to enable -error: Compilation failed, aborting rustdoc - -error: aborting due to 2 previous errors +error: aborting due to previous error For more information about this error, try `rustc --explain E0658`. diff --git a/tests/rustdoc-ui/feature-gate-rustdoc_missing_doc_code_examples.rs b/tests/rustdoc-ui/feature-gate-rustdoc_missing_doc_code_examples.rs index daba6986864..c34ea0567a9 100644 --- a/tests/rustdoc-ui/feature-gate-rustdoc_missing_doc_code_examples.rs +++ b/tests/rustdoc-ui/feature-gate-rustdoc_missing_doc_code_examples.rs @@ -1,10 +1,12 @@ #![deny(unknown_lints)] //~^ NOTE defined here - #![allow(rustdoc::missing_doc_code_examples)] //~^ ERROR unknown lint //~| ERROR unknown lint +//~| ERROR unknown lint +//~| NOTE lint is unstable //~| NOTE lint is unstable //~| NOTE lint is unstable //~| NOTE see issue //~| NOTE see issue +//~| NOTE see issue diff --git a/tests/rustdoc-ui/feature-gate-rustdoc_missing_doc_code_examples.stderr b/tests/rustdoc-ui/feature-gate-rustdoc_missing_doc_code_examples.stderr index cbe9a3d14af..326dcfe3bde 100644 --- a/tests/rustdoc-ui/feature-gate-rustdoc_missing_doc_code_examples.stderr +++ b/tests/rustdoc-ui/feature-gate-rustdoc_missing_doc_code_examples.stderr @@ -1,5 +1,5 @@ error: unknown lint: `rustdoc::missing_doc_code_examples` - --> $DIR/feature-gate-rustdoc_missing_doc_code_examples.rs:4:1 + --> $DIR/feature-gate-rustdoc_missing_doc_code_examples.rs:3:1 | LL | #![allow(rustdoc::missing_doc_code_examples)] | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ @@ -14,7 +14,7 @@ LL | #![deny(unknown_lints)] | ^^^^^^^^^^^^^ error: unknown lint: `rustdoc::missing_doc_code_examples` - --> $DIR/feature-gate-rustdoc_missing_doc_code_examples.rs:4:1 + --> $DIR/feature-gate-rustdoc_missing_doc_code_examples.rs:3:1 | LL | #![allow(rustdoc::missing_doc_code_examples)] | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ @@ -23,7 +23,15 @@ LL | #![allow(rustdoc::missing_doc_code_examples)] = note: see issue #101730 <https://github.com/rust-lang/rust/issues/101730> for more information = help: add `#![feature(rustdoc_missing_doc_code_examples)]` to the crate attributes to enable -error: Compilation failed, aborting rustdoc +error: unknown lint: `rustdoc::missing_doc_code_examples` + --> $DIR/feature-gate-rustdoc_missing_doc_code_examples.rs:3:1 + | +LL | #![allow(rustdoc::missing_doc_code_examples)] + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + | + = note: the `rustdoc::missing_doc_code_examples` lint is unstable + = note: see issue #101730 <https://github.com/rust-lang/rust/issues/101730> for more information + = help: add `#![feature(rustdoc_missing_doc_code_examples)]` to the crate attributes to enable error: aborting due to 3 previous errors diff --git a/tests/rustdoc-ui/impl-fn-nesting.stderr b/tests/rustdoc-ui/impl-fn-nesting.stderr index 608749af895..75e6b4ed217 100644 --- a/tests/rustdoc-ui/impl-fn-nesting.stderr +++ b/tests/rustdoc-ui/impl-fn-nesting.stderr @@ -58,9 +58,7 @@ error[E0412]: cannot find type `UnknownType` in this scope LL | pub fn doubly_nested(c: UnknownType) { | ^^^^^^^^^^^ not found in this scope -error: Compilation failed, aborting rustdoc - -error: aborting due to 11 previous errors +error: aborting due to 10 previous errors Some errors have detailed explanations: E0405, E0412. For more information about an error, try `rustc --explain E0405`. diff --git a/tests/rustdoc-ui/intra-doc/proc-macro-doc.rs b/tests/rustdoc-ui/intra-doc/proc-macro-doc.rs new file mode 100644 index 00000000000..8335fc902cc --- /dev/null +++ b/tests/rustdoc-ui/intra-doc/proc-macro-doc.rs @@ -0,0 +1,27 @@ +// check-pass +// force-host +// no-prefer-dynamic +// compile-flags: --crate-type proc-macro + +#![deny(rustdoc::broken_intra_doc_links)] + +extern crate proc_macro; +use proc_macro::*; + +/// [`Unpin`] +#[proc_macro_derive(F)] +pub fn derive_(t: proc_macro::TokenStream) -> proc_macro::TokenStream { + t +} + +/// [`Vec`] +#[proc_macro_attribute] +pub fn attr(t: proc_macro::TokenStream, _: proc_macro::TokenStream) -> proc_macro::TokenStream { + t +} + +/// [`std::fs::File`] +#[proc_macro] +pub fn func(t: proc_macro::TokenStream) -> proc_macro::TokenStream { + t +} diff --git a/tests/rustdoc-ui/intra-doc/unknown-disambiguator.stderr b/tests/rustdoc-ui/intra-doc/unknown-disambiguator.stderr index 19e541736bd..741a7f51a77 100644 --- a/tests/rustdoc-ui/intra-doc/unknown-disambiguator.stderr +++ b/tests/rustdoc-ui/intra-doc/unknown-disambiguator.stderr @@ -20,22 +20,6 @@ LL | //! Linking to [foo@banana] and [`bar@banana!()`]. | = note: see https://doc.rust-lang.org/$CHANNEL/rustdoc/write-documentation/linking-to-items-by-name.html#namespaces-and-disambiguators for more info about disambiguators -error: unknown disambiguator `foo` - --> $DIR/unknown-disambiguator.rs:10:34 - | -LL | //! And with weird backticks: [``foo@hello``] [foo`@`hello]. - | ^^^ - | - = note: see https://doc.rust-lang.org/$CHANNEL/rustdoc/write-documentation/linking-to-items-by-name.html#namespaces-and-disambiguators for more info about disambiguators - -error: unknown disambiguator `foo` - --> $DIR/unknown-disambiguator.rs:10:48 - | -LL | //! And with weird backticks: [``foo@hello``] [foo`@`hello]. - | ^^^ - | - = note: see https://doc.rust-lang.org/$CHANNEL/rustdoc/write-documentation/linking-to-items-by-name.html#namespaces-and-disambiguators for more info about disambiguators - error: unknown disambiguator `` --> $DIR/unknown-disambiguator.rs:7:31 | @@ -52,5 +36,21 @@ LL | //! And to [no disambiguator](@nectarine) and [another](@apricot!()). | = note: see https://doc.rust-lang.org/$CHANNEL/rustdoc/write-documentation/linking-to-items-by-name.html#namespaces-and-disambiguators for more info about disambiguators +error: unknown disambiguator `foo` + --> $DIR/unknown-disambiguator.rs:10:34 + | +LL | //! And with weird backticks: [``foo@hello``] [foo`@`hello]. + | ^^^ + | + = note: see https://doc.rust-lang.org/$CHANNEL/rustdoc/write-documentation/linking-to-items-by-name.html#namespaces-and-disambiguators for more info about disambiguators + +error: unknown disambiguator `foo` + --> $DIR/unknown-disambiguator.rs:10:48 + | +LL | //! And with weird backticks: [``foo@hello``] [foo`@`hello]. + | ^^^ + | + = note: see https://doc.rust-lang.org/$CHANNEL/rustdoc/write-documentation/linking-to-items-by-name.html#namespaces-and-disambiguators for more info about disambiguators + error: aborting due to 6 previous errors diff --git a/tests/rustdoc-ui/intra-doc/unresolved-import-recovery.stderr b/tests/rustdoc-ui/intra-doc/unresolved-import-recovery.stderr index b54f8200666..14f56061852 100644 --- a/tests/rustdoc-ui/intra-doc/unresolved-import-recovery.stderr +++ b/tests/rustdoc-ui/intra-doc/unresolved-import-recovery.stderr @@ -6,8 +6,6 @@ LL | use unresolved_crate::module::Name; | = help: consider adding `extern crate unresolved_crate` to use the `unresolved_crate` crate -error: Compilation failed, aborting rustdoc - -error: aborting due to 2 previous errors +error: aborting due to previous error For more information about this error, try `rustc --explain E0433`. diff --git a/tests/rustdoc-ui/issue-61732.stderr b/tests/rustdoc-ui/issue-61732.stderr index 38fadaa4435..d16ec6a853a 100644 --- a/tests/rustdoc-ui/issue-61732.stderr +++ b/tests/rustdoc-ui/issue-61732.stderr @@ -6,8 +6,6 @@ LL | pub(in crate::r#mod) fn main() {} | = help: consider adding `extern crate r#mod` to use the `r#mod` crate -error: Compilation failed, aborting rustdoc - -error: aborting due to 2 previous errors +error: aborting due to previous error For more information about this error, try `rustc --explain E0433`. diff --git a/tests/rustdoc-ui/lint-group.rs b/tests/rustdoc-ui/lint-group.rs index 09aca6d2b27..ad88157f64f 100644 --- a/tests/rustdoc-ui/lint-group.rs +++ b/tests/rustdoc-ui/lint-group.rs @@ -6,6 +6,7 @@ //! println!("sup"); //! ``` +#![deny(rustdoc::missing_doc_code_examples)] #![deny(rustdoc::all)] /// what up, let's make an [error] diff --git a/tests/rustdoc-ui/lint-group.stderr b/tests/rustdoc-ui/lint-group.stderr index 4f2c9658891..7ff09fcc45a 100644 --- a/tests/rustdoc-ui/lint-group.stderr +++ b/tests/rustdoc-ui/lint-group.stderr @@ -1,5 +1,5 @@ error: missing code example in this documentation - --> $DIR/lint-group.rs:18:1 + --> $DIR/lint-group.rs:19:1 | LL | /// wait, this doesn't have a doctest? | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ @@ -7,12 +7,11 @@ LL | /// wait, this doesn't have a doctest? note: the lint level is defined here --> $DIR/lint-group.rs:9:9 | -LL | #![deny(rustdoc::all)] - | ^^^^^^^^^^^^ - = note: `#[deny(rustdoc::missing_doc_code_examples)]` implied by `#[deny(rustdoc::all)]` +LL | #![deny(rustdoc::missing_doc_code_examples)] + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ error: documentation test in private item - --> $DIR/lint-group.rs:21:1 + --> $DIR/lint-group.rs:22:1 | LL | / /// wait, this *does* have a doctest? LL | | /// @@ -21,16 +20,21 @@ LL | | /// println!("sup"); LL | | /// ``` | |_______^ | +note: the lint level is defined here + --> $DIR/lint-group.rs:10:9 + | +LL | #![deny(rustdoc::all)] + | ^^^^^^^^^^^^ = note: `#[deny(rustdoc::private_doc_tests)]` implied by `#[deny(rustdoc::all)]` error: missing code example in this documentation - --> $DIR/lint-group.rs:28:1 + --> $DIR/lint-group.rs:29:1 | LL | /// <unknown> | ^^^^^^^^^^^^^ error: unresolved link to `error` - --> $DIR/lint-group.rs:11:29 + --> $DIR/lint-group.rs:12:29 | LL | /// what up, let's make an [error] | ^^^^^ no item named `error` in scope @@ -39,7 +43,7 @@ LL | /// what up, let's make an [error] = note: `#[deny(rustdoc::broken_intra_doc_links)]` implied by `#[deny(rustdoc::all)]` error: unclosed HTML tag `unknown` - --> $DIR/lint-group.rs:28:5 + --> $DIR/lint-group.rs:29:5 | LL | /// <unknown> | ^^^^^^^^^ diff --git a/tests/rustdoc-ui/rustdoc-all-only-stable-lints.rs b/tests/rustdoc-ui/rustdoc-all-only-stable-lints.rs new file mode 100644 index 00000000000..e106d06aff5 --- /dev/null +++ b/tests/rustdoc-ui/rustdoc-all-only-stable-lints.rs @@ -0,0 +1,6 @@ +// check-pass + +// Ensure `rustdoc::all` only affects stable lints. See #106289. + +#![deny(unknown_lints)] +#![allow(rustdoc::all)] diff --git a/tests/rustdoc-ui/unknown-renamed-lints.stderr b/tests/rustdoc-ui/unknown-renamed-lints.stderr index b105f47d751..bf529b9f8e2 100644 --- a/tests/rustdoc-ui/unknown-renamed-lints.stderr +++ b/tests/rustdoc-ui/unknown-renamed-lints.stderr @@ -58,7 +58,5 @@ error: unknown lint: `rustdoc::intra_doc_link_resolution_failure` LL | #![deny(rustdoc::intra_doc_link_resolution_failure)] | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ -error: Compilation failed, aborting rustdoc - -error: aborting due to 9 previous errors +error: aborting due to 8 previous errors diff --git a/tests/rustdoc/cfg_doc_reexport.rs b/tests/rustdoc/cfg_doc_reexport.rs index 89c7f0a6f34..a10c84f2cac 100644 --- a/tests/rustdoc/cfg_doc_reexport.rs +++ b/tests/rustdoc/cfg_doc_reexport.rs @@ -5,8 +5,8 @@ #![no_core] // @has 'foo/index.html' -// @has - '//*[@class="item-left"]/*[@class="stab portability"]' 'foobar' -// @has - '//*[@class="item-left"]/*[@class="stab portability"]' 'bar' +// @has - '//*[@class="item-name"]/*[@class="stab portability"]' 'foobar' +// @has - '//*[@class="item-name"]/*[@class="stab portability"]' 'bar' #[doc(cfg(feature = "foobar"))] mod imp_priv { diff --git a/tests/rustdoc/deprecated.rs b/tests/rustdoc/deprecated.rs index 5cbe4d59108..51860441b35 100644 --- a/tests/rustdoc/deprecated.rs +++ b/tests/rustdoc/deprecated.rs @@ -1,6 +1,6 @@ -// @has deprecated/index.html '//*[@class="item-left"]/span[@class="stab deprecated"]' \ +// @has deprecated/index.html '//*[@class="item-name"]/span[@class="stab deprecated"]' \ // 'Deprecated' -// @has - '//*[@class="item-right docblock-short"]' 'Deprecated docs' +// @has - '//*[@class="desc docblock-short"]' 'Deprecated docs' // @has deprecated/struct.S.html '//*[@class="stab deprecated"]' \ // 'Deprecated since 1.0.0: text' @@ -8,7 +8,7 @@ #[deprecated(since = "1.0.0", note = "text")] pub struct S; -// @matches deprecated/index.html '//*[@class="item-right docblock-short"]' '^Docs' +// @matches deprecated/index.html '//*[@class="desc docblock-short"]' '^Docs' /// Docs pub struct T; diff --git a/tests/rustdoc/doc-cfg.rs b/tests/rustdoc/doc-cfg.rs index 1cfbfec6fcd..c4702d4109e 100644 --- a/tests/rustdoc/doc-cfg.rs +++ b/tests/rustdoc/doc-cfg.rs @@ -12,7 +12,7 @@ pub struct Portable; // @has doc_cfg/unix_only/index.html \ // '//*[@id="main-content"]/*[@class="item-info"]/*[@class="stab portability"]' \ // 'Available on Unix only.' -// @matches - '//*[@class="item-left"]//*[@class="stab portability"]' '\AARM\Z' +// @matches - '//*[@class="item-name"]//*[@class="stab portability"]' '\AARM\Z' // @count - '//*[@class="stab portability"]' 2 #[doc(cfg(unix))] pub mod unix_only { @@ -42,7 +42,7 @@ pub mod unix_only { // @has doc_cfg/wasi_only/index.html \ // '//*[@id="main-content"]/*[@class="item-info"]/*[@class="stab portability"]' \ // 'Available on WASI only.' -// @matches - '//*[@class="item-left"]//*[@class="stab portability"]' '\AWebAssembly\Z' +// @matches - '//*[@class="item-name"]//*[@class="stab portability"]' '\AWebAssembly\Z' // @count - '//*[@class="stab portability"]' 2 #[doc(cfg(target_os = "wasi"))] pub mod wasi_only { @@ -74,7 +74,7 @@ pub mod wasi_only { // the portability header is different on the module view versus the full view // @has doc_cfg/index.html -// @matches - '//*[@class="item-left"]//*[@class="stab portability"]' '\Aavx\Z' +// @matches - '//*[@class="item-name"]//*[@class="stab portability"]' '\Aavx\Z' // @has doc_cfg/fn.uses_target_feature.html // @has - '//*[@id="main-content"]/*[@class="item-info"]/*[@class="stab portability"]' \ diff --git a/tests/rustdoc/duplicate-cfg.rs b/tests/rustdoc/duplicate-cfg.rs index 1ac2e523249..12846c5c17a 100644 --- a/tests/rustdoc/duplicate-cfg.rs +++ b/tests/rustdoc/duplicate-cfg.rs @@ -2,8 +2,8 @@ #![feature(doc_cfg)] // @has 'foo/index.html' -// @matches '-' '//*[@class="item-left"]//*[@class="stab portability"]' '^sync$' -// @has '-' '//*[@class="item-left"]//*[@class="stab portability"]/@title' 'Available on crate feature `sync` only' +// @matches '-' '//*[@class="item-name"]//*[@class="stab portability"]' '^sync$' +// @has '-' '//*[@class="item-name"]//*[@class="stab portability"]/@title' 'Available on crate feature `sync` only' // @has 'foo/struct.Foo.html' // @has '-' '//*[@class="stab portability"]' 'sync' diff --git a/tests/rustdoc/glob-shadowing-const.rs b/tests/rustdoc/glob-shadowing-const.rs index 5b786cf53f2..58fe8173e03 100644 --- a/tests/rustdoc/glob-shadowing-const.rs +++ b/tests/rustdoc/glob-shadowing-const.rs @@ -15,6 +15,6 @@ mod sub4 { pub use sub4::inner::*; // @has 'foo/index.html' -// @has - '//div[@class="item-right docblock-short"]' '1' -// @!has - '//div[@class="item-right docblock-short"]' '0' +// @has - '//div[@class="desc docblock-short"]' '1' +// @!has - '//div[@class="desc docblock-short"]' '0' fn main() { assert_eq!(X, 1); } diff --git a/tests/rustdoc/glob-shadowing.rs b/tests/rustdoc/glob-shadowing.rs index 2668b333497..c117b9d6489 100644 --- a/tests/rustdoc/glob-shadowing.rs +++ b/tests/rustdoc/glob-shadowing.rs @@ -1,17 +1,17 @@ // @has 'glob_shadowing/index.html' -// @count - '//div[@class="item-left"]' 6 -// @!has - '//div[@class="item-right docblock-short"]' 'sub1::describe' -// @has - '//div[@class="item-right docblock-short"]' 'sub2::describe' +// @count - '//div[@class="item-name"]' 6 +// @!has - '//div[@class="desc docblock-short"]' 'sub1::describe' +// @has - '//div[@class="desc docblock-short"]' 'sub2::describe' -// @!has - '//div[@class="item-right docblock-short"]' 'sub1::describe2' +// @!has - '//div[@class="desc docblock-short"]' 'sub1::describe2' -// @!has - '//div[@class="item-right docblock-short"]' 'sub1::prelude' -// @has - '//div[@class="item-right docblock-short"]' 'mod::prelude' +// @!has - '//div[@class="desc docblock-short"]' 'sub1::prelude' +// @has - '//div[@class="desc docblock-short"]' 'mod::prelude' -// @has - '//div[@class="item-right docblock-short"]' 'sub1::Foo (struct)' -// @has - '//div[@class="item-right docblock-short"]' 'mod::Foo (function)' +// @has - '//div[@class="desc docblock-short"]' 'sub1::Foo (struct)' +// @has - '//div[@class="desc docblock-short"]' 'mod::Foo (function)' -// @has - '//div[@class="item-right docblock-short"]' 'sub4::inner::X' +// @has - '//div[@class="desc docblock-short"]' 'sub4::inner::X' // @has 'glob_shadowing/fn.describe.html' // @has - '//div[@class="docblock"]' 'sub2::describe' diff --git a/tests/rustdoc/inline_cross/macros.rs b/tests/rustdoc/inline_cross/macros.rs index b11d5b6c4fa..a41b9c5b197 100644 --- a/tests/rustdoc/inline_cross/macros.rs +++ b/tests/rustdoc/inline_cross/macros.rs @@ -6,9 +6,9 @@ extern crate macros; -// @has foo/index.html '//*[@class="item-left"]/span[@class="stab deprecated"]' \ +// @has foo/index.html '//*[@class="item-name"]/span[@class="stab deprecated"]' \ // Deprecated -// @has - '//*[@class="item-left"]/span[@class="stab unstable"]' \ +// @has - '//*[@class="item-name"]/span[@class="stab unstable"]' \ // Experimental // @has foo/macro.my_macro.html diff --git a/tests/rustdoc/internal.rs b/tests/rustdoc/internal.rs index caad43a087c..27b0897689e 100644 --- a/tests/rustdoc/internal.rs +++ b/tests/rustdoc/internal.rs @@ -3,12 +3,12 @@ // Check that the unstable marker is not added for "rustc_private". // @!matches internal/index.html \ -// '//*[@class="item-right docblock-short"]/span[@class="stab unstable"]' \ +// '//*[@class="desc docblock-short"]/span[@class="stab unstable"]' \ // '' // @!matches internal/index.html \ -// '//*[@class="item-right docblock-short"]/span[@class="stab internal"]' \ +// '//*[@class="desc docblock-short"]/span[@class="stab internal"]' \ // '' -// @matches - '//*[@class="item-right docblock-short"]' 'Docs' +// @matches - '//*[@class="desc docblock-short"]' 'Docs' // @!has internal/struct.S.html '//*[@class="stab unstable"]' '' // @!has internal/struct.S.html '//*[@class="stab internal"]' '' diff --git a/tests/rustdoc/issue-107995.rs b/tests/rustdoc/issue-107995.rs new file mode 100644 index 00000000000..1273e4fdd12 --- /dev/null +++ b/tests/rustdoc/issue-107995.rs @@ -0,0 +1,28 @@ +// Regression test for <https://github.com/rust-lang/rust/issues/107995>. + +#![crate_name = "foo"] + +// @has 'foo/fn.foo.html' +// @has - '//*[@class="docblock"]//a[@href="fn.bar.html"]' 'bar`' +/// A foo, see also [ bar`] +pub fn foo() {} + +// @has 'foo/fn.bar.html' +// @has - '//*[@class="docblock"]' 'line Path line' +// @has - '//*[@class="docblock"]//a[@href="struct.Path.html"]' 'Path' +#[doc = "line ["] +#[doc = "Path"] +#[doc = "] line"] +pub fn bar() {} + +// @has 'foo/fn.another.html' +// @has - '//*[@class="docblock"]//a[@href="struct.Path.html"]' 'Path' +/// [ `Path`] +pub fn another() {} + +// @has 'foo/fn.last.html' +// @has - '//*[@class="docblock"]//a[@href="struct.Path.html"]' 'Path' +/// [ Path`] +pub fn last() {} + +pub struct Path; diff --git a/tests/rustdoc/issue-108231.rs b/tests/rustdoc/issue-108231.rs new file mode 100644 index 00000000000..684f0494fd5 --- /dev/null +++ b/tests/rustdoc/issue-108231.rs @@ -0,0 +1,23 @@ +// Regression test for <https://github.com/rust-lang/rust/issues/108231>. +// Macros with `#[macro_export]` attribute should be visible at the top level +// even if they are inside a doc hidden item. + +#![crate_name = "foo"] + +// @has 'foo/index.html' +// @count - '//*[@id="main-content"]//a[@class="macro"]' 1 +// @has - '//*[@id="main-content"]//a[@class="macro"]' 'foo' + +#[doc(hidden)] +pub mod __internal { + /// This one should be visible. + #[macro_export] + macro_rules! foo { + () => {}; + } + + /// This one should be hidden. + macro_rules! bar { + () => {}; + } +} diff --git a/tests/rustdoc/issue-32374.rs b/tests/rustdoc/issue-32374.rs index 1153a745b0b..985bf03a121 100644 --- a/tests/rustdoc/issue-32374.rs +++ b/tests/rustdoc/issue-32374.rs @@ -2,11 +2,11 @@ #![doc(issue_tracker_base_url = "https://issue_url/")] #![unstable(feature = "test", issue = "32374")] -// @matches issue_32374/index.html '//*[@class="item-left"]/span[@class="stab deprecated"]' \ +// @matches issue_32374/index.html '//*[@class="item-name"]/span[@class="stab deprecated"]' \ // 'Deprecated' -// @matches issue_32374/index.html '//*[@class="item-left"]/span[@class="stab unstable"]' \ +// @matches issue_32374/index.html '//*[@class="item-name"]/span[@class="stab unstable"]' \ // 'Experimental' -// @matches issue_32374/index.html '//*[@class="item-right docblock-short"]/text()' 'Docs' +// @matches issue_32374/index.html '//*[@class="desc docblock-short"]/text()' 'Docs' // @has issue_32374/struct.T.html '//*[@class="stab deprecated"]/span' '👎' // @has issue_32374/struct.T.html '//*[@class="stab deprecated"]/span' \ diff --git a/tests/rustdoc/issue-46377.rs b/tests/rustdoc/issue-46377.rs index 4489f038c59..1311b4721e2 100644 --- a/tests/rustdoc/issue-46377.rs +++ b/tests/rustdoc/issue-46377.rs @@ -1,3 +1,3 @@ -// @has 'issue_46377/index.html' '//*[@class="item-right docblock-short"]' 'Check out this struct!' +// @has 'issue_46377/index.html' '//*[@class="desc docblock-short"]' 'Check out this struct!' /// # Check out this struct! pub struct SomeStruct; diff --git a/tests/rustdoc/issue-55364.rs b/tests/rustdoc/issue-55364.rs index b987da30ed2..941cb3ce1ca 100644 --- a/tests/rustdoc/issue-55364.rs +++ b/tests/rustdoc/issue-55364.rs @@ -29,8 +29,8 @@ pub mod subone { // @has - '//section[@id="main-content"]/details/div[@class="docblock"]//a[@href="../fn.foo.html"]' 'foo' // @has - '//section[@id="main-content"]/details/div[@class="docblock"]//a[@href="../fn.bar.html"]' 'bar' // Though there should be such links later -// @has - '//section[@id="main-content"]/div[@class="item-table"]//div[@class="item-left"]/a[@class="fn"][@href="fn.foo.html"]' 'foo' -// @has - '//section[@id="main-content"]/div[@class="item-table"]//div[@class="item-left"]/a[@class="fn"][@href="fn.bar.html"]' 'bar' +// @has - '//section[@id="main-content"]/ul[@class="item-table"]//div[@class="item-name"]/a[@class="fn"][@href="fn.foo.html"]' 'foo' +// @has - '//section[@id="main-content"]/ul[@class="item-table"]//div[@class="item-name"]/a[@class="fn"][@href="fn.bar.html"]' 'bar' /// See either [foo] or [bar]. pub mod subtwo { @@ -68,8 +68,8 @@ pub mod subthree { // Next we go *deeper* - In order to ensure it's not just "this or parent" // we test `crate::` and a `super::super::...` chain // @has issue_55364/subfour/subfive/subsix/subseven/subeight/index.html -// @has - '//section[@id="main-content"]/div[@class="item-table"]//div[@class="item-right docblock-short"]//a[@href="../../../../../subone/fn.foo.html"]' 'other foo' -// @has - '//section[@id="main-content"]/div[@class="item-table"]//div[@class="item-right docblock-short"]//a[@href="../../../../../subtwo/fn.bar.html"]' 'other bar' +// @has - '//section[@id="main-content"]/ul[@class="item-table"]//div[@class="desc docblock-short"]//a[@href="../../../../../subone/fn.foo.html"]' 'other foo' +// @has - '//section[@id="main-content"]/ul[@class="item-table"]//div[@class="desc docblock-short"]//a[@href="../../../../../subtwo/fn.bar.html"]' 'other bar' pub mod subfour { pub mod subfive { pub mod subsix { diff --git a/tests/rustdoc/issue-95873.rs b/tests/rustdoc/issue-95873.rs index 3df93eb7cf1..83f1f2f75bf 100644 --- a/tests/rustdoc/issue-95873.rs +++ b/tests/rustdoc/issue-95873.rs @@ -1,2 +1,2 @@ -// @has issue_95873/index.html "//*[@class='item-left']" "pub use ::std as x;" +// @has issue_95873/index.html "//*[@class='item-name']" "pub use ::std as x;" pub use ::std as x; diff --git a/tests/rustdoc/reexport-check.rs b/tests/rustdoc/reexport-check.rs index 94fa0338532..5908d2150f2 100644 --- a/tests/rustdoc/reexport-check.rs +++ b/tests/rustdoc/reexport-check.rs @@ -8,13 +8,13 @@ extern crate reexport_check; #[allow(deprecated, deprecated_in_future)] pub use std::i32; // @!has 'foo/index.html' '//code' 'pub use self::string::String;' -// @has 'foo/index.html' '//div[@class="item-left"]' 'String' +// @has 'foo/index.html' '//div[@class="item-name"]' 'String' pub use std::string::String; // i32 is deprecated, String is not // @count 'foo/index.html' '//span[@class="stab deprecated"]' 1 -// @has 'foo/index.html' '//div[@class="item-right docblock-short"]' 'Docs in original' +// @has 'foo/index.html' '//div[@class="desc docblock-short"]' 'Docs in original' // this is a no-op, but shows what happens if there's an attribute that isn't a doc-comment #[doc(inline)] pub use reexport_check::S; diff --git a/tests/rustdoc/reexport-hidden-macro.rs b/tests/rustdoc/reexport-hidden-macro.rs new file mode 100644 index 00000000000..afcfa979616 --- /dev/null +++ b/tests/rustdoc/reexport-hidden-macro.rs @@ -0,0 +1,22 @@ +// Ensure that inlined reexport of hidden macros is working as expected. +// Part of <https://github.com/rust-lang/rust/issues/59368>. + +#![crate_name = "foo"] + +// @has 'foo/index.html' +// @has - '//*[@id="main-content"]//a[@href="macro.Macro2.html"]' 'Macro2' + +// @has 'foo/macro.Macro2.html' +// @has - '//*[@class="docblock"]' 'Displayed' + +#[macro_export] +#[doc(hidden)] +macro_rules! foo { + () => {}; +} + +/// not displayed +pub use crate::foo as Macro; +/// Displayed +#[doc(inline)] +pub use crate::foo as Macro2; diff --git a/tests/rustdoc/short-docblock-codeblock.rs b/tests/rustdoc/short-docblock-codeblock.rs index 3c5fa7b36ad..7ecd80b8c72 100644 --- a/tests/rustdoc/short-docblock-codeblock.rs +++ b/tests/rustdoc/short-docblock-codeblock.rs @@ -1,6 +1,6 @@ #![crate_name = "foo"] -// @count foo/index.html '//*[@class="item-right docblock-short"]' 0 +// @count foo/index.html '//*[@class="desc docblock-short"]' 0 /// ``` /// let x = 12; diff --git a/tests/rustdoc/short-docblock.rs b/tests/rustdoc/short-docblock.rs index 1a8a689be1d..791d3547c9f 100644 --- a/tests/rustdoc/short-docblock.rs +++ b/tests/rustdoc/short-docblock.rs @@ -1,7 +1,7 @@ #![crate_name = "foo"] -// @has foo/index.html '//*[@class="item-right docblock-short"]' 'fooo' -// @!has foo/index.html '//*[@class="item-right docblock-short"]/h1' 'fooo' +// @has foo/index.html '//*[@class="desc docblock-short"]' 'fooo' +// @!has foo/index.html '//*[@class="desc docblock-short"]/h1' 'fooo' // @has foo/fn.foo.html '//h2[@id="fooo"]/a[@href="#fooo"]' 'fooo' /// # fooo @@ -9,8 +9,8 @@ /// foo pub fn foo() {} -// @has foo/index.html '//*[@class="item-right docblock-short"]' 'mooood' -// @!has foo/index.html '//*[@class="item-right docblock-short"]/h2' 'mooood' +// @has foo/index.html '//*[@class="desc docblock-short"]' 'mooood' +// @!has foo/index.html '//*[@class="desc docblock-short"]/h2' 'mooood' // @has foo/foo/index.html '//h3[@id="mooood"]/a[@href="#mooood"]' 'mooood' /// ## mooood @@ -18,7 +18,7 @@ pub fn foo() {} /// foo mod pub mod foo {} -// @has foo/index.html '//*[@class="item-right docblock-short"]/a[@href=\ +// @has foo/index.html '//*[@class="desc docblock-short"]/a[@href=\ // "https://nougat.world"]/code' 'nougat' /// [`nougat`](https://nougat.world) diff --git a/tests/ui/associated-inherent-types/ambiguity.rs b/tests/ui/associated-inherent-types/ambiguity.rs new file mode 100644 index 00000000000..73920555b3e --- /dev/null +++ b/tests/ui/associated-inherent-types/ambiguity.rs @@ -0,0 +1,16 @@ +#![feature(inherent_associated_types)] +#![allow(incomplete_features)] + +struct Wrapper<T>(T); + +impl Wrapper<i32> { + type Foo = i32; +} + +impl Wrapper<()> { + type Foo = (); +} + +fn main() { + let _: Wrapper<_>::Foo = (); //~ ERROR multiple applicable items in scope +} diff --git a/tests/ui/associated-inherent-types/ambiguity.stderr b/tests/ui/associated-inherent-types/ambiguity.stderr new file mode 100644 index 00000000000..155c296cbb3 --- /dev/null +++ b/tests/ui/associated-inherent-types/ambiguity.stderr @@ -0,0 +1,20 @@ +error[E0034]: multiple applicable items in scope + --> $DIR/ambiguity.rs:15:24 + | +LL | let _: Wrapper<_>::Foo = (); + | ^^^ multiple `Foo` found + | +note: candidate #1 is defined in an impl for the type `Wrapper<i32>` + --> $DIR/ambiguity.rs:7:5 + | +LL | type Foo = i32; + | ^^^^^^^^ +note: candidate #2 is defined in an impl for the type `Wrapper<()>` + --> $DIR/ambiguity.rs:11:5 + | +LL | type Foo = (); + | ^^^^^^^^ + +error: aborting due to previous error + +For more information about this error, try `rustc --explain E0034`. diff --git a/tests/ui/associated-inherent-types/bugs/ice-substitution.rs b/tests/ui/associated-inherent-types/bugs/ice-substitution.rs new file mode 100644 index 00000000000..53ac79e0561 --- /dev/null +++ b/tests/ui/associated-inherent-types/bugs/ice-substitution.rs @@ -0,0 +1,23 @@ +// known-bug: unknown +// failure-status: 101 +// normalize-stderr-test "note: .*\n\n" -> "" +// normalize-stderr-test "thread 'rustc' panicked.*\n" -> "" +// rustc-env:RUST_BACKTRACE=0 + +// FIXME: I presume a type variable that couldn't be solved by `resolve_vars_if_possible` +// escapes the InferCtxt snapshot. + +#![feature(inherent_associated_types)] +#![allow(incomplete_features)] + +struct Cont<T>(T); + +impl<T: Copy> Cont<T> { + type Out = Vec<T>; +} + +pub fn weird<T: Copy>(x: T) { + let _: Cont<_>::Out = vec![true]; +} + +fn main() {} diff --git a/tests/ui/associated-inherent-types/bugs/ice-substitution.stderr b/tests/ui/associated-inherent-types/bugs/ice-substitution.stderr new file mode 100644 index 00000000000..7b0d1c50516 --- /dev/null +++ b/tests/ui/associated-inherent-types/bugs/ice-substitution.stderr @@ -0,0 +1,6 @@ +error: the compiler unexpectedly panicked. this is a bug. + +query stack during panic: +#0 [typeck] type-checking `weird` +#1 [typeck_item_bodies] type-checking all item bodies +end of query stack diff --git a/tests/ui/associated-inherent-types/bugs/inference-fail.rs b/tests/ui/associated-inherent-types/bugs/inference-fail.rs new file mode 100644 index 00000000000..a920b412b1a --- /dev/null +++ b/tests/ui/associated-inherent-types/bugs/inference-fail.rs @@ -0,0 +1,15 @@ +// known-bug: unknown + +#![feature(inherent_associated_types)] +#![allow(incomplete_features)] + +struct S<T>(T); + +impl S<()> { + type P = i128; +} + +fn main() { + // We fail to infer `_ == ()` here. + let _: S<_>::P; +} diff --git a/tests/ui/associated-inherent-types/bugs/inference-fail.stderr b/tests/ui/associated-inherent-types/bugs/inference-fail.stderr new file mode 100644 index 00000000000..425691bd6c4 --- /dev/null +++ b/tests/ui/associated-inherent-types/bugs/inference-fail.stderr @@ -0,0 +1,9 @@ +error[E0282]: type annotations needed + --> $DIR/inference-fail.rs:14:14 + | +LL | let _: S<_>::P; + | ^ cannot infer type + +error: aborting due to previous error + +For more information about this error, try `rustc --explain E0282`. diff --git a/tests/ui/associated-inherent-types/bugs/lack-of-regionck.rs b/tests/ui/associated-inherent-types/bugs/lack-of-regionck.rs new file mode 100644 index 00000000000..632dbf3854b --- /dev/null +++ b/tests/ui/associated-inherent-types/bugs/lack-of-regionck.rs @@ -0,0 +1,19 @@ +// known-bug: unknown +// check-pass + +// We currently don't region-check inherent associated type projections at all. + +#![feature(inherent_associated_types)] +#![allow(incomplete_features, dead_code)] + +struct S<T>(T); + +impl S<&'static ()> { + type T = (); +} + +fn usr<'a>() { + let _: S::<&'a ()>::T; // this should *fail* but it doesn't! +} + +fn main() {} diff --git a/tests/ui/associated-inherent-types/dispatch-on-self-type-0.rs b/tests/ui/associated-inherent-types/dispatch-on-self-type-0.rs new file mode 100644 index 00000000000..f846bfa4168 --- /dev/null +++ b/tests/ui/associated-inherent-types/dispatch-on-self-type-0.rs @@ -0,0 +1,41 @@ +// check-pass + +#![feature(inherent_associated_types)] +#![allow(incomplete_features)] + +// Check that inherent associated types are dispatched on the concrete Self type. + +struct Select<T>(T); + +impl Select<u8> { + type Projection = (); +} + +impl Select<String> { + type Projection = bool; +} + +struct Choose<T>(T); +struct NonCopy; + +impl<T: Copy> Choose<T> { + type Result = Vec<T>; +} + +impl Choose<NonCopy> { + type Result = (); +} + +fn main() { + let _: Select<String>::Projection = false; + let _: Select<u8>::Projection = (); + + let _: Choose<NonCopy>::Result = (); + let _: Choose<bool>::Result = vec![true]; +} + +// Test if we use the correct `ParamEnv` when proving obligations. + +pub fn parameterized<T: Copy>(x: T) { + let _: Choose<T>::Result = vec![x]; +} diff --git a/tests/ui/associated-inherent-types/dispatch-on-self-type-1.rs b/tests/ui/associated-inherent-types/dispatch-on-self-type-1.rs new file mode 100644 index 00000000000..9b0fa8dc6f3 --- /dev/null +++ b/tests/ui/associated-inherent-types/dispatch-on-self-type-1.rs @@ -0,0 +1,39 @@ +// check-pass + +#![feature(inherent_associated_types, auto_traits, negative_impls)] +#![allow(incomplete_features)] + +use std::cmp::Ordering; + +// Check that inherent associated types are dispatched on the concrete Self type. + +struct Select<T, U>(T, U); + +impl<T: Ordinary, U: Ordinary> Select<T, U> { + type Type = (); +} + +impl<T: Ordinary> Select<T, Special> { + type Type = bool; +} + +impl<T: Ordinary> Select<Special, T> { + type Type = Ordering; +} + +impl Select<Special, Special> { + type Type = (bool, bool); +} + +fn main() { + let _: Select<String, Special>::Type = false; + let _: Select<Special, Special>::Type = (true, false); + let _: Select<Special, u8>::Type = Ordering::Equal; + let _: Select<i128, ()>::Type = (); +} + +enum Special {} + +impl !Ordinary for Special {} + +auto trait Ordinary {} diff --git a/tests/ui/associated-inherent-types/dispatch-on-self-type-2.rs b/tests/ui/associated-inherent-types/dispatch-on-self-type-2.rs new file mode 100644 index 00000000000..7b205952f52 --- /dev/null +++ b/tests/ui/associated-inherent-types/dispatch-on-self-type-2.rs @@ -0,0 +1,17 @@ +#![feature(inherent_associated_types)] +#![allow(incomplete_features)] + +struct Parameterized<T, U>(T, U); + +impl Parameterized<(), ()> { + type Output = bool; +} + +impl<T> Parameterized<bool, T> { + type Result = T; +} + +fn main() { + let _: Parameterized<(), ()>::Output = String::new(); //~ ERROR mismatched types + let _: Parameterized<bool, u32>::Result = (); //~ ERROR mismatched types +} diff --git a/tests/ui/associated-inherent-types/dispatch-on-self-type-2.stderr b/tests/ui/associated-inherent-types/dispatch-on-self-type-2.stderr new file mode 100644 index 00000000000..c9a48872af4 --- /dev/null +++ b/tests/ui/associated-inherent-types/dispatch-on-self-type-2.stderr @@ -0,0 +1,19 @@ +error[E0308]: mismatched types + --> $DIR/dispatch-on-self-type-2.rs:15:44 + | +LL | let _: Parameterized<(), ()>::Output = String::new(); + | ----------------------------- ^^^^^^^^^^^^^ expected `bool`, found `String` + | | + | expected due to this + +error[E0308]: mismatched types + --> $DIR/dispatch-on-self-type-2.rs:16:47 + | +LL | let _: Parameterized<bool, u32>::Result = (); + | -------------------------------- ^^ expected `u32`, found `()` + | | + | expected due to this + +error: aborting due to 2 previous errors + +For more information about this error, try `rustc --explain E0308`. diff --git a/tests/ui/associated-inherent-types/not-found-self-type-differs-shadowing-trait-item.rs b/tests/ui/associated-inherent-types/not-found-self-type-differs-shadowing-trait-item.rs new file mode 100644 index 00000000000..d2efb24c666 --- /dev/null +++ b/tests/ui/associated-inherent-types/not-found-self-type-differs-shadowing-trait-item.rs @@ -0,0 +1,31 @@ +#![feature(inherent_associated_types)] +#![allow(incomplete_features)] + +// Check that it's okay to report “[inherent] associated type […] not found” for inherent associated +// type candidates that are not applicable (due to unsuitable Self type) even if there exists a +// “shadowed” associated type from a trait with the same name since its use would be ambiguous +// anyway if the IAT didn't exist. +// FIXME(inherent_associated_types): Figure out which error would be more helpful here. + +// revisions: shadowed uncovered + +struct S<T>(T); + +trait Tr { + type Pr; +} + +impl<T> Tr for S<T> { + type Pr = (); +} + +#[cfg(shadowed)] +impl S<()> { + type Pr = i32; +} + +fn main() { + let _: S::<bool>::Pr = (); + //[shadowed]~^ ERROR associated type `Pr` not found + //[uncovered]~^^ ERROR ambiguous associated type +} diff --git a/tests/ui/associated-inherent-types/not-found-self-type-differs-shadowing-trait-item.shadowed.stderr b/tests/ui/associated-inherent-types/not-found-self-type-differs-shadowing-trait-item.shadowed.stderr new file mode 100644 index 00000000000..3561db354c0 --- /dev/null +++ b/tests/ui/associated-inherent-types/not-found-self-type-differs-shadowing-trait-item.shadowed.stderr @@ -0,0 +1,15 @@ +error[E0220]: associated type `Pr` not found for `S<bool>` in the current scope + --> $DIR/not-found-self-type-differs-shadowing-trait-item.rs:28:23 + | +LL | struct S<T>(T); + | ----------- associated item `Pr` not found for this struct +... +LL | let _: S::<bool>::Pr = (); + | ^^ associated item not found in `S<bool>` + | + = note: the associated type was found for + - `S<()>` + +error: aborting due to previous error + +For more information about this error, try `rustc --explain E0220`. diff --git a/tests/ui/associated-inherent-types/not-found-self-type-differs-shadowing-trait-item.uncovered.stderr b/tests/ui/associated-inherent-types/not-found-self-type-differs-shadowing-trait-item.uncovered.stderr new file mode 100644 index 00000000000..88c72042ce2 --- /dev/null +++ b/tests/ui/associated-inherent-types/not-found-self-type-differs-shadowing-trait-item.uncovered.stderr @@ -0,0 +1,9 @@ +error[E0223]: ambiguous associated type + --> $DIR/not-found-self-type-differs-shadowing-trait-item.rs:28:12 + | +LL | let _: S::<bool>::Pr = (); + | ^^^^^^^^^^^^^ help: use the fully-qualified path: `<S<bool> as Tr>::Pr` + +error: aborting due to previous error + +For more information about this error, try `rustc --explain E0223`. diff --git a/tests/ui/associated-inherent-types/not-found-self-type-differs.alias.stderr b/tests/ui/associated-inherent-types/not-found-self-type-differs.alias.stderr new file mode 100644 index 00000000000..4396435a6dd --- /dev/null +++ b/tests/ui/associated-inherent-types/not-found-self-type-differs.alias.stderr @@ -0,0 +1,16 @@ +error[E0220]: associated type `Proj` not found for `Family<Option<()>>` in the current scope + --> $DIR/not-found-self-type-differs.rs:17:34 + | +LL | struct Family<T>(T); + | ---------------- associated item `Proj` not found for this struct +... +LL | type Alias = Family<Option<()>>::Proj; + | ^^^^ associated item not found in `Family<Option<()>>` + | + = note: the associated type was found for + - `Family<()>` + - `Family<Result<T, ()>>` + +error: aborting due to previous error + +For more information about this error, try `rustc --explain E0220`. diff --git a/tests/ui/associated-inherent-types/not-found-self-type-differs.local.stderr b/tests/ui/associated-inherent-types/not-found-self-type-differs.local.stderr new file mode 100644 index 00000000000..d527db02217 --- /dev/null +++ b/tests/ui/associated-inherent-types/not-found-self-type-differs.local.stderr @@ -0,0 +1,16 @@ +error[E0220]: associated type `Proj` not found for `Family<PathBuf>` in the current scope + --> $DIR/not-found-self-type-differs.rs:21:40 + | +LL | struct Family<T>(T); + | ---------------- associated item `Proj` not found for this struct +... +LL | let _: Family<std::path::PathBuf>::Proj = (); + | ^^^^ associated item not found in `Family<PathBuf>` + | + = note: the associated type was found for + - `Family<()>` + - `Family<Result<T, ()>>` + +error: aborting due to previous error + +For more information about this error, try `rustc --explain E0220`. diff --git a/tests/ui/associated-inherent-types/not-found-self-type-differs.rs b/tests/ui/associated-inherent-types/not-found-self-type-differs.rs new file mode 100644 index 00000000000..93f58dcb6e6 --- /dev/null +++ b/tests/ui/associated-inherent-types/not-found-self-type-differs.rs @@ -0,0 +1,22 @@ +// revisions: local alias + +#![feature(inherent_associated_types)] +#![allow(incomplete_features)] + +struct Family<T>(T); + +impl Family<()> { + type Proj = (); +} + +impl<T> Family<Result<T, ()>> { + type Proj = Self; +} + +#[cfg(alias)] +type Alias = Family<Option<()>>::Proj; //[alias]~ ERROR associated type `Proj` not found for `Family<Option<()>>` + +fn main() { + #[cfg(local)] + let _: Family<std::path::PathBuf>::Proj = (); //[local]~ ERROR associated type `Proj` not found for `Family<PathBuf>` +} diff --git a/tests/ui/associated-inherent-types/not-found-unsatisfied-bounds-0.rs b/tests/ui/associated-inherent-types/not-found-unsatisfied-bounds-0.rs new file mode 100644 index 00000000000..b00830fa1c1 --- /dev/null +++ b/tests/ui/associated-inherent-types/not-found-unsatisfied-bounds-0.rs @@ -0,0 +1,21 @@ +// Regression test for issue #104251. + +#![feature(inherent_associated_types)] +#![allow(incomplete_features)] + +struct Container<T: ?Sized>(T); + +impl<T> Container<T> { + type Yield = i32; +} + +struct Duple<T, U>(T, U); + +impl<T: Copy, U: Send> Duple<T, U> { + type Combination = (T, U); +} + +fn main() { + let _: Container<[u8]>::Yield = 1; //~ ERROR the associated type `Yield` exists for `Container<[u8]>`, but its trait bounds were not satisfied + let _: Duple<String, std::rc::Rc<str>>::Combination; //~ ERROR the associated type `Combination` exists for `Duple<String, Rc<str>>`, but its trait bounds were not satisfied +} diff --git a/tests/ui/associated-inherent-types/not-found-unsatisfied-bounds-0.stderr b/tests/ui/associated-inherent-types/not-found-unsatisfied-bounds-0.stderr new file mode 100644 index 00000000000..73657906761 --- /dev/null +++ b/tests/ui/associated-inherent-types/not-found-unsatisfied-bounds-0.stderr @@ -0,0 +1,27 @@ +error: the associated type `Yield` exists for `Container<[u8]>`, but its trait bounds were not satisfied + --> $DIR/not-found-unsatisfied-bounds-0.rs:19:29 + | +LL | struct Container<T: ?Sized>(T); + | --------------------------- associated item `Yield` not found for this struct +... +LL | let _: Container<[u8]>::Yield = 1; + | ^^^^^ associated type cannot be referenced on `Container<[u8]>` due to unsatisfied trait bounds + | + = note: the following trait bounds were not satisfied: + `[u8]: Sized` + +error: the associated type `Combination` exists for `Duple<String, Rc<str>>`, but its trait bounds were not satisfied + --> $DIR/not-found-unsatisfied-bounds-0.rs:20:45 + | +LL | struct Duple<T, U>(T, U); + | ------------------ associated item `Combination` not found for this struct +... +LL | let _: Duple<String, std::rc::Rc<str>>::Combination; + | ^^^^^^^^^^^ associated type cannot be referenced on `Duple<String, Rc<str>>` due to unsatisfied trait bounds + | + = note: the following trait bounds were not satisfied: + `Rc<str>: Send` + `String: Copy` + +error: aborting due to 2 previous errors + diff --git a/tests/ui/associated-inherent-types/not-found-unsatisfied-bounds-1.rs b/tests/ui/associated-inherent-types/not-found-unsatisfied-bounds-1.rs new file mode 100644 index 00000000000..c80b1364ae3 --- /dev/null +++ b/tests/ui/associated-inherent-types/not-found-unsatisfied-bounds-1.rs @@ -0,0 +1,18 @@ +// fail-check + +#![feature(inherent_associated_types)] +#![allow(incomplete_features)] + +// Test if we use the correct `ParamEnv` when proving obligations. + +fn parameterized<T>() { + let _: Container<T>::Proj = String::new(); //~ ERROR the associated type `Proj` exists for `Container<T>`, but its trait bounds were not satisfied +} + +struct Container<T>(T); + +impl<T: Clone> Container<T> { + type Proj = String; +} + +fn main() {} diff --git a/tests/ui/associated-inherent-types/not-found-unsatisfied-bounds-1.stderr b/tests/ui/associated-inherent-types/not-found-unsatisfied-bounds-1.stderr new file mode 100644 index 00000000000..230bfa538b4 --- /dev/null +++ b/tests/ui/associated-inherent-types/not-found-unsatisfied-bounds-1.stderr @@ -0,0 +1,14 @@ +error: the associated type `Proj` exists for `Container<T>`, but its trait bounds were not satisfied + --> $DIR/not-found-unsatisfied-bounds-1.rs:9:26 + | +LL | let _: Container<T>::Proj = String::new(); + | ^^^^ associated type cannot be referenced on `Container<T>` due to unsatisfied trait bounds +... +LL | struct Container<T>(T); + | ------------------- associated item `Proj` not found for this struct + | + = note: the following trait bounds were not satisfied: + `T: Clone` + +error: aborting due to previous error + diff --git a/tests/ui/associated-inherent-types/not-found-unsatisfied-bounds-in-multiple-impls.rs b/tests/ui/associated-inherent-types/not-found-unsatisfied-bounds-in-multiple-impls.rs new file mode 100644 index 00000000000..5b0e8de9c58 --- /dev/null +++ b/tests/ui/associated-inherent-types/not-found-unsatisfied-bounds-in-multiple-impls.rs @@ -0,0 +1,20 @@ +#![feature(inherent_associated_types)] +#![allow(incomplete_features)] + +struct S<A, B>(A, B); +struct Featureless; + +trait One {} +trait Two {} + +impl<T: One> S<Featureless, T> { + type X = (); +} + +impl<T: Two> S<T, Featureless> { + type X = String; +} + +fn main() { + let _: S::<Featureless, Featureless>::X; //~ ERROR the associated type `X` exists for `S<Featureless, Featureless>`, but its trait bounds were not satisfied +} diff --git a/tests/ui/associated-inherent-types/not-found-unsatisfied-bounds-in-multiple-impls.stderr b/tests/ui/associated-inherent-types/not-found-unsatisfied-bounds-in-multiple-impls.stderr new file mode 100644 index 00000000000..3ddab25deb5 --- /dev/null +++ b/tests/ui/associated-inherent-types/not-found-unsatisfied-bounds-in-multiple-impls.stderr @@ -0,0 +1,20 @@ +error: the associated type `X` exists for `S<Featureless, Featureless>`, but its trait bounds were not satisfied + --> $DIR/not-found-unsatisfied-bounds-in-multiple-impls.rs:19:43 + | +LL | struct S<A, B>(A, B); + | -------------- associated item `X` not found for this struct +LL | struct Featureless; + | ------------------ + | | + | doesn't satisfy `Featureless: One` + | doesn't satisfy `Featureless: Two` +... +LL | let _: S::<Featureless, Featureless>::X; + | ^ associated type cannot be referenced on `S<Featureless, Featureless>` due to unsatisfied trait bounds + | + = note: the following trait bounds were not satisfied: + `Featureless: One` + `Featureless: Two` + +error: aborting due to previous error + diff --git a/tests/ui/associated-inherent-types/substitute-params-bad.rs b/tests/ui/associated-inherent-types/substitute-params-bad.rs new file mode 100644 index 00000000000..00eb1a14da4 --- /dev/null +++ b/tests/ui/associated-inherent-types/substitute-params-bad.rs @@ -0,0 +1,23 @@ +// Regression test for issue #105305 and for +// https://github.com/rust-lang/rust/issues/107468#issuecomment-1409096700 + +#![feature(inherent_associated_types)] +#![allow(incomplete_features)] + +struct S<T>(T); + +impl<T, 'a> S<T> { //~ ERROR lifetime parameters must be declared prior to type and const parameters + type P = T; +} + +struct Subj<T>(T); + +impl<T, S> Subj<(T, S)> { + type Un = (T, S); +} + +fn main() { + type A = S<()>::P; + + let _: Subj<(i32, i32)>::Un = 0i32; //~ ERROR mismatched types +} diff --git a/tests/ui/associated-inherent-types/substitute-params-bad.stderr b/tests/ui/associated-inherent-types/substitute-params-bad.stderr new file mode 100644 index 00000000000..7a7808ba67b --- /dev/null +++ b/tests/ui/associated-inherent-types/substitute-params-bad.stderr @@ -0,0 +1,20 @@ +error: lifetime parameters must be declared prior to type and const parameters + --> $DIR/substitute-params-bad.rs:9:9 + | +LL | impl<T, 'a> S<T> { + | ----^^- help: reorder the parameters: lifetimes, then consts and types: `<'a, T>` + +error[E0308]: mismatched types + --> $DIR/substitute-params-bad.rs:22:35 + | +LL | let _: Subj<(i32, i32)>::Un = 0i32; + | -------------------- ^^^^ expected `(i32, i32)`, found `i32` + | | + | expected due to this + | + = note: expected tuple `(i32, i32)` + found type `i32` + +error: aborting due to 2 previous errors + +For more information about this error, try `rustc --explain E0308`. diff --git a/tests/ui/associated-inherent-types/struct-generics.rs b/tests/ui/associated-inherent-types/substitute-params.rs index 8952b379173..e94d6833159 100644 --- a/tests/ui/associated-inherent-types/struct-generics.rs +++ b/tests/ui/associated-inherent-types/substitute-params.rs @@ -9,7 +9,15 @@ impl<T> S<T> { type P = T; } +impl<T> S<(T,)> { + type Un = T; +} + fn main() { + // Regression test for issue #104240. type A = S<()>::P; let _: A = (); + + // Regression test for issue #107468. + let _: S<(i32,)>::Un = 0i32; } diff --git a/tests/ui/async-await/in-trait/async-default-fn-overridden.rs b/tests/ui/async-await/in-trait/async-default-fn-overridden.rs new file mode 100644 index 00000000000..0fd1a2703db --- /dev/null +++ b/tests/ui/async-await/in-trait/async-default-fn-overridden.rs @@ -0,0 +1,66 @@ +// run-pass +// edition:2021 + +#![feature(async_fn_in_trait)] +//~^ WARN the feature `async_fn_in_trait` is incomplete and may not be safe to use + +use std::future::Future; + +trait AsyncTrait { + async fn default_impl() { + assert!(false); + } + + async fn call_default_impl() { + Self::default_impl().await + } +} + +struct AsyncType; + +impl AsyncTrait for AsyncType { + async fn default_impl() { + // :) + } +} + +async fn async_main() { + // Should not assert false + AsyncType::call_default_impl().await; +} + +// ------------------------------------------------------------------------- // +// Implementation Details Below... + +use std::pin::Pin; +use std::task::*; + +pub fn noop_waker() -> Waker { + let raw = RawWaker::new(std::ptr::null(), &NOOP_WAKER_VTABLE); + + // SAFETY: the contracts for RawWaker and RawWakerVTable are upheld + unsafe { Waker::from_raw(raw) } +} + +const NOOP_WAKER_VTABLE: RawWakerVTable = RawWakerVTable::new(noop_clone, noop, noop, noop); + +unsafe fn noop_clone(_p: *const ()) -> RawWaker { + RawWaker::new(std::ptr::null(), &NOOP_WAKER_VTABLE) +} + +unsafe fn noop(_p: *const ()) {} + +fn main() { + let mut fut = async_main(); + + // Poll loop, just to test the future... + let waker = noop_waker(); + let ctx = &mut Context::from_waker(&waker); + + loop { + match unsafe { Pin::new_unchecked(&mut fut).poll(ctx) } { + Poll::Pending => {} + Poll::Ready(()) => break, + } + } +} diff --git a/tests/ui/async-await/in-trait/async-default-fn-overridden.stderr b/tests/ui/async-await/in-trait/async-default-fn-overridden.stderr new file mode 100644 index 00000000000..61a826258d0 --- /dev/null +++ b/tests/ui/async-await/in-trait/async-default-fn-overridden.stderr @@ -0,0 +1,11 @@ +warning: the feature `async_fn_in_trait` is incomplete and may not be safe to use and/or cause compiler crashes + --> $DIR/async-default-fn-overridden.rs:4:12 + | +LL | #![feature(async_fn_in_trait)] + | ^^^^^^^^^^^^^^^^^ + | + = note: see issue #91611 <https://github.com/rust-lang/rust/issues/91611> for more information + = note: `#[warn(incomplete_features)]` on by default + +warning: 1 warning emitted + diff --git a/tests/ui/check-cfg/invalid-cfg-value.stderr b/tests/ui/check-cfg/invalid-cfg-value.stderr index 60abcb18824..83383ea61a4 100644 --- a/tests/ui/check-cfg/invalid-cfg-value.stderr +++ b/tests/ui/check-cfg/invalid-cfg-value.stderr @@ -2,7 +2,9 @@ warning: unexpected `cfg` condition value --> $DIR/invalid-cfg-value.rs:7:7 | LL | #[cfg(feature = "sedre")] - | ^^^^^^^^^^^^^^^^^ + | ^^^^^^^^^^------- + | | + | help: did you mean: `"serde"` | = note: expected values for `feature` are: full, serde = note: `#[warn(unexpected_cfgs)]` on by default diff --git a/tests/ui/const-generics/early/invalid-const-arguments.stderr b/tests/ui/const-generics/early/invalid-const-arguments.stderr index b46e7e24f49..cee34e3b715 100644 --- a/tests/ui/const-generics/early/invalid-const-arguments.stderr +++ b/tests/ui/const-generics/early/invalid-const-arguments.stderr @@ -49,12 +49,9 @@ error[E0747]: type provided when a constant was expected --> $DIR/invalid-const-arguments.rs:10:19 | LL | impl<N> Foo for B<N> {} - | ^ - | -help: consider changing this type parameter to be a `const` generic - | -LL | impl<const N: u8> Foo for B<N> {} - | ~~~~~~~~~~~ + | - ^ + | | + | help: consider changing this type parameter to a const parameter: `const N: u8` error[E0747]: unresolved item provided when a constant was expected --> $DIR/invalid-const-arguments.rs:14:32 diff --git a/tests/ui/consts/const-eval/raw-bytes.32bit.stderr b/tests/ui/consts/const-eval/raw-bytes.32bit.stderr index 91a426580c3..a0f8dd097c7 100644 --- a/tests/ui/consts/const-eval/raw-bytes.32bit.stderr +++ b/tests/ui/consts/const-eval/raw-bytes.32bit.stderr @@ -167,7 +167,7 @@ error[E0080]: it is undefined behavior to use this value --> $DIR/raw-bytes.rs:96:1 | LL | const USIZE_AS_REF: &'static u8 = unsafe { mem::transmute(1337usize) }; - | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ constructing invalid value: encountered a dangling reference (address 0x539 is unallocated) + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ constructing invalid value: encountered a dangling reference (0x539[noalloc] has no provenance) | = note: The rules on what exactly is undefined behavior aren't clear, so this check might be overzealous. Please open an issue on the rustc repository if you believe it should not be considered undefined behavior. = note: the raw bytes of the constant (size: 4, align: 4) { @@ -178,7 +178,7 @@ error[E0080]: it is undefined behavior to use this value --> $DIR/raw-bytes.rs:99:1 | LL | const USIZE_AS_BOX: Box<u8> = unsafe { mem::transmute(1337usize) }; - | ^^^^^^^^^^^^^^^^^^^^^^^^^^^ constructing invalid value: encountered a dangling box (address 0x539 is unallocated) + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^ constructing invalid value: encountered a dangling box (0x539[noalloc] has no provenance) | = note: The rules on what exactly is undefined behavior aren't clear, so this check might be overzealous. Please open an issue on the rustc repository if you believe it should not be considered undefined behavior. = note: the raw bytes of the constant (size: 4, align: 4) { diff --git a/tests/ui/consts/const-eval/raw-bytes.64bit.stderr b/tests/ui/consts/const-eval/raw-bytes.64bit.stderr index e4c5e62f6bd..9706f3ec2e0 100644 --- a/tests/ui/consts/const-eval/raw-bytes.64bit.stderr +++ b/tests/ui/consts/const-eval/raw-bytes.64bit.stderr @@ -167,7 +167,7 @@ error[E0080]: it is undefined behavior to use this value --> $DIR/raw-bytes.rs:96:1 | LL | const USIZE_AS_REF: &'static u8 = unsafe { mem::transmute(1337usize) }; - | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ constructing invalid value: encountered a dangling reference (address 0x539 is unallocated) + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ constructing invalid value: encountered a dangling reference (0x539[noalloc] has no provenance) | = note: The rules on what exactly is undefined behavior aren't clear, so this check might be overzealous. Please open an issue on the rustc repository if you believe it should not be considered undefined behavior. = note: the raw bytes of the constant (size: 8, align: 8) { @@ -178,7 +178,7 @@ error[E0080]: it is undefined behavior to use this value --> $DIR/raw-bytes.rs:99:1 | LL | const USIZE_AS_BOX: Box<u8> = unsafe { mem::transmute(1337usize) }; - | ^^^^^^^^^^^^^^^^^^^^^^^^^^^ constructing invalid value: encountered a dangling box (address 0x539 is unallocated) + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^ constructing invalid value: encountered a dangling box (0x539[noalloc] has no provenance) | = note: The rules on what exactly is undefined behavior aren't clear, so this check might be overzealous. Please open an issue on the rustc repository if you believe it should not be considered undefined behavior. = note: the raw bytes of the constant (size: 8, align: 8) { diff --git a/tests/ui/consts/const-eval/ub-ref-ptr.stderr b/tests/ui/consts/const-eval/ub-ref-ptr.stderr index ce618802bd2..6bd367b6469 100644 --- a/tests/ui/consts/const-eval/ub-ref-ptr.stderr +++ b/tests/ui/consts/const-eval/ub-ref-ptr.stderr @@ -85,7 +85,7 @@ error[E0080]: it is undefined behavior to use this value --> $DIR/ub-ref-ptr.rs:43:1 | LL | const USIZE_AS_REF: &'static u8 = unsafe { mem::transmute(1337usize) }; - | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ constructing invalid value: encountered a dangling reference (address 0x539 is unallocated) + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ constructing invalid value: encountered a dangling reference (0x539[noalloc] has no provenance) | = note: The rules on what exactly is undefined behavior aren't clear, so this check might be overzealous. Please open an issue on the rustc repository if you believe it should not be considered undefined behavior. = note: the raw bytes of the constant (size: $SIZE, align: $ALIGN) { @@ -96,7 +96,7 @@ error[E0080]: it is undefined behavior to use this value --> $DIR/ub-ref-ptr.rs:46:1 | LL | const USIZE_AS_BOX: Box<u8> = unsafe { mem::transmute(1337usize) }; - | ^^^^^^^^^^^^^^^^^^^^^^^^^^^ constructing invalid value: encountered a dangling box (address 0x539 is unallocated) + | ^^^^^^^^^^^^^^^^^^^^^^^^^^^ constructing invalid value: encountered a dangling box (0x539[noalloc] has no provenance) | = note: The rules on what exactly is undefined behavior aren't clear, so this check might be overzealous. Please open an issue on the rustc repository if you believe it should not be considered undefined behavior. = note: the raw bytes of the constant (size: $SIZE, align: $ALIGN) { diff --git a/tests/ui/did_you_mean/println-typo.rs b/tests/ui/did_you_mean/println-typo.rs new file mode 100644 index 00000000000..685b5e1f284 --- /dev/null +++ b/tests/ui/did_you_mean/println-typo.rs @@ -0,0 +1,6 @@ +// https://internals.rust-lang.org/t/18227 + +fn main() { + prinltn!(); //~ ERROR cannot find macro `prinltn` in this scope + //^ a macro with a similar name exists: `println` +} diff --git a/tests/ui/did_you_mean/println-typo.stderr b/tests/ui/did_you_mean/println-typo.stderr new file mode 100644 index 00000000000..43b7b1894e2 --- /dev/null +++ b/tests/ui/did_you_mean/println-typo.stderr @@ -0,0 +1,11 @@ +error: cannot find macro `prinltn` in this scope + --> $DIR/println-typo.rs:4:5 + | +LL | prinltn!(); + | ^^^^^^^ help: a macro with a similar name exists: `println` + --> $SRC_DIR/std/src/macros.rs:LL:COL + | + = note: similarly named macro `println` defined here + +error: aborting due to previous error + diff --git a/tests/ui/dyn-star/dyn-star-to-dyn.rs b/tests/ui/dyn-star/dyn-star-to-dyn.rs index a6d9df9523a..1d974b7ecb2 100644 --- a/tests/ui/dyn-star/dyn-star-to-dyn.rs +++ b/tests/ui/dyn-star/dyn-star-to-dyn.rs @@ -1,9 +1,17 @@ -// build-pass +// run-pass #![feature(dyn_star)] //~^ WARN the feature `dyn_star` is incomplete and may not be safe to use and/or cause compiler crashes +use std::fmt::Debug; + fn main() { - let x: dyn* Send = &(); - let x = Box::new(x) as Box<dyn Send>; + let x: dyn* Debug = &42; + let x = Box::new(x) as Box<dyn Debug>; + assert_eq!("42", format!("{x:?}")); + + // Also test opposite direction. + let x: Box<dyn Debug> = Box::new(42); + let x = &x as dyn* Debug; + assert_eq!("42", format!("{x:?}")); } diff --git a/tests/ui/dyn-star/llvm-old-style-ptrs.rs b/tests/ui/dyn-star/llvm-old-style-ptrs.rs new file mode 100644 index 00000000000..d35519632be --- /dev/null +++ b/tests/ui/dyn-star/llvm-old-style-ptrs.rs @@ -0,0 +1,23 @@ +// run-pass +// compile-flags: -Copt-level=0 -Cllvm-args=-opaque-pointers=0 + +// (opaque-pointers flag is called force-opaque-pointers in LLVM 13...) +// min-llvm-version: 14.0 + +// This test can be removed once non-opaque pointers are gone from LLVM, maybe. + +#![feature(dyn_star, pointer_like_trait)] +#![allow(incomplete_features)] + +use std::fmt::Debug; +use std::marker::PointerLike; + +fn make_dyn_star<'a>(t: impl PointerLike + Debug + 'a) -> dyn* Debug + 'a { + t as _ +} + +fn main() { + println!("{:?}", make_dyn_star(Box::new(1i32))); + println!("{:?}", make_dyn_star(2usize)); + println!("{:?}", make_dyn_star((3usize,))); +} diff --git a/tests/ui/errors/traits/blame-trait-error-spans-on-exprs.rs b/tests/ui/errors/traits/blame-trait-error-spans-on-exprs.rs index 2b75f432412..6fea409ed47 100644 --- a/tests/ui/errors/traits/blame-trait-error-spans-on-exprs.rs +++ b/tests/ui/errors/traits/blame-trait-error-spans-on-exprs.rs @@ -71,6 +71,8 @@ struct DoubleWrapper<T> { impl<T: T1> T1 for DoubleWrapper<T> {} +impl<'a, T: T2> T1 for &'a T {} + fn example<Q>(q: Q) { // In each of the following examples, we expect the error span to point at the 'q' variable, // since the missing constraint is `Q: T3`. @@ -126,6 +128,10 @@ fn example<Q>(q: Q) { Two { a: Two { a: (), b: Two { a: Two { a: (), b: q }, b: () } }, b: () }, //~^ ERROR the trait bound `Q: T1` is not satisfied [E0277] ); + + // Verifies for reference: + want(&Burrito { spicy: false, filling: q }); + //~^ ERROR the trait bound `Q: T3` is not satisfied [E0277] } fn main() {} diff --git a/tests/ui/errors/traits/blame-trait-error-spans-on-exprs.stderr b/tests/ui/errors/traits/blame-trait-error-spans-on-exprs.stderr index 5f87c670d8a..6913771f288 100644 --- a/tests/ui/errors/traits/blame-trait-error-spans-on-exprs.stderr +++ b/tests/ui/errors/traits/blame-trait-error-spans-on-exprs.stderr @@ -1,5 +1,5 @@ error[E0277]: the trait bound `Q: T3` is not satisfied - --> $DIR/blame-trait-error-spans-on-exprs.rs:79:60 + --> $DIR/blame-trait-error-spans-on-exprs.rs:81:60 | LL | want(Wrapper { value: Burrito { spicy: false, filling: q } }); | ---- required by a bound introduced by this call ^ the trait `T3` is not implemented for `Q` @@ -29,7 +29,7 @@ LL | fn example<Q: T3>(q: Q) { | ++++ error[E0277]: the trait bound `Q: T3` is not satisfied - --> $DIR/blame-trait-error-spans-on-exprs.rs:83:84 + --> $DIR/blame-trait-error-spans-on-exprs.rs:85:84 | LL | want(Wrapper { value: BurritoKinds::SmallBurrito { spicy: true, small_filling: q } }); | ---- required by a bound introduced by this call ^ the trait `T3` is not implemented for `Q` @@ -59,7 +59,7 @@ LL | fn example<Q: T3>(q: Q) { | ++++ error[E0277]: the trait bound `Q: T3` is not satisfied - --> $DIR/blame-trait-error-spans-on-exprs.rs:87:39 + --> $DIR/blame-trait-error-spans-on-exprs.rs:89:39 | LL | want(Wrapper { value: Taco(false, q) }); | ---- ^ the trait `T3` is not implemented for `Q` @@ -91,7 +91,7 @@ LL | fn example<Q: T3>(q: Q) { | ++++ error[E0277]: the trait bound `Q: T3` is not satisfied - --> $DIR/blame-trait-error-spans-on-exprs.rs:91:27 + --> $DIR/blame-trait-error-spans-on-exprs.rs:93:27 | LL | want(Wrapper { value: TacoKinds::OneTaco(false, q) }); | ---- ^^^^^^^^^^^^^^^^^^^^^^^^^^^^ the trait `T3` is not implemented for `Q` @@ -123,7 +123,7 @@ LL | fn example<Q: T3>(q: Q) { | ++++ error[E0277]: the trait bound `Q: T3` is not satisfied - --> $DIR/blame-trait-error-spans-on-exprs.rs:95:74 + --> $DIR/blame-trait-error-spans-on-exprs.rs:97:74 | LL | want(Wrapper { value: GenericBurrito { spiciness: NotSpicy, filling: q } }); | ---- required by a bound introduced by this call ^ the trait `T3` is not implemented for `Q` @@ -153,7 +153,7 @@ LL | fn example<Q: T3>(q: Q) { | ++++ error[E0277]: the trait bound `Q: T2` is not satisfied - --> $DIR/blame-trait-error-spans-on-exprs.rs:99:14 + --> $DIR/blame-trait-error-spans-on-exprs.rs:101:14 | LL | want((3, q)); | ---- ^ the trait `T2` is not implemented for `Q` @@ -178,7 +178,7 @@ LL | fn example<Q: T2>(q: Q) { | ++++ error[E0277]: the trait bound `Q: T3` is not satisfied - --> $DIR/blame-trait-error-spans-on-exprs.rs:103:31 + --> $DIR/blame-trait-error-spans-on-exprs.rs:105:31 | LL | want(Wrapper { value: (3, q) }); | ---- ^ the trait `T3` is not implemented for `Q` @@ -210,7 +210,7 @@ LL | fn example<Q: T3>(q: Q) { | ++++ error[E0277]: the trait bound `Q: T3` is not satisfied - --> $DIR/blame-trait-error-spans-on-exprs.rs:107:15 + --> $DIR/blame-trait-error-spans-on-exprs.rs:109:15 | LL | want(((3, q), 5)); | ---- ^ the trait `T3` is not implemented for `Q` @@ -242,7 +242,7 @@ LL | fn example<Q: T3>(q: Q) { | ++++ error[E0277]: the trait bound `Q: T1` is not satisfied - --> $DIR/blame-trait-error-spans-on-exprs.rs:110:49 + --> $DIR/blame-trait-error-spans-on-exprs.rs:112:49 | LL | want(DoubleWrapper { item: Wrapper { value: q } }); | ---- ^ the trait `T1` is not implemented for `Q` @@ -267,7 +267,7 @@ LL | fn example<Q: T1>(q: Q) { | ++++ error[E0277]: the trait bound `Q: T1` is not satisfied - --> $DIR/blame-trait-error-spans-on-exprs.rs:113:88 + --> $DIR/blame-trait-error-spans-on-exprs.rs:115:88 | LL | want(DoubleWrapper { item: Wrapper { value: DoubleWrapper { item: Wrapper { value: q } } } }); | ---- required by a bound introduced by this call ^ the trait `T1` is not implemented for `Q` @@ -292,7 +292,7 @@ LL | fn example<Q: T1>(q: Q) { | ++++ error[E0277]: the trait bound `Q: T3` is not satisfied - --> $DIR/blame-trait-error-spans-on-exprs.rs:117:27 + --> $DIR/blame-trait-error-spans-on-exprs.rs:119:27 | LL | want(Wrapper { value: AliasBurrito { spiciness: q, filling: q } }); | ---- ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ the trait `T3` is not implemented for `Q` @@ -324,7 +324,7 @@ LL | fn example<Q: T3>(q: Q) { | ++++ error[E0277]: the trait bound `Q: T1` is not satisfied - --> $DIR/blame-trait-error-spans-on-exprs.rs:120:35 + --> $DIR/blame-trait-error-spans-on-exprs.rs:122:35 | LL | want(Two { a: Two { a: (), b: q }, b: () }); | ---- ^ the trait `T1` is not implemented for `Q` @@ -349,7 +349,7 @@ LL | fn example<Q: T1>(q: Q) { | ++++ error[E0277]: the trait bound `Q: T1` is not satisfied - --> $DIR/blame-trait-error-spans-on-exprs.rs:126:59 + --> $DIR/blame-trait-error-spans-on-exprs.rs:128:59 | LL | want( | ---- required by a bound introduced by this call @@ -375,6 +375,38 @@ help: consider restricting type parameter `Q` LL | fn example<Q: T1>(q: Q) { | ++++ -error: aborting due to 13 previous errors +error[E0277]: the trait bound `Q: T3` is not satisfied + --> $DIR/blame-trait-error-spans-on-exprs.rs:133:44 + | +LL | want(&Burrito { spicy: false, filling: q }); + | ---- ^ the trait `T3` is not implemented for `Q` + | | + | required by a bound introduced by this call + | +note: required for `Burrito<Q>` to implement `T2` + --> $DIR/blame-trait-error-spans-on-exprs.rs:22:13 + | +LL | impl<A: T3> T2 for Burrito<A> {} + | -- ^^ ^^^^^^^^^^ + | | + | unsatisfied trait bound introduced here +note: required for `&Burrito<Q>` to implement `T1` + --> $DIR/blame-trait-error-spans-on-exprs.rs:74:17 + | +LL | impl<'a, T: T2> T1 for &'a T {} + | -- ^^ ^^^^^ + | | + | unsatisfied trait bound introduced here +note: required by a bound in `want` + --> $DIR/blame-trait-error-spans-on-exprs.rs:53:12 + | +LL | fn want<V: T1>(_x: V) {} + | ^^ required by this bound in `want` +help: consider restricting type parameter `Q` + | +LL | fn example<Q: T3>(q: Q) { + | ++++ + +error: aborting due to 14 previous errors For more information about this error, try `rustc --explain E0277`. diff --git a/tests/ui/lint/unaligned_references.rs b/tests/ui/lint/unaligned_references.rs index 04b66885e85..0c9c79c08b2 100644 --- a/tests/ui/lint/unaligned_references.rs +++ b/tests/ui/lint/unaligned_references.rs @@ -13,6 +13,20 @@ pub struct Packed2 { z: u8, } +trait Foo { + fn evil(&self); +} + +// Test for #108122 +#[automatically_derived] +impl Foo for Packed2 { + fn evil(&self) { + unsafe { + &self.x; //~ ERROR reference to packed field + } + } +} + fn main() { unsafe { let good = Good { data: 0, ptr: &0, data2: [0, 0], aligned: [0; 32] }; @@ -37,6 +51,7 @@ fn main() { let _ = &packed2.x; //~ ERROR reference to packed field let _ = &packed2.y; // ok, has align 2 in packed(2) struct let _ = &packed2.z; // ok, has align 1 + packed2.evil(); } unsafe { @@ -71,22 +86,10 @@ fn main() { #[repr(packed)] struct Misalign<T>(u8, T); - let m1 = Misalign( - 0, - Wrapper { - a: U16(10), - b: HasDrop, - }, - ); + let m1 = Misalign(0, Wrapper { a: U16(10), b: HasDrop }); let _ref = &m1.1.a; //~ ERROR reference to packed field - let m2 = Misalign( - 0, - Wrapper2 { - a: U16(10), - b: HasDrop, - }, - ); + let m2 = Misalign(0, Wrapper2 { a: U16(10), b: HasDrop }); let _ref = &m2.1.a; //~ ERROR reference to packed field } } diff --git a/tests/ui/lint/unaligned_references.stderr b/tests/ui/lint/unaligned_references.stderr index 07b59464bde..775dcac678e 100644 --- a/tests/ui/lint/unaligned_references.stderr +++ b/tests/ui/lint/unaligned_references.stderr @@ -1,5 +1,14 @@ error[E0793]: reference to packed field is unaligned - --> $DIR/unaligned_references.rs:20:17 + --> $DIR/unaligned_references.rs:25:13 + | +LL | &self.x; + | ^^^^^^^ + | + = note: fields of packed structs are not properly aligned, and creating a misaligned reference is undefined behavior (even if that reference is never dereferenced) + = help: copy the field contents to a local variable, or replace the reference with a raw pointer and use `read_unaligned`/`write_unaligned` (loads and stores via `*p` must be properly aligned even when using raw pointers) + +error[E0793]: reference to packed field is unaligned + --> $DIR/unaligned_references.rs:34:17 | LL | let _ = &good.ptr; | ^^^^^^^^^ @@ -8,7 +17,7 @@ LL | let _ = &good.ptr; = help: copy the field contents to a local variable, or replace the reference with a raw pointer and use `read_unaligned`/`write_unaligned` (loads and stores via `*p` must be properly aligned even when using raw pointers) error[E0793]: reference to packed field is unaligned - --> $DIR/unaligned_references.rs:21:17 + --> $DIR/unaligned_references.rs:35:17 | LL | let _ = &good.data; | ^^^^^^^^^^ @@ -17,7 +26,7 @@ LL | let _ = &good.data; = help: copy the field contents to a local variable, or replace the reference with a raw pointer and use `read_unaligned`/`write_unaligned` (loads and stores via `*p` must be properly aligned even when using raw pointers) error[E0793]: reference to packed field is unaligned - --> $DIR/unaligned_references.rs:23:17 + --> $DIR/unaligned_references.rs:37:17 | LL | let _ = &good.data as *const _; | ^^^^^^^^^^ @@ -26,7 +35,7 @@ LL | let _ = &good.data as *const _; = help: copy the field contents to a local variable, or replace the reference with a raw pointer and use `read_unaligned`/`write_unaligned` (loads and stores via `*p` must be properly aligned even when using raw pointers) error[E0793]: reference to packed field is unaligned - --> $DIR/unaligned_references.rs:24:27 + --> $DIR/unaligned_references.rs:38:27 | LL | let _: *const _ = &good.data; | ^^^^^^^^^^ @@ -35,7 +44,7 @@ LL | let _: *const _ = &good.data; = help: copy the field contents to a local variable, or replace the reference with a raw pointer and use `read_unaligned`/`write_unaligned` (loads and stores via `*p` must be properly aligned even when using raw pointers) error[E0793]: reference to packed field is unaligned - --> $DIR/unaligned_references.rs:26:17 + --> $DIR/unaligned_references.rs:40:17 | LL | let _ = good.data.clone(); | ^^^^^^^^^^^^^^^^^ @@ -44,7 +53,7 @@ LL | let _ = good.data.clone(); = help: copy the field contents to a local variable, or replace the reference with a raw pointer and use `read_unaligned`/`write_unaligned` (loads and stores via `*p` must be properly aligned even when using raw pointers) error[E0793]: reference to packed field is unaligned - --> $DIR/unaligned_references.rs:28:17 + --> $DIR/unaligned_references.rs:42:17 | LL | let _ = &good.data2[0]; | ^^^^^^^^^^^^^^ @@ -53,7 +62,7 @@ LL | let _ = &good.data2[0]; = help: copy the field contents to a local variable, or replace the reference with a raw pointer and use `read_unaligned`/`write_unaligned` (loads and stores via `*p` must be properly aligned even when using raw pointers) error[E0793]: reference to packed field is unaligned - --> $DIR/unaligned_references.rs:37:17 + --> $DIR/unaligned_references.rs:51:17 | LL | let _ = &packed2.x; | ^^^^^^^^^^ @@ -62,7 +71,7 @@ LL | let _ = &packed2.x; = help: copy the field contents to a local variable, or replace the reference with a raw pointer and use `read_unaligned`/`write_unaligned` (loads and stores via `*p` must be properly aligned even when using raw pointers) error[E0793]: reference to packed field is unaligned - --> $DIR/unaligned_references.rs:81:20 + --> $DIR/unaligned_references.rs:90:20 | LL | let _ref = &m1.1.a; | ^^^^^^^ @@ -71,7 +80,7 @@ LL | let _ref = &m1.1.a; = help: copy the field contents to a local variable, or replace the reference with a raw pointer and use `read_unaligned`/`write_unaligned` (loads and stores via `*p` must be properly aligned even when using raw pointers) error[E0793]: reference to packed field is unaligned - --> $DIR/unaligned_references.rs:90:20 + --> $DIR/unaligned_references.rs:93:20 | LL | let _ref = &m2.1.a; | ^^^^^^^ @@ -79,6 +88,6 @@ LL | let _ref = &m2.1.a; = note: fields of packed structs are not properly aligned, and creating a misaligned reference is undefined behavior (even if that reference is never dereferenced) = help: copy the field contents to a local variable, or replace the reference with a raw pointer and use `read_unaligned`/`write_unaligned` (loads and stores via `*p` must be properly aligned even when using raw pointers) -error: aborting due to 9 previous errors +error: aborting due to 10 previous errors For more information about this error, try `rustc --explain E0793`. diff --git a/tests/ui/mir/field-projection-invariant.rs b/tests/ui/mir/field-projection-invariant.rs new file mode 100644 index 00000000000..b5d6add043c --- /dev/null +++ b/tests/ui/mir/field-projection-invariant.rs @@ -0,0 +1,24 @@ +// build-pass +struct Inv<'a>(&'a mut &'a ()); +enum Foo<T> { + Bar, + Var(T), +} +type Supertype = Foo<for<'a> fn(Inv<'a>, Inv<'a>)>; + +fn foo(x: Foo<for<'a, 'b> fn(Inv<'a>, Inv<'b>)>) { + match x { + Supertype::Bar => {} + Supertype::Var(x) => {} + } +} + +fn foo_nested(x: Foo<Foo<for<'a, 'b> fn(Inv<'a>, Inv<'b>)>>) { + match x { + Foo::Bar => {} + Foo::Var(Supertype::Bar) => {} + Foo::Var(Supertype::Var(x)) => {} + } +} + +fn main() {} diff --git a/tests/ui/mir/field-projection-mutating-context.rs b/tests/ui/mir/field-projection-mutating-context.rs new file mode 100644 index 00000000000..a1002c088dc --- /dev/null +++ b/tests/ui/mir/field-projection-mutating-context.rs @@ -0,0 +1,19 @@ +use std::sync::Mutex; + +static GLOBAL: Mutex<&'static str> = Mutex::new("global str"); + +struct Foo<T>(T); // `T` is covariant. + +fn foo() { + let mut x: Foo<for<'a> fn(&'a str)> = Foo(|_| ()); + let Foo(ref mut y): Foo<fn(&'static str)> = x; + //~^ ERROR mismatched types + *y = |s| *GLOBAL.lock().unwrap() = s; + let string = String::from("i am shortlived"); + (x.0)(&string); +} + +fn main() { + foo(); + println!("{}", GLOBAL.lock().unwrap()); +} diff --git a/tests/ui/mir/field-projection-mutating-context.stderr b/tests/ui/mir/field-projection-mutating-context.stderr new file mode 100644 index 00000000000..9b18b3427ad --- /dev/null +++ b/tests/ui/mir/field-projection-mutating-context.stderr @@ -0,0 +1,12 @@ +error[E0308]: mismatched types + --> $DIR/field-projection-mutating-context.rs:9:13 + | +LL | let Foo(ref mut y): Foo<fn(&'static str)> = x; + | ^^^^^^^^^ one type is more general than the other + | + = note: expected fn pointer `for<'a> fn(&'a str)` + found fn pointer `fn(&str)` + +error: aborting due to previous error + +For more information about this error, try `rustc --explain E0308`. diff --git a/tests/ui/mir/field-projection-mutating-context2.rs b/tests/ui/mir/field-projection-mutating-context2.rs new file mode 100644 index 00000000000..dd9c44a16d3 --- /dev/null +++ b/tests/ui/mir/field-projection-mutating-context2.rs @@ -0,0 +1,17 @@ +use std::sync::Mutex; + +static GLOBAL: Mutex<&'static str> = Mutex::new("global str"); + +struct Foo<T>(T); // `T` is covariant. + +fn foo<'a>(mut x: Foo<fn(&'a str)>, string: &'a str) { + let Foo(ref mut y): Foo<fn(&'static str)> = x; + //~^ ERROR lifetime may not live long enough + *y = |s| *GLOBAL.lock().unwrap() = s; + (x.0)(&string); +} + +fn main() { + foo(Foo(|_| ()), &String::from("i am shortlived")); + println!("{}", GLOBAL.lock().unwrap()); +} diff --git a/tests/ui/mir/field-projection-mutating-context2.stderr b/tests/ui/mir/field-projection-mutating-context2.stderr new file mode 100644 index 00000000000..a7b66fe10ce --- /dev/null +++ b/tests/ui/mir/field-projection-mutating-context2.stderr @@ -0,0 +1,10 @@ +error: lifetime may not live long enough + --> $DIR/field-projection-mutating-context2.rs:8:25 + | +LL | fn foo<'a>(mut x: Foo<fn(&'a str)>, string: &'a str) { + | -- lifetime `'a` defined here +LL | let Foo(ref mut y): Foo<fn(&'static str)> = x; + | ^^^^^^^^^^^^^^^^^^^^^ type annotation requires that `'a` must outlive `'static` + +error: aborting due to previous error + diff --git a/tests/ui/mir/field-ty-ascription-enums.rs b/tests/ui/mir/field-ty-ascription-enums.rs new file mode 100644 index 00000000000..179af617090 --- /dev/null +++ b/tests/ui/mir/field-ty-ascription-enums.rs @@ -0,0 +1,15 @@ +// build-pass + +enum Foo<T> { + Var(T), +} // `T` is covariant. + +fn foo<'b>(x: Foo<for<'a> fn(&'a ())>) { + let Foo::Var(x): Foo<fn(&'b ())> = x; +} + +fn foo_nested<'b>(x: Foo<Foo<for<'a> fn(&'a ())>>) { + let Foo::Var(Foo::Var(x)): Foo<Foo<fn(&'b ())>> = x; +} + +fn main() {} diff --git a/tests/ui/mir/field-ty-ascription.rs b/tests/ui/mir/field-ty-ascription.rs new file mode 100644 index 00000000000..178c7916bc5 --- /dev/null +++ b/tests/ui/mir/field-ty-ascription.rs @@ -0,0 +1,37 @@ +// build-pass + +struct Foo<T>(T); // `T` is covariant. + +struct Bar<T> { + x: T, +} // `T` is covariant. + +fn bar<'b>(x: Bar<for<'a> fn(&'a ())>) { + let Bar { x }: Bar<fn(&'b ())> = x; +} + +fn bar_nested<'b>(x: Bar<Bar<for<'a> fn(&'a ())>>) { + let Bar { x: Bar { x } }: Bar<Bar<fn(&'b ())>> = x; +} + +fn bar_foo_nested<'b>(x: Bar<Foo<for<'a> fn(&'a ())>>) { + let Bar { x: Foo ( x ) }: Bar<Foo<fn(&'b ())>> = x; +} + +fn foo<'b>(x: Foo<for<'a> fn(&'a ())>) { + let Foo(y): Foo<fn(&'b ())> = x; +} + +fn foo_nested<'b>(x: Foo<Foo<for<'a> fn(&'a ())>>) { + let Foo(Foo(y)): Foo<Foo<fn(&'b ())>> = x; +} + +fn tuple<'b>(x: (u32, for<'a> fn(&'a ()))) { + let (_, y): (u32, fn(&'b ())) = x; +} + +fn tuple_nested<'b>(x: (u32, (u32, for<'a> fn(&'a ())))) { + let (_, (_, y)): (u32, (u32, fn(&'b ()))) = x; +} + +fn main() {} diff --git a/tests/ui/panics/default-backtrace-ice.stderr b/tests/ui/panics/default-backtrace-ice.stderr index 7bf08bee922..4bd4780e25f 100644 --- a/tests/ui/panics/default-backtrace-ice.stderr +++ b/tests/ui/panics/default-backtrace-ice.stderr @@ -13,4 +13,5 @@ error: the compiler unexpectedly panicked. this is a bug. query stack during panic: +#0 [resolver_for_lowering] getting the resolver for lowering end of query stack diff --git a/tests/ui/recursion_limit/issue_21102.rs b/tests/ui/recursion_limit/issue_21102.rs new file mode 100644 index 00000000000..e1fee46313d --- /dev/null +++ b/tests/ui/recursion_limit/issue_21102.rs @@ -0,0 +1,9 @@ +#![recursion_limit="4"] +#![invalid_attribute] +#![invalid_attribute] +#![invalid_attribute] +#![invalid_attribute] +#![invalid_attribute] +//~^ERROR recursion limit reached while expanding + +fn main() {} diff --git a/tests/ui/recursion_limit/issue_21102.stderr b/tests/ui/recursion_limit/issue_21102.stderr new file mode 100644 index 00000000000..1bd722c492b --- /dev/null +++ b/tests/ui/recursion_limit/issue_21102.stderr @@ -0,0 +1,10 @@ +error: recursion limit reached while expanding `#[invalid_attribute]` + --> $DIR/issue_21102.rs:6:1 + | +LL | #![invalid_attribute] + | ^^^^^^^^^^^^^^^^^^^^^ + | + = help: consider increasing the recursion limit by adding a `#![recursion_limit = "8"]` attribute to your crate (`issue_21102`) + +error: aborting due to previous error + diff --git a/tests/ui/traits/new-solver/builtin-fn-must-return-sized.rs b/tests/ui/traits/new-solver/builtin-fn-must-return-sized.rs new file mode 100644 index 00000000000..ba473653ecf --- /dev/null +++ b/tests/ui/traits/new-solver/builtin-fn-must-return-sized.rs @@ -0,0 +1,17 @@ +// compile-flags: -Ztrait-solver=next + +#![feature(fn_traits)] +#![feature(unboxed_closures)] +#![feature(tuple_trait)] + +use std::ops::Fn; +use std::marker::Tuple; + +fn foo<F: Fn<T>, T: Tuple>(f: Option<F>, t: T) { + let y = (f.unwrap()).call(t); +} + +fn main() { + foo::<fn() -> str, _>(None, ()); + //~^ expected a `Fn<_>` closure, found `fn() -> str` +} diff --git a/tests/ui/traits/new-solver/builtin-fn-must-return-sized.stderr b/tests/ui/traits/new-solver/builtin-fn-must-return-sized.stderr new file mode 100644 index 00000000000..f7551739b13 --- /dev/null +++ b/tests/ui/traits/new-solver/builtin-fn-must-return-sized.stderr @@ -0,0 +1,18 @@ +error[E0277]: expected a `Fn<_>` closure, found `fn() -> str` + --> $DIR/builtin-fn-must-return-sized.rs:15:27 + | +LL | foo::<fn() -> str, _>(None, ()); + | --------------------- ^^^^ expected an `Fn<_>` closure, found `fn() -> str` + | | + | required by a bound introduced by this call + | + = help: the trait `Fn<_>` is not implemented for `fn() -> str` +note: required by a bound in `foo` + --> $DIR/builtin-fn-must-return-sized.rs:10:11 + | +LL | fn foo<F: Fn<T>, T: Tuple>(f: Option<F>, t: T) { + | ^^^^^ required by this bound in `foo` + +error: aborting due to previous error + +For more information about this error, try `rustc --explain E0277`. diff --git a/tests/ui/traits/non_lifetime_binders/bad-sized-cond.rs b/tests/ui/traits/non_lifetime_binders/bad-sized-cond.rs new file mode 100644 index 00000000000..dfc800c8e7e --- /dev/null +++ b/tests/ui/traits/non_lifetime_binders/bad-sized-cond.rs @@ -0,0 +1,23 @@ +#![feature(non_lifetime_binders)] +//~^ WARN is incomplete and may not be safe + +pub fn foo() +where + for<V> V: Sized, +{ +} + +pub fn bar() +where + for<V> V: IntoIterator, +{ +} + +fn main() { + foo(); + //~^ ERROR the size for values of type `V` cannot be known at compilation time + + bar(); + //~^ ERROR the size for values of type `V` cannot be known at compilation time + //~| ERROR `V` is not an iterator +} diff --git a/tests/ui/traits/non_lifetime_binders/bad-sized-cond.stderr b/tests/ui/traits/non_lifetime_binders/bad-sized-cond.stderr new file mode 100644 index 00000000000..6480e490e8b --- /dev/null +++ b/tests/ui/traits/non_lifetime_binders/bad-sized-cond.stderr @@ -0,0 +1,62 @@ +warning: the feature `non_lifetime_binders` is incomplete and may not be safe to use and/or cause compiler crashes + --> $DIR/bad-sized-cond.rs:1:12 + | +LL | #![feature(non_lifetime_binders)] + | ^^^^^^^^^^^^^^^^^^^^ + | + = note: see issue #108185 <https://github.com/rust-lang/rust/issues/108185> for more information + = note: `#[warn(incomplete_features)]` on by default + +error[E0277]: the size for values of type `V` cannot be known at compilation time + --> $DIR/bad-sized-cond.rs:17:5 + | +LL | foo(); + | ^^^ doesn't have a size known at compile-time + | + = help: the trait `Sized` is not implemented for `V` +note: required by a bound in `foo` + --> $DIR/bad-sized-cond.rs:6:15 + | +LL | pub fn foo() + | --- required by a bound in this +LL | where +LL | for<V> V: Sized, + | ^^^^^ required by this bound in `foo` + +error[E0277]: the size for values of type `V` cannot be known at compilation time + --> $DIR/bad-sized-cond.rs:20:5 + | +LL | bar(); + | ^^^ doesn't have a size known at compile-time + | + = help: the trait `Sized` is not implemented for `V` + = note: required for `V` to implement `IntoIterator` +note: required by a bound in `bar` + --> $DIR/bad-sized-cond.rs:12:15 + | +LL | pub fn bar() + | --- required by a bound in this +LL | where +LL | for<V> V: IntoIterator, + | ^^^^^^^^^^^^ required by this bound in `bar` + +error[E0277]: `V` is not an iterator + --> $DIR/bad-sized-cond.rs:20:5 + | +LL | bar(); + | ^^^ `V` is not an iterator + | + = help: the trait `Iterator` is not implemented for `V` + = note: required for `V` to implement `IntoIterator` +note: required by a bound in `bar` + --> $DIR/bad-sized-cond.rs:12:15 + | +LL | pub fn bar() + | --- required by a bound in this +LL | where +LL | for<V> V: IntoIterator, + | ^^^^^^^^^^^^ required by this bound in `bar` + +error: aborting due to 3 previous errors; 1 warning emitted + +For more information about this error, try `rustc --explain E0277`. diff --git a/tests/ui/traits/suggest-deferences/issue-39029.stderr b/tests/ui/traits/suggest-deferences/issue-39029.stderr index 49e20c6a76a..49105de3d69 100644 --- a/tests/ui/traits/suggest-deferences/issue-39029.stderr +++ b/tests/ui/traits/suggest-deferences/issue-39029.stderr @@ -1,8 +1,8 @@ error[E0277]: the trait bound `NoToSocketAddrs: ToSocketAddrs` is not satisfied - --> $DIR/issue-39029.rs:16:37 + --> $DIR/issue-39029.rs:16:38 | LL | let _errors = TcpListener::bind(&bad); - | ----------------- ^^^^ the trait `ToSocketAddrs` is not implemented for `NoToSocketAddrs` + | ----------------- ^^^ the trait `ToSocketAddrs` is not implemented for `NoToSocketAddrs` | | | required by a bound introduced by this call | |
