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

SCM Repository

[diderot] Annotation of /branches/vis15/src/compiler/high-opt/eps-util.sml
ViewVC logotype

Annotation of /branches/vis15/src/compiler/high-opt/eps-util.sml

Parent Directory Parent Directory | Revision Log Revision Log


Revision 4295 - (view) (download)

1 : jhr 3515 (* eps-util.sml
2 :     *
3 :     * This code is part of the Diderot Project (http://diderot-language.cs.uchicago.edu)
4 :     *
5 :     * COPYRIGHT (c) 2015 The University of Chicago
6 :     * All rights reserved.
7 :     *)
8 :    
9 :     (* Helper functions for normalize-ein_exp
10 :     * does the rewriting for Epsilon and deltas
11 :     *)
12 :     structure EpsUtil : sig
13 :    
14 :     val epsToDels : Ein.ein_exp list
15 : jhr 4220 -> (Ein.ein_exp * Ein.sumrange list) option * Ein.ein_exp list option * Ein.ein_exp list
16 : jhr 3515
17 :     val reduceDelta : Ein.ein_exp list * Ein.ein_exp list * Ein.ein_exp list
18 :     -> bool * Ein.ein_exp
19 :    
20 : cchiw 4289 val matchEps : Ein.mu list * Ein.mu list -> bool
21 : jhr 3515
22 :     end = struct
23 :    
24 :     structure E = Ein
25 :    
26 :     fun err str = raise Fail (String.concat["Ill-formed EIN Operator",str])
27 :    
28 :     (* check to see if a pair of Epsilon expressions can be converted to deltas *)
29 :     fun doubleEps (E.Epsilon(a,b,c), E.Epsilon(d,e,f)) = let
30 :     fun createDeltas (s, t, u, v) =
31 :     (* FIXME: what does the following comment mean? *)
32 :     (*If multiple summation ids are the same, it might not remove from the summation queue*)
33 :     if (s=u andalso t=v) orelse (s=v andalso t=u)
34 :     then NONE
35 :     else let
36 : cchiw 3978 val d1 = [E.Delta(s, u), E.Delta(t, v)]
37 :     val d2 = [E.Delta(s, v), E.Delta(t, u)]
38 : jhr 3515 in
39 :     SOME(d1, d2)
40 :     end
41 :     in
42 :     if (a=d) then createDeltas(b, c, e, f)
43 :     else if (a=e) then createDeltas(b, c, f, d)
44 :     else if (a=f) then createDeltas(b, c, d, e)
45 :     else if (b=d) then createDeltas(c, a, e, f)
46 :     else if (b=e) then createDeltas(c, a, f, d)
47 :     else if (b=f) then createDeltas(c, a, d, e)
48 :     else if (c=d) then createDeltas(a, b, e, f)
49 :     else if (c=e) then createDeltas(a, b, f, d)
50 :     else if (c=f) then createDeltas(a, b, d, e)
51 :     else NONE
52 : jhr 4143 end
53 : jhr 3515 | doubleEps _ = raise Fail "None Epsilon Argument"
54 :    
55 :     (* distributeEps (epsAll, sumexp)
56 :     * ???
57 :     *)
58 : jhr 4143 (*distributeEps:ein_exp list* ein_exp list
59 :     -> int*ein_exp list * ein_exp list *ein_exp list *sum_index_id list
60 :     * ein_exp list
61 :     *epsAll is a list of epsilons
62 :     *sumExp is a summation expression with epsilon
63 :     * Before this function, there is call to filter all the epislons
64 :     * in a product expression.
65 :     *Sometimes a matching epislon can be hidden in a SummationExp, so that makes the search a little more complicated
66 :     *The arguments to this function are either
67 :     *(1) a list of epsilons in epsAll
68 :     *(2) or a single item in both epsAll and sumExp.
69 :     *In case (1), We check two epislons at a time for a match
70 :     *If there is match then we return unused epsilon list, and rewriten deltas pairs
71 :     *In case (2) We check the embedded eps for a match and if we find one return sum_ids and the rest of the product
72 :     *)
73 : jhr 3515 fun distributeEps (epsAll, sumexp) = let
74 : jhr 4143 fun distEps ([], _) = NONE
75 : jhr 3515 | distEps ([e1], eps) = (case sumexp
76 :     of [E.Sum(sx, E.Opn(E.Prod, e2::ps))] => (case doubleEps(e1, e2)
77 : cchiw 4138 of SOME(d1, d2) => SOME(eps, d1, d2, sx, ps)
78 :     | NONE => NONE
79 : jhr 3515 (* end case *))
80 :     | _ => NONE
81 :     (* end case *))
82 :     | distEps (e1::e2::current,eps) = (case doubleEps(e1, e2)
83 :     of SOME(d1, d2) => SOME(eps@current, d1, d2, [], sumexp)
84 :     | _ => distEps(e2::current, eps@[e1])
85 :     (* end case *))
86 :     in
87 :     distEps (epsAll, [])
88 :     end
89 :    
90 :     (*epsToDels:ein_exp list
91 :     -> int*ein_exp * sum_index_id*ein_exp list *ein_exp list
92 :     *Looks at ein_exp list and searches for epsilons
93 :     *calls above function to look for transition
94 :     *return: change, e', sx
95 :     *)
96 :     fun epsToDels exps = let
97 : jhr 3520 val (epsAll, rest, sumexp) = EinFilter.filterEps exps
98 : jhr 4220 (* DEBUG *
99 :     fun pp e = String.concatWith"," (List.map EinPP.expToString e)
100 :     val _ =print(String.concat["\n\nepsall:",pp epsAll,"\nresl:",pp rest, "\nsumexp",pp sumexp])
101 :     *)
102 : cchiw 4219 in
103 : jhr 3515 case distributeEps(epsAll, sumexp)
104 : jhr 4220 of NONE => if (length epsAll > 0)
105 :     then (NONE, SOME epsAll, rest@sumexp)
106 :     else (NONE, NONE, rest@sumexp)
107 : jhr 3515 | SOME(epsUnused, d1, d2, sx, ps) => let
108 : jhr 4220 (* d1, d2 are rewritten delta expressions *)
109 : jhr 4143 (* in some cases there are embedded expressions of the form E.Sum(sx, ...ps)*)
110 :     (* sx does not apply to the rest of the expression ("rest")*)
111 :     (* return expression in pieces in order to preserve structure*)
112 : cchiw 4138 val a = E.Opn(E.Prod, epsUnused@d1@ps)
113 :     val b = E.Opn(E.Prod, epsUnused@d2@ps)
114 : jhr 3515 in
115 : cchiw 4219 (SOME(E.Op2(E.Sub, a, b), sx), NONE, rest)
116 : jhr 4143 end
117 : jhr 3515 (*end case *)
118 :     end
119 : jhr 4143
120 :     (* reduceDelta:ein_exp*ein_exp* ein_exp list ->int *ein_exp
121 :     * Apply deltas to tensors/fields
122 :     * returns change or rewriten ein_exp
123 :     *
124 :     * distPart:mu list*mu*mu* mu list
125 :     * looks for match with index_id and delta
126 :     * current delta is Delta_{i,j},Differentiation has index_ids pd
127 :     *
128 :     * distribute:int*ein_exp list*ein_exp list *ein_exp list*ein_exp list
129 :     * distribute deltas of ein_exp list
130 :     *)
131 : jhr 3515 fun reduceDelta (eps, dels, es)=let
132 : jhr 4295 fun appDel (changed, [], beta, mu, nu) = (changed, List.rev beta, mu @ List.rev nu)
133 : cchiw 3979 | appDel (changed, a::alpha, beta, [], nu) = appDel(changed, alpha, a::beta, List.rev nu, [])
134 : jhr 3515 | appDel (changed, a::alpha, beta, E.Delta(i, j)::mu, nu) =
135 : cchiw 4289 if (a = j)
136 : jhr 4295 then appDel(true, alpha, i::beta, mu, nu)
137 :     else appDel(changed, a::alpha, beta, mu, E.Delta(i, j)::nu)
138 : jhr 3515 (* FIXME: instead of appending singletons, build results in reverse order! *)
139 :     fun distribute (changed, [], rest, mu) = (changed, E.Opn(E.Prod, eps@mu@rest))
140 : jhr 4143 | distribute (changed, p1::ps, rest, mu) = (case p1
141 : jhr 3515 of E.Tensor(id, alpha) => let
142 :     val (changed, alpha_betas, nu) = appDel(changed, alpha, [], mu, [])
143 :     in
144 :     distribute(changed, ps, rest@[E.Tensor(id, alpha_betas)], nu)
145 :     end
146 :     | E.Field(id, alpha) => let
147 :     val (changed, alpha_betas, nu) = appDel(changed, alpha, [], mu, [])
148 :     in
149 :     distribute(changed, ps, rest@[E.Field(id, alpha_betas)], nu)
150 :     end
151 :     | E.Conv(v, alpha, h, dx) => let
152 :     val (changed, alpha_betas, nu1) = appDel(changed, alpha, [] ,mu, [])
153 :     val (changed, dx_betas, nu2) = appDel(changed, dx, [], nu1, [])
154 :     in
155 :     distribute(changed, ps, rest@[E.Conv(v,alpha_betas, h ,dx_betas)], nu2)
156 :     end
157 :     | E.Probe(E.Conv(v, alpha, h, dx), t) => let
158 :     val (changed, alpha_betas, nu1) = appDel(changed, alpha, [], mu, [])
159 :     val (changed, dx_betas, nu2) = appDel(changed, dx, [], nu1, [])
160 :     in
161 :     distribute(
162 :     changed, ps, rest@[E.Probe(E.Conv(v,alpha_betas, h ,dx_betas),t)], nu2)
163 :     end
164 :     | E.Apply(E.Partial d, e) => let
165 :     val (changed, d_betas, nu) = appDel(changed,d,[],mu,[])
166 :     in
167 :     distribute(changed, ps, rest@[E.Apply(E.Partial d_betas,e)],nu)
168 :     end
169 :     | _ => distribute(changed, ps, rest@[p1], mu)
170 :     (* end case *))
171 :     in
172 :     distribute (false, es, [], dels)
173 :     end
174 :    
175 : jhr 3980 (* matchEps: checks if two different indices in 'ids' both appear in 'mus' *)
176 : cchiw 3978 fun matchEps (ids, mus) = let
177 : cchiw 4289 (* fun inMus id = List.exists (fn (E.C _) => false | (E.V x) => (x = id)) mus*)
178 :     fun inMus id = List.exists (fn x => (x = id)) mus
179 : jhr 3980 fun match0 [] = false
180 :     | match0 (id::ids) = if inMus id
181 :     then match1 (ids, id)
182 :     else match0 ids
183 :     and match1 ([], id) = false
184 :     | match1 (id::ids, id') = ((id <> id') andalso inMus id) orelse match1 (ids, id')
185 :     in
186 :     match0 ids
187 :     end
188 : jhr 3515
189 :     end

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