Migrate pattern bindings with variant name lint

This commit is contained in:
TheOddGarlic 2022-08-29 10:06:50 +03:00 committed by mejrs
parent 6f82a00aa1
commit e1c5073c07
3 changed files with 24 additions and 23 deletions

View File

@ -233,3 +233,7 @@ mir_build_trailing_irrefutable_let_patterns = trailing irrefutable {$count ->
[one] it
*[other] them
} into the body
mir_build_bindings_with_variant_name =
pattern binding `{$ident}` is named the same as one of the variants of the type `{$ty_path}`
.suggestion = to match on the variant, qualify the path

View File

@ -3,7 +3,7 @@ use rustc_errors::{error_code, Applicability, DiagnosticBuilder, ErrorGuaranteed
use rustc_macros::{LintDiagnostic, SessionDiagnostic, SessionSubdiagnostic};
use rustc_middle::ty::{self, Ty};
use rustc_session::{parse::ParseSess, SessionDiagnostic};
use rustc_span::Span;
use rustc_span::{symbol::Ident, Span};
#[derive(LintDiagnostic)]
#[diag(mir_build::unconditional_recursion)]
@ -513,3 +513,12 @@ pub struct LeadingIrrefutableLetPatterns {
pub struct TrailingIrrefutableLetPatterns {
pub count: usize,
}
#[derive(LintDiagnostic)]
#[diag(mir_build::bindings_with_variant_name, code = "E0170")]
pub struct BindingsWithVariantName {
#[suggestion(code = "{ty_path}::{ident}", applicability = "machine-applicable")]
pub suggestion: Option<Span>,
pub ty_path: String,
pub ident: Ident,
}

View File

@ -9,8 +9,8 @@ use crate::errors::*;
use rustc_arena::TypedArena;
use rustc_ast::Mutability;
use rustc_errors::{
error_code, pluralize, struct_span_err, Applicability, DelayDm, Diagnostic, DiagnosticBuilder,
ErrorGuaranteed, MultiSpan,
pluralize, struct_span_err, Applicability, Diagnostic, DiagnosticBuilder, ErrorGuaranteed,
MultiSpan,
};
use rustc_hir as hir;
use rustc_hir::def::*;
@ -547,32 +547,20 @@ fn check_for_bindings_named_same_as_variants(
})
{
let variant_count = edef.variants().len();
cx.tcx.struct_span_lint_hir(
let ty_path = cx.tcx.def_path_str(edef.did());
cx.tcx.emit_spanned_lint(
BINDINGS_WITH_VARIANT_NAME,
p.hir_id,
p.span,
DelayDm(|| format!(
"pattern binding `{}` is named the same as one \
of the variants of the type `{}`",
ident, cx.tcx.def_path_str(edef.did())
)),
|lint| {
let ty_path = cx.tcx.def_path_str(edef.did());
lint.code(error_code!(E0170));
BindingsWithVariantName {
// If this is an irrefutable pattern, and there's > 1 variant,
// then we can't actually match on this. Applying the below
// suggestion would produce code that breaks on `check_irrefutable`.
if rf == Refutable || variant_count == 1 {
lint.span_suggestion(
p.span,
"to match on the variant, qualify the path",
format!("{}::{}", ty_path, ident),
Applicability::MachineApplicable,
);
}
lint
suggestion: if rf == Refutable || variant_count == 1 {
Some(p.span)
} else { None },
ty_path,
ident,
},
)
}