Skip to content

Commit 3fff727

Browse files
committed
Use more detailed spans in dyn compat errors within bodies
1 parent d76fe15 commit 3fff727

File tree

45 files changed

+205
-206
lines changed

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

45 files changed

+205
-206
lines changed

compiler/rustc_hir_analysis/src/collect.rs

Lines changed: 6 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -31,7 +31,7 @@ use rustc_hir::def_id::{DefId, LocalDefId};
3131
use rustc_hir::intravisit::{self, InferKind, Visitor, VisitorExt, walk_generics};
3232
use rustc_hir::{self as hir, GenericParamKind, HirId, Node, PreciseCapturingArgKind};
3333
use rustc_infer::infer::{InferCtxt, TyCtxtInferExt};
34-
use rustc_infer::traits::ObligationCause;
34+
use rustc_infer::traits::{DynCompatibilityViolation, ObligationCause};
3535
use rustc_middle::hir::nested_filter;
3636
use rustc_middle::query::Providers;
3737
use rustc_middle::ty::util::{Discr, IntTypeExt};
@@ -40,7 +40,7 @@ use rustc_middle::{bug, span_bug};
4040
use rustc_span::{DUMMY_SP, Ident, Span, Symbol, kw, sym};
4141
use rustc_trait_selection::error_reporting::traits::suggestions::NextTypeParamName;
4242
use rustc_trait_selection::infer::InferCtxtExt;
43-
use rustc_trait_selection::traits::ObligationCtxt;
43+
use rustc_trait_selection::traits::{ObligationCtxt, hir_ty_lowering_dyn_compatibility_violations};
4444
use tracing::{debug, instrument};
4545

4646
use crate::errors;
@@ -625,6 +625,10 @@ impl<'tcx> HirTyLowerer<'tcx> for ItemCtxt<'tcx> {
625625

626626
(input_tys, output_ty)
627627
}
628+
629+
fn dyn_compatibility_violations(&self, trait_def_id: DefId) -> Vec<DynCompatibilityViolation> {
630+
hir_ty_lowering_dyn_compatibility_violations(self.tcx, trait_def_id)
631+
}
628632
}
629633

630634
/// Synthesize a new lifetime name that doesn't clash with any of the lifetimes already present.

compiler/rustc_hir_analysis/src/hir_ty_lowering/dyn_compatibility.rs

Lines changed: 2 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -11,7 +11,7 @@ use rustc_middle::ty::{
1111
};
1212
use rustc_span::{ErrorGuaranteed, Span};
1313
use rustc_trait_selection::error_reporting::traits::report_dyn_incompatibility;
14-
use rustc_trait_selection::traits::{self, hir_ty_lowering_dyn_compatibility_violations};
14+
use rustc_trait_selection::traits;
1515
use smallvec::{SmallVec, smallvec};
1616
use tracing::{debug, instrument};
1717

@@ -97,8 +97,7 @@ impl<'tcx> dyn HirTyLowerer<'tcx> + '_ {
9797
// to avoid ICEs.
9898
for (clause, span) in user_written_bounds {
9999
if let Some(trait_pred) = clause.as_trait_clause() {
100-
let violations =
101-
hir_ty_lowering_dyn_compatibility_violations(tcx, trait_pred.def_id());
100+
let violations = self.dyn_compatibility_violations(trait_pred.def_id());
102101
if !violations.is_empty() {
103102
let reported = report_dyn_incompatibility(
104103
tcx,

compiler/rustc_hir_analysis/src/hir_ty_lowering/mod.rs

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -33,7 +33,7 @@ use rustc_hir::def::{CtorKind, CtorOf, DefKind, Res};
3333
use rustc_hir::def_id::{DefId, LocalDefId};
3434
use rustc_hir::{self as hir, AnonConst, GenericArg, GenericArgs, HirId};
3535
use rustc_infer::infer::{InferCtxt, TyCtxtInferExt};
36-
use rustc_infer::traits::ObligationCause;
36+
use rustc_infer::traits::{DynCompatibilityViolation, ObligationCause};
3737
use rustc_middle::middle::stability::AllowUnstable;
3838
use rustc_middle::mir::interpret::LitToConstInput;
3939
use rustc_middle::ty::print::PrintPolyTraitRefExt as _;
@@ -200,6 +200,10 @@ pub trait HirTyLowerer<'tcx> {
200200
{
201201
self
202202
}
203+
204+
/// Performs minimalistic dyn compat checks outside of bodies, but full within bodies.
205+
/// Outside of bodies we could end up in cycles, so we delay most checks to later phases.
206+
fn dyn_compatibility_violations(&self, trait_def_id: DefId) -> Vec<DynCompatibilityViolation>;
203207
}
204208

205209
/// The "qualified self" of an associated item path.

compiler/rustc_hir_typeck/src/fn_ctxt/mod.rs

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -14,7 +14,7 @@ use rustc_hir::def_id::{DefId, LocalDefId};
1414
use rustc_hir::{self as hir, HirId, ItemLocalMap};
1515
use rustc_hir_analysis::hir_ty_lowering::{HirTyLowerer, RegionInferReason};
1616
use rustc_infer::infer;
17-
use rustc_infer::traits::Obligation;
17+
use rustc_infer::traits::{DynCompatibilityViolation, Obligation};
1818
use rustc_middle::ty::{self, Const, Ty, TyCtxt, TypeVisitableExt};
1919
use rustc_session::Session;
2020
use rustc_span::{self, DUMMY_SP, ErrorGuaranteed, Ident, Span, sym};
@@ -388,6 +388,10 @@ impl<'tcx> HirTyLowerer<'tcx> for FnCtxt<'_, 'tcx> {
388388
};
389389
(input_tys, output_ty)
390390
}
391+
392+
fn dyn_compatibility_violations(&self, trait_def_id: DefId) -> Vec<DynCompatibilityViolation> {
393+
self.tcx.dyn_compatibility_violations(trait_def_id).to_vec()
394+
}
391395
}
392396

393397
/// The `ty` representation of a user-provided type. Depending on the use-site

tests/ui/async-await/dyn/mut-is-pointer-like.stderr

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -8,10 +8,10 @@ LL | #![feature(async_fn_in_dyn_trait)]
88
= note: `#[warn(incomplete_features)]` on by default
99

1010
error[E0038]: the trait `AsyncTrait` is not dyn compatible
11-
--> $DIR/mut-is-pointer-like.rs:35:16
11+
--> $DIR/mut-is-pointer-like.rs:35:29
1212
|
1313
LL | let x: Pin<&mut dyn AsyncTrait<Output = ()>> = f;
14-
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ `AsyncTrait` is not dyn compatible
14+
| ^^^^^^^^^^^^^^^^^^^^^^^ `AsyncTrait` is not dyn compatible
1515
|
1616
note: for a trait to be dyn compatible it needs to allow building a vtable
1717
for more information, visit <https://doc.rust-lang.org/reference/items/traits.html#dyn-compatibility>

tests/ui/async-await/dyn/works.stderr

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -8,10 +8,10 @@ LL | #![feature(async_fn_in_dyn_trait)]
88
= note: `#[warn(incomplete_features)]` on by default
99

1010
error[E0038]: the trait `AsyncTrait` is not dyn compatible
11-
--> $DIR/works.rs:27:16
11+
--> $DIR/works.rs:27:21
1212
|
1313
LL | let x: &dyn AsyncTrait = &"hello, world!";
14-
| ^^^^^^^^^^^^^^^ `AsyncTrait` is not dyn compatible
14+
| ^^^^^^^^^^ `AsyncTrait` is not dyn compatible
1515
|
1616
note: for a trait to be dyn compatible it needs to allow building a vtable
1717
for more information, visit <https://doc.rust-lang.org/reference/items/traits.html#dyn-compatibility>

tests/ui/async-await/dyn/wrong-size.stderr

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -8,10 +8,10 @@ LL | #![feature(async_fn_in_dyn_trait)]
88
= note: `#[warn(incomplete_features)]` on by default
99

1010
error[E0038]: the trait `AsyncTrait` is not dyn compatible
11-
--> $DIR/wrong-size.rs:21:12
11+
--> $DIR/wrong-size.rs:21:17
1212
|
1313
LL | let x: &dyn AsyncTrait = &"hello, world!";
14-
| ^^^^^^^^^^^^^^^ `AsyncTrait` is not dyn compatible
14+
| ^^^^^^^^^^ `AsyncTrait` is not dyn compatible
1515
|
1616
note: for a trait to be dyn compatible it needs to allow building a vtable
1717
for more information, visit <https://doc.rust-lang.org/reference/items/traits.html#dyn-compatibility>

tests/ui/async-await/in-trait/dyn-compatibility.stderr

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,8 @@
11
error[E0038]: the trait `Foo` is not dyn compatible
2-
--> $DIR/dyn-compatibility.rs:9:12
2+
--> $DIR/dyn-compatibility.rs:9:17
33
|
44
LL | let x: &dyn Foo = todo!();
5-
| ^^^^^^^^ `Foo` is not dyn compatible
5+
| ^^^ `Foo` is not dyn compatible
66
|
77
note: for a trait to be dyn compatible it needs to allow building a vtable
88
for more information, visit <https://doc.rust-lang.org/reference/items/traits.html#dyn-compatibility>

tests/ui/did_you_mean/trait-object-reference-without-parens-suggestion.rs

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4,4 +4,5 @@ fn main() {
44
let _: &Copy + 'static; //~ ERROR expected a path
55
//~^ ERROR is not dyn compatible
66
let _: &'static Copy + 'static; //~ ERROR expected a path
7+
//~^ ERROR is not dyn compatible
78
}

tests/ui/did_you_mean/trait-object-reference-without-parens-suggestion.stderr

Lines changed: 13 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -21,16 +21,26 @@ LL | let _: &'static (Copy + 'static);
2121
| + +
2222

2323
error[E0038]: the trait `Copy` is not dyn compatible
24-
--> $DIR/trait-object-reference-without-parens-suggestion.rs:4:12
24+
--> $DIR/trait-object-reference-without-parens-suggestion.rs:4:13
2525
|
2626
LL | let _: &Copy + 'static;
27-
| ^^^^^ `Copy` is not dyn compatible
27+
| ^^^^ `Copy` is not dyn compatible
28+
|
29+
= note: the trait is not dyn compatible because it requires `Self: Sized`
30+
= note: for a trait to be dyn compatible it needs to allow building a vtable
31+
for more information, visit <https://doc.rust-lang.org/reference/items/traits.html#dyn-compatibility>
32+
33+
error[E0038]: the trait `Copy` is not dyn compatible
34+
--> $DIR/trait-object-reference-without-parens-suggestion.rs:6:21
35+
|
36+
LL | let _: &'static Copy + 'static;
37+
| ^^^^ `Copy` is not dyn compatible
2838
|
2939
= note: the trait is not dyn compatible because it requires `Self: Sized`
3040
= note: for a trait to be dyn compatible it needs to allow building a vtable
3141
for more information, visit <https://doc.rust-lang.org/reference/items/traits.html#dyn-compatibility>
3242

33-
error: aborting due to 3 previous errors
43+
error: aborting due to 4 previous errors
3444

3545
Some errors have detailed explanations: E0038, E0178.
3646
For more information about an error, try `rustc --explain E0038`.

tests/ui/dyn-compatibility/almost-supertrait-associated-type.stderr

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -16,10 +16,10 @@ LL | fn transmute(&self, t: T) -> <Self as Super<NotActuallySuper>>::Assoc;
1616
= help: consider moving `transmute` to another trait
1717

1818
error[E0038]: the trait `Foo` is not dyn compatible
19-
--> $DIR/almost-supertrait-associated-type.rs:7:27
19+
--> $DIR/almost-supertrait-associated-type.rs:7:32
2020
|
2121
LL | (&PhantomData::<T> as &dyn Foo<T, U>).transmute(t)
22-
| ^^^^^^^^^^^^^^ `Foo` is not dyn compatible
22+
| ^^^^^^^^^ `Foo` is not dyn compatible
2323
|
2424
note: for a trait to be dyn compatible it needs to allow building a vtable
2525
for more information, visit <https://doc.rust-lang.org/reference/items/traits.html#dyn-compatibility>

tests/ui/dyn-compatibility/generics.stderr

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -31,10 +31,10 @@ LL | fn bar<T>(&self, t: T);
3131
= help: consider moving `bar` to another trait
3232

3333
error[E0038]: the trait `Bar` is not dyn compatible
34-
--> $DIR/generics.rs:22:10
34+
--> $DIR/generics.rs:22:15
3535
|
3636
LL | t as &dyn Bar
37-
| ^^^^^^^^ `Bar` is not dyn compatible
37+
| ^^^ `Bar` is not dyn compatible
3838
|
3939
note: for a trait to be dyn compatible it needs to allow building a vtable
4040
for more information, visit <https://doc.rust-lang.org/reference/items/traits.html#dyn-compatibility>

tests/ui/dyn-compatibility/mention-correct-dyn-incompatible-trait.stderr

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,8 @@
11
error[E0038]: the trait `Bar` is not dyn compatible
2-
--> $DIR/mention-correct-dyn-incompatible-trait.rs:19:15
2+
--> $DIR/mention-correct-dyn-incompatible-trait.rs:19:24
33
|
44
LL | let test: &mut dyn Bar = &mut thing;
5-
| ^^^^^^^^^^^^ `Bar` is not dyn compatible
5+
| ^^^ `Bar` is not dyn compatible
66
|
77
note: for a trait to be dyn compatible it needs to allow building a vtable
88
for more information, visit <https://doc.rust-lang.org/reference/items/traits.html#dyn-compatibility>

tests/ui/dyn-compatibility/no-static.stderr

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -23,10 +23,10 @@ LL | fn foo() where Self: Sized {}
2323
| +++++++++++++++++
2424

2525
error[E0038]: the trait `Foo` is not dyn compatible
26-
--> $DIR/no-static.rs:18:12
26+
--> $DIR/no-static.rs:18:20
2727
|
2828
LL | let b: Box<dyn Foo> = Box::new(Bar);
29-
| ^^^^^^^^^^^^ `Foo` is not dyn compatible
29+
| ^^^ `Foo` is not dyn compatible
3030
|
3131
note: for a trait to be dyn compatible it needs to allow building a vtable
3232
for more information, visit <https://doc.rust-lang.org/reference/items/traits.html#dyn-compatibility>

tests/ui/feature-gates/feature-gate-dispatch-from-dyn-missing-impl.stderr

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,11 +1,11 @@
11
error[E0038]: the trait `Trait` is not dyn compatible
2-
--> $DIR/feature-gate-dispatch-from-dyn-missing-impl.rs:32:25
2+
--> $DIR/feature-gate-dispatch-from-dyn-missing-impl.rs:32:33
33
|
44
LL | fn ptr(self: Ptr<Self>);
55
| --------- help: consider changing method `ptr`'s `self` parameter to be `&self`: `&Self`
66
...
77
LL | Ptr(Box::new(4)) as Ptr<dyn Trait>;
8-
| ^^^^^^^^^^^^^^ `Trait` is not dyn compatible
8+
| ^^^^^ `Trait` is not dyn compatible
99
|
1010
note: for a trait to be dyn compatible it needs to allow building a vtable
1111
for more information, visit <https://doc.rust-lang.org/reference/items/traits.html#dyn-compatibility>

tests/ui/generic-associated-types/issue-76535.stderr

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -15,10 +15,10 @@ LL | let sub: Box<dyn SuperTrait<SubType<'a> = SubStruct>> = Box::new(SuperS
1515
| ++++
1616

1717
error[E0038]: the trait `SuperTrait` is not dyn compatible
18-
--> $DIR/issue-76535.rs:34:14
18+
--> $DIR/issue-76535.rs:34:22
1919
|
2020
LL | let sub: Box<dyn SuperTrait<SubType = SubStruct>> = Box::new(SuperStruct::new(0));
21-
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ `SuperTrait` is not dyn compatible
21+
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ `SuperTrait` is not dyn compatible
2222
|
2323
note: for a trait to be dyn compatible it needs to allow building a vtable
2424
for more information, visit <https://doc.rust-lang.org/reference/items/traits.html#dyn-compatibility>

tests/ui/generic-associated-types/issue-78671.stderr

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -15,10 +15,10 @@ LL | Box::new(Family) as &dyn CollectionFamily<Member<T>=usize>
1515
| +++
1616

1717
error[E0038]: the trait `CollectionFamily` is not dyn compatible
18-
--> $DIR/issue-78671.rs:5:25
18+
--> $DIR/issue-78671.rs:5:30
1919
|
2020
LL | Box::new(Family) as &dyn CollectionFamily<Member=usize>
21-
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ `CollectionFamily` is not dyn compatible
21+
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ `CollectionFamily` is not dyn compatible
2222
|
2323
note: for a trait to be dyn compatible it needs to allow building a vtable
2424
for more information, visit <https://doc.rust-lang.org/reference/items/traits.html#dyn-compatibility>

tests/ui/generic-associated-types/issue-79422.stderr

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -15,10 +15,10 @@ LL | as Box<dyn MapLike<u8, u8, VRefCont<'a> = dyn RefCont<'_, u8>>>;
1515
| ++++
1616

1717
error[E0038]: the trait `MapLike` is not dyn compatible
18-
--> $DIR/issue-79422.rs:45:12
18+
--> $DIR/issue-79422.rs:45:20
1919
|
2020
LL | as Box<dyn MapLike<u8, u8, VRefCont = dyn RefCont<'_, u8>>>;
21-
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ `MapLike` is not dyn compatible
21+
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ `MapLike` is not dyn compatible
2222
|
2323
note: for a trait to be dyn compatible it needs to allow building a vtable
2424
for more information, visit <https://doc.rust-lang.org/reference/items/traits.html#dyn-compatibility>

tests/ui/higher-ranked/trait-bounds/span-bug-issue-121597.rs

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -15,5 +15,4 @@ fn main() {
1515
//~^ ERROR the trait `Foo` is not dyn compatible
1616

1717
needs_bar(x);
18-
//~^ ERROR mismatched types
1918
}
Lines changed: 4 additions & 21 deletions
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,8 @@
11
error[E0038]: the trait `Foo` is not dyn compatible
2-
--> $DIR/span-bug-issue-121597.rs:14:12
2+
--> $DIR/span-bug-issue-121597.rs:14:17
33
|
44
LL | let x: &dyn Foo = &();
5-
| ^^^^^^^^ `Foo` is not dyn compatible
5+
| ^^^ `Foo` is not dyn compatible
66
|
77
note: for a trait to be dyn compatible it needs to allow building a vtable
88
for more information, visit <https://doc.rust-lang.org/reference/items/traits.html#dyn-compatibility>
@@ -13,23 +13,6 @@ LL | trait Foo: for<T> Bar<T> {}
1313
| |
1414
| this trait is not dyn compatible...
1515

16-
error[E0308]: mismatched types
17-
--> $DIR/span-bug-issue-121597.rs:17:15
18-
|
19-
LL | needs_bar(x);
20-
| --------- ^ types differ in mutability
21-
| |
22-
| arguments to this function are incorrect
23-
|
24-
= note: expected raw pointer `*mut Type2`
25-
found reference `&dyn Foo`
26-
note: function defined here
27-
--> $DIR/span-bug-issue-121597.rs:11:4
28-
|
29-
LL | fn needs_bar(_: *mut Type2) {}
30-
| ^^^^^^^^^ -------------
31-
32-
error: aborting due to 2 previous errors
16+
error: aborting due to 1 previous error
3317

34-
Some errors have detailed explanations: E0038, E0308.
35-
For more information about an error, try `rustc --explain E0038`.
18+
For more information about this error, try `rustc --explain E0038`.

tests/ui/impl-trait/dyn-incompatible-trait-in-return-position-dyn-trait.rs

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -21,6 +21,8 @@ impl DynIncompatible for B {
2121

2222
fn car() -> dyn DynIncompatible { //~ ERROR the trait `DynIncompatible` is not dyn compatible
2323
//~^ ERROR return type cannot be a trait object without pointer indirection
24+
//~| ERROR the trait `DynIncompatible` is not dyn compatible
25+
//~| ERROR the trait `DynIncompatible` is not dyn compatible
2426
if true {
2527
return A;
2628
}

0 commit comments

Comments
 (0)