-
Notifications
You must be signed in to change notification settings - Fork 0
/
elim.ml
36 lines (34 loc) · 1.51 KB
/
elim.ml
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
open KNormal
let rec effect e = (* 副作用の有無 (caml2html: elim_effect) *)
match (KNormal.rm_outside_pos e) with (* Oct. 14. 2021 *)
| Let(_, e1, e2) | IfEq(_, _, e1, e2) | IfNEq(_, _, e1, e2) | IfLE(_, _, e1, e2) | IfLT(_, _, e1, e2) -> effect e1 || effect e2
| LetRec(_, e) | LetTuple(_, _, e) -> effect e
| App _ | Put _ | ExtFunApp _ -> true
| _ -> false
let rec f = function (* 不要定義削除ルーチン本体 (caml2html: elim_f) *)
| IfEq(x, y, e1, e2) -> IfEq(x, y, f e1, f e2)
| IfNEq(x, y, e1, e2) -> IfNEq(x, y, f e1, f e2)
| IfLE(x, y, e1, e2) -> IfLE(x, y, f e1, f e2)
| IfLT(x, y, e1, e2) -> IfLT(x, y, f e1, f e2)
| Let((x, t), e1, e2) -> (* letの場合 (caml2html: elim_let) *)
let e1' = f e1 in
let e2' = f e2 in
if effect e1' || S.mem x (fv e2') then Let((x, t), e1', e2') else
(Format.eprintf "eliminating variable %s@." x;
e2')
| LetRec({ name = (x, t); args = yts; body = e1 }, e2) -> (* let recの場合 (caml2html: elim_letrec) *)
let e2' = f e2 in
if S.mem x (fv e2') then
LetRec({ name = (x, t); args = yts; body = f e1 }, e2')
else
(Format.eprintf "eliminating function %s@." x;
e2')
| LetTuple(xts, y, e) ->
let xs = List.map fst xts in
let e' = f e in
let live = fv e' in
if List.exists (fun x -> S.mem x live) xs then LetTuple(xts, y, e') else
(Format.eprintf "eliminating variables %s@." (Id.pp_list xs);
e')
| ExprWithPos(e, pos) -> ExprWithPos(f e, pos) (* Oct. 14. 2021 *)
| e -> e