844b2592fbb06f0f1145d71cfc2302071ca40402
[IRC.git] / Robust / src / IR / Flat / BuildCodeMultiCore.java
1 package IR.Flat;
2
3 import java.io.FileOutputStream;
4 import java.io.PrintWriter;
5 import java.util.HashSet;
6 import java.util.Hashtable;
7 import java.util.Iterator;
8 import java.util.LinkedList;
9 import java.util.Queue;
10 import java.util.Set;
11 import java.util.Vector;
12
13 import Analysis.Locality.LocalityBinding;
14 import Analysis.Scheduling.Schedule;
15 import Analysis.TaskStateAnalysis.FEdge;
16 import Analysis.TaskStateAnalysis.FlagState;
17 import Analysis.TaskStateAnalysis.SafetyAnalysis;
18 import Analysis.OwnershipAnalysis.AllocationSite;
19 import Analysis.OwnershipAnalysis.OwnershipAnalysis;
20 import Analysis.OwnershipAnalysis.HeapRegionNode;
21 import Analysis.Prefetch.*;
22 import IR.ClassDescriptor;
23 import IR.Descriptor;
24 import IR.FlagDescriptor;
25 import IR.MethodDescriptor;
26 import IR.State;
27 import IR.TagVarDescriptor;
28 import IR.TaskDescriptor;
29 import IR.TypeDescriptor;
30 import IR.TypeUtil;
31 import IR.VarDescriptor;
32 import IR.Tree.DNFFlag;
33 import IR.Tree.DNFFlagAtom;
34 import IR.Tree.FlagExpressionNode;
35 import IR.Tree.TagExpressionList;
36
37 public class BuildCodeMultiCore extends BuildCode {
38   private Vector<Schedule> scheduling;
39   int coreNum;
40   Schedule currentSchedule;
41   Hashtable[] fsate2qnames;
42   String objqarrayprefix= "objqueuearray4class";
43   String objqueueprefix = "objqueue4parameter_";
44   String paramqarrayprefix = "paramqueuearray4task";
45   String coreqarrayprefix = "paramqueuearrays_core";
46   String taskprefix = "task_";
47   String taskarrayprefix = "taskarray_core";
48   String otqueueprefix = "___otqueue";
49   int startupcorenum;    // record the core containing startup task, suppose only one core can hava startup object
50
51   private OwnershipAnalysis m_oa;
52   private Vector<Vector<Integer>> m_aliasSets;
53   Hashtable<Integer, Vector<FlatNew>> m_aliasFNTbl4Para;
54   Hashtable<FlatNew, Vector<FlatNew>> m_aliasFNTbl;
55   Hashtable<FlatNew, Vector<Integer>> m_aliaslocksTbl4FN;
56
57   public BuildCodeMultiCore(State st, 
58                             Hashtable temptovar, 
59                             TypeUtil typeutil, 
60                             SafetyAnalysis sa, 
61                             Vector<Schedule> scheduling, 
62                             int coreNum, 
63                             PrefetchAnalysis pa) {
64     super(st, temptovar, typeutil, sa, pa);
65     this.scheduling = scheduling;
66     this.coreNum = coreNum;
67     this.currentSchedule = null;
68     this.fsate2qnames = null;
69     this.startupcorenum = 0;
70
71     // sometimes there are extra cores then needed in scheduling
72     // TODO
73     // currently, it is guaranteed that in scheduling, the corenum
74     // is started from 0 and continuous.
75     // MAY need modification here in the future when take hardware
76     // information into account.
77     if(this.scheduling.size() < this.coreNum) {
78       this.coreNum = this.scheduling.size();
79     }
80
81     this.m_oa = null;
82     this.m_aliasSets = null;
83     this.m_aliasFNTbl4Para = null;
84     this.m_aliasFNTbl = null;
85     this.m_aliaslocksTbl4FN = null;
86   }
87
88   public void setOwnershipAnalysis(OwnershipAnalysis m_oa) {
89     this.m_oa = m_oa;
90   }
91
92   public void buildCode() {
93     /* Create output streams to write to */
94     PrintWriter outclassdefs=null;
95     PrintWriter outstructs=null;
96     PrintWriter outmethodheader=null;
97     PrintWriter outmethod=null;
98     PrintWriter outvirtual=null;
99     PrintWriter outtask=null;
100     PrintWriter outtaskdefs=null;
101     //PrintWriter outoptionalarrays=null;
102     //PrintWriter optionalheaders=null;
103
104     try {
105       outstructs=new PrintWriter(new FileOutputStream(PREFIX+"structdefs.h"), true);
106       outmethodheader=new PrintWriter(new FileOutputStream(PREFIX+"methodheaders.h"), true);
107       outclassdefs=new PrintWriter(new FileOutputStream(PREFIX+"classdefs.h"), true);
108       outvirtual=new PrintWriter(new FileOutputStream(PREFIX+"virtualtable.h"), true);
109       outmethod=new PrintWriter(new FileOutputStream(PREFIX+"methods.c"), true);
110       if (state.TASK) {
111         outtask=new PrintWriter(new FileOutputStream(PREFIX+"task.h"), true);
112         outtaskdefs=new PrintWriter(new FileOutputStream(PREFIX+"taskdefs.c"), true);
113         /* optional
114            if (state.OPTIONAL){
115             outoptionalarrays=new PrintWriter(new FileOutputStream(PREFIX+"optionalarrays.c"), true);
116             optionalheaders=new PrintWriter(new FileOutputStream(PREFIX+"optionalstruct.h"), true);
117            } */
118       }
119       /*if (state.structfile!=null) {
120           outrepairstructs=new PrintWriter(new FileOutputStream(PREFIX+state.structfile+".struct"), true);
121          }*/
122     } catch (Exception e) {
123       e.printStackTrace();
124       System.exit(-1);
125     }
126
127     /* Build the virtual dispatch tables */
128     super.buildVirtualTables(outvirtual);
129
130     /* Output includes */
131     outmethodheader.println("#ifndef METHODHEADERS_H");
132     outmethodheader.println("#define METHODHEADERS_H");
133     outmethodheader.println("#include \"structdefs.h\"");
134     /*if (state.DSM)
135         outmethodheader.println("#include \"dstm.h\"");*/
136
137     /* Output Structures */
138     super.outputStructs(outstructs);
139
140     // Output the C class declarations
141     // These could mutually reference each other
142     super.outputClassDeclarations(outclassdefs);
143
144     // Output function prototypes and structures for parameters
145     Iterator it=state.getClassSymbolTable().getDescriptorsIterator();
146     int numclasses = this.state.numClasses();
147     while(it.hasNext()) {
148       ClassDescriptor cn=(ClassDescriptor)it.next();
149       super.generateCallStructs(cn, outclassdefs, outstructs, outmethodheader);
150     }
151     outclassdefs.close();
152
153     if (state.TASK) {
154       /* Map flags to integers */
155       /* The runtime keeps track of flags using these integers */
156       it=state.getClassSymbolTable().getDescriptorsIterator();
157       while(it.hasNext()) {
158         ClassDescriptor cn=(ClassDescriptor)it.next();
159         super.mapFlags(cn);
160       }
161       /* Generate Tasks */
162       generateTaskStructs(outstructs, outmethodheader);
163
164       /* Outputs generic task structures if this is a task
165          program */
166       outputTaskTypes(outtask);
167     }
168
169     /* Build the actual methods */
170     super.outputMethods(outmethod);
171
172     if (state.TASK) {
173       Iterator[] taskits = new Iterator[this.coreNum];
174       for(int i = 0; i < taskits.length; ++i) {
175         taskits[i] = null;
176       }
177       int[] numtasks = new int[this.coreNum];
178       int[][] numqueues = new int[this.coreNum][numclasses];
179       /* Output code for tasks */
180       for(int i = 0; i < this.scheduling.size(); ++i) {
181         this.currentSchedule = this.scheduling.elementAt(i);
182         outputTaskCode(outtaskdefs, outmethod, outtask, taskits, numtasks, numqueues);
183       }
184
185       // Output task descriptors
186       boolean comma = false;
187       outtaskdefs.println("struct parameterwrapper ** objectqueues[][NUMCLASSES] = {");
188       boolean needcomma = false;
189       for(int i = 0; i < numqueues.length ; ++i) {
190         if(needcomma) {
191           outtaskdefs.println(",");
192         } else {
193           needcomma = true;
194         }
195         outtaskdefs.println("/* object queue array for core " + i + "*/");
196         outtaskdefs.print("{");
197         comma = false;
198         for(int j = 0; j < numclasses; ++j) {
199           if(comma) {
200             outtaskdefs.println(",");
201           } else {
202             comma = true;
203           }
204           outtaskdefs.print(this.objqarrayprefix + j + "_core" + i);
205         }
206         outtaskdefs.print("}");
207       }
208       outtaskdefs.println("};");
209       needcomma = false;
210       outtaskdefs.println("int numqueues[][NUMCLASSES] = {");
211       for(int i = 0; i < numqueues.length; ++i) {
212         if(needcomma) {
213           outtaskdefs.println(",");
214         } else {
215           needcomma = true;
216         }
217         int[] tmparray = numqueues[i];
218         comma = false;
219         outtaskdefs.print("{");
220         for(int j = 0; j < tmparray.length; ++j) {
221           if(comma) {
222             outtaskdefs.print(",");
223           } else {
224             comma = true;
225           }
226           outtaskdefs.print(tmparray[j]);
227         }
228         outtaskdefs.print("}");
229       }
230       outtaskdefs.println("};");
231
232       /* parameter queue arrays for all the tasks*/
233       outtaskdefs.println("struct parameterwrapper *** paramqueues[] = {");
234       needcomma = false;
235       for(int i = 0; i < this.coreNum ; ++i) {
236         if(needcomma) {
237           outtaskdefs.println(",");
238         } else {
239           needcomma = true;
240         }
241         outtaskdefs.println("/* parameter queue array for core " + i + "*/");
242         outtaskdefs.print(this.coreqarrayprefix + i);
243       }
244       outtaskdefs.println("};");
245
246       for(int i = 0; i < taskits.length; ++i) {
247         outtaskdefs.println("struct taskdescriptor * " + this.taskarrayprefix + i + "[]={");
248         Iterator taskit = taskits[i];
249         if(taskit != null) {
250           boolean first=true;
251           while(taskit.hasNext()) {
252             TaskDescriptor td=(TaskDescriptor)taskit.next();
253             if (first)
254               first=false;
255             else
256               outtaskdefs.println(",");
257             outtaskdefs.print("&" + this.taskprefix +td.getCoreSafeSymbol(i));
258           }
259         }
260         outtaskdefs.println();
261         outtaskdefs.println("};");
262       }
263       outtaskdefs.println("struct taskdescriptor ** taskarray[]= {");
264       comma = false;
265       for(int i = 0; i < taskits.length; ++i) {
266         if (comma)
267           outtaskdefs.println(",");
268         else
269           comma = true;
270         outtaskdefs.print(this.taskarrayprefix + i);
271       }
272       outtaskdefs.println("};");
273
274       outtaskdefs.print("int numtasks[]= {");
275       comma = false;
276       for(int i = 0; i < taskits.length; ++i) {
277         if (comma)
278           outtaskdefs.print(",");
279         else
280           comma=true;
281         outtaskdefs.print(numtasks[i]);
282       }
283       outtaskdefs.println("};");
284       outtaskdefs.println("int corenum=0;");
285
286       outtaskdefs.close();
287       outtask.println("#endif");
288       outtask.close();
289       /* Record maximum number of task parameters */
290       outstructs.println("#define MAXTASKPARAMS "+maxtaskparams);
291       /* Record maximum number of all types, i.e. length of classsize[] */
292       outstructs.println("#define NUMTYPES "+(state.numClasses() + state.numArrays()));
293       /* Record number of cores */
294       outstructs.println("#define NUMCORES "+this.coreNum);
295       /* Record number of core containing startup task */
296       outstructs.println("#define STARTUPCORE "+this.startupcorenum);
297     }     //else if (state.main!=null) {
298           /* Generate main method */
299           // outputMainMethod(outmethod);
300           //}
301
302     /* Generate information for task with optional parameters */
303     /*if (state.TASK&&state.OPTIONAL){
304         generateOptionalArrays(outoptionalarrays, optionalheaders, state.getAnalysisResult(), state.getOptionalTaskDescriptors());
305         outoptionalarrays.close();
306        } */
307
308     /* Output structure definitions for repair tool */
309     /*if (state.structfile!=null) {
310         buildRepairStructs(outrepairstructs);
311         outrepairstructs.close();
312        }*/
313
314     /* Close files */
315     outmethodheader.println("#endif");
316     outmethodheader.close();
317     outmethod.close();
318     outstructs.println("#endif");
319     outstructs.close();
320   }
321
322   /** This function outputs (1) structures that parameters are
323    * passed in (when PRECISE GC is enabled) and (2) function
324    * prototypes for the tasks */
325
326   private void generateTaskStructs(PrintWriter output, 
327                                    PrintWriter headersout) {
328     /* Cycle through tasks */
329     for(int i = 0; i < this.scheduling.size(); ++i) {
330       Schedule tmpschedule = this.scheduling.elementAt(i);
331       int num = tmpschedule.getCoreNum();
332       Iterator<TaskDescriptor> taskit = tmpschedule.getTasks().iterator();
333
334       while(taskit.hasNext()) {
335         /* Classify parameters */
336         TaskDescriptor task=taskit.next();
337         FlatMethod fm=state.getMethodFlat(task);
338         super.generateTempStructs(fm, null);
339
340         ParamsObject objectparams=(ParamsObject) paramstable.get(task);
341         TempObject objecttemps=(TempObject) tempstable.get(task);
342
343         /* Output parameter structure */
344         if ((GENERATEPRECISEGC) || (this.state.MULTICOREGC)) {
345           output.println("struct "+task.getCoreSafeSymbol(num)+"_params {");
346           output.println("  int size;");
347           output.println("  void * next;");
348           for(int j=0; j<objectparams.numPointers(); j++) {
349             TempDescriptor temp=objectparams.getPointer(j);
350             output.println("  struct "+temp.getType().getSafeSymbol()+" * "+temp.getSafeSymbol()+";");
351           }
352
353           output.println("};\n");
354           if ((objectparams.numPointers()+fm.numTags())>maxtaskparams) {
355             maxtaskparams=objectparams.numPointers()+fm.numTags();
356           }
357         }
358
359         /* Output temp structure */
360         if ((GENERATEPRECISEGC) || (this.state.MULTICOREGC)) {
361           output.println("struct "+task.getCoreSafeSymbol(num)+"_locals {");
362           output.println("  int size;");
363           output.println("  void * next;");
364           for(int j=0; j<objecttemps.numPointers(); j++) {
365             TempDescriptor temp=objecttemps.getPointer(j);
366             if (temp.getType().isNull())
367               output.println("  void * "+temp.getSafeSymbol()+";");
368             else if(temp.getType().isTag())
369               output.println("  struct "+
370                              (new TypeDescriptor(typeutil.getClass(TypeUtil.TagClass))).getSafeSymbol()+" * "+temp.getSafeSymbol()+";");
371             else
372               output.println("  struct "+temp.getType().getSafeSymbol()+" * "+temp.getSafeSymbol()+";");
373           }
374           output.println("};\n");
375         }
376
377         /* Output task declaration */
378         headersout.print("void " + task.getCoreSafeSymbol(num)+"(");
379
380         if ((GENERATEPRECISEGC) || (this.state.MULTICOREGC)) {
381           headersout.print("struct "+task.getCoreSafeSymbol(num)+"_params * "+paramsprefix);
382         } else
383           headersout.print("void * parameterarray[]");
384         headersout.println(");\n");
385       }
386     }
387
388   }
389
390   /* This method outputs code for each task. */
391
392   private void outputTaskCode(PrintWriter outtaskdefs, 
393                                   PrintWriter outmethod, 
394                                   PrintWriter outtask, 
395                                   Iterator[] taskits, 
396                                   int[] numtasks,
397                               int[][] numqueues) {
398     /* Compile task based program */
399     outtaskdefs.println("#include \"task.h\"");
400     outtaskdefs.println("#include \"methodheaders.h\"");
401
402     /* Output object transfer queues into method.c*/
403     generateObjectTransQueues(outmethod);
404
405     //Vector[] qnames = new Vector[2];
406     int numclasses = numqueues[0].length;
407     Vector qnames[]= new Vector[numclasses];
408     for(int i = 0; i < qnames.length; ++i) {
409       qnames[i] = null;
410     }
411     Iterator<TaskDescriptor> taskit=this.currentSchedule.getTasks().iterator();
412     while(taskit.hasNext()) {
413       TaskDescriptor td=taskit.next();
414       FlatMethod fm=state.getMethodFlat(td);
415       generateTaskMethod(fm, null, outmethod);
416       generateTaskDescriptor(outtaskdefs, outtask, fm, td, qnames);
417     }
418
419     // generate queuearray for this core
420     int num = this.currentSchedule.getCoreNum();
421     boolean comma = false;
422     for(int i = 0; i < qnames.length; ++i) {
423       outtaskdefs.println("/* object queue array for class " + i + " on core " + num + "*/");
424       outtaskdefs.println("struct parameterwrapper * " + this.objqarrayprefix + i + "_core" + num + "[] = {");
425       comma = false;
426       Vector tmpvector = qnames[i];
427       if(tmpvector != null) {
428         for(int j = 0; j < tmpvector.size(); ++j) {
429           if(comma) {
430             outtaskdefs.println(",");
431           } else {
432             comma = true;
433           }
434           outtaskdefs.print("&" + tmpvector.elementAt(j));
435         }
436         numqueues[num][i] = tmpvector.size();
437       } else {
438         numqueues[num][i] = 0;
439       }
440       outtaskdefs.println("};");
441     }
442
443     /* All the queues for tasks residing on this core*/
444     comma = false;
445     outtaskdefs.println("/* object queue array for tasks on core " + num + "*/");
446     outtaskdefs.println("struct parameterwrapper ** " + this.coreqarrayprefix + num + "[] = {");
447     taskit=this.currentSchedule.getTasks().iterator();
448     while(taskit.hasNext()) {
449       if (comma) {
450         outtaskdefs.println(",");
451       } else {
452         comma = true;
453       }
454       TaskDescriptor td=taskit.next();
455       outtaskdefs.print(this.paramqarrayprefix + td.getCoreSafeSymbol(num));
456     }
457     outtaskdefs.println("};");
458
459     // record the iterator of tasks on this core
460     taskit=this.currentSchedule.getTasks().iterator();
461     taskits[num] = taskit;
462     numtasks[num] = this.currentSchedule.getTasks().size();
463   }
464
465   /** Prints out definitions for generic task structures */
466   private void outputTaskTypes(PrintWriter outtask) {
467     outtask.println("#ifndef _TASK_H");
468     outtask.println("#define _TASK_H");
469     outtask.println("#include \"ObjectHash.h\"");
470     outtask.println("#include \"structdefs.h\"");
471     outtask.println("#include \"Queue.h\"");
472     outtask.println("#include <string.h>");
473         outtask.println("#include \"runtime_arch.h\"");
474     //outtask.println("#ifdef RAW");
475     //outtask.println("#include <raw.h>");
476     //outtask.println("#endif");
477     outtask.println();
478     outtask.println("struct tagobjectiterator {");
479     outtask.println("  int istag; /* 0 if object iterator, 1 if tag iterator */");
480     outtask.println("  struct ObjectIterator it; /* Object iterator */");
481     outtask.println("  struct ObjectHash * objectset;");
482     outtask.println("#ifdef OPTIONAL");
483     outtask.println("  int failedstate;");
484     outtask.println("#endif");
485     outtask.println("  int slot;");
486     outtask.println("  int tagobjindex; /* Index for tag or object depending on use */");
487     outtask.println("  /*if tag we have an object binding */");
488     outtask.println("  int tagid;");
489     outtask.println("  int tagobjectslot;");
490     outtask.println("  /*if object, we may have one or more tag bindings */");
491     outtask.println("  int numtags;");
492     outtask.println("  int tagbindings[MAXTASKPARAMS-1]; /* list slots */");
493     outtask.println("};");
494     outtask.println();
495     outtask.println("struct parameterwrapper {");
496     outtask.println("  //int type;");
497     outtask.println("  struct ObjectHash * objectset;");
498     outtask.println("  int numberofterms;");
499     outtask.println("  int * intarray;");
500     outtask.println("  int numbertags;");
501     outtask.println("  int * tagarray;");
502     outtask.println("  struct taskdescriptor * task;");
503     outtask.println("  int slot;");
504     outtask.println("  struct tagobjectiterator iterators[MAXTASKPARAMS-1];");
505     outtask.println("};");
506     outtask.println();
507     outtask.println("extern struct parameterwrapper ** objectqueues[][NUMCLASSES];");
508     outtask.println("extern int numqueues[][NUMCLASSES];");
509     outtask.println();
510     outtask.println("struct parameterdescriptor {");
511     outtask.println("  int type;");
512     outtask.println("  int numberterms;");
513     outtask.println("  int *intarray;");
514     outtask.println("  struct parameterwrapper * queue;");
515     outtask.println("  int numbertags;");
516     outtask.println("  int *tagarray;");
517     outtask.println("};");
518     outtask.println();
519     outtask.println("struct taskdescriptor {");
520     outtask.println("  void * taskptr;");
521     outtask.println("  int numParameters;");
522     outtask.println("  int numTotal;");
523     outtask.println("  struct parameterdescriptor **descriptorarray;");
524     outtask.println("  char * name;");
525     outtask.println("};");
526     outtask.println();
527     outtask.println("extern struct taskdescriptor ** taskarray[];");
528     outtask.println("extern int numtasks[];");
529     outtask.println("extern int corenum;");     // define corenum to identify different core
530     outtask.println("extern struct parameterwrapper *** paramqueues[];");
531     outtask.println();
532   }
533
534   private void generateObjectTransQueues(PrintWriter output) {
535     if(this.fsate2qnames == null) {
536       this.fsate2qnames = new Hashtable[this.coreNum];
537       for(int i = 0; i < this.fsate2qnames.length; ++i) {
538         this.fsate2qnames[i] = null;
539       }
540     }
541     int num = this.currentSchedule.getCoreNum();
542     assert(this.fsate2qnames[num] == null);
543     Hashtable<FlagState, String> flag2qname = new Hashtable<FlagState, String>();
544     this.fsate2qnames[num] = flag2qname;
545     Hashtable<FlagState, Queue<Integer>> targetCoreTbl = this.currentSchedule.getTargetCoreTable();
546     if(targetCoreTbl != null) {
547       Object[] keys = targetCoreTbl.keySet().toArray();
548       output.println();
549       output.println("/* Object transfer queues for core" + num + ".*/");
550       for(int i = 0; i < keys.length; ++i) {
551         FlagState tmpfstate = (FlagState)keys[i];
552         Object[] targetcores = targetCoreTbl.get(tmpfstate).toArray();
553         String queuename = this.otqueueprefix + tmpfstate.getClassDescriptor().getCoreSafeSymbol(num) + tmpfstate.getuid() + "___";
554         String queueins = queuename + "ins";
555         flag2qname.put(tmpfstate, queuename);
556         output.println("struct " + queuename + " {");
557         output.println("  int * cores;");
558         output.println("  int index;");
559         output.println("  int length;");
560         output.println("};");
561         output.print("int " + queuename + "cores[] = {");
562         for(int j = 0; j < targetcores.length; ++j) {
563           if(j > 0) {
564             output.print(", ");
565           }
566           output.print(((Integer)targetcores[j]).intValue());
567         }
568         output.println("};");
569         output.println("struct " + queuename + " " + queueins + "= {");
570         output.println(/*".cores = " + */ queuename + "cores,");
571         output.println(/*".index = " + */ "0,");
572         output.println(/*".length = " +*/ targetcores.length + "};");
573       }
574     }
575     output.println();
576   }
577
578   private void generateTaskMethod(FlatMethod fm, 
579                                       LocalityBinding lb, 
580                                       PrintWriter output) {
581     /*if (State.PRINTFLAT)
582         System.out.println(fm.printMethod());*/
583     TaskDescriptor task=fm.getTask();
584     assert(task != null);
585     int num = this.currentSchedule.getCoreNum();
586
587     //ParamsObject objectparams=(ParamsObject)paramstable.get(lb!=null?lb:task);
588     generateTaskHeader(fm, lb, task,output);
589
590     TempObject objecttemp=(TempObject) tempstable.get(lb!=null ? lb : task);
591     /*if (state.DSM&&lb.getHasAtomic()) {
592         output.println("transrecord_t * trans;");
593        }*/
594
595     if ((GENERATEPRECISEGC) || (this.state.MULTICOREGC)) {
596       output.print("   struct "+task.getCoreSafeSymbol(num)+"_locals "+localsprefix+"={");
597
598       output.print(objecttemp.numPointers()+",");
599       output.print(paramsprefix);
600       for(int j=0; j<objecttemp.numPointers(); j++)
601         output.print(", NULL");
602       output.println("};");
603     }
604
605     for(int i=0; i<objecttemp.numPrimitives(); i++) {
606       TempDescriptor td=objecttemp.getPrimitive(i);
607       TypeDescriptor type=td.getType();
608       if (type.isNull())
609         output.println("   void * "+td.getSafeSymbol()+";");
610       else if (type.isClass()||type.isArray())
611         output.println("   struct "+type.getSafeSymbol()+" * "+td.getSafeSymbol()+";");
612       else
613         output.println("   "+type.getSafeSymbol()+" "+td.getSafeSymbol()+";");
614     }
615
616     for(int i = 0; i < fm.numParameters(); ++i) {
617       TempDescriptor temp = fm.getParameter(i);
618       output.println("   int "+generateTempFlagName(fm, temp, lb)+" = "+super.generateTemp(fm, temp, lb)+
619                      "->flag;");
620     }
621
622     /* Assign labels to FlatNode's if necessary.*/
623
624     Hashtable<FlatNode, Integer> nodetolabel=super.assignLabels(fm);
625
626     /* Check to see if we need to do a GC if this is a
627      * multi-threaded program...*/
628     if(this.state.MULTICOREGC) {
629       output.println("if(gcflag) gc("+localsprefixaddr+");");
630     }
631
632     /*if ((state.THREAD||state.DSM)&&GENERATEPRECISEGC) {
633         if (state.DSM&&lb.isAtomic())
634             output.println("checkcollect2(&"+localsprefix+",trans);");
635         else
636             output.println("checkcollect(&"+localsprefix+");");
637        }*/
638
639     /* Create queues to store objects need to be transferred to other cores and their destination*/
640     //output.println("   struct Queue * totransobjqueue = createQueue();");
641     output.println("   clearQueue(totransobjqueue);");
642     output.println("   struct transObjInfo * tmpObjInfo = NULL;");
643
644     this.m_aliasSets = null;
645     this.m_aliasFNTbl4Para = null;
646     this.m_aliasFNTbl = null;
647     this.m_aliaslocksTbl4FN = null;
648     outputAliasLockCode(fm, lb, output);
649
650     /* generate print information for RAW version */
651     output.println("#ifdef MULTICORE");
652         if(this.state.RAW) {
653                 output.println("{");
654                 output.println("int tmpsum = 0;");
655                 output.println("char * taskname = \"" + task.getSymbol() + "\";");
656                 output.println("int tmplen = " + task.getSymbol().length() + ";");
657                 output.println("int tmpindex = 1;");
658                 output.println("for(;tmpindex < tmplen; tmpindex++) {");
659                 output.println("   tmpsum = tmpsum * 10 + *(taskname + tmpindex) - '0';");
660                 output.println("}");
661         }
662     output.println("#ifdef RAWPATH");
663         if(this.state.RAW) {
664                 output.println("BAMBOO_DEBUGPRINT(0xAAAA);");
665                 output.println("BAMBOO_DEBUGPRINT_REG(tmpsum);"); 
666         } else {
667                 output.println("BAMBOO_START_CRITICAL_SECTION();");
668                 output.println("tprintf(\"Process %x(%d): task %s\\n\", corenum, corenum, \"" + task.getSymbol() + "\");");
669                 output.println("BAMBOO_CLOSE_CRITICAL_SECTION();");
670         }
671         //output.println("BAMBOO_DEBUGPRINT(BAMBOO_GET_EXE_TIME());");
672     output.println("#endif");
673     output.println("#ifdef DEBUG");
674         if(this.state.RAW) {
675                 output.println("BAMBOO_DEBUGPRINT(0xAAAA);");
676                 output.println("BAMBOO_DEBUGPRINT_REG(tmpsum);");
677         } else {
678                 output.println("BAMBOO_START_CRITICAL_SECTION();");
679                 output.println("tprintf(\"Process %x(%d): task %s\\n\", corenum, corenum, \"" + task.getSymbol() + "\");");
680                 output.println("BAMBOO_CLOSE_CRITICAL_SECTION();");
681         }
682     output.println("#endif");
683         if(this.state.RAW) {
684                 output.println("}");
685         }
686         output.println("#endif");
687
688     for(int i = 0; i < fm.numParameters(); ++i) {
689       TempDescriptor temp = fm.getParameter(i);
690       output.println("   ++" + super.generateTemp(fm, temp, lb)+"->version;");
691     }
692
693     /* Do the actual code generation */
694     FlatNode current_node=null;
695     HashSet tovisit=new HashSet();
696     HashSet visited=new HashSet();
697     tovisit.add(fm.getNext(0));
698     while(current_node!=null||!tovisit.isEmpty()) {
699       if (current_node==null) {
700         current_node=(FlatNode)tovisit.iterator().next();
701         tovisit.remove(current_node);
702       }
703       visited.add(current_node);
704       if (nodetolabel.containsKey(current_node))
705         output.println("L"+nodetolabel.get(current_node)+":");
706       /*if (state.INSTRUCTIONFAILURE) {
707           if (state.THREAD||state.DSM) {
708               output.println("if ((++instructioncount)>failurecount) {instructioncount=0;injectinstructionfailure();}");
709           }
710           else
711               output.println("if ((--instructioncount)==0) injectinstructionfailure();");
712          }*/
713       if (current_node.numNext()==0) {
714         output.print("   ");
715         super.generateFlatNode(fm, lb, current_node, output);
716         if (current_node.kind()!=FKind.FlatReturnNode) {
717           //output.println("   flushAll();");
718           output.println("#ifdef CACHEFLUSH");
719           output.println("BAMBOO_START_CRITICAL_SECTION();");
720           output.println("#ifdef DEBUG");
721           output.println("BAMBOO_DEBUGPRINT(0xec00);");
722           output.println("#endif");
723           output.println("BAMBOO_CACHE_FLUSH_ALL();");
724           output.println("#ifdef DEBUG");
725           output.println("BAMBOO_DEBUGPRINT(0xecff);");
726           output.println("#endif");
727           output.println("BAMBOO_CLOSE_CRITICAL_SECTION();");
728           output.println("#endif");
729           outputTransCode(output);
730           output.println("   return;");
731         }
732         current_node=null;
733       } else if(current_node.numNext()==1) {
734         output.print("   ");
735         super.generateFlatNode(fm, lb, current_node, output);
736         FlatNode nextnode=current_node.getNext(0);
737         if (visited.contains(nextnode)) {
738           output.println("goto L"+nodetolabel.get(nextnode)+";");
739           current_node=null;
740         } else
741           current_node=nextnode;
742       } else if (current_node.numNext()==2) {
743         /* Branch */
744         output.print("   ");
745         super.generateFlatCondBranch(fm, lb, (FlatCondBranch)current_node, "L"+nodetolabel.get(current_node.getNext(1)), output);
746         if (!visited.contains(current_node.getNext(1)))
747           tovisit.add(current_node.getNext(1));
748         if (visited.contains(current_node.getNext(0))) {
749           output.println("goto L"+nodetolabel.get(current_node.getNext(0))+";");
750           current_node=null;
751         } else
752           current_node=current_node.getNext(0);
753       } else throw new Error();
754     }
755
756     output.println("}\n\n");
757   }
758
759   /** This method outputs TaskDescriptor information */
760   private void generateTaskDescriptor(PrintWriter output, 
761                                       PrintWriter outtask, 
762                                       FlatMethod fm, 
763                                       TaskDescriptor task, 
764                                       Vector[] qnames) {
765     int num = this.currentSchedule.getCoreNum();
766
767     output.println("/* TaskDescriptor information for task " + task.getSymbol() + " on core " + num + "*/");
768
769     for (int i=0; i<task.numParameters(); i++) {
770       VarDescriptor param_var=task.getParameter(i);
771       TypeDescriptor param_type=task.getParamType(i);
772       FlagExpressionNode param_flag=task.getFlag(param_var);
773       TagExpressionList param_tag=task.getTag(param_var);
774
775       int dnfterms;
776       if (param_flag==null) {
777         output.println("int parameterdnf_"+i+"_"+task.getCoreSafeSymbol(num)+"[]={");
778         output.println("0x0, 0x0 };");
779         dnfterms=1;
780       } else {
781         DNFFlag dflag=param_flag.getDNF();
782         dnfterms=dflag.size();
783
784         Hashtable flags=(Hashtable)flagorder.get(param_type.getClassDesc());
785         output.println("int parameterdnf_"+i+"_"+task.getCoreSafeSymbol(num)+"[]={");
786         for(int j=0; j<dflag.size(); j++) {
787           if (j!=0)
788             output.println(",");
789           Vector term=dflag.get(j);
790           int andmask=0;
791           int checkmask=0;
792           for(int k=0; k<term.size(); k++) {
793             DNFFlagAtom dfa=(DNFFlagAtom)term.get(k);
794             FlagDescriptor fd=dfa.getFlag();
795             boolean negated=dfa.getNegated();
796             int flagid=1<<((Integer)flags.get(fd)).intValue();
797             andmask|=flagid;
798             if (!negated)
799               checkmask|=flagid;
800           }
801           output.print("0x"+Integer.toHexString(andmask)+", 0x"+Integer.toHexString(checkmask));
802         }
803         output.println("};");
804       }
805
806       output.println("int parametertag_"+i+"_"+task.getCoreSafeSymbol(num)+"[]={");
807       //BUG...added next line to fix, test with any task program
808       if (param_tag!=null)
809         for(int j=0; j<param_tag.numTags(); j++) {
810           if (j!=0)
811             output.println(",");
812           /* for each tag we need */
813           /* which slot it is */
814           /* what type it is */
815           TagVarDescriptor tvd=(TagVarDescriptor)task.getParameterTable().get(param_tag.getName(j));
816           TempDescriptor tmp=param_tag.getTemp(j);
817           int slot=fm.getTagInt(tmp);
818           output.println(slot+", "+state.getTagId(tvd.getTag()));
819         }
820       output.println("};");
821
822       // generate object queue for this parameter
823       String qname = this.objqueueprefix+i+"_"+task.getCoreSafeSymbol(num);
824       if(param_type.getClassDesc().getSymbol().equals("StartupObject")) {
825         this.startupcorenum = num;
826       }
827       if(qnames[param_type.getClassDesc().getId()] == null) {
828         qnames[param_type.getClassDesc().getId()] = new Vector();
829       }
830       qnames[param_type.getClassDesc().getId()].addElement(qname);
831       outtask.println("extern struct parameterwrapper " + qname + ";");
832       output.println("struct parameterwrapper " + qname + "={");
833       output.println(".objectset = 0,");      // objectset
834       output.println("/* number of DNF terms */ .numberofterms = "+dnfterms+",");     // numberofterms
835       output.println(".intarray = parameterdnf_"+i+"_"+task.getCoreSafeSymbol(num)+",");    // intarray
836       // numbertags
837       if (param_tag!=null)
838         output.println("/* number of tags */ .numbertags = "+param_tag.numTags()+",");
839       else
840         output.println("/* number of tags */ .numbertags = 0,");
841       output.println(".tagarray = parametertag_"+i+"_"+task.getCoreSafeSymbol(num)+",");    // tagarray
842       output.println(".task = 0,");      // task
843       output.println(".slot = " + i + ",");    // slot
844       // iterators
845       output.println("};");
846
847       output.println("struct parameterdescriptor parameter_"+i+"_"+task.getCoreSafeSymbol(num)+"={");
848       output.println("/* type */"+param_type.getClassDesc().getId()+",");
849       output.println("/* number of DNF terms */"+dnfterms+",");
850       output.println("parameterdnf_"+i+"_"+task.getCoreSafeSymbol(num)+",");    // intarray
851       output.println("&" + qname + ",");     // queue
852       //BUG, added next line to fix and else statement...test
853       //with any task program
854       if (param_tag!=null)
855         output.println("/* number of tags */"+param_tag.numTags()+",");
856       else
857         output.println("/* number of tags */ 0,");
858       output.println("parametertag_"+i+"_"+task.getCoreSafeSymbol(num));     // tagarray
859       output.println("};");
860     }
861
862     /* parameter queues for this task*/
863     output.println("struct parameterwrapper * " + this.paramqarrayprefix + task.getCoreSafeSymbol(num)+"[] = {");
864     for (int i=0; i<task.numParameters(); i++) {
865       if (i!=0)
866         output.println(",");
867       output.print("&" + this.objqueueprefix + i + "_" + task.getCoreSafeSymbol(num));
868     }
869     output.println("};");
870
871     output.println("struct parameterdescriptor * parameterdescriptors_"+task.getCoreSafeSymbol(num)+"[] = {");
872     for (int i=0; i<task.numParameters(); i++) {
873       if (i!=0)
874         output.println(",");
875       output.print("&parameter_"+i+"_"+task.getCoreSafeSymbol(num));
876     }
877     output.println("};");
878
879     output.println("struct taskdescriptor " + this.taskprefix + task.getCoreSafeSymbol(num) + "={");
880     output.println("&"+task.getCoreSafeSymbol(num)+",");
881     output.println("/* number of parameters */" +task.numParameters() + ",");
882     int numtotal=task.numParameters()+fm.numTags();
883     output.println("/* number total parameters */" +numtotal + ",");
884     output.println("parameterdescriptors_"+task.getCoreSafeSymbol(num)+",");
885     output.println("\""+task.getSymbol()+"\"");
886     output.println("};");
887
888     output.println();
889   }
890
891   /** This method generates header information for the task
892    *  referenced by the Descriptor des. */
893
894   private void generateTaskHeader(FlatMethod fm, 
895                                   LocalityBinding lb, 
896                                   Descriptor des, 
897                                   PrintWriter output) {
898     /* Print header */
899     ParamsObject objectparams=(ParamsObject)paramstable.get(lb!=null ? lb : des);
900     TaskDescriptor task=(TaskDescriptor) des;
901
902     int num = this.currentSchedule.getCoreNum();
903     //catch the constructor case
904     output.print("void ");
905     output.print(task.getCoreSafeSymbol(num)+"(");
906
907     boolean printcomma=false;
908     if ((GENERATEPRECISEGC) || (this.state.MULTICOREGC)) {
909       output.print("struct "+task.getCoreSafeSymbol(num)+"_params * "+paramsprefix);
910       printcomma=true;
911     }
912
913     /*if (state.DSM&&lb.isAtomic()) {
914         if (printcomma)
915             output.print(", ");
916         output.print("transrecord_t * trans");
917         printcomma=true;
918        }*/
919
920     if (!GENERATEPRECISEGC && !this.state.MULTICOREGC) {
921       /* Imprecise Task */
922       output.println("void * parameterarray[]) {");
923       /* Unpack variables */
924       for(int i=0; i<objectparams.numPrimitives(); i++) {
925         TempDescriptor temp=objectparams.getPrimitive(i);
926         output.println("struct "+temp.getType().getSafeSymbol()+" * "+temp.getSafeSymbol()+"=parameterarray["+i+"];");
927       }
928       for(int i=0; i<fm.numTags(); i++) {
929         TempDescriptor temp=fm.getTag(i);
930         int offset=i+objectparams.numPrimitives();
931         output.println("struct ___TagDescriptor___ * "+temp.getSafeSymbol()+i+"___=parameterarray["+offset+"];");     // add i to fix bugs of duplicate definition of tags
932       }
933
934       if ((objectparams.numPrimitives()+fm.numTags())>maxtaskparams)
935         maxtaskparams=objectparams.numPrimitives()+fm.numTags();
936     } else output.println(") {");
937   }
938
939   protected void generateFlagOrAnd(FlatFlagActionNode ffan, 
940                                    FlatMethod fm, 
941                                    LocalityBinding lb, 
942                                    TempDescriptor temp,
943                                    PrintWriter output, 
944                                    int ormask, 
945                                    int andmask) {
946     if (ffan.getTaskType()==FlatFlagActionNode.NEWOBJECT) {
947       output.println("flagorandinit("+super.generateTemp(fm, temp, lb)+", 0x"+Integer.toHexString(ormask)+", 0x"+Integer.toHexString(andmask)+");");
948     } else {
949       int num = this.currentSchedule.getCoreNum();
950       ClassDescriptor cd = temp.getType().getClassDesc();
951       Vector<FlagState> initfstates = ffan.getInitFStates(cd);
952       for(int i = 0; i < initfstates.size(); ++i) {
953         FlagState tmpFState = initfstates.elementAt(i);
954         output.println("{");
955         QueueInfo qinfo = outputqueues(tmpFState, num, output, false);
956         output.println("flagorand("+super.generateTemp(fm, temp, lb)+", 0x"+Integer.toHexString(ormask)+
957                        ", 0x"+Integer.toHexString(andmask)+", " + qinfo.qname +
958                        ", " + qinfo.length + ");");
959         output.println("}");
960       }
961       if(ffan.getTaskType()==FlatFlagActionNode.TASKEXIT) {
962           // generate codes for profiling, recording which task exit it is
963           output.println("#ifdef PROFILE");
964           output.println("setTaskExitIndex(" + ffan.getTaskExitIndex() + ");");
965           output.println("#endif");
966       }
967     }
968   }
969
970   protected void generateObjectDistribute(FlatFlagActionNode ffan, 
971                                               FlatMethod fm, 
972                                               LocalityBinding lb, 
973                                               TempDescriptor temp,
974                                           PrintWriter output) {
975     ClassDescriptor cd = temp.getType().getClassDesc();
976     Vector<FlagState> initfstates = null;
977     Vector[] targetFStates = null;
978     if (ffan.getTaskType()==FlatFlagActionNode.NEWOBJECT) {
979       targetFStates = new Vector[1];
980       targetFStates[0] = ffan.getTargetFStates4NewObj(cd);
981     } else {
982       initfstates = ffan.getInitFStates(cd);
983       targetFStates = new Vector[initfstates.size()];
984       for(int i = 0; i < initfstates.size(); ++i) {
985         FlagState fs = initfstates.elementAt(i);
986         targetFStates[i] = ffan.getTargetFStates(fs);
987
988         if(!fs.isSetmask()) {
989           Hashtable flags=(Hashtable)flagorder.get(cd);
990           int andmask=0;
991           int checkmask=0;
992           Iterator it_flags = fs.getFlags();
993           while(it_flags.hasNext()) {
994             FlagDescriptor fd = (FlagDescriptor)it_flags.next();
995             int flagid=1<<((Integer)flags.get(fd)).intValue();
996             andmask|=flagid;
997             checkmask|=flagid;
998           }
999           fs.setAndmask(andmask);
1000           fs.setCheckmask(checkmask);
1001           fs.setSetmask(true);
1002         }
1003       }
1004     }
1005     boolean isolate = true;     // check if this flagstate can associate to some task with multiple params which can
1006                                 // reside on multiple cores
1007     if((this.currentSchedule == null) && (fm.getMethod().getClassDesc().getSymbol().equals("ServerSocket"))) {
1008       // ServerSocket object will always reside on current core
1009       for(int j = 0; j < targetFStates.length; ++j) {
1010         if(initfstates != null) {
1011           FlagState fs = initfstates.elementAt(j);
1012           output.println("if(" + generateTempFlagName(fm, temp, lb) + "&(0x" + Integer.toHexString(fs.getAndmask())
1013                          + ")==(0x" + Integer.toHexString(fs.getCheckmask()) + ")) {");
1014         }
1015         Vector<FlagState> tmpfstates = (Vector<FlagState>)targetFStates[j];
1016         for(int i = 0; i < tmpfstates.size(); ++i) {
1017           FlagState tmpFState = tmpfstates.elementAt(i);
1018           // TODO
1019           // may have bugs here
1020           output.println("/* reside on this core*");
1021           output.println("enqueueObject("+super.generateTemp(fm, temp, lb)+", NULL, 0);");
1022         }
1023         if(initfstates != null) {
1024           output.println("}");
1025         }
1026       }
1027       return;
1028     }
1029
1030     int num = this.currentSchedule.getCoreNum();
1031     Hashtable<FlagState, Queue<Integer>> targetCoreTbl = this.currentSchedule.getTargetCoreTable();
1032     for(int j = 0; j < targetFStates.length; ++j) {
1033       FlagState fs = null;
1034       if(initfstates != null) {
1035         fs = initfstates.elementAt(j);
1036         output.println("if((" + generateTempFlagName(fm, temp, lb) + "&(0x" + Integer.toHexString(fs.getAndmask())
1037                        + "))==(0x" + Integer.toHexString(fs.getCheckmask()) + ")) {");
1038       }
1039       Vector<FlagState> tmpfstates = (Vector<FlagState>)targetFStates[j];
1040       for(int i = 0; i < tmpfstates.size(); ++i) {
1041         FlagState tmpFState = tmpfstates.elementAt(i);
1042
1043         if(this.currentSchedule.getAllyCoreTable() == null) {
1044           isolate = true;
1045         } else {
1046           isolate = (this.currentSchedule.getAllyCoreTable().get(tmpFState) == null) ||
1047                     (this.currentSchedule.getAllyCoreTable().get(tmpFState).size() == 0);
1048         }
1049
1050         Vector<Integer> sendto = new Vector<Integer>();
1051         Queue<Integer> queue = null;
1052         if(targetCoreTbl != null) {
1053           queue = targetCoreTbl.get(tmpFState);
1054         }
1055         if((queue != null) &&
1056            ((queue.size() != 1) ||
1057             ((queue.size() == 1) && (queue.element().intValue() != num)))) {
1058           // this object may be transferred to other cores
1059           String queuename = (String) this.fsate2qnames[num].get(tmpFState);
1060           String queueins = queuename + "ins";
1061
1062           Object[] cores = queue.toArray();
1063           String index = "0";
1064           Integer targetcore = (Integer)cores[0];
1065           if(queue.size() > 1) {
1066             index = queueins + ".index";
1067           }
1068           if(queue.size() > 1) {
1069             output.println("switch(" + queueins + ".index % " + queueins + ".length) {");
1070             for(int k = 0; k < cores.length; ++k) {
1071               output.println("case " + k + ":");
1072               targetcore = (Integer)cores[k];
1073               if(targetcore.intValue() == num) {
1074                 output.println("/* reside on this core*/");
1075                 if(isolate) {
1076                   output.println("{");
1077                   QueueInfo qinfo = outputqueues(tmpFState, num, output, true);
1078                   output.println("enqueueObject("+super.generateTemp(fm, temp, lb)+", " + qinfo.qname +
1079                                  ", " + qinfo.length + ");");
1080                   output.println("}");
1081                 } /*else {
1082                   // TODO
1083                   // really needed?
1084                   output.println("/* possibly needed by multi-parameter tasks on this core*//*");
1085                   output.println("enqueueObject("+super.generateTemp(fm, temp, lb)+", NULL, 0);");
1086                 }*/  // deleted 09/07/06, multi-param tasks are pinned to one core now
1087               } else {
1088                 /*if(!isolate) {
1089                   // TODO
1090                   // Is it possible to decide the actual queues?
1091                   output.println("/* possibly needed by multi-parameter tasks on this core*//*");
1092                   output.println("enqueueObject("+super.generateTemp(fm, temp, lb)+", NULL, 0);");
1093                 }*/ // deleted 09/07/06, multi-param tasks are pinned to one core now
1094                 output.println("/* transfer to core " + targetcore.toString() + "*/");
1095                 output.println("{");
1096                 // enqueue this object and its destinations for later process
1097                 // all the possible queues
1098                 QueueInfo qinfo = null;
1099                 TranObjInfo tmpinfo = new TranObjInfo();
1100                 tmpinfo.name = super.generateTemp(fm, temp, lb);
1101                 tmpinfo.targetcore = targetcore;
1102                 FlagState targetFS = this.currentSchedule.getTargetFState(tmpFState);
1103                 if(targetFS != null) {
1104                   tmpinfo.fs = targetFS;
1105                 } else {
1106                   tmpinfo.fs = tmpFState;
1107                 }
1108                   qinfo = outputtransqueues(tmpinfo.fs, targetcore, output);
1109                   output.println("tmpObjInfo = RUNMALLOC(sizeof(struct transObjInfo));");
1110                   output.println("tmpObjInfo->objptr = (void *)" + tmpinfo.name + ";");
1111                   output.println("tmpObjInfo->targetcore = "+targetcore.toString()+";");
1112                   output.println("tmpObjInfo->queues = " + qinfo.qname + ";");
1113                   output.println("tmpObjInfo->length = " + qinfo.length + ";");
1114                   output.println("addNewItem(totransobjqueue, (void*)tmpObjInfo);");
1115                 output.println("}");
1116               }
1117               output.println("break;");
1118             }
1119             output.println("}");
1120           } else {
1121             /*if(!isolate) {
1122               // TODO
1123               // Is it possible to decide the actual queues?
1124               output.println("/* possibly needed by multi-parameter tasks on this core*//*");
1125               output.println("enqueueObject("+super.generateTemp(fm, temp, lb)+", NULL, 0);");
1126             }*/ // deleted 09/07/06, multi-param tasks are pinned to one core now
1127             output.println("/* transfer to core " + targetcore.toString() + "*/");
1128             output.println("{");
1129             // enqueue this object and its destinations for later process
1130             // all the possible queues
1131             QueueInfo qinfo = null;
1132             TranObjInfo tmpinfo = new TranObjInfo();
1133             tmpinfo.name = super.generateTemp(fm, temp, lb);
1134             tmpinfo.targetcore = targetcore;
1135             FlagState targetFS = this.currentSchedule.getTargetFState(tmpFState);
1136             if(targetFS != null) {
1137               tmpinfo.fs = targetFS;
1138             } else {
1139               tmpinfo.fs = tmpFState;
1140             }
1141               qinfo = outputtransqueues(tmpinfo.fs, targetcore, output);
1142               output.println("tmpObjInfo = RUNMALLOC(sizeof(struct transObjInfo));");
1143               output.println("tmpObjInfo->objptr = (void *)" + tmpinfo.name + ";");
1144               output.println("tmpObjInfo->targetcore = "+targetcore.toString()+";");
1145               output.println("tmpObjInfo->queues = " + qinfo.qname + ";");
1146               output.println("tmpObjInfo->length = " + qinfo.length + ";");
1147               output.println("addNewItem(totransobjqueue, (void*)tmpObjInfo);");
1148             output.println("}");
1149           }
1150           output.println("/* increase index*/");
1151           output.println("++" + queueins + ".index;");
1152         } else {
1153           // this object will reside on current core
1154           output.println("/* reside on this core*/");
1155           if(isolate) {
1156             output.println("{");
1157             QueueInfo qinfo = outputqueues(tmpFState, num, output, true);
1158             output.println("enqueueObject("+super.generateTemp(fm, temp, lb)+", " + qinfo.qname +
1159                            ", " + qinfo.length + ");");
1160             output.println("}");
1161           } /*else {
1162             // TODO
1163             // really needed?
1164             output.println("enqueueObject("+super.generateTemp(fm, temp, lb)+", NULL, 0);");
1165           }*/ // deleted 09/07/06, multi-param tasks are pinned to one core now
1166         }
1167
1168         // codes for multi-params tasks
1169         if(!isolate) {
1170           // flagstate associated with some multi-params tasks
1171           // need to be send to other cores
1172           Vector<Integer> targetcores = this.currentSchedule.getAllyCores(tmpFState);
1173           output.println("/* send the shared object to possible queues on other cores*/");
1174           // TODO, temporary solution, send to mostly the first two 
1175           int upperbound = targetcores.size() > 2? 2: targetcores.size();
1176           for(int k = 0; k < upperbound; ++k) {
1177             // TODO
1178             // add the information of exactly which queue
1179             int targetcore = targetcores.elementAt(k).intValue();
1180             if(!sendto.contains(targetcore)) {
1181             // previously not sended to this target core
1182             // enqueue this object and its destinations for later process
1183             output.println("{");
1184             // all the possible queues
1185             QueueInfo qinfo = null;
1186             TranObjInfo tmpinfo = new TranObjInfo();
1187             tmpinfo.name = super.generateTemp(fm, temp, lb);
1188             tmpinfo.targetcore = targetcore;
1189             FlagState targetFS = this.currentSchedule.getTargetFState(tmpFState);
1190             if(targetFS != null) {
1191               tmpinfo.fs = targetFS;
1192             } else {
1193               tmpinfo.fs = tmpFState;
1194             }
1195               qinfo = outputtransqueues(tmpinfo.fs, targetcore, output);
1196               output.println("tmpObjInfo = RUNMALLOC(sizeof(struct transObjInfo));");
1197               output.println("tmpObjInfo->objptr = (void *)" + tmpinfo.name + ";");
1198               output.println("tmpObjInfo->targetcore = "+targetcore+";");
1199               output.println("tmpObjInfo->queues = " + qinfo.qname + ";");
1200               output.println("tmpObjInfo->length = " + qinfo.length + ";");
1201               output.println("addNewItem(totransobjqueue, (void*)tmpObjInfo);");
1202               output.println("}");
1203               sendto.addElement(targetcore);
1204             }
1205           }
1206         }
1207       }
1208
1209       if(initfstates != null) {
1210         output.println("}");
1211       }
1212     }
1213   }
1214
1215   private QueueInfo outputqueues(FlagState tmpFState, 
1216                                  int num, 
1217                                  PrintWriter output, 
1218                                  boolean isEnqueue) {
1219     // queue array
1220     QueueInfo qinfo = new QueueInfo();
1221     qinfo.qname  = "queues_" + tmpFState.getLabel() + "_" + tmpFState.getiuid();
1222     output.println("struct parameterwrapper * " + qinfo.qname + "[] = {");
1223     Iterator it_edges = tmpFState.getEdgeVector().iterator();
1224     Vector<TaskDescriptor> residetasks = this.currentSchedule.getTasks();
1225     Vector<TaskDescriptor> tasks = new Vector<TaskDescriptor>();
1226     Vector<Integer> indexes = new Vector<Integer>();
1227     boolean comma = false;
1228     qinfo.length = 0;
1229     while(it_edges.hasNext()) {
1230       FEdge fe = (FEdge)it_edges.next();
1231       TaskDescriptor td = fe.getTask();
1232       int paraindex = fe.getIndex();
1233       if((!isEnqueue) || (isEnqueue && residetasks.contains(td))) {
1234         if((!tasks.contains(td)) ||
1235            ((tasks.contains(td)) && (paraindex != indexes.elementAt(tasks.indexOf(td)).intValue()))) {
1236           tasks.addElement(td);
1237           indexes.addElement(paraindex);
1238           if(comma) {
1239             output.println(",");
1240           } else {
1241             comma = true;
1242           }
1243           output.print("&" + this.objqueueprefix + paraindex + "_" + td.getCoreSafeSymbol(num));
1244           ++qinfo.length;
1245         }
1246       }
1247     }
1248     output.println("};");
1249     return qinfo;
1250   }
1251
1252   private QueueInfo outputtransqueues(FlagState tmpFState, 
1253                                       int targetcore, 
1254                                       PrintWriter output) {
1255     // queue array
1256     QueueInfo qinfo = new QueueInfo();
1257     qinfo.qname  = "queues_" + tmpFState.getLabel() + "_" + tmpFState.getiuid();
1258     output.println("int " + qinfo.qname + "_clone[] = {");
1259     Iterator it_edges = tmpFState.getEdgeVector().iterator();
1260     Vector<TaskDescriptor> residetasks = this.scheduling.get(targetcore).getTasks();
1261     Vector<TaskDescriptor> tasks = new Vector<TaskDescriptor>();
1262     Vector<Integer> indexes = new Vector<Integer>();
1263     boolean comma = false;
1264     qinfo.length = 0;
1265     while(it_edges.hasNext()) {
1266       FEdge fe = (FEdge)it_edges.next();
1267       TaskDescriptor td = fe.getTask();
1268       int paraindex = fe.getIndex();
1269       if(residetasks.contains(td)) {
1270         if((!tasks.contains(td)) ||
1271            ((tasks.contains(td)) && (paraindex != indexes.elementAt(tasks.indexOf(td)).intValue()))) {
1272           tasks.addElement(td);
1273           indexes.addElement(paraindex);
1274           if(comma) {
1275             output.println(",");
1276           } else {
1277             comma = true;
1278           }
1279           output.print(residetasks.indexOf(td) + ", ");
1280           output.print(paraindex);
1281           ++qinfo.length;
1282         }
1283       }
1284     }
1285     output.println("};");
1286     output.println("int * " + qinfo.qname + " = RUNMALLOC(sizeof(int) * " + qinfo.length * 2 + ");");
1287     output.println("memcpy(" + qinfo.qname + ", (int *)" + qinfo.qname + "_clone, sizeof(int) * " + qinfo.length * 2 + ");");
1288     return qinfo;
1289   }
1290
1291   private class QueueInfo {
1292     public int length;
1293     public String qname;
1294   }
1295
1296   private String generateTempFlagName(FlatMethod fm, 
1297                                       TempDescriptor td, 
1298                                       LocalityBinding lb) {
1299     MethodDescriptor md=fm.getMethod();
1300     TaskDescriptor task=fm.getTask();
1301     TempObject objecttemps=(TempObject) tempstable.get(lb!=null ? lb : md!=null ? md : task);
1302
1303     if (objecttemps.isLocalPrim(td)||objecttemps.isParamPrim(td)) {
1304       return td.getSafeSymbol() + "_oldflag";
1305     }
1306
1307     if (objecttemps.isLocalPtr(td)) {
1308       return localsprefix+"_"+td.getSafeSymbol() + "_oldflag";
1309     }
1310
1311     if (objecttemps.isParamPtr(td)) {
1312       return paramsprefix+"_"+td.getSafeSymbol() + "_oldflag";
1313     }
1314     throw new Error();
1315   }
1316
1317   protected void outputTransCode(PrintWriter output) {
1318     output.println("while(0 == isEmpty(totransobjqueue)) {");
1319     output.println("   struct transObjInfo * totransobj = (struct transObjInfo *)(getItem(totransobjqueue));");
1320     output.println("   transferObject(totransobj);");
1321     output.println("   RUNFREE(totransobj->queues);");
1322     output.println("   RUNFREE(totransobj);");
1323     output.println("}");
1324     //output.println("freeQueue(totransobjqueue);");
1325   }
1326
1327   protected void outputAliasLockCode(FlatMethod fm, 
1328                                          LocalityBinding lb, 
1329                                          PrintWriter output) {
1330     if(this.m_oa == null) {
1331       return;
1332     }
1333     TaskDescriptor td = fm.getTask();
1334     Object[] allocSites = this.m_oa.getFlaggedAllocationSitesReachableFromTask(td).toArray();
1335     Vector<Vector<Integer>> aliasSets = new Vector<Vector<Integer>>();
1336     Vector<Vector<FlatNew>> aliasFNSets = new Vector<Vector<FlatNew>>();
1337     Hashtable<Integer, Vector<FlatNew>> aliasFNTbl4Para = new Hashtable<Integer, Vector<FlatNew>>();
1338     Hashtable<FlatNew, Vector<FlatNew>> aliasFNTbl = new Hashtable<FlatNew, Vector<FlatNew>>();
1339     Set<HeapRegionNode> common;
1340     for( int i = 0; i < fm.numParameters(); ++i ) {
1341       // for the ith parameter check for aliases to all
1342       // higher numbered parameters
1343       aliasSets.add(null);
1344       for( int j = i + 1; j < fm.numParameters(); ++j ) {
1345         common = this.m_oa.createsPotentialAliases(td, i, j);
1346         if(!common.isEmpty()) {
1347           // ith parameter and jth parameter has alias, create lock to protect them
1348           if(aliasSets.elementAt(i) == null) {
1349             aliasSets.setElementAt(new Vector<Integer>(), i);
1350           }
1351           aliasSets.elementAt(i).add(j);
1352         }
1353       }
1354
1355       // for the ith parameter, check for aliases against
1356       // the set of allocation sites reachable from this
1357       // task context
1358       aliasFNSets.add(null);
1359       for(int j = 0; j < allocSites.length; j++) {
1360         AllocationSite as = (AllocationSite)allocSites[j];
1361         common = this.m_oa.createsPotentialAliases(td, i, as);
1362         if( !common.isEmpty() ) {
1363           // ith parameter and allocationsite as has alias
1364           if(aliasFNSets.elementAt(i) == null) {
1365             aliasFNSets.setElementAt(new Vector<FlatNew>(), i);
1366           }
1367           aliasFNSets.elementAt(i).add(as.getFlatNew());
1368         }
1369       }
1370     }
1371
1372     // for each allocation site check for aliases with
1373     // other allocation sites in the context of execution
1374     // of this task
1375     for( int i = 0; i < allocSites.length; ++i ) {
1376       AllocationSite as1 = (AllocationSite)allocSites[i];
1377       for(int j = i + 1; j < allocSites.length; j++) {
1378         AllocationSite as2 = (AllocationSite)allocSites[j];
1379
1380         common = this.m_oa.createsPotentialAliases(td, as1, as2);
1381         if( !common.isEmpty() ) {
1382           // as1 and as2 has alias
1383           if(!aliasFNTbl.containsKey(as1.getFlatNew())) {
1384             aliasFNTbl.put(as1.getFlatNew(), new Vector<FlatNew>());
1385           }
1386           if(!aliasFNTbl.get(as1.getFlatNew()).contains(as2.getFlatNew())) {
1387             aliasFNTbl.get(as1.getFlatNew()).add(as2.getFlatNew());
1388           }
1389         }
1390       }
1391     }
1392
1393     // if FlatNew N1->N2->N3, we group N1, N2, N3 together
1394     Iterator<FlatNew> it = aliasFNTbl.keySet().iterator();
1395     Vector<FlatNew> visited = new Vector<FlatNew>();
1396     while(it.hasNext()) {
1397       FlatNew tmpfn = it.next();
1398       if(visited.contains(tmpfn)) {
1399         continue;
1400       }
1401       visited.add(tmpfn);
1402       Queue<FlatNew> tovisit = new LinkedList<FlatNew>();
1403       Vector<FlatNew> tmpv = aliasFNTbl.get(tmpfn);
1404       if(tmpv == null) {
1405         continue;
1406       }
1407
1408       for(int j = 0; j < tmpv.size(); j++) {
1409         tovisit.add(tmpv.elementAt(j));
1410       }
1411
1412       while(!tovisit.isEmpty()) {
1413         FlatNew fn = tovisit.poll();
1414         visited.add(fn);
1415         Vector<FlatNew> tmpset = aliasFNTbl.get(fn);
1416         if(tmpset != null) {
1417           // merge tmpset to the alias set of the ith parameter
1418           for(int j = 0; j < tmpset.size(); j++) {
1419             if(!tmpv.contains(tmpset.elementAt(j))) {
1420               tmpv.add(tmpset.elementAt(j));
1421               tovisit.add(tmpset.elementAt(j));
1422             }
1423           }
1424           aliasFNTbl.remove(fn);
1425         }
1426       }
1427       it = aliasFNTbl.keySet().iterator();
1428     }
1429
1430     // check alias between parameters and between parameter-flatnew
1431     for(int i = 0; i < aliasSets.size(); i++) {
1432       Queue<Integer> tovisit = new LinkedList<Integer>();
1433       Vector<Integer> tmpv = aliasSets.elementAt(i);
1434       if(tmpv == null) {
1435         continue;
1436       }
1437
1438       for(int j = 0; j < tmpv.size(); j++) {
1439         tovisit.add(tmpv.elementAt(j));
1440       }
1441
1442       while(!tovisit.isEmpty()) {
1443         int index = tovisit.poll().intValue();
1444         Vector<Integer> tmpset = aliasSets.elementAt(index);
1445         if(tmpset != null) {
1446           // merge tmpset to the alias set of the ith parameter
1447           for(int j = 0; j < tmpset.size(); j++) {
1448             if(!tmpv.contains(tmpset.elementAt(j))) {
1449               tmpv.add(tmpset.elementAt(j));
1450               tovisit.add(tmpset.elementAt(j));
1451             }
1452           }
1453           aliasSets.setElementAt(null, index);
1454         }
1455
1456         Vector<FlatNew> tmpFNSet = aliasFNSets.elementAt(index);
1457         if(tmpFNSet != null) {
1458           // merge tmpFNSet to the aliasFNSet of the ith parameter
1459           if(aliasFNSets.elementAt(i) == null) {
1460             aliasFNSets.setElementAt(tmpFNSet, i);
1461           } else {
1462             Vector<FlatNew> tmpFNv = aliasFNSets.elementAt(i);
1463             for(int j = 0; j < tmpFNSet.size(); j++) {
1464               if(!tmpFNv.contains(tmpFNSet.elementAt(j))) {
1465                 tmpFNv.add(tmpFNSet.elementAt(j));
1466               }
1467             }
1468           }
1469           aliasFNSets.setElementAt(null, index);
1470         }
1471       }
1472     }
1473
1474     int numlock = 0;
1475     int numparalock = 0;
1476     Vector<Vector<Integer>> tmpaliasSets = new Vector<Vector<Integer>>();
1477     for(int i = 0; i < aliasSets.size(); i++) {
1478       Vector<Integer> tmpv = aliasSets.elementAt(i);
1479       if(tmpv != null) {
1480         tmpv.add(0, i);
1481         tmpaliasSets.add(tmpv);
1482         numlock++;
1483       }
1484
1485       Vector<FlatNew> tmpFNv = aliasFNSets.elementAt(i);
1486       if(tmpFNv != null) {
1487         aliasFNTbl4Para.put(i, tmpFNv);
1488         if(tmpv == null) {
1489           numlock++;
1490         }
1491       }
1492     }
1493     numparalock = numlock;
1494     aliasSets.clear();
1495     aliasSets = null;
1496     this.m_aliasSets = tmpaliasSets;
1497     tmpaliasSets.clear();
1498     tmpaliasSets = null;
1499     aliasFNSets.clear();
1500     aliasFNSets = null;
1501     this.m_aliasFNTbl4Para = aliasFNTbl4Para;
1502     this.m_aliasFNTbl = aliasFNTbl;
1503     numlock += this.m_aliasFNTbl.size();
1504
1505     // create locks
1506     if(numlock > 0) {
1507       output.println("int aliaslocks[" + numlock + "];");
1508       output.println("int tmpi = 0;");      
1509       // associate locks with parameters
1510       int lockindex = 0;
1511       for(int i = 0; i < this.m_aliasSets.size(); i++) {
1512         Vector<Integer> toadd = this.m_aliasSets.elementAt(i);
1513         
1514         output.print("int tmplen_" + lockindex + " = 0;");
1515         output.println("void * tmpptrs_" + lockindex + "[] = {");
1516         for(int j = 0; j < toadd.size(); j++) {
1517             int para = toadd.elementAt(j).intValue();
1518             output.print(super.generateTemp(fm, fm.getParameter(para), lb));
1519             if(j < toadd.size() - 1) {
1520                 output.print(", ");
1521             } else {
1522                 output.println("};");
1523             }
1524         }
1525         output.println("aliaslocks[tmpi++] = getAliasLock(tmpptrs_" + lockindex + ", tmplen_" + lockindex + ", lockRedirectTbl);");
1526         
1527         for(int j = 0; j < toadd.size(); j++) {
1528           int para = toadd.elementAt(j).intValue();
1529           output.println("addAliasLock("  + super.generateTemp(fm, fm.getParameter(para), lb) + ", aliaslocks[" + i + "]);");
1530         }
1531         // check if this lock is also associated with any FlatNew nodes
1532         if(this.m_aliasFNTbl4Para.containsKey(toadd.elementAt(0))) {
1533           if(this.m_aliaslocksTbl4FN == null) {
1534             this.m_aliaslocksTbl4FN = new Hashtable<FlatNew, Vector<Integer>>();
1535           }
1536           Vector<FlatNew> tmpv = this.m_aliasFNTbl4Para.get(toadd.elementAt(0));
1537           for(int j = 0; j < tmpv.size(); j++) {
1538             FlatNew fn = tmpv.elementAt(j);
1539             if(!this.m_aliaslocksTbl4FN.containsKey(fn)) {
1540               this.m_aliaslocksTbl4FN.put(fn, new Vector<Integer>());
1541             }
1542             this.m_aliaslocksTbl4FN.get(fn).add(i);
1543           }
1544           this.m_aliasFNTbl4Para.remove(toadd.elementAt(0));
1545         }
1546         lockindex++;
1547       }
1548       
1549       Object[] key = this.m_aliasFNTbl4Para.keySet().toArray();
1550       for(int i = 0; i < key.length; i++) {
1551         int para = ((Integer)key[i]).intValue();
1552
1553         output.println("void * tmpptrs_" + lockindex + "[] = {" + super.generateTemp(fm, fm.getParameter(para), lb) + "};");
1554         output.println("aliaslocks[tmpi++] = getAliasLock(tmpptrs_" + lockindex + ", 1, lockRedirectTbl);");
1555         
1556         output.println("addAliasLock(" + super.generateTemp(fm, fm.getParameter(para), lb) + ", aliaslocks[" + lockindex + "]);");
1557         Vector<FlatNew> tmpv = this.m_aliasFNTbl4Para.get(para);
1558         for(int j = 0; j < tmpv.size(); j++) {
1559           FlatNew fn = tmpv.elementAt(j);
1560           if(this.m_aliaslocksTbl4FN == null) {
1561             this.m_aliaslocksTbl4FN = new Hashtable<FlatNew, Vector<Integer>>();
1562           }
1563           if(!this.m_aliaslocksTbl4FN.containsKey(fn)) {
1564             this.m_aliaslocksTbl4FN.put(fn, new Vector<Integer>());
1565           }
1566           this.m_aliaslocksTbl4FN.get(fn).add(lockindex);
1567         }
1568         lockindex++;
1569       }
1570       
1571       // check m_aliasFNTbl for locks associated with FlatNew nodes
1572       Object[] FNkey = this.m_aliasFNTbl.keySet().toArray();
1573       for(int i = 0; i < FNkey.length; i++) {
1574         FlatNew fn = (FlatNew)FNkey[i];
1575         Vector<FlatNew> tmpv = this.m_aliasFNTbl.get(fn);
1576         
1577         output.println("aliaslocks[tmpi++] = (int)(RUNMALLOC(sizeof(int)));");
1578         
1579         if(this.m_aliaslocksTbl4FN == null) {
1580           this.m_aliaslocksTbl4FN = new Hashtable<FlatNew, Vector<Integer>>();
1581         }
1582         if(!this.m_aliaslocksTbl4FN.containsKey(fn)) {
1583           this.m_aliaslocksTbl4FN.put(fn, new Vector<Integer>());
1584         }
1585         this.m_aliaslocksTbl4FN.get(fn).add(lockindex);
1586         for(int j = 0; j < tmpv.size(); j++) {
1587           FlatNew tfn = tmpv.elementAt(j);
1588           if(!this.m_aliaslocksTbl4FN.containsKey(tfn)) {
1589             this.m_aliaslocksTbl4FN.put(tfn, new Vector<Integer>());
1590           }
1591           this.m_aliaslocksTbl4FN.get(tfn).add(lockindex);
1592         }
1593         lockindex++;
1594       }
1595     }
1596   }
1597
1598   protected void generateFlatReturnNode(FlatMethod fm, 
1599                                         LocalityBinding lb, 
1600                                         FlatReturnNode frn, 
1601                                         PrintWriter output) {
1602     if (frn.getReturnTemp()!=null) {
1603       if (frn.getReturnTemp().getType().isPtr())
1604         output.println("return (struct "+fm.getMethod().getReturnType().getSafeSymbol()+"*)"+generateTemp(fm, frn.getReturnTemp(), lb)+";");
1605       else
1606         output.println("return "+generateTemp(fm, frn.getReturnTemp(), lb)+";");
1607     } else {
1608       if(fm.getTask() != null) {
1609         output.println("#ifdef CACHEFLUSH");
1610         output.println("BAMBOO_START_CRITICAL_SECTION();");
1611         output.println("#ifdef DEBUG");
1612         output.println("BAMBOO_DEBUGPRINT(0xec00);");
1613         output.println("#endif");
1614         output.println("BAMBOO_CACHE_FLUSH_ALL();");
1615         output.println("#ifdef DEBUG");
1616         output.println("BAMBOO_DEBUGPRINT(0xecff);");
1617         output.println("#endif");
1618         output.println("BAMBOO_CLOSE_CRITICAL_SECTION();");
1619         output.println("#endif");
1620         outputTransCode(output);
1621       }
1622       output.println("return;");
1623     }
1624   }
1625
1626   protected void generateFlatNew(FlatMethod fm, 
1627                                  LocalityBinding lb, 
1628                                  FlatNew fn,
1629                                  PrintWriter output) {
1630     if (state.DSM && locality.getAtomic(lb).get(fn).intValue() > 0
1631         && !fn.isGlobal()) {
1632       // Stash pointer in case of GC
1633       String revertptr = super.generateTemp(fm, reverttable.get(lb), lb);
1634       output.println(revertptr + "=trans->revertlist;");
1635     }
1636     if (fn.getType().isArray()) {
1637       int arrayid = state.getArrayNumber(fn.getType())
1638                     + state.numClasses();
1639       if (fn.isGlobal()) {
1640         output.println(super.generateTemp(fm, fn.getDst(), lb)
1641                        + "=allocate_newarrayglobal(trans, " + arrayid + ", "
1642                        + super.generateTemp(fm, fn.getSize(), lb) + ");");
1643       } else if ((GENERATEPRECISEGC) || (this.state.MULTICOREGC)) {
1644         output.println(super.generateTemp(fm, fn.getDst(), lb)
1645                        + "=allocate_newarray(&" + localsprefix + ", "
1646                        + arrayid + ", " + super.generateTemp(fm, fn.getSize(), lb)
1647                        + ");");
1648       } else {
1649         output.println(super.generateTemp(fm, fn.getDst(), lb)
1650                        + "=allocate_newarray(" + arrayid + ", "
1651                        + super.generateTemp(fm, fn.getSize(), lb) + ");");
1652       }
1653     } else {
1654       if (fn.isGlobal()) {
1655         output.println(super.generateTemp(fm, fn.getDst(), lb)
1656                        + "=allocate_newglobal(trans, "
1657                        + fn.getType().getClassDesc().getId() + ");");
1658       } else if ((GENERATEPRECISEGC) || (this.state.MULTICOREGC)) {
1659         output.println(super.generateTemp(fm, fn.getDst(), lb)
1660                        + "=allocate_new(&" + localsprefix + ", "
1661                        + fn.getType().getClassDesc().getId() + ");");
1662       } else {
1663         output.println(super.generateTemp(fm, fn.getDst(), lb)
1664                        + "=allocate_new("
1665                        + fn.getType().getClassDesc().getId() + ");");
1666       }
1667     }
1668     if (state.DSM && locality.getAtomic(lb).get(fn).intValue() > 0
1669         && !fn.isGlobal()) {
1670       String revertptr = super.generateTemp(fm, reverttable.get(lb), lb);
1671       output.println("trans->revertlist=" + revertptr + ";");
1672     }
1673     // create alias lock if necessary
1674     if((this.m_aliaslocksTbl4FN != null) && (this.m_aliaslocksTbl4FN.containsKey(fn))) {
1675       Vector<Integer> tmpv = this.m_aliaslocksTbl4FN.get(fn);
1676       for(int i = 0; i < tmpv.size(); i++) {
1677         output.println("addAliasLock(" + super.generateTemp(fm, fn.getDst(), lb) + ", aliaslocks[" + tmpv.elementAt(i).intValue() + "]);");
1678       }
1679     }
1680     // generate codes for profiling, recording how many new objects are created
1681     if(!fn.getType().isArray() && 
1682             (fn.getType().getClassDesc() != null) 
1683             && (fn.getType().getClassDesc().hasFlags())) {
1684         output.println("#ifdef PROFILE");
1685         output.println("addNewObjInfo(\"" + fn.getType().getClassDesc().getSymbol() + "\");");
1686         output.println("#endif");
1687     }
1688   }
1689
1690   class TranObjInfo {
1691     public String name;
1692     public int targetcore;
1693     public FlagState fs;
1694   }
1695
1696   private boolean contains(Vector<TranObjInfo> sendto, 
1697                            TranObjInfo t) {
1698     if(sendto.size() == 0) {
1699       return false;
1700     }
1701     for(int i = 0; i < sendto.size(); i++) {
1702       TranObjInfo tmp = sendto.elementAt(i);
1703       if(!tmp.name.equals(t.name)) {
1704         return false;
1705       }
1706       if(tmp.targetcore != t.targetcore) {
1707         return false;
1708       }
1709       if(tmp.fs != t.fs) {
1710         return false;
1711       }
1712     }
1713     return true;
1714   }
1715 }