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