Skip to content

Commit aa46052

Browse files
committed
rustc_resolve: improve const generic errors
Signed-off-by: Usman Akinyemi <usmanakinyemi202@gmail.com>
1 parent f824853 commit aa46052

20 files changed

Lines changed: 526 additions & 314 deletions

compiler/rustc_hir_analysis/src/hir_ty_lowering/generics.rs

Lines changed: 11 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,7 @@ use rustc_errors::codes::*;
33
use rustc_errors::{Applicability, Diag, ErrorGuaranteed, MultiSpan, struct_span_code_err};
44
use rustc_hir::def::{DefKind, Res};
55
use rustc_hir::def_id::DefId;
6-
use rustc_hir::{self as hir, GenericArg};
6+
use rustc_hir::{self as hir, GenericArg, QPath, TyKind};
77
use rustc_middle::ty::{
88
self, GenericArgsRef, GenericParamDef, GenericParamDefKind, IsSuggestable, Ty,
99
};
@@ -41,6 +41,16 @@ fn generic_arg_mismatch_err(
4141
param.kind.descr(),
4242
);
4343

44+
if let GenericArg::Type(ty, ..) = arg
45+
&& let TyKind::Path(qpath) = &ty.kind
46+
&& let QPath::Resolved(_, path) = qpath
47+
{
48+
let res = path.res;
49+
if matches!(res, Res::Err) {
50+
return err.delay_as_bug();
51+
}
52+
}
53+
4454
let add_braces_suggestion = |arg: &GenericArg<'_>, err: &mut Diag<'_>| {
4555
let suggestions = vec![
4656
(arg.span().shrink_to_lo(), String::from("{ ")),

compiler/rustc_resolve/src/build_reduced_graph.rs

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -898,7 +898,7 @@ impl<'a, 'ra, 'tcx> BuildReducedGraphVisitor<'a, 'ra, 'tcx> {
898898
}
899899

900900
// These items live in both the type and value namespaces.
901-
ItemKind::Struct(ident, _, ref vdata) => {
901+
ItemKind::Struct(ident, ref generics, ref vdata) => {
902902
self.build_reduced_graph_for_struct_variant(
903903
vdata.fields(),
904904
ident,
@@ -947,6 +947,7 @@ impl<'a, 'ra, 'tcx> BuildReducedGraphVisitor<'a, 'ra, 'tcx> {
947947
.struct_constructors
948948
.insert(local_def_id, (ctor_res, ctor_vis.to_def_id(), ret_fields));
949949
}
950+
self.r.struct_generics.insert(local_def_id, generics.clone());
950951
}
951952

952953
ItemKind::Union(ident, _, ref vdata) => {

compiler/rustc_resolve/src/errors.rs

Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -882,6 +882,20 @@ pub(crate) struct UnexpectedResChangeTyToConstParamSugg {
882882
pub applicability: Applicability,
883883
}
884884

885+
#[derive(Subdiagnostic)]
886+
#[suggestion(
887+
"you might have meant to introduce a const parameter on the `{$item_name}`",
888+
code = "{snippet}",
889+
applicability = "machine-applicable",
890+
style = "verbose"
891+
)]
892+
pub(crate) struct UnexpectedMissingConstParameter {
893+
#[primary_span]
894+
pub span: Span,
895+
pub snippet: String,
896+
pub item_name: String,
897+
}
898+
885899
#[derive(Subdiagnostic)]
886900
#[multipart_suggestion(
887901
"you might have meant to write a const parameter here",

compiler/rustc_resolve/src/late.rs

Lines changed: 18 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -4426,7 +4426,7 @@ impl<'a, 'ast, 'ra, 'tcx> LateResolutionVisitor<'a, 'ast, 'ra, 'tcx> {
44264426
let Finalize { node_id, path_span, .. } = finalize;
44274427
let report_errors = |this: &mut Self, res: Option<Res>| {
44284428
if this.should_report_errs() {
4429-
let (err, candidates) = this.smart_resolve_report_errors(
4429+
let (mut err, candidates) = this.smart_resolve_report_errors(
44304430
path,
44314431
None,
44324432
path_span,
@@ -4437,7 +4437,8 @@ impl<'a, 'ast, 'ra, 'tcx> LateResolutionVisitor<'a, 'ast, 'ra, 'tcx> {
44374437

44384438
let def_id = this.parent_scope.module.nearest_parent_mod();
44394439
let instead = res.is_some();
4440-
let suggestion = if let Some((start, end)) = this.diag_metadata.in_range
4440+
let (suggestion, const_err) = if let Some((start, end)) =
4441+
this.diag_metadata.in_range
44414442
&& path[0].ident.span.lo() == end.span.lo()
44424443
&& !matches!(start.kind, ExprKind::Lit(_))
44434444
{
@@ -4449,22 +4450,30 @@ impl<'a, 'ast, 'ra, 'tcx> LateResolutionVisitor<'a, 'ast, 'ra, 'tcx> {
44494450
span = span.with_lo(span.lo() + BytePos(1));
44504451
sugg = "";
44514452
}
4452-
Some((
4453-
span,
4454-
"you might have meant to write `.` instead of `..`",
4455-
sugg.to_string(),
4456-
Applicability::MaybeIncorrect,
4457-
))
4453+
(
4454+
Some((
4455+
span,
4456+
"you might have meant to write `.` instead of `..`",
4457+
sugg.to_string(),
4458+
Applicability::MaybeIncorrect,
4459+
)),
4460+
None,
4461+
)
44584462
} else if res.is_none()
44594463
&& let PathSource::Type
44604464
| PathSource::Expr(_)
44614465
| PathSource::PreciseCapturingArg(..) = source
44624466
{
44634467
this.suggest_adding_generic_parameter(path, source)
44644468
} else {
4465-
None
4469+
(None, None)
44664470
};
44674471

4472+
if let Some(const_err) = const_err {
4473+
err.cancel();
4474+
err = const_err;
4475+
}
4476+
44684477
let ue = UseError {
44694478
err,
44704479
candidates,

0 commit comments

Comments
 (0)