aboutsummaryrefslogtreecommitdiff
path: root/src/boot/fe
diff options
context:
space:
mode:
authorGraydon Hoare <[email protected]>2010-08-16 13:02:46 -0700
committerGraydon Hoare <[email protected]>2010-08-16 13:02:46 -0700
commit7e62aa68018c94bcfc3fd6beab90cf7b87f91cbf (patch)
treead8091a45871afa2685ec65f6c841fb0c942becf /src/boot/fe
parentEvil solution to the problem of importing the same opaque from two different ... (diff)
downloadrust-7e62aa68018c94bcfc3fd6beab90cf7b87f91cbf.tar.xz
rust-7e62aa68018c94bcfc3fd6beab90cf7b87f91cbf.zip
Absent any deep overhauls to syntax or constant-handling, hack in the ability to project a cexp var binding to a token in the parser. Use it in comp/rustc.rc and comp/lib/llvm.rs.
Diffstat (limited to 'src/boot/fe')
-rw-r--r--src/boot/fe/cexp.ml45
-rw-r--r--src/boot/fe/item.ml14
-rw-r--r--src/boot/fe/parser.ml3
3 files changed, 43 insertions, 19 deletions
diff --git a/src/boot/fe/cexp.ml b/src/boot/fe/cexp.ml
index fc849b28..9c1b40e1 100644
--- a/src/boot/fe/cexp.ml
+++ b/src/boot/fe/cexp.ml
@@ -310,7 +310,7 @@ type cdir =
| CDIR_mod of (Ast.ident * Ast.mod_item)
| CDIR_auth of auth
-type env = { env_bindings: (Ast.ident * pval) list;
+type env = { env_bindings: ((Ast.ident * pval) list) ref;
env_prefix: filename list;
env_items: (filename, Ast.mod_items) Hashtbl.t;
env_files: (node_id,filename) Hashtbl.t;
@@ -357,10 +357,11 @@ and eval_cexp (env:env) (exp:cexp) : cdir array =
| CEXP_let {node=cl} ->
let ident = cl.let_ident in
let v = eval_pexp env cl.let_value in
- let env = { env with
- env_bindings = ((ident,v)::env.env_bindings ) }
- in
- eval_cexps env cl.let_body
+ let old_bindings = !(env.env_bindings) in
+ env.env_bindings := (ident,v)::old_bindings;
+ let res = eval_cexps env cl.let_body in
+ env.env_bindings := old_bindings;
+ res
| CEXP_src_mod {node=s; id=id} ->
let name = s.src_ident in
@@ -381,6 +382,7 @@ and eval_cexp (env:env) (exp:cexp) : cdir array =
ps.pstate_opaque_id
ps.pstate_sess
ps.pstate_get_mod
+ ps.pstate_get_cenv_tok
ps.pstate_infer_lib_name
env.env_required
env.env_required_syms
@@ -518,7 +520,7 @@ and eval_pexp (env:env) (exp:Pexp.pexp) : pval =
| Pexp.PEXP_lval (Pexp.PLVAL_ident ident) ->
begin
- match ltab_search env.env_bindings ident with
+ match ltab_search !(env.env_bindings) ident with
None -> raise (err (Printf.sprintf "no binding for '%s' found"
ident) env.env_ps)
| Some v -> v
@@ -622,11 +624,6 @@ let parse_crate_file
let oref = ref (Opaque 0) in
let required = Hashtbl.create 4 in
let required_syms = Hashtbl.create 4 in
- let ps =
- make_parser tref nref oref sess get_mod
- infer_lib_name required required_syms fname
- in
-
let files = Hashtbl.create 0 in
let items = Hashtbl.create 4 in
let target_bindings =
@@ -648,11 +645,23 @@ let parse_crate_file
("build_input", PVAL_str fname);
]
in
- let initial_bindings =
- target_bindings
- @ build_bindings
+ let bindings =
+ ref (target_bindings
+ @ build_bindings)
in
- let env = { env_bindings = initial_bindings;
+ let get_cenv_tok ps ident =
+ match ltab_search (!bindings) ident with
+ None -> raise (err (Printf.sprintf "no binding for '%s' found"
+ ident) ps)
+ | Some (PVAL_bool b) -> LIT_BOOL b
+ | Some (PVAL_str s) -> LIT_STR s
+ | Some (PVAL_num n) -> LIT_INT n
+ in
+ let ps =
+ make_parser tref nref oref sess get_mod get_cenv_tok
+ infer_lib_name required required_syms fname
+ in
+ let env = { env_bindings = bindings;
env_prefix = [Filename.dirname fname];
env_items = Hashtbl.create 0;
env_files = files;
@@ -720,8 +729,12 @@ let parse_src_file
let oref = ref (Opaque 0) in
let required = Hashtbl.create 0 in
let required_syms = Hashtbl.create 0 in
+ let get_cenv_tok ps ident =
+ raise (err (Printf.sprintf "no binding for '%s' found"
+ ident) ps)
+ in
let ps =
- make_parser tref nref oref sess get_mod
+ make_parser tref nref oref sess get_mod get_cenv_tok
infer_lib_name required required_syms fname
in
with_err_handling sess
diff --git a/src/boot/fe/item.ml b/src/boot/fe/item.ml
index b5a8bb7a..91a0c3dd 100644
--- a/src/boot/fe/item.ml
+++ b/src/boot/fe/item.ml
@@ -786,9 +786,17 @@ and parse_mod_item (ps:pstate) : (Ast.ident * Ast.mod_item) =
EQ ->
begin
bump ps;
- match peek ps with
- LIT_STR s -> (bump ps; s)
- | _ -> raise (unexpected ps)
+ let do_tok t =
+ bump ps;
+ match t with
+ LIT_STR s -> s
+ | _ -> raise (unexpected ps)
+ in
+ match peek ps with
+ IDENT i ->
+ do_tok (ps.pstate_get_cenv_tok ps i)
+ | t ->
+ do_tok t
end
| _ -> ps.pstate_infer_lib_name ident
in
diff --git a/src/boot/fe/parser.ml b/src/boot/fe/parser.ml
index ab7ff56c..4add7b01 100644
--- a/src/boot/fe/parser.ml
+++ b/src/boot/fe/parser.ml
@@ -23,6 +23,7 @@ type pstate =
pstate_node_id : node_id ref;
pstate_opaque_id : opaque_id ref;
pstate_get_mod : get_mod_fn;
+ pstate_get_cenv_tok : pstate -> Ast.ident -> token;
pstate_infer_lib_name : (Ast.ident -> filename);
pstate_required : (node_id, (required_lib * nabi_conv)) Hashtbl.t;
pstate_required_syms : (node_id, string) Hashtbl.t; }
@@ -45,6 +46,7 @@ let make_parser
(oref:opaque_id ref)
(sess:Session.sess)
(get_mod:get_mod_fn)
+ (get_cenv_tok:pstate -> Ast.ident -> token)
(infer_lib_name:Ast.ident -> filename)
(required:(node_id, (required_lib * nabi_conv)) Hashtbl.t)
(required_syms:(node_id, string) Hashtbl.t)
@@ -68,6 +70,7 @@ let make_parser
pstate_node_id = nref;
pstate_opaque_id = oref;
pstate_get_mod = get_mod;
+ pstate_get_cenv_tok = get_cenv_tok;
pstate_infer_lib_name = infer_lib_name;
pstate_required = required;
pstate_required_syms = required_syms; }