Skip to content

Commit 49ec909

Browse files
committed
macros: subdiagnostic derive
Add a new derive, `#[derive(SessionSubdiagnostic)]`, which enables deriving structs for labels, notes, helps and suggestions. Signed-off-by: David Wood <[email protected]>
1 parent aa2abc9 commit 49ec909

File tree

10 files changed

+1735
-151
lines changed

10 files changed

+1735
-151
lines changed

compiler/rustc_error_messages/locales/en-US/typeck.ftl

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -82,3 +82,11 @@ typeck-value-of-associated-struct-already-specified =
8282
8383
typeck-address-of-temporary-taken = cannot take address of a temporary
8484
.label = temporary value
85+
86+
typeck-add-return-type-add = try adding a return type
87+
88+
typeck-add-return-type-missing-here = a return type might be missing here
89+
90+
typeck-expected-default-return-type = expected `()` because of default return type
91+
92+
typeck-expected-return-type = expected `{$expected}` because of return type

compiler/rustc_errors/src/diagnostic.rs

Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -78,6 +78,13 @@ impl<'source> Into<FluentValue<'source>> for DiagnosticArgValue<'source> {
7878
}
7979
}
8080

81+
/// Trait implemented by error types. This should not be implemented manually. Instead, use
82+
/// `#[derive(SessionSubdiagnostic)]` -- see [rustc_macros::SessionSubdiagnostic].
83+
pub trait AddSubdiagnostic {
84+
/// Add a subdiagnostic to an existing diagnostic.
85+
fn add_to_diagnostic(self, diag: &mut Diagnostic);
86+
}
87+
8188
#[must_use]
8289
#[derive(Clone, Debug, Encodable, Decodable)]
8390
pub struct Diagnostic {
@@ -768,6 +775,13 @@ impl Diagnostic {
768775
self
769776
}
770777

778+
/// Add a subdiagnostic from a type that implements `SessionSubdiagnostic` - see
779+
/// [rustc_macros::SessionSubdiagnostic].
780+
pub fn subdiagnostic(&mut self, subdiagnostic: impl AddSubdiagnostic) -> &mut Self {
781+
subdiagnostic.add_to_diagnostic(self);
782+
self
783+
}
784+
771785
pub fn set_span<S: Into<MultiSpan>>(&mut self, sp: S) -> &mut Self {
772786
self.span = sp.into();
773787
if let Some(span) = self.span.primary_span() {

compiler/rustc_errors/src/diagnostic_builder.rs

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -530,6 +530,11 @@ impl<'a, G: EmissionGuarantee> DiagnosticBuilder<'a, G> {
530530
name: impl Into<Cow<'static, str>>,
531531
arg: DiagnosticArgValue<'static>,
532532
) -> &mut Self);
533+
534+
forward!(pub fn subdiagnostic(
535+
&mut self,
536+
subdiagnostic: impl crate::AddSubdiagnostic
537+
) -> &mut Self);
533538
}
534539

535540
impl<G: EmissionGuarantee> Debug for DiagnosticBuilder<'_, G> {

compiler/rustc_errors/src/lib.rs

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -370,8 +370,8 @@ impl fmt::Display for ExplicitBug {
370370
impl error::Error for ExplicitBug {}
371371

372372
pub use diagnostic::{
373-
Diagnostic, DiagnosticArg, DiagnosticArgValue, DiagnosticId, DiagnosticStyledString,
374-
IntoDiagnosticArg, SubDiagnostic,
373+
AddSubdiagnostic, Diagnostic, DiagnosticArg, DiagnosticArgValue, DiagnosticId,
374+
DiagnosticStyledString, IntoDiagnosticArg, SubDiagnostic,
375375
};
376376
pub use diagnostic_builder::{DiagnosticBuilder, EmissionGuarantee};
377377
use std::backtrace::Backtrace;

compiler/rustc_macros/src/lib.rs

Lines changed: 17 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,6 @@
1-
#![feature(proc_macro_diagnostic)]
21
#![feature(allow_internal_unstable)]
2+
#![feature(let_else)]
3+
#![feature(proc_macro_diagnostic)]
34
#![allow(rustc::default_hash_types)]
45
#![recursion_limit = "128"]
56

@@ -77,3 +78,18 @@ decl_derive!(
7778
suggestion_hidden,
7879
suggestion_verbose)] => session_diagnostic::session_diagnostic_derive
7980
);
81+
decl_derive!(
82+
[SessionSubdiagnostic, attributes(
83+
// struct/variant attributes
84+
label,
85+
help,
86+
note,
87+
suggestion,
88+
suggestion_short,
89+
suggestion_hidden,
90+
suggestion_verbose,
91+
// field attributes
92+
skip_arg,
93+
primary_span,
94+
applicability)] => session_diagnostic::session_subdiagnostic_derive
95+
);

0 commit comments

Comments
 (0)