Skip to content

Commit 72544af

Browse files
committed
Record macro import site spans.
1 parent 1817ca4 commit 72544af

File tree

3 files changed

+40
-25
lines changed

3 files changed

+40
-25
lines changed

src/librustc/middle/cstore.rs

+6-1
Original file line numberDiff line numberDiff line change
@@ -423,7 +423,12 @@ impl<'tcx> CrateStore<'tcx> for DummyCrateStore {
423423
fn metadata_encoding_version(&self) -> &[u8] { bug!("metadata_encoding_version") }
424424
}
425425

426-
pub enum LoadedMacro {
426+
pub struct LoadedMacro {
427+
pub import_site: Span,
428+
pub kind: LoadedMacroKind,
429+
}
430+
431+
pub enum LoadedMacroKind {
427432
Def(ast::MacroDef),
428433
CustomDerive(String, Rc<MultiItemModifier>),
429434
}

src/librustc_metadata/macro_import.rs

+30-20
Original file line numberDiff line numberDiff line change
@@ -18,7 +18,7 @@ use std::mem;
1818
use creader::{CrateLoader, Macros};
1919

2020
use rustc::hir::def_id::DefIndex;
21-
use rustc::middle::cstore::LoadedMacro;
21+
use rustc::middle::cstore::{LoadedMacro, LoadedMacroKind};
2222
use rustc::session::Session;
2323
use rustc::util::nodemap::FnvHashMap;
2424
use rustc_back::dynamic_lib::DynamicLibrary;
@@ -28,14 +28,19 @@ use syntax::ast;
2828
use syntax::attr;
2929
use syntax::parse::token;
3030
use syntax_ext::deriving::custom::CustomDerive;
31-
use syntax_pos::Span;
31+
use syntax_pos::{Span, DUMMY_SP};
3232

3333
pub fn call_bad_macro_reexport(a: &Session, b: Span) {
3434
span_err!(a, b, E0467, "bad macro reexport");
3535
}
3636

3737
pub type MacroSelection = FnvHashMap<token::InternedString, Span>;
3838

39+
enum ImportSelection {
40+
All(Span),
41+
Some(MacroSelection),
42+
}
43+
3944
pub fn load_macros(loader: &mut CrateLoader, extern_crate: &ast::Item, allows_macros: bool)
4045
-> Vec<LoadedMacro> {
4146
loader.load_crate(extern_crate, allows_macros)
@@ -46,7 +51,7 @@ impl<'a> CrateLoader<'a> {
4651
extern_crate: &ast::Item,
4752
allows_macros: bool) -> Vec<LoadedMacro> {
4853
// Parse the attributes relating to macros.
49-
let mut import = Some(FnvHashMap()); // None => load all
54+
let mut import = ImportSelection::Some(FnvHashMap());
5055
let mut reexport = FnvHashMap();
5156

5257
for attr in &extern_crate.attrs {
@@ -55,11 +60,9 @@ impl<'a> CrateLoader<'a> {
5560
"macro_use" => {
5661
let names = attr.meta_item_list();
5762
if names.is_none() {
58-
// no names => load all
59-
import = None;
60-
}
61-
if let (Some(sel), Some(names)) = (import.as_mut(), names) {
62-
for attr in names {
63+
import = ImportSelection::All(attr.span);
64+
} else if let ImportSelection::Some(ref mut sel) = import {
65+
for attr in names.unwrap() {
6366
if let Some(word) = attr.word() {
6467
sel.insert(word.name().clone(), attr.span());
6568
} else {
@@ -98,10 +101,10 @@ impl<'a> CrateLoader<'a> {
98101
fn load_macros<'b>(&mut self,
99102
vi: &ast::Item,
100103
allows_macros: bool,
101-
import: Option<MacroSelection>,
104+
import: ImportSelection,
102105
reexport: MacroSelection)
103106
-> Vec<LoadedMacro> {
104-
if let Some(sel) = import.as_ref() {
107+
if let ImportSelection::Some(ref sel) = import {
105108
if sel.is_empty() && reexport.is_empty() {
106109
return Vec::new();
107110
}
@@ -120,15 +123,19 @@ impl<'a> CrateLoader<'a> {
120123
for mut def in macros.macro_rules.drain(..) {
121124
let name = def.ident.name.as_str();
122125

123-
def.use_locally = match import.as_ref() {
124-
None => true,
125-
Some(sel) => sel.contains_key(&name),
126+
let import_site = match import {
127+
ImportSelection::All(span) => Some(span),
128+
ImportSelection::Some(ref sel) => sel.get(&name).cloned()
126129
};
130+
def.use_locally = import_site.is_some();
127131
def.export = reexport.contains_key(&name);
128132
def.allow_internal_unstable = attr::contains_name(&def.attrs,
129133
"allow_internal_unstable");
130134
debug!("load_macros: loaded: {:?}", def);
131-
ret.push(LoadedMacro::Def(def));
135+
ret.push(LoadedMacro {
136+
kind: LoadedMacroKind::Def(def),
137+
import_site: import_site.unwrap_or(DUMMY_SP),
138+
});
132139
seen.insert(name);
133140
}
134141

@@ -137,7 +144,7 @@ impl<'a> CrateLoader<'a> {
137144
// exported macros, enforced elsewhere
138145
assert_eq!(ret.len(), 0);
139146

140-
if import.is_some() {
147+
if let ImportSelection::Some(..) = import {
141148
self.sess.span_err(vi.span, "`rustc-macro` crates cannot be \
142149
selectively imported from, must \
143150
use `#[macro_use]`");
@@ -151,10 +158,10 @@ impl<'a> CrateLoader<'a> {
151158
self.load_derive_macros(vi.span, &macros, index, &mut ret);
152159
}
153160

154-
if let Some(sel) = import.as_ref() {
161+
if let ImportSelection::Some(sel) = import {
155162
for (name, span) in sel {
156163
if !seen.contains(&name) {
157-
span_err!(self.sess, *span, E0469,
164+
span_err!(self.sess, span, E0469,
158165
"imported macro not found");
159166
}
160167
}
@@ -199,18 +206,21 @@ impl<'a> CrateLoader<'a> {
199206
mem::transmute::<*mut u8, fn(&mut Registry)>(sym)
200207
};
201208

202-
struct MyRegistrar<'a>(&'a mut Vec<LoadedMacro>);
209+
struct MyRegistrar<'a>(&'a mut Vec<LoadedMacro>, Span);
203210

204211
impl<'a> Registry for MyRegistrar<'a> {
205212
fn register_custom_derive(&mut self,
206213
trait_name: &str,
207214
expand: fn(TokenStream) -> TokenStream) {
208215
let derive = Rc::new(CustomDerive::new(expand));
209-
self.0.push(LoadedMacro::CustomDerive(trait_name.to_string(), derive));
216+
self.0.push(LoadedMacro {
217+
kind: LoadedMacroKind::CustomDerive(trait_name.to_string(), derive),
218+
import_site: self.1,
219+
});
210220
}
211221
}
212222

213-
registrar(&mut MyRegistrar(ret));
223+
registrar(&mut MyRegistrar(ret, span));
214224

215225
// Intentionally leak the dynamic library. We can't ever unload it
216226
// since the library can make things that will live arbitrarily long.

src/librustc_resolve/build_reduced_graph.rs

+4-4
Original file line numberDiff line numberDiff line change
@@ -20,7 +20,7 @@ use {NameBinding, NameBindingKind, ToNameBinding};
2020
use Resolver;
2121
use {resolve_error, resolve_struct_error, ResolutionError};
2222

23-
use rustc::middle::cstore::LoadedMacro;
23+
use rustc::middle::cstore::LoadedMacroKind;
2424
use rustc::hir::def::*;
2525
use rustc::hir::def_id::{CRATE_DEF_INDEX, DefId};
2626
use rustc::hir::map::DefPathData;
@@ -189,9 +189,9 @@ impl<'b> Resolver<'b> {
189189
// crate root, because `$crate` won't work properly.
190190
let is_crate_root = self.current_module.parent.is_none();
191191
for def in self.crate_loader.load_macros(item, is_crate_root) {
192-
match def {
193-
LoadedMacro::Def(def) => self.add_macro(Mark::root(), def),
194-
LoadedMacro::CustomDerive(name, ext) => {
192+
match def.kind {
193+
LoadedMacroKind::Def(def) => self.add_macro(Mark::root(), def),
194+
LoadedMacroKind::CustomDerive(name, ext) => {
195195
self.insert_custom_derive(&name, ext, item.span);
196196
}
197197
}

0 commit comments

Comments
 (0)