Home My Page Projects Code Snippets Project Openings diderot
Summary Activity Tracker Tasks SCM

SCM Repository

[diderot] Diff of /branches/vis15/src/compiler/translate/translate.sml
ViewVC logotype

Diff of /branches/vis15/src/compiler/translate/translate.sml

Parent Directory Parent Directory | Revision Log Revision Log | View Patch Patch

revision 3471, Mon Nov 30 18:23:37 2015 UTC revision 3476, Wed Dec 2 20:44:59 2015 UTC
# Line 5  Line 5 
5   * COPYRIGHT (c) 2015 The University of Chicago   * COPYRIGHT (c) 2015 The University of Chicago
6   * All rights reserved.   * All rights reserved.
7   *   *
8   * Translate Simple-AST code into the IL representation.  This translation is based on the   * Translate Simple-AST code into the HighIR representation.  This translation is based on the
9   * algorithm described in   * algorithm described in
10   *   *
11   *      Single-pass generation of static single assignment form for structured languages   *      Single-pass generation of static single assignment form for structured languages
# Line 15  Line 15 
15    
16  structure Translate : sig  structure Translate : sig
17    
18      val translate : Simple.program -> HighIL.program      val translate : Simple.program -> HighIR.program
19    
20    end = struct    end = struct
21    
# Line 23  Line 23 
23      structure Ty = SimpleTypes      structure Ty = SimpleTypes
24      structure VMap = SimpleVar.Map      structure VMap = SimpleVar.Map
25      structure VSet = SimpleVar.Set      structure VSet = SimpleVar.Set
26      structure IL = HighIL      structure IR = HighIR
27      structure Op = HighOps      structure Op = HighOps
28      structure DstTy = HighILTypes      structure DstTy = HighTypes
29      structure Census = HighILCensus      structure Census = HighCensus
30    
31      val cvtTy = TranslateTy.tr      val cvtTy = TranslateTy.tr
32    
33    (* maps from SimpleAST variables to the current corresponding SSA variable *)    (* maps from SimpleAST variables to the current corresponding SSA variable *)
34      type env = IL.var VMap.map      type env = IR.var VMap.map
35    
36  (* +DEBUG *)  (* +DEBUG *)
37      fun prEnv (prefix, env) = let      fun prEnv (prefix, env) = let
# Line 40  Line 40 
40            fun nl () = if (!wid > 0) then (print "\n"; wid := 0) else ()            fun nl () = if (!wid > 0) then (print "\n"; wid := 0) else ()
41            fun prElem (src, dst) = let            fun prElem (src, dst) = let
42                  val s = String.concat [                  val s = String.concat [
43                          " ", SimpleVar.uniqueNameOf src, "->", IL.Var.toString dst                          " ", SimpleVar.uniqueNameOf src, "->", IR.Var.toString dst
44                        ]                        ]
45                  in                  in
46                    pr s;                    pr s;
# Line 61  Line 61 
61            (* end case *))            (* end case *))
62    
63    (* create a new instance of a variable *)    (* create a new instance of a variable *)
64      fun newVar x = IL.Var.new (SimpleVar.nameOf x, cvtTy(SimpleVar.typeOf x))      fun newVar x = IR.Var.new (SimpleVar.nameOf x, cvtTy(SimpleVar.typeOf x))
65    
66    (* generate fresh SSA variables and add them to the environment *)    (* generate fresh SSA variables and add them to the environment *)
67      fun freshVars (env, xs) = let      fun freshVars (env, xs) = let
# Line 82  Line 82 
82          env : env,                      (* the environment that was current at the conditional *)          env : env,                      (* the environment that was current at the conditional *)
83                                          (* associated with this node. *)                                          (* associated with this node. *)
84          arity : int ref,                (* actual number of predecessors *)          arity : int ref,                (* actual number of predecessors *)
85          nd : IL.node,                   (* the CFG node for this pending join *)          nd : IR.node,                   (* the CFG node for this pending join *)
86          phiMap : (IL.var * IL.var list) VMap.map ref,          phiMap : (IR.var * IR.var list) VMap.map ref,
87                                          (* a mapping from Simple AST variables that are assigned *)                                          (* a mapping from Simple AST variables that are assigned *)
88                                          (* to their phi nodes. *)                                          (* to their phi nodes. *)
89          predKill : bool array           (* killed predecessor edges (because of DIE or STABILIZE *)          predKill : bool array           (* killed predecessor edges (because of DIE or STABILIZE *)
# Line 96  Line 96 
96    
97    (* create a new pending-join node *)    (* create a new pending-join node *)
98      fun newJoin (env, arity) = JOIN{      fun newJoin (env, arity) = JOIN{
99              env = env, arity = ref arity, nd = IL.Node.mkJOIN [], phiMap = ref VMap.empty,              env = env, arity = ref arity, nd = IR.Node.mkJOIN [], phiMap = ref VMap.empty,
100              predKill = Array.array(arity, false)              predKill = Array.array(arity, false)
101            }            }
102    
# Line 106  Line 106 
106            Array.update (predKill, i, true))            Array.update (predKill, i, true))
107        | killPath _ = ()        | killPath _ = ()
108    
109    (* record an assignment to the IL variable dstVar (corresponding to the Simple AST variable    (* record an assignment to the IR variable dstVar (corresponding to the Simple AST variable
110     * srcVar) in the current pending-join node.  The predIndex specifies which path into the     * srcVar) in the current pending-join node.  The predIndex specifies which path into the
111     * JOIN node this assignment occurs on.     * JOIN node this assignment occurs on.
112     *)     *)
# Line 123  Line 123 
123                          val rhs = List.tabulate (arity, fn i => if (i = predIndex) then dstVar else dstVar')                          val rhs = List.tabulate (arity, fn i => if (i = predIndex) then dstVar else dstVar')
124                          in                          in
125  (*  (*
126  print(concat["recordAssign: ", SimpleVar.uniqueNameOf srcVar, " --> ", IL.Var.toString lhs,  print(concat["recordAssign: ", SimpleVar.uniqueNameOf srcVar, " --> ", IR.Var.toString lhs,
127  " @ ", IL.Node.toString nd, "\n"]);  " @ ", IR.Node.toString nd, "\n"]);
128  *)  *)
129                            phiMap := VMap.insert (m, srcVar, (lhs, rhs))                            phiMap := VMap.insert (m, srcVar, (lhs, rhs))
130                          end                          end
# Line 144  Line 144 
144     * updating the environment.     * updating the environment.
145     *)     *)
146      fun commitJoin (joinStk, JOIN{env, arity, nd, phiMap, predKill}) = let      fun commitJoin (joinStk, JOIN{env, arity, nd, phiMap, predKill}) = let
147            val IL.JOIN{preds, mask, phis, ...} = IL.Node.kind nd            val IR.JOIN{preds, mask, phis, ...} = IR.Node.kind nd
148          (* update the predKill array based on reachability *)          (* update the predKill array based on reachability *)
149            val _ = let            val _ = let
150                  fun update (_, []) = ()                  fun update (_, []) = ()
151                    | update (i, nd::nds) = (                    | update (i, nd::nds) = (
152                        if IL.Node.isReachable nd then ()                        if IR.Node.isReachable nd then ()
153                        else if Array.sub(predKill, i) then ()                        else if Array.sub(predKill, i) then ()
154                        else (arity := !arity-1; Array.update(predKill, i, true));                        else (arity := !arity-1; Array.update(predKill, i, true));
155                        update (i+1, nds))                        update (i+1, nds))
# Line 175  Line 175 
175                          val dstVar = List.nth(xs, ix)                          val dstVar = List.nth(xs, ix)
176                          in                          in
177  (*  (*
178  print(concat["doVar (", SimpleVar.uniqueNameOf srcVar, ", ", IL.phiToString phi, ", _) @ ", IL.Node.toString nd, "\n"]);  print(concat["doVar (", SimpleVar.uniqueNameOf srcVar, ", ", IR.phiToString phi, ", _) @ ", IR.Node.toString nd, "\n"]);
179  *)  *)
180                            recordAssign (joinStk, srcVar, dstVar);                            recordAssign (joinStk, srcVar, dstVar);
181                            VMap.insert (env, srcVar, dstVar)                            VMap.insert (env, srcVar, dstVar)
# Line 197  Line 197 
197                              end                              end
198                        fun doVar (srcVar, phi as (dstVar, srcVars), (env, phis)) = (                        fun doVar (srcVar, phi as (dstVar, srcVars), (env, phis)) = (
199  (*  (*
200  print(concat["doVar (", SimpleVar.uniqueNameOf srcVar, ", ", IL.phiToString phi, ", _) @ ", IL.Node.toString nd, "\n"]);  print(concat["doVar (", SimpleVar.uniqueNameOf srcVar, ", ", IR.phiToString phi, ", _) @ ", IR.Node.toString nd, "\n"]);
201  *)  *)
202                              recordAssign (joinStk, srcVar, dstVar);                              recordAssign (joinStk, srcVar, dstVar);
203                              (VMap.insert (env, srcVar, dstVar), (dstVar, filterPhiRHS srcVars) ::phis))                              (VMap.insert (env, srcVar, dstVar), (dstVar, filterPhiRHS srcVars) ::phis))
# Line 211  Line 211 
211                            val xs = List.map SOME xs                            val xs = List.map SOME xs
212                            in                            in
213  (*  (*
214  print(concat["doVar (", SimpleVar.uniqueNameOf srcVar, ", ", IL.phiToString phi, ", _) @ ", IL.Node.toString nd, "\n"]);  print(concat["doVar (", SimpleVar.uniqueNameOf srcVar, ", ", IR.phiToString phi, ", _) @ ", IR.Node.toString nd, "\n"]);
215  *)  *)
216                              recordAssign (joinStk, srcVar, dstVar);                              recordAssign (joinStk, srcVar, dstVar);
217                              IL.Var.setBinding (dstVar, IL.VB_PHI xs);                              IR.Var.setBinding (dstVar, IR.VB_PHI xs);
218                              (VMap.insert (env, srcVar, dstVar), (dstVar, xs)::phis)                              (VMap.insert (env, srcVar, dstVar), (dstVar, xs)::phis)
219                            end                            end
220                      val (env, phis') = VMap.foldli doVar (env, []) (!phiMap)                      val (env, phis') = VMap.foldli doVar (env, []) (!phiMap)
# Line 227  Line 227 
227    
228    (* expression translation *)    (* expression translation *)
229      fun cvtExp (env : env, lhs, exp) = (case exp      fun cvtExp (env : env, lhs, exp) = (case exp
230             of S.E_Var x => [IL.ASSGN(lhs, IL.VAR(lookup env x))]             of S.E_Var x => [IR.ASSGN(lhs, IR.VAR(lookup env x))]
231              | S.E_Lit lit => [IL.ASSGN(lhs, IL.LIT lit)]              | S.E_Lit lit => [IR.ASSGN(lhs, IR.LIT lit)]
232              | S.E_Tuple xs => raise Fail "E_Tuple not implemeted"              | S.E_Tuple xs => raise Fail "E_Tuple not implemeted"
233              | S.E_Apply _ => raise Fail "unexpected E_Apply"              | S.E_Apply _ => raise Fail "unexpected E_Apply"
234              | S.E_Prim(f, tyArgs, args, ty) => let              | S.E_Prim(f, tyArgs, args, ty) => let
# Line 236  Line 236 
236                  in                  in
237                    TranslateBasis.translate (lhs, f, tyArgs, args')                    TranslateBasis.translate (lhs, f, tyArgs, args')
238                  end                  end
239              | S.E_Cons(args, _) => [IL.ASSGN(lhs, IL.CONS(List.map (lookup env) args, IL.Var.ty lhs))]              | S.E_Cons(args, _) => [IR.ASSGN(lhs, IR.CONS(List.map (lookup env) args, IR.Var.ty lhs))]
240              | S.E_Seq(args, _) => [IL.ASSGN(lhs, IL.SEQ(List.map (lookup env) args, IL.Var.ty lhs))]              | S.E_Seq(args, _) => [IR.ASSGN(lhs, IR.SEQ(List.map (lookup env) args, IR.Var.ty lhs))]
241              | S.E_Slice(x, indices, ty) => let              | S.E_Slice(x, indices, ty) => let
242                  val x = lookup env x                  val x = lookup env x
243                  val mask = List.map isSome indices                  val mask = List.map isSome indices
# Line 246  Line 246 
246                  val indices = List.mapPartial cvt indices                  val indices = List.mapPartial cvt indices
247                  in                  in
248                    if List.all (fn b => b) mask                    if List.all (fn b => b) mask
249                      then [IL.ASSGN(lhs, IL.OP(Op.TensorSub(IL.Var.ty x), x::indices))]                      then [IR.ASSGN(lhs, IR.OP(Op.TensorSub(IR.Var.ty x), x::indices))]
250                      else [IL.ASSGN(lhs, IL.OP(Op.Slice(IL.Var.ty x, mask), x::indices))]                      else [IR.ASSGN(lhs, IR.OP(Op.Slice(IR.Var.ty x, mask), x::indices))]
251                  end                  end
252              | S.E_Coerce{srcTy, dstTy, x} => (case (srcTy, dstTy)              | S.E_Coerce{srcTy, dstTy, x} => (case (srcTy, dstTy)
253                   of (Ty.T_Int, Ty.T_Tensor _) =>                   of (Ty.T_Int, Ty.T_Tensor _) =>
254                        [IL.ASSGN(lhs, IL.OP(Op.IntToReal, [lookup env x]))]                        [IR.ASSGN(lhs, IR.OP(Op.IntToReal, [lookup env x]))]
255                    | (Ty.T_Sequence(ty, n), Ty.T_DynSequence _) =>                    | (Ty.T_Sequence(ty, n), Ty.T_DynSequence _) =>
256                        [IL.ASSGN(lhs, IL.OP(Op.MkDynamic(cvtTy ty, n), [lookup env x]))]                        [IR.ASSGN(lhs, IR.OP(Op.MkDynamic(cvtTy ty, n), [lookup env x]))]
257                    | (Ty.T_Field _, Ty.T_Field _) =>                    | (Ty.T_Field _, Ty.T_Field _) =>
258                      (* change in continuity is a no-op *)                      (* change in continuity is a no-op *)
259                        [IL.ASSGN(lhs, IL.VAR(lookup env x))]                        [IR.ASSGN(lhs, IR.VAR(lookup env x))]
260                    | _ => raise Fail(concat[                    | _ => raise Fail(concat[
261                          "unsupported type coercion: ", Ty.toString srcTy,                          "unsupported type coercion: ", Ty.toString srcTy,
262                          " ==> ", Ty.toString dstTy                          " ==> ", Ty.toString dstTy
263                        ])                        ])
264                  (* end case *))                  (* end case *))
265              | S.E_LoadSeq(ty, nrrd) => [IL.ASSGN(lhs, IL.OP(Op.LoadSeq(cvtTy ty, nrrd), []))]              | S.E_LoadSeq(ty, nrrd) => [IR.ASSGN(lhs, IR.OP(Op.LoadSeq(cvtTy ty, nrrd), []))]
266              | S.E_LoadImage(_, nrrd, info) => [IL.ASSGN(lhs, IL.OP(Op.LoadImage(DstTy.ImageTy info, nrrd), []))]              | S.E_LoadImage(_, nrrd, info) => [IR.ASSGN(lhs, IR.OP(Op.LoadImage(DstTy.ImageTy info, nrrd), []))]
267            (* end case *))            (* end case *))
268    
269    (* add nodes to save the strand state, followed by an exit node *)    (* add nodes to save the strand state, followed by an exit node *)
270      fun saveStrandState (env, (srcState, dstState), exit) = let      fun saveStrandState (env, (srcState, dstState), exit) = let
271            val stateOut = List.map (lookup env) srcState            val stateOut = List.map (lookup env) srcState
272            fun save (x, x', cfg) = IL.CFG.appendNode (cfg, IL.Node.mkSAVE(x, x'))            fun save (x, x', cfg) = IR.CFG.appendNode (cfg, IR.Node.mkSAVE(x, x'))
273            in            in
274              IL.CFG.appendNode (              IR.CFG.appendNode (
275                ListPair.foldlEq save IL.CFG.empty (dstState, stateOut),                ListPair.foldlEq save IR.CFG.empty (dstState, stateOut),
276                exit)                exit)
277            end            end
278  (*DEBUG*)handle ex => raise ex  (*DEBUG*)handle ex => raise ex
# Line 295  Line 295 
295                          recordAssign (joinStk, lhs, lhs');                          recordAssign (joinStk, lhs, lhs');
296                          cvt (                          cvt (
297                            VMap.insert(env, lhs, lhs'),                            VMap.insert(env, lhs, lhs'),
298                            IL.CFG.concat(cfg, IL.CFG.mkBlock assigns),                            IR.CFG.concat(cfg, IR.CFG.mkBlock assigns),
299                            stms)                            stms)
300                        end                        end
301                    | S.S_IfThenElse(x, b0, b1) => let                    | S.S_IfThenElse(x, b0, b1) => let
# Line 303  Line 303 
303                        val join as JOIN{nd=joinNd, ...} = newJoin (env, 2)                        val join as JOIN{nd=joinNd, ...} = newJoin (env, 2)
304                        val (cfg0, _) = cvtBlock (state, env, (0, join)::joinStk, b0)                        val (cfg0, _) = cvtBlock (state, env, (0, join)::joinStk, b0)
305                        val (cfg1, _) = cvtBlock (state, env, (1, join)::joinStk, b1)                        val (cfg1, _) = cvtBlock (state, env, (1, join)::joinStk, b1)
306                        val cond = IL.Node.mkCOND x'                        val cond = IR.Node.mkCOND x'
307                        fun addEdgeToJoin nd = (case IL.Node.kind nd                        fun addEdgeToJoin nd = (case IR.Node.kind nd
308                               of IL.EXIT{succ, ...} => (                               of IR.EXIT{succ, ...} => (
309                                    succ := SOME joinNd;                                    succ := SOME joinNd;
310                                    IL.Node.setPred (joinNd, nd))  (* will be converted to fake later *)                                    IR.Node.setPred (joinNd, nd))  (* will be converted to fake later *)
311                                | _ => IL.Node.addEdge(nd, joinNd)                                | _ => IR.Node.addEdge(nd, joinNd)
312                              (* end case *))                              (* end case *))
313                      (* package the CFG the represents the conditional (cond, two blocks, and join) *)                      (* package the CFG the represents the conditional (cond, two blocks, and join) *)
314  (* QUESTION: under what conditions do we insert an UNREACHABLE exit node?  Is it when there  (* QUESTION: under what conditions do we insert an UNREACHABLE exit node?  Is it when there
315   * are no real predecessors to the join and the join stack is empty?   * are no real predecessors to the join and the join stack is empty?
316   *)   *)
317                        val condCFG = (                        val condCFG = (
318                              if IL.CFG.isEmpty cfg0                              if IR.CFG.isEmpty cfg0
319                                then (                                then (
320                                  IL.Node.setTrueBranch (cond, joinNd);                                  IR.Node.setTrueBranch (cond, joinNd);
321                                  IL.Node.setPred (joinNd, cond))                                  IR.Node.setPred (joinNd, cond))
322                                else (                                else (
323                                  IL.Node.setTrueBranch (cond, IL.CFG.entry cfg0);                                  IR.Node.setTrueBranch (cond, IR.CFG.entry cfg0);
324                                  IL.Node.setPred (IL.CFG.entry cfg0, cond);                                  IR.Node.setPred (IR.CFG.entry cfg0, cond);
325                                  addEdgeToJoin (IL.CFG.exit cfg0));                                  addEdgeToJoin (IR.CFG.exit cfg0));
326                              if IL.CFG.isEmpty cfg1                              if IR.CFG.isEmpty cfg1
327                                then (                                then (
328                                  IL.Node.setFalseBranch (cond, joinNd);                                  IR.Node.setFalseBranch (cond, joinNd);
329                                  IL.Node.setPred (joinNd, cond))                                  IR.Node.setPred (joinNd, cond))
330                                else (                                else (
331                                  IL.Node.setFalseBranch (cond, IL.CFG.entry cfg1);                                  IR.Node.setFalseBranch (cond, IR.CFG.entry cfg1);
332                                  IL.Node.setPred (IL.CFG.entry cfg1, cond);                                  IR.Node.setPred (IR.CFG.entry cfg1, cond);
333                                  addEdgeToJoin (IL.CFG.exit cfg1));                                  addEdgeToJoin (IR.CFG.exit cfg1));
334                              IL.CFG{entry = cond, exit = joinNd})                              IR.CFG{entry = cond, exit = joinNd})
335                        val env = commitJoin (joinStk, join)                        val env = commitJoin (joinStk, join)
336                        in                        in
337                          cvt (env, IL.CFG.concat (cfg, condCFG), stms)                          cvt (env, IR.CFG.concat (cfg, condCFG), stms)
338                        end                        end
339                    | S.S_New(strandId, args) => let                    | S.S_New(strandId, args) => let
340                        val nd = IL.Node.mkNEW{                        val nd = IR.Node.mkNEW{
341                                strand = strandId,                                strand = strandId,
342                                args = List.map (lookup env) args                                args = List.map (lookup env) args
343                              }                              }
344                        in                        in
345                          cvt (env, IL.CFG.appendNode (cfg, nd), stms)                          cvt (env, IR.CFG.appendNode (cfg, nd), stms)
346                        end                        end
347                    | S.S_Continue => (                    | S.S_Continue => (
348                        killPath joinStk;                        killPath joinStk;
349                        (IL.CFG.concat (cfg, saveStrandState (env, state, IL.Node.mkACTIVE())), env))                        (IR.CFG.concat (cfg, saveStrandState (env, state, IR.Node.mkACTIVE())), env))
350                    | S.S_Die => (                    | S.S_Die => (
351                        killPath joinStk;                        killPath joinStk;
352                        (IL.CFG.appendNode (cfg, IL.Node.mkDIE ()), env))                        (IR.CFG.appendNode (cfg, IR.Node.mkDIE ()), env))
353                    | S.S_Stabilize => (                    | S.S_Stabilize => (
354                        killPath joinStk;                        killPath joinStk;
355                        (IL.CFG.concat (cfg, saveStrandState (env, state, IL.Node.mkSTABILIZE())), env))                        (IR.CFG.concat (cfg, saveStrandState (env, state, IR.Node.mkSTABILIZE())), env))
356                    | S.S_Return _ => raise Fail "unexpected return"                    | S.S_Return _ => raise Fail "unexpected return"
357                    | S.S_Print args => let                    | S.S_Print args => let
358                        val args = List.map (lookup env) args                        val args = List.map (lookup env) args
359                        val nd = IL.Node.mkMASSIGN([], Op.Print(List.map IL.Var.ty args), args)                        val nd = IR.Node.mkMASSIGN([], Op.Print(List.map IR.Var.ty args), args)
360                        in                        in
361                          cvt (env, IL.CFG.appendNode (cfg, nd), stms)                          cvt (env, IR.CFG.appendNode (cfg, nd), stms)
362                        end                        end
363                  (* end case *))                  (* end case *))
364            in            in
365              cvt (env, IL.CFG.empty, stms)              cvt (env, IR.CFG.empty, stms)
366            end            end
367  (*DEBUG*)handle ex => raise ex  (*DEBUG*)handle ex => raise ex
368    
369      fun cvtFragmentBlock (env0, prefixCFG, blk) = let      fun cvtFragmentBlock (env0, prefixCFG, blk) = let
370            val (cfg, env) = cvtBlock (([], []), env0, [], blk)            val (cfg, env) = cvtBlock (([], []), env0, [], blk)
371            val cfg = IL.CFG.concat(prefixCFG, cfg)            val cfg = IR.CFG.concat(prefixCFG, cfg)
372            val entry = IL.Node.mkENTRY ()            val entry = IR.Node.mkENTRY ()
373          (* the live variables out are those that were not live coming in *)          (* the live variables out are those that were not live coming in *)
374            val liveOut = VMap.foldli            val liveOut = VMap.foldli
375                  (fn (x, x', xs) => if VMap.inDomain(env0, x) then xs else x'::xs)                  (fn (x, x', xs) => if VMap.inDomain(env0, x) then xs else x'::xs)
376                    [] env                    [] env
377            val exit = IL.Node.mkFRAGMENT liveOut            val exit = IR.Node.mkFRAGMENT liveOut
378            in            in
379              if IL.CFG.isEmpty cfg              if IR.CFG.isEmpty cfg
380                then IL.Node.addEdge (entry, exit)                then IR.Node.addEdge (entry, exit)
381                else (                else (
382                  IL.Node.addEdge (entry, IL.CFG.entry cfg);                  IR.Node.addEdge (entry, IR.CFG.entry cfg);
383                  IL.Node.addEdge (IL.CFG.exit cfg, exit));                  IR.Node.addEdge (IR.CFG.exit cfg, exit));
384              (IL.CFG{entry = entry, exit = exit}, env)              (IR.CFG{entry = entry, exit = exit}, env)
385            end            end
386  (*DEBUG*)handle ex => raise ex  (*DEBUG*)handle ex => raise ex
387    
# Line 392  Line 392 
392            val (env, loadCFG) = let            val (env, loadCFG) = let
393                (* allocate shadow variables for the state variables *)                (* allocate shadow variables for the state variables *)
394                  val (env, stateIn) = freshVars (env, state)                  val (env, stateIn) = freshVars (env, state)
395                  fun load (x, x') = IL.ASSGN(x, IL.STATE x')                  fun load (x, x') = IR.ASSGN(x, IR.STATE x')
396                  val cfg = IL.CFG.mkBlock (ListPair.map load (stateIn, svars))                  val cfg = IR.CFG.mkBlock (ListPair.map load (stateIn, svars))
397                  in                  in
398                    (env, IL.CFG.concat(loadGlobsCFG, cfg))                    (env, IR.CFG.concat(loadGlobsCFG, cfg))
399                  end                  end
400          (* convert the body of the method *)          (* convert the body of the method *)
401            val (cfg, env) = cvtBlock ((state, svars), env, [], blk)            val (cfg, env) = cvtBlock ((state, svars), env, [], blk)
402          (* add the entry/exit nodes *)          (* add the entry/exit nodes *)
403            val entry = IL.Node.mkENTRY ()            val entry = IR.Node.mkENTRY ()
404            val loadCFG = IL.CFG.prependNode (entry, loadCFG)            val loadCFG = IR.CFG.prependNode (entry, loadCFG)
405            val exit = (case name            val exit = (case name
406                   of StrandUtil.Initially => IL.Node.mkACTIVE ()                   of StrandUtil.Initially => IR.Node.mkACTIVE ()
407                    | StrandUtil.Update => IL.Node.mkACTIVE ()                    | StrandUtil.Update => IR.Node.mkACTIVE ()
408                    | StrandUtil.Stabilize => IL.Node.mkRETURN []                    | StrandUtil.Stabilize => IR.Node.mkRETURN []
409                  (* end case *))                  (* end case *))
410            val body = IL.CFG.concat (loadCFG, cfg)            val body = IR.CFG.concat (loadCFG, cfg)
411  (*DEBUG**val _ = prEnv (StrandUtil.nameToString name, env);*)  (*DEBUG**val _ = prEnv (StrandUtil.nameToString name, env);*)
412  (* FIXME: the following code doesn't work properly *)  (* FIXME: the following code doesn't work properly *)
413            val body = if IL.Node.hasSucc(IL.CFG.exit body)            val body = if IR.Node.hasSucc(IR.CFG.exit body)
414                  then IL.CFG.concat (body, saveStrandState (env, (state, svars), exit))                  then IR.CFG.concat (body, saveStrandState (env, (state, svars), exit))
415                  else IL.CFG{entry = IL.CFG.entry body, exit = exit}                  else IR.CFG{entry = IR.CFG.entry body, exit = exit}
416            in            in
417              IL.Method{              IR.Method{
418                  name = name,                  name = name,
419                  body = body                  body = body
420                }                }
# Line 434  Line 434 
434                  end                  end
435            val (cfg, env) = cvtFragmentBlock (env, loadCFG, rangeInit)            val (cfg, env) = cvtFragmentBlock (env, loadCFG, rangeInit)
436            val (env, iters) = List.foldl cvtIter (env, []) iters            val (env, iters) = List.foldl cvtIter (env, []) iters
437            val (argInitCFG, env) = cvtFragmentBlock (env, IL.CFG.empty, argInit)            val (argInitCFG, env) = cvtFragmentBlock (env, IR.CFG.empty, argInit)
438            in            in
439              IL.Initially{              IR.Initially{
440                  isArray = isArray,                  isArray = isArray,
441                  rangeInit = cfg,                  rangeInit = cfg,
442                  iters = List.rev iters,                  iters = List.rev iters,
# Line 447  Line 447 
447    
448    (* a function for generating a block of assignments to load globals *)    (* a function for generating a block of assignments to load globals *)
449      fun loadGlobs globs env = let      fun loadGlobs globs env = let
450            fun load (env, [], stms) = (IL.CFG.mkBlock(List.rev stms), env)            fun load (env, [], stms) = (IR.CFG.mkBlock(List.rev stms), env)
451              | load (env, (x, x')::globs, stms) = let              | load (env, (x, x')::globs, stms) = let
452                  val x'' = newVar x                  val x'' = newVar x
453                  val stm = IL.ASSGN(x'', IL.GLOBAL x')                  val stm = IR.ASSGN(x'', IR.GLOBAL x')
454                  val env = VMap.insert (env, x, x'')                  val env = VMap.insert (env, x, x'')
455                  in                  in
456                    load (env, globs, stm::stms)                    load (env, globs, stm::stms)
# Line 463  Line 463 
463            val (initBlk, env) = cvtBlock (([], []), VMap.empty, [], inputInit)            val (initBlk, env) = cvtBlock (([], []), VMap.empty, [], inputInit)
464            fun cvt ((x, inp), (gvs, stms)) = let            fun cvt ((x, inp), (gvs, stms)) = let
465                  val x' = newVar x                  val x' = newVar x
466                  val gx = IL.GlobalVar.new(                  val gx = IR.GlobalVar.new(
467                          true,                          true,
468                          SimpleVar.nameOf x,                          SimpleVar.nameOf x,
469                          cvtTy(SimpleVar.typeOf x))                          cvtTy(SimpleVar.typeOf x))
470                  val rhs = (case VMap.find(env, x)                  val rhs = (case VMap.find(env, x)
471                         of SOME dflt => IL.OP(Op.InputWithDefault(Inputs.map cvtTy inp), [dflt])                         of SOME dflt => IR.OP(Op.InputWithDefault(Inputs.map cvtTy inp), [dflt])
472                          | NONE => IL.OP(Op.Input(Inputs.map cvtTy inp), [])                          | NONE => IR.OP(Op.Input(Inputs.map cvtTy inp), [])
473                        (* end case *))                        (* end case *))
474                  val stms =  IL.ASSGN(x', rhs) :: IL.GASSGN(gx, x') :: stms                  val stms =  IR.ASSGN(x', rhs) :: IR.GASSGN(gx, x') :: stms
475                  in                  in
476                    IL.GlobalVar.setBinding (gx, x');                    IR.GlobalVar.setBinding (gx, x');
477                    ((x, gx)::gvs, stms)                    ((x, gx)::gvs, stms)
478                  end                  end
479            val (gvs, stms) = List.foldr cvt ([], []) inputs            val (gvs, stms) = List.foldr cvt ([], []) inputs
480            val cfg = IL.CFG.appendBlock (initBlk, stms)            val cfg = IR.CFG.appendBlock (initBlk, stms)
481            val cfg = IL.CFG.prependNode (IL.Node.mkENTRY(), cfg)            val cfg = IR.CFG.prependNode (IR.Node.mkENTRY(), cfg)
482            val cfg = IL.CFG.appendNode (cfg, IL.Node.mkRETURN [])            val cfg = IR.CFG.appendNode (cfg, IR.Node.mkRETURN [])
483            in            in
484              (cfg, gvs)              (cfg, gvs)
485            end            end
486    
487    (* convert Simple globals to HighIL globals and return a function that generates    (* convert Simple globals to HighIR globals and return a function that generates
488     * an initial binding of globals to local shadow variables.     * an initial binding of globals to local shadow variables.
489     *)     *)
490      fun cvtGlobals globals = let      fun cvtGlobals globals = let
491            fun cvt x = let            fun cvt x = let
492                  val gx = IL.GlobalVar.new(                  val gx = IR.GlobalVar.new(
493                          false,                          false,
494                          SimpleVar.nameOf x,                          SimpleVar.nameOf x,
495                          cvtTy(SimpleVar.typeOf x))                          cvtTy(SimpleVar.typeOf x))
# Line 510  Line 510 
510                 *)                 *)
511                  val (cfg, env) = loadGlobs inputGlobs VMap.empty                  val (cfg, env) = loadGlobs inputGlobs VMap.empty
512                  val (globBlk, env) = cvtBlock (([], []), env, [], globalInit)                  val (globBlk, env) = cvtBlock (([], []), env, [], globalInit)
513                (* build a sequence of statements for initializing the IL globals *)                (* build a sequence of statements for initializing the IR globals *)
514                  val saveGlobsBlk = let                  val saveGlobsBlk = let
515                        fun saveGlob (x, gx) = let                        fun saveGlob (x, gx) = let
516                              val x' = lookup env x (* the local variable that holds the global *)                              val x' = lookup env x (* the local variable that holds the global *)
517                              in                              in
518                                IL.GlobalVar.setBinding (gx, x');                                IR.GlobalVar.setBinding (gx, x');
519                                IL.GASSGN(gx, x')                                IR.GASSGN(gx, x')
520                              end                              end
521                        in                        in
522                          IL.CFG.mkBlock (List.map saveGlob globals)                          IR.CFG.mkBlock (List.map saveGlob globals)
523                        end                        end
524                  val cfg = IL.CFG.prependNode (IL.Node.mkENTRY(), cfg)                  val cfg = IR.CFG.prependNode (IR.Node.mkENTRY(), cfg)
525                  val cfg = IL.CFG.concat(cfg, globBlk)                  val cfg = IR.CFG.concat(cfg, globBlk)
526                  val cfg = IL.CFG.concat(cfg, saveGlobsBlk)                  val cfg = IR.CFG.concat(cfg, saveGlobsBlk)
527                  val cfg = IL.CFG.appendNode (cfg, IL.Node.mkRETURN [])                  val cfg = IR.CFG.appendNode (cfg, IR.Node.mkRETURN [])
528                  in                  in
529                    cfg                    cfg
530                  end                  end
# Line 544  Line 544 
544                        end                        end
545                (* create the state variables *)                (* create the state variables *)
546                  val svars = let                  val svars = let
547                        fun newSVar x = IL.StateVar.new (                        fun newSVar x = IR.StateVar.new (
548                              SimpleVar.kindOf x = S.StrandOutputVar,                              SimpleVar.kindOf x = S.StrandOutputVar,
549                              SimpleVar.nameOf x, cvtTy(SimpleVar.typeOf x))                              SimpleVar.nameOf x, cvtTy(SimpleVar.typeOf x))
550                        in                        in
# Line 555  Line 555 
555                      (* load globals into local variables *)                      (* load globals into local variables *)
556                        val (loadGlobsCFG, env) = loadGlobals env                        val (loadGlobsCFG, env) = loadGlobals env
557                        val (cfg, env) = cvtBlock (([], []), env, [], stateInit)                        val (cfg, env) = cvtBlock (([], []), env, [], stateInit)
558                        val cfg = IL.CFG.concat(loadGlobsCFG, cfg)                        val cfg = IR.CFG.concat(loadGlobsCFG, cfg)
559                        val cfg = IL.CFG.prependNode (IL.Node.mkENTRY(), cfg)                        val cfg = IR.CFG.prependNode (IR.Node.mkENTRY(), cfg)
560                        val cfg = IL.CFG.concat (cfg,                        val cfg = IR.CFG.concat (cfg,
561                              saveStrandState (env, (state, svars), IL.Node.mkSINIT()))                              saveStrandState (env, (state, svars), IR.Node.mkSINIT()))
562                        in                        in
563                          (cfg, env)                          (cfg, env)
564                        end                        end
565                  fun cvtMeth (S.Method(name, blk)) =                  fun cvtMeth (S.Method(name, blk)) =
566                        cvtMethod (loadGlobals, env, name, state, svars, blk)                        cvtMethod (loadGlobals, env, name, state, svars, blk)
567                  in                  in
568                    IL.Strand{                    IR.Strand{
569                        name = name,                        name = name,
570                        params = params,                        params = params,
571                        state = svars,                        state = svars,
# Line 573  Line 573 
573                        methods = List.map cvtMeth methods                        methods = List.map cvtMeth methods
574                      }                      }
575                  end                  end
576            val prog = IL.Program{            val prog = IR.Program{
577                    props = props,                    props = props,
578                    globals = List.map #2 (inputGlobs @ globals),                    globals = List.map #2 (inputGlobs @ globals),
579                    inputInit = inputInit,                    inputInit = inputInit,

Legend:
Removed from v.3471  
changed lines
  Added in v.3476

root@smlnj-gforge.cs.uchicago.edu
ViewVC Help
Powered by ViewVC 1.0.0