1
Fork 0

tweak logic of "unknown field" label

This commit is contained in:
Esteban Küber 2023-11-18 00:40:11 +00:00
parent 1ee37bf03f
commit 289ce572b3
12 changed files with 101 additions and 49 deletions

View file

@ -2191,7 +2191,8 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
if let Some(field_name) =
find_best_match_for_name(&available_field_names, field.ident.name, None)
{
err.span_suggestion(
err.span_label(field.ident.span, "unknown field");
err.span_suggestion_verbose(
field.ident.span,
"a field with a similar name exists",
field_name,
@ -2420,30 +2421,32 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
ty: Ty<'tcx>,
) {
let Some(output_ty) = self.get_impl_future_output_ty(ty) else {
err.span_label(field_ident.span, "unknown field");
return;
};
if let ty::Adt(def, _) = output_ty.kind() {
// no field access on enum type
if !def.is_enum() {
if def
.non_enum_variant()
.fields
.iter()
.any(|field| field.ident(self.tcx) == field_ident)
{
err.span_label(
field_ident.span,
"field not available in `impl Future`, but it is available in its `Output`",
);
err.span_suggestion_verbose(
base.span.shrink_to_hi(),
"consider `await`ing on the `Future` and access the field of its `Output`",
".await",
Applicability::MaybeIncorrect,
);
}
}
let ty::Adt(def, _) = output_ty.kind() else {
err.span_label(field_ident.span, "unknown field");
return;
};
// no field access on enum type
if def.is_enum() {
err.span_label(field_ident.span, "unknown field");
return;
}
if !def.non_enum_variant().fields.iter().any(|field| field.ident(self.tcx) == field_ident) {
err.span_label(field_ident.span, "unknown field");
return;
}
err.span_label(
field_ident.span,
"field not available in `impl Future`, but it is available in its `Output`",
);
err.span_suggestion_verbose(
base.span.shrink_to_hi(),
"consider `await`ing on the `Future` and access the field of its `Output`",
".await",
Applicability::MaybeIncorrect,
);
}
fn ban_nonexisting_field(
@ -2467,16 +2470,17 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
self.suggest_first_deref_field(&mut err, expr, base, ident);
}
ty::Param(param_ty) => {
err.span_label(ident.span, "unknown field");
self.point_at_param_definition(&mut err, param_ty);
}
ty::Alias(ty::Opaque, _) => {
self.suggest_await_on_field_access(&mut err, ident, base, base_ty.peel_refs());
}
_ => {}
_ => {
err.span_label(ident.span, "unknown field");
}
}
err.span_label(ident.span, "unknown field");
self.suggest_fn_call(&mut err, base, base_ty, |output_ty| {
if let ty::Adt(def, _) = output_ty.kind()
&& !def.is_enum()
@ -2635,6 +2639,7 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
field: Ident,
len: ty::Const<'tcx>,
) {
err.span_label(field.span, "unknown field");
if let (Some(len), Ok(user_index)) =
(len.try_eval_target_usize(self.tcx, self.param_env), field.as_str().parse::<u64>())
&& let Ok(base) = self.tcx.sess.source_map().span_to_snippet(base.span)
@ -2657,6 +2662,7 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
base: &hir::Expr<'_>,
field: Ident,
) {
err.span_label(field.span, "unknown field");
if let Ok(base) = self.tcx.sess.source_map().span_to_snippet(base.span) {
let msg = format!("`{base}` is a raw pointer; try dereferencing it");
let suggestion = format!("(*{base}).{field}");