@@ -229,38 +229,30 @@ impl<'a> SessionDiagnosticDerive<'a> {
229
229
230
230
let span = ast. span ( ) . unwrap ( ) ;
231
231
let ( diag, sess) = ( & builder. diag , & builder. sess ) ;
232
- let init = match ( builder. kind , builder. slug , builder . code ) {
233
- ( None , _, _ ) => {
232
+ let init = match ( builder. kind , builder. slug ) {
233
+ ( None , _) => {
234
234
span_err ( span, "diagnostic kind not specified" )
235
235
. help ( "use the `#[error(...)]` attribute to create an error" )
236
236
. emit ( ) ;
237
237
return SessionDiagnosticDeriveError :: ErrorHandled . to_compile_error ( ) ;
238
238
}
239
- ( Some ( ( kind, _) ) , None , _ ) => {
239
+ ( Some ( ( kind, _) ) , None ) => {
240
240
span_err ( span, "`slug` not specified" )
241
241
. help ( & format ! ( "use the `#[{}(slug = \" ...\" )]` attribute to set this diagnostic's slug" , kind. descr( ) ) )
242
242
. emit ( ) ;
243
243
return SessionDiagnosticDeriveError :: ErrorHandled . to_compile_error ( ) ;
244
244
}
245
- ( Some ( ( kind, _) ) , _, None ) => {
246
- span_err ( span, "`code` not specified" )
247
- . help ( & format ! ( "use the `#[{}(code = \" ...\" )]` attribute to set this diagnostic's error code" , kind. descr( ) ) )
248
- . emit ( ) ;
249
- return SessionDiagnosticDeriveError :: ErrorHandled . to_compile_error ( ) ;
250
- }
251
- ( Some ( ( SessionDiagnosticKind :: Error , _) ) , Some ( ( slug, _) ) , Some ( ( code, _) ) ) => {
245
+ ( Some ( ( SessionDiagnosticKind :: Error , _) ) , Some ( ( slug, _) ) ) => {
252
246
quote ! {
253
- let mut #diag = #sess. struct_err_with_code (
247
+ let mut #diag = #sess. struct_err (
254
248
rustc_errors:: DiagnosticMessage :: fluent( #slug) ,
255
- rustc_errors:: DiagnosticId :: Error ( #code. to_string( ) )
256
249
) ;
257
250
}
258
251
}
259
- ( Some ( ( SessionDiagnosticKind :: Warn , _) ) , Some ( ( slug, _) ) , Some ( ( code , _ ) ) ) => {
252
+ ( Some ( ( SessionDiagnosticKind :: Warn , _) ) , Some ( ( slug, _) ) ) => {
260
253
quote ! {
261
- let mut #diag = #sess. struct_warn_with_code (
254
+ let mut #diag = #sess. struct_warn (
262
255
rustc_errors:: DiagnosticMessage :: fluent( #slug) ,
263
- rustc_errors:: DiagnosticId :: Error ( #code. to_string( ) )
264
256
) ;
265
257
}
266
258
}
@@ -363,9 +355,9 @@ struct SessionDiagnosticDeriveBuilder<'a> {
363
355
/// Slug is a mandatory part of the struct attribute as corresponds to the Fluent message that
364
356
/// has the actual diagnostic message.
365
357
slug : Option < ( String , proc_macro:: Span ) > ,
366
- /// Error codes are a mandatory part of the struct attribute. Slugs may replace error codes
367
- /// in future but it is desirable to mandate error codes until such a time .
368
- code : Option < ( String , proc_macro:: Span ) > ,
358
+ /// Error codes are a optional part of the struct attribute - this is only set to detect
359
+ /// multiple specifications .
360
+ code : Option < proc_macro:: Span > ,
369
361
}
370
362
371
363
impl < ' a > SessionDiagnosticDeriveBuilder < ' a > {
@@ -403,6 +395,7 @@ impl<'a> SessionDiagnosticDeriveBuilder<'a> {
403
395
} ;
404
396
self . set_kind_once ( kind, span) ?;
405
397
398
+ let mut tokens = Vec :: new ( ) ;
406
399
for attr in nested {
407
400
let span = attr. span ( ) . unwrap ( ) ;
408
401
let meta = match attr {
@@ -427,7 +420,7 @@ impl<'a> SessionDiagnosticDeriveBuilder<'a> {
427
420
self . set_slug_once ( s. value ( ) , s. span ( ) . unwrap ( ) ) ;
428
421
}
429
422
"code" => {
430
- self . set_code_once ( s. value ( ) , s. span ( ) . unwrap ( ) ) ;
423
+ tokens . push ( self . set_code_once ( s. value ( ) , s. span ( ) . unwrap ( ) ) ) ;
431
424
}
432
425
other => {
433
426
let diag = span_err (
@@ -475,7 +468,7 @@ impl<'a> SessionDiagnosticDeriveBuilder<'a> {
475
468
}
476
469
}
477
470
478
- Ok ( quote ! { } )
471
+ Ok ( tokens . drain ( .. ) . collect ( ) )
479
472
}
480
473
481
474
#[ must_use]
@@ -504,17 +497,20 @@ impl<'a> SessionDiagnosticDeriveBuilder<'a> {
504
497
}
505
498
}
506
499
507
- fn set_code_once ( & mut self , code : String , span : proc_macro:: Span ) {
500
+ fn set_code_once ( & mut self , code : String , span : proc_macro:: Span ) -> proc_macro2 :: TokenStream {
508
501
match self . code {
509
502
None => {
510
- self . code = Some ( ( code , span) ) ;
503
+ self . code = Some ( span) ;
511
504
}
512
- Some ( ( _ , prev_span) ) => {
505
+ Some ( prev_span) => {
513
506
span_err ( span, "`code` specified multiple times" )
514
507
. span_note ( prev_span, "previously specified here" )
515
508
. emit ( ) ;
516
509
}
517
510
}
511
+
512
+ let diag = & self . diag ;
513
+ quote ! { #diag. code( rustc_errors:: DiagnosticId :: Error ( #code. to_string( ) ) ) ; }
518
514
}
519
515
520
516
fn set_slug_once ( & mut self , slug : String , span : proc_macro:: Span ) {
0 commit comments