Home My Page Projects Code Snippets Project Openings diderot

# SCM Repository

[diderot] Diff of /branches/charisee_dev/src/compiler/high-to-mid/split.sml
 [diderot] / branches / charisee_dev / src / compiler / high-to-mid / split.sml

# Diff of /branches/charisee_dev/src/compiler/high-to-mid/split.sml

branches/charisee/src/compiler/high-to-mid/split.sml revision 2838, Tue Nov 25 03:40:24 2014 UTC branches/charisee_dev/src/compiler/high-to-mid/split.sml revision 3316, Sat Oct 17 01:40:08 2015 UTC
# Line 4  Line 4
5   *)   *)
6
7     (*
8      During the transition from high-IL to mid-IL, complicated EIN expressions are split into simpler ones in order to better identify methods for code generation and common subexpressions. Combining EIN operators in the optimization phase can lead to large and complicated EIN operators. A general code generator would need to expand every operation to work on scalars, which could miss the opportunity for vectorization and lead to poor code generation. Instead, every EIN operator is split into a set of simple EIN operators.  Each EIN expression then only has one operation working on  constants, tensors, deltas, epsilons, images and kernels.
9
10     (1) When the outer EIN operator is $\in {--, +, -, *, /, \sum}$ then for each subexpression analyze to see if they need to be rewritten.
11
12     (1a.) When a subexpression is a field expression $\circledast,\nabla$ then it becomes 0. When it is another operation ${@ --, +, -, *, /, \sum}$ then we lift that subexpression and create a new EIN operator. We replace the subexpression with a tensor expression that represent it's size.
13
14     (1b) Call cleanIndex.sml to clean the indices in the subexpression, and get the shape for the tensor replacement.
15
16     (1c) Call cleanParams.sml to clean the params in the subexpression.\\
17     *)
18
19  structure Split = struct  structure Split = struct
20
21      local      local
22
23      structure E = Ein      structure E = Ein
structure mk= mkOperators
structure SrcIL = HighIL
structure SrcTy = HighILTypes
structure SrcOp = HighOps
structure SrcSV = SrcIL.StateVar
structure VTbl = SrcIL.Var.Tbl
24      structure DstIL = MidIL      structure DstIL = MidIL
25      structure DstTy = MidILTypes      structure DstTy = MidILTypes
structure DstOp = MidOps
26      structure DstV = DstIL.Var      structure DstV = DstIL.Var
27      structure SrcV = SrcIL.Var
28      structure P=Printer      structure P=Printer
structure F=Filter
structure T=TransformEin
structure Var = MidIL.Var
29      structure cleanP=cleanParams      structure cleanP=cleanParams
30      structure cleanI=cleanIndex      structure cleanI=cleanIndex
31
val testing=1
in
32
33        in
34
35      fun setEin(params,index,body)=Ein.EIN{params=params, index=index, body=body}      val numFlag=1   (*remove common subexpression*)
36      fun assignEinApp(y,params,index,body,args)= (y,DstIL.EINAPP(setEin(params,index,body),args))      val testing=0
37      fun setEinZero(y,params,index,args)=  (y,DstIL.EINAPP(setEin(params,index,E.Const 0),args))      fun mkEin e = E.mkEin e
38        val einappzero= DstIL.EINAPP(mkEin([],[],E.Const 0),[])
39        fun setEinZero y=  (y,einappzero)
40      fun cleanParams e =cleanP.cleanParams e      fun cleanParams e =cleanP.cleanParams e
41      fun cleanIndex e =cleanI.cleanIndex e      fun cleanIndex e =cleanI.cleanIndex e
42        fun toStringBind e= MidToString.toStringBind e
43      fun itos i =Int.toString i      fun itos i =Int.toString i
44      fun err str=raise Fail str      fun err str=raise Fail str
45      val cnt = ref 0      val cnt = ref 0
46        fun incUse (DstIL.V{useCnt, ...}) = (useCnt := !useCnt + 1)
47      fun genName prefix = let      fun genName prefix = let
48          val n = !cnt          val n = !cnt
49      in      in
# Line 53  Line 55
55          | _ =>(print(String.concat n);1)          | _ =>(print(String.concat n);1)
56          (*end case*))          (*end case*))
57
fun printEINAPP(id, DstIL.EINAPP(rator, args))=let
val a=String.concatWith " , " (List.map Var.toString args)
in
String.concat([(DstTy.toString (Var.ty id)),"<",Var.toString id,"> ==",P.printerE rator, a,"\n"])
end
| printEINAPP(id, DstIL.OP(rator, args))=let
val a=String.concatWith " , " (List.map Var.toString args)
in
String.concat([(DstTy.toString (Var.ty id)),"<",Var.toString id,"> =",DstOp.toString rator,a,"\n"])
end

| printEINAPP(id,_)= String.concat([Var.toString id,"<",(DstTy.toString (Var.ty id)),"> non-einapp\n"])

(* mkreplacement:params*index*index_list*int list* ein_exp-> ein_exp* params*args*code*
*creates new param and replacement tensor for the original ein_exp
*Then cleans params for suebxpression
*)
fun mkreplacement(params,args,tshape,sizes,body)=let
val id=length(params)
val params'=params@[E.TEN(1,sizes)]
val e'=E.Tensor(id,tshape)
val M  = DstV.new (genName ("TLifted_"^itos id), DstTy.TensorTy sizes)
val args'=args@[M]
val einapp=cleanParams(M,body,params',sizes,args')
in
(e',params',args',[einapp])
end

58      (* lift:ein_app*params*index*sum_id*args-> (ein_exp* params*args*code)      (* lift:ein_app*params*index*sum_id*args-> (ein_exp* params*args*code)
59      *lifts expression and returns replacement tensor      *lifts expression and returns replacement tensor
60      * cleans the index and params of subexpression      * cleans the index and params of subexpression
61        *creates new param and replacement tensor for the original ein_exp
62      *)      *)
63      fun lift(e,params,index,sx,args)=let      fun lift(name,e,params,index,sx,args,fieldset,flag)=let
64          val (tshape,sizes,body)=cleanIndex(e,index,sx)          val (tshape,sizes,body)=cleanIndex(e,index,sx)
65          val (Re,Rparams,Rargs,code)=mkreplacement(params,args,tshape,sizes,body)          val id=length(params)
66      in          val Rparams=params@[E.TEN(1,sizes)]
67          (Re,Rparams,Rargs,code)          val Re=E.Tensor(id,tshape)
68            val M  = DstV.new (genName (name^"_l_"^itos id), DstTy.TensorTy sizes)
69            val Rargs=args@[M]
70            val einapp=cleanParams(M,body,Rparams,sizes,Rargs)
71            val (_,einapp0)=einapp
72            val (Rargs,newbies,fieldset) =(case flag
73                of 1=> let
74                    val (fieldset,var) = einSet.rtnVar(fieldset,M,einapp0)
75                    in (case var
76                        of NONE=> (args@[M],[einapp],fieldset)
77                        | SOME v=> (incUse v ;(args@[v],[],fieldset))
78                        (*end case*))
79      end      end
80                | _=>(args@[M],[einapp],fieldset)
81      (* simplelift:ein_app*params*index*sum_id*args-> (ein_exp* params*args*code)                (*end case*))
*lifts expression and returns replacement tensor
* cleans params of subexpression
*)
fun simplelift(e,params,index,args)=(*let
val tshape=List.map (fn x => E.V x) index
val(Re,Rparams,Rargs,code)=mkreplacement(params,args,tshape,index,e)
82          in          in
83          (Re,Rparams,Rargs,code)              (Re,Rparams,Rargs,newbies,fieldset)
84          end          end
*)lift(e,params,index,[],args)

85
86
87      (* isOp: ein->int      (* isOp: ein->int
# Line 117  Line 94
94          | E.Apply _   => 0          | E.Apply _   => 0
95          | E.Lift _    => 0          | E.Lift _    => 0
96          | E.Neg _     => 1          | E.Neg _     => 1
97            | E.Sqrt _    => 1
98            | E.Cosine _      => 1
99            | E.ArcCosine _   => 1
100            | E.Sine _        => 1
101            | E.ArcSine _     => 1
102            | E.PowInt _      => 1
103            | E.PowReal _     => 1
105          | E.Sub _     => 1          | E.Sub _     => 1
106          | E.Prod _    => 1          | E.Prod _    => 1
# Line 130  Line 114
114          | _           => 2          | _           => 2
115      (*end case*))      (*end case*))
116
117        fun rewriteOp3(name,sx,e1,x)=let
118            val ((y, DstIL.EINAPP(ein,args)),fieldset,flag)=x
119            val params=Ein.params ein
120            val index=Ein.index ein
121            in (case (isOp e1)
122                of  0   => (E.Const 0,params,args,[],fieldset)
123                | 1     => lift(name,e1,params,index,sx,args,fieldset,flag)
124                | 2     => (e1,params,args,[],fieldset)
125                (*end*))
126            end
127
128      (* simpleOp:ein_exp*params*index*args-> ein_exp*params*args*code      (* rewriteOp:ein_exp*params*index*args-> ein_exp*params*args*code
129       * If e1 an op then call simplelift() to replace it      * If e1 an op then call lift() to replace it
130       * Otherwise rewrite to 0 or it remains the same      *)
131       *)      fun rewriteOp(name,e1,params,index,sx,args,fieldset,flag)=(case (isOp e1)
132      fun simpleOp(e1,params,index,args)=(case (isOp e1)          of  0   => (E.Const 0,params,args,[],fieldset)
133          of  0   => (E.Const 0,params,args,[])          | 1     => lift(name,e1,params,index,sx,args,fieldset,flag)
134          | 2     => (e1,params,args,[])          | 2     => (e1,params,args,[],fieldset)             (*not lifted*)
| _     => simplelift(e1,params,index,args)
135          (*end*))          (*end*))
136
137        fun rewriteOps(name,list1,params,index,sx,args,fieldset0,flag)=let
138            fun m([],rest,params,args,code,fieldset)=(rest,params,args,code,fieldset)
139            | m(e1::es,rest,params,args,code,fieldset)=let
140
141      (* simpleOps:ein_exp list*params*index*args-> ein_exp list*params*args*code              val (e1',params',args',code',fieldset)= rewriteOp(name,e1,params,index,sx,args,fieldset,flag)
* calls simpleOp on ein_exp list
*)
fun simpleOps(list1,params,index,args)=let
fun m([],rest,params,args,code)=(rest,params,args,code)
| m(e1::es,rest,params,args,code)=let
val (e1',params',args',code')= simpleOp(e1,params,index,args)
142              in              in
143                  m(es,rest@[e1'],params',args',code@code')                  m(es,rest@[e1'],params',args',code@code',fieldset)
144              end              end
145          in          in
146              m(list1,[],params,args,[])                  m(list1,[],params,args,[],fieldset0)
147          end          end
148
149      (* prodOps:ein_exp list*params*index*sum_id list*args-> ein_exp list*params*args*code
150       * calls lift  on ein_exp list      (*rewriteOrig: var* ein_exp* params*index list*mid-il vars
151               When the operation is zero then we return a real.
152            -Moved is Zero to before split.
153       *)       *)
154      fun prodOps(list1,params,index,sx,args)=let      fun rewriteOrig(y,body,params,index,sx,args) =cleanParams(y,body,params,index,args)
155          fun m([],rest,params,args,code)=(rest,params,args,code)
156          | m(e1::es,rest,params,args,code)=(case (isOp e1)      fun rewriteOrig3(sx,body,params,args,x) =let
157              of  0   => m(es,rest@[E.Const 0],params,args,code)          val ((y,DstIL.EINAPP(ein,_)),_,_)=x
158              | 2     => m(es,rest@[e1],params,args,code)          val index=Ein.index ein
159              | 1     => let          in  cleanParams(y,body,params,index,args)
160                  val (e1',params',args',code')= lift(e1,params,index,sx,args)          end
161
162        (* handleNeg:var*ein_exp *params*index*args-> (var*einap)*code
163        * calls rewriteOp() lift  on ein_exp
164        *)
165        fun handleNeg(e1,x)=let
166            val (e1',params',args',code,fieldset)=  rewriteOp3("neg",[],e1,x)
167            val body' =E.Neg e1'
168            val einapp= rewriteOrig3([],body',params',args',x)
169                  in                  in
170                      m(es,rest@[e1'],params',args',code@code')              (einapp,code,fieldset)
171                  end                  end
172              (*end case*))
173        (* handleSqrt:var*ein_exp *params*index*args-> (var*einap)*code
174        * calls rewriteOp() lift  on ein_exp
175        *)
176        fun handleSqrt(y,e1,params,index,args,fieldset,flag)=let
177            val (e1',params',args',code,fieldset)=  rewriteOp("sqrt", e1,params,index,[],args,fieldset,flag)
178            val body =E.Sqrt e1'
179            val einapp= rewriteOrig(y,body,params',index,[],args')
180          in          in
181              m(list1,[],params,args,[])          (einapp,code,fieldset)
182          end          end
183
184
185      fun isZero(y,body,params,index,args) =(case (cleanI.isZero body)      (* handleCosine:var*ein_exp *params*index*args-> (var*einap)*code
186          of 1=>  setEinZero(y,params,[],args)      * calls rewriteOp() lift  on ein_exp
187          | _ =>  cleanParams(y,body,params,index,args)      *)
188      (*end case*))      fun handleCosine(y,e1,params,index,args,fieldset,flag)=let
189            val (e1',params',args',code,fieldset)=  rewriteOp("cosine", e1,params,index,[],args,fieldset,flag)
190            val body =E.Cosine e1'
191            val einapp= rewriteOrig(y,body,params',index,[],args')
192            in
193                (einapp,code,fieldset)
194        end
195
196      (* handleNeg:var*ein_exp *params*index*args-> (var*einap)*code      (* handleArcCosine:var*ein_exp *params*index*args-> (var*einap)*code
197      * calls simpleOp() lift  on ein_exp      * calls rewriteOp() lift  on ein_exp
198      *)      *)
199      fun handleNeg(y,e1,params,index,args)=let      fun handleArcCosine(y,e1,params,index,args,fieldset,flag)=let
200          val (e1',params',args',code)=  simpleOp(e1,params,index,args)          val (e1',params',args',code,fieldset)=  rewriteOp("ArcCosine", e1,params,index,[],args,fieldset,flag)
201          val body =E.Neg e1'          val body =E.ArcCosine e1'
202          val einapp= isZero(y,body,params',index,args')          val einapp= rewriteOrig(y,body,params',index,[],args')
203      in      in
204          (einapp,code)              (einapp,code,fieldset)
205      end      end
206
207        (* handleSine:var*ein_exp *params*index*args-> (var*einap)*code
208        * calls rewriteOp() lift  on ein_exp
209        *)
210        fun handleSine(y,e1,params,index,args,fieldset,flag)=let
211            val (e1',params',args',code,fieldset)=  rewriteOp("sine", e1,params,index,[],args,fieldset,flag)
212            val body =E.Sine e1'
213            val einapp= rewriteOrig(y,body,params',index,[],args')
214            in
215                (einapp,code,fieldset)
216        end
217
218        (* handleSine:var*ein_exp *params*index*args-> (var*einap)*code
219        * calls rewriteOp() lift  on ein_exp
220        *)
221        fun handleArcSine(y,e1,params,index,args,fieldset,flag)=let
222            val (e1',params',args',code,fieldset)=  rewriteOp("ArcSine", e1,params,index,[],args,fieldset,flag)
223            val body =E.ArcSine e1'
224            val einapp= rewriteOrig(y,body,params',index,[],args')
225            in
226                (einapp,code,fieldset)
227            end
228
229
230     (* handleSub:var*ein_exp*ein_exp *params*index*args-> (var*einap)*code     (* handleSub:var*ein_exp*ein_exp *params*index*args-> (var*einap)*code
231      * calls simpleOps() lift  on ein_exp      * calls rewriteOps() lift  on ein_exp
232      *)      *)
233      fun handleSub(y,e1,e2,params,index,args)=let      fun handleSub(y,e1,e2,params,index,args,fieldset,flag)=let
234          val ([e1',e2'],params',args',code)=  simpleOps([e1,e2],params,index,args)          val ([e1',e2'],params',args',code,fieldset)=  rewriteOps("subt",[e1,e2],params,index,[],args,fieldset,flag)
235          val body =E.Sub(e1',e2')          val body =E.Sub(e1',e2')
236          val einapp= isZero(y,body,params',index,args')          val einapp= rewriteOrig(y,body,params',index,[],args')
237      in      in
238          (einapp,code)              (einapp,code,fieldset)
239      end      end
240
241      (* handleDiv:var*ein_exp *ein_exp*params*index*args-> (var*einap)*code      (* handleDiv:var*ein_exp *ein_exp*params*index*args-> (var*einap)*code
242      * calls simpleOp() lift  on ein_exp      * calls rewriteOp() lift  on ein_exp
243      *)      *)
244      fun handleDiv(y,e1,e2,params,index,args)=let      fun handleDiv(y,e1,e2,params,index,args,fieldset,flag)=let
245          val (e1',params1',args1',code1')=simpleOp(e1,params,index,args)          val (e1',params1',args1',code1',fieldset)=rewriteOp("div-num",e1,params,index,[],args,fieldset,flag)
246          val (e2',params2',args2',code2')=simpleOp(e2,params1',[],args1')          val (e2',params2',args2',code2',fieldset)=rewriteOp("div-denom",e2,params1',index,[],args1',fieldset,flag)
247          val body =E.Div(e1',e2')          val body =E.Div(e1',e2')
248          val einapp= isZero(y,body,params2',index,args2')          val einapp= rewriteOrig(y,body,params2',index,[],args2')
249      in      in
250              (einapp,code1'@code2')                  (einapp,code1'@code2',fieldset)
251      end      end
252

254      * calls simpleOps() lift  on ein_exp      * calls rewriteOps() lift  on ein_exp
255      *)      *)
257          val (e1',params',args',code)=  simpleOps(e1,params,index,args)
259    fun pb es=String.concatWith "\n\n\t-*-" (List.map P.printbody es)
260    (*)val _ =print("\n****Inside Add:"^Int.toString(length index)^"\n -"^ pb e1 ^"----- newbies\n-"^ pb e1')*)
261
263    val einapp= rewriteOrig(y,body,params',index,[],args')
264    in
265    (einapp,code,fieldset)
266    end
268
270            fun pb es=String.concatWith "\n-" (List.map P.printbody es)
271
272
274          val einapp= isZero(y,body,params',index,args')          val einapp= rewriteOrig(y,body,params',index,[],args')
275      in      in
276          (einapp,code)              (einapp,code,fieldset)
277      end      end
278
279      (* handleProd:var*ein_exp list*params*index*args-> (var*einap)*code      (* handleProd:var*ein_exp list*params*index*args-> (var*einap)*code
280       * calls prodOps() lift  on ein_exp       * calls rewriteOps() lift  on ein_exp
281       *)       *)
282      fun handleProd(y,e1,params,index,args)=let      fun handleProd(y,e1,params,index,args,fieldset,flag)=let
283          val (e1',params',args',code)=  prodOps(e1,params,index,[],args)          val (e1',params',args',code,fieldset)=  rewriteOps("prod",e1,params,index,[],args,fieldset,flag)
284          val body =E.Prod e1'          val body =E.Prod e1'
285          val einapp= isZero(y,body,params',index,args')          val einapp= rewriteOrig(y,body,params',index,[],args')
286      in      in
287          (einapp,code)              (einapp,code,fieldset)
288      end      end
289
290     (* handleSumProd:var*ein_exp *params*index*args-> (var*einap)*code     (* handleSumProd:var*ein_exp *params*index*args-> (var*einap)*code
291      * calls prodOps() lift  on ein_exp      * calls rewriteOps() lift  on ein_exp
292      *)      *)
293      fun handleSumProd(y,e1,params,index,sx,args)=let      fun handleSumProd(y,e1,params,index,sx,args,fieldset,flag)=let
294          val _ =List.map (fn (_,_,ub)=> Int.toString ub) sx          val (e1',params',args',code,fieldset)=  rewriteOps("sumprod",e1,params,index,sx,args,fieldset,flag)
val (e1',params',args',code)=  prodOps(e1,params,index,sx,args)
295          val body= E.Sum(sx,E.Prod e1')          val body= E.Sum(sx,E.Prod e1')
296          val einapp= isZero(y,body,params',index,args')          val einapp= rewriteOrig(y,body,params',index,sx,args')
297      in      in
298          (einapp,code)              (einapp,code,fieldset)
299      end      end
300
301      (* split:var*ein_app-> (var*einap)*code      (* split:var*ein_app-> (var*einap)*code
302      * split ein expression into smaller pieces      * split ein expression into smaller pieces
303          note we leave summation around probe exp
304      *)      *)
305      fun split(y,einapp as DstIL.EINAPP(Ein.EIN{params, index, body},args))=let      fun split((y,einapp as DstIL.EINAPP(Ein.EIN{params, index, body},args)),fieldset,flag) =let
306          val zero=   (setEinZero(y,params,[],args),[])          val x= ((y,einapp),fieldset,flag)
307          val default=((y,einapp),[])          val zero=   (setEinZero y,[],fieldset)
308            val default=((y,einapp),[],fieldset)
309          val sumIndex=ref []          val sumIndex=ref []
310            val str="Poorly formed EIN operator. Argument needs to be applied in High-IL"^(P.printbody body)
311            val _=testp["\n\nStarting split",P.printbody body]
312          fun rewrite b=(case b          fun rewrite b=(case b
313              of E.Probe _              => default              of E.Probe(E.Conv _,_)   => default
314              | E.Conv _                => zero              | E.Probe(E.Field _,_)    => raise Fail str
315              | E.Field _               => zero              | E.Probe _               => raise Fail str
316              | E.Apply _               => zero              | E.Conv _                => raise Fail "should have been swept"
317              | E.Lift e                => zero              | E.Field _               => raise Fail "should have been swept"
318                | E.Apply _               => raise Fail "should have been swept"
319                | E.Lift e                => raise Fail "should have been swept"
320              | E.Delta _               => default              | E.Delta _               => default
321              | E.Epsilon _             => default              | E.Epsilon _             => default
322                | E.Eps2 _                => default
323              | E.Tensor _              => default              | E.Tensor _              => default
324              | E.Const _               => default              | E.Const _               => default
325              | E.Neg e1                => handleNeg(y,e1,params,index,args)              | E.ConstR _              => default
326              | E.Sub (e1,e2)           => handleSub(y,e1,e2,params,index,args)              | E.Neg e1                => handleNeg(e1,x)
327              | E.Div (e1,e2)           => handleDiv(y,e1,e2,params,index,args)              | E.Sqrt e1               => handleSqrt(y,e1,params,index,args,fieldset,flag)
328              | E.Sum(_,E.Probe _)      => default              | E.Cosine e1             => handleCosine(y,e1,params,index,args,fieldset,flag)
329              | E.Sum(_,E.Conv _)       => zero              | E.ArcCosine e1          => handleArcCosine(y,e1,params,index,args,fieldset,flag)
330              | E.Sum(sx,E.Prod e1)     => handleSumProd(y,e1,params,index,sx,args)              | E.Sine e1               => handleSine(y,e1,params,index,args,fieldset,flag)
331              | E.Sum(sx,E.Neg n)       => rewrite (E.Neg(E.Sum(sx,n)))              | E.ArcSine e1            => handleArcSine(y,e1,params,index,args,fieldset,flag)
332              | E.Sum(sx,E.Add a)       => rewrite (E.Add(List.map (fn e=> E.Sum(sx,e)) a))              | E.PowInt e1             => err(" PowInt unsupported")
333              | E.Sum(sx,E.Sub (e1,e2)) => rewrite (E.Sub(E.Sum(sx,e1),E.Sum(sx,e2)))              | E.PowReal e1            => err(" PowReal unsupported")
334              | E.Sum(sx,E.Div(e1,e2))  => rewrite(E.Div(E.Sum(sx,e1),E.Sum(sx,e2)))              | E.Sub (e1,e2)           => handleSub(y,e1,e2,params,index,args,fieldset,flag)
335              | E.Sum(c1, E.Sum (c2,e)) => rewrite (E.Sum (c1@c2,e))              | E.Div (e1,e2)           => handleDiv(y,e1,e2,params,index,args,fieldset,flag)
336              | E.Sum(sx,_)             => default  (*
337              | E.Add e1                => handleAdd(y,e1,params,index,args)              | E.Sum(_,E.Prod[E.Eps2 _, E.Probe(E.Conv _,_)  ])      => default
338              | E.Prod e1               => handleProd(y,e1,params,index,args)              | E.Sum(_,E.Prod[E.Epsilon _, E.Probe(E.Conv _,_)  ])      => default
339    *)
340                | E.Sum(_,E.Probe(E.Conv _,_))    => default
341                | E.Sum(sx,E.Prod e1)     => handleSumProd(y,e1,params,index,sx,args,fieldset,flag)
342                | E.Sum(sx,E.Delta d)     => handleSumProd(y,[E.Delta d],params,index,sx,args,fieldset,flag)
343                | E.Sum(sx,E.Tensor _)    => default
344                | E.Sum(sx,_)             => err(" summation not distributed:"^str)
346                | E.Prod[E.Tensor(id0,[]),E.Tensor(id1,[i]),E.Tensor(id2,[])]=>
347                        rewrite (E.Prod[E.Prod[E.Tensor(id0,[]),E.Tensor(id2,[])],E.Tensor(id1,[i])])
348                | E.Prod e1               => handleProd(y,e1,params,index,args,fieldset,flag)
349              | E.Partial _             => err(" Partial used after normalize")              | E.Partial _             => err(" Partial used after normalize")
350              | E.Krn _                 => err("Krn used before expand")              | E.Krn _                 => err("Krn used before expand")
351              | E.Value _               => err("Value used before expand")              | E.Value _               => err("Value used before expand")
352              | E.Img _                 => err("Probe used before expand")              | E.Img _                 => err("Probe used before expand")
353              (*end case *))              (*end case *))
354            val (einapp2,newbies,fieldset) =rewrite body
val (einapp2,newbies) =rewrite body
355          in          in
356              (einapp2,newbies)              ((einapp2,newbies),fieldset)
357          end          end
358          |split(y,app) =((y,app),[])          |split((y,app),fieldset,_) =(((y,app),[]),fieldset)
359
360
361      (* iterMultiple:code*code=> (code*code)      fun iterMultiple(einapp2,newbies2,fieldset)=let
362       * recursively split ein expression into smaller pieces          fun itercode([],rest,code,_)=(rest,code)
363      *)            | itercode(e1::newbies,rest,code,cnt)=let
364      fun iterMultiple(einapp2,newbies2)=let                  val ((einapp3,code3),_) = split(e1,fieldset,numFlag)
365          fun itercode([],rest,code)=(rest,code)                      val (rest4,code4)=itercode(code3,[],[],cnt+1)
366          | itercode(e1::newbies,rest,code)=let          in
367              val (einapp3,code3) =split(e1)              itercode(newbies,rest@[einapp3],code4@( rest4)@code,cnt+2)
val (rest4,code4)=itercode(code3,[],[])
in itercode(newbies,rest@[einapp3],code4@rest4@code)
368              end              end
369          val(rest,code)= itercode(newbies2,[],[])              val(rest,code)= itercode(newbies2,[],[],1)
370          in          in
371              (einapp2,code@rest)              ((code)@rest@[einapp2])
372          end          end
373
374
375      fun iterSplit(y,einapp)=let      fun iterAll(einapp2,fieldset)=let
376          val (einapp2,newbies2)=split(y,einapp)          fun itercode([],rest,code,_)=(rest,code)
377            | itercode(e1::newbies,rest,code,cnt)=let
378                val ((einapp3,code3),_) = split(e1,fieldset,numFlag)
379                val (rest4,code4)=itercode(code3,[],[],cnt+1)
380                    val _ =testp [toStringBind(e1),"\n\t===>\n",toStringBind(einapp3),"\nand\n",(String.concatWith",\n\t"(List.map toStringBind (code4@rest4)))]
381      in      in
382          iterMultiple(einapp2,newbies2)                  itercode(newbies,rest@[einapp3],code4@( rest4)@code,cnt+2)
383                end
384            val(rest,code)= itercode(einapp2,[],[],0)
385            in
386                (code@rest)
387      end      end
388
389        fun splitEinApp einapp3= let
390            val fieldset= einSet.EinSet.empty
391
392            (* **** split in parts **** *)
393      (* gettest:code*code=> (code*code)          (*
394      * print results for splitting einapp          val ((einapp4,newbies4),fieldset)=split(einapp3,fieldset,0)
395            val _ =testp["\n\t===>\n",toStringBind(einapp4),"\nand\n",(String.concatWith",\n\t"(List.map toStringBind newbies4))]
396            val (newbies5)= iterMultiple(einapp4,newbies4,fieldset)
397      *)      *)
398      fun gettest(einapp)=(case testing
399          of 0=>iterSplit(einapp)          (* **** split all at once **** *)
400          | _=>let          val (newbies5)= iterAll([einapp3],fieldset)
401              val star="\n*************\n"
val _ =print(String.concat[star])
val (einapp2,newbies)=iterSplit(einapp)
val a=printEINAPP einapp2
val b=String.concatWith",\n\t"(List.map printEINAPP newbies)
val _ =print(String.concat[printEINAPP einapp,"=>",a," newbies\n\t",b, "\n",a,star])
402              in              in
403                  (einapp2,newbies)              newbies5
404              end              end
(*end case*))
405
406
407    end; (* local *)    end; (* local *)

Legend:
 Removed from v.2838 changed lines Added in v.3316