auto merge of #11720 : sfackler/rust/macro-export-source, r=alexcrichton
The old method of serializing the AST gives totally bogus spans if the expansion of an imported macro causes compilation errors. The best solution seems to be to serialize the actual textual macro definition and load it the same way the std-macros are. I'm not totally confident that getting the source from the CodeMap will always do the right thing, but it seems to work in simple cases.
This commit is contained in:
@@ -299,7 +299,7 @@ pub struct MacroCrate {
|
||||
|
||||
pub trait CrateLoader {
|
||||
fn load_crate(&mut self, crate: &ast::ViewItem) -> MacroCrate;
|
||||
fn get_exported_macros(&mut self, crate_num: ast::CrateNum) -> ~[@ast::Item];
|
||||
fn get_exported_macros(&mut self, crate_num: ast::CrateNum) -> ~[~str];
|
||||
fn get_registrar_symbol(&mut self, crate_num: ast::CrateNum) -> Option<~str>;
|
||||
}
|
||||
|
||||
|
||||
@@ -406,9 +406,20 @@ pub fn expand_view_item(vi: &ast::ViewItem,
|
||||
fn load_extern_macros(crate: &ast::ViewItem, fld: &mut MacroExpander) {
|
||||
let MacroCrate { lib, cnum } = fld.cx.loader.load_crate(crate);
|
||||
|
||||
let crate_name = match crate.node {
|
||||
ast::ViewItemExternMod(ref name, _, _) => token::ident_to_str(name),
|
||||
_ => unreachable!(),
|
||||
};
|
||||
let name = format!("<{} macros>", crate_name).to_managed();
|
||||
|
||||
let exported_macros = fld.cx.loader.get_exported_macros(cnum);
|
||||
for &it in exported_macros.iter() {
|
||||
expand_item_mac(it, fld);
|
||||
for source in exported_macros.iter() {
|
||||
let item = parse::parse_item_from_source_str(name,
|
||||
source.to_managed(),
|
||||
fld.cx.cfg(),
|
||||
fld.cx.parse_sess())
|
||||
.expect("expected a serialized item");
|
||||
expand_item_mac(item, fld);
|
||||
}
|
||||
|
||||
let path = match lib {
|
||||
@@ -944,7 +955,6 @@ pub fn inject_std_macros(parse_sess: @parse::ParseSess,
|
||||
let sm = match parse_item_from_source_str(@"<std-macros>",
|
||||
std_macros(),
|
||||
cfg.clone(),
|
||||
~[],
|
||||
parse_sess) {
|
||||
Some(item) => item,
|
||||
None => fail!("expected core macros to parse correctly")
|
||||
@@ -1212,7 +1222,7 @@ mod test {
|
||||
fail!("lolwut")
|
||||
}
|
||||
|
||||
fn get_exported_macros(&mut self, _: ast::CrateNum) -> ~[@ast::Item] {
|
||||
fn get_exported_macros(&mut self, _: ast::CrateNum) -> ~[~str] {
|
||||
fail!("lolwut")
|
||||
}
|
||||
|
||||
@@ -1289,7 +1299,7 @@ mod test {
|
||||
let item_ast = parse::parse_item_from_source_str(
|
||||
@"<test>",
|
||||
src,
|
||||
cfg,~[],sess);
|
||||
cfg,sess);
|
||||
match item_ast {
|
||||
Some(_) => (), // success
|
||||
None => fail!("expected this to parse")
|
||||
|
||||
@@ -250,7 +250,6 @@ pub mod rt {
|
||||
@"<quote expansion>",
|
||||
s,
|
||||
self.cfg(),
|
||||
~[],
|
||||
self.parse_sess());
|
||||
match res {
|
||||
Some(ast) => ast,
|
||||
|
||||
@@ -130,10 +130,10 @@ pub fn parse_item_from_source_str(
|
||||
name: @str,
|
||||
source: @str,
|
||||
cfg: ast::CrateConfig,
|
||||
attrs: ~[ast::Attribute],
|
||||
sess: @ParseSess
|
||||
) -> Option<@ast::Item> {
|
||||
let mut p = new_parser_from_source_str(sess, cfg, name, source);
|
||||
let attrs = p.parse_outer_attributes();
|
||||
maybe_aborted(p.parse_item(attrs),p)
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user