diff options
| author | Vadim Petrochenkov <vadim.petrochenkov@gmail.com> | 2018-07-12 13:24:59 +0300 |
|---|---|---|
| committer | Vadim Petrochenkov <vadim.petrochenkov@gmail.com> | 2018-07-14 20:10:07 +0300 |
| commit | 431aefb2d4d579b152f7f26f3e70d2fdc3db4bfb (patch) | |
| tree | c30139184897e67a9138bc21109ddb0be9064f7f /src/librustc_resolve | |
| parent | 1731f0af22af16c461b2b7abe58988b8549b2de6 (diff) | |
| download | rust-431aefb2d4d579b152f7f26f3e70d2fdc3db4bfb.tar.gz rust-431aefb2d4d579b152f7f26f3e70d2fdc3db4bfb.zip | |
Functions introducing procedural macros reserve a slot in the macro namespace as well
Diffstat (limited to 'src/librustc_resolve')
| -rw-r--r-- | src/librustc_resolve/build_reduced_graph.rs | 20 | ||||
| -rw-r--r-- | src/librustc_resolve/macros.rs | 17 |
2 files changed, 34 insertions, 3 deletions
diff --git a/src/librustc_resolve/build_reduced_graph.rs b/src/librustc_resolve/build_reduced_graph.rs index a770f078404..29312912a24 100644 --- a/src/librustc_resolve/build_reduced_graph.rs +++ b/src/librustc_resolve/build_reduced_graph.rs @@ -34,7 +34,7 @@ use syntax::attr; use syntax::ast::{self, Block, ForeignItem, ForeignItemKind, Item, ItemKind, NodeId}; use syntax::ast::{Mutability, StmtKind, TraitItem, TraitItemKind, Variant}; -use syntax::ext::base::SyntaxExtension; +use syntax::ext::base::{MacroKind, SyntaxExtension}; use syntax::ext::base::Determinacy::Undetermined; use syntax::ext::hygiene::Mark; use syntax::ext::tt::macro_rules; @@ -335,6 +335,24 @@ impl<'a> Resolver<'a> { ItemKind::Fn(..) => { let def = Def::Fn(self.definitions.local_def_id(item.id)); self.define(parent, ident, ValueNS, (def, vis, sp, expansion)); + + // Functions introducing procedural macros reserve a slot + // in the macro namespace as well (see #52225). + if attr::contains_name(&item.attrs, "proc_macro") || + attr::contains_name(&item.attrs, "proc_macro_attribute") { + let def = Def::Macro(def.def_id(), MacroKind::ProcMacroStub); + self.define(parent, ident, MacroNS, (def, vis, sp, expansion)); + } + if let Some(attr) = attr::find_by_name(&item.attrs, "proc_macro_derive") { + if let Some(trait_attr) = + attr.meta_item_list().and_then(|list| list.get(0).cloned()) { + if let Some(ident) = trait_attr.name().map(Ident::with_empty_ctxt) { + let sp = trait_attr.span; + let def = Def::Macro(def.def_id(), MacroKind::ProcMacroStub); + self.define(parent, ident, MacroNS, (def, vis, sp, expansion)); + } + } + } } // These items live in the type namespace. diff --git a/src/librustc_resolve/macros.rs b/src/librustc_resolve/macros.rs index 024506ed7f8..c99172efc7c 100644 --- a/src/librustc_resolve/macros.rs +++ b/src/librustc_resolve/macros.rs @@ -321,6 +321,10 @@ impl<'a> base::Resolver for Resolver<'a> { InvocationKind::Attr { attr: None, .. } => return Ok(None), _ => self.resolve_invoc_to_def(invoc, scope, force)?, }; + if let Def::Macro(_, MacroKind::ProcMacroStub) = def { + self.report_proc_macro_stub(invoc.span()); + return Err(Determinacy::Determined); + } let def_id = def.def_id(); self.macro_defs.insert(invoc.expansion_data.mark, def_id); @@ -338,9 +342,13 @@ impl<'a> base::Resolver for Resolver<'a> { fn resolve_macro(&mut self, scope: Mark, path: &ast::Path, kind: MacroKind, force: bool) -> Result<Lrc<SyntaxExtension>, Determinacy> { - self.resolve_macro_to_def(scope, path, kind, force).map(|def| { + self.resolve_macro_to_def(scope, path, kind, force).and_then(|def| { + if let Def::Macro(_, MacroKind::ProcMacroStub) = def { + self.report_proc_macro_stub(path.span); + return Err(Determinacy::Determined); + } self.unused_macros.remove(&def.def_id()); - self.get_macro(def) + Ok(self.get_macro(def)) }) } @@ -363,6 +371,11 @@ impl<'a> base::Resolver for Resolver<'a> { } impl<'a> Resolver<'a> { + fn report_proc_macro_stub(&self, span: Span) { + self.session.span_err(span, + "can't use a procedural macro from the same crate that defines it"); + } + fn resolve_invoc_to_def(&mut self, invoc: &mut Invocation, scope: Mark, force: bool) -> Result<Def, Determinacy> { let (attr, traits, item) = match invoc.kind { |
