diff options
| author | Zack M. Davis <code@zackmdavis.net> | 2017-09-21 20:29:29 -0700 |
|---|---|---|
| committer | Zack M. Davis <code@zackmdavis.net> | 2017-09-21 21:20:31 -0700 |
| commit | 083f053294b062e12bacfea17a07f83e1b4c3732 (patch) | |
| tree | e6a5bee5c9d9085fd2638dcab4e01907a8695ada /src/libsyntax/ext | |
| parent | 35176867f62f76b9bc27267878f2d74d9c776221 (diff) | |
| download | rust-083f053294b062e12bacfea17a07f83e1b4c3732.tar.gz rust-083f053294b062e12bacfea17a07f83e1b4c3732.zip | |
suggest an outer attribute when `#![derive(...)]` (predictably) fails
Diffstat (limited to 'src/libsyntax/ext')
| -rw-r--r-- | src/libsyntax/ext/base.rs | 4 | ||||
| -rw-r--r-- | src/libsyntax/ext/expand.rs | 18 |
2 files changed, 17 insertions, 5 deletions
diff --git a/src/libsyntax/ext/base.rs b/src/libsyntax/ext/base.rs index c139cfeaebf..0e05cce35e2 100644 --- a/src/libsyntax/ext/base.rs +++ b/src/libsyntax/ext/base.rs @@ -783,6 +783,10 @@ impl<'a> ExtCtxt<'a> { pub fn span_err(&self, sp: Span, msg: &str) { self.parse_sess.span_diagnostic.span_err(sp, msg); } + pub fn mut_span_err(&self, sp: Span, msg: &str) + -> DiagnosticBuilder<'a> { + self.parse_sess.span_diagnostic.mut_span_err(sp, msg) + } pub fn span_warn(&self, sp: Span, msg: &str) { self.parse_sess.span_diagnostic.span_warn(sp, msg); } diff --git a/src/libsyntax/ext/expand.rs b/src/libsyntax/ext/expand.rs index 3a1b9342530..5deb4c3cc00 100644 --- a/src/libsyntax/ext/expand.rs +++ b/src/libsyntax/ext/expand.rs @@ -292,12 +292,20 @@ impl<'a, 'b> MacroExpander<'a, 'b> { _ => false, }; if !derive_allowed { - let span = item.attrs().iter() + let attr = item.attrs().iter() .find(|attr| attr.check_name("derive")) - .expect("`derive` attribute should exist").span; - self.cx.span_err(span, - "`derive` may only be applied to structs, enums \ - and unions"); + .expect("`derive` attribute should exist"); + let span = attr.span; + let mut err = self.cx.mut_span_err(span, + "`derive` may only be applied to \ + structs, enums and unions"); + if let ast::AttrStyle::Inner = attr.style { + let trait_list = traits.iter() + .map(|t| format!("{}", t)).collect::<Vec<_>>(); + let suggestion = format!("#[derive({})]", trait_list.join(", ")); + err.span_suggestion(span, "try an outer attribute", suggestion); + } + err.emit(); } let item = item |
