Enable item macros to define macros.

This commit is contained in:
Paul Stansifer 2012-07-06 14:29:50 -07:00
parent 579768baa5
commit cabee6391d
3 changed files with 17 additions and 6 deletions

View File

@ -20,7 +20,12 @@ type syntax_expander_tt_ = fn@(ext_ctxt, span, ast::token_tree) -> @ast::expr;
type syntax_expander_tt_item type syntax_expander_tt_item
= {expander: syntax_expander_tt_item_, span: option<span>}; = {expander: syntax_expander_tt_item_, span: option<span>};
type syntax_expander_tt_item_ type syntax_expander_tt_item_
= fn@(ext_ctxt, span, ast::ident, ast::token_tree) -> @ast::item; = fn@(ext_ctxt, span, ast::ident, ast::token_tree) -> mac_result;
enum mac_result {
mr_item(@ast::item),
mr_def(macro_def)
}
enum syntax_extension { enum syntax_extension {
normal(syntax_expander), normal(syntax_expander),

View File

@ -170,10 +170,16 @@ fn expand_item_mac(exts: hashmap<str, syntax_extension>,
cx.bt_push(expanded_from({call_site: it.span, cx.bt_push(expanded_from({call_site: it.span,
callie: {name: *extname, callie: {name: *extname,
span: expand.span}})); span: expand.span}}));
let it = fld.fold_item( let maybe_it =
expand.expander(cx, it.span, it.ident, tt)); alt expand.expander(cx, it.span, it.ident, tt) {
mr_item(it) { fld.fold_item(it) }
mr_def(mdef) {
exts.insert(*mdef.ident, mdef.ext);
none
}
};
cx.bt_pop(); cx.bt_pop();
ret it ret maybe_it
} }
_ { cx.span_fatal(it.span, _ { cx.span_fatal(it.span,
#fmt("%s is not a legal here", *extname)) } #fmt("%s is not a legal here", *extname)) }

View File

@ -11,7 +11,7 @@ import pipes::parse_proto::proto_parser;
import pipes::pipec::methods; import pipes::pipec::methods;
fn expand_proto(cx: ext_ctxt, _sp: span, id: ast::ident, tt: ast::token_tree) fn expand_proto(cx: ext_ctxt, _sp: span, id: ast::ident, tt: ast::token_tree)
-> @ast::item -> base::mac_result
{ {
let sess = cx.parse_sess(); let sess = cx.parse_sess();
let cfg = cx.cfg(); let cfg = cx.cfg();
@ -25,5 +25,5 @@ fn expand_proto(cx: ext_ctxt, _sp: span, id: ast::ident, tt: ast::token_tree)
let proto = rust_parser.parse_proto(id); let proto = rust_parser.parse_proto(id);
proto.compile(cx) base::mr_item(proto.compile(cx))
} }