From 2566b4105d60a422229c645a784186b52e15fde6 Mon Sep 17 00:00:00 2001 From: Nathan Fenner Date: Mon, 27 Feb 2023 23:58:35 -0800 Subject: [PATCH 1/3] Point error span at Some constructor argument when trait resolution fails --- .../src/fn_ctxt/adjust_fulfillment_errors.rs | 14 +++- .../blame-trait-error.rs | 13 +++ .../blame-trait-error.stderr | 81 ++++++++++++++++++- .../blame-trait-error-spans-on-exprs.stderr | 4 +- 4 files changed, 103 insertions(+), 9 deletions(-) diff --git a/compiler/rustc_hir_typeck/src/fn_ctxt/adjust_fulfillment_errors.rs b/compiler/rustc_hir_typeck/src/fn_ctxt/adjust_fulfillment_errors.rs index d64492e503db0..3b72326be7c95 100644 --- a/compiler/rustc_hir_typeck/src/fn_ctxt/adjust_fulfillment_errors.rs +++ b/compiler/rustc_hir_typeck/src/fn_ctxt/adjust_fulfillment_errors.rs @@ -714,12 +714,18 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> { self.tcx.parent(expr_ctor_def_id) } hir::def::DefKind::Ctor(hir::def::CtorOf::Variant, hir::def::CtorKind::Fn) => { - // If this is a variant, its parent is the type definition. - if in_ty_adt.did() != self.tcx.parent(expr_ctor_def_id) { - // FIXME: Deal with type aliases? + if in_ty_adt.did() == self.tcx.parent(expr_ctor_def_id) { + // The constructor definition refers to the variant: + // For example, for a local type `MyEnum::MyVariant` triggers this case. + expr_ctor_def_id + } else if in_ty_adt.did() == self.tcx.parent(self.tcx.parent(expr_ctor_def_id)) + { + // The constructor definition refers to the "constructor" of the variant: + // For example, `Some(5)` triggers this case. + self.tcx.parent(expr_ctor_def_id) + } else { return Err(expr); } - expr_ctor_def_id } _ => { return Err(expr); diff --git a/tests/ui/errors/trait-bound-error-spans/blame-trait-error.rs b/tests/ui/errors/trait-bound-error-spans/blame-trait-error.rs index 5134c672f5f4e..5e939b71b13ea 100644 --- a/tests/ui/errors/trait-bound-error-spans/blame-trait-error.rs +++ b/tests/ui/errors/trait-bound-error-spans/blame-trait-error.rs @@ -18,11 +18,24 @@ struct Burrito { filling: F, } +impl T1 for Option {} + +impl<'a, A: T1> T1 for &'a A {} + fn want(_x: V) {} fn example(q: Q) { want(Wrapper { value: Burrito { filling: q } }); //~^ ERROR the trait bound `Q: T3` is not satisfied [E0277] + + want(Some(())); + //~^ ERROR `()` is not an iterator [E0277] + + want(Some(q)); + //~^ ERROR `Q` is not an iterator [E0277] + + want(&Some(q)); + //~^ ERROR `Q` is not an iterator [E0277] } fn main() {} diff --git a/tests/ui/errors/trait-bound-error-spans/blame-trait-error.stderr b/tests/ui/errors/trait-bound-error-spans/blame-trait-error.stderr index 27b002db1306a..e95c73f36dcee 100644 --- a/tests/ui/errors/trait-bound-error-spans/blame-trait-error.stderr +++ b/tests/ui/errors/trait-bound-error-spans/blame-trait-error.stderr @@ -1,5 +1,5 @@ error[E0277]: the trait bound `Q: T3` is not satisfied - --> $DIR/blame-trait-error.rs:24:46 + --> $DIR/blame-trait-error.rs:28:46 | LL | want(Wrapper { value: Burrito { filling: q } }); | ---- ^ the trait `T3` is not implemented for `Q` @@ -21,7 +21,7 @@ LL | impl T1 for Wrapper {} | | | unsatisfied trait bound introduced here note: required by a bound in `want` - --> $DIR/blame-trait-error.rs:21:12 + --> $DIR/blame-trait-error.rs:25:12 | LL | fn want(_x: V) {} | ^^ required by this bound in `want` @@ -30,6 +30,81 @@ help: consider restricting type parameter `Q` LL | fn example(q: Q) { | ++++ -error: aborting due to previous error +error[E0277]: `()` is not an iterator + --> $DIR/blame-trait-error.rs:31:15 + | +LL | want(Some(())); + | ---- ^^ `()` is not an iterator + | | + | required by a bound introduced by this call + | + = help: the trait `Iterator` is not implemented for `()` + = help: the trait `T1` is implemented for `Option` +note: required for `Option<()>` to implement `T1` + --> $DIR/blame-trait-error.rs:21:20 + | +LL | impl T1 for Option {} + | -------- ^^ ^^^^^^^^^^ + | | + | unsatisfied trait bound introduced here +note: required by a bound in `want` + --> $DIR/blame-trait-error.rs:25:12 + | +LL | fn want(_x: V) {} + | ^^ required by this bound in `want` + +error[E0277]: `Q` is not an iterator + --> $DIR/blame-trait-error.rs:34:15 + | +LL | want(Some(q)); + | ---- ^ `Q` is not an iterator + | | + | required by a bound introduced by this call + | +note: required for `Option` to implement `T1` + --> $DIR/blame-trait-error.rs:21:20 + | +LL | impl T1 for Option {} + | -------- ^^ ^^^^^^^^^^ + | | + | unsatisfied trait bound introduced here +note: required by a bound in `want` + --> $DIR/blame-trait-error.rs:25:12 + | +LL | fn want(_x: V) {} + | ^^ required by this bound in `want` +help: consider restricting type parameter `Q` + | +LL | fn example(q: Q) { + | +++++++++++++++++++++ + +error[E0277]: `Q` is not an iterator + --> $DIR/blame-trait-error.rs:37:16 + | +LL | want(&Some(q)); + | ---- ^ `Q` is not an iterator + | | + | required by a bound introduced by this call + | +note: required for `Option` to implement `T1` + --> $DIR/blame-trait-error.rs:21:20 + | +LL | impl T1 for Option {} + | -------- ^^ ^^^^^^^^^^ + | | + | unsatisfied trait bound introduced here + = note: 1 redundant requirement hidden + = note: required for `&Option` to implement `T1` +note: required by a bound in `want` + --> $DIR/blame-trait-error.rs:25:12 + | +LL | fn want(_x: V) {} + | ^^ required by this bound in `want` +help: consider restricting type parameter `Q` + | +LL | fn example(q: Q) { + | +++++++++++++++++++++ + +error: aborting due to 4 previous errors For more information about this error, try `rustc --explain E0277`. 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 6913771f2883e..b6a24e12bcc76 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 @@ -91,10 +91,10 @@ LL | fn example(q: Q) { | ++++ error[E0277]: the trait bound `Q: T3` is not satisfied - --> $DIR/blame-trait-error-spans-on-exprs.rs:93:27 + --> $DIR/blame-trait-error-spans-on-exprs.rs:93:53 | LL | want(Wrapper { value: TacoKinds::OneTaco(false, q) }); - | ---- ^^^^^^^^^^^^^^^^^^^^^^^^^^^^ the trait `T3` is not implemented for `Q` + | ---- ^ the trait `T3` is not implemented for `Q` | | | required by a bound introduced by this call | From f0212e65321cf4e6a05ac78d44ec242829ffa289 Mon Sep 17 00:00:00 2001 From: Nathan Fenner Date: Tue, 28 Feb 2023 14:58:14 -0800 Subject: [PATCH 2/3] Fix error spans for arguments to tuple enum constructors --- .../src/fn_ctxt/adjust_fulfillment_errors.rs | 19 +- .../blame-trait-error.rs | 61 ++++ .../blame-trait-error.stderr | 302 +++++++++++++++++- 3 files changed, 371 insertions(+), 11 deletions(-) diff --git a/compiler/rustc_hir_typeck/src/fn_ctxt/adjust_fulfillment_errors.rs b/compiler/rustc_hir_typeck/src/fn_ctxt/adjust_fulfillment_errors.rs index 3b72326be7c95..778e0bdaefd63 100644 --- a/compiler/rustc_hir_typeck/src/fn_ctxt/adjust_fulfillment_errors.rs +++ b/compiler/rustc_hir_typeck/src/fn_ctxt/adjust_fulfillment_errors.rs @@ -714,12 +714,19 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> { self.tcx.parent(expr_ctor_def_id) } hir::def::DefKind::Ctor(hir::def::CtorOf::Variant, hir::def::CtorKind::Fn) => { - if in_ty_adt.did() == self.tcx.parent(expr_ctor_def_id) { - // The constructor definition refers to the variant: - // For example, for a local type `MyEnum::MyVariant` triggers this case. - expr_ctor_def_id - } else if in_ty_adt.did() == self.tcx.parent(self.tcx.parent(expr_ctor_def_id)) - { + // For a typical enum like + // `enum Blah { Variant(T) }` + // we get the following resolutions: + // - expr_ctor_def_id ::: DefId(0:29 ~ source_file[b442]::Blah::Variant::{constructor#0}) + // - self.tcx.parent(expr_ctor_def_id) ::: DefId(0:28 ~ source_file[b442]::Blah::Variant) + // - self.tcx.parent(self.tcx.parent(expr_ctor_def_id)) ::: DefId(0:26 ~ source_file[b442]::Blah) + + // Therefore, we need to go up once to obtain the variant and up twice to obtain the type. + // Note that this pattern still holds even when we `use` a variant or `use` an enum type to rename it, or chain `use` expressions + // together; this resolution is handled automatically by `qpath_res`. + + // FIXME: Deal with type aliases? + if in_ty_adt.did() == self.tcx.parent(self.tcx.parent(expr_ctor_def_id)) { // The constructor definition refers to the "constructor" of the variant: // For example, `Some(5)` triggers this case. self.tcx.parent(expr_ctor_def_id) diff --git a/tests/ui/errors/trait-bound-error-spans/blame-trait-error.rs b/tests/ui/errors/trait-bound-error-spans/blame-trait-error.rs index 5e939b71b13ea..0fbd851431ea6 100644 --- a/tests/ui/errors/trait-bound-error-spans/blame-trait-error.rs +++ b/tests/ui/errors/trait-bound-error-spans/blame-trait-error.rs @@ -24,6 +24,31 @@ impl<'a, A: T1> T1 for &'a A {} fn want(_x: V) {} +enum ExampleTuple { + ExampleTupleVariant(T), +} +use ExampleDifferentTupleVariantName as ExampleYetAnotherTupleVariantName; +use ExampleTuple as ExampleOtherTuple; +use ExampleTuple::ExampleTupleVariant as ExampleDifferentTupleVariantName; +use ExampleTuple::*; + +impl T1 for ExampleTuple where A: T3 {} + +enum ExampleStruct { + ExampleStructVariant { field: T }, +} +use ExampleDifferentStructVariantName as ExampleYetAnotherStructVariantName; +use ExampleStruct as ExampleOtherStruct; +use ExampleStruct::ExampleStructVariant as ExampleDifferentStructVariantName; +use ExampleStruct::*; + +impl T1 for ExampleStruct where A: T3 {} + +struct ExampleActuallyTupleStruct(T, i32); +use ExampleActuallyTupleStruct as ExampleActuallyTupleStructOther; + +impl T1 for ExampleActuallyTupleStruct where A: T3 {} + fn example(q: Q) { want(Wrapper { value: Burrito { filling: q } }); //~^ ERROR the trait bound `Q: T3` is not satisfied [E0277] @@ -36,6 +61,42 @@ fn example(q: Q) { want(&Some(q)); //~^ ERROR `Q` is not an iterator [E0277] + + want(&ExampleTuple::ExampleTupleVariant(q)); + //~^ ERROR `Q: T3` is not satisfied [E0277] + + want(&ExampleTupleVariant(q)); + //~^ ERROR `Q: T3` is not satisfied [E0277] + + want(&ExampleOtherTuple::ExampleTupleVariant(q)); + //~^ ERROR `Q: T3` is not satisfied [E0277] + + want(&ExampleDifferentTupleVariantName(q)); + //~^ ERROR `Q: T3` is not satisfied [E0277] + + want(&ExampleYetAnotherTupleVariantName(q)); + //~^ ERROR `Q: T3` is not satisfied [E0277] + + want(&ExampleStruct::ExampleStructVariant { field: q }); + //~^ ERROR `Q: T3` is not satisfied [E0277] + + want(&ExampleStructVariant { field: q }); + //~^ ERROR `Q: T3` is not satisfied [E0277] + + want(&ExampleOtherStruct::ExampleStructVariant { field: q }); + //~^ ERROR `Q: T3` is not satisfied [E0277] + + want(&ExampleDifferentStructVariantName { field: q }); + //~^ ERROR `Q: T3` is not satisfied [E0277] + + want(&ExampleYetAnotherStructVariantName { field: q }); + //~^ ERROR `Q: T3` is not satisfied [E0277] + + want(&ExampleActuallyTupleStruct(q, 0)); + //~^ ERROR `Q: T3` is not satisfied [E0277] + + want(&ExampleActuallyTupleStructOther(q, 0)); + //~^ ERROR `Q: T3` is not satisfied [E0277] } fn main() {} diff --git a/tests/ui/errors/trait-bound-error-spans/blame-trait-error.stderr b/tests/ui/errors/trait-bound-error-spans/blame-trait-error.stderr index e95c73f36dcee..9228a047e8785 100644 --- a/tests/ui/errors/trait-bound-error-spans/blame-trait-error.stderr +++ b/tests/ui/errors/trait-bound-error-spans/blame-trait-error.stderr @@ -1,5 +1,5 @@ error[E0277]: the trait bound `Q: T3` is not satisfied - --> $DIR/blame-trait-error.rs:28:46 + --> $DIR/blame-trait-error.rs:53:46 | LL | want(Wrapper { value: Burrito { filling: q } }); | ---- ^ the trait `T3` is not implemented for `Q` @@ -31,7 +31,7 @@ LL | fn example(q: Q) { | ++++ error[E0277]: `()` is not an iterator - --> $DIR/blame-trait-error.rs:31:15 + --> $DIR/blame-trait-error.rs:56:15 | LL | want(Some(())); | ---- ^^ `()` is not an iterator @@ -54,7 +54,7 @@ LL | fn want(_x: V) {} | ^^ required by this bound in `want` error[E0277]: `Q` is not an iterator - --> $DIR/blame-trait-error.rs:34:15 + --> $DIR/blame-trait-error.rs:59:15 | LL | want(Some(q)); | ---- ^ `Q` is not an iterator @@ -79,7 +79,7 @@ LL | fn example(q: Q) { | +++++++++++++++++++++ error[E0277]: `Q` is not an iterator - --> $DIR/blame-trait-error.rs:37:16 + --> $DIR/blame-trait-error.rs:62:16 | LL | want(&Some(q)); | ---- ^ `Q` is not an iterator @@ -105,6 +105,298 @@ help: consider restricting type parameter `Q` LL | fn example(q: Q) { | +++++++++++++++++++++ -error: aborting due to 4 previous errors +error[E0277]: the trait bound `Q: T3` is not satisfied + --> $DIR/blame-trait-error.rs:65:45 + | +LL | want(&ExampleTuple::ExampleTupleVariant(q)); + | ---- ^ the trait `T3` is not implemented for `Q` + | | + | required by a bound introduced by this call + | +note: required for `ExampleTuple` to implement `T1` + --> $DIR/blame-trait-error.rs:35:9 + | +LL | impl T1 for ExampleTuple where A: T3 {} + | ^^ ^^^^^^^^^^^^^^^ -- unsatisfied trait bound introduced here + = note: 1 redundant requirement hidden + = note: required for `&ExampleTuple` to implement `T1` +note: required by a bound in `want` + --> $DIR/blame-trait-error.rs:25:12 + | +LL | fn want(_x: V) {} + | ^^ required by this bound in `want` +help: consider restricting type parameter `Q` + | +LL | fn example(q: Q) { + | ++++ + +error[E0277]: the trait bound `Q: T3` is not satisfied + --> $DIR/blame-trait-error.rs:68:31 + | +LL | want(&ExampleTupleVariant(q)); + | ---- ^ the trait `T3` is not implemented for `Q` + | | + | required by a bound introduced by this call + | +note: required for `ExampleTuple` to implement `T1` + --> $DIR/blame-trait-error.rs:35:9 + | +LL | impl T1 for ExampleTuple where A: T3 {} + | ^^ ^^^^^^^^^^^^^^^ -- unsatisfied trait bound introduced here + = note: 1 redundant requirement hidden + = note: required for `&ExampleTuple` to implement `T1` +note: required by a bound in `want` + --> $DIR/blame-trait-error.rs:25:12 + | +LL | fn want(_x: V) {} + | ^^ required by this bound in `want` +help: consider restricting type parameter `Q` + | +LL | fn example(q: Q) { + | ++++ + +error[E0277]: the trait bound `Q: T3` is not satisfied + --> $DIR/blame-trait-error.rs:71:50 + | +LL | want(&ExampleOtherTuple::ExampleTupleVariant(q)); + | ---- ^ the trait `T3` is not implemented for `Q` + | | + | required by a bound introduced by this call + | +note: required for `ExampleTuple` to implement `T1` + --> $DIR/blame-trait-error.rs:35:9 + | +LL | impl T1 for ExampleTuple where A: T3 {} + | ^^ ^^^^^^^^^^^^^^^ -- unsatisfied trait bound introduced here + = note: 1 redundant requirement hidden + = note: required for `&ExampleTuple` to implement `T1` +note: required by a bound in `want` + --> $DIR/blame-trait-error.rs:25:12 + | +LL | fn want(_x: V) {} + | ^^ required by this bound in `want` +help: consider restricting type parameter `Q` + | +LL | fn example(q: Q) { + | ++++ + +error[E0277]: the trait bound `Q: T3` is not satisfied + --> $DIR/blame-trait-error.rs:74:44 + | +LL | want(&ExampleDifferentTupleVariantName(q)); + | ---- ^ the trait `T3` is not implemented for `Q` + | | + | required by a bound introduced by this call + | +note: required for `ExampleTuple` to implement `T1` + --> $DIR/blame-trait-error.rs:35:9 + | +LL | impl T1 for ExampleTuple where A: T3 {} + | ^^ ^^^^^^^^^^^^^^^ -- unsatisfied trait bound introduced here + = note: 1 redundant requirement hidden + = note: required for `&ExampleTuple` to implement `T1` +note: required by a bound in `want` + --> $DIR/blame-trait-error.rs:25:12 + | +LL | fn want(_x: V) {} + | ^^ required by this bound in `want` +help: consider restricting type parameter `Q` + | +LL | fn example(q: Q) { + | ++++ + +error[E0277]: the trait bound `Q: T3` is not satisfied + --> $DIR/blame-trait-error.rs:77:45 + | +LL | want(&ExampleYetAnotherTupleVariantName(q)); + | ---- ^ the trait `T3` is not implemented for `Q` + | | + | required by a bound introduced by this call + | +note: required for `ExampleTuple` to implement `T1` + --> $DIR/blame-trait-error.rs:35:9 + | +LL | impl T1 for ExampleTuple where A: T3 {} + | ^^ ^^^^^^^^^^^^^^^ -- unsatisfied trait bound introduced here + = note: 1 redundant requirement hidden + = note: required for `&ExampleTuple` to implement `T1` +note: required by a bound in `want` + --> $DIR/blame-trait-error.rs:25:12 + | +LL | fn want(_x: V) {} + | ^^ required by this bound in `want` +help: consider restricting type parameter `Q` + | +LL | fn example(q: Q) { + | ++++ + +error[E0277]: the trait bound `Q: T3` is not satisfied + --> $DIR/blame-trait-error.rs:80:56 + | +LL | want(&ExampleStruct::ExampleStructVariant { field: q }); + | ---- required by a bound introduced by this call ^ the trait `T3` is not implemented for `Q` + | +note: required for `ExampleStruct` to implement `T1` + --> $DIR/blame-trait-error.rs:45:9 + | +LL | impl T1 for ExampleStruct where A: T3 {} + | ^^ ^^^^^^^^^^^^^^^^ -- unsatisfied trait bound introduced here + = note: 1 redundant requirement hidden + = note: required for `&ExampleStruct` to implement `T1` +note: required by a bound in `want` + --> $DIR/blame-trait-error.rs:25:12 + | +LL | fn want(_x: V) {} + | ^^ required by this bound in `want` +help: consider restricting type parameter `Q` + | +LL | fn example(q: Q) { + | ++++ + +error[E0277]: the trait bound `Q: T3` is not satisfied + --> $DIR/blame-trait-error.rs:83:41 + | +LL | want(&ExampleStructVariant { field: q }); + | ---- ^ the trait `T3` is not implemented for `Q` + | | + | required by a bound introduced by this call + | +note: required for `ExampleStruct` to implement `T1` + --> $DIR/blame-trait-error.rs:45:9 + | +LL | impl T1 for ExampleStruct where A: T3 {} + | ^^ ^^^^^^^^^^^^^^^^ -- unsatisfied trait bound introduced here + = note: 1 redundant requirement hidden + = note: required for `&ExampleStruct` to implement `T1` +note: required by a bound in `want` + --> $DIR/blame-trait-error.rs:25:12 + | +LL | fn want(_x: V) {} + | ^^ required by this bound in `want` +help: consider restricting type parameter `Q` + | +LL | fn example(q: Q) { + | ++++ + +error[E0277]: the trait bound `Q: T3` is not satisfied + --> $DIR/blame-trait-error.rs:86:61 + | +LL | want(&ExampleOtherStruct::ExampleStructVariant { field: q }); + | ---- required by a bound introduced by this call ^ the trait `T3` is not implemented for `Q` + | +note: required for `ExampleStruct` to implement `T1` + --> $DIR/blame-trait-error.rs:45:9 + | +LL | impl T1 for ExampleStruct where A: T3 {} + | ^^ ^^^^^^^^^^^^^^^^ -- unsatisfied trait bound introduced here + = note: 1 redundant requirement hidden + = note: required for `&ExampleStruct` to implement `T1` +note: required by a bound in `want` + --> $DIR/blame-trait-error.rs:25:12 + | +LL | fn want(_x: V) {} + | ^^ required by this bound in `want` +help: consider restricting type parameter `Q` + | +LL | fn example(q: Q) { + | ++++ + +error[E0277]: the trait bound `Q: T3` is not satisfied + --> $DIR/blame-trait-error.rs:89:54 + | +LL | want(&ExampleDifferentStructVariantName { field: q }); + | ---- required by a bound introduced by this call ^ the trait `T3` is not implemented for `Q` + | +note: required for `ExampleStruct` to implement `T1` + --> $DIR/blame-trait-error.rs:45:9 + | +LL | impl T1 for ExampleStruct where A: T3 {} + | ^^ ^^^^^^^^^^^^^^^^ -- unsatisfied trait bound introduced here + = note: 1 redundant requirement hidden + = note: required for `&ExampleStruct` to implement `T1` +note: required by a bound in `want` + --> $DIR/blame-trait-error.rs:25:12 + | +LL | fn want(_x: V) {} + | ^^ required by this bound in `want` +help: consider restricting type parameter `Q` + | +LL | fn example(q: Q) { + | ++++ + +error[E0277]: the trait bound `Q: T3` is not satisfied + --> $DIR/blame-trait-error.rs:92:55 + | +LL | want(&ExampleYetAnotherStructVariantName { field: q }); + | ---- required by a bound introduced by this call ^ the trait `T3` is not implemented for `Q` + | +note: required for `ExampleStruct` to implement `T1` + --> $DIR/blame-trait-error.rs:45:9 + | +LL | impl T1 for ExampleStruct where A: T3 {} + | ^^ ^^^^^^^^^^^^^^^^ -- unsatisfied trait bound introduced here + = note: 1 redundant requirement hidden + = note: required for `&ExampleStruct` to implement `T1` +note: required by a bound in `want` + --> $DIR/blame-trait-error.rs:25:12 + | +LL | fn want(_x: V) {} + | ^^ required by this bound in `want` +help: consider restricting type parameter `Q` + | +LL | fn example(q: Q) { + | ++++ + +error[E0277]: the trait bound `Q: T3` is not satisfied + --> $DIR/blame-trait-error.rs:95:38 + | +LL | want(&ExampleActuallyTupleStruct(q, 0)); + | ---- ^ the trait `T3` is not implemented for `Q` + | | + | required by a bound introduced by this call + | +note: required for `ExampleActuallyTupleStruct` to implement `T1` + --> $DIR/blame-trait-error.rs:50:9 + | +LL | impl T1 for ExampleActuallyTupleStruct where A: T3 {} + | ^^ ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ -- unsatisfied trait bound introduced here + = note: 1 redundant requirement hidden + = note: required for `&ExampleActuallyTupleStruct` to implement `T1` +note: required by a bound in `want` + --> $DIR/blame-trait-error.rs:25:12 + | +LL | fn want(_x: V) {} + | ^^ required by this bound in `want` +help: consider restricting type parameter `Q` + | +LL | fn example(q: Q) { + | ++++ + +error[E0277]: the trait bound `Q: T3` is not satisfied + --> $DIR/blame-trait-error.rs:98:43 + | +LL | want(&ExampleActuallyTupleStructOther(q, 0)); + | ---- ^ the trait `T3` is not implemented for `Q` + | | + | required by a bound introduced by this call + | +note: required for `ExampleActuallyTupleStruct` to implement `T1` + --> $DIR/blame-trait-error.rs:50:9 + | +LL | impl T1 for ExampleActuallyTupleStruct where A: T3 {} + | ^^ ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ -- unsatisfied trait bound introduced here + = note: 1 redundant requirement hidden + = note: required for `&ExampleActuallyTupleStruct` to implement `T1` +note: required by a bound in `want` + --> $DIR/blame-trait-error.rs:25:12 + | +LL | fn want(_x: V) {} + | ^^ required by this bound in `want` +help: consider restricting type parameter `Q` + | +LL | fn example(q: Q) { + | ++++ + +error: aborting due to 16 previous errors For more information about this error, try `rustc --explain E0277`. From be15f174fa13386a1b5f69fedbe0301c84d3df4d Mon Sep 17 00:00:00 2001 From: Nathan Fenner Date: Tue, 28 Feb 2023 14:59:32 -0800 Subject: [PATCH 3/3] restore unaddressed FIXME --- .../rustc_hir_typeck/src/fn_ctxt/adjust_fulfillment_errors.rs | 1 + 1 file changed, 1 insertion(+) diff --git a/compiler/rustc_hir_typeck/src/fn_ctxt/adjust_fulfillment_errors.rs b/compiler/rustc_hir_typeck/src/fn_ctxt/adjust_fulfillment_errors.rs index 778e0bdaefd63..b09886fe3a96a 100644 --- a/compiler/rustc_hir_typeck/src/fn_ctxt/adjust_fulfillment_errors.rs +++ b/compiler/rustc_hir_typeck/src/fn_ctxt/adjust_fulfillment_errors.rs @@ -731,6 +731,7 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> { // For example, `Some(5)` triggers this case. self.tcx.parent(expr_ctor_def_id) } else { + // FIXME: Deal with type aliases? return Err(expr); } }