mirror of
https://github.com/rust-lang/rust.git
synced 2024-11-21 22:34:05 +00:00
Rollup merge of #132935 - compiler-errors:arg-math, r=nnethercote
Make sure to ignore elided lifetimes when pointing at args for fulfillment errors See the comment I left in the code. --- If we have something like: ``` fn foo<'a, T: 'a + BoundThatIsNotSatisfied>() {} ``` And the user turbofishes just the type args: ``` foo::<()>(); ``` Then if we try pointing at `()` (i.e. the type argument for `T`), we don't actually consider the possibility that the lifetimes may have been left out of the turbofish. We try indexing incorrectly into the HIR args, and bail on the suggestion.
This commit is contained in:
commit
9a4a954359
@ -316,12 +316,24 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
|
||||
.tcx
|
||||
.generics_of(def_id)
|
||||
.own_args(ty::GenericArgs::identity_for_item(self.tcx, def_id));
|
||||
let Some((index, _)) =
|
||||
own_args.iter().enumerate().find(|(_, arg)| **arg == param_to_point_at)
|
||||
else {
|
||||
let Some(mut index) = own_args.iter().position(|arg| *arg == param_to_point_at) else {
|
||||
return false;
|
||||
};
|
||||
let Some(arg) = segment.args().args.get(index) else {
|
||||
// SUBTLE: We may or may not turbofish lifetime arguments, which will
|
||||
// otherwise be elided. if our "own args" starts with a lifetime, but
|
||||
// the args list does not, then we should chop off all of the lifetimes,
|
||||
// since they're all elided.
|
||||
let segment_args = segment.args().args;
|
||||
if matches!(own_args[0].unpack(), ty::GenericArgKind::Lifetime(_))
|
||||
&& segment_args.first().is_some_and(|arg| arg.is_ty_or_const())
|
||||
&& let Some(offset) = own_args.iter().position(|arg| {
|
||||
matches!(arg.unpack(), ty::GenericArgKind::Type(_) | ty::GenericArgKind::Const(_))
|
||||
})
|
||||
&& let Some(new_index) = index.checked_sub(offset)
|
||||
{
|
||||
index = new_index;
|
||||
}
|
||||
let Some(arg) = segment_args.get(index) else {
|
||||
return false;
|
||||
};
|
||||
error.obligation.cause.span = arg
|
||||
|
@ -15,10 +15,10 @@ LL | for<'b> <T as X<'b, T>>::U: Clone,
|
||||
| ^^^^^ required by this bound in `X`
|
||||
|
||||
error[E0277]: the trait bound `str: Clone` is not satisfied
|
||||
--> $DIR/hr-associated-type-bound-param-3.rs:18:5
|
||||
--> $DIR/hr-associated-type-bound-param-3.rs:18:18
|
||||
|
|
||||
LL | <(i32,) as X<(i32,)>>::f("abc");
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ the trait `Clone` is not implemented for `str`
|
||||
| ^^^^^^ the trait `Clone` is not implemented for `str`
|
||||
|
|
||||
= help: the trait `Clone` is implemented for `String`
|
||||
note: required by a bound in `X::f`
|
||||
|
@ -15,10 +15,10 @@ LL | for<'b> <(T,) as X<'b, T>>::U: Clone,
|
||||
| ^^^^^ required by this bound in `X`
|
||||
|
||||
error[E0277]: the trait bound `str: Clone` is not satisfied
|
||||
--> $DIR/hr-associated-type-bound-param-4.rs:18:5
|
||||
--> $DIR/hr-associated-type-bound-param-4.rs:18:18
|
||||
|
|
||||
LL | <(i32,) as X<i32>>::f("abc");
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^ the trait `Clone` is not implemented for `str`
|
||||
| ^^^ the trait `Clone` is not implemented for `str`
|
||||
|
|
||||
= help: the trait `Clone` is implemented for `String`
|
||||
note: required by a bound in `X::f`
|
||||
|
@ -31,10 +31,10 @@ LL | for<'b> <T::Next as X<'b, T::Next>>::U: Clone,
|
||||
| ^^^^^ required by this bound in `X`
|
||||
|
||||
error[E0277]: the trait bound `str: Clone` is not satisfied
|
||||
--> $DIR/hr-associated-type-bound-param-5.rs:36:5
|
||||
--> $DIR/hr-associated-type-bound-param-5.rs:36:15
|
||||
|
|
||||
LL | <i32 as X<Box<i32>>>::f("abc");
|
||||
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ the trait `Clone` is not implemented for `str`
|
||||
| ^^^^^^^^ the trait `Clone` is not implemented for `str`
|
||||
|
|
||||
= help: the trait `Clone` is implemented for `String`
|
||||
note: required by a bound in `X::f`
|
||||
|
@ -17,5 +17,6 @@ impl<S, T> X<'_, T> for (S,) {
|
||||
pub fn main() {
|
||||
<(i32,) as X<i32>>::f("abc");
|
||||
//~^ ERROR the trait bound `for<'b> i32: X<'b, i32>` is not satisfied
|
||||
//~| ERROR the trait bound `for<'b> i32: X<'b, i32>` is not satisfied
|
||||
//~| ERROR the trait bound `i32: X<'_, i32>` is not satisfied
|
||||
}
|
||||
|
@ -17,6 +17,22 @@ LL | <(i32,) as X<i32>>::f("abc");
|
||||
|
|
||||
= help: the trait `X<'_, T>` is implemented for `(S,)`
|
||||
|
||||
error[E0277]: the trait bound `for<'b> i32: X<'b, i32>` is not satisfied
|
||||
--> $DIR/hr-associated-type-bound-param-6.rs:18:18
|
||||
|
|
||||
LL | <(i32,) as X<i32>>::f("abc");
|
||||
| ^^^ the trait `for<'b> X<'b, i32>` is not implemented for `i32`
|
||||
|
|
||||
= help: the trait `X<'_, T>` is implemented for `(S,)`
|
||||
note: required by a bound in `X::f`
|
||||
--> $DIR/hr-associated-type-bound-param-6.rs:3:16
|
||||
|
|
||||
LL | for<'b> T: X<'b, T>,
|
||||
| ^^^^^^^^ required by this bound in `X::f`
|
||||
...
|
||||
LL | fn f(x: &<T as X<'_, T>>::U) {
|
||||
| - required by a bound in this associated function
|
||||
|
||||
error[E0277]: the trait bound `i32: X<'_, i32>` is not satisfied
|
||||
--> $DIR/hr-associated-type-bound-param-6.rs:18:27
|
||||
|
|
||||
@ -25,6 +41,6 @@ LL | <(i32,) as X<i32>>::f("abc");
|
||||
|
|
||||
= help: the trait `X<'_, T>` is implemented for `(S,)`
|
||||
|
||||
error: aborting due to 3 previous errors
|
||||
error: aborting due to 4 previous errors
|
||||
|
||||
For more information about this error, try `rustc --explain E0277`.
|
||||
|
@ -1,8 +1,8 @@
|
||||
error[E0277]: the trait bound `for<'a> T: Trait<'a, '_>` is not satisfied
|
||||
--> $DIR/candidate-from-env-universe-err-2.rs:15:5
|
||||
--> $DIR/candidate-from-env-universe-err-2.rs:15:15
|
||||
|
|
||||
LL | impl_hr::<T>();
|
||||
| ^^^^^^^^^^^^^^ the trait `for<'a> Trait<'a, '_>` is not implemented for `T`
|
||||
| ^ the trait `for<'a> Trait<'a, '_>` is not implemented for `T`
|
||||
|
|
||||
note: required by a bound in `impl_hr`
|
||||
--> $DIR/candidate-from-env-universe-err-2.rs:12:19
|
||||
|
Loading…
Reference in New Issue
Block a user