Skip to content

Commit fbc96e1

Browse files
committed
Persistent macro scopes.
1 parent a23bdd2 commit fbc96e1

File tree

3 files changed

+167
-99
lines changed

3 files changed

+167
-99
lines changed

src/librustc_resolve/build_reduced_graph.rs

+40-29
Original file line numberDiff line numberDiff line change
@@ -13,7 +13,7 @@
1313
//! Here we build the "reduced graph": the graph of the module tree without
1414
//! any imports resolved.
1515
16-
use macros;
16+
use macros::{InvocationData, LegacyImports, LegacyScope};
1717
use resolve_imports::ImportDirectiveSubclass::{self, GlobImport};
1818
use {Module, ModuleS, ModuleKind};
1919
use Namespace::{self, TypeNS, ValueNS};
@@ -84,7 +84,7 @@ impl<'b> Resolver<'b> {
8484
}
8585

8686
/// Constructs the reduced graph for one item.
87-
fn build_reduced_graph_for_item(&mut self, item: &Item, expansion: Mark) {
87+
fn build_reduced_graph_for_item(&mut self, item: &Item, legacy_imports: &mut LegacyImports) {
8888
let parent = self.current_module;
8989
let name = item.ident.name;
9090
let sp = item.span;
@@ -200,16 +200,9 @@ impl<'b> Resolver<'b> {
200200
LoadedMacroKind::Def(mut def) => {
201201
let name = def.ident.name;
202202
if def.use_locally {
203-
let ext = macro_rules::compile(&self.session.parse_sess, &def);
204-
let shadowing =
205-
self.resolve_macro_name(Mark::root(), name, false).is_some();
206-
self.invocations[&Mark::root()].module.get().macros.borrow_mut()
207-
.insert(name, macros::NameBinding {
208-
ext: Rc::new(ext),
209-
expansion: expansion,
210-
shadowing: shadowing,
211-
span: loaded_macro.import_site,
212-
});
203+
let ext =
204+
Rc::new(macro_rules::compile(&self.session.parse_sess, &def));
205+
legacy_imports.insert(name, (ext, loaded_macro.import_site));
213206
self.macro_names.insert(name);
214207
}
215208
if def.export {
@@ -250,7 +243,6 @@ impl<'b> Resolver<'b> {
250243
attr::contains_name(&item.attrs, "no_implicit_prelude")
251244
},
252245
normal_ancestor_id: Some(item.id),
253-
macros_escape: self.contains_macro_use(&item.attrs),
254246
..ModuleS::new(Some(parent), ModuleKind::Def(def, name))
255247
});
256248
self.define(parent, name, TypeNS, (module, sp, vis));
@@ -520,45 +512,62 @@ impl<'b> Resolver<'b> {
520512

521513
pub struct BuildReducedGraphVisitor<'a, 'b: 'a> {
522514
pub resolver: &'a mut Resolver<'b>,
523-
pub expansion: Mark,
515+
pub legacy_scope: LegacyScope<'b>,
516+
pub legacy_imports: LegacyImports,
524517
}
525518

526519
impl<'a, 'b> BuildReducedGraphVisitor<'a, 'b> {
527-
fn visit_invoc(&mut self, id: ast::NodeId) {
528-
let mark = Mark::from_placeholder_id(id);
529-
self.resolver.invocations[&mark].module.set(self.resolver.current_module);
520+
fn visit_invoc(&mut self, id: ast::NodeId) -> &'b InvocationData<'b> {
521+
let invocation = self.resolver.invocations[&Mark::from_placeholder_id(id)];
522+
invocation.module.set(self.resolver.current_module);
523+
invocation.legacy_scope.set(self.legacy_scope);
524+
invocation
530525
}
531526
}
532527

533528
macro_rules! method {
534529
($visit:ident: $ty:ty, $invoc:path, $walk:ident) => {
535530
fn $visit(&mut self, node: &$ty) {
536-
match node.node {
537-
$invoc(..) => self.visit_invoc(node.id),
538-
_ => visit::$walk(self, node),
531+
if let $invoc(..) = node.node {
532+
self.visit_invoc(node.id);
533+
} else {
534+
visit::$walk(self, node);
539535
}
540536
}
541537
}
542538
}
543539

544540
impl<'a, 'b> Visitor for BuildReducedGraphVisitor<'a, 'b> {
545541
method!(visit_impl_item: ast::ImplItem, ast::ImplItemKind::Macro, walk_impl_item);
546-
method!(visit_stmt: ast::Stmt, ast::StmtKind::Mac, walk_stmt);
547542
method!(visit_expr: ast::Expr, ast::ExprKind::Mac, walk_expr);
548543
method!(visit_pat: ast::Pat, ast::PatKind::Mac, walk_pat);
549544
method!(visit_ty: ast::Ty, ast::TyKind::Mac, walk_ty);
550545

551546
fn visit_item(&mut self, item: &Item) {
552-
match item.node {
547+
let macro_use = match item.node {
553548
ItemKind::Mac(..) if item.id == ast::DUMMY_NODE_ID => return, // Scope placeholder
554-
ItemKind::Mac(..) => return self.visit_invoc(item.id),
555-
_ => {}
556-
}
549+
ItemKind::Mac(..) => {
550+
return self.legacy_scope = LegacyScope::Expansion(self.visit_invoc(item.id));
551+
}
552+
ItemKind::Mod(..) => self.resolver.contains_macro_use(&item.attrs),
553+
_ => false,
554+
};
557555

558-
let parent = self.resolver.current_module;
559-
self.resolver.build_reduced_graph_for_item(item, self.expansion);
556+
let (parent, legacy_scope) = (self.resolver.current_module, self.legacy_scope);
557+
self.resolver.build_reduced_graph_for_item(item, &mut self.legacy_imports);
560558
visit::walk_item(self, item);
561559
self.resolver.current_module = parent;
560+
if !macro_use {
561+
self.legacy_scope = legacy_scope;
562+
}
563+
}
564+
565+
fn visit_stmt(&mut self, stmt: &ast::Stmt) {
566+
if let ast::StmtKind::Mac(..) = stmt.node {
567+
self.legacy_scope = LegacyScope::Expansion(self.visit_invoc(stmt.id));
568+
} else {
569+
visit::walk_stmt(self, stmt);
570+
}
562571
}
563572

564573
fn visit_foreign_item(&mut self, foreign_item: &ForeignItem) {
@@ -567,18 +576,20 @@ impl<'a, 'b> Visitor for BuildReducedGraphVisitor<'a, 'b> {
567576
}
568577

569578
fn visit_block(&mut self, block: &Block) {
570-
let parent = self.resolver.current_module;
579+
let (parent, legacy_scope) = (self.resolver.current_module, self.legacy_scope);
571580
self.resolver.build_reduced_graph_for_block(block);
572581
visit::walk_block(self, block);
573582
self.resolver.current_module = parent;
583+
self.legacy_scope = legacy_scope;
574584
}
575585

576586
fn visit_trait_item(&mut self, item: &TraitItem) {
577587
let parent = self.resolver.current_module;
578588
let def_id = parent.def_id().unwrap();
579589

580590
if let TraitItemKind::Macro(_) = item.node {
581-
return self.visit_invoc(item.id);
591+
self.visit_invoc(item.id);
592+
return
582593
}
583594

584595
// Add the item to the trait info.

src/librustc_resolve/lib.rs

+9-6
Original file line numberDiff line numberDiff line change
@@ -57,6 +57,7 @@ use syntax::ext::base::MultiItemModifier;
5757
use syntax::ext::hygiene::Mark;
5858
use syntax::ast::{self, FloatTy};
5959
use syntax::ast::{CRATE_NODE_ID, Name, NodeId, IntTy, UintTy};
60+
use syntax::ext::base::SyntaxExtension;
6061
use syntax::parse::token::{self, keywords};
6162
use syntax::util::lev_distance::find_best_match_for_name;
6263

@@ -77,7 +78,7 @@ use std::mem::replace;
7778
use std::rc::Rc;
7879

7980
use resolve_imports::{ImportDirective, NameResolution};
80-
use macros::InvocationData;
81+
use macros::{InvocationData, LegacyBinding};
8182

8283
// NB: This module needs to be declared first so diagnostics are
8384
// registered before they are used.
@@ -792,9 +793,6 @@ pub struct ModuleS<'a> {
792793
// access the children must be preceded with a
793794
// `populate_module_if_necessary` call.
794795
populated: Cell<bool>,
795-
796-
macros: RefCell<FnvHashMap<Name, macros::NameBinding>>,
797-
macros_escape: bool,
798796
}
799797

800798
pub type Module<'a> = &'a ModuleS<'a>;
@@ -812,8 +810,6 @@ impl<'a> ModuleS<'a> {
812810
globs: RefCell::new((Vec::new())),
813811
traits: RefCell::new(None),
814812
populated: Cell::new(true),
815-
macros: RefCell::new(FnvHashMap()),
816-
macros_escape: false,
817813
}
818814
}
819815

@@ -1087,6 +1083,7 @@ pub struct Resolver<'a> {
10871083
pub derive_modes: FnvHashMap<Name, Rc<MultiItemModifier>>,
10881084
crate_loader: &'a mut CrateLoader,
10891085
macro_names: FnvHashSet<Name>,
1086+
builtin_macros: FnvHashMap<Name, Rc<SyntaxExtension>>,
10901087

10911088
// Maps the `Mark` of an expansion to its containing module or block.
10921089
invocations: FnvHashMap<Mark, &'a InvocationData<'a>>,
@@ -1099,6 +1096,7 @@ pub struct ResolverArenas<'a> {
10991096
import_directives: arena::TypedArena<ImportDirective<'a>>,
11001097
name_resolutions: arena::TypedArena<RefCell<NameResolution<'a>>>,
11011098
invocation_data: arena::TypedArena<InvocationData<'a>>,
1099+
legacy_bindings: arena::TypedArena<LegacyBinding<'a>>,
11021100
}
11031101

11041102
impl<'a> ResolverArenas<'a> {
@@ -1126,6 +1124,9 @@ impl<'a> ResolverArenas<'a> {
11261124
-> &'a InvocationData<'a> {
11271125
self.invocation_data.alloc(expansion_data)
11281126
}
1127+
fn alloc_legacy_binding(&'a self, binding: LegacyBinding<'a>) -> &'a LegacyBinding<'a> {
1128+
self.legacy_bindings.alloc(binding)
1129+
}
11291130
}
11301131

11311132
impl<'a> ty::NodeIdTree for Resolver<'a> {
@@ -1273,6 +1274,7 @@ impl<'a> Resolver<'a> {
12731274
derive_modes: FnvHashMap(),
12741275
crate_loader: crate_loader,
12751276
macro_names: FnvHashSet(),
1277+
builtin_macros: FnvHashMap(),
12761278
invocations: invocations,
12771279
}
12781280
}
@@ -1285,6 +1287,7 @@ impl<'a> Resolver<'a> {
12851287
import_directives: arena::TypedArena::new(),
12861288
name_resolutions: arena::TypedArena::new(),
12871289
invocation_data: arena::TypedArena::new(),
1290+
legacy_bindings: arena::TypedArena::new(),
12881291
}
12891292
}
12901293

0 commit comments

Comments
 (0)