From 16918a8e28d4e7a476f31ff3d3c1e2d998c086af Mon Sep 17 00:00:00 2001 From: Vadim Petrochenkov Date: Wed, 19 Jun 2019 01:08:45 +0300 Subject: Rename some things in `syntax_pos/hygiene` More consistent with other naming: ExpnFormat -> ExpnKind ExpnKind::name -> ExpnKind::descr DesugaringKind::name -> DesugaringKind::descr Shorter, no tautology: CompilerDesugaring -> Desugaring CompilerDesugaringKind -> DesugaringKind --- src/libsyntax_ext/proc_macro_decls.rs | 4 ++-- src/libsyntax_ext/test.rs | 4 ++-- src/libsyntax_ext/test_case.rs | 4 ++-- 3 files changed, 6 insertions(+), 6 deletions(-) (limited to 'src/libsyntax_ext') diff --git a/src/libsyntax_ext/proc_macro_decls.rs b/src/libsyntax_ext/proc_macro_decls.rs index 45e65288a24..dee8f4b3eb5 100644 --- a/src/libsyntax_ext/proc_macro_decls.rs +++ b/src/libsyntax_ext/proc_macro_decls.rs @@ -4,7 +4,7 @@ use crate::deriving; use syntax::ast::{self, Ident}; use syntax::attr; -use syntax::source_map::{ExpnInfo, MacroAttribute, respan}; +use syntax::source_map::{ExpnInfo, ExpnKind, respan}; use syntax::ext::base::ExtCtxt; use syntax::ext::build::AstBuilder; use syntax::ext::expand::ExpansionConfig; @@ -348,7 +348,7 @@ fn mk_decls( ) -> P { let mark = Mark::fresh(Mark::root()); mark.set_expn_info(ExpnInfo::with_unstable( - MacroAttribute(sym::proc_macro), DUMMY_SP, cx.parse_sess.edition, + ExpnKind::MacroAttribute(sym::proc_macro), DUMMY_SP, cx.parse_sess.edition, &[sym::rustc_attrs, Symbol::intern("proc_macro_internals")], )); let span = DUMMY_SP.apply_mark(mark); diff --git a/src/libsyntax_ext/test.rs b/src/libsyntax_ext/test.rs index 24d3055e711..7f4f1fd7e01 100644 --- a/src/libsyntax_ext/test.rs +++ b/src/libsyntax_ext/test.rs @@ -9,7 +9,7 @@ use syntax::ast; use syntax::print::pprust; use syntax::symbol::{Symbol, sym}; use syntax_pos::Span; -use syntax::source_map::{ExpnInfo, MacroAttribute}; +use syntax::source_map::{ExpnInfo, ExpnKind}; use std::iter; pub fn expand_test( @@ -63,7 +63,7 @@ pub fn expand_test_or_bench( let (sp, attr_sp) = { let mark = Mark::fresh(Mark::root()); mark.set_expn_info(ExpnInfo::with_unstable( - MacroAttribute(sym::test), attr_sp, cx.parse_sess.edition, + ExpnKind::MacroAttribute(sym::test), attr_sp, cx.parse_sess.edition, &[sym::rustc_attrs, sym::test], )); (item.span.with_ctxt(SyntaxContext::empty().apply_mark(mark)), diff --git a/src/libsyntax_ext/test_case.rs b/src/libsyntax_ext/test_case.rs index 186673c142f..5f88e2e098a 100644 --- a/src/libsyntax_ext/test_case.rs +++ b/src/libsyntax_ext/test_case.rs @@ -16,7 +16,7 @@ use syntax::ast; use syntax::source_map::respan; use syntax::symbol::sym; use syntax_pos::Span; -use syntax::source_map::{ExpnInfo, MacroAttribute}; +use syntax::source_map::{ExpnInfo, ExpnKind}; pub fn expand( ecx: &mut ExtCtxt<'_>, @@ -29,7 +29,7 @@ pub fn expand( let sp = { let mark = Mark::fresh(Mark::root()); mark.set_expn_info(ExpnInfo::with_unstable( - MacroAttribute(sym::test_case), attr_sp, ecx.parse_sess.edition, + ExpnKind::MacroAttribute(sym::test_case), attr_sp, ecx.parse_sess.edition, &[sym::test, sym::rustc_attrs], )); attr_sp.with_ctxt(SyntaxContext::empty().apply_mark(mark)) -- cgit 1.4.1-3-g733a5 From f1d4ebf01505877ff36ba63f8a26ea8ea0973969 Mon Sep 17 00:00:00 2001 From: Vadim Petrochenkov Date: Thu, 20 Jun 2019 02:33:39 +0300 Subject: Remove unnecessary expansions created by `#[test_case/test/bench]` The expansions were created to allow unstable things inside `#[test_case/test/bench]`, but that's not a proper way to do that. Put the required `allow_internal_unstable`s into the macros' properties instead. --- src/libcore/macros.rs | 3 +++ src/libsyntax_ext/lib.rs | 24 ++++++++++++++++-------- src/libsyntax_ext/test.rs | 14 +++----------- src/libsyntax_ext/test_case.rs | 14 ++------------ 4 files changed, 24 insertions(+), 31 deletions(-) (limited to 'src/libsyntax_ext') diff --git a/src/libcore/macros.rs b/src/libcore/macros.rs index 2e999a0682b..293a2dd9492 100644 --- a/src/libcore/macros.rs +++ b/src/libcore/macros.rs @@ -1244,12 +1244,14 @@ mod builtin { /// Attribute macro applied to a function to turn it into a unit test. #[stable(feature = "rust1", since = "1.0.0")] + #[allow_internal_unstable(test, rustc_attrs)] #[rustc_builtin_macro] #[rustc_macro_transparency = "semitransparent"] pub macro test($item:item) { /* compiler built-in */ } /// Attribute macro applied to a function to turn it into a benchmark test. #[stable(feature = "rust1", since = "1.0.0")] + #[allow_internal_unstable(test, rustc_attrs)] #[rustc_builtin_macro] #[rustc_macro_transparency = "semitransparent"] pub macro bench($item:item) { /* compiler built-in */ } @@ -1257,6 +1259,7 @@ mod builtin { /// An implementation detail of the `#[test]` and `#[bench]` macros. #[unstable(feature = "custom_test_frameworks", issue = "50297", reason = "custom test frameworks are an unstable feature")] + #[allow_internal_unstable(test, rustc_attrs)] #[rustc_builtin_macro] #[rustc_macro_transparency = "semitransparent"] pub macro test_case($item:item) { /* compiler built-in */ } diff --git a/src/libsyntax_ext/lib.rs b/src/libsyntax_ext/lib.rs index 62530f4fe7b..da0f8ca6da0 100644 --- a/src/libsyntax_ext/lib.rs +++ b/src/libsyntax_ext/lib.rs @@ -72,6 +72,7 @@ pub fn register_builtins(resolver: &mut dyn syntax::ext::base::Resolver, let mut register = |name, ext| { resolver.add_builtin(ast::Ident::with_empty_ctxt(name), Lrc::new(ext)); }; + macro_rules! register { ($( $name:ident: $f:expr, )*) => { $( register(sym::$name, SyntaxExtension::default( @@ -125,24 +126,31 @@ pub fn register_builtins(resolver: &mut dyn syntax::ext::base::Resolver, trace_macros: trace_macros::expand_trace_macros, } + let allow_internal_unstable = Some([sym::test, sym::rustc_attrs][..].into()); register(sym::test_case, SyntaxExtension { stability: Some(Stability::unstable( sym::custom_test_frameworks, Some(Symbol::intern(EXPLAIN_CUSTOM_TEST_FRAMEWORKS)), 50297, )), + allow_internal_unstable: allow_internal_unstable.clone(), ..SyntaxExtension::default( SyntaxExtensionKind::LegacyAttr(Box::new(test_case::expand)), edition ) }); - register(sym::test, SyntaxExtension::default( - SyntaxExtensionKind::LegacyAttr(Box::new(test::expand_test)), edition - )); - register(sym::bench, SyntaxExtension::default( - SyntaxExtensionKind::LegacyAttr(Box::new(test::expand_bench)), edition - )); - - // format_args uses `unstable` things internally. + register(sym::test, SyntaxExtension { + allow_internal_unstable: allow_internal_unstable.clone(), + ..SyntaxExtension::default( + SyntaxExtensionKind::LegacyAttr(Box::new(test::expand_test)), edition + ) + }); + register(sym::bench, SyntaxExtension { + allow_internal_unstable, + ..SyntaxExtension::default( + SyntaxExtensionKind::LegacyAttr(Box::new(test::expand_bench)), edition + ) + }); + let allow_internal_unstable = Some([sym::fmt_internals][..].into()); register(sym::format_args, SyntaxExtension { allow_internal_unstable: allow_internal_unstable.clone(), diff --git a/src/libsyntax_ext/test.rs b/src/libsyntax_ext/test.rs index 7f4f1fd7e01..c5c5ef57b31 100644 --- a/src/libsyntax_ext/test.rs +++ b/src/libsyntax_ext/test.rs @@ -3,13 +3,12 @@ use syntax::ext::base::*; use syntax::ext::build::AstBuilder; -use syntax::ext::hygiene::{Mark, SyntaxContext}; +use syntax::ext::hygiene::SyntaxContext; use syntax::attr; use syntax::ast; use syntax::print::pprust; use syntax::symbol::{Symbol, sym}; use syntax_pos::Span; -use syntax::source_map::{ExpnInfo, ExpnKind}; use std::iter; pub fn expand_test( @@ -60,15 +59,8 @@ pub fn expand_test_or_bench( return vec![Annotatable::Item(item)]; } - let (sp, attr_sp) = { - let mark = Mark::fresh(Mark::root()); - mark.set_expn_info(ExpnInfo::with_unstable( - ExpnKind::MacroAttribute(sym::test), attr_sp, cx.parse_sess.edition, - &[sym::rustc_attrs, sym::test], - )); - (item.span.with_ctxt(SyntaxContext::empty().apply_mark(mark)), - attr_sp.with_ctxt(SyntaxContext::empty().apply_mark(mark))) - }; + let ctxt = SyntaxContext::empty().apply_mark(cx.current_expansion.mark); + let (sp, attr_sp) = (item.span.with_ctxt(ctxt), attr_sp.with_ctxt(ctxt)); // Gensym "test" so we can extern crate without conflicting with any local names let test_id = cx.ident_of("test").gensym(); diff --git a/src/libsyntax_ext/test_case.rs b/src/libsyntax_ext/test_case.rs index 5f88e2e098a..af2cf42e04b 100644 --- a/src/libsyntax_ext/test_case.rs +++ b/src/libsyntax_ext/test_case.rs @@ -11,12 +11,11 @@ use syntax::ext::base::*; use syntax::ext::build::AstBuilder; -use syntax::ext::hygiene::{Mark, SyntaxContext}; +use syntax::ext::hygiene::SyntaxContext; use syntax::ast; use syntax::source_map::respan; use syntax::symbol::sym; use syntax_pos::Span; -use syntax::source_map::{ExpnInfo, ExpnKind}; pub fn expand( ecx: &mut ExtCtxt<'_>, @@ -26,17 +25,8 @@ pub fn expand( ) -> Vec { if !ecx.ecfg.should_test { return vec![]; } - let sp = { - let mark = Mark::fresh(Mark::root()); - mark.set_expn_info(ExpnInfo::with_unstable( - ExpnKind::MacroAttribute(sym::test_case), attr_sp, ecx.parse_sess.edition, - &[sym::test, sym::rustc_attrs], - )); - attr_sp.with_ctxt(SyntaxContext::empty().apply_mark(mark)) - }; - + let sp = attr_sp.with_ctxt(SyntaxContext::empty().apply_mark(ecx.current_expansion.mark)); let mut item = anno_item.expect_item(); - item = item.map(|mut item| { item.vis = respan(item.vis.span, ast::VisibilityKind::Public); item.ident = item.ident.gensym(); -- cgit 1.4.1-3-g733a5 From aff9738462e8959c0a3eef57124b08d5f811cdec Mon Sep 17 00:00:00 2001 From: Vadim Petrochenkov Date: Sun, 30 Jun 2019 15:58:56 +0300 Subject: hygiene: Reuse `MacroKind` in `ExpnKind` Orthogonality and reuse are good. --- src/librustc/ich/impls_syntax.rs | 3 +-- src/librustc/lint/mod.rs | 19 ++++++++---------- src/librustc_allocator/expand.rs | 4 ++-- src/librustc_resolve/macros.rs | 38 +++++++++++++++++------------------ src/librustc_save_analysis/lib.rs | 3 ++- src/libsyntax/ext/base.rs | 12 ++--------- src/libsyntax/ext/derive.rs | 9 ++++----- src/libsyntax/std_inject.rs | 5 +++-- src/libsyntax/test.rs | 4 ++-- src/libsyntax_ext/proc_macro_decls.rs | 4 ++-- src/libsyntax_pos/hygiene.rs | 34 +++++++++++++++---------------- src/libsyntax_pos/lib.rs | 9 ++++++--- 12 files changed, 67 insertions(+), 77 deletions(-) (limited to 'src/libsyntax_ext') diff --git a/src/librustc/ich/impls_syntax.rs b/src/librustc/ich/impls_syntax.rs index f679a65c642..69e8c355019 100644 --- a/src/librustc/ich/impls_syntax.rs +++ b/src/librustc/ich/impls_syntax.rs @@ -408,8 +408,7 @@ impl_stable_hash_for!(struct ::syntax_pos::hygiene::ExpnInfo { }); impl_stable_hash_for!(enum ::syntax_pos::hygiene::ExpnKind { - MacroAttribute(sym), - MacroBang(sym), + Macro(kind, descr), Desugaring(kind) }); diff --git a/src/librustc/lint/mod.rs b/src/librustc/lint/mod.rs index 9876d6c1fa5..3c8b0041a98 100644 --- a/src/librustc/lint/mod.rs +++ b/src/librustc/lint/mod.rs @@ -38,6 +38,7 @@ use syntax::ast; use syntax::source_map::{MultiSpan, ExpnKind, DesugaringKind}; use syntax::early_buffered_lints::BufferedEarlyLintId; use syntax::edition::Edition; +use syntax::ext::base::MacroKind; use syntax::symbol::{Symbol, sym}; use syntax_pos::Span; @@ -884,10 +885,9 @@ pub fn in_external_macro(sess: &Session, span: Span) -> bool { }; match info.kind { - ExpnKind::MacroAttribute(..) => true, // definitely a plugin ExpnKind::Desugaring(DesugaringKind::ForLoop) => false, ExpnKind::Desugaring(_) => true, // well, it's "external" - ExpnKind::MacroBang(..) => { + ExpnKind::Macro(MacroKind::Bang, _) => { if info.def_site.is_dummy() { // dummy span for the def_site means it's an external macro return true; @@ -898,19 +898,16 @@ pub fn in_external_macro(sess: &Session, span: Span) -> bool { Err(_) => true, } } + ExpnKind::Macro(..) => true, // definitely a plugin } } /// Returns whether `span` originates in a derive macro's expansion pub fn in_derive_expansion(span: Span) -> bool { - let info = match span.ctxt().outer_expn_info() { - Some(info) => info, - // no ExpnInfo means this span doesn't come from a macro - None => return false, - }; - - match info.kind { - ExpnKind::MacroAttribute(symbol) => symbol.as_str().starts_with("derive("), - _ => false, + if let Some(info) = span.ctxt().outer_expn_info() { + if let ExpnKind::Macro(MacroKind::Derive, _) = info.kind { + return true; + } } + false } diff --git a/src/librustc_allocator/expand.rs b/src/librustc_allocator/expand.rs index 18bbb257128..d0eefbb1179 100644 --- a/src/librustc_allocator/expand.rs +++ b/src/librustc_allocator/expand.rs @@ -11,7 +11,7 @@ use syntax::{ respan, ExpnInfo, ExpnKind, }, ext::{ - base::{ExtCtxt, Resolver}, + base::{ExtCtxt, MacroKind, Resolver}, build::AstBuilder, expand::ExpansionConfig, hygiene::{Mark, SyntaxContext}, @@ -87,7 +87,7 @@ impl MutVisitor for ExpandAllocatorDirectives<'_> { // Create a fresh Mark for the new macro expansion we are about to do let mark = Mark::fresh(Mark::root()); mark.set_expn_info(ExpnInfo::with_unstable( - ExpnKind::MacroAttribute(sym::global_allocator), item.span, self.sess.edition, + ExpnKind::Macro(MacroKind::Attr, sym::global_allocator), item.span, self.sess.edition, &[sym::rustc_attrs], )); diff --git a/src/librustc_resolve/macros.rs b/src/librustc_resolve/macros.rs index 61300e3ee3c..7f57b0a5052 100644 --- a/src/librustc_resolve/macros.rs +++ b/src/librustc_resolve/macros.rs @@ -114,17 +114,21 @@ fn sub_namespace_match(candidate: Option, requirement: Option String { - let mut path_str = String::with_capacity(64); - for (i, segment) in path.segments.iter().enumerate() { - if i != 0 { - path_str.push_str("::"); - } - if segment.ident.name != kw::PathRoot { - path_str.push_str(&segment.ident.as_str()) +fn fast_print_path(path: &ast::Path) -> Symbol { + if path.segments.len() == 1 { + return path.segments[0].ident.name + } else { + let mut path_str = String::with_capacity(64); + for (i, segment) in path.segments.iter().enumerate() { + if i != 0 { + path_str.push_str("::"); + } + if segment.ident.name != kw::PathRoot { + path_str.push_str(&segment.ident.as_str()) + } } + Symbol::intern(&path_str) } - path_str } impl<'a> base::Resolver for Resolver<'a> { @@ -219,14 +223,10 @@ impl<'a> base::Resolver for Resolver<'a> { }; let span = invoc.span(); - let path = fast_print_path(path); - let format = match kind { - MacroKind::Derive => format!("derive({})", path), - _ => path.clone(), - }; - invoc.expansion_data.mark.set_expn_info(ext.expn_info(span, &format)); + let descr = fast_print_path(path); + invoc.expansion_data.mark.set_expn_info(ext.expn_info(span, descr)); - self.check_stability_and_deprecation(&ext, &path, span); + self.check_stability_and_deprecation(&ext, descr, span); if let Res::Def(_, def_id) = res { if after_derive { @@ -991,7 +991,7 @@ impl<'a> Resolver<'a> { } } - fn check_stability_and_deprecation(&self, ext: &SyntaxExtension, path: &str, span: Span) { + fn check_stability_and_deprecation(&self, ext: &SyntaxExtension, descr: Symbol, span: Span) { if let Some(stability) = &ext.stability { if let StabilityLevel::Unstable { reason, issue } = stability.level { let feature = stability.feature; @@ -1000,14 +1000,14 @@ impl<'a> Resolver<'a> { } } if let Some(depr) = &stability.rustc_depr { - let (message, lint) = stability::rustc_deprecation_message(depr, path); + let (message, lint) = stability::rustc_deprecation_message(depr, &descr.as_str()); stability::early_report_deprecation( self.session, &message, depr.suggestion, lint, span ); } } if let Some(depr) = &ext.deprecation { - let (message, lint) = stability::deprecation_message(depr, path); + let (message, lint) = stability::deprecation_message(depr, &descr.as_str()); stability::early_report_deprecation(self.session, &message, None, lint, span); } } diff --git a/src/librustc_save_analysis/lib.rs b/src/librustc_save_analysis/lib.rs index aeaee1887b9..2c8f7a44f5a 100644 --- a/src/librustc_save_analysis/lib.rs +++ b/src/librustc_save_analysis/lib.rs @@ -843,7 +843,8 @@ impl<'l, 'tcx> SaveContext<'l, 'tcx> { let callee = span.source_callee()?; // Ignore attribute macros, their spans are usually mangled - if let ExpnKind::MacroAttribute(_) = callee.kind { + if let ExpnKind::Macro(MacroKind::Attr, _) | + ExpnKind::Macro(MacroKind::Derive, _) = callee.kind { return None; } diff --git a/src/libsyntax/ext/base.rs b/src/libsyntax/ext/base.rs index 2f8d6f00ba7..04f124685cb 100644 --- a/src/libsyntax/ext/base.rs +++ b/src/libsyntax/ext/base.rs @@ -640,18 +640,10 @@ impl SyntaxExtension { } } - fn expn_kind(&self, descr: Symbol) -> ExpnKind { - match self.kind { - SyntaxExtensionKind::Bang(..) | - SyntaxExtensionKind::LegacyBang(..) => ExpnKind::MacroBang(descr), - _ => ExpnKind::MacroAttribute(descr), - } - } - - pub fn expn_info(&self, call_site: Span, descr: &str) -> ExpnInfo { + pub fn expn_info(&self, call_site: Span, descr: Symbol) -> ExpnInfo { ExpnInfo { call_site, - kind: self.expn_kind(Symbol::intern(descr)), + kind: ExpnKind::Macro(self.macro_kind(), descr), def_site: self.span, default_transparency: self.default_transparency, allow_internal_unstable: self.allow_internal_unstable.clone(), diff --git a/src/libsyntax/ext/derive.rs b/src/libsyntax/ext/derive.rs index 24050be792b..68e7225c3cf 100644 --- a/src/libsyntax/ext/derive.rs +++ b/src/libsyntax/ext/derive.rs @@ -1,7 +1,7 @@ use crate::attr::HasAttrs; use crate::ast; use crate::source_map::{ExpnInfo, ExpnKind}; -use crate::ext::base::ExtCtxt; +use crate::ext::base::{ExtCtxt, MacroKind}; use crate::ext::build::AstBuilder; use crate::parse::parser::PathStyle; use crate::symbol::{Symbol, sym}; @@ -46,7 +46,7 @@ pub fn collect_derives(cx: &mut ExtCtxt<'_>, attrs: &mut Vec) -> pub fn add_derived_markers(cx: &mut ExtCtxt<'_>, span: Span, traits: &[ast::Path], item: &mut T) where T: HasAttrs, { - let (mut names, mut pretty_name) = (FxHashSet::default(), "derive(".to_owned()); + let (mut names, mut pretty_name) = (FxHashSet::default(), String::new()); for (i, path) in traits.iter().enumerate() { if i > 0 { pretty_name.push_str(", "); @@ -54,11 +54,10 @@ pub fn add_derived_markers(cx: &mut ExtCtxt<'_>, span: Span, traits: &[ast::P pretty_name.push_str(&path.to_string()); names.insert(unwrap_or!(path.segments.get(0), continue).ident.name); } - pretty_name.push(')'); cx.current_expansion.mark.set_expn_info(ExpnInfo::with_unstable( - ExpnKind::MacroAttribute(Symbol::intern(&pretty_name)), span, cx.parse_sess.edition, - &[sym::rustc_attrs, sym::structural_match], + ExpnKind::Macro(MacroKind::Derive, Symbol::intern(&pretty_name)), span, + cx.parse_sess.edition, &[sym::rustc_attrs, sym::structural_match], )); let span = span.with_ctxt(cx.backtrace()); diff --git a/src/libsyntax/std_inject.rs b/src/libsyntax/std_inject.rs index 7ee073117e9..81f9ff9b661 100644 --- a/src/libsyntax/std_inject.rs +++ b/src/libsyntax/std_inject.rs @@ -1,7 +1,7 @@ use crate::ast; use crate::attr; use crate::edition::Edition; -use crate::ext::hygiene::{Mark, SyntaxContext}; +use crate::ext::hygiene::{Mark, SyntaxContext, MacroKind}; use crate::symbol::{Ident, Symbol, kw, sym}; use crate::source_map::{ExpnInfo, ExpnKind, dummy_spanned, respan}; use crate::ptr::P; @@ -17,7 +17,8 @@ use syntax_pos::{DUMMY_SP, Span}; fn ignored_span(sp: Span, edition: Edition) -> Span { let mark = Mark::fresh(Mark::root()); mark.set_expn_info(ExpnInfo::with_unstable( - ExpnKind::MacroAttribute(Symbol::intern("std_inject")), sp, edition, &[sym::prelude_import] + ExpnKind::Macro(MacroKind::Attr, Symbol::intern("std_inject")), sp, edition, + &[sym::prelude_import], )); sp.with_ctxt(SyntaxContext::empty().apply_mark(mark)) } diff --git a/src/libsyntax/test.rs b/src/libsyntax/test.rs index 35a1a552a13..7ec7bb6ff45 100644 --- a/src/libsyntax/test.rs +++ b/src/libsyntax/test.rs @@ -21,7 +21,7 @@ use crate::entry::{self, EntryPointType}; use crate::ext::base::{ExtCtxt, Resolver}; use crate::ext::build::AstBuilder; use crate::ext::expand::ExpansionConfig; -use crate::ext::hygiene::{self, Mark, SyntaxContext}; +use crate::ext::hygiene::{self, Mark, SyntaxContext, MacroKind}; use crate::mut_visit::{*, ExpectOne}; use crate::feature_gate::Features; use crate::util::map_in_place::MapInPlace; @@ -280,7 +280,7 @@ fn generate_test_harness(sess: &ParseSess, }; mark.set_expn_info(ExpnInfo::with_unstable( - ExpnKind::MacroAttribute(sym::test_case), DUMMY_SP, sess.edition, + ExpnKind::Macro(MacroKind::Attr, sym::test_case), DUMMY_SP, sess.edition, &[sym::main, sym::test, sym::rustc_attrs], )); diff --git a/src/libsyntax_ext/proc_macro_decls.rs b/src/libsyntax_ext/proc_macro_decls.rs index dee8f4b3eb5..0733a8ec95c 100644 --- a/src/libsyntax_ext/proc_macro_decls.rs +++ b/src/libsyntax_ext/proc_macro_decls.rs @@ -5,7 +5,7 @@ use crate::deriving; use syntax::ast::{self, Ident}; use syntax::attr; use syntax::source_map::{ExpnInfo, ExpnKind, respan}; -use syntax::ext::base::ExtCtxt; +use syntax::ext::base::{ExtCtxt, MacroKind}; use syntax::ext::build::AstBuilder; use syntax::ext::expand::ExpansionConfig; use syntax::ext::hygiene::Mark; @@ -348,7 +348,7 @@ fn mk_decls( ) -> P { let mark = Mark::fresh(Mark::root()); mark.set_expn_info(ExpnInfo::with_unstable( - ExpnKind::MacroAttribute(sym::proc_macro), DUMMY_SP, cx.parse_sess.edition, + ExpnKind::Macro(MacroKind::Attr, sym::proc_macro), DUMMY_SP, cx.parse_sess.edition, &[sym::rustc_attrs, Symbol::intern("proc_macro_internals")], )); let span = DUMMY_SP.apply_mark(mark); diff --git a/src/libsyntax_pos/hygiene.rs b/src/libsyntax_pos/hygiene.rs index 67dcdabe701..28d452233cc 100644 --- a/src/libsyntax_pos/hygiene.rs +++ b/src/libsyntax_pos/hygiene.rs @@ -135,11 +135,9 @@ impl Mark { pub fn looks_like_proc_macro_derive(self) -> bool { HygieneData::with(|data| { if data.default_transparency(self) == Transparency::Opaque { - if let Some(expn_info) = &data.marks[self.0 as usize].expn_info { - if let ExpnKind::MacroAttribute(name) = expn_info.kind { - if name.as_str().starts_with("derive(") { - return true; - } + if let Some(expn_info) = data.expn_info(self) { + if let ExpnKind::Macro(MacroKind::Derive, _) = expn_info.kind { + return true; } } } @@ -193,7 +191,7 @@ impl HygieneData { } fn default_transparency(&self, mark: Mark) -> Transparency { - self.marks[mark.0 as usize].expn_info.as_ref().map_or( + self.expn_info(mark).map_or( Transparency::SemiTransparent, |einfo| einfo.default_transparency ) } @@ -613,7 +611,8 @@ impl fmt::Debug for SyntaxContext { } } -/// Extra information for tracking spans of macro and syntax sugar expansion +/// A subset of properties from both macro definition and macro call available through global data. +/// Avoid using this if you have access to the original definition or call structures. #[derive(Clone, Debug, RustcEncodable, RustcDecodable)] pub struct ExpnInfo { // --- The part unique to each expansion. @@ -627,7 +626,7 @@ pub struct ExpnInfo { /// call_site span would have its own ExpnInfo, with the call_site /// pointing to the `foo!` invocation. pub call_site: Span, - /// The format with which the macro was invoked. + /// The kind of this expansion - macro or compiler desugaring. pub kind: ExpnKind, // --- The part specific to the macro/desugaring definition. @@ -675,13 +674,12 @@ impl ExpnInfo { } } -/// The source of expansion. +/// Expansion kind. #[derive(Clone, Debug, RustcEncodable, RustcDecodable)] pub enum ExpnKind { - /// e.g., #[derive(...)] - MacroAttribute(Symbol), - /// e.g., `format!()` - MacroBang(Symbol), + /// Expansion produced by a macro. + /// FIXME: Some code injected by the compiler before HIR lowering also gets this kind. + Macro(MacroKind, Symbol), /// Desugaring done by the compiler during HIR lowering. Desugaring(DesugaringKind) } @@ -689,8 +687,8 @@ pub enum ExpnKind { impl ExpnKind { pub fn descr(&self) -> Symbol { match *self { - ExpnKind::MacroBang(name) | ExpnKind::MacroAttribute(name) => name, - ExpnKind::Desugaring(kind) => kind.descr(), + ExpnKind::Macro(_, descr) => descr, + ExpnKind::Desugaring(kind) => Symbol::intern(kind.descr()), } } } @@ -743,8 +741,8 @@ pub enum DesugaringKind { } impl DesugaringKind { - pub fn descr(self) -> Symbol { - Symbol::intern(match self { + pub fn descr(self) -> &'static str { + match self { DesugaringKind::CondTemporary => "if and while condition", DesugaringKind::Async => "async", DesugaringKind::Await => "await", @@ -752,7 +750,7 @@ impl DesugaringKind { DesugaringKind::TryBlock => "try block", DesugaringKind::ExistentialType => "existential type", DesugaringKind::ForLoop => "for loop", - }) + } } } diff --git a/src/libsyntax_pos/lib.rs b/src/libsyntax_pos/lib.rs index 1369fca3b4a..4fd27ce4f96 100644 --- a/src/libsyntax_pos/lib.rs +++ b/src/libsyntax_pos/lib.rs @@ -27,7 +27,7 @@ extern crate serialize as rustc_serialize; // used by deriving pub mod edition; use edition::Edition; pub mod hygiene; -pub use hygiene::{Mark, SyntaxContext, ExpnInfo, ExpnKind, DesugaringKind}; +pub use hygiene::{Mark, SyntaxContext, ExpnInfo, ExpnKind, MacroKind, DesugaringKind}; mod span_encoding; pub use span_encoding::{Span, DUMMY_SP}; @@ -442,9 +442,12 @@ impl Span { // Don't print recursive invocations. if !info.call_site.source_equal(&prev_span) { let (pre, post) = match info.kind { - ExpnKind::MacroAttribute(..) => ("#[", "]"), - ExpnKind::MacroBang(..) => ("", "!"), ExpnKind::Desugaring(..) => ("desugaring of `", "`"), + ExpnKind::Macro(macro_kind, _) => match macro_kind { + MacroKind::Bang => ("", "!"), + MacroKind::Attr => ("#[", "]"), + MacroKind::Derive => ("#[derive(", ")]"), + } }; result.push(MacroBacktrace { call_site: info.call_site, -- cgit 1.4.1-3-g733a5 From 99c7432896bbfdab1f7f70f8d763cab5f3efe64a Mon Sep 17 00:00:00 2001 From: Vadim Petrochenkov Date: Sat, 6 Jul 2019 21:02:45 +0300 Subject: hygiene: Introduce a helper method for creating new expansions Creating a fresh expansion and immediately generating a span from it is the most common scenario. Also avoid allocating `allow_internal_unstable` lists for derive markers repeatedly. And rename `ExpnInfo::with_unstable` to `ExpnInfo::allow_unstable`, seems to be a better fitting name. --- src/librustc/hir/lowering.rs | 8 ++--- src/librustc/ty/query/on_disk_cache.rs | 45 +++++++++++++------------- src/librustc_allocator/expand.rs | 12 +++---- src/librustc_resolve/macros.rs | 7 ++-- src/libsyntax/ext/base.rs | 2 ++ src/libsyntax/ext/derive.rs | 7 ++-- src/libsyntax/ext/expand.rs | 4 +-- src/libsyntax/std_inject.rs | 22 ++++--------- src/libsyntax/test.rs | 23 +++---------- src/libsyntax_ext/proc_macro_decls.rs | 6 ++-- src/libsyntax_pos/hygiene.rs | 59 ++++++++++++++-------------------- src/libsyntax_pos/symbol.rs | 2 ++ 12 files changed, 80 insertions(+), 117 deletions(-) (limited to 'src/libsyntax_ext') diff --git a/src/librustc/hir/lowering.rs b/src/librustc/hir/lowering.rs index c44fd30be85..7e7bb5f61a3 100644 --- a/src/librustc/hir/lowering.rs +++ b/src/librustc/hir/lowering.rs @@ -60,7 +60,7 @@ use syntax::attr; use syntax::ast; use syntax::ast::*; use syntax::errors; -use syntax::ext::hygiene::{Mark, SyntaxContext}; +use syntax::ext::hygiene::Mark; use syntax::print::pprust; use syntax::source_map::{respan, ExpnInfo, ExpnKind, DesugaringKind, Spanned}; use syntax::std_inject; @@ -875,13 +875,11 @@ impl<'a> LoweringContext<'a> { span: Span, allow_internal_unstable: Option>, ) -> Span { - let mark = Mark::fresh(Mark::root()); - mark.set_expn_info(ExpnInfo { + span.fresh_expansion(Mark::root(), ExpnInfo { def_site: span, allow_internal_unstable, ..ExpnInfo::default(ExpnKind::Desugaring(reason), span, self.sess.edition()) - }); - span.with_ctxt(SyntaxContext::empty().apply_mark(mark)) + }) } fn with_anonymous_lifetime_mode( diff --git a/src/librustc/ty/query/on_disk_cache.rs b/src/librustc/ty/query/on_disk_cache.rs index 56c9474170c..d0be13a7111 100644 --- a/src/librustc/ty/query/on_disk_cache.rs +++ b/src/librustc/ty/query/on_disk_cache.rs @@ -588,41 +588,40 @@ impl<'a, 'tcx> SpecializedDecoder for CacheDecoder<'a, 'tcx> { let expn_info_tag = u8::decode(self)?; - let ctxt = match expn_info_tag { + // FIXME(mw): This method does not restore `MarkData::parent` or + // `SyntaxContextData::prev_ctxt` or `SyntaxContextData::opaque`. These things + // don't seem to be used after HIR lowering, so everything should be fine + // as long as incremental compilation does not kick in before that. + let location = || Span::new(lo, hi, SyntaxContext::empty()); + let recover_from_expn_info = |this: &Self, expn_info, pos| { + let span = location().fresh_expansion(Mark::root(), expn_info); + this.synthetic_expansion_infos.borrow_mut().insert(pos, span.ctxt()); + span + }; + Ok(match expn_info_tag { TAG_NO_EXPANSION_INFO => { - SyntaxContext::empty() + location() } TAG_EXPANSION_INFO_INLINE => { - let pos = AbsoluteBytePos::new(self.opaque.position()); - let expn_info: ExpnInfo = Decodable::decode(self)?; - let ctxt = SyntaxContext::allocate_directly(expn_info); - self.synthetic_expansion_infos.borrow_mut().insert(pos, ctxt); - ctxt + let expn_info = Decodable::decode(self)?; + recover_from_expn_info( + self, expn_info, AbsoluteBytePos::new(self.opaque.position()) + ) } TAG_EXPANSION_INFO_SHORTHAND => { let pos = AbsoluteBytePos::decode(self)?; - let cached_ctxt = self.synthetic_expansion_infos - .borrow() - .get(&pos) - .cloned(); - - if let Some(ctxt) = cached_ctxt { - ctxt + if let Some(cached_ctxt) = self.synthetic_expansion_infos.borrow().get(&pos) { + Span::new(lo, hi, *cached_ctxt) } else { - let expn_info = self.with_position(pos.to_usize(), |this| { - ExpnInfo::decode(this) - })?; - let ctxt = SyntaxContext::allocate_directly(expn_info); - self.synthetic_expansion_infos.borrow_mut().insert(pos, ctxt); - ctxt + let expn_info = + self.with_position(pos.to_usize(), |this| ExpnInfo::decode(this))?; + recover_from_expn_info(self, expn_info, pos) } } _ => { unreachable!() } - }; - - Ok(Span::new(lo, hi, ctxt)) + }) } } diff --git a/src/librustc_allocator/expand.rs b/src/librustc_allocator/expand.rs index d0eefbb1179..9803ee99f1a 100644 --- a/src/librustc_allocator/expand.rs +++ b/src/librustc_allocator/expand.rs @@ -14,7 +14,7 @@ use syntax::{ base::{ExtCtxt, MacroKind, Resolver}, build::AstBuilder, expand::ExpansionConfig, - hygiene::{Mark, SyntaxContext}, + hygiene::Mark, }, mut_visit::{self, MutVisitor}, parse::ParseSess, @@ -84,16 +84,12 @@ impl MutVisitor for ExpandAllocatorDirectives<'_> { } self.found = true; - // Create a fresh Mark for the new macro expansion we are about to do - let mark = Mark::fresh(Mark::root()); - mark.set_expn_info(ExpnInfo::with_unstable( + // Create a new expansion for the generated allocator code. + let span = item.span.fresh_expansion(Mark::root(), ExpnInfo::allow_unstable( ExpnKind::Macro(MacroKind::Attr, sym::global_allocator), item.span, self.sess.edition, - &[sym::rustc_attrs], + [sym::rustc_attrs][..].into(), )); - // Tie the span to the macro expansion info we just created - let span = item.span.with_ctxt(SyntaxContext::empty().apply_mark(mark)); - // Create an expansion config let ecfg = ExpansionConfig::default(self.crate_name.take().unwrap()); diff --git a/src/librustc_resolve/macros.rs b/src/librustc_resolve/macros.rs index 7ad54d572f4..6f276e04a5a 100644 --- a/src/librustc_resolve/macros.rs +++ b/src/librustc_resolve/macros.rs @@ -17,7 +17,7 @@ use syntax::errors::DiagnosticBuilder; use syntax::ext::base::{self, Indeterminate}; use syntax::ext::base::{MacroKind, SyntaxExtension}; use syntax::ext::expand::{AstFragment, Invocation, InvocationKind}; -use syntax::ext::hygiene::{self, Mark}; +use syntax::ext::hygiene::{self, Mark, ExpnInfo, ExpnKind}; use syntax::ext::tt::macro_rules; use syntax::feature_gate::{feature_err, emit_feature_err, is_builtin_attr_name}; use syntax::feature_gate::{AttributeGate, GateIssue, Stability, BUILTIN_ATTRIBUTES}; @@ -148,7 +148,10 @@ impl<'a> base::Resolver for Resolver<'a> { } fn get_module_scope(&mut self, id: ast::NodeId) -> Mark { - let mark = Mark::fresh(Mark::root()); + let span = DUMMY_SP.fresh_expansion(Mark::root(), ExpnInfo::default( + ExpnKind::Macro(MacroKind::Attr, sym::test_case), DUMMY_SP, self.session.edition() + )); + let mark = span.ctxt().outer(); let module = self.module_map[&self.definitions.local_def_id(id)]; self.definitions.set_invocation_parent(mark, module.def_id().unwrap().index); self.invocations.insert(mark, self.arenas.alloc_invocation_data(InvocationData { diff --git a/src/libsyntax/ext/base.rs b/src/libsyntax/ext/base.rs index cb4edee30cd..37d5885db60 100644 --- a/src/libsyntax/ext/base.rs +++ b/src/libsyntax/ext/base.rs @@ -721,6 +721,7 @@ pub struct ExtCtxt<'a> { pub resolver: &'a mut dyn Resolver, pub current_expansion: ExpansionData, pub expansions: FxHashMap>, + pub allow_derive_markers: Lrc<[Symbol]>, } impl<'a> ExtCtxt<'a> { @@ -740,6 +741,7 @@ impl<'a> ExtCtxt<'a> { directory_ownership: DirectoryOwnership::Owned { relative: None }, }, expansions: FxHashMap::default(), + allow_derive_markers: [sym::rustc_attrs, sym::structural_match][..].into(), } } diff --git a/src/libsyntax/ext/derive.rs b/src/libsyntax/ext/derive.rs index 11c1fceb7e7..1c15deab373 100644 --- a/src/libsyntax/ext/derive.rs +++ b/src/libsyntax/ext/derive.rs @@ -8,7 +8,6 @@ use crate::symbol::{Symbol, sym}; use crate::errors::Applicability; use syntax_pos::Span; -use syntax_pos::hygiene::{Mark, SyntaxContext}; use rustc_data_structures::fx::FxHashSet; pub fn collect_derives(cx: &mut ExtCtxt<'_>, attrs: &mut Vec) -> Vec { @@ -55,13 +54,11 @@ pub fn add_derived_markers(cx: &mut ExtCtxt<'_>, span: Span, traits: &[ast::P names.insert(unwrap_or!(path.segments.get(0), continue).ident.name); } - let mark = Mark::fresh(cx.current_expansion.mark); - mark.set_expn_info(ExpnInfo::with_unstable( + let span = span.fresh_expansion(cx.current_expansion.mark, ExpnInfo::allow_unstable( ExpnKind::Macro(MacroKind::Derive, Symbol::intern(&pretty_name)), span, - cx.parse_sess.edition, &[sym::rustc_attrs, sym::structural_match], + cx.parse_sess.edition, cx.allow_derive_markers.clone(), )); - let span = span.with_ctxt(SyntaxContext::empty().apply_mark(mark)); item.visit_attrs(|attrs| { if names.contains(&sym::Eq) && names.contains(&sym::PartialEq) { let meta = cx.meta_word(span, sym::structural_match); diff --git a/src/libsyntax/ext/expand.rs b/src/libsyntax/ext/expand.rs index 2349382eb5e..39a8a7af2a3 100644 --- a/src/libsyntax/ext/expand.rs +++ b/src/libsyntax/ext/expand.rs @@ -362,7 +362,7 @@ impl<'a, 'b> MacroExpander<'a, 'b> { derives.reserve(traits.len()); invocations.reserve(traits.len()); for path in traits { - let mark = Mark::fresh(self.cx.current_expansion.mark); + let mark = Mark::fresh(self.cx.current_expansion.mark, None); derives.push(mark); invocations.push(Invocation { kind: InvocationKind::Derive { @@ -847,7 +847,7 @@ struct InvocationCollector<'a, 'b> { impl<'a, 'b> InvocationCollector<'a, 'b> { fn collect(&mut self, fragment_kind: AstFragmentKind, kind: InvocationKind) -> AstFragment { - let mark = Mark::fresh(self.cx.current_expansion.mark); + let mark = Mark::fresh(self.cx.current_expansion.mark, None); self.invocations.push(Invocation { kind, fragment_kind, diff --git a/src/libsyntax/std_inject.rs b/src/libsyntax/std_inject.rs index 81f9ff9b661..d86b76f71ec 100644 --- a/src/libsyntax/std_inject.rs +++ b/src/libsyntax/std_inject.rs @@ -1,7 +1,7 @@ use crate::ast; use crate::attr; use crate::edition::Edition; -use crate::ext::hygiene::{Mark, SyntaxContext, MacroKind}; +use crate::ext::hygiene::{Mark, MacroKind}; use crate::symbol::{Ident, Symbol, kw, sym}; use crate::source_map::{ExpnInfo, ExpnKind, dummy_spanned, respan}; use crate::ptr::P; @@ -9,19 +9,7 @@ use crate::tokenstream::TokenStream; use std::cell::Cell; use std::iter; -use syntax_pos::{DUMMY_SP, Span}; - -/// Craft a span that will be ignored by the stability lint's -/// call to source_map's `is_internal` check. -/// The expanded code uses the unstable `#[prelude_import]` attribute. -fn ignored_span(sp: Span, edition: Edition) -> Span { - let mark = Mark::fresh(Mark::root()); - mark.set_expn_info(ExpnInfo::with_unstable( - ExpnKind::Macro(MacroKind::Attr, Symbol::intern("std_inject")), sp, edition, - &[sym::prelude_import], - )); - sp.with_ctxt(SyntaxContext::empty().apply_mark(mark)) -} +use syntax_pos::DUMMY_SP; pub fn injected_crate_name() -> Option<&'static str> { INJECTED_CRATE_NAME.with(|name| name.get()) @@ -87,7 +75,11 @@ pub fn maybe_inject_crates_ref( INJECTED_CRATE_NAME.with(|opt_name| opt_name.set(Some(name))); - let span = ignored_span(DUMMY_SP, edition); + let span = DUMMY_SP.fresh_expansion(Mark::root(), ExpnInfo::allow_unstable( + ExpnKind::Macro(MacroKind::Attr, sym::std_inject), DUMMY_SP, edition, + [sym::prelude_import][..].into(), + )); + krate.module.items.insert(0, P(ast::Item { attrs: vec![ast::Attribute { style: ast::AttrStyle::Outer, diff --git a/src/libsyntax/test.rs b/src/libsyntax/test.rs index 7ec7bb6ff45..799d64a9962 100644 --- a/src/libsyntax/test.rs +++ b/src/libsyntax/test.rs @@ -43,7 +43,6 @@ struct TestCtxt<'a> { test_cases: Vec, reexport_test_harness_main: Option, is_libtest: bool, - ctxt: SyntaxContext, features: &'a Features, test_runner: Option, @@ -259,8 +258,6 @@ fn generate_test_harness(sess: &ParseSess, let mut cleaner = EntryPointCleaner { depth: 0 }; cleaner.visit_crate(krate); - let mark = Mark::fresh(Mark::root()); - let mut econfig = ExpansionConfig::default("test".to_string()); econfig.features = Some(features); @@ -274,16 +271,10 @@ fn generate_test_harness(sess: &ParseSess, is_libtest: attr::find_crate_name(&krate.attrs) .map(|s| s == sym::test).unwrap_or(false), toplevel_reexport: None, - ctxt: SyntaxContext::empty().apply_mark(mark), features, test_runner }; - mark.set_expn_info(ExpnInfo::with_unstable( - ExpnKind::Macro(MacroKind::Attr, sym::test_case), DUMMY_SP, sess.edition, - &[sym::main, sym::test, sym::rustc_attrs], - )); - TestHarnessGenerator { cx, tests: Vec::new(), @@ -291,13 +282,6 @@ fn generate_test_harness(sess: &ParseSess, }.visit_crate(krate); } -/// Craft a span that will be ignored by the stability lint's -/// call to source_map's `is_internal` check. -/// The expanded code calls some unstable functions in the test crate. -fn ignored_span(cx: &TestCtxt<'_>, sp: Span) -> Span { - sp.with_ctxt(cx.ctxt) -} - enum HasTestSignature { Yes, No(BadTestSignature), @@ -314,12 +298,15 @@ enum BadTestSignature { /// Creates a function item for use as the main function of a test build. /// This function will call the `test_runner` as specified by the crate attribute fn mk_main(cx: &mut TestCtxt<'_>) -> P { - // Writing this out by hand with 'ignored_span': + // Writing this out by hand: // pub fn main() { // #![main] // test::test_main_static(&[..tests]); // } - let sp = ignored_span(cx, DUMMY_SP); + let sp = DUMMY_SP.fresh_expansion(Mark::root(), ExpnInfo::allow_unstable( + ExpnKind::Macro(MacroKind::Attr, sym::test_case), DUMMY_SP, cx.ext_cx.parse_sess.edition, + [sym::main, sym::test, sym::rustc_attrs][..].into(), + )); let ecx = &cx.ext_cx; let test_id = Ident::with_empty_ctxt(sym::test); diff --git a/src/libsyntax_ext/proc_macro_decls.rs b/src/libsyntax_ext/proc_macro_decls.rs index 0733a8ec95c..2f78644dff2 100644 --- a/src/libsyntax_ext/proc_macro_decls.rs +++ b/src/libsyntax_ext/proc_macro_decls.rs @@ -346,12 +346,10 @@ fn mk_decls( custom_attrs: &[ProcMacroDef], custom_macros: &[ProcMacroDef], ) -> P { - let mark = Mark::fresh(Mark::root()); - mark.set_expn_info(ExpnInfo::with_unstable( + let span = DUMMY_SP.fresh_expansion(Mark::root(), ExpnInfo::allow_unstable( ExpnKind::Macro(MacroKind::Attr, sym::proc_macro), DUMMY_SP, cx.parse_sess.edition, - &[sym::rustc_attrs, Symbol::intern("proc_macro_internals")], + [sym::rustc_attrs, sym::proc_macro_internals][..].into(), )); - let span = DUMMY_SP.apply_mark(mark); let hidden = cx.meta_list_item_word(span, sym::hidden); let doc = cx.meta_list(span, sym::doc, vec![hidden]); diff --git a/src/libsyntax_pos/hygiene.rs b/src/libsyntax_pos/hygiene.rs index ba2b2b7a2dd..f060bf356f6 100644 --- a/src/libsyntax_pos/hygiene.rs +++ b/src/libsyntax_pos/hygiene.rs @@ -82,11 +82,8 @@ pub enum Transparency { } impl Mark { - pub fn fresh(parent: Mark) -> Self { - HygieneData::with(|data| { - data.marks.push(MarkData { parent, expn_info: None }); - Mark(data.marks.len() as u32 - 1) - }) + pub fn fresh(parent: Mark, expn_info: Option) -> Self { + HygieneData::with(|data| data.fresh_mark(parent, expn_info)) } /// The mark of the theoretical expansion that generates freshly parsed, unexpanded AST. @@ -180,6 +177,11 @@ impl HygieneData { GLOBALS.with(|globals| f(&mut *globals.hygiene_data.borrow_mut())) } + fn fresh_mark(&mut self, parent: Mark, expn_info: Option) -> Mark { + self.marks.push(MarkData { parent, expn_info }); + Mark(self.marks.len() as u32 - 1) + } + fn expn_info(&self, mark: Mark) -> Option<&ExpnInfo> { self.marks[mark.0 as usize].expn_info.as_ref() } @@ -396,33 +398,6 @@ impl SyntaxContext { SyntaxContext(raw) } - // Allocate a new SyntaxContext with the given ExpnInfo. This is used when - // deserializing Spans from the incr. comp. cache. - // FIXME(mw): This method does not restore MarkData::parent or - // SyntaxContextData::prev_ctxt or SyntaxContextData::opaque. These things - // don't seem to be used after HIR lowering, so everything should be fine - // as long as incremental compilation does not kick in before that. - pub fn allocate_directly(expansion_info: ExpnInfo) -> Self { - HygieneData::with(|data| { - data.marks.push(MarkData { - parent: Mark::root(), - expn_info: Some(expansion_info), - }); - - let mark = Mark(data.marks.len() as u32 - 1); - - data.syntax_contexts.push(SyntaxContextData { - outer_mark: mark, - transparency: Transparency::SemiTransparent, - prev_ctxt: SyntaxContext::empty(), - opaque: SyntaxContext::empty(), - opaque_and_semitransparent: SyntaxContext::empty(), - dollar_crate_name: kw::DollarCrate, - }); - SyntaxContext(data.syntax_contexts.len() as u32 - 1) - }) - } - /// Extend a syntax context with a given mark and default transparency for that mark. pub fn apply_mark(self, mark: Mark) -> SyntaxContext { HygieneData::with(|data| data.apply_mark(self, mark)) @@ -615,6 +590,20 @@ impl fmt::Debug for SyntaxContext { } } +impl Span { + /// Creates a fresh expansion with given properties. + /// Expansions are normally created by macros, but in some cases expansions are created for + /// other compiler-generated code to set per-span properties like allowed unstable features. + /// The returned span belongs to the created expansion and has the new properties, + /// but its location is inherited from the current span. + pub fn fresh_expansion(self, parent: Mark, expn_info: ExpnInfo) -> Span { + HygieneData::with(|data| { + let mark = data.fresh_mark(parent, Some(expn_info)); + self.with_ctxt(data.apply_mark(SyntaxContext::empty(), mark)) + }) + } +} + /// A subset of properties from both macro definition and macro call available through global data. /// Avoid using this if you have access to the original definition or call structures. #[derive(Clone, Debug, RustcEncodable, RustcDecodable)] @@ -669,10 +658,10 @@ impl ExpnInfo { } } - pub fn with_unstable(kind: ExpnKind, call_site: Span, edition: Edition, - allow_internal_unstable: &[Symbol]) -> ExpnInfo { + pub fn allow_unstable(kind: ExpnKind, call_site: Span, edition: Edition, + allow_internal_unstable: Lrc<[Symbol]>) -> ExpnInfo { ExpnInfo { - allow_internal_unstable: Some(allow_internal_unstable.into()), + allow_internal_unstable: Some(allow_internal_unstable), ..ExpnInfo::default(kind, call_site, edition) } } diff --git a/src/libsyntax_pos/symbol.rs b/src/libsyntax_pos/symbol.rs index 89fcf3b1f8f..581fd47c4b3 100644 --- a/src/libsyntax_pos/symbol.rs +++ b/src/libsyntax_pos/symbol.rs @@ -508,6 +508,7 @@ symbols! { proc_macro_expr, proc_macro_gen, proc_macro_hygiene, + proc_macro_internals, proc_macro_mod, proc_macro_non_items, proc_macro_path_invoc, @@ -631,6 +632,7 @@ symbols! { static_nobundle, static_recursion, std, + std_inject, str, stringify, stmt, -- cgit 1.4.1-3-g733a5