Convert uses of BuiltinLintDiag::Normal to custom variants
This ensures all diagnostic messages are created at diagnostic emission time, making them translatable.
This commit is contained in:
parent
41a20b4c56
commit
b7abf014ec
@ -247,5 +247,3 @@ builtin_macros_unexpected_lit = expected path to a trait, found literal
|
||||
.label = not a trait
|
||||
.str_lit = try using `#[derive({$sym})]`
|
||||
.other = for example, write `#[derive(Debug)]` for `Debug`
|
||||
|
||||
builtin_macros_unnameable_test_items = cannot test inner items
|
||||
|
@ -1,6 +1,7 @@
|
||||
use crate::errors;
|
||||
use crate::util::expr_to_spanned_string;
|
||||
use ast::token::IdentIsRaw;
|
||||
use lint::BuiltinLintDiag;
|
||||
use rustc_ast as ast;
|
||||
use rustc_ast::ptr::P;
|
||||
use rustc_ast::token::{self, Delimiter};
|
||||
@ -509,19 +510,19 @@ fn expand_preparsed_asm(
|
||||
};
|
||||
|
||||
if template_str.contains(".intel_syntax") {
|
||||
ecx.psess().buffer_lint(
|
||||
ecx.psess().buffer_lint_with_diagnostic(
|
||||
lint::builtin::BAD_ASM_STYLE,
|
||||
find_span(".intel_syntax"),
|
||||
ecx.current_expansion.lint_node_id,
|
||||
"avoid using `.intel_syntax`, Intel syntax is the default",
|
||||
BuiltinLintDiag::AvoidUsingIntelSyntax,
|
||||
);
|
||||
}
|
||||
if template_str.contains(".att_syntax") {
|
||||
ecx.psess().buffer_lint(
|
||||
ecx.psess().buffer_lint_with_diagnostic(
|
||||
lint::builtin::BAD_ASM_STYLE,
|
||||
find_span(".att_syntax"),
|
||||
ecx.current_expansion.lint_node_id,
|
||||
"avoid using `.att_syntax`, prefer using `options(att_syntax)` instead",
|
||||
BuiltinLintDiag::AvoidUsingAttSyntax,
|
||||
);
|
||||
}
|
||||
}
|
||||
|
@ -11,6 +11,7 @@
|
||||
resolve_path, DummyResult, ExpandResult, ExtCtxt, MacEager, MacResult, MacroExpanderResult,
|
||||
};
|
||||
use rustc_expand::module::DirOwnership;
|
||||
use rustc_lint_defs::BuiltinLintDiag;
|
||||
use rustc_parse::new_parser_from_file;
|
||||
use rustc_parse::parser::{ForceCollect, Parser};
|
||||
use rustc_session::lint::builtin::INCOMPLETE_INCLUDE;
|
||||
@ -143,11 +144,11 @@ impl<'a> MacResult for ExpandInclude<'a> {
|
||||
fn make_expr(mut self: Box<ExpandInclude<'a>>) -> Option<P<ast::Expr>> {
|
||||
let expr = parse_expr(&mut self.p).ok()?;
|
||||
if self.p.token != token::Eof {
|
||||
self.p.psess.buffer_lint(
|
||||
self.p.psess.buffer_lint_with_diagnostic(
|
||||
INCOMPLETE_INCLUDE,
|
||||
self.p.token.span,
|
||||
self.node_id,
|
||||
"include macro expected single expression in source",
|
||||
BuiltinLintDiag::IncompleteInclude,
|
||||
);
|
||||
}
|
||||
Some(expr)
|
||||
|
@ -9,6 +9,7 @@
|
||||
use rustc_expand::base::{ExtCtxt, ResolverExpand};
|
||||
use rustc_expand::expand::{AstFragment, ExpansionConfig};
|
||||
use rustc_feature::Features;
|
||||
use rustc_lint_defs::BuiltinLintDiag;
|
||||
use rustc_session::lint::builtin::UNNAMEABLE_TEST_ITEMS;
|
||||
use rustc_session::Session;
|
||||
use rustc_span::hygiene::{AstPass, SyntaxContext, Transparency};
|
||||
@ -159,11 +160,11 @@ struct InnerItemLinter<'a> {
|
||||
impl<'a> Visitor<'a> for InnerItemLinter<'_> {
|
||||
fn visit_item(&mut self, i: &'a ast::Item) {
|
||||
if let Some(attr) = attr::find_by_name(&i.attrs, sym::rustc_test_marker) {
|
||||
self.sess.psess.buffer_lint(
|
||||
self.sess.psess.buffer_lint_with_diagnostic(
|
||||
UNNAMEABLE_TEST_ITEMS,
|
||||
attr.span,
|
||||
i.id,
|
||||
crate::fluent_generated::builtin_macros_unnameable_test_items,
|
||||
BuiltinLintDiag::UnnameableTestItems,
|
||||
);
|
||||
}
|
||||
}
|
||||
|
@ -5,7 +5,7 @@
|
||||
use rustc_expand::base::{Annotatable, ExpandResult, ExtCtxt};
|
||||
use rustc_expand::expand::AstFragment;
|
||||
use rustc_feature::AttributeTemplate;
|
||||
use rustc_lint_defs::builtin::DUPLICATE_MACRO_ATTRIBUTES;
|
||||
use rustc_lint_defs::{builtin::DUPLICATE_MACRO_ATTRIBUTES, BuiltinLintDiag};
|
||||
use rustc_parse::{parser, validate_attr};
|
||||
use rustc_session::errors::report_lit_error;
|
||||
use rustc_span::{BytePos, Span, Symbol};
|
||||
@ -42,11 +42,11 @@ pub(crate) fn warn_on_duplicate_attribute(ecx: &ExtCtxt<'_>, item: &Annotatable,
|
||||
};
|
||||
if let Some(attrs) = attrs {
|
||||
if let Some(attr) = attr::find_by_name(attrs, name) {
|
||||
ecx.psess().buffer_lint(
|
||||
ecx.psess().buffer_lint_with_diagnostic(
|
||||
DUPLICATE_MACRO_ATTRIBUTES,
|
||||
attr.span,
|
||||
ecx.current_expansion.lint_node_id,
|
||||
"duplicated attribute",
|
||||
BuiltinLintDiag::DuplicateMacroAttribute,
|
||||
);
|
||||
}
|
||||
}
|
||||
|
@ -14,6 +14,7 @@
|
||||
use rustc_data_structures::flat_map_in_place::FlatMapInPlace;
|
||||
use rustc_feature::Features;
|
||||
use rustc_feature::{ACCEPTED_FEATURES, REMOVED_FEATURES, UNSTABLE_FEATURES};
|
||||
use rustc_lint_defs::BuiltinLintDiag;
|
||||
use rustc_parse::validate_attr;
|
||||
use rustc_session::parse::feature_err;
|
||||
use rustc_session::Session;
|
||||
@ -248,7 +249,6 @@ fn process_cfg_attr(&self, attr: &Attribute) -> Vec<Attribute> {
|
||||
/// Gives a compiler warning when the `cfg_attr` contains no attributes and
|
||||
/// is in the original source file. Gives a compiler error if the syntax of
|
||||
/// the attribute is incorrect.
|
||||
#[allow(rustc::untranslatable_diagnostic)] // FIXME: make this translatable
|
||||
pub(crate) fn expand_cfg_attr(&self, attr: &Attribute, recursive: bool) -> Vec<Attribute> {
|
||||
let Some((cfg_predicate, expanded_attrs)) =
|
||||
rustc_parse::parse_cfg_attr(attr, &self.sess.psess)
|
||||
@ -258,11 +258,11 @@ pub(crate) fn expand_cfg_attr(&self, attr: &Attribute, recursive: bool) -> Vec<A
|
||||
|
||||
// Lint on zero attributes in source.
|
||||
if expanded_attrs.is_empty() {
|
||||
self.sess.psess.buffer_lint(
|
||||
self.sess.psess.buffer_lint_with_diagnostic(
|
||||
rustc_lint_defs::builtin::UNUSED_ATTRIBUTES,
|
||||
attr.span,
|
||||
ast::CRATE_NODE_ID,
|
||||
"`#[cfg_attr]` does not expand to any attributes",
|
||||
BuiltinLintDiag::CfgAttrNoAttributes,
|
||||
);
|
||||
}
|
||||
|
||||
@ -283,7 +283,6 @@ pub(crate) fn expand_cfg_attr(&self, attr: &Attribute, recursive: bool) -> Vec<A
|
||||
}
|
||||
}
|
||||
|
||||
#[allow(rustc::untranslatable_diagnostic)] // FIXME: make this translatable
|
||||
fn expand_cfg_attr_item(
|
||||
&self,
|
||||
attr: &Attribute,
|
||||
@ -342,19 +341,19 @@ fn expand_cfg_attr_item(
|
||||
item_span,
|
||||
);
|
||||
if attr.has_name(sym::crate_type) {
|
||||
self.sess.psess.buffer_lint(
|
||||
self.sess.psess.buffer_lint_with_diagnostic(
|
||||
rustc_lint_defs::builtin::DEPRECATED_CFG_ATTR_CRATE_TYPE_NAME,
|
||||
attr.span,
|
||||
ast::CRATE_NODE_ID,
|
||||
"`crate_type` within an `#![cfg_attr] attribute is deprecated`",
|
||||
BuiltinLintDiag::CrateTypeInCfgAttr,
|
||||
);
|
||||
}
|
||||
if attr.has_name(sym::crate_name) {
|
||||
self.sess.psess.buffer_lint(
|
||||
self.sess.psess.buffer_lint_with_diagnostic(
|
||||
rustc_lint_defs::builtin::DEPRECATED_CFG_ATTR_CRATE_TYPE_NAME,
|
||||
attr.span,
|
||||
ast::CRATE_NODE_ID,
|
||||
"`crate_name` within an `#![cfg_attr] attribute is deprecated`",
|
||||
BuiltinLintDiag::CrateNameInCfgAttr,
|
||||
);
|
||||
}
|
||||
attr
|
||||
|
@ -110,7 +110,8 @@
|
||||
use rustc_ast::token::{Delimiter, IdentIsRaw, Token, TokenKind};
|
||||
use rustc_ast::{NodeId, DUMMY_NODE_ID};
|
||||
use rustc_data_structures::fx::FxHashMap;
|
||||
use rustc_errors::{DiagMessage, MultiSpan};
|
||||
use rustc_errors::MultiSpan;
|
||||
use rustc_lint_defs::BuiltinLintDiag;
|
||||
use rustc_session::lint::builtin::{META_VARIABLE_MISUSE, MISSING_FRAGMENT_SPECIFIER};
|
||||
use rustc_session::parse::ParseSess;
|
||||
use rustc_span::symbol::kw;
|
||||
@ -252,7 +253,7 @@ fn check_binders(
|
||||
// 1. The meta-variable is already bound in the current LHS: This is an error.
|
||||
let mut span = MultiSpan::from_span(span);
|
||||
span.push_span_label(prev_info.span, "previous declaration");
|
||||
buffer_lint(psess, span, node_id, "duplicate matcher binding");
|
||||
buffer_lint(psess, span, node_id, BuiltinLintDiag::DuplicateMatcherBinding);
|
||||
} else if get_binder_info(macros, binders, name).is_none() {
|
||||
// 2. The meta-variable is free: This is a binder.
|
||||
binders.insert(name, BinderInfo { span, ops: ops.into() });
|
||||
@ -267,11 +268,11 @@ fn check_binders(
|
||||
// FIXME: Report this as a hard error eventually and remove equivalent errors from
|
||||
// `parse_tt_inner` and `nameize`. Until then the error may be reported twice, once
|
||||
// as a hard error and then once as a buffered lint.
|
||||
psess.buffer_lint(
|
||||
psess.buffer_lint_with_diagnostic(
|
||||
MISSING_FRAGMENT_SPECIFIER,
|
||||
span,
|
||||
node_id,
|
||||
"missing fragment specifier",
|
||||
BuiltinLintDiag::MissingFragmentSpecifier,
|
||||
);
|
||||
}
|
||||
if !macros.is_empty() {
|
||||
@ -595,7 +596,7 @@ fn check_ops_is_prefix(
|
||||
return;
|
||||
}
|
||||
}
|
||||
buffer_lint(psess, span.into(), node_id, format!("unknown macro variable `{name}`"));
|
||||
buffer_lint(psess, span.into(), node_id, BuiltinLintDiag::UnknownMacroVariable(name));
|
||||
}
|
||||
|
||||
/// Returns whether `binder_ops` is a prefix of `occurrence_ops`.
|
||||
@ -628,8 +629,7 @@ fn ops_is_prefix(
|
||||
if i >= occurrence_ops.len() {
|
||||
let mut span = MultiSpan::from_span(span);
|
||||
span.push_span_label(binder.span, "expected repetition");
|
||||
let message = format!("variable '{name}' is still repeating at this depth");
|
||||
buffer_lint(psess, span, node_id, message);
|
||||
buffer_lint(psess, span, node_id, BuiltinLintDiag::MetaVariableStillRepeating(name));
|
||||
return;
|
||||
}
|
||||
let occurrence = &occurrence_ops[i];
|
||||
@ -637,21 +637,15 @@ fn ops_is_prefix(
|
||||
let mut span = MultiSpan::from_span(span);
|
||||
span.push_span_label(binder.span, "expected repetition");
|
||||
span.push_span_label(occurrence.span, "conflicting repetition");
|
||||
let message = "meta-variable repeats with different Kleene operator";
|
||||
buffer_lint(psess, span, node_id, message);
|
||||
buffer_lint(psess, span, node_id, BuiltinLintDiag::MetaVariableWrongOperator);
|
||||
return;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
fn buffer_lint(
|
||||
psess: &ParseSess,
|
||||
span: MultiSpan,
|
||||
node_id: NodeId,
|
||||
message: impl Into<DiagMessage>,
|
||||
) {
|
||||
fn buffer_lint(psess: &ParseSess, span: MultiSpan, node_id: NodeId, diag: BuiltinLintDiag) {
|
||||
// Macros loaded from other crates have dummy node ids.
|
||||
if node_id != DUMMY_NODE_ID {
|
||||
psess.buffer_lint(META_VARIABLE_MISUSE, span, node_id, message);
|
||||
psess.buffer_lint_with_diagnostic(META_VARIABLE_MISUSE, span, node_id, diag);
|
||||
}
|
||||
}
|
||||
|
@ -399,30 +399,17 @@ pub(crate) fn check_attr_crate_type(
|
||||
|
||||
if let ast::MetaItemKind::NameValue(spanned) = a.meta_kind().unwrap() {
|
||||
let span = spanned.span;
|
||||
let lev_candidate = find_best_match_for_name(
|
||||
let candidate = find_best_match_for_name(
|
||||
&CRATE_TYPES.iter().map(|(k, _)| *k).collect::<Vec<_>>(),
|
||||
n,
|
||||
None,
|
||||
);
|
||||
if let Some(candidate) = lev_candidate {
|
||||
lint_buffer.buffer_lint_with_diagnostic(
|
||||
lint::builtin::UNKNOWN_CRATE_TYPES,
|
||||
ast::CRATE_NODE_ID,
|
||||
span,
|
||||
BuiltinLintDiag::UnknownCrateTypes(
|
||||
span,
|
||||
"did you mean".to_string(),
|
||||
format!("\"{candidate}\""),
|
||||
),
|
||||
BuiltinLintDiag::UnknownCrateTypes { span, candidate },
|
||||
);
|
||||
} else {
|
||||
lint_buffer.buffer_lint(
|
||||
lint::builtin::UNKNOWN_CRATE_TYPES,
|
||||
ast::CRATE_NODE_ID,
|
||||
span,
|
||||
"invalid `crate_type` value",
|
||||
);
|
||||
}
|
||||
}
|
||||
} else {
|
||||
// This is here mainly to check for using a macro, such as
|
||||
|
@ -156,6 +156,9 @@ lint_builtin_unused_doc_comment = unused doc comment
|
||||
lint_builtin_while_true = denote infinite loops with `loop {"{"} ... {"}"}`
|
||||
.suggestion = use `loop`
|
||||
|
||||
lint_cfg_attr_no_attributes =
|
||||
`#[cfg_attr]` does not expand to any attributes
|
||||
|
||||
lint_check_name_unknown_tool = unknown lint tool: `{$tool_name}`
|
||||
|
||||
lint_command_line_source = `forbid` lint level was set on command line
|
||||
@ -164,6 +167,12 @@ lint_confusable_identifier_pair = found both `{$existing_sym}` and `{$sym}` as i
|
||||
.current_use = this identifier can be confused with `{$existing_sym}`
|
||||
.other_use = other identifier used here
|
||||
|
||||
lint_crate_name_in_cfg_attr_deprecated =
|
||||
`crate_name` within an `#![cfg_attr] attribute is deprecated`
|
||||
|
||||
lint_crate_type_in_cfg_attr_deprecated =
|
||||
`crate_type` within an `#![cfg_attr] attribute is deprecated`
|
||||
|
||||
lint_cstring_ptr = getting the inner pointer of a temporary `CString`
|
||||
.as_ptr_label = this pointer will be invalid
|
||||
.unwrap_label = this `CString` is deallocated at the end of the statement, bind it to a variable to extend its lifetime
|
||||
@ -662,6 +671,8 @@ lint_unknown_lint =
|
||||
lint_unknown_tool_in_scoped_lint = unknown tool name `{$tool_name}` found in scoped lint: `{$tool_name}::{$lint_name}`
|
||||
.help = add `#![register_tool({$tool_name})]` to the crate root
|
||||
|
||||
lint_unnameable_test_items = cannot test inner items
|
||||
|
||||
lint_unsupported_group = `{$lint_group}` lint group is not supported with ´--force-warn´
|
||||
|
||||
lint_untranslatable_diag = diagnostics should be created using translatable messages
|
||||
@ -701,3 +712,6 @@ lint_unused_result = unused result of type `{$ty}`
|
||||
|
||||
lint_variant_size_differences =
|
||||
enum variant is more than three times larger ({$largest} bytes) than the next largest
|
||||
|
||||
lint_wasm_c_abi =
|
||||
older versions of the `wasm-bindgen` crate will be incompatible with future versions of Rust; please update to `wasm-bindgen` v0.2.88
|
||||
|
@ -11,8 +11,13 @@
|
||||
use rustc_session::Session;
|
||||
use rustc_span::BytePos;
|
||||
|
||||
use std::fmt::Write;
|
||||
|
||||
mod check_cfg;
|
||||
|
||||
#[cfg(test)]
|
||||
mod tests;
|
||||
|
||||
pub(super) fn builtin(sess: &Session, diagnostic: BuiltinLintDiag, diag: &mut Diag<'_, ()>) {
|
||||
match diagnostic {
|
||||
BuiltinLintDiag::UnicodeTextFlow(span, content) => {
|
||||
@ -52,7 +57,6 @@ pub(super) fn builtin(sess: &Session, diagnostic: BuiltinLintDiag, diag: &mut Di
|
||||
);
|
||||
}
|
||||
}
|
||||
BuiltinLintDiag::Normal(_) => (),
|
||||
BuiltinLintDiag::AbsPathWithModule(span) => {
|
||||
let (sugg, app) = match sess.source_map().span_to_snippet(span) {
|
||||
Ok(ref s) => {
|
||||
@ -87,8 +91,15 @@ pub(super) fn builtin(sess: &Session, diagnostic: BuiltinLintDiag, diag: &mut Di
|
||||
),
|
||||
);
|
||||
}
|
||||
BuiltinLintDiag::UnknownCrateTypes(span, note, sugg) => {
|
||||
diag.span_suggestion(span, note, sugg, Applicability::MaybeIncorrect);
|
||||
BuiltinLintDiag::UnknownCrateTypes { span, candidate } => {
|
||||
if let Some(candidate) = candidate {
|
||||
diag.span_suggestion(
|
||||
span,
|
||||
"did you mean",
|
||||
format!(r#""{candidate}""#),
|
||||
Applicability::MaybeIncorrect,
|
||||
);
|
||||
}
|
||||
}
|
||||
BuiltinLintDiag::UnusedImports { fix_msg, fixes, test_module_span, .. } => {
|
||||
if !fixes.is_empty() {
|
||||
@ -361,20 +372,46 @@ pub(super) fn builtin(sess: &Session, diagnostic: BuiltinLintDiag, diag: &mut Di
|
||||
"reduce the glob import's visibility or increase visibility of imported items",
|
||||
);
|
||||
}
|
||||
BuiltinLintDiag::MaybeTypo { span, name } => {
|
||||
BuiltinLintDiag::UnknownDiagnosticAttribute { span, typo_name } => {
|
||||
if let Some(typo_name) = typo_name {
|
||||
diag.span_suggestion_verbose(
|
||||
span,
|
||||
"an attribute with a similar name exists",
|
||||
name,
|
||||
typo_name,
|
||||
Applicability::MachineApplicable,
|
||||
);
|
||||
}
|
||||
}
|
||||
BuiltinLintDiag::MacroUseDeprecated
|
||||
| BuiltinLintDiag::UnusedMacroUse
|
||||
| BuiltinLintDiag::PrivateExternCrateReexport(_)
|
||||
| BuiltinLintDiag::UnusedLabel
|
||||
| BuiltinLintDiag::MacroIsPrivate(_)
|
||||
| BuiltinLintDiag::UnusedMacroDefinition(_)
|
||||
| BuiltinLintDiag::MacroRuleNeverUsed(_, _)
|
||||
| BuiltinLintDiag::UnstableFeature(_)
|
||||
| BuiltinLintDiag::AvoidUsingIntelSyntax
|
||||
| BuiltinLintDiag::AvoidUsingAttSyntax
|
||||
| BuiltinLintDiag::IncompleteInclude
|
||||
| BuiltinLintDiag::UnnameableTestItems
|
||||
| BuiltinLintDiag::DuplicateMacroAttribute
|
||||
| BuiltinLintDiag::CfgAttrNoAttributes
|
||||
| BuiltinLintDiag::CrateTypeInCfgAttr
|
||||
| BuiltinLintDiag::CrateNameInCfgAttr
|
||||
| BuiltinLintDiag::MissingFragmentSpecifier
|
||||
| BuiltinLintDiag::MetaVariableStillRepeating(_)
|
||||
| BuiltinLintDiag::MetaVariableWrongOperator
|
||||
| BuiltinLintDiag::DuplicateMatcherBinding
|
||||
| BuiltinLintDiag::UnknownMacroVariable(_)
|
||||
| BuiltinLintDiag::UnusedExternCrate2 { .. }
|
||||
| BuiltinLintDiag::WasmCAbi
|
||||
| BuiltinLintDiag::IllFormedAttributeInput { .. }
|
||||
| BuiltinLintDiag::InnerAttributeUnstable { .. } => {}
|
||||
}
|
||||
}
|
||||
|
||||
pub(super) fn builtin_message(diagnostic: &BuiltinLintDiag) -> DiagMessage {
|
||||
match diagnostic {
|
||||
BuiltinLintDiag::Normal(msg) => msg.clone(),
|
||||
BuiltinLintDiag::AbsPathWithModule(_) => {
|
||||
"absolute paths must start with `self`, `super`, `crate`, or an \
|
||||
external crate name in the 2018 edition"
|
||||
@ -391,7 +428,7 @@ pub(super) fn builtin_message(diagnostic: &BuiltinLintDiag) -> DiagMessage {
|
||||
BuiltinLintDiag::ElidedLifetimesInPaths(_, _, _, _) => {
|
||||
"hidden lifetime parameters in types are deprecated".into()
|
||||
}
|
||||
BuiltinLintDiag::UnknownCrateTypes(_, _, _) => "invalid `crate_type` value".into(),
|
||||
BuiltinLintDiag::UnknownCrateTypes { .. } => "invalid `crate_type` value".into(),
|
||||
BuiltinLintDiag::UnusedImports { span_snippets, .. } => format!(
|
||||
"unused import{}{}",
|
||||
pluralize!(span_snippets.len()),
|
||||
@ -490,5 +527,81 @@ pub(super) fn builtin_message(diagnostic: &BuiltinLintDiag) -> DiagMessage {
|
||||
import_vis
|
||||
)
|
||||
.into(),
|
||||
BuiltinLintDiag::MacroUseDeprecated => "deprecated `#[macro_use]` attribute used to \
|
||||
import macros should be replaced at use sites \
|
||||
with a `use` item to import the macro \
|
||||
instead"
|
||||
.into(),
|
||||
BuiltinLintDiag::UnusedMacroUse => "unused `#[macro_use]` import".into(),
|
||||
BuiltinLintDiag::PrivateExternCrateReexport(ident) => format!(
|
||||
"extern crate `{ident}` is private, and cannot be \
|
||||
re-exported (error E0365), consider declaring with \
|
||||
`pub`"
|
||||
)
|
||||
.into(),
|
||||
BuiltinLintDiag::UnusedLabel => "unused label".into(),
|
||||
BuiltinLintDiag::MacroIsPrivate(ident) => format!("macro `{ident}` is private").into(),
|
||||
BuiltinLintDiag::UnusedMacroDefinition(name) => {
|
||||
format!("unused macro definition: `{}`", name).into()
|
||||
}
|
||||
BuiltinLintDiag::MacroRuleNeverUsed(n, name) => {
|
||||
format!("rule #{} of macro `{}` is never used", n + 1, name).into()
|
||||
}
|
||||
BuiltinLintDiag::UnstableFeature(msg) => msg.clone().into(),
|
||||
BuiltinLintDiag::AvoidUsingIntelSyntax => {
|
||||
"avoid using `.intel_syntax`, Intel syntax is the default".into()
|
||||
}
|
||||
BuiltinLintDiag::AvoidUsingAttSyntax => {
|
||||
"avoid using `.att_syntax`, prefer using `options(att_syntax)` instead".into()
|
||||
}
|
||||
BuiltinLintDiag::IncompleteInclude => {
|
||||
"include macro expected single expression in source".into()
|
||||
}
|
||||
BuiltinLintDiag::UnnameableTestItems => crate::fluent_generated::lint_unnameable_test_items,
|
||||
BuiltinLintDiag::DuplicateMacroAttribute => "duplicated attribute".into(),
|
||||
BuiltinLintDiag::CfgAttrNoAttributes => {
|
||||
crate::fluent_generated::lint_cfg_attr_no_attributes
|
||||
}
|
||||
BuiltinLintDiag::CrateTypeInCfgAttr => {
|
||||
crate::fluent_generated::lint_crate_type_in_cfg_attr_deprecated
|
||||
}
|
||||
BuiltinLintDiag::CrateNameInCfgAttr => {
|
||||
crate::fluent_generated::lint_crate_name_in_cfg_attr_deprecated
|
||||
}
|
||||
BuiltinLintDiag::MissingFragmentSpecifier => "missing fragment specifier".into(),
|
||||
BuiltinLintDiag::MetaVariableStillRepeating(name) => {
|
||||
format!("variable '{name}' is still repeating at this depth").into()
|
||||
}
|
||||
BuiltinLintDiag::MetaVariableWrongOperator => {
|
||||
"meta-variable repeats with different Kleene operator".into()
|
||||
}
|
||||
BuiltinLintDiag::DuplicateMatcherBinding => "duplicate matcher binding".into(),
|
||||
BuiltinLintDiag::UnknownMacroVariable(name) => {
|
||||
format!("unknown macro variable `{name}`").into()
|
||||
}
|
||||
BuiltinLintDiag::UnusedExternCrate2 { extern_crate, local_crate } => format!(
|
||||
"external crate `{}` unused in `{}`: remove the dependency or add `use {} as _;`",
|
||||
extern_crate, local_crate, extern_crate
|
||||
)
|
||||
.into(),
|
||||
BuiltinLintDiag::WasmCAbi => crate::fluent_generated::lint_wasm_c_abi,
|
||||
BuiltinLintDiag::IllFormedAttributeInput { suggestions } => suggestions
|
||||
.iter()
|
||||
.enumerate()
|
||||
.fold("attribute must be of the form ".to_string(), |mut acc, (i, sugg)| {
|
||||
if i != 0 {
|
||||
write!(acc, " or ").unwrap();
|
||||
}
|
||||
write!(acc, "`{sugg}`").unwrap();
|
||||
acc
|
||||
})
|
||||
.into(),
|
||||
BuiltinLintDiag::InnerAttributeUnstable { is_macro } => if *is_macro {
|
||||
"inner macro attributes are unstable"
|
||||
} else {
|
||||
"custom inner attributes are unstable"
|
||||
}
|
||||
.into(),
|
||||
BuiltinLintDiag::UnknownDiagnosticAttribute { .. } => "unknown diagnostic attribute".into(),
|
||||
}
|
||||
}
|
||||
|
@ -5,12 +5,13 @@
|
||||
use rustc_data_structures::stable_hasher::{
|
||||
HashStable, StableCompare, StableHasher, ToStableHashKey,
|
||||
};
|
||||
use rustc_error_messages::{DiagMessage, MultiSpan};
|
||||
use rustc_error_messages::MultiSpan;
|
||||
use rustc_hir::def::Namespace;
|
||||
use rustc_hir::HashStableContext;
|
||||
use rustc_hir::HirId;
|
||||
use rustc_macros::{Decodable, Encodable, HashStable_Generic};
|
||||
use rustc_span::edition::Edition;
|
||||
use rustc_span::symbol::MacroRulesNormalizedIdent;
|
||||
use rustc_span::{sym, symbol::Ident, Span, Symbol};
|
||||
use rustc_target::spec::abi::Abi;
|
||||
|
||||
@ -577,7 +578,6 @@ pub enum DeprecatedSinceKind {
|
||||
// becomes hacky (and it gets allocated).
|
||||
#[derive(Debug)]
|
||||
pub enum BuiltinLintDiag {
|
||||
Normal(DiagMessage),
|
||||
AbsPathWithModule(Span),
|
||||
ProcMacroDeriveResolutionFallback {
|
||||
span: Span,
|
||||
@ -586,7 +586,10 @@ pub enum BuiltinLintDiag {
|
||||
},
|
||||
MacroExpandedMacroExportsAccessedByAbsolutePaths(Span),
|
||||
ElidedLifetimesInPaths(usize, Span, bool, Span),
|
||||
UnknownCrateTypes(Span, String, String),
|
||||
UnknownCrateTypes {
|
||||
span: Span,
|
||||
candidate: Option<Symbol>,
|
||||
},
|
||||
UnusedImports {
|
||||
fix_msg: String,
|
||||
fixes: Vec<(Span, String)>,
|
||||
@ -694,9 +697,42 @@ pub enum BuiltinLintDiag {
|
||||
max_vis: String,
|
||||
import_vis: String,
|
||||
},
|
||||
MaybeTypo {
|
||||
UnknownDiagnosticAttribute {
|
||||
span: Span,
|
||||
name: Symbol,
|
||||
typo_name: Option<Symbol>,
|
||||
},
|
||||
MacroUseDeprecated,
|
||||
UnusedMacroUse,
|
||||
PrivateExternCrateReexport(Ident),
|
||||
UnusedLabel,
|
||||
MacroIsPrivate(Ident),
|
||||
UnusedMacroDefinition(Symbol),
|
||||
MacroRuleNeverUsed(usize, Symbol),
|
||||
UnstableFeature(String),
|
||||
AvoidUsingIntelSyntax,
|
||||
AvoidUsingAttSyntax,
|
||||
IncompleteInclude,
|
||||
UnnameableTestItems,
|
||||
DuplicateMacroAttribute,
|
||||
CfgAttrNoAttributes,
|
||||
CrateTypeInCfgAttr,
|
||||
CrateNameInCfgAttr,
|
||||
MissingFragmentSpecifier,
|
||||
MetaVariableStillRepeating(MacroRulesNormalizedIdent),
|
||||
MetaVariableWrongOperator,
|
||||
DuplicateMatcherBinding,
|
||||
UnknownMacroVariable(MacroRulesNormalizedIdent),
|
||||
// FIXME: combine with UnusedExternCrate?
|
||||
UnusedExternCrate2 {
|
||||
extern_crate: Symbol,
|
||||
local_crate: Symbol,
|
||||
},
|
||||
WasmCAbi,
|
||||
IllFormedAttributeInput {
|
||||
suggestions: Vec<String>,
|
||||
},
|
||||
InnerAttributeUnstable {
|
||||
is_macro: bool,
|
||||
},
|
||||
}
|
||||
|
||||
@ -745,16 +781,6 @@ pub fn take(&mut self, id: NodeId) -> Vec<BufferedEarlyLint> {
|
||||
self.map.swap_remove(&id).unwrap_or_default()
|
||||
}
|
||||
|
||||
pub fn buffer_lint(
|
||||
&mut self,
|
||||
lint: &'static Lint,
|
||||
id: NodeId,
|
||||
sp: impl Into<MultiSpan>,
|
||||
msg: impl Into<DiagMessage>,
|
||||
) {
|
||||
self.add_lint(lint, id, sp.into(), BuiltinLintDiag::Normal(msg.into()))
|
||||
}
|
||||
|
||||
pub fn buffer_lint_with_diagnostic(
|
||||
&mut self,
|
||||
lint: &'static Lint,
|
||||
|
@ -284,8 +284,6 @@ metadata_unsupported_abi =
|
||||
metadata_unsupported_abi_i686 =
|
||||
ABI not supported by `#[link(kind = "raw-dylib")]` on i686
|
||||
|
||||
metadata_wasm_c_abi =
|
||||
older versions of the `wasm-bindgen` crate will be incompatible with future versions of Rust; please update to `wasm-bindgen` v0.2.88
|
||||
metadata_wasm_import_form =
|
||||
wasm import module must be of the form `wasm_import_module = "string"`
|
||||
|
||||
|
@ -20,7 +20,7 @@
|
||||
use rustc_middle::ty::{TyCtxt, TyCtxtFeed};
|
||||
use rustc_session::config::{self, CrateType, ExternLocation};
|
||||
use rustc_session::cstore::{CrateDepKind, CrateSource, ExternCrate, ExternCrateSource};
|
||||
use rustc_session::lint;
|
||||
use rustc_session::lint::{self, BuiltinLintDiag};
|
||||
use rustc_session::output::validate_crate_name;
|
||||
use rustc_session::search_paths::PathKind;
|
||||
use rustc_span::edition::Edition;
|
||||
@ -974,15 +974,14 @@ fn report_unused_deps(&mut self, krate: &ast::Crate) {
|
||||
continue;
|
||||
}
|
||||
|
||||
self.sess.psess.buffer_lint(
|
||||
self.sess.psess.buffer_lint_with_diagnostic(
|
||||
lint::builtin::UNUSED_CRATE_DEPENDENCIES,
|
||||
span,
|
||||
ast::CRATE_NODE_ID,
|
||||
format!(
|
||||
"external crate `{}` unused in `{}`: remove the dependency or add `use {} as _;`",
|
||||
name,
|
||||
self.tcx.crate_name(LOCAL_CRATE),
|
||||
name),
|
||||
BuiltinLintDiag::UnusedExternCrate2 {
|
||||
extern_crate: name_interned,
|
||||
local_crate: self.tcx.crate_name(LOCAL_CRATE),
|
||||
},
|
||||
);
|
||||
}
|
||||
}
|
||||
@ -1016,11 +1015,11 @@ fn report_future_incompatible_deps(&self, krate: &ast::Crate) {
|
||||
// Make a point span rather than covering the whole file
|
||||
let span = krate.spans.inner_span.shrink_to_lo();
|
||||
|
||||
self.sess.psess.buffer_lint(
|
||||
self.sess.psess.buffer_lint_with_diagnostic(
|
||||
lint::builtin::WASM_C_ABI,
|
||||
span,
|
||||
ast::CRATE_NODE_ID,
|
||||
crate::fluent_generated::metadata_wasm_c_abi,
|
||||
BuiltinLintDiag::WasmCAbi,
|
||||
);
|
||||
}
|
||||
}
|
||||
|
@ -10,6 +10,7 @@
|
||||
use rustc_feature::{AttributeTemplate, BuiltinAttribute, BUILTIN_ATTRIBUTE_MAP};
|
||||
use rustc_session::errors::report_lit_error;
|
||||
use rustc_session::lint::builtin::ILL_FORMED_ATTRIBUTE_INPUT;
|
||||
use rustc_session::lint::BuiltinLintDiag;
|
||||
use rustc_session::parse::ParseSess;
|
||||
use rustc_span::{sym, Span, Symbol};
|
||||
|
||||
@ -176,37 +177,26 @@ fn emit_malformed_attribute(
|
||||
};
|
||||
|
||||
let error_msg = format!("malformed `{name}` attribute input");
|
||||
let mut msg = "attribute must be of the form ".to_owned();
|
||||
let mut suggestions = vec![];
|
||||
let mut first = true;
|
||||
let inner = if style == ast::AttrStyle::Inner { "!" } else { "" };
|
||||
if template.word {
|
||||
first = false;
|
||||
let code = format!("#{inner}[{name}]");
|
||||
msg.push_str(&format!("`{code}`"));
|
||||
suggestions.push(code);
|
||||
suggestions.push(format!("#{inner}[{name}]"));
|
||||
}
|
||||
if let Some(descr) = template.list {
|
||||
if !first {
|
||||
msg.push_str(" or ");
|
||||
}
|
||||
first = false;
|
||||
let code = format!("#{inner}[{name}({descr})]");
|
||||
msg.push_str(&format!("`{code}`"));
|
||||
suggestions.push(code);
|
||||
suggestions.push(format!("#{inner}[{name}({descr})]"));
|
||||
}
|
||||
if let Some(descr) = template.name_value_str {
|
||||
if !first {
|
||||
msg.push_str(" or ");
|
||||
suggestions.push(format!("#{inner}[{name} = \"{descr}\"]"));
|
||||
}
|
||||
let code = format!("#{inner}[{name} = \"{descr}\"]");
|
||||
msg.push_str(&format!("`{code}`"));
|
||||
suggestions.push(code);
|
||||
}
|
||||
suggestions.sort();
|
||||
if should_warn(name) {
|
||||
psess.buffer_lint(ILL_FORMED_ATTRIBUTE_INPUT, span, ast::CRATE_NODE_ID, msg);
|
||||
psess.buffer_lint_with_diagnostic(
|
||||
ILL_FORMED_ATTRIBUTE_INPUT,
|
||||
span,
|
||||
ast::CRATE_NODE_ID,
|
||||
BuiltinLintDiag::IllFormedAttributeInput { suggestions: suggestions.clone() },
|
||||
);
|
||||
} else {
|
||||
suggestions.sort();
|
||||
psess
|
||||
.dcx
|
||||
.struct_span_err(span, error_msg)
|
||||
|
@ -388,14 +388,11 @@ pub(crate) fn check_unused(&mut self, krate: &ast::Crate) {
|
||||
{
|
||||
if let ImportKind::MacroUse { .. } = import.kind {
|
||||
if !import.span.is_dummy() {
|
||||
self.lint_buffer.buffer_lint(
|
||||
self.lint_buffer.buffer_lint_with_diagnostic(
|
||||
MACRO_USE_EXTERN_CRATE,
|
||||
import.root_id,
|
||||
import.span,
|
||||
"deprecated `#[macro_use]` attribute used to \
|
||||
import macros should be replaced at use sites \
|
||||
with a `use` item to import the macro \
|
||||
instead",
|
||||
BuiltinLintDiag::MacroUseDeprecated,
|
||||
);
|
||||
}
|
||||
}
|
||||
@ -412,8 +409,12 @@ pub(crate) fn check_unused(&mut self, krate: &ast::Crate) {
|
||||
}
|
||||
}
|
||||
ImportKind::MacroUse { .. } => {
|
||||
let msg = "unused `#[macro_use]` import";
|
||||
self.lint_buffer.buffer_lint(UNUSED_IMPORTS, import.root_id, import.span, msg);
|
||||
self.lint_buffer.buffer_lint_with_diagnostic(
|
||||
UNUSED_IMPORTS,
|
||||
import.root_id,
|
||||
import.span,
|
||||
BuiltinLintDiag::UnusedMacroUse,
|
||||
);
|
||||
}
|
||||
_ => {}
|
||||
}
|
||||
|
@ -1246,16 +1246,11 @@ fn finalize_import(&mut self, import: Import<'a>) -> Option<UnresolvedImportErro
|
||||
if !any_successful_reexport {
|
||||
let (ns, binding) = reexport_error.unwrap();
|
||||
if pub_use_of_private_extern_crate_hack(import, binding) {
|
||||
let msg = format!(
|
||||
"extern crate `{ident}` is private, and cannot be \
|
||||
re-exported (error E0365), consider declaring with \
|
||||
`pub`"
|
||||
);
|
||||
self.lint_buffer.buffer_lint(
|
||||
self.lint_buffer.buffer_lint_with_diagnostic(
|
||||
PUB_USE_OF_PRIVATE_EXTERN_CRATE,
|
||||
import_id,
|
||||
import.span,
|
||||
msg,
|
||||
BuiltinLintDiag::PrivateExternCrateReexport(ident),
|
||||
);
|
||||
} else {
|
||||
if ns == TypeNS {
|
||||
|
@ -24,7 +24,7 @@
|
||||
use rustc_middle::ty::DelegationFnSig;
|
||||
use rustc_middle::{bug, span_bug};
|
||||
use rustc_session::config::{CrateType, ResolveDocLinks};
|
||||
use rustc_session::lint;
|
||||
use rustc_session::lint::{self, BuiltinLintDiag};
|
||||
use rustc_session::parse::feature_err;
|
||||
use rustc_span::source_map::{respan, Spanned};
|
||||
use rustc_span::symbol::{kw, sym, Ident, Symbol};
|
||||
@ -4815,7 +4815,12 @@ pub(crate) fn late_resolve_crate(&mut self, krate: &Crate) {
|
||||
late_resolution_visitor.resolve_doc_links(&krate.attrs, MaybeExported::Ok(CRATE_NODE_ID));
|
||||
visit::walk_crate(&mut late_resolution_visitor, krate);
|
||||
for (id, span) in late_resolution_visitor.diag_metadata.unused_labels.iter() {
|
||||
self.lint_buffer.buffer_lint(lint::builtin::UNUSED_LABELS, *id, *span, "unused label");
|
||||
self.lint_buffer.buffer_lint_with_diagnostic(
|
||||
lint::builtin::UNUSED_LABELS,
|
||||
*id,
|
||||
*span,
|
||||
BuiltinLintDiag::UnusedLabel,
|
||||
);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -51,7 +51,7 @@
|
||||
use rustc_middle::ty::{ResolverGlobalCtxt, ResolverOutputs, TyCtxt, TyCtxtFeed};
|
||||
use rustc_query_system::ich::StableHashingContext;
|
||||
use rustc_session::lint::builtin::PRIVATE_MACRO_USE;
|
||||
use rustc_session::lint::LintBuffer;
|
||||
use rustc_session::lint::{BuiltinLintDiag, LintBuffer};
|
||||
use rustc_span::hygiene::{ExpnId, LocalExpnId, MacroKind, SyntaxContext, Transparency};
|
||||
use rustc_span::symbol::{kw, sym, Ident, Symbol};
|
||||
use rustc_span::{Span, DUMMY_SP};
|
||||
@ -1860,8 +1860,12 @@ fn record_use_inner(
|
||||
}
|
||||
if let NameBindingKind::Import { import, binding } = used_binding.kind {
|
||||
if let ImportKind::MacroUse { warn_private: true } = import.kind {
|
||||
let msg = format!("macro `{ident}` is private");
|
||||
self.lint_buffer().buffer_lint(PRIVATE_MACRO_USE, import.root_id, ident.span, msg);
|
||||
self.lint_buffer().buffer_lint_with_diagnostic(
|
||||
PRIVATE_MACRO_USE,
|
||||
import.root_id,
|
||||
ident.span,
|
||||
BuiltinLintDiag::MacroIsPrivate(ident),
|
||||
);
|
||||
}
|
||||
// Avoid marking `extern crate` items that refer to a name from extern prelude,
|
||||
// but not introduce it, as used if they are accessed from lexical scope.
|
||||
|
@ -311,11 +311,11 @@ fn record_macro_rule_usage(&mut self, id: NodeId, rule_i: usize) {
|
||||
|
||||
fn check_unused_macros(&mut self) {
|
||||
for (_, &(node_id, ident)) in self.unused_macros.iter() {
|
||||
self.lint_buffer.buffer_lint(
|
||||
self.lint_buffer.buffer_lint_with_diagnostic(
|
||||
UNUSED_MACROS,
|
||||
node_id,
|
||||
ident.span,
|
||||
format!("unused macro definition: `{}`", ident.name),
|
||||
BuiltinLintDiag::UnusedMacroDefinition(ident.name),
|
||||
);
|
||||
}
|
||||
for (&(def_id, arm_i), &(ident, rule_span)) in self.unused_macro_rules.iter() {
|
||||
@ -324,11 +324,11 @@ fn check_unused_macros(&mut self) {
|
||||
continue;
|
||||
}
|
||||
let node_id = self.def_id_to_node_id[def_id];
|
||||
self.lint_buffer.buffer_lint(
|
||||
self.lint_buffer.buffer_lint_with_diagnostic(
|
||||
UNUSED_MACRO_RULES,
|
||||
node_id,
|
||||
rule_span,
|
||||
format!("rule #{} of macro `{}` is never used", arm_i + 1, ident.name),
|
||||
BuiltinLintDiag::MacroRuleNeverUsed(arm_i, ident.name),
|
||||
);
|
||||
}
|
||||
}
|
||||
@ -552,14 +552,25 @@ fn smart_resolve_macro_path(
|
||||
|
||||
// We are trying to avoid reporting this error if other related errors were reported.
|
||||
if res != Res::Err && inner_attr && !self.tcx.features().custom_inner_attributes {
|
||||
let msg = match res {
|
||||
Res::Def(..) => "inner macro attributes are unstable",
|
||||
Res::NonMacroAttr(..) => "custom inner attributes are unstable",
|
||||
let is_macro = match res {
|
||||
Res::Def(..) => true,
|
||||
Res::NonMacroAttr(..) => false,
|
||||
_ => unreachable!(),
|
||||
};
|
||||
if soft_custom_inner_attributes_gate {
|
||||
self.tcx.sess.psess.buffer_lint(SOFT_UNSTABLE, path.span, node_id, msg);
|
||||
self.tcx.sess.psess.buffer_lint_with_diagnostic(
|
||||
SOFT_UNSTABLE,
|
||||
path.span,
|
||||
node_id,
|
||||
BuiltinLintDiag::InnerAttributeUnstable { is_macro },
|
||||
);
|
||||
} else {
|
||||
// FIXME: deduplicate with rustc_lint (`BuiltinLintDiag::InnerAttributeUnstable`)
|
||||
let msg = if is_macro {
|
||||
"inner macro attributes are unstable"
|
||||
} else {
|
||||
"custom inner attributes are unstable"
|
||||
};
|
||||
feature_err(&self.tcx.sess, sym::custom_inner_attributes, path.span, msg).emit();
|
||||
}
|
||||
}
|
||||
@ -572,17 +583,13 @@ fn smart_resolve_macro_path(
|
||||
let distance =
|
||||
edit_distance(attribute.ident.name.as_str(), sym::on_unimplemented.as_str(), 5);
|
||||
|
||||
let help = if distance.is_some() {
|
||||
BuiltinLintDiag::MaybeTypo { span: attribute.span(), name: sym::on_unimplemented }
|
||||
} else {
|
||||
BuiltinLintDiag::Normal
|
||||
};
|
||||
let typo_name = distance.map(|_| sym::on_unimplemented);
|
||||
|
||||
self.tcx.sess.psess.buffer_lint_with_diagnostic(
|
||||
UNKNOWN_OR_MALFORMED_DIAGNOSTIC_ATTRIBUTES,
|
||||
attribute.span(),
|
||||
node_id,
|
||||
"unknown diagnostic attribute",
|
||||
help,
|
||||
BuiltinLintDiag::UnknownDiagnosticAttribute { span: attribute.span(), typo_name },
|
||||
);
|
||||
}
|
||||
|
||||
@ -835,8 +842,14 @@ fn check_stability_and_deprecation(
|
||||
let allowed_by_implication = implied_by.is_some_and(|feature| is_allowed(feature));
|
||||
if !is_allowed(feature) && !allowed_by_implication {
|
||||
let lint_buffer = &mut self.lint_buffer;
|
||||
let soft_handler =
|
||||
|lint, span, msg: String| lint_buffer.buffer_lint(lint, node_id, span, msg);
|
||||
let soft_handler = |lint, span, msg: String| {
|
||||
lint_buffer.buffer_lint_with_diagnostic(
|
||||
lint,
|
||||
node_id,
|
||||
span,
|
||||
BuiltinLintDiag::UnstableFeature(msg),
|
||||
)
|
||||
};
|
||||
stability::report_unstable(
|
||||
self.tcx.sess,
|
||||
feature,
|
||||
|
@ -300,23 +300,6 @@ pub fn clone_source_map(&self) -> Lrc<SourceMap> {
|
||||
self.source_map.clone()
|
||||
}
|
||||
|
||||
pub fn buffer_lint(
|
||||
&self,
|
||||
lint: &'static Lint,
|
||||
span: impl Into<MultiSpan>,
|
||||
node_id: NodeId,
|
||||
msg: impl Into<DiagMessage>,
|
||||
) {
|
||||
self.buffered_lints.with_lock(|buffered_lints| {
|
||||
buffered_lints.push(BufferedEarlyLint {
|
||||
span: span.into(),
|
||||
node_id,
|
||||
lint_id: LintId::of(lint),
|
||||
diagnostic: BuiltinLintDiag::Normal(msg.into()),
|
||||
});
|
||||
});
|
||||
}
|
||||
|
||||
pub fn buffer_lint_with_diagnostic(
|
||||
&self,
|
||||
lint: &'static Lint,
|
||||
|
Loading…
Reference in New Issue
Block a user