diff --git a/compiler/rustc_borrowck/src/lib.rs b/compiler/rustc_borrowck/src/lib.rs index 2fc057ae38823..bd46a40c02da1 100644 --- a/compiler/rustc_borrowck/src/lib.rs +++ b/compiler/rustc_borrowck/src/lib.rs @@ -27,7 +27,6 @@ use rustc_abi::FieldIdx; use rustc_data_structures::frozen::Frozen; use rustc_data_structures::fx::{FxIndexMap, FxIndexSet}; use rustc_data_structures::graph::dominators::Dominators; -use rustc_errors::LintDiagnostic; use rustc_hir as hir; use rustc_hir::CRATE_HIR_ID; use rustc_hir::def_id::LocalDefId; @@ -715,7 +714,7 @@ impl<'tcx> Deref for BorrowckInferCtxt<'tcx> { } } -struct MirBorrowckCtxt<'a, 'infcx, 'tcx> { +pub(crate) struct MirBorrowckCtxt<'a, 'infcx, 'tcx> { root_cx: &'a mut BorrowCheckRootCtxt<'tcx>, infcx: &'infcx BorrowckInferCtxt<'tcx>, body: &'a Body<'tcx>, @@ -1428,13 +1427,15 @@ impl<'a, 'tcx> MirBorrowckCtxt<'a, '_, 'tcx> { borrow, Some((WriteKind::StorageDeadOrDrop, place)), ); - this.infcx.tcx.node_span_lint( + this.infcx.tcx.emit_node_span_lint( TAIL_EXPR_DROP_ORDER, CRATE_HIR_ID, borrowed, - |diag| { - session_diagnostics::TailExprDropOrder { borrowed }.decorate_lint(diag); - explain.add_explanation_to_diagnostic(&this, diag, "", None, None); + session_diagnostics::TailExprDropOrder { + borrowed, + callback: |diag| { + explain.add_explanation_to_diagnostic(&this, diag, "", None, None); + }, }, ); // We may stop at the first case diff --git a/compiler/rustc_borrowck/src/session_diagnostics.rs b/compiler/rustc_borrowck/src/session_diagnostics.rs index eaa41ce1caacf..fea5c2b990372 100644 --- a/compiler/rustc_borrowck/src/session_diagnostics.rs +++ b/compiler/rustc_borrowck/src/session_diagnostics.rs @@ -1,6 +1,6 @@ -use rustc_errors::MultiSpan; use rustc_errors::codes::*; -use rustc_macros::{Diagnostic, LintDiagnostic, Subdiagnostic}; +use rustc_errors::{Diag, DiagCtxtHandle, Diagnostic, Level, MultiSpan}; +use rustc_macros::{Diagnostic, Subdiagnostic}; use rustc_middle::ty::{GenericArg, Ty}; use rustc_span::Span; @@ -595,9 +595,20 @@ pub(crate) struct SimdIntrinsicArgConst { pub intrinsic: String, } -#[derive(LintDiagnostic)] -#[diag("relative drop order changing in Rust 2024")] -pub(crate) struct TailExprDropOrder { - #[label("this temporary value will be dropped at the end of the block")] +pub(crate) struct TailExprDropOrder)> { pub borrowed: Span, + pub callback: F, +} + +impl<'a, F: FnOnce(&mut Diag<'_, ()>)> Diagnostic<'a, ()> for TailExprDropOrder { + fn into_diag(self, dcx: DiagCtxtHandle<'a>, level: Level) -> Diag<'a, ()> { + let Self { borrowed, callback } = self; + let mut diag = Diag::new(dcx, level, "relative drop order changing in Rust 2024") + .with_span_label( + borrowed, + "this temporary value will be dropped at the end of the block", + ); + callback(&mut diag); + diag + } } diff --git a/compiler/rustc_lint/src/builtin.rs b/compiler/rustc_lint/src/builtin.rs index 3f511fd65a416..e7b821a400ea4 100644 --- a/compiler/rustc_lint/src/builtin.rs +++ b/compiler/rustc_lint/src/builtin.rs @@ -22,7 +22,7 @@ use rustc_ast::visit::{FnCtxt, FnKind}; use rustc_ast::{self as ast, *}; use rustc_ast_pretty::pprust::expr_to_string; use rustc_attr_parsing::AttributeParser; -use rustc_errors::{Applicability, LintDiagnostic, msg}; +use rustc_errors::{Applicability, Diagnostic, msg}; use rustc_feature::GateIssue; use rustc_hir::attrs::{AttributeKind, DocAttribute}; use rustc_hir::def::{DefKind, Res}; @@ -235,7 +235,7 @@ impl UnsafeCode { &self, cx: &EarlyContext<'_>, span: Span, - decorate: impl for<'a> LintDiagnostic<'a, ()>, + decorate: impl for<'a> Diagnostic<'a, ()>, ) { // This comes from a macro that has `#[allow_internal_unsafe]`. if span.allows_unsafe() { diff --git a/compiler/rustc_lint/src/context.rs b/compiler/rustc_lint/src/context.rs index 561bdd1a2db67..971170aaba304 100644 --- a/compiler/rustc_lint/src/context.rs +++ b/compiler/rustc_lint/src/context.rs @@ -11,7 +11,7 @@ use rustc_ast::util::parser::ExprPrecedence; use rustc_data_structures::fx::FxIndexMap; use rustc_data_structures::sync; use rustc_data_structures::unord::UnordMap; -use rustc_errors::{Diag, LintBuffer, LintDiagnostic, MultiSpan}; +use rustc_errors::{Diag, Diagnostic, LintBuffer, LintDiagnostic, MultiSpan}; use rustc_feature::Features; use rustc_hir::def::Res; use rustc_hir::def_id::{CrateNum, DefId}; @@ -522,17 +522,28 @@ pub trait LintContext { decorate: impl for<'a, 'b> FnOnce(&'b mut Diag<'a, ()>), ); + // FIXME: These methods should not take an Into -- instead, callers should need to + // set the span in their `decorate` function (preferably using set_span). + /// Emit a lint at the appropriate level, with an optional associated span. + /// + /// [`lint_level`]: rustc_middle::lint::lint_level#decorate-signature + #[track_caller] + fn opt_span_diag_lint>( + &self, + lint: &'static Lint, + span: Option, + decorate: impl for<'a> Diagnostic<'a, ()>, + ); + /// Emit a lint at `span` from a lint struct (some type that implements `LintDiagnostic`, /// typically generated by `#[derive(LintDiagnostic)]`). fn emit_span_lint>( &self, lint: &'static Lint, span: S, - decorator: impl for<'a> LintDiagnostic<'a, ()>, + decorator: impl for<'a> Diagnostic<'a, ()>, ) { - self.opt_span_lint(lint, Some(span), |lint| { - decorator.decorate_lint(lint); - }); + self.opt_span_diag_lint(lint, Some(span), decorator); } /// Emit a lint at `span` from a lazily-constructed lint struct (some type that implements @@ -570,6 +581,12 @@ pub trait LintContext { }); } + /// Emit a lint from a lint struct (some type that implements `LintDiagnostic`, typically + /// generated by `#[derive(LintDiagnostic)]`). + fn emit_diag_lint(&self, lint: &'static Lint, decorator: impl for<'a> Diagnostic<'a, ()>) { + self.opt_span_diag_lint(lint, None as Option, decorator); + } + /// Emit a lint at the appropriate level, with no associated span. /// /// [`lint_level`]: rustc_middle::lint::lint_level#decorate-signature @@ -644,6 +661,20 @@ impl<'tcx> LintContext for LateContext<'tcx> { } } + fn opt_span_diag_lint>( + &self, + lint: &'static Lint, + span: Option, + decorate: impl for<'a> Diagnostic<'a, ()>, + ) { + let hir_id = self.last_node_with_lint_attrs; + + match span { + Some(s) => self.tcx.emit_node_span_lint(lint, hir_id, s, decorate), + None => self.tcx.emit_node_lint(lint, hir_id, decorate), + } + } + fn get_lint_level(&self, lint: &'static Lint) -> LevelAndSource { self.tcx.lint_level_at_node(lint, self.last_node_with_lint_attrs) } @@ -664,6 +695,15 @@ impl LintContext for EarlyContext<'_> { self.builder.opt_span_lint(lint, span.map(|s| s.into()), decorate) } + fn opt_span_diag_lint>( + &self, + lint: &'static Lint, + span: Option, + decorator: impl for<'a> Diagnostic<'a, ()>, + ) { + self.builder.opt_span_diag_lint(lint, span.map(|s| s.into()), decorator) + } + fn get_lint_level(&self, lint: &'static Lint) -> LevelAndSource { self.builder.lint_level(lint) } diff --git a/compiler/rustc_lint/src/dangling.rs b/compiler/rustc_lint/src/dangling.rs index 448c0ded637c6..d162ae4b77647 100644 --- a/compiler/rustc_lint/src/dangling.rs +++ b/compiler/rustc_lint/src/dangling.rs @@ -269,7 +269,6 @@ fn lint_expr(cx: &LateContext<'_>, expr: &Expr<'_>) { && let Some(fn_id) = cx.typeck_results().type_dependent_def_id(expr.hir_id) && find_attr!(cx.tcx, fn_id, RustcAsPtr(_)) { - // FIXME: use `emit_node_lint` when `#[primary_span]` is added. cx.tcx.emit_node_span_lint( DANGLING_POINTERS_FROM_TEMPORARIES, expr.hir_id, diff --git a/compiler/rustc_lint/src/internal.rs b/compiler/rustc_lint/src/internal.rs index 0723395d6d1cd..cb4c5077a5263 100644 --- a/compiler/rustc_lint/src/internal.rs +++ b/compiler/rustc_lint/src/internal.rs @@ -638,7 +638,7 @@ impl EarlyLintPass for BadUseOfFindAttr { cx.emit_span_lint( BAD_USE_OF_FIND_ATTR, segment.span(), - AttributeKindInFindAttr {}, + AttributeKindInFindAttr, ); } } diff --git a/compiler/rustc_lint/src/levels.rs b/compiler/rustc_lint/src/levels.rs index a3376ad967e06..a134b623d7bd4 100644 --- a/compiler/rustc_lint/src/levels.rs +++ b/compiler/rustc_lint/src/levels.rs @@ -2,7 +2,7 @@ use rustc_ast::attr::AttributeExt; use rustc_ast_pretty::pprust; use rustc_data_structures::fx::{FxHashSet, FxIndexMap}; use rustc_data_structures::unord::UnordSet; -use rustc_errors::{Diag, LintDiagnostic, MultiSpan, msg}; +use rustc_errors::{Diag, Diagnostic, MultiSpan, msg}; use rustc_feature::{Features, GateIssue}; use rustc_hir::HirId; use rustc_hir::intravisit::{self, Visitor}; @@ -10,8 +10,8 @@ use rustc_index::IndexVec; use rustc_middle::bug; use rustc_middle::hir::nested_filter; use rustc_middle::lint::{ - LevelAndSource, LintExpectation, LintLevelSource, ShallowLintLevelMap, lint_level, - reveal_actual_level, + LevelAndSource, LintExpectation, LintLevelSource, ShallowLintLevelMap, diag_lint_level, + lint_level, reveal_actual_level, }; use rustc_middle::query::Providers; use rustc_middle::ty::{RegisteredTools, TyCtxt}; @@ -822,8 +822,11 @@ impl<'s, P: LintLevelsProvider> LintLevelsBuilder<'s, P> { RenamedLintSuggestion::WithSpan { suggestion: sp, replace }; let name = tool_ident.map(|tool| format!("{tool}::{name}")).unwrap_or(name); - let lint = RenamedLint { name: name.as_str(), replace, suggestion }; - self.emit_span_lint(RENAMED_AND_REMOVED_LINTS, sp.into(), lint); + self.emit_span_lint( + RENAMED_AND_REMOVED_LINTS, + sp.into(), + RenamedLint { name: name.as_str(), replace, suggestion }, + ); } // If this lint was renamed, apply the new lint instead of ignoring the @@ -844,8 +847,11 @@ impl<'s, P: LintLevelsProvider> LintLevelsBuilder<'s, P> { if self.lint_added_lints { let name = tool_ident.map(|tool| format!("{tool}::{name}")).unwrap_or(name); - let lint = RemovedLint { name: name.as_str(), reason }; - self.emit_span_lint(RENAMED_AND_REMOVED_LINTS, sp.into(), lint); + self.emit_span_lint( + RENAMED_AND_REMOVED_LINTS, + sp.into(), + RemovedLint { name: name.as_str(), reason }, + ); } continue; } @@ -861,8 +867,11 @@ impl<'s, P: LintLevelsProvider> LintLevelsBuilder<'s, P> { from_rustc, } }); - let lint = UnknownLint { name, suggestion }; - self.emit_span_lint(UNKNOWN_LINTS, sp.into(), lint); + self.emit_span_lint( + UNKNOWN_LINTS, + sp.into(), + UnknownLint { name, suggestion }, + ); } continue; } @@ -967,8 +976,6 @@ impl<'s, P: LintLevelsProvider> LintLevelsBuilder<'s, P> { /// Used to emit a lint-related diagnostic based on the current state of /// this lint context. - /// - /// [`lint_level`]: rustc_middle::lint::lint_level#decorate-signature #[track_caller] pub(crate) fn opt_span_lint( &self, @@ -980,25 +987,34 @@ impl<'s, P: LintLevelsProvider> LintLevelsBuilder<'s, P> { lint_level(self.sess, lint, level, span, decorate) } + /// Used to emit a lint-related diagnostic based on the current state of + /// this lint context. + #[track_caller] + pub(crate) fn opt_span_diag_lint( + &self, + lint: &'static Lint, + span: Option, + decorator: impl for<'a> Diagnostic<'a, ()>, + ) { + let level = self.lint_level(lint); + diag_lint_level(self.sess, lint, level, span, decorator) + } + #[track_caller] pub fn emit_span_lint( &self, lint: &'static Lint, span: MultiSpan, - decorate: impl for<'a> LintDiagnostic<'a, ()>, + decorator: impl for<'a> Diagnostic<'a, ()>, ) { let level = self.lint_level(lint); - lint_level(self.sess, lint, level, Some(span), |lint| { - decorate.decorate_lint(lint); - }); + diag_lint_level(self.sess, lint, level, Some(span), decorator); } #[track_caller] - pub fn emit_lint(&self, lint: &'static Lint, decorate: impl for<'a> LintDiagnostic<'a, ()>) { + pub fn emit_lint(&self, lint: &'static Lint, decorator: impl for<'a> Diagnostic<'a, ()>) { let level = self.lint_level(lint); - lint_level(self.sess, lint, level, None, |lint| { - decorate.decorate_lint(lint); - }); + diag_lint_level(self.sess, lint, level, None, decorator); } } diff --git a/compiler/rustc_lint/src/lints.rs b/compiler/rustc_lint/src/lints.rs index 1d8f2d4e3442d..0461d19d544c6 100644 --- a/compiler/rustc_lint/src/lints.rs +++ b/compiler/rustc_lint/src/lints.rs @@ -5,8 +5,8 @@ use std::num::NonZero; use rustc_errors::codes::*; use rustc_errors::{ Applicability, Diag, DiagArgValue, DiagCtxtHandle, DiagMessage, DiagStyledString, Diagnostic, - ElidedLifetimeInPathSubdiag, EmissionGuarantee, Level, LintDiagnostic, MultiSpan, - Subdiagnostic, SuggestionStyle, msg, + ElidedLifetimeInPathSubdiag, EmissionGuarantee, Level, MultiSpan, Subdiagnostic, + SuggestionStyle, msg, }; use rustc_hir as hir; use rustc_hir::def_id::DefId; @@ -24,7 +24,7 @@ use crate::errors::{OverruledAttributeSub, RequestedLevel}; use crate::lifetime_syntax::LifetimeSyntaxCategories; // array_into_iter.rs -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag( "this method call resolves to `<&{$target} as IntoIterator>::into_iter` (due to backwards compatibility), but will resolve to `<{$target} as IntoIterator>::into_iter` in Rust {$edition}" )] @@ -65,7 +65,7 @@ pub(crate) enum ShadowedIntoIterDiagSub { } // autorefs.rs -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("implicit autoref creates a reference to the dereference of a raw pointer")] #[note( "creating a reference requires the pointer target to be valid and imposes aliasing requirements" @@ -119,7 +119,7 @@ pub(crate) struct ImplicitUnsafeAutorefsSuggestion { } // builtin.rs -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("denote infinite loops with `loop {\"{\"} ... {\"}\"}`")] pub(crate) struct BuiltinWhileTrue { #[suggestion( @@ -132,7 +132,7 @@ pub(crate) struct BuiltinWhileTrue { pub replace: String, } -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("the `{$ident}:` in this pattern is redundant")] pub(crate) struct BuiltinNonShorthandFieldPatterns { pub ident: Ident, @@ -145,7 +145,7 @@ pub(crate) struct BuiltinNonShorthandFieldPatterns { pub prefix: &'static str, } -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] pub(crate) enum BuiltinUnsafe { #[diag( "`allow_internal_unsafe` allows defining macros using unsafe without triggering the `unsafe_code` lint at their call site" @@ -210,14 +210,14 @@ pub(crate) enum BuiltinUnsafe { GlobalAsm, } -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("missing documentation for {$article} {$desc}")] pub(crate) struct BuiltinMissingDoc<'a> { pub article: &'a str, pub desc: &'a str, } -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("type could implement `Copy`; consider adding `impl Copy`")] pub(crate) struct BuiltinMissingCopyImpl; @@ -227,14 +227,18 @@ pub(crate) struct BuiltinMissingDebugImpl<'a> { } // Needed for def_path_str -impl<'a> LintDiagnostic<'a, ()> for BuiltinMissingDebugImpl<'_> { - fn decorate_lint<'b>(self, diag: &'b mut rustc_errors::Diag<'a, ()>) { - diag.primary_message(msg!("type does not implement `{$debug}`; consider adding `#[derive(Debug)]` or a manual implementation")); - diag.arg("debug", self.tcx.def_path_str(self.def_id)); +impl<'a> Diagnostic<'a, ()> for BuiltinMissingDebugImpl<'_> { + fn into_diag(self, dcx: DiagCtxtHandle<'a>, level: Level) -> Diag<'a, ()> { + let Self { tcx, def_id } = self; + Diag::new( + dcx, + level, + msg!("type does not implement `{$debug}`; consider adding `#[derive(Debug)]` or a manual implementation"), + ).with_arg("debug", tcx.def_path_str(def_id)) } } -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("anonymous parameters are deprecated and will be removed in the next edition")] pub(crate) struct BuiltinAnonymousParams<'a> { #[suggestion("try naming the parameter or explicitly ignoring it", code = "_: {ty_snip}")] @@ -242,7 +246,7 @@ pub(crate) struct BuiltinAnonymousParams<'a> { pub ty_snip: &'a str, } -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("unused doc comment")] pub(crate) struct BuiltinUnusedDocComment<'a> { pub kind: &'a str, @@ -260,7 +264,7 @@ pub(crate) enum BuiltinUnusedDocCommentSub { BlockHelp, } -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("functions generic over types or consts must be mangled")] pub(crate) struct BuiltinNoMangleGeneric { // Use of `#[no_mangle]` suggests FFI intent; correct @@ -274,20 +278,20 @@ pub(crate) struct BuiltinNoMangleGeneric { pub suggestion: Span, } -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("const items should never be `#[no_mangle]`")] pub(crate) struct BuiltinConstNoMangle { #[suggestion("try a static value", code = "pub static ", applicability = "machine-applicable")] pub suggestion: Option, } -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag( "transmuting &T to &mut T is undefined behavior, even if the reference is unused, consider instead using an UnsafeCell" )] pub(crate) struct BuiltinMutablesTransmutes; -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("use of an unstable feature")] pub(crate) struct BuiltinUnstableFeatures; @@ -297,19 +301,20 @@ pub(crate) struct BuiltinUngatedAsyncFnTrackCaller<'a> { pub session: &'a Session, } -impl<'a> LintDiagnostic<'a, ()> for BuiltinUngatedAsyncFnTrackCaller<'_> { - fn decorate_lint<'b>(self, diag: &'b mut Diag<'a, ()>) { - diag.primary_message(msg!("`#[track_caller]` on async functions is a no-op")); - diag.span_label(self.label, msg!("this function will not propagate the caller location")); +impl<'a> Diagnostic<'a, ()> for BuiltinUngatedAsyncFnTrackCaller<'_> { + fn into_diag(self, dcx: DiagCtxtHandle<'a>, level: Level) -> Diag<'a, ()> { + let mut diag = Diag::new(dcx, level, "`#[track_caller]` on async functions is a no-op") + .with_span_label(self.label, "this function will not propagate the caller location"); rustc_session::parse::add_feature_diagnostics( - diag, + &mut diag, self.session, sym::async_fn_track_caller, ); + diag } } -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("unreachable `pub` {$what}")] pub(crate) struct BuiltinUnreachablePub<'a> { pub what: &'a str, @@ -320,7 +325,7 @@ pub(crate) struct BuiltinUnreachablePub<'a> { pub help: bool, } -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("the `expr` fragment specifier will accept more expressions in the 2024 edition")] pub(crate) struct MacroExprFragment2024 { #[suggestion( @@ -340,18 +345,18 @@ pub(crate) struct BuiltinTypeAliasBounds<'hir> { pub ty: Option<&'hir hir::Ty<'hir>>, } -impl<'a> LintDiagnostic<'a, ()> for BuiltinTypeAliasBounds<'_> { - fn decorate_lint<'b>(self, diag: &'b mut Diag<'a, ()>) { - diag.primary_message(if self.in_where_clause { +impl<'a> Diagnostic<'a, ()> for BuiltinTypeAliasBounds<'_> { + fn into_diag(self, dcx: DiagCtxtHandle<'a>, level: Level) -> Diag<'a, ()> { + let mut diag = Diag::new(dcx, level, if self.in_where_clause { msg!("where clauses on type aliases are not enforced") } else { msg!("bounds on generic parameters in type aliases are not enforced") - }); - diag.span_label(self.label, msg!("will not be checked at usage sites of the type alias")); - diag.note(msg!( - "this is a known limitation of the type checker that may be lifted in a future edition. - see issue #112792 for more information" - )); + }) + .with_span_label(self.label, msg!("will not be checked at usage sites of the type alias")) + .with_note(msg!( + "this is a known limitation of the type checker that may be lifted in a future edition. + see issue #112792 for more information" + )); if self.enable_feat_help { diag.help(msg!("add `#![feature(lazy_type_alias)]` to the crate attributes to enable the desired semantics")); } @@ -413,10 +418,11 @@ impl<'a> LintDiagnostic<'a, ()> for BuiltinTypeAliasBounds<'_> { Applicability::HasPlaceholders, ); } + diag } } -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag( "{$predicate_kind_name} bound {$predicate} does not depend on any type or lifetime parameters" )] @@ -425,7 +431,7 @@ pub(crate) struct BuiltinTrivialBounds<'a> { pub predicate: Clause<'a>, } -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("use of a double negation")] #[note( "the prefix `--` could be misinterpreted as a decrement operator which exists in other languages" @@ -445,7 +451,7 @@ pub(crate) struct BuiltinDoubleNegationsAddParens { pub end_span: Span, } -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] pub(crate) enum BuiltinEllipsisInclusiveRangePatternsLint { #[diag("`...` range patterns are deprecated")] Parenthesise { @@ -469,7 +475,7 @@ pub(crate) enum BuiltinEllipsisInclusiveRangePatternsLint { }, } -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("`{$kw}` is a keyword in the {$next} edition")] pub(crate) struct BuiltinKeywordIdents { pub kw: Ident, @@ -483,7 +489,7 @@ pub(crate) struct BuiltinKeywordIdents { pub prefix: &'static str, } -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("outlives requirements can be inferred")] pub(crate) struct BuiltinExplicitOutlives { pub count: usize, @@ -505,7 +511,7 @@ pub(crate) struct BuiltinExplicitOutlivesSuggestion { pub applicability: Applicability, } -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag( "the feature `{$name}` is incomplete and may not be safe to use and/or cause compiler crashes" )] @@ -517,7 +523,7 @@ pub(crate) struct BuiltinIncompleteFeatures { pub help: Option, } -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("the feature `{$name}` is internal to the compiler or standard library")] #[note("using it is strongly discouraged")] pub(crate) struct BuiltinInternalFeatures { @@ -542,11 +548,11 @@ pub(crate) struct BuiltinUnpermittedTypeInit<'a> { pub tcx: TyCtxt<'a>, } -impl<'a> LintDiagnostic<'a, ()> for BuiltinUnpermittedTypeInit<'_> { - fn decorate_lint<'b>(self, diag: &'b mut Diag<'a, ()>) { - diag.primary_message(self.msg); - diag.arg("ty", self.ty); - diag.span_label(self.label, msg!("this code causes undefined behavior when executed")); +impl<'a> Diagnostic<'a, ()> for BuiltinUnpermittedTypeInit<'_> { + fn into_diag(self, dcx: DiagCtxtHandle<'a>, level: Level) -> Diag<'a, ()> { + let mut diag = Diag::new(dcx, level, self.msg) + .with_arg("ty", self.ty) + .with_span_label(self.label, msg!("this code causes undefined behavior when executed")); if let InhabitedPredicate::True = self.ty.inhabited_predicate(self.tcx) { // Only suggest late `MaybeUninit::assume_init` initialization if the type is inhabited. diag.span_label( @@ -554,7 +560,8 @@ impl<'a> LintDiagnostic<'a, ()> for BuiltinUnpermittedTypeInit<'_> { msg!("help: use `MaybeUninit` instead, and only call `assume_init` after initialization is done"), ); } - self.sub.add_to_diag(diag); + self.sub.add_to_diag(&mut diag); + diag } } @@ -624,7 +631,7 @@ impl Subdiagnostic for BuiltinClashingExternSub<'_> { } } -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("dereferencing a null pointer")] pub(crate) struct BuiltinDerefNullptr { #[label("this code causes undefined behavior when executed")] @@ -633,7 +640,7 @@ pub(crate) struct BuiltinDerefNullptr { // FIXME: migrate fluent::lint::builtin_asm_labels -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] pub(crate) enum BuiltinSpecialModuleNameUsed { #[diag("found module declaration for lib.rs")] #[note("lib.rs is the root of this crate's library target")] @@ -645,7 +652,7 @@ pub(crate) enum BuiltinSpecialModuleNameUsed { } // deref_into_dyn_supertrait.rs -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("this `Deref` implementation is covered by an implicit supertrait coercion")] pub(crate) struct SupertraitAsDerefTarget<'a> { pub self_ty: Ty<'a>, @@ -667,7 +674,7 @@ pub(crate) struct SupertraitAsDerefTargetLabel { } // enum_intrinsics_non_enums.rs -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("the return value of `mem::discriminant` is unspecified when called with a non-enum type")] pub(crate) struct EnumIntrinsicsMemDiscriminate<'a> { pub ty_param: Ty<'a>, @@ -677,7 +684,7 @@ pub(crate) struct EnumIntrinsicsMemDiscriminate<'a> { pub note: Span, } -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("the return value of `mem::variant_count` is unspecified when called with a non-enum type")] #[note( "the type parameter of `variant_count` should be an enum, but it was instantiated with the type `{$ty_param}`, which is not an enum" @@ -705,7 +712,7 @@ pub(crate) struct ExpectationNote { } // ptr_nulls.rs -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] pub(crate) enum UselessPtrNullChecksDiag<'a> { #[diag( "function pointers are not nullable, so checking them for null will always return false" @@ -730,7 +737,7 @@ pub(crate) enum UselessPtrNullChecksDiag<'a> { FnRet { fn_name: Ident }, } -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] pub(crate) enum InvalidNullArgumentsDiag { #[diag( "calling this function with a null pointer is undefined behavior, even if the result of the function is unused" @@ -755,7 +762,7 @@ pub(crate) enum InvalidNullArgumentsDiag { } // for_loops_over_fallibles.rs -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag( "for loop over {$article} `{$ref_prefix}{$ty}`. This is more readably written as an `if let` statement" )] @@ -838,7 +845,7 @@ pub(crate) enum UseLetUnderscoreIgnoreSuggestion { } // drop_forget_useless.rs -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("calls to `std::mem::drop` with a reference instead of an owned value does nothing")] pub(crate) struct DropRefDiag<'a> { pub arg_ty: Ty<'a>, @@ -848,7 +855,7 @@ pub(crate) struct DropRefDiag<'a> { pub sugg: UseLetUnderscoreIgnoreSuggestion, } -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("calls to `std::mem::drop` with a value that implements `Copy` does nothing")] pub(crate) struct DropCopyDiag<'a> { pub arg_ty: Ty<'a>, @@ -858,7 +865,7 @@ pub(crate) struct DropCopyDiag<'a> { pub sugg: UseLetUnderscoreIgnoreSuggestion, } -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("calls to `std::mem::forget` with a reference instead of an owned value does nothing")] pub(crate) struct ForgetRefDiag<'a> { pub arg_ty: Ty<'a>, @@ -868,7 +875,7 @@ pub(crate) struct ForgetRefDiag<'a> { pub sugg: UseLetUnderscoreIgnoreSuggestion, } -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("calls to `std::mem::forget` with a value that implements `Copy` does nothing")] pub(crate) struct ForgetCopyDiag<'a> { pub arg_ty: Ty<'a>, @@ -878,7 +885,7 @@ pub(crate) struct ForgetCopyDiag<'a> { pub sugg: UseLetUnderscoreIgnoreSuggestion, } -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag( "calls to `std::mem::drop` with `std::mem::ManuallyDrop` instead of the inner value does nothing" )] @@ -903,7 +910,7 @@ pub(crate) struct UndroppedManuallyDropsSuggestion { } // invalid_from_utf8.rs -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] pub(crate) enum InvalidFromUtf8Diag { #[diag("calls to `{$method}` with an invalid literal are undefined behavior")] Unchecked { @@ -922,7 +929,7 @@ pub(crate) enum InvalidFromUtf8Diag { } // interior_mutable_consts.rs -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("mutation of an interior mutable `const` item with call to `{$method_name}`")] #[note("each usage of a `const` item creates a new temporary")] #[note("only the temporaries and never the original `const {$const_name}` will be modified")] @@ -957,7 +964,7 @@ pub(crate) enum ConstItemInteriorMutationsSuggestionStatic { } // reference_casting.rs -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] pub(crate) enum InvalidReferenceCastingDiag<'tcx> { #[diag( "casting `&T` to `&mut T` is undefined behavior, even if the reference is unused, consider instead using an `UnsafeCell`" @@ -1002,7 +1009,7 @@ pub(crate) enum InvalidReferenceCastingDiag<'tcx> { } // map_unit_fn.rs -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("`Iterator::map` call that discard the iterator's values")] #[note( "`Iterator::map`, like many of the methods on `Iterator`, gets executed lazily, meaning that its effects won't be visible until it is iterated" @@ -1026,7 +1033,7 @@ pub(crate) struct MappingToUnit { } // internal.rs -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("prefer `{$preferred}` over `{$used}`, it has better performance")] #[note("a `use rustc_data_structures::fx::{$preferred}` may be necessary")] pub(crate) struct DefaultHashTypesDiag<'a> { @@ -1034,7 +1041,7 @@ pub(crate) struct DefaultHashTypesDiag<'a> { pub used: Symbol, } -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("using `{$query}` can result in unstable query results")] #[note( "if you believe this case to be fine, allow this lint and add a comment explaining your rationale" @@ -1043,7 +1050,7 @@ pub(crate) struct QueryInstability { pub query: Symbol, } -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("`{$method}` accesses information that is not tracked by the query system")] #[note( "if you believe this case to be fine, allow this lint and add a comment explaining your rationale" @@ -1052,16 +1059,16 @@ pub(crate) struct QueryUntracked { pub method: Symbol, } -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("use `.eq_ctxt()` instead of `.ctxt() == .ctxt()`")] pub(crate) struct SpanUseEqCtxtDiag; -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("using `Symbol::intern` on a string literal")] #[help("consider adding the symbol to `compiler/rustc_span/src/symbol.rs`")] pub(crate) struct SymbolInternStringLiteralDiag; -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("usage of `ty::TyKind::`")] pub(crate) struct TykindKind { #[suggestion( @@ -1072,12 +1079,12 @@ pub(crate) struct TykindKind { pub suggestion: Span, } -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("usage of `ty::TyKind`")] #[help("try using `Ty` instead")] pub(crate) struct TykindDiag; -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("usage of qualified `ty::{$ty}`")] pub(crate) struct TyQualified { pub ty: String, @@ -1089,14 +1096,14 @@ pub(crate) struct TyQualified { pub suggestion: Span, } -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("do not use `rustc_type_ir::inherent` unless you're inside of the trait solver")] #[note( "the method or struct you're looking for is likely defined somewhere else downstream in the compiler" )] pub(crate) struct TypeIrInherentUsage; -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag( "do not use `rustc_type_ir::Interner` or `rustc_type_ir::InferCtxtLike` unless you're inside of the trait solver" )] @@ -1105,12 +1112,12 @@ pub(crate) struct TypeIrInherentUsage; )] pub(crate) struct TypeIrTraitUsage; -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("do not use `rustc_type_ir` unless you are implementing type system internals")] #[note("use `rustc_middle::ty` instead")] pub(crate) struct TypeIrDirectUse; -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("non-glob import of `rustc_type_ir::inherent`")] pub(crate) struct NonGlobImportTypeIrInherent { #[suggestion( @@ -1122,18 +1129,18 @@ pub(crate) struct NonGlobImportTypeIrInherent { pub snippet: &'static str, } -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("implementing `LintPass` by hand")] #[help("try using `declare_lint_pass!` or `impl_lint_pass!` instead")] pub(crate) struct LintPassByHand; -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("{$msg}")] pub(crate) struct BadOptAccessDiag<'a> { pub msg: &'a str, } -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag( "dangerous use of `extern crate {$name}` which is not guaranteed to exist exactly once in the sysroot" )] @@ -1144,14 +1151,14 @@ pub(crate) struct ImplicitSysrootCrateImportDiag<'a> { pub name: &'a str, } -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("use of `AttributeKind` in `find_attr!(...)` invocation")] #[note("`find_attr!(...)` already imports `AttributeKind::*`")] #[help("remove `AttributeKind`")] -pub(crate) struct AttributeKindInFindAttr {} +pub(crate) struct AttributeKindInFindAttr; // let_underscore.rs -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] pub(crate) enum NonBindingLet { #[diag("non-binding let on a synchronization lock")] SyncLock { @@ -1213,7 +1220,7 @@ impl Subdiagnostic for NonBindingLetSub { } // levels.rs -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("{$lint_level}({$lint_source}) incompatible with previous forbid")] pub(crate) struct OverruledAttributeLint<'a> { #[label("overruled by previous forbid")] @@ -1224,7 +1231,7 @@ pub(crate) struct OverruledAttributeLint<'a> { pub sub: OverruledAttributeSub, } -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("lint name `{$name}` is deprecated and may not have an effect in the future")] pub(crate) struct DeprecatedLintName<'a> { pub name: String, @@ -1233,7 +1240,7 @@ pub(crate) struct DeprecatedLintName<'a> { pub replace: &'a str, } -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("lint name `{$name}` is deprecated and may not have an effect in the future")] #[help("change it to {$replace}")] pub(crate) struct DeprecatedLintNameFromCommandLine<'a> { @@ -1243,7 +1250,7 @@ pub(crate) struct DeprecatedLintNameFromCommandLine<'a> { pub requested_level: RequestedLevel<'a>, } -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("lint `{$name}` has been renamed to `{$replace}`")] pub(crate) struct RenamedLint<'a> { pub name: &'a str, @@ -1264,7 +1271,7 @@ pub(crate) enum RenamedLintSuggestion<'a> { WithoutSpan { replace: &'a str }, } -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("lint `{$name}` has been renamed to `{$replace}`")] pub(crate) struct RenamedLintFromCommandLine<'a> { pub name: &'a str, @@ -1275,14 +1282,14 @@ pub(crate) struct RenamedLintFromCommandLine<'a> { pub requested_level: RequestedLevel<'a>, } -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("lint `{$name}` has been removed: {$reason}")] pub(crate) struct RemovedLint<'a> { pub name: &'a str, pub reason: &'a str, } -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("lint `{$name}` has been removed: {$reason}")] pub(crate) struct RemovedLintFromCommandLine<'a> { pub name: &'a str, @@ -1291,7 +1298,7 @@ pub(crate) struct RemovedLintFromCommandLine<'a> { pub requested_level: RequestedLevel<'a>, } -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("unknown lint: `{$name}`")] pub(crate) struct UnknownLint { pub name: String, @@ -1324,7 +1331,7 @@ pub(crate) enum UnknownLintSuggestion { WithoutSpan { replace: Symbol, from_rustc: bool }, } -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("unknown lint: `{$name}`", code = E0602)] pub(crate) struct UnknownLintFromCommandLine<'a> { pub name: String, @@ -1334,7 +1341,7 @@ pub(crate) struct UnknownLintFromCommandLine<'a> { pub requested_level: RequestedLevel<'a>, } -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("{$level}({$name}) is ignored unless specified at crate level")] pub(crate) struct IgnoredUnlessCrateSpecified<'a> { pub level: &'a str, @@ -1376,18 +1383,18 @@ pub(crate) struct DanglingPointersFromLocals<'tcx> { } // multiple_supertrait_upcastable.rs -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("`{$ident}` is dyn-compatible and has multiple supertraits")] pub(crate) struct MultipleSupertraitUpcastable { pub ident: Ident, } // non_ascii_idents.rs -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("identifier contains non-ASCII characters")] pub(crate) struct IdentifierNonAsciiChar; -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag( "identifier contains {$codepoints_len -> [one] { $identifier_type -> @@ -1421,7 +1428,7 @@ pub(crate) struct IdentifierUncommonCodepoints { pub identifier_type: &'static str, } -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("found both `{$existing_sym}` and `{$sym}` as identifiers, which look alike")] pub(crate) struct ConfusableIdentifierPair { pub existing_sym: Symbol, @@ -1432,7 +1439,7 @@ pub(crate) struct ConfusableIdentifierPair { pub main_label: Span, } -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag( "the usage of Script Group `{$set}` in this crate consists solely of mixed script confusables" )] @@ -1450,9 +1457,9 @@ pub(crate) struct NonFmtPanicUnused { } // Used because of two suggestions based on one Option -impl<'a> LintDiagnostic<'a, ()> for NonFmtPanicUnused { - fn decorate_lint<'b>(self, diag: &'b mut Diag<'a, ()>) { - diag.primary_message(msg!( +impl<'a> Diagnostic<'a, ()> for NonFmtPanicUnused { + fn into_diag(self, dcx: DiagCtxtHandle<'a>, level: Level) -> Diag<'a, ()> { + let mut diag = Diag::new(dcx, level, msg!( "panic message contains {$count -> [one] an unused *[other] unused @@ -1460,9 +1467,9 @@ impl<'a> LintDiagnostic<'a, ()> for NonFmtPanicUnused { [one] placeholder *[other] placeholders }" - )); - diag.arg("count", self.count); - diag.note(msg!("this message is not used as a format string when given without arguments, but will be in Rust 2021")); + )) + .with_arg("count", self.count) + .with_note(msg!("this message is not used as a format string when given without arguments, but will be in Rust 2021")); if let Some(span) = self.suggestion { diag.span_suggestion( span.shrink_to_hi(), @@ -1482,10 +1489,11 @@ impl<'a> LintDiagnostic<'a, ()> for NonFmtPanicUnused { Applicability::MachineApplicable, ); } + diag } } -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag( "panic message contains {$count -> [one] a brace @@ -1504,7 +1512,7 @@ pub(crate) struct NonFmtPanicBraces { } // nonstandard_style.rs -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("{$sort} `{$name}` should have an upper camel case name")] pub(crate) struct NonCamelCaseType<'a> { pub sort: &'a str, @@ -1532,7 +1540,7 @@ pub(crate) enum NonCamelCaseTypeSub { }, } -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("{$sort} `{$name}` should have a snake case name")] pub(crate) struct NonSnakeCaseDiag<'a> { pub sort: &'a str, @@ -1630,7 +1638,7 @@ pub(crate) struct NonUpperCaseGlobalSubTool { } // noop_method_call.rs -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("call to `.{$method}()` on a reference in this situation does nothing")] #[note( "the type `{$orig_ty}` does not implement `{$trait_}`, so calling `{$method}` on `&{$orig_ty}` copies the reference, which does not do anything and can be removed" @@ -1649,7 +1657,7 @@ pub(crate) struct NoopMethodCallDiag<'a> { pub suggest_derive: Option, } -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag( "using `.deref()` on a double reference, which returns `{$ty}` instead of dereferencing the inner type" )] @@ -1657,7 +1665,7 @@ pub(crate) struct SuspiciousDoubleRefDerefDiag<'a> { pub ty: Ty<'a>, } -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag( "using `.clone()` on a double reference, which returns `{$ty}` instead of cloning the inner type" )] @@ -1685,8 +1693,9 @@ pub(crate) enum NonLocalDefinitionsDiag { }, } -impl<'a> LintDiagnostic<'a, ()> for NonLocalDefinitionsDiag { - fn decorate_lint<'b>(self, diag: &'b mut Diag<'a, ()>) { +impl<'a> Diagnostic<'a, ()> for NonLocalDefinitionsDiag { + fn into_diag(self, dcx: DiagCtxtHandle<'a>, level: Level) -> Diag<'a, ()> { + let mut diag = Diag::new(dcx, level, ""); match self { NonLocalDefinitionsDiag::Impl { depth, @@ -1759,6 +1768,7 @@ impl<'a> LintDiagnostic<'a, ()> for NonLocalDefinitionsDiag { } } } + diag } } @@ -1773,7 +1783,7 @@ pub(crate) struct NonLocalDefinitionsCargoUpdateNote { } // precedence.rs -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("`-` has lower precedence than method calls, which might be unexpected")] #[note("e.g. `-4.abs()` equals `-4`; while `(-4).abs()` equals `4`")] pub(crate) struct AmbiguousNegativeLiteralsDiag { @@ -1808,7 +1818,7 @@ pub(crate) struct AmbiguousNegativeLiteralsCurrentBehaviorSuggestion { } // disallowed_pass_by_ref.rs -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("passing `{$ty}` by reference")] pub(crate) struct DisallowedPassByRefDiag { pub ty: String, @@ -1817,7 +1827,7 @@ pub(crate) struct DisallowedPassByRefDiag { } // redundant_semicolon.rs -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag( "unnecessary trailing {$multiple -> [true] semicolons @@ -1853,11 +1863,11 @@ pub(crate) struct DropTraitConstraintsDiag<'a> { } // Needed for def_path_str -impl<'a> LintDiagnostic<'a, ()> for DropTraitConstraintsDiag<'_> { - fn decorate_lint<'b>(self, diag: &'b mut Diag<'a, ()>) { - diag.primary_message(msg!("bounds on `{$predicate}` are most likely incorrect, consider instead using `{$needs_drop}` to detect whether a type can be trivially dropped")); - diag.arg("predicate", self.predicate); - diag.arg("needs_drop", self.tcx.def_path_str(self.def_id)); +impl<'a> Diagnostic<'a, ()> for DropTraitConstraintsDiag<'_> { + fn into_diag(self, dcx: DiagCtxtHandle<'a>, level: Level) -> Diag<'a, ()> { + Diag::new(dcx, level, msg!("bounds on `{$predicate}` are most likely incorrect, consider instead using `{$needs_drop}` to detect whether a type can be trivially dropped")) + .with_arg("predicate", self.predicate) + .with_arg("needs_drop", self.tcx.def_path_str(self.def_id)) } } @@ -1867,10 +1877,10 @@ pub(crate) struct DropGlue<'a> { } // Needed for def_path_str -impl<'a> LintDiagnostic<'a, ()> for DropGlue<'_> { - fn decorate_lint<'b>(self, diag: &'b mut Diag<'a, ()>) { - diag.primary_message(msg!("types that do not implement `Drop` can still have drop glue, consider instead using `{$needs_drop}` to detect whether a type is trivially dropped")); - diag.arg("needs_drop", self.tcx.def_path_str(self.def_id)); +impl<'a> Diagnostic<'a, ()> for DropGlue<'_> { + fn into_diag(self, dcx: DiagCtxtHandle<'a>, level: Level) -> Diag<'a, ()> { + Diag::new(dcx, level, msg!("types that do not implement `Drop` can still have drop glue, consider instead using `{$needs_drop}` to detect whether a type is trivially dropped")) + .with_arg("needs_drop", self.tcx.def_path_str(self.def_id)) } } @@ -1925,7 +1935,7 @@ pub(crate) enum IntegerToPtrTransmutesSuggestion<'tcx> { } // types.rs -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("range endpoint is out of range for `{$ty}`")] pub(crate) struct RangeEndpointOutOfRange<'a> { pub ty: &'a str, @@ -1958,7 +1968,7 @@ pub(crate) enum UseInclusiveRange<'a> { }, } -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("literal out of range for `{$ty}`")] pub(crate) struct OverflowingBinHex<'a> { pub ty: &'a str, @@ -2016,7 +2026,7 @@ pub(crate) struct OverflowingBinHexSignBitSub<'a> { pub int_ty: &'a str, } -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("literal out of range for `{$ty}`")] #[note("the literal `{$lit}` does not fit into the type `{$ty}` whose range is `{$min}..={$max}`")] pub(crate) struct OverflowingInt<'a> { @@ -2034,7 +2044,7 @@ pub(crate) struct OverflowingIntHelp<'a> { pub suggestion_ty: &'a str, } -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("only `u8` can be cast into `char`")] pub(crate) struct OnlyCastu8ToChar { #[suggestion( @@ -2046,7 +2056,7 @@ pub(crate) struct OnlyCastu8ToChar { pub literal: u128, } -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("literal out of range for `{$ty}`")] #[note("the literal `{$lit}` does not fit into the type `{$ty}` whose range is `{$min}..={$max}`")] pub(crate) struct OverflowingUInt<'a> { @@ -2056,7 +2066,7 @@ pub(crate) struct OverflowingUInt<'a> { pub max: u128, } -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("literal out of range for `{$ty}`")] #[note( "the literal `{$lit}` does not fit into the type `{$ty}` and will be converted to `{$ty}::INFINITY`" @@ -2066,31 +2076,31 @@ pub(crate) struct OverflowingLiteral<'a> { pub lit: String, } -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("surrogate values are not valid for `char`")] #[note("`0xD800..=0xDFFF` are reserved for Unicode surrogates and are not valid `char` values")] pub(crate) struct SurrogateCharCast { pub literal: u128, } -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("value exceeds maximum `char` value")] #[note("maximum valid `char` value is `0x10FFFF`")] pub(crate) struct TooLargeCharCast { pub literal: u128, } -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag( "repr(C) does not follow the power alignment rule. This may affect platform C ABI compatibility for this type" )] pub(crate) struct UsesPowerAlignment; -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("comparison is useless due to type limits")] pub(crate) struct UnusedComparisons; -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] pub(crate) enum InvalidNanComparisons { #[diag("incorrect NaN comparison, NaN cannot be directly compared to itself")] EqNe { @@ -2120,7 +2130,7 @@ pub(crate) enum InvalidNanComparisonsSuggestion { Spanless, } -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] pub(crate) enum AmbiguousWidePointerComparisons<'a> { #[diag( "ambiguous wide pointer comparison, the comparison includes metadata which may not be expected" @@ -2233,7 +2243,7 @@ pub(crate) struct AmbiguousWidePointerComparisonsExpectSuggestion<'a> { pub(crate) after: Span, } -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] pub(crate) enum UnpredictableFunctionPointerComparisons<'a, 'tcx> { #[diag( "function pointer comparisons do not produce meaningful results since their addresses are not guaranteed to be unique" @@ -2309,12 +2319,16 @@ pub(crate) struct ImproperCTypes<'a> { } // Used because of the complexity of Option, DiagMessage, and Option -impl<'a> LintDiagnostic<'a, ()> for ImproperCTypes<'_> { - fn decorate_lint<'b>(self, diag: &'b mut Diag<'a, ()>) { - diag.primary_message(msg!("`extern` {$desc} uses type `{$ty}`, which is not FFI-safe")); - diag.arg("ty", self.ty); - diag.arg("desc", self.desc); - diag.span_label(self.label, msg!("not FFI-safe")); +impl<'a> Diagnostic<'a, ()> for ImproperCTypes<'_> { + fn into_diag(self, dcx: DiagCtxtHandle<'a>, level: Level) -> Diag<'a, ()> { + let mut diag = Diag::new( + dcx, + level, + msg!("`extern` {$desc} uses type `{$ty}`, which is not FFI-safe"), + ) + .with_arg("ty", self.ty) + .with_arg("desc", self.desc) + .with_span_label(self.label, msg!("not FFI-safe")); if let Some(help) = self.help { diag.help(help); } @@ -2322,6 +2336,7 @@ impl<'a> LintDiagnostic<'a, ()> for ImproperCTypes<'_> { if let Some(note) = self.span_note { diag.span_note(note, msg!("the type is defined here")); } + diag } } @@ -2332,34 +2347,34 @@ pub(crate) struct ImproperGpuKernelArg<'a> { pub ty: Ty<'a>, } -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("function with the \"gpu-kernel\" ABI has a mangled name")] #[help("use `unsafe(no_mangle)` or `unsafe(export_name = \"\")`")] #[note("mangled names make it hard to find the kernel, this is usually not intended")] pub(crate) struct MissingGpuKernelExportName; -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("enum variant is more than three times larger ({$largest} bytes) than the next largest")] pub(crate) struct VariantSizeDifferencesDiag { pub largest: u64, } -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("atomic loads cannot have `Release` or `AcqRel` ordering")] #[help("consider using ordering modes `Acquire`, `SeqCst` or `Relaxed`")] pub(crate) struct AtomicOrderingLoad; -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("atomic stores cannot have `Acquire` or `AcqRel` ordering")] #[help("consider using ordering modes `Release`, `SeqCst` or `Relaxed`")] pub(crate) struct AtomicOrderingStore; -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("memory fences cannot have `Relaxed` ordering")] #[help("consider using ordering modes `Acquire`, `Release`, `AcqRel` or `SeqCst`")] pub(crate) struct AtomicOrderingFence; -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag( "`{$method}`'s failure ordering may not be `Release` or `AcqRel`, since a failed `{$method}` does not result in a write" )] @@ -2371,7 +2386,7 @@ pub(crate) struct InvalidAtomicOrderingDiag { } // unused.rs -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("unused {$op} that must be used")] pub(crate) struct UnusedOp<'a> { pub op: &'a str, @@ -2406,7 +2421,7 @@ pub(crate) enum UnusedOpSuggestion { }, } -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("unused result of type `{$ty}`")] pub(crate) struct UnusedResult<'a> { pub ty: Ty<'a>, @@ -2414,7 +2429,7 @@ pub(crate) struct UnusedResult<'a> { // FIXME(davidtwco): this isn't properly translatable because of the // pre/post strings -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag( "unused {$pre}{$count -> [one] closure @@ -2430,7 +2445,7 @@ pub(crate) struct UnusedClosure<'a> { // FIXME(davidtwco): this isn't properly translatable because of the // pre/post strings -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag( "unused {$pre}{$count -> [one] coroutine @@ -2481,12 +2496,13 @@ pub(crate) enum UnusedDefSuggestion { } // Needed because of def_path_str -impl<'a> LintDiagnostic<'a, ()> for UnusedDef<'_, '_> { - fn decorate_lint<'b>(self, diag: &'b mut Diag<'a, ()>) { - diag.primary_message(msg!("unused {$pre}`{$def}`{$post} that must be used")); - diag.arg("pre", self.pre); - diag.arg("post", self.post); - diag.arg("def", self.cx.tcx.def_path_str(self.def_id)); +impl<'a> Diagnostic<'a, ()> for UnusedDef<'_, '_> { + fn into_diag(self, dcx: DiagCtxtHandle<'a>, level: Level) -> Diag<'a, ()> { + let mut diag = + Diag::new(dcx, level, msg!("unused {$pre}`{$def}`{$post} that must be used")) + .with_arg("pre", self.pre) + .with_arg("post", self.post) + .with_arg("def", self.cx.tcx.def_path_str(self.def_id)); // check for #[must_use = "..."] if let Some(note) = self.note { diag.note(note.to_string()); @@ -2494,10 +2510,11 @@ impl<'a> LintDiagnostic<'a, ()> for UnusedDef<'_, '_> { if let Some(sugg) = self.suggestion { diag.subdiagnostic(sugg); } + diag } } -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("path statement drops value")] pub(crate) struct PathStatementDrop { #[subdiagnostic] @@ -2523,11 +2540,11 @@ pub(crate) enum PathStatementDropSub { }, } -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("path statement with no effect")] pub(crate) struct PathStatementNoEffect; -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("unnecessary {$delim} around {$item}")] pub(crate) struct UnusedDelim<'a> { pub delim: &'static str, @@ -2547,17 +2564,17 @@ pub(crate) struct UnusedDelimSuggestion { pub end_replace: &'static str, } -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("braces around {$node} is unnecessary")] pub(crate) struct UnusedImportBracesDiag { pub node: Symbol, } -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("unnecessary allocation, use `&` instead")] pub(crate) struct UnusedAllocationDiag; -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("unnecessary allocation, use `&mut` instead")] pub(crate) struct UnusedAllocationMutDiag; @@ -2580,14 +2597,14 @@ impl<'a> Diagnostic<'a, ()> for AsyncFnInTraitDiag { } } -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("binding has unit type `()`")] pub(crate) struct UnitBindingsDiag { #[label("this pattern is inferred to be the unit type `()`")] pub label: Span, } -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] pub(crate) enum InvalidAsmLabel { #[diag("avoid using named labels in inline assembly")] #[help("only local labels of the form `:` should be used in inline asm")] @@ -3344,7 +3361,7 @@ pub(crate) struct AssociatedConstElidedLifetime { pub lifetimes_in_scope: MultiSpan, } -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("creating a {$shared_label}reference to mutable static")] pub(crate) struct RefOfMutStatic<'a> { #[label("{$shared_label}reference to mutable static")] @@ -3384,9 +3401,9 @@ pub(crate) enum MutRefSugg { }, } -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("`use` of a local item without leading `self::`, `super::`, or `crate::`")] -pub(crate) struct UnqualifiedLocalImportsDiag {} +pub(crate) struct UnqualifiedLocalImportsDiag; #[derive(LintDiagnostic)] #[diag("will be parsed as a guarded string in Rust 2024")] @@ -3438,8 +3455,8 @@ pub(crate) struct MismatchedLifetimeSyntaxes { pub suggestions: Vec, } -impl<'a, G: EmissionGuarantee> LintDiagnostic<'a, G> for MismatchedLifetimeSyntaxes { - fn decorate_lint<'b>(self, diag: &'b mut Diag<'a, G>) { +impl<'a, G: EmissionGuarantee> Diagnostic<'a, G> for MismatchedLifetimeSyntaxes { + fn into_diag(self, dcx: DiagCtxtHandle<'a>, level: Level) -> Diag<'a, G> { let counts = self.inputs.len() + self.outputs.len(); let message = match counts { LifetimeSyntaxCategories { hidden: 0, elided: 0, named: 0 } => { @@ -3462,7 +3479,7 @@ impl<'a, G: EmissionGuarantee> LintDiagnostic<'a, G> for MismatchedLifetimeSynta msg!("hiding or eliding a lifetime that's named elsewhere is confusing") } }; - diag.primary_message(message); + let mut diag = Diag::new(dcx, level, message); for s in self.inputs.hidden { diag.span_label(s, msg!("the lifetime is hidden here")); @@ -3497,6 +3514,7 @@ impl<'a, G: EmissionGuarantee> LintDiagnostic<'a, G> for MismatchedLifetimeSynta diag.subdiagnostic(s); } } + diag } } @@ -3933,7 +3951,7 @@ pub(crate) struct MalformedOnConstAttrLint { pub span: Span, } -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("`Eq::assert_receiver_is_total_eq` should never be implemented by hand")] #[note("this method was used to add checks to the `Eq` derive macro")] pub(crate) struct EqInternalMethodImplemented; diff --git a/compiler/rustc_lint/src/opaque_hidden_inferred_bound.rs b/compiler/rustc_lint/src/opaque_hidden_inferred_bound.rs index b5b57eaa33894..5e43b8c65db40 100644 --- a/compiler/rustc_lint/src/opaque_hidden_inferred_bound.rs +++ b/compiler/rustc_lint/src/opaque_hidden_inferred_bound.rs @@ -1,6 +1,6 @@ use rustc_hir::{self as hir, AmbigArg}; use rustc_infer::infer::TyCtxtInferExt; -use rustc_macros::{LintDiagnostic, Subdiagnostic}; +use rustc_macros::{Diagnostic, Subdiagnostic}; use rustc_middle::ty::print::{PrintTraitPredicateExt as _, TraitPredPrintModifiersAndPath}; use rustc_middle::ty::{self, BottomUpFolder, Ty, TypeFoldable}; use rustc_session::{declare_lint, declare_lint_pass}; @@ -201,7 +201,7 @@ impl<'tcx> LateLintPass<'tcx> for OpaqueHiddenInferredBound { } } -#[derive(LintDiagnostic)] +#[derive(Diagnostic)] #[diag("opaque type `{$ty}` does not satisfy its associated type bounds")] struct OpaqueHiddenInferredBoundLint<'tcx> { ty: Ty<'tcx>, diff --git a/compiler/rustc_lint/src/unqualified_local_imports.rs b/compiler/rustc_lint/src/unqualified_local_imports.rs index d3aff05123763..888bf026b4ed9 100644 --- a/compiler/rustc_lint/src/unqualified_local_imports.rs +++ b/compiler/rustc_lint/src/unqualified_local_imports.rs @@ -77,7 +77,7 @@ impl<'tcx> LateLintPass<'tcx> for UnqualifiedLocalImports { cx.emit_span_lint( UNQUALIFIED_LOCAL_IMPORTS, first_seg.ident.span, - lints::UnqualifiedLocalImportsDiag {}, + lints::UnqualifiedLocalImportsDiag, ); } } diff --git a/compiler/rustc_middle/src/lint.rs b/compiler/rustc_middle/src/lint.rs index 08ccc4a0fca41..7347fe6d9d5e0 100644 --- a/compiler/rustc_middle/src/lint.rs +++ b/compiler/rustc_middle/src/lint.rs @@ -299,7 +299,6 @@ fn explain_lint_level_source( /// for example: /// - [`TyCtxt::emit_node_span_lint`] /// - [`TyCtxt::node_span_lint`] -/// - [`TyCtxt::emit_node_lint`] /// - [`TyCtxt::node_lint`] /// - `LintContext::opt_span_lint` /// @@ -490,7 +489,6 @@ pub fn lint_level( /// /// - [`TyCtxt::emit_node_span_lint`] /// - [`TyCtxt::node_span_lint`] -/// - [`TyCtxt::emit_node_lint`] /// - [`TyCtxt::node_lint`] /// - `LintContext::opt_span_lint` /// diff --git a/compiler/rustc_middle/src/ty/context.rs b/compiler/rustc_middle/src/ty/context.rs index d21f07a23e328..7107453faa615 100644 --- a/compiler/rustc_middle/src/ty/context.rs +++ b/compiler/rustc_middle/src/ty/context.rs @@ -29,7 +29,7 @@ use rustc_data_structures::steal::Steal; use rustc_data_structures::sync::{ self, DynSend, DynSync, FreezeReadGuard, Lock, RwLock, WorkerLocal, }; -use rustc_errors::{Applicability, Diag, DiagCtxtHandle, Diagnostic, LintDiagnostic, MultiSpan}; +use rustc_errors::{Applicability, Diag, DiagCtxtHandle, Diagnostic, MultiSpan}; use rustc_hir::def::DefKind; use rustc_hir::def_id::{CrateNum, DefId, LOCAL_CRATE, LocalDefId}; use rustc_hir::definitions::{DefPathData, Definitions, DisambiguatorState}; @@ -2554,18 +2554,17 @@ impl<'tcx> TyCtxt<'tcx> { } } - /// Emit a lint from a lint struct (some type that implements `LintDiagnostic`, typically - /// generated by `#[derive(LintDiagnostic)]`). + /// Emit a lint from a lint struct (some type that implements `Diagnostic`, typically generated + /// by `#[derive(Diagnostic)]`). #[track_caller] pub fn emit_node_lint( self, lint: &'static Lint, id: HirId, - decorator: impl for<'a> LintDiagnostic<'a, ()>, + decorator: impl for<'a> Diagnostic<'a, ()>, ) { - self.node_lint(lint, id, |lint| { - decorator.decorate_lint(lint); - }) + let level = self.lint_level_at_node(lint, id); + diag_lint_level(self.sess, lint, level, None, decorator); } /// Emit a lint at the appropriate level for a hir node. diff --git a/tests/ui/borrowck/borrowck-unsafe-static-mutable-borrows.stderr b/tests/ui/borrowck/borrowck-unsafe-static-mutable-borrows.stderr index 709cf76b444c2..6c3fd9eb400f2 100644 --- a/tests/ui/borrowck/borrowck-unsafe-static-mutable-borrows.stderr +++ b/tests/ui/borrowck/borrowck-unsafe-static-mutable-borrows.stderr @@ -4,8 +4,8 @@ warning: creating a mutable reference to mutable static LL | let sfoo: *mut Foo = &mut SFOO; | ^^^^^^^^^ mutable reference to mutable static | - = note: for more information, see = note: mutable references to mutable statics are dangerous; it's undefined behavior if any other pointer to the static is used or if any other reference is created for the static while the mutable reference lives + = note: for more information, see = note: `#[warn(static_mut_refs)]` (part of `#[warn(rust_2024_compatibility)]`) on by default help: use `&raw mut` instead to create a raw pointer | diff --git a/tests/ui/consts/const_let_assign2.stderr b/tests/ui/consts/const_let_assign2.stderr index ad3587b713411..e4edb58461054 100644 --- a/tests/ui/consts/const_let_assign2.stderr +++ b/tests/ui/consts/const_let_assign2.stderr @@ -4,8 +4,8 @@ warning: creating a mutable reference to mutable static LL | let ptr = unsafe { &mut BB }; | ^^^^^^^ mutable reference to mutable static | - = note: for more information, see = note: mutable references to mutable statics are dangerous; it's undefined behavior if any other pointer to the static is used or if any other reference is created for the static while the mutable reference lives + = note: for more information, see = note: `#[warn(static_mut_refs)]` (part of `#[warn(rust_2024_compatibility)]`) on by default help: use `&raw mut` instead to create a raw pointer | diff --git a/tests/ui/deriving/internal_eq_trait_method_impls.stderr b/tests/ui/deriving/internal_eq_trait_method_impls.stderr index 8ff8fe337a78c..118c4011e33e9 100644 --- a/tests/ui/deriving/internal_eq_trait_method_impls.stderr +++ b/tests/ui/deriving/internal_eq_trait_method_impls.stderr @@ -28,9 +28,9 @@ error: `Eq::assert_receiver_is_total_eq` should never be implemented by hand LL | fn assert_receiver_is_total_eq(&self) {} | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ | + = note: this method was used to add checks to the `Eq` derive macro = warning: this was previously accepted by the compiler but is being phased out; it will become a hard error in a future release! = note: for more information, see issue #152336 - = note: this method was used to add checks to the `Eq` derive macro note: the lint level is defined here --> $DIR/internal_eq_trait_method_impls.rs:1:21 | diff --git a/tests/ui/issues/issue-39367.stderr b/tests/ui/issues/issue-39367.stderr index 1592b8b6672c7..e94c961f431d1 100644 --- a/tests/ui/issues/issue-39367.stderr +++ b/tests/ui/issues/issue-39367.stderr @@ -9,8 +9,8 @@ LL | | (Box::new(__static_ref_initialize())); LL | | }); | |______________^ shared reference to mutable static | - = note: for more information, see = note: shared references to mutable statics are dangerous; it's undefined behavior if the static is mutated or if a mutable reference is created for it while the shared reference lives + = note: for more information, see = note: `#[warn(static_mut_refs)]` (part of `#[warn(rust_2024_compatibility)]`) on by default warning: 1 warning emitted diff --git a/tests/ui/lint/static-mut-refs.e2021.stderr b/tests/ui/lint/static-mut-refs.e2021.stderr index 86854ab2ddab2..56b4ad239afe3 100644 --- a/tests/ui/lint/static-mut-refs.e2021.stderr +++ b/tests/ui/lint/static-mut-refs.e2021.stderr @@ -4,8 +4,8 @@ warning: creating a shared reference to mutable static LL | let _y = &X; | ^^ shared reference to mutable static | - = note: for more information, see = note: shared references to mutable statics are dangerous; it's undefined behavior if the static is mutated or if a mutable reference is created for it while the shared reference lives + = note: for more information, see = note: `#[warn(static_mut_refs)]` (part of `#[warn(rust_2024_compatibility)]`) on by default help: use `&raw const` instead to create a raw pointer | @@ -18,8 +18,8 @@ warning: creating a mutable reference to mutable static LL | let _y = &mut X; | ^^^^^^ mutable reference to mutable static | - = note: for more information, see = note: mutable references to mutable statics are dangerous; it's undefined behavior if any other pointer to the static is used or if any other reference is created for the static while the mutable reference lives + = note: for more information, see help: use `&raw mut` instead to create a raw pointer | LL | let _y = &raw mut X; @@ -31,8 +31,8 @@ warning: creating a shared reference to mutable static LL | let ref _a = X; | ^ shared reference to mutable static | - = note: for more information, see = note: shared references to mutable statics are dangerous; it's undefined behavior if the static is mutated or if a mutable reference is created for it while the shared reference lives + = note: for more information, see warning: creating a shared reference to mutable static --> $DIR/static-mut-refs.rs:54:25 @@ -40,8 +40,8 @@ warning: creating a shared reference to mutable static LL | let (_b, _c) = (&X, &Y); | ^^ shared reference to mutable static | - = note: for more information, see = note: shared references to mutable statics are dangerous; it's undefined behavior if the static is mutated or if a mutable reference is created for it while the shared reference lives + = note: for more information, see help: use `&raw const` instead to create a raw pointer | LL | let (_b, _c) = (&raw const X, &Y); @@ -53,8 +53,8 @@ warning: creating a shared reference to mutable static LL | let (_b, _c) = (&X, &Y); | ^^ shared reference to mutable static | - = note: for more information, see = note: shared references to mutable statics are dangerous; it's undefined behavior if the static is mutated or if a mutable reference is created for it while the shared reference lives + = note: for more information, see help: use `&raw const` instead to create a raw pointer | LL | let (_b, _c) = (&X, &raw const Y); @@ -66,8 +66,8 @@ warning: creating a shared reference to mutable static LL | foo(&X); | ^^ shared reference to mutable static | - = note: for more information, see = note: shared references to mutable statics are dangerous; it's undefined behavior if the static is mutated or if a mutable reference is created for it while the shared reference lives + = note: for more information, see help: use `&raw const` instead to create a raw pointer | LL | foo(&raw const X); @@ -79,8 +79,8 @@ warning: creating a shared reference to mutable static LL | let _ = Z.len(); | ^^^^^^^ shared reference to mutable static | - = note: for more information, see = note: shared references to mutable statics are dangerous; it's undefined behavior if the static is mutated or if a mutable reference is created for it while the shared reference lives + = note: for more information, see warning: creating a shared reference to mutable static --> $DIR/static-mut-refs.rs:72:33 @@ -88,8 +88,8 @@ warning: creating a shared reference to mutable static LL | let _ = format!("{:?}", Z); | ^ shared reference to mutable static | - = note: for more information, see = note: shared references to mutable statics are dangerous; it's undefined behavior if the static is mutated or if a mutable reference is created for it while the shared reference lives + = note: for more information, see warning: creating a shared reference to mutable static --> $DIR/static-mut-refs.rs:76:18 @@ -97,8 +97,8 @@ warning: creating a shared reference to mutable static LL | let _v = &A.value; | ^^^^^^^^ shared reference to mutable static | - = note: for more information, see = note: shared references to mutable statics are dangerous; it's undefined behavior if the static is mutated or if a mutable reference is created for it while the shared reference lives + = note: for more information, see help: use `&raw const` instead to create a raw pointer | LL | let _v = &raw const A.value; @@ -110,8 +110,8 @@ warning: creating a shared reference to mutable static LL | let _s = &A.s.value; | ^^^^^^^^^^ shared reference to mutable static | - = note: for more information, see = note: shared references to mutable statics are dangerous; it's undefined behavior if the static is mutated or if a mutable reference is created for it while the shared reference lives + = note: for more information, see help: use `&raw const` instead to create a raw pointer | LL | let _s = &raw const A.s.value; @@ -123,8 +123,8 @@ warning: creating a shared reference to mutable static LL | let ref _v = A.value; | ^^^^^^^ shared reference to mutable static | - = note: for more information, see = note: shared references to mutable statics are dangerous; it's undefined behavior if the static is mutated or if a mutable reference is created for it while the shared reference lives + = note: for more information, see warning: creating a mutable reference to mutable static --> $DIR/static-mut-refs.rs:14:14 @@ -135,8 +135,8 @@ LL | &mut ($x.0) LL | let _x = bar!(FOO); | --------- in this macro invocation | - = note: for more information, see = note: mutable references to mutable statics are dangerous; it's undefined behavior if any other pointer to the static is used or if any other reference is created for the static while the mutable reference lives + = note: for more information, see = note: this warning originates in the macro `bar` (in Nightly builds, run with -Z macro-backtrace for more info) warning: 12 warnings emitted diff --git a/tests/ui/lint/static-mut-refs.e2024.stderr b/tests/ui/lint/static-mut-refs.e2024.stderr index 5c21c5b0dd9b3..0b7f48a507c94 100644 --- a/tests/ui/lint/static-mut-refs.e2024.stderr +++ b/tests/ui/lint/static-mut-refs.e2024.stderr @@ -4,8 +4,8 @@ error: creating a shared reference to mutable static LL | let _y = &X; | ^^ shared reference to mutable static | - = note: for more information, see = note: shared references to mutable statics are dangerous; it's undefined behavior if the static is mutated or if a mutable reference is created for it while the shared reference lives + = note: for more information, see = note: `#[deny(static_mut_refs)]` (part of `#[deny(rust_2024_compatibility)]`) on by default help: use `&raw const` instead to create a raw pointer | @@ -18,8 +18,8 @@ error: creating a mutable reference to mutable static LL | let _y = &mut X; | ^^^^^^ mutable reference to mutable static | - = note: for more information, see = note: mutable references to mutable statics are dangerous; it's undefined behavior if any other pointer to the static is used or if any other reference is created for the static while the mutable reference lives + = note: for more information, see help: use `&raw mut` instead to create a raw pointer | LL | let _y = &raw mut X; @@ -31,8 +31,8 @@ error: creating a shared reference to mutable static LL | let ref _a = X; | ^ shared reference to mutable static | - = note: for more information, see = note: shared references to mutable statics are dangerous; it's undefined behavior if the static is mutated or if a mutable reference is created for it while the shared reference lives + = note: for more information, see error: creating a shared reference to mutable static --> $DIR/static-mut-refs.rs:54:25 @@ -40,8 +40,8 @@ error: creating a shared reference to mutable static LL | let (_b, _c) = (&X, &Y); | ^^ shared reference to mutable static | - = note: for more information, see = note: shared references to mutable statics are dangerous; it's undefined behavior if the static is mutated or if a mutable reference is created for it while the shared reference lives + = note: for more information, see help: use `&raw const` instead to create a raw pointer | LL | let (_b, _c) = (&raw const X, &Y); @@ -53,8 +53,8 @@ error: creating a shared reference to mutable static LL | let (_b, _c) = (&X, &Y); | ^^ shared reference to mutable static | - = note: for more information, see = note: shared references to mutable statics are dangerous; it's undefined behavior if the static is mutated or if a mutable reference is created for it while the shared reference lives + = note: for more information, see help: use `&raw const` instead to create a raw pointer | LL | let (_b, _c) = (&X, &raw const Y); @@ -66,8 +66,8 @@ error: creating a shared reference to mutable static LL | foo(&X); | ^^ shared reference to mutable static | - = note: for more information, see = note: shared references to mutable statics are dangerous; it's undefined behavior if the static is mutated or if a mutable reference is created for it while the shared reference lives + = note: for more information, see help: use `&raw const` instead to create a raw pointer | LL | foo(&raw const X); @@ -79,8 +79,8 @@ error: creating a shared reference to mutable static LL | let _ = Z.len(); | ^^^^^^^ shared reference to mutable static | - = note: for more information, see = note: shared references to mutable statics are dangerous; it's undefined behavior if the static is mutated or if a mutable reference is created for it while the shared reference lives + = note: for more information, see error: creating a shared reference to mutable static --> $DIR/static-mut-refs.rs:72:33 @@ -88,8 +88,8 @@ error: creating a shared reference to mutable static LL | let _ = format!("{:?}", Z); | ^ shared reference to mutable static | - = note: for more information, see = note: shared references to mutable statics are dangerous; it's undefined behavior if the static is mutated or if a mutable reference is created for it while the shared reference lives + = note: for more information, see error: creating a shared reference to mutable static --> $DIR/static-mut-refs.rs:76:18 @@ -97,8 +97,8 @@ error: creating a shared reference to mutable static LL | let _v = &A.value; | ^^^^^^^^ shared reference to mutable static | - = note: for more information, see = note: shared references to mutable statics are dangerous; it's undefined behavior if the static is mutated or if a mutable reference is created for it while the shared reference lives + = note: for more information, see help: use `&raw const` instead to create a raw pointer | LL | let _v = &raw const A.value; @@ -110,8 +110,8 @@ error: creating a shared reference to mutable static LL | let _s = &A.s.value; | ^^^^^^^^^^ shared reference to mutable static | - = note: for more information, see = note: shared references to mutable statics are dangerous; it's undefined behavior if the static is mutated or if a mutable reference is created for it while the shared reference lives + = note: for more information, see help: use `&raw const` instead to create a raw pointer | LL | let _s = &raw const A.s.value; @@ -123,8 +123,8 @@ error: creating a shared reference to mutable static LL | let ref _v = A.value; | ^^^^^^^ shared reference to mutable static | - = note: for more information, see = note: shared references to mutable statics are dangerous; it's undefined behavior if the static is mutated or if a mutable reference is created for it while the shared reference lives + = note: for more information, see error: creating a mutable reference to mutable static --> $DIR/static-mut-refs.rs:14:14 @@ -135,8 +135,8 @@ LL | &mut ($x.0) LL | let _x = bar!(FOO); | --------- in this macro invocation | - = note: for more information, see = note: mutable references to mutable statics are dangerous; it's undefined behavior if any other pointer to the static is used or if any other reference is created for the static while the mutable reference lives + = note: for more information, see = note: this error originates in the macro `bar` (in Nightly builds, run with -Z macro-backtrace for more info) error: aborting due to 12 previous errors diff --git a/tests/ui/macros/non-fmt-panic.stderr b/tests/ui/macros/non-fmt-panic.stderr index edef9d8d97c43..9cadaf3fbe388 100644 --- a/tests/ui/macros/non-fmt-panic.stderr +++ b/tests/ui/macros/non-fmt-panic.stderr @@ -4,8 +4,8 @@ warning: panic message contains a brace LL | panic!("here's a brace: {"); | ^ | - = note: for more information, see = note: this message is not used as a format string, but will be in Rust 2021 + = note: for more information, see = note: `#[warn(non_fmt_panics)]` (part of `#[warn(rust_2021_compatibility)]`) on by default help: add a "{}" format string to use the message literally | @@ -18,8 +18,8 @@ warning: panic message contains a brace LL | unreachable!("here's a brace: {"); | ^ | - = note: for more information, see = note: this message is not used as a format string, but will be in Rust 2021 + = note: for more information, see help: add a "{}" format string to use the message literally | LL | unreachable!("{}", "here's a brace: {"); @@ -31,8 +31,8 @@ warning: panic message contains a brace LL | std::panic!("another one: }"); | ^ | - = note: for more information, see = note: this message is not used as a format string, but will be in Rust 2021 + = note: for more information, see help: add a "{}" format string to use the message literally | LL | std::panic!("{}", "another one: }"); @@ -44,8 +44,8 @@ warning: panic message contains an unused formatting placeholder LL | core::panic!("Hello {}"); | ^^ | - = note: for more information, see = note: this message is not used as a format string when given without arguments, but will be in Rust 2021 + = note: for more information, see help: add the missing argument | LL | core::panic!("Hello {}", ...); @@ -61,8 +61,8 @@ warning: panic message contains unused formatting placeholders LL | assert!(false, "{:03x} {test} bla"); | ^^^^^^ ^^^^^^ | - = note: for more information, see = note: this message is not used as a format string when given without arguments, but will be in Rust 2021 + = note: for more information, see help: add the missing arguments | LL | assert!(false, "{:03x} {test} bla", ...); @@ -120,8 +120,8 @@ warning: panic message contains braces LL | debug_assert!(false, "{{}} bla"); | ^^^^ | - = note: for more information, see = note: this message is not used as a format string, but will be in Rust 2021 + = note: for more information, see help: add a "{}" format string to use the message literally | LL | debug_assert!(false, "{}", "{{}} bla"); @@ -241,8 +241,8 @@ warning: panic message contains an unused formatting placeholder LL | panic!(concat!("{", "}")); | ^^^^^^^^^^^^^^^^^ | - = note: for more information, see = note: this message is not used as a format string when given without arguments, but will be in Rust 2021 + = note: for more information, see help: add the missing argument | LL | panic!(concat!("{", "}"), ...); @@ -258,8 +258,8 @@ warning: panic message contains braces LL | panic!(concat!("{", "{")); | ^^^^^^^^^^^^^^^^^^^^^^^^^ | - = note: for more information, see = note: this message is not used as a format string, but will be in Rust 2021 + = note: for more information, see help: add a "{}" format string to use the message literally | LL | panic!("{}", concat!("{", "{")); @@ -271,8 +271,8 @@ warning: panic message contains an unused formatting placeholder LL | fancy_panic::fancy_panic!("test {} 123"); | ^^ | - = note: for more information, see = note: this message is not used as a format string when given without arguments, but will be in Rust 2021 + = note: for more information, see warning: panic message is not a string literal --> $DIR/non-fmt-panic.rs:53:12 diff --git a/tests/ui/nll/borrowck-thread-local-static-mut-borrow-outlives-fn.stderr b/tests/ui/nll/borrowck-thread-local-static-mut-borrow-outlives-fn.stderr index 63744c15fda9c..19a3a786ac940 100644 --- a/tests/ui/nll/borrowck-thread-local-static-mut-borrow-outlives-fn.stderr +++ b/tests/ui/nll/borrowck-thread-local-static-mut-borrow-outlives-fn.stderr @@ -4,8 +4,8 @@ warning: creating a mutable reference to mutable static LL | S1 { a: unsafe { &mut X1 } } | ^^^^^^^ mutable reference to mutable static | - = note: for more information, see = note: mutable references to mutable statics are dangerous; it's undefined behavior if any other pointer to the static is used or if any other reference is created for the static while the mutable reference lives + = note: for more information, see = note: `#[warn(static_mut_refs)]` (part of `#[warn(rust_2024_compatibility)]`) on by default help: use `&raw mut` instead to create a raw pointer | diff --git a/tests/ui/statics/issue-15261.stderr b/tests/ui/statics/issue-15261.stderr index 20ac078524508..fdc8e0c1f5ef7 100644 --- a/tests/ui/statics/issue-15261.stderr +++ b/tests/ui/statics/issue-15261.stderr @@ -4,8 +4,8 @@ warning: creating a shared reference to mutable static LL | static n: &'static usize = unsafe { &n_mut }; | ^^^^^^ shared reference to mutable static | - = note: for more information, see = note: shared references to mutable statics are dangerous; it's undefined behavior if the static is mutated or if a mutable reference is created for it while the shared reference lives + = note: for more information, see = note: `#[warn(static_mut_refs)]` (part of `#[warn(rust_2024_compatibility)]`) on by default help: use `&raw const` instead to create a raw pointer | diff --git a/tests/ui/statics/static-mut-shared-parens.stderr b/tests/ui/statics/static-mut-shared-parens.stderr index c900fcde16f6a..1265bdc7cf0d3 100644 --- a/tests/ui/statics/static-mut-shared-parens.stderr +++ b/tests/ui/statics/static-mut-shared-parens.stderr @@ -4,8 +4,8 @@ warning: creating a shared reference to mutable static LL | let _ = unsafe { (&TEST) as *const usize }; | ^^^^^^^ shared reference to mutable static | - = note: for more information, see = note: shared references to mutable statics are dangerous; it's undefined behavior if the static is mutated or if a mutable reference is created for it while the shared reference lives + = note: for more information, see = note: `#[warn(static_mut_refs)]` (part of `#[warn(rust_2024_compatibility)]`) on by default help: use `&raw const` instead to create a raw pointer | @@ -18,8 +18,8 @@ warning: creating a mutable reference to mutable static LL | let _ = unsafe { (&mut TEST) as *const usize }; | ^^^^^^^^^^^ mutable reference to mutable static | - = note: for more information, see = note: mutable references to mutable statics are dangerous; it's undefined behavior if any other pointer to the static is used or if any other reference is created for the static while the mutable reference lives + = note: for more information, see help: use `&raw mut` instead to create a raw pointer | LL | let _ = unsafe { (&raw mut TEST) as *const usize }; diff --git a/tests/ui/statics/static-mut-xc.stderr b/tests/ui/statics/static-mut-xc.stderr index 73c4e91b8e034..d0b30ce6f8514 100644 --- a/tests/ui/statics/static-mut-xc.stderr +++ b/tests/ui/statics/static-mut-xc.stderr @@ -4,8 +4,8 @@ warning: creating a shared reference to mutable static LL | assert_eq!(static_mut_xc::a, 3); | ^^^^^^^^^^^^^^^^ shared reference to mutable static | - = note: for more information, see = note: shared references to mutable statics are dangerous; it's undefined behavior if the static is mutated or if a mutable reference is created for it while the shared reference lives + = note: for more information, see = note: `#[warn(static_mut_refs)]` (part of `#[warn(rust_2024_compatibility)]`) on by default warning: creating a shared reference to mutable static @@ -14,8 +14,8 @@ warning: creating a shared reference to mutable static LL | assert_eq!(static_mut_xc::a, 4); | ^^^^^^^^^^^^^^^^ shared reference to mutable static | - = note: for more information, see = note: shared references to mutable statics are dangerous; it's undefined behavior if the static is mutated or if a mutable reference is created for it while the shared reference lives + = note: for more information, see warning: creating a shared reference to mutable static --> $DIR/static-mut-xc.rs:25:16 @@ -23,8 +23,8 @@ warning: creating a shared reference to mutable static LL | assert_eq!(static_mut_xc::a, 5); | ^^^^^^^^^^^^^^^^ shared reference to mutable static | - = note: for more information, see = note: shared references to mutable statics are dangerous; it's undefined behavior if the static is mutated or if a mutable reference is created for it while the shared reference lives + = note: for more information, see warning: creating a shared reference to mutable static --> $DIR/static-mut-xc.rs:28:16 @@ -32,8 +32,8 @@ warning: creating a shared reference to mutable static LL | assert_eq!(static_mut_xc::a, 15); | ^^^^^^^^^^^^^^^^ shared reference to mutable static | - = note: for more information, see = note: shared references to mutable statics are dangerous; it's undefined behavior if the static is mutated or if a mutable reference is created for it while the shared reference lives + = note: for more information, see warning: creating a shared reference to mutable static --> $DIR/static-mut-xc.rs:31:16 @@ -41,8 +41,8 @@ warning: creating a shared reference to mutable static LL | assert_eq!(static_mut_xc::a, -3); | ^^^^^^^^^^^^^^^^ shared reference to mutable static | - = note: for more information, see = note: shared references to mutable statics are dangerous; it's undefined behavior if the static is mutated or if a mutable reference is created for it while the shared reference lives + = note: for more information, see warning: creating a shared reference to mutable static --> $DIR/static-mut-xc.rs:33:18 @@ -50,8 +50,8 @@ warning: creating a shared reference to mutable static LL | static_bound(&static_mut_xc::a); | ^^^^^^^^^^^^^^^^^ shared reference to mutable static | - = note: for more information, see = note: shared references to mutable statics are dangerous; it's undefined behavior if the static is mutated or if a mutable reference is created for it while the shared reference lives + = note: for more information, see help: use `&raw const` instead to create a raw pointer | LL | static_bound(&raw const static_mut_xc::a); @@ -63,8 +63,8 @@ warning: creating a mutable reference to mutable static LL | static_bound_set(&mut static_mut_xc::a); | ^^^^^^^^^^^^^^^^^^^^^ mutable reference to mutable static | - = note: for more information, see = note: mutable references to mutable statics are dangerous; it's undefined behavior if any other pointer to the static is used or if any other reference is created for the static while the mutable reference lives + = note: for more information, see help: use `&raw mut` instead to create a raw pointer | LL | static_bound_set(&raw mut static_mut_xc::a); diff --git a/tests/ui/statics/static-recursive.stderr b/tests/ui/statics/static-recursive.stderr index 16d5e183ccbd7..1ae96dfd5a832 100644 --- a/tests/ui/statics/static-recursive.stderr +++ b/tests/ui/statics/static-recursive.stderr @@ -4,8 +4,8 @@ warning: creating a shared reference to mutable static LL | static mut S: *const u8 = unsafe { &S as *const *const u8 as *const u8 }; | ^^ shared reference to mutable static | - = note: for more information, see = note: shared references to mutable statics are dangerous; it's undefined behavior if the static is mutated or if a mutable reference is created for it while the shared reference lives + = note: for more information, see = note: `#[warn(static_mut_refs)]` (part of `#[warn(rust_2024_compatibility)]`) on by default help: use `&raw const` instead to create a raw pointer | @@ -18,8 +18,8 @@ warning: creating a shared reference to mutable static LL | assert_eq!(S, *(S as *const *const u8)); | ^ shared reference to mutable static | - = note: for more information, see = note: shared references to mutable statics are dangerous; it's undefined behavior if the static is mutated or if a mutable reference is created for it while the shared reference lives + = note: for more information, see warning: 2 warnings emitted