rustc: Introduce ext module. Move some things from parser to ext.
Introduce an ext_ctxt record to provide a span_err method for use while expanding syntax extensions. Hopefully it will be useful for other things.
This commit is contained in:
parent
dbd066a02a
commit
af46f3ed0d
49
src/comp/front/ext.rs
Normal file
49
src/comp/front/ext.rs
Normal file
@ -0,0 +1,49 @@
|
||||
import std::option;
|
||||
import std::map::hashmap;
|
||||
|
||||
import driver::session::session;
|
||||
import util::common::span;
|
||||
import util::common::new_str_hash;
|
||||
|
||||
type syntax_expander = fn(&ext_ctxt, &parser::parser, span,
|
||||
&vec[@ast::expr],
|
||||
option::t[str]) -> @ast::expr;
|
||||
|
||||
// Temporary: to introduce a tag in order to make a recursive type work
|
||||
tag syntax_extension {
|
||||
x(syntax_expander);
|
||||
}
|
||||
|
||||
// A temporary hard-coded map of methods for expanding syntax extension
|
||||
// AST nodes into full ASTs
|
||||
fn syntax_expander_table() -> hashmap[str, syntax_extension] {
|
||||
auto syntax_expanders = new_str_hash[syntax_extension]();
|
||||
syntax_expanders.insert("fmt", x(extfmt::expand_syntax_ext));
|
||||
syntax_expanders.insert("env", x(extenv::expand_syntax_ext));
|
||||
ret syntax_expanders;
|
||||
}
|
||||
|
||||
type span_err_fn = fn (span sp, str msg) -> !;
|
||||
|
||||
// Provides a limited set of services necessary for syntax extensions
|
||||
// to do their thing
|
||||
type ext_ctxt = rec(span_err_fn span_err);
|
||||
|
||||
fn mk_ctxt(session sess) -> ext_ctxt {
|
||||
fn ext_span_err_(session sess, span sp, str err) -> ! {
|
||||
sess.span_err(sp, err);
|
||||
}
|
||||
auto ext_span_err = bind ext_span_err_(sess, _, _);
|
||||
ret rec(span_err = ext_span_err);
|
||||
}
|
||||
|
||||
//
|
||||
// Local Variables:
|
||||
// mode: rust
|
||||
// fill-column: 78;
|
||||
// indent-tabs-mode: nil
|
||||
// c-basic-offset: 4
|
||||
// buffer-file-coding-system: utf-8-unix
|
||||
// compile-command: "make -k -C $RBUILD 2>&1 | sed -e 's/\\/x\\//x:\\//g'";
|
||||
// End:
|
||||
//
|
@ -11,10 +11,13 @@ import std::vec;
|
||||
import std::option;
|
||||
import std::generic_os;
|
||||
|
||||
import ext::*;
|
||||
|
||||
export expand_syntax_ext;
|
||||
|
||||
// FIXME: Need to thread parser through here to handle errors correctly
|
||||
fn expand_syntax_ext(&parser::parser p,
|
||||
fn expand_syntax_ext(&ext_ctxt cx,
|
||||
&parser::parser p,
|
||||
common::span sp,
|
||||
&vec[@ast::expr] args,
|
||||
option::t[str] body) -> @ast::expr {
|
||||
|
@ -15,9 +15,12 @@ import std::option::some;
|
||||
|
||||
import std::extfmt::ct::*;
|
||||
|
||||
import ext::*;
|
||||
|
||||
export expand_syntax_ext;
|
||||
|
||||
fn expand_syntax_ext(&parser p, common::span sp,
|
||||
fn expand_syntax_ext(&ext_ctxt cx,
|
||||
&parser p, common::span sp,
|
||||
&vec[@ast::expr] args,
|
||||
option::t[str] body) -> @ast::expr {
|
||||
|
||||
|
@ -27,11 +27,6 @@ tag file_type {
|
||||
|
||||
type ty_or_bang = util::common::ty_or_bang[@ast::ty];
|
||||
|
||||
// Temporary: to introduce a tag in order to make a recursive type work
|
||||
tag syntax_extension {
|
||||
x(syntax_expander);
|
||||
}
|
||||
|
||||
state type parser =
|
||||
state obj {
|
||||
fn peek() -> token::token;
|
||||
@ -53,15 +48,12 @@ state type parser =
|
||||
fn get_reader() -> lexer::reader;
|
||||
fn get_filemap() -> codemap::filemap;
|
||||
fn get_bad_expr_words() -> hashmap[str, ()];
|
||||
fn get_syntax_expanders() -> hashmap[str, syntax_extension];
|
||||
fn get_syntax_expanders() -> hashmap[str, ext::syntax_extension];
|
||||
fn get_chpos() -> uint;
|
||||
fn get_ann() -> ast::ann;
|
||||
fn next_ann_num() -> uint;
|
||||
};
|
||||
|
||||
type syntax_expander = fn(&parser, common::span, &vec[@ast::expr],
|
||||
option::t[str]) -> @ast::expr;
|
||||
|
||||
fn new_parser(session::session sess,
|
||||
eval::env env,
|
||||
ast::def_id initial_def,
|
||||
@ -80,7 +72,8 @@ fn new_parser(session::session sess,
|
||||
vec[op_spec] precs,
|
||||
mutable uint next_ann_var,
|
||||
hashmap[str, ()] bad_words,
|
||||
hashmap[str, syntax_extension] syntax_expanders)
|
||||
hashmap[str, ext::syntax_extension]
|
||||
syntax_expanders)
|
||||
{
|
||||
fn peek() -> token::token {
|
||||
ret tok;
|
||||
@ -153,7 +146,7 @@ fn new_parser(session::session sess,
|
||||
ret bad_words;
|
||||
}
|
||||
|
||||
fn get_syntax_expanders() -> hashmap[str, syntax_extension] {
|
||||
fn get_syntax_expanders() -> hashmap[str, ext::syntax_extension] {
|
||||
ret syntax_expanders;
|
||||
}
|
||||
|
||||
@ -183,7 +176,7 @@ fn new_parser(session::session sess,
|
||||
ret stdio_parser(sess, env, ftype, lexer::next_token(rdr),
|
||||
npos, npos, npos, initial_def._1, UNRESTRICTED,
|
||||
initial_def._0, rdr, prec_table(), next_ann,
|
||||
bad_expr_word_table(), syntax_expander_table());
|
||||
bad_expr_word_table(), ext::syntax_expander_table());
|
||||
}
|
||||
|
||||
// These are the words that shouldn't be allowed as value identifiers,
|
||||
@ -227,13 +220,6 @@ fn bad_expr_word_table() -> hashmap[str, ()] {
|
||||
ret words;
|
||||
}
|
||||
|
||||
fn syntax_expander_table() -> hashmap[str, syntax_extension] {
|
||||
auto syntax_expanders = new_str_hash[syntax_extension]();
|
||||
syntax_expanders.insert("fmt", x(extfmt::expand_syntax_ext));
|
||||
syntax_expanders.insert("env", x(extenv::expand_syntax_ext));
|
||||
ret syntax_expanders;
|
||||
}
|
||||
|
||||
fn unexpected(&parser p, token::token t) -> ! {
|
||||
let str s = "unexpected token: ";
|
||||
s += token::to_str(p.get_reader(), t);
|
||||
@ -1060,11 +1046,13 @@ fn expand_syntax_ext(&parser p, common::span sp,
|
||||
auto extname = path.node.idents.(0);
|
||||
|
||||
alt (p.get_syntax_expanders().find(extname)) {
|
||||
case (none[syntax_extension]) {
|
||||
case (none) {
|
||||
p.err("unknown syntax expander: '" + extname + "'");
|
||||
}
|
||||
case (some[syntax_extension](x(?ext))) {
|
||||
ret ast::expr_ext(path, args, body, ext(p, sp, args, body),
|
||||
case (some(ext::x(?ext))) {
|
||||
auto ext_cx = ext::mk_ctxt(p.get_session());
|
||||
ret ast::expr_ext(path, args, body,
|
||||
ext(ext_cx, p, sp, args, body),
|
||||
p.get_ann());
|
||||
}
|
||||
}
|
||||
|
@ -38,6 +38,7 @@ mod pretty {
|
||||
mod front {
|
||||
mod ast;
|
||||
mod creader;
|
||||
mod ext;
|
||||
mod extfmt;
|
||||
mod extenv;
|
||||
mod codemap;
|
||||
|
Loading…
x
Reference in New Issue
Block a user