about summary refs log tree commit diff
path: root/src/libsyntax
diff options
context:
space:
mode:
authorbors <bors@rust-lang.org>2018-06-27 11:20:16 +0000
committerbors <bors@rust-lang.org>2018-06-27 11:20:16 +0000
commit142c98dd5a9fbd60c13e62a5c1358a40ee622dbb (patch)
tree903290645b3895b243b4bef0a1ffc794f793ebee /src/libsyntax
parentc20824323cf7ed6ad95cb8d7b780a7934927a753 (diff)
parentd347270e0c241823d6e3333060f5ee902fffee6a (diff)
downloadrust-142c98dd5a9fbd60c13e62a5c1358a40ee622dbb.tar.gz
rust-142c98dd5a9fbd60c13e62a5c1358a40ee622dbb.zip
Auto merge of #51496 - petrochenkov:mhelper2, r=nikomatsakis
Implement `#[macro_export(local_inner_macros)]` (a solution for the macro helper import problem)

Implement a solution for the macro helper issue discussed in https://github.com/rust-lang/rust/issues/35896 as described in https://github.com/rust-lang/rust/issues/35896#issuecomment-395977901.

Macros exported from libraries can be marked with `#[macro_export(local_inner_macros)]` and this annotation changes how nested macros in them are resolved.

If we have a fn-like macro call `ident!(...)` and `ident` comes from a `macro_rules!` macro marked with  `#[macro_export(local_inner_macros)]` then it's replaced with `$crate::ident!(...)` and resolved as such (`$crate` gets the same context as `ident`).
Diffstat (limited to 'src/libsyntax')
-rw-r--r--src/libsyntax/ext/base.rs3
-rw-r--r--src/libsyntax/ext/derive.rs1
-rw-r--r--src/libsyntax/ext/expand.rs10
-rw-r--r--src/libsyntax/ext/tt/macro_rules.rs7
-rw-r--r--src/libsyntax/std_inject.rs1
-rw-r--r--src/libsyntax/test.rs1
6 files changed, 22 insertions, 1 deletions
diff --git a/src/libsyntax/ext/base.rs b/src/libsyntax/ext/base.rs
index 16d786dd6ca..9afce74f53c 100644
--- a/src/libsyntax/ext/base.rs
+++ b/src/libsyntax/ext/base.rs
@@ -621,6 +621,9 @@ pub enum SyntaxExtension {
         /// Whether the contents of the macro can use `unsafe`
         /// without triggering the `unsafe_code` lint.
         allow_internal_unsafe: bool,
+        /// Enables the macro helper hack (`ident!(...)` -> `$crate::ident!(...)`)
+        /// for a given macro.
+        local_inner_macros: bool,
         /// The macro's feature name if it is unstable, and the stability feature
         unstable_feature: Option<(Symbol, u32)>,
         /// Edition of the crate in which the macro is defined
diff --git a/src/libsyntax/ext/derive.rs b/src/libsyntax/ext/derive.rs
index 940fb6405f1..32ace937ac0 100644
--- a/src/libsyntax/ext/derive.rs
+++ b/src/libsyntax/ext/derive.rs
@@ -64,6 +64,7 @@ pub fn add_derived_markers<T>(cx: &mut ExtCtxt, span: Span, traits: &[ast::Path]
         format: ExpnFormat::MacroAttribute(Symbol::intern(&pretty_name)),
         allow_internal_unstable: true,
         allow_internal_unsafe: false,
+        local_inner_macros: false,
         edition: hygiene::default_edition(),
     });
 
diff --git a/src/libsyntax/ext/expand.rs b/src/libsyntax/ext/expand.rs
index 69c99c63aaf..23880c1270f 100644
--- a/src/libsyntax/ext/expand.rs
+++ b/src/libsyntax/ext/expand.rs
@@ -542,6 +542,7 @@ impl<'a, 'b> MacroExpander<'a, 'b> {
             format: MacroAttribute(Symbol::intern(&format!("{}", attr.path))),
             allow_internal_unstable: false,
             allow_internal_unsafe: false,
+            local_inner_macros: false,
             edition: ext.edition(),
         });
 
@@ -695,6 +696,7 @@ impl<'a, 'b> MacroExpander<'a, 'b> {
                                           def_site_span: Option<Span>,
                                           allow_internal_unstable,
                                           allow_internal_unsafe,
+                                          local_inner_macros,
                                           // can't infer this type
                                           unstable_feature: Option<(Symbol, u32)>,
                                           edition| {
@@ -729,6 +731,7 @@ impl<'a, 'b> MacroExpander<'a, 'b> {
                 format: macro_bang_format(path),
                 allow_internal_unstable,
                 allow_internal_unsafe,
+                local_inner_macros,
                 edition,
             });
             Ok(())
@@ -737,7 +740,7 @@ impl<'a, 'b> MacroExpander<'a, 'b> {
         let opt_expanded = match *ext {
             DeclMacro(ref expand, def_span, edition) => {
                 if let Err(dummy_span) = validate_and_set_expn_info(self, def_span.map(|(_, s)| s),
-                                                                    false, false, None,
+                                                                    false, false, false, None,
                                                                     edition) {
                     dummy_span
                 } else {
@@ -750,12 +753,14 @@ impl<'a, 'b> MacroExpander<'a, 'b> {
                 def_info,
                 allow_internal_unstable,
                 allow_internal_unsafe,
+                local_inner_macros,
                 unstable_feature,
                 edition,
             } => {
                 if let Err(dummy_span) = validate_and_set_expn_info(self, def_info.map(|(_, s)| s),
                                                                     allow_internal_unstable,
                                                                     allow_internal_unsafe,
+                                                                    local_inner_macros,
                                                                     unstable_feature,
                                                                     edition) {
                     dummy_span
@@ -777,6 +782,7 @@ impl<'a, 'b> MacroExpander<'a, 'b> {
                         format: macro_bang_format(path),
                         allow_internal_unstable,
                         allow_internal_unsafe: false,
+                        local_inner_macros: false,
                         edition: hygiene::default_edition(),
                     });
 
@@ -816,6 +822,7 @@ impl<'a, 'b> MacroExpander<'a, 'b> {
                         // FIXME probably want to follow macro_rules macros here.
                         allow_internal_unstable,
                         allow_internal_unsafe: false,
+                        local_inner_macros: false,
                         edition,
                     });
 
@@ -890,6 +897,7 @@ impl<'a, 'b> MacroExpander<'a, 'b> {
             format: MacroAttribute(pretty_name),
             allow_internal_unstable: false,
             allow_internal_unsafe: false,
+            local_inner_macros: false,
             edition: ext.edition(),
         };
 
diff --git a/src/libsyntax/ext/tt/macro_rules.rs b/src/libsyntax/ext/tt/macro_rules.rs
index 4ee5357f476..3b3892729d9 100644
--- a/src/libsyntax/ext/tt/macro_rules.rs
+++ b/src/libsyntax/ext/tt/macro_rules.rs
@@ -286,6 +286,12 @@ pub fn compile(sess: &ParseSess, features: &Features, def: &ast::Item, edition:
     if body.legacy {
         let allow_internal_unstable = attr::contains_name(&def.attrs, "allow_internal_unstable");
         let allow_internal_unsafe = attr::contains_name(&def.attrs, "allow_internal_unsafe");
+        let mut local_inner_macros = false;
+        if let Some(macro_export) = attr::find_by_name(&def.attrs, "macro_export") {
+            if let Some(l) = macro_export.meta_item_list() {
+                local_inner_macros = attr::list_contains_name(&l, "local_inner_macros");
+            }
+        }
 
         let unstable_feature = attr::find_stability(&sess.span_diagnostic,
                                                     &def.attrs, def.span).and_then(|stability| {
@@ -301,6 +307,7 @@ pub fn compile(sess: &ParseSess, features: &Features, def: &ast::Item, edition:
             def_info: Some((def.id, def.span)),
             allow_internal_unstable,
             allow_internal_unsafe,
+            local_inner_macros,
             unstable_feature,
             edition,
         }
diff --git a/src/libsyntax/std_inject.rs b/src/libsyntax/std_inject.rs
index 66e8e0d7a9c..68121d42b69 100644
--- a/src/libsyntax/std_inject.rs
+++ b/src/libsyntax/std_inject.rs
@@ -29,6 +29,7 @@ fn ignored_span(sp: Span) -> Span {
         format: MacroAttribute(Symbol::intern("std_inject")),
         allow_internal_unstable: true,
         allow_internal_unsafe: false,
+        local_inner_macros: false,
         edition: hygiene::default_edition(),
     });
     sp.with_ctxt(SyntaxContext::empty().apply_mark(mark))
diff --git a/src/libsyntax/test.rs b/src/libsyntax/test.rs
index 141fd122ff5..51fbe34028e 100644
--- a/src/libsyntax/test.rs
+++ b/src/libsyntax/test.rs
@@ -311,6 +311,7 @@ fn generate_test_harness(sess: &ParseSess,
         format: MacroAttribute(Symbol::intern("test")),
         allow_internal_unstable: true,
         allow_internal_unsafe: false,
+        local_inner_macros: false,
         edition: hygiene::default_edition(),
     });