Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Fix a error suggestion for E0121 when using placeholder _ as return types on function signature. #127110

Merged
merged 1 commit into from
Jun 30, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
19 changes: 18 additions & 1 deletion compiler/rustc_hir_analysis/src/collect.rs
Original file line number Diff line number Diff line change
Expand Up @@ -1459,8 +1459,25 @@ fn infer_return_ty_for_fn_sig<'tcx>(
Some(ty) => {
let fn_sig = tcx.typeck(def_id).liberated_fn_sigs()[hir_id];
// Typeck doesn't expect erased regions to be returned from `type_of`.
// This is a heuristic approach. If the scope has region paramters,
// we should change fn_sig's lifetime from `ReErased` to `ReError`,
// otherwise to `ReStatic`.
let has_region_params = generics.params.iter().any(|param| match param.kind {
GenericParamKind::Lifetime { .. } => true,
_ => false,
});
let fn_sig = tcx.fold_regions(fn_sig, |r, _| match *r {
ty::ReErased => tcx.lifetimes.re_static,
ty::ReErased => {
if has_region_params {
ty::Region::new_error_with_message(
tcx,
DUMMY_SP,
"erased region is not allowed here in return type",
)
} else {
tcx.lifetimes.re_static
}
}
_ => r,
});

Expand Down
33 changes: 33 additions & 0 deletions tests/ui/return/infer-return-ty-for-fn-sig-issue-125488.fixed
Original file line number Diff line number Diff line change
@@ -0,0 +1,33 @@
//@ run-rustfix

#[allow(dead_code)]

fn main() {
struct S<'a>(&'a ());

fn f1(s: S<'_>) -> S<'_> {
//~^ ERROR the placeholder `_` is not allowed
s
}

fn f2(s: S<'_>) -> S<'_> {
//~^ ERROR the placeholder `_` is not allowed
let x = true;
if x {
s
} else {
s
}
}

fn f3(s: S<'_>) -> S<'_> {
//~^ ERROR the placeholder `_` is not allowed
return s;
}

fn f4(s: S<'_>) -> S<'_> {
//~^ ERROR the placeholder `_` is not allowed
let _x = 1;
return s;
}
}
33 changes: 33 additions & 0 deletions tests/ui/return/infer-return-ty-for-fn-sig-issue-125488.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,33 @@
//@ run-rustfix

#[allow(dead_code)]

fn main() {
struct S<'a>(&'a ());

fn f1(s: S<'_>) -> _ {
//~^ ERROR the placeholder `_` is not allowed
s
}

fn f2(s: S<'_>) -> _ {
//~^ ERROR the placeholder `_` is not allowed
let x = true;
if x {
s
} else {
s
}
}

fn f3(s: S<'_>) -> _ {
//~^ ERROR the placeholder `_` is not allowed
return s;
}

fn f4(s: S<'_>) -> _ {
//~^ ERROR the placeholder `_` is not allowed
let _x = 1;
return s;
}
}
39 changes: 39 additions & 0 deletions tests/ui/return/infer-return-ty-for-fn-sig-issue-125488.stderr
Original file line number Diff line number Diff line change
@@ -0,0 +1,39 @@
error[E0121]: the placeholder `_` is not allowed within types on item signatures for return types
--> $DIR/infer-return-ty-for-fn-sig-issue-125488.rs:8:24
|
LL | fn f1(s: S<'_>) -> _ {
| ^
| |
| not allowed in type signatures
| help: replace with the correct return type: `S<'_>`

error[E0121]: the placeholder `_` is not allowed within types on item signatures for return types
--> $DIR/infer-return-ty-for-fn-sig-issue-125488.rs:13:24
|
LL | fn f2(s: S<'_>) -> _ {
| ^
| |
| not allowed in type signatures
| help: replace with the correct return type: `S<'_>`

error[E0121]: the placeholder `_` is not allowed within types on item signatures for return types
--> $DIR/infer-return-ty-for-fn-sig-issue-125488.rs:23:24
|
LL | fn f3(s: S<'_>) -> _ {
| ^
| |
| not allowed in type signatures
| help: replace with the correct return type: `S<'_>`

error[E0121]: the placeholder `_` is not allowed within types on item signatures for return types
--> $DIR/infer-return-ty-for-fn-sig-issue-125488.rs:28:24
|
LL | fn f4(s: S<'_>) -> _ {
| ^
| |
| not allowed in type signatures
| help: replace with the correct return type: `S<'_>`

error: aborting due to 4 previous errors

For more information about this error, try `rustc --explain E0121`.
2 changes: 1 addition & 1 deletion tests/ui/typeck/typeck_type_placeholder_item.rs
Original file line number Diff line number Diff line change
Expand Up @@ -47,7 +47,7 @@ impl Test9 {

fn test11(x: &usize) -> &_ {
//~^ ERROR the placeholder `_` is not allowed within types on item signatures for return types
&x //~ ERROR cannot return reference to function parameter
&x
}

unsafe fn test12(x: *const usize) -> *const *const _ {
Expand Down
12 changes: 3 additions & 9 deletions tests/ui/typeck/typeck_type_placeholder_item.stderr
Original file line number Diff line number Diff line change
Expand Up @@ -158,7 +158,7 @@ LL | fn test11(x: &usize) -> &_ {
| -^
| ||
| |not allowed in type signatures
| help: replace with the correct return type: `&'static &'static usize`
| help: replace with the correct return type: `&&usize`

error[E0121]: the placeholder `_` is not allowed within types on item signatures for return types
--> $DIR/typeck_type_placeholder_item.rs:53:52
Expand Down Expand Up @@ -687,13 +687,7 @@ help: add `#![feature(const_trait_impl)]` to the crate attributes to enable
LL + #![feature(const_trait_impl)]
|

error[E0515]: cannot return reference to function parameter `x`
--> $DIR/typeck_type_placeholder_item.rs:50:5
|
LL | &x
| ^^ returns a reference to data owned by the current function

error: aborting due to 75 previous errors
error: aborting due to 74 previous errors

Some errors have detailed explanations: E0015, E0046, E0121, E0282, E0403, E0515.
Some errors have detailed explanations: E0015, E0046, E0121, E0282, E0403.
For more information about an error, try `rustc --explain E0015`.
Loading