2 import IR.Tree.Modifiers;
3 import IR.Tree.FlagExpressionNode;
4 import IR.Tree.DNFFlag;
5 import IR.Tree.DNFFlagAtom;
6 import IR.Tree.TagExpressionList;
7 import IR.Tree.OffsetNode;
14 import Analysis.TaskStateAnalysis.FlagState;
15 import Analysis.TaskStateAnalysis.FlagComparator;
16 import Analysis.TaskStateAnalysis.OptionalTaskDescriptor;
17 import Analysis.TaskStateAnalysis.Predicate;
18 import Analysis.TaskStateAnalysis.SafetyAnalysis;
19 import Analysis.TaskStateAnalysis.TaskIndex;
20 import Analysis.CallGraph.CallGraph;
21 import Analysis.Loops.GlobalFieldType;
22 import Util.CodePrinter;
24 public class BuildCode {
27 Hashtable paramstable;
32 String localsprefix="___locals___";
33 String localsprefixaddr="&"+localsprefix;
34 String localsprefixderef=localsprefix+".";
35 String fcrevert="___fcrevert___";
36 String paramsprefix="___params___";
37 String nextobjstr="___nextobject___";
38 String localcopystr="___localcopy___";
39 public static boolean GENERATEPRECISEGC=false;
40 public static String PREFIX="";
41 public static String arraytype="ArrayObject";
42 public static int flagcount = 0;
45 protected int maxtaskparams=0;
46 protected int maxcount=0;
47 ClassDescriptor[] cdarray;
48 TypeDescriptor[] arraytable;
51 Hashtable<String, ClassDescriptor> printedfieldstbl;
52 int globaldefscount=0;
53 boolean mgcstaticinit = false;
55 public BuildCode(State st, Hashtable temptovar, TypeUtil typeutil) {
56 this(st, temptovar, typeutil, null);
59 public BuildCode(State st, Hashtable temptovar, TypeUtil typeutil, SafetyAnalysis sa) {
62 callgraph=new CallGraph(state);
63 this.temptovar=temptovar;
64 paramstable=new Hashtable();
65 tempstable=new Hashtable();
66 fieldorder=new Hashtable();
67 flagorder=new Hashtable();
68 this.typeutil=typeutil;
69 virtualcalls=new Virtual(state, null);
70 printedfieldstbl = new Hashtable<String, ClassDescriptor>();
73 /** The buildCode method outputs C code for all the methods. The Flat
74 * versions of the methods must already be generated and stored in
75 * the State object. */
78 public void buildCode() {
79 /* Create output streams to write to */
80 PrintWriter outclassdefs=null;
81 PrintWriter outstructs=null;
82 PrintWriter outrepairstructs=null;
83 PrintWriter outmethodheader=null;
84 PrintWriter outmethod=null;
85 PrintWriter outvirtual=null;
86 PrintWriter outtask=null;
87 PrintWriter outtaskdefs=null;
88 PrintWriter outoptionalarrays=null;
89 PrintWriter optionalheaders=null;
90 PrintWriter outglobaldefs=null;
91 PrintWriter outglobaldefsprim=null;
94 buildCodeSetup(); //EXTENSION POINT
95 outstructs=new CodePrinter(new FileOutputStream(PREFIX+"structdefs.h"), true);
96 outmethodheader=new CodePrinter(new FileOutputStream(PREFIX+"methodheaders.h"), true);
97 outclassdefs=new CodePrinter(new FileOutputStream(PREFIX+"classdefs.h"), true);
98 outglobaldefs=new CodePrinter(new FileOutputStream(PREFIX+"globaldefs.h"), true);
99 outglobaldefsprim=new CodePrinter(new FileOutputStream(PREFIX+"globaldefsprim.h"), true);
100 outmethod=new CodePrinter(new FileOutputStream(PREFIX+"methods.c"), true);
101 outvirtual=new CodePrinter(new FileOutputStream(PREFIX+"virtualtable.h"), true);
103 outtask=new CodePrinter(new FileOutputStream(PREFIX+"task.h"), true);
104 outtaskdefs=new CodePrinter(new FileOutputStream(PREFIX+"taskdefs.c"), true);
105 if (state.OPTIONAL) {
106 outoptionalarrays=new CodePrinter(new FileOutputStream(PREFIX+"optionalarrays.c"), true);
107 optionalheaders=new CodePrinter(new FileOutputStream(PREFIX+"optionalstruct.h"), true);
110 if (state.structfile!=null) {
111 outrepairstructs=new CodePrinter(new FileOutputStream(PREFIX+state.structfile+".struct"), true);
113 } catch (Exception e) {
118 /* Fix field safe symbols due to shadowing */
119 FieldShadow.handleFieldShadow(state);
121 /* Build the virtual dispatch tables */
122 buildVirtualTables(outvirtual);
124 /* Tag the methods that are invoked by static blocks */
125 tagMethodInvokedByStaticBlock();
127 /* Output includes */
128 outmethodheader.println("#ifndef METHODHEADERS_H");
129 outmethodheader.println("#define METHODHEADERS_H");
130 outmethodheader.println("#include \"structdefs.h\"");
132 if (state.EVENTMONITOR) {
133 outmethodheader.println("#include \"monitor.h\"");
136 additionalIncludesMethodsHeader(outmethodheader);
138 /* Output Structures */
139 outputStructs(outstructs);
141 // Output the C class declarations
142 // These could mutually reference each other
144 outglobaldefs.println("#ifndef __GLOBALDEF_H_");
145 outglobaldefs.println("#define __GLOBALDEF_H_");
146 outglobaldefs.println("");
147 outglobaldefs.println("struct global_defs_t {");
148 outglobaldefs.println(" int size;");
149 outglobaldefs.println(" void * next;");
150 outglobaldefsprim.println("#ifndef __GLOBALDEFPRIM_H_");
151 outglobaldefsprim.println("#define __GLOBALDEFPRIM_H_");
152 outglobaldefsprim.println("");
153 outglobaldefsprim.println("struct global_defsprim_t {");
155 outclassdefs.println("#ifndef __CLASSDEF_H_");
156 outclassdefs.println("#define __CLASSDEF_H_");
157 outputClassDeclarations(outclassdefs, outglobaldefs, outglobaldefsprim);
159 // Output function prototypes and structures for parameters
160 Iterator it=state.getClassSymbolTable().getDescriptorsIterator();
161 while(it.hasNext()) {
162 ClassDescriptor cn=(ClassDescriptor)it.next();
163 generateCallStructs(cn, outclassdefs, outstructs, outmethodheader, outglobaldefs, outglobaldefsprim);
165 outclassdefs.println("#include \"globaldefs.h\"");
166 outclassdefs.println("#include \"globaldefsprim.h\"");
167 outclassdefs.println("#endif");
168 outclassdefs.close();
170 outglobaldefs.println("};");
171 outglobaldefs.println("");
172 outglobaldefs.println("extern struct global_defs_t * global_defs_p;");
173 outglobaldefs.println("#endif");
174 outglobaldefs.flush();
175 outglobaldefs.close();
177 outglobaldefsprim.println("};");
178 outglobaldefsprim.println("");
179 outglobaldefsprim.println("extern struct global_defsprim_t * global_defsprim_p;");
180 outglobaldefsprim.println("#endif");
181 outglobaldefsprim.flush();
182 outglobaldefsprim.close();
185 /* Map flags to integers */
186 /* The runtime keeps track of flags using these integers */
187 it=state.getClassSymbolTable().getDescriptorsIterator();
188 while(it.hasNext()) {
189 ClassDescriptor cn=(ClassDescriptor)it.next();
193 generateTaskStructs(outstructs, outmethodheader);
195 /* Outputs generic task structures if this is a task
197 outputTaskTypes(outtask);
201 // an opportunity for subclasses to do extra
203 preCodeGenInitialization();
206 /* Build the actual methods */
207 outputMethods(outmethod);
210 // opportunity for subclasses to gen extra code
211 additionalCodeGen(outmethodheader,
217 /* Output code for tasks */
218 outputTaskCode(outtaskdefs, outmethod);
220 /* Record maximum number of task parameters */
221 outstructs.println("#define MAXTASKPARAMS "+maxtaskparams);
222 } else if (state.main!=null) {
223 /* Generate main method */
224 outputMainMethod(outmethod);
227 /* Generate information for task with optional parameters */
228 if (state.TASK&&state.OPTIONAL) {
229 generateOptionalArrays(outoptionalarrays, optionalheaders, state.getAnalysisResult(), state.getOptionalTaskDescriptors());
230 outoptionalarrays.close();
233 /* Output structure definitions for repair tool */
234 if (state.structfile!=null) {
235 buildRepairStructs(outrepairstructs);
236 outrepairstructs.close();
240 outmethodheader.println("#endif");
241 outmethodheader.close();
243 outstructs.println("#endif");
248 postCodeGenCleanUp();
253 /* This method goes though the call graph and tag those methods that are
254 * invoked inside static blocks
256 protected void tagMethodInvokedByStaticBlock() {
257 Iterator it_sclasses = this.state.getSClassSymbolTable().getDescriptorsIterator();
258 MethodDescriptor current_md=null;
259 HashSet tovisit=new HashSet();
260 HashSet visited=new HashSet();
262 while(it_sclasses.hasNext()) {
263 ClassDescriptor cd = (ClassDescriptor)it_sclasses.next();
264 MethodDescriptor md = (MethodDescriptor)cd.getMethodTable().get("staticblocks");
270 while(!tovisit.isEmpty()) {
271 current_md=(MethodDescriptor)tovisit.iterator().next();
272 tovisit.remove(current_md);
273 visited.add(current_md);
274 Iterator it_callee = this.callgraph.getCalleeSet(current_md).iterator();
275 while(it_callee.hasNext()) {
276 Descriptor d = (Descriptor)it_callee.next();
277 if(d instanceof MethodDescriptor) {
278 if(!visited.contains(d)) {
279 ((MethodDescriptor)d).setIsInvokedByStatic(true);
287 /* This code generates code for each static block and static field
289 protected void outputStaticBlocks(PrintWriter outmethod) {
290 // execute all the static blocks and all the static field initializations
291 // execute all the static blocks and all the static field initializations
292 SymbolTable sctbl = this.state.getSClassSymbolTable();
293 Iterator it_sclasses = sctbl.getDescriptorsIterator();
294 if(it_sclasses.hasNext()) {
295 while(it_sclasses.hasNext()) {
296 ClassDescriptor t_cd = (ClassDescriptor)it_sclasses.next();
297 MethodDescriptor t_md = (MethodDescriptor)t_cd.getMethodTable().get("staticblocks");
299 outmethod.println(" {");
300 if ((GENERATEPRECISEGC) || (this.state.MULTICOREGC)) {
301 outmethod.print(" struct "+t_cd.getSafeSymbol()+t_md.getSafeSymbol()+"_"+t_md.getSafeMethodDescriptor()+"_params __parameterlist__={");
302 outmethod.println("0, NULL};");
303 outmethod.println(" "+t_cd.getSafeSymbol()+t_md.getSafeSymbol()+"_"+t_md.getSafeMethodDescriptor()+"(& __parameterlist__);");
305 outmethod.println(" "+t_cd.getSafeSymbol()+t_md.getSafeSymbol()+"_"+t_md.getSafeMethodDescriptor()+"();");
307 outmethod.println(" }");
313 /* This code generates code to create a Class object for each class for
316 protected void outputClassObjects(PrintWriter outmethod) {
317 // for each class, initialize its Class object
318 SymbolTable ctbl = this.state.getClassSymbolTable();
319 for(Iterator it_classes = ctbl.getDescriptorsIterator();it_classes.hasNext();) {
320 ClassDescriptor t_cd = (ClassDescriptor)it_classes.next();
321 outmethod.println(" {");
322 if ((GENERATEPRECISEGC) || (this.state.MULTICOREGC)) {
323 outmethod.println(" struct garbagelist dummy={0,NULL};");
324 outmethod.println(" global_defs_p->"+t_cd.getSafeSymbol()+"classobj = allocate_new(&dummy, " + typeutil.getClass(TypeUtil.ObjectClass).getId() + ");");
326 outmethod.println(" global_defs_p->"+t_cd.getSafeSymbol()+"classobj = allocate_new("+typeutil.getClass(TypeUtil.ObjectClass).getId() + ");");
327 outmethod.println(" global_defs_p->"+t_cd.getSafeSymbol()+"classobj->type = " + t_cd.getId() + ";");
328 outmethod.println(" }");
332 /* This code just generates the main C method for java programs.
333 * The main C method packs up the arguments into a string array
334 * and passes it to the java main method. */
336 protected void outputMainMethod(PrintWriter outmethod) {
337 outmethod.println("int main(int argc, const char *argv[]) {");
338 outmethod.println(" int i;");
339 outmethod.println(" global_defs_p=calloc(1, sizeof(struct global_defs_t));");
340 outmethod.println(" global_defsprim_p=calloc(1, sizeof(struct global_defsprim_t));");
341 if (GENERATEPRECISEGC) {
342 outmethod.println(" global_defs_p->size="+globaldefscount+";");
343 outmethod.println(" for(i=0;i<"+globaldefscount+";i++) {");
344 outmethod.println(" ((struct garbagelist *)global_defs_p)->array[i]=NULL;");
345 outmethod.println(" }");
347 outputStaticBlocks(outmethod);
348 outputClassObjects(outmethod);
351 additionalCodeAtTopOfMain(outmethod);
354 outmethod.println("initializethreads();");
357 if ((GENERATEPRECISEGC) || (this.state.MULTICOREGC)) {
358 outmethod.println(" struct ArrayObject * stringarray=allocate_newarray(NULL, STRINGARRAYTYPE, argc-1);");
360 outmethod.println(" struct ArrayObject * stringarray=allocate_newarray(STRINGARRAYTYPE, argc-1);");
362 outmethod.println(" for(i=1;i<argc;i++) {");
363 outmethod.println(" int length=strlen(argv[i]);");
365 if ((GENERATEPRECISEGC) || (this.state.MULTICOREGC)) {
366 outmethod.println(" struct ___String___ *newstring=NewString(NULL, argv[i], length);");
368 outmethod.println(" struct ___String___ *newstring=NewString(argv[i], length);");
370 outmethod.println(" ((void **)(((char *)& stringarray->___length___)+sizeof(int)))[i-1]=newstring;");
371 outmethod.println(" }");
373 MethodDescriptor md=typeutil.getMain();
374 ClassDescriptor cd=typeutil.getMainClass();
376 outmethod.println(" {");
377 if ((GENERATEPRECISEGC) || (this.state.MULTICOREGC)) {
378 outmethod.print(" struct "+cd.getSafeSymbol()+md.getSafeSymbol()+"_"+md.getSafeMethodDescriptor()+"_params __parameterlist__={");
379 outmethod.println("1, NULL,"+"stringarray};");
380 outmethod.println(" "+cd.getSafeSymbol()+md.getSafeSymbol()+"_"+md.getSafeMethodDescriptor()+"(& __parameterlist__);");
382 outmethod.println(" "+cd.getSafeSymbol()+md.getSafeSymbol()+"_"+md.getSafeMethodDescriptor()+"(stringarray);");
384 outmethod.println(" }");
387 outmethod.println("pthread_mutex_lock(&gclistlock);");
388 outmethod.println("threadcount--;");
389 outmethod.println("pthread_cond_signal(&gccond);");
390 outmethod.println("pthread_mutex_unlock(&gclistlock);");
393 if (state.EVENTMONITOR) {
394 outmethod.println("dumpdata();");
398 outmethod.println("pthread_exit(NULL);");
401 additionalCodeAtBottomOfMain(outmethod);
403 outmethod.println("}");
406 /* This method outputs code for each task. */
408 protected void outputTaskCode(PrintWriter outtaskdefs, PrintWriter outmethod) {
409 /* Compile task based program */
410 outtaskdefs.println("#include \"task.h\"");
411 outtaskdefs.println("#include \"methodheaders.h\"");
412 Iterator taskit=state.getTaskSymbolTable().getDescriptorsIterator();
413 while(taskit.hasNext()) {
414 TaskDescriptor td=(TaskDescriptor)taskit.next();
415 FlatMethod fm=state.getMethodFlat(td);
416 generateFlatMethod(fm, outmethod);
417 generateTaskDescriptor(outtaskdefs, fm, td);
420 //Output task descriptors
421 taskit=state.getTaskSymbolTable().getDescriptorsIterator();
422 outtaskdefs.println("struct taskdescriptor * taskarray[]= {");
424 while(taskit.hasNext()) {
425 TaskDescriptor td=(TaskDescriptor)taskit.next();
429 outtaskdefs.println(",");
430 outtaskdefs.print("&task_"+td.getSafeSymbol());
432 outtaskdefs.println("};");
434 outtaskdefs.println("int numtasks="+state.getTaskSymbolTable().getValueSet().size()+";");
438 /* This method outputs most of the methods.c file. This includes
439 * some standard includes and then an array with the sizes of
440 * objets and array that stores supertype and then the code for
441 * the Java methods.. */
442 protected void outputMethods(PrintWriter outmethod) {
443 outmethod.println("#include \"methodheaders.h\"");
444 outmethod.println("#include \"virtualtable.h\"");
445 outmethod.println("#include \"runtime.h\"");
447 // always include: compiler directives will leave out
448 // instrumentation when option is not set
449 outmethod.println("#include \"coreprof/coreprof.h\"");
451 if (state.FASTCHECK) {
452 outmethod.println("#include \"localobjects.h\"");
454 if(state.MULTICORE) {
456 outmethod.println("#include \"task.h\"");
458 outmethod.println("#include \"multicoreruntime.h\"");
459 outmethod.println("#include \"runtime_arch.h\"");
461 if (state.THREAD||state.DSM||state.SINGLETM) {
462 outmethod.println("#include <thread.h>");
465 outmethod.println("#include \"thread.h\"");
467 if (state.main!=null) {
468 outmethod.println("#include <string.h>");
470 if (state.CONSCHECK) {
471 outmethod.println("#include \"checkers.h\"");
475 additionalIncludesMethodsImplementation(outmethod);
477 outmethod.println("struct global_defs_t * global_defs_p;");
478 outmethod.println("struct global_defsprim_t * global_defsprim_p;");
479 //Store the sizes of classes & array elements
480 generateSizeArray(outmethod);
482 //Store table of supertypes
483 generateSuperTypeTable(outmethod);
485 //Store the layout of classes
486 generateLayoutStructs(outmethod);
489 additionalCodeAtTopMethodsImplementation(outmethod);
491 generateMethods(outmethod);
494 protected void generateMethods(PrintWriter outmethod) {
495 /* Generate code for methods */
496 Iterator classit=state.getClassSymbolTable().getDescriptorsIterator();
497 while(classit.hasNext()) {
498 ClassDescriptor cn=(ClassDescriptor)classit.next();
499 Iterator methodit=cn.getMethods();
500 while(methodit.hasNext()) {
501 /* Classify parameters */
502 MethodDescriptor md=(MethodDescriptor)methodit.next();
503 FlatMethod fm=state.getMethodFlat(md);
504 if (!md.getModifiers().isNative()) {
505 generateFlatMethod(fm, outmethod);
511 protected void outputStructs(PrintWriter outstructs) {
512 outstructs.println("#ifndef STRUCTDEFS_H");
513 outstructs.println("#define STRUCTDEFS_H");
514 outstructs.println("#include \"classdefs.h\"");
515 outstructs.println("#ifndef INTPTR");
516 outstructs.println("#ifdef BIT64");
517 outstructs.println("#define INTPTR long");
518 outstructs.println("#else");
519 outstructs.println("#define INTPTR int");
520 outstructs.println("#endif");
521 outstructs.println("#endif");
524 additionalIncludesStructsHeader(outstructs);
527 /* Output #defines that the runtime uses to determine type
528 * numbers for various objects it needs */
529 outstructs.println("#define MAXCOUNT "+maxcount);
531 outstructs.println("#define STRINGARRAYTYPE "+
532 (state.getArrayNumber(
533 (new TypeDescriptor(typeutil.getClass(TypeUtil.StringClass))).makeArray(state))+state.numClasses()));
535 outstructs.println("#define OBJECTARRAYTYPE "+
536 (state.getArrayNumber(
537 (new TypeDescriptor(typeutil.getClass(TypeUtil.ObjectClass))).makeArray(state))+state.numClasses()));
540 outstructs.println("#define STRINGTYPE "+typeutil.getClass(TypeUtil.StringClass).getId());
541 outstructs.println("#define CHARARRAYTYPE "+
542 (state.getArrayNumber((new TypeDescriptor(TypeDescriptor.CHAR)).makeArray(state))+state.numClasses()));
544 outstructs.println("#define BYTEARRAYTYPE "+
545 (state.getArrayNumber((new TypeDescriptor(TypeDescriptor.BYTE)).makeArray(state))+state.numClasses()));
547 outstructs.println("#define BYTEARRAYARRAYTYPE "+
548 (state.getArrayNumber((new TypeDescriptor(TypeDescriptor.BYTE)).makeArray(state).makeArray(state))+state.numClasses()));
550 outstructs.println("#define NUMCLASSES "+state.numClasses());
551 int totalClassSize = state.numClasses() + state.numArrays();
552 outstructs.println("#define TOTALNUMCLASSANDARRAY "+ totalClassSize);
554 outstructs.println("#define STARTUPTYPE "+typeutil.getClass(TypeUtil.StartupClass).getId());
555 outstructs.println("#define TAGTYPE "+typeutil.getClass(TypeUtil.TagClass).getId());
556 outstructs.println("#define TAGARRAYTYPE "+
557 (state.getArrayNumber(new TypeDescriptor(typeutil.getClass(TypeUtil.TagClass)).makeArray(state))+state.numClasses()));
561 protected void outputClassDeclarations(PrintWriter outclassdefs, PrintWriter outglobaldefs, PrintWriter outglobaldefsprim) {
562 if (state.THREAD||state.DSM||state.SINGLETM)
563 outclassdefs.println("#include <pthread.h>");
564 outclassdefs.println("#ifndef INTPTR");
565 outclassdefs.println("#ifdef BIT64");
566 outclassdefs.println("#define INTPTR long");
567 outclassdefs.println("#else");
568 outclassdefs.println("#define INTPTR int");
569 outclassdefs.println("#endif");
570 outclassdefs.println("#endif");
572 outclassdefs.println("#include \"optionalstruct.h\"");
573 outclassdefs.println("struct "+arraytype+";");
574 /* Start by declaring all structs */
575 Iterator it=state.getClassSymbolTable().getDescriptorsIterator();
576 while(it.hasNext()) {
577 ClassDescriptor cn=(ClassDescriptor)it.next();
578 outclassdefs.println("struct "+cn.getSafeSymbol()+";");
580 if((cn.getNumStaticFields() != 0) || (cn.getNumStaticBlocks() != 0)) {
581 // this class has static fields/blocks, need to add a global flag to
582 // indicate if its static fields have been initialized and/or if its
583 // static blocks have been executed
584 outglobaldefsprim.println(" int "+cn.getSafeSymbol()+"static_block_exe_flag;");
587 // for each class, create a global object
588 outglobaldefs.println(" struct ___Object___ *"+cn.getSafeSymbol()+"classobj;");
591 outclassdefs.println("");
592 //Print out definition for array type
593 outclassdefs.println("struct "+arraytype+" {");
594 outclassdefs.println(" int type;");
597 additionalClassObjectFields(outclassdefs);
600 if (state.EVENTMONITOR) {
601 outclassdefs.println(" int objuid;");
604 outclassdefs.println(" pthread_t tid;");
605 outclassdefs.println(" void * lockentry;");
606 outclassdefs.println(" int lockcount;");
609 outclassdefs.println(" int mutex;");
610 outclassdefs.println(" volatile int notifycount;");
611 outclassdefs.println(" int objlock;");
612 if(state.MULTICOREGC) {
613 outclassdefs.println(" int marked;");
617 outclassdefs.println(" int flag;");
618 if(!state.MULTICORE) {
619 outclassdefs.println(" void * flagptr;");
621 outclassdefs.println(" int version;");
622 outclassdefs.println(" int * lock;"); // lock entry for this obj
623 outclassdefs.println(" int mutex;");
624 outclassdefs.println(" int lockcount;");
625 if(state.MULTICOREGC) {
626 outclassdefs.println(" int marked;");
630 outclassdefs.println(" int numfses;");
631 outclassdefs.println(" int * fses;");
635 printClassStruct(typeutil.getClass(TypeUtil.ObjectClass), outclassdefs, outglobaldefs, outglobaldefsprim);
636 printedfieldstbl.clear();
637 printExtraArrayFields(outclassdefs);
638 if (state.ARRAYPAD) {
639 outclassdefs.println(" int paddingforarray;");
642 outclassdefs.println(" int ___length___;");
643 outclassdefs.println("};\n");
646 // TODO add version for normal Java later
647 outclassdefs.println("");
648 //Print out definition for Class type
649 outclassdefs.println("struct Class {");
650 outclassdefs.println(" int type;");
653 additionalClassObjectFields(outclassdefs);
656 if (state.EVENTMONITOR) {
657 outclassdefs.println(" int objuid;");
660 outclassdefs.println(" pthread_t tid;");
661 outclassdefs.println(" void * lockentry;");
662 outclassdefs.println(" int lockcount;");
665 outclassdefs.println(" int mutex;");
666 outclassdefs.println(" volatile int notifycount;");
667 outclassdefs.println(" int objlock;");
668 if(state.MULTICOREGC) {
669 outclassdefs.println(" int marked;");
673 outclassdefs.println(" int flag;");
674 if(!state.MULTICORE) {
675 outclassdefs.println(" void * flagptr;");
677 outclassdefs.println(" int version;");
678 outclassdefs.println(" int * lock;"); // lock entry for this obj
679 outclassdefs.println(" int mutex;");
680 outclassdefs.println(" int lockcount;");
681 if(state.MULTICOREGC) {
682 outclassdefs.println(" int marked;");
686 outclassdefs.println(" int numfses;");
687 outclassdefs.println(" int * fses;");
690 printClassStruct(typeutil.getClass(TypeUtil.ObjectClass), outclassdefs, outglobaldefs, outglobaldefsprim);
691 printedfieldstbl.clear();
692 outclassdefs.println("};\n");
695 outclassdefs.println("");
696 outclassdefs.println("extern int classsize[];");
697 outclassdefs.println("extern int hasflags[];");
698 outclassdefs.println("extern unsigned INTPTR * pointerarray[];");
699 outclassdefs.println("extern int* supertypes[];");
700 outclassdefs.println("");
703 /** Prints out definitions for generic task structures */
705 protected void outputTaskTypes(PrintWriter outtask) {
706 outtask.println("#ifndef _TASK_H");
707 outtask.println("#define _TASK_H");
708 outtask.println("struct parameterdescriptor {");
709 outtask.println("int type;");
710 outtask.println("int numberterms;");
711 outtask.println("int *intarray;");
712 outtask.println("void * queue;");
713 outtask.println("int numbertags;");
714 outtask.println("int *tagarray;");
715 outtask.println("};");
717 outtask.println("struct taskdescriptor {");
718 outtask.println("void * taskptr;");
719 outtask.println("int numParameters;");
720 outtask.println(" int numTotal;");
721 outtask.println("struct parameterdescriptor **descriptorarray;");
722 outtask.println("char * name;");
723 outtask.println("};");
724 outtask.println("extern struct taskdescriptor * taskarray[];");
725 outtask.println("extern numtasks;");
726 outtask.println("#endif");
730 protected void buildRepairStructs(PrintWriter outrepairstructs) {
731 Iterator classit=state.getClassSymbolTable().getDescriptorsIterator();
732 while(classit.hasNext()) {
733 ClassDescriptor cn=(ClassDescriptor)classit.next();
734 outrepairstructs.println("structure "+cn.getSymbol()+" {");
735 outrepairstructs.println(" int __type__;");
737 outrepairstructs.println(" int __flag__;");
738 if(!state.MULTICORE) {
739 outrepairstructs.println(" int __flagptr__;");
742 printRepairStruct(cn, outrepairstructs);
743 outrepairstructs.println("}\n");
746 for(int i=0; i<state.numArrays(); i++) {
747 TypeDescriptor tdarray=arraytable[i];
748 TypeDescriptor tdelement=tdarray.dereference();
749 outrepairstructs.println("structure "+arraytype+"_"+state.getArrayNumber(tdarray)+" {");
750 outrepairstructs.println(" int __type__;");
751 printRepairStruct(typeutil.getClass(TypeUtil.ObjectClass), outrepairstructs);
752 outrepairstructs.println(" int length;");
753 outrepairstructs.println("}\n");
757 protected void printRepairStruct(ClassDescriptor cn, PrintWriter output) {
758 ClassDescriptor sp=cn.getSuperDesc();
760 printRepairStruct(sp, output);
762 Vector fields=(Vector)fieldorder.get(cn);
764 for(int i=0; i<fields.size(); i++) {
765 FieldDescriptor fd=(FieldDescriptor)fields.get(i);
766 if (fd.getType().isArray()) {
767 output.println(" "+arraytype+"_"+ state.getArrayNumber(fd.getType()) +" * "+fd.getSymbol()+";");
768 } else if (fd.getType().isClass())
769 output.println(" "+fd.getType().getRepairSymbol()+" * "+fd.getSymbol()+";");
770 else if (fd.getType().isFloat())
771 output.println(" int "+fd.getSymbol()+"; /* really float */");
773 output.println(" "+fd.getType().getRepairSymbol()+" "+fd.getSymbol()+";");
777 /** This method outputs TaskDescriptor information */
778 protected void generateTaskDescriptor(PrintWriter output, FlatMethod fm, TaskDescriptor task) {
779 for (int i=0; i<task.numParameters(); i++) {
780 VarDescriptor param_var=task.getParameter(i);
781 TypeDescriptor param_type=task.getParamType(i);
782 FlagExpressionNode param_flag=task.getFlag(param_var);
783 TagExpressionList param_tag=task.getTag(param_var);
786 if (param_flag==null) {
787 output.println("int parameterdnf_"+i+"_"+task.getSafeSymbol()+"[]={");
788 output.println("0x0, 0x0 };");
791 DNFFlag dflag=param_flag.getDNF();
792 dnfterms=dflag.size();
794 Hashtable flags=(Hashtable)flagorder.get(param_type.getClassDesc());
795 output.println("int parameterdnf_"+i+"_"+task.getSafeSymbol()+"[]={");
796 for(int j=0; j<dflag.size(); j++) {
799 Vector term=dflag.get(j);
802 for(int k=0; k<term.size(); k++) {
803 DNFFlagAtom dfa=(DNFFlagAtom)term.get(k);
804 FlagDescriptor fd=dfa.getFlag();
805 boolean negated=dfa.getNegated();
806 int flagid=1<<((Integer)flags.get(fd)).intValue();
811 output.print("0x"+Integer.toHexString(andmask)+", 0x"+Integer.toHexString(checkmask));
813 output.println("};");
816 output.println("int parametertag_"+i+"_"+task.getSafeSymbol()+"[]={");
818 for(int j=0; j<param_tag.numTags(); j++) {
821 /* for each tag we need */
822 /* which slot it is */
823 /* what type it is */
824 TagVarDescriptor tvd=(TagVarDescriptor)task.getParameterTable().get(param_tag.getName(j));
825 TempDescriptor tmp=param_tag.getTemp(j);
826 int slot=fm.getTagInt(tmp);
827 output.println(slot+", "+state.getTagId(tvd.getTag()));
829 output.println("};");
831 output.println("struct parameterdescriptor parameter_"+i+"_"+task.getSafeSymbol()+"={");
832 output.println("/* type */"+param_type.getClassDesc().getId()+",");
833 output.println("/* number of DNF terms */"+dnfterms+",");
834 output.println("parameterdnf_"+i+"_"+task.getSafeSymbol()+",");
835 output.println("0,");
837 output.println("/* number of tags */"+param_tag.numTags()+",");
839 output.println("/* number of tags */ 0,");
840 output.println("parametertag_"+i+"_"+task.getSafeSymbol());
841 output.println("};");
845 output.println("struct parameterdescriptor * parameterdescriptors_"+task.getSafeSymbol()+"[] = {");
846 for (int i=0; i<task.numParameters(); i++) {
849 output.print("¶meter_"+i+"_"+task.getSafeSymbol());
851 output.println("};");
853 output.println("struct taskdescriptor task_"+task.getSafeSymbol()+"={");
854 output.println("&"+task.getSafeSymbol()+",");
855 output.println("/* number of parameters */" +task.numParameters() + ",");
856 int numtotal=task.numParameters()+fm.numTags();
857 output.println("/* number total parameters */" +numtotal + ",");
858 output.println("parameterdescriptors_"+task.getSafeSymbol()+",");
859 output.println("\""+task.getSymbol()+"\"");
860 output.println("};");
864 /** The buildVirtualTables method outputs the virtual dispatch
865 * tables for methods. */
867 protected void buildVirtualTables(PrintWriter outvirtual) {
868 Iterator classit=state.getClassSymbolTable().getDescriptorsIterator();
869 while(classit.hasNext()) {
870 ClassDescriptor cd=(ClassDescriptor)classit.next();
871 if (virtualcalls.getMethodCount(cd)>maxcount)
872 maxcount=virtualcalls.getMethodCount(cd);
874 MethodDescriptor[][] virtualtable=null;
875 virtualtable=new MethodDescriptor[state.numClasses()+state.numArrays()][maxcount];
877 /* Fill in virtual table */
878 classit=state.getClassSymbolTable().getDescriptorsIterator();
879 while(classit.hasNext()) {
880 ClassDescriptor cd=(ClassDescriptor)classit.next();
881 fillinRow(cd, virtualtable, cd.getId());
884 ClassDescriptor objectcd=typeutil.getClass(TypeUtil.ObjectClass);
885 Iterator arrayit=state.getArrayIterator();
886 while(arrayit.hasNext()) {
887 TypeDescriptor td=(TypeDescriptor)arrayit.next();
888 int id=state.getArrayNumber(td);
889 fillinRow(objectcd, virtualtable, id+state.numClasses());
892 outvirtual.print("void * virtualtable[]={");
893 boolean needcomma=false;
894 for(int i=0; i<state.numClasses()+state.numArrays(); i++) {
895 for(int j=0; j<maxcount; j++) {
897 outvirtual.print(", ");
898 if (virtualtable[i][j]!=null) {
899 MethodDescriptor md=virtualtable[i][j];
900 outvirtual.print("& "+md.getClassDesc().getSafeSymbol()+md.getSafeSymbol()+"_"+md.getSafeMethodDescriptor());
902 outvirtual.print("0");
906 outvirtual.println("");
908 outvirtual.println("};");
912 protected void fillinRow(ClassDescriptor cd, MethodDescriptor[][] virtualtable, int rownum) {
913 /* Get inherited methods */
914 Iterator it_sifs = cd.getSuperInterfaces();
915 while(it_sifs.hasNext()) {
916 ClassDescriptor superif = (ClassDescriptor)it_sifs.next();
917 fillinRow(superif, virtualtable, rownum);
919 if (cd.getSuperDesc()!=null)
920 fillinRow(cd.getSuperDesc(), virtualtable, rownum);
921 /* Override them with our methods */
922 for(Iterator it=cd.getMethods(); it.hasNext(); ) {
923 MethodDescriptor md=(MethodDescriptor)it.next();
924 if (md.isStatic()||md.getReturnType()==null)
926 Vector<Integer> numvec = virtualcalls.getMethodNumber(md);
927 for(int i = 0; i < numvec.size(); i++) {
928 int methodnum = numvec.elementAt(i).intValue();
929 virtualtable[rownum][methodnum]=md;
934 /** Generate array that contains the sizes of class objects. The
935 * object allocation functions in the runtime use this
938 protected void generateSizeArray(PrintWriter outclassdefs) {
939 outclassdefs.print("extern struct prefetchCountStats * evalPrefetch;\n");
940 generateSizeArrayExtensions(outclassdefs);
942 Iterator it=state.getClassSymbolTable().getDescriptorsIterator();
943 cdarray=new ClassDescriptor[state.numClasses()];
946 while(it.hasNext()) {
947 ClassDescriptor cd=(ClassDescriptor)it.next();
948 cdarray[cd.getId()] = cd;
951 arraytable=new TypeDescriptor[state.numArrays()];
953 Iterator arrayit=state.getArrayIterator();
954 while(arrayit.hasNext()) {
955 TypeDescriptor td=(TypeDescriptor)arrayit.next();
956 int id=state.getArrayNumber(td);
960 /* Print out types */
961 outclassdefs.println("/* ");
962 for(int i=0; i<state.numClasses(); i++) {
963 ClassDescriptor cd=cdarray[i];
965 outclassdefs.println("NULL " + i);
967 outclassdefs.println(cd +" "+i);
971 for(int i=0; i<state.numArrays(); i++) {
972 TypeDescriptor arraytd=arraytable[i];
973 outclassdefs.println(arraytd.toPrettyString() +" "+(i+state.numClasses()));
976 outclassdefs.println("*/");
979 outclassdefs.print("int classsize[]={");
981 boolean needcomma=false;
982 for(int i=0; i<state.numClasses(); i++) {
984 outclassdefs.print(", ");
986 outclassdefs.print("sizeof(struct "+cdarray[i].getSafeSymbol()+")");
988 outclassdefs.print("0");
994 for(int i=0; i<state.numArrays(); i++) {
996 outclassdefs.print(", ");
997 TypeDescriptor tdelement=arraytable[i].dereference();
998 if (tdelement.isArray()||tdelement.isClass()||tdelement.isNull())
999 outclassdefs.print("sizeof(void *)");
1001 outclassdefs.print("sizeof("+tdelement.getSafeSymbol()+")");
1005 outclassdefs.println("};");
1007 ClassDescriptor objectclass=typeutil.getClass(TypeUtil.ObjectClass);
1009 outclassdefs.print("int typearray[]={");
1010 for(int i=0; i<state.numClasses(); i++) {
1011 ClassDescriptor cd=cdarray[i];
1012 ClassDescriptor supercd=i>0 ? cd.getSuperDesc() : null;
1014 outclassdefs.print(", ");
1016 outclassdefs.print("-1");
1018 outclassdefs.print(supercd.getId());
1022 for(int i=0; i<state.numArrays(); i++) {
1023 TypeDescriptor arraytd=arraytable[i];
1024 ClassDescriptor arraycd=arraytd.getClassDesc();
1025 if (arraycd==null) {
1027 outclassdefs.print(", ");
1028 outclassdefs.print(objectclass.getId());
1032 ClassDescriptor cd=arraycd.getSuperDesc();
1035 TypeDescriptor supertd=new TypeDescriptor(cd);
1036 supertd.setArrayCount(arraytd.getArrayCount());
1037 type=state.getArrayNumber(supertd);
1039 type+=state.numClasses();
1042 cd=cd.getSuperDesc();
1045 outclassdefs.print(", ");
1046 outclassdefs.print(type);
1050 outclassdefs.println("};");
1055 outclassdefs.print("int typearray2[]={");
1056 for(int i=0; i<state.numArrays(); i++) {
1057 TypeDescriptor arraytd=arraytable[i];
1058 ClassDescriptor arraycd=arraytd.getClassDesc();
1059 if (arraycd==null) {
1061 outclassdefs.print(", ");
1062 outclassdefs.print("-1");
1066 ClassDescriptor cd=arraycd.getSuperDesc();
1067 int level=arraytd.getArrayCount()-1;
1069 for(; level>0; level--) {
1070 TypeDescriptor supertd=new TypeDescriptor(objectclass);
1071 supertd.setArrayCount(level);
1072 type=state.getArrayNumber(supertd);
1074 type+=state.numClasses();
1079 outclassdefs.print(", ");
1080 outclassdefs.print(type);
1084 outclassdefs.println("};");
1087 /** Constructs params and temp objects for each method or task.
1088 * These objects tell the compiler which temps need to be
1091 protected void generateTempStructs(FlatMethod fm) {
1092 MethodDescriptor md=fm.getMethod();
1093 TaskDescriptor task=fm.getTask();
1094 ParamsObject objectparams=md!=null ? new ParamsObject(md,tag++) : new ParamsObject(task, tag++);
1096 paramstable.put(md, objectparams);
1098 paramstable.put(task, objectparams);
1100 for(int i=0; i<fm.numParameters(); i++) {
1101 TempDescriptor temp=fm.getParameter(i);
1102 TypeDescriptor type=temp.getType();
1103 if (type.isPtr()&&((GENERATEPRECISEGC) || (this.state.MULTICOREGC)))
1104 objectparams.addPtr(temp);
1106 objectparams.addPrim(temp);
1109 for(int i=0; i<fm.numTags(); i++) {
1110 TempDescriptor temp=fm.getTag(i);
1111 if ((GENERATEPRECISEGC) || (this.state.MULTICOREGC))
1112 objectparams.addPtr(temp);
1114 objectparams.addPrim(temp);
1117 TempObject objecttemps=md!=null ? new TempObject(objectparams,md,tag++) : new TempObject(objectparams, task, tag++);
1119 tempstable.put(md, objecttemps);
1121 tempstable.put(task, objecttemps);
1123 for(Iterator nodeit=fm.getNodeSet().iterator(); nodeit.hasNext(); ) {
1124 FlatNode fn=(FlatNode)nodeit.next();
1125 TempDescriptor[] writes=fn.writesTemps();
1126 for(int i=0; i<writes.length; i++) {
1127 TempDescriptor temp=writes[i];
1128 TypeDescriptor type=temp.getType();
1129 if (type.isPtr()&&((GENERATEPRECISEGC) || (this.state.MULTICOREGC)))
1130 objecttemps.addPtr(temp);
1132 objecttemps.addPrim(temp);
1137 /** This method outputs the following information about classes
1139 * (1) For classes, what are the locations of pointers.
1140 * (2) For arrays, does the array contain pointers or primitives.
1141 * (3) For classes, does the class contain flags.
1144 protected void generateLayoutStructs(PrintWriter output) {
1145 Iterator it=state.getClassSymbolTable().getDescriptorsIterator();
1146 while(it.hasNext()) {
1147 ClassDescriptor cn=(ClassDescriptor)it.next();
1148 output.println("unsigned INTPTR "+cn.getSafeSymbol()+"_pointers[]={");
1149 Iterator allit=cn.getFieldTable().getAllDescriptorsIterator();
1151 while(allit.hasNext()) {
1152 FieldDescriptor fd=(FieldDescriptor)allit.next();
1153 TypeDescriptor type=fd.getType();
1157 output.print(count);
1158 allit=cn.getFieldTable().getAllDescriptorsIterator();
1159 while(allit.hasNext()) {
1160 FieldDescriptor fd=(FieldDescriptor)allit.next();
1164 TypeDescriptor type=fd.getType();
1166 output.println(",");
1167 output.print("((unsigned INTPTR)&(((struct "+cn.getSafeSymbol() +" *)0)->"+
1168 fd.getSafeSymbol()+"))");
1171 output.println("};");
1173 output.println("unsigned INTPTR * pointerarray[]={");
1174 boolean needcomma=false;
1175 for(int i=0; i<state.numClasses(); i++) {
1176 ClassDescriptor cn=cdarray[i];
1178 output.println(",");
1181 output.print(cn.getSafeSymbol()+"_pointers");
1183 output.print("NULL");
1187 for(int i=0; i<state.numArrays(); i++) {
1189 output.println(", ");
1190 TypeDescriptor tdelement=arraytable[i].dereference();
1191 if (tdelement.isArray()||tdelement.isClass())
1192 output.print("((unsigned INTPTR *)1)");
1198 output.println("};");
1200 output.println("int hasflags[]={");
1201 for(int i=0; i<state.numClasses(); i++) {
1202 ClassDescriptor cn=cdarray[i];
1204 output.println(", ");
1206 if ((cn != null) && (cn.hasFlags()))
1211 output.println("};");
1214 private int checkarraysupertype(ClassDescriptor arraycd, TypeDescriptor arraytd) {
1217 TypeDescriptor supertd=new TypeDescriptor(arraycd);
1218 supertd.setArrayCount(arraytd.getArrayCount());
1219 type=state.getArrayNumber(supertd);
1224 ClassDescriptor cd = arraycd.getSuperDesc();
1226 type = checkarraysupertype(cd, arraytd);
1232 Iterator it_sifs = arraycd.getSuperInterfaces();
1233 while(it_sifs.hasNext()) {
1234 ClassDescriptor ifcd = (ClassDescriptor)it_sifs.next();
1235 type = checkarraysupertype(ifcd, arraytd);
1245 /** Print out table to give us supertypes */
1246 protected void generateSuperTypeTable(PrintWriter output) {
1247 ClassDescriptor objectclass=typeutil.getClass(TypeUtil.ObjectClass);
1248 for(int i=0; i<state.numClasses(); i++) {
1249 ClassDescriptor cn=cdarray[i];
1253 output.print("int supertypes" + cn.getSafeSymbol() + "[] = {");
1254 boolean ncomma = false;
1256 if((cn != null) && (cn.getSuperDesc() != null)) {
1259 Iterator it_sifs = cn != null? cn.getSuperInterfaces() : null;
1260 while(it_sifs != null && it_sifs.hasNext()) {
1266 if ((cn != null) && (cn.getSuperDesc()!=null)) {
1270 ClassDescriptor cdsuper=cn.getSuperDesc();
1271 output.print(cdsuper.getId());
1273 it_sifs = cn != null? cn.getSuperInterfaces() : null;
1274 while(it_sifs != null && it_sifs.hasNext()) {
1278 output.print(((ClassDescriptor)it_sifs.next()).getId());
1281 output.println("};");
1284 for(int i=0; i<state.numArrays(); i++) {
1285 TypeDescriptor arraytd=arraytable[i];
1286 ClassDescriptor arraycd=arraytd.getClassDesc();
1287 output.print("int supertypes___arraytype___" + (i+state.numClasses()) + "[] = {");
1288 boolean ncomma = false;
1290 if (arraycd==null) {
1294 output.print(objectclass.getId());
1295 output.println("};");
1298 if((arraycd != null) && (arraycd.getSuperDesc() != null)) {
1301 Iterator it_sifs = arraycd != null? arraycd.getSuperInterfaces() : null;
1302 while(it_sifs != null && it_sifs.hasNext()) {
1308 if ((arraycd != null) && (arraycd.getSuperDesc()!=null)) {
1309 ClassDescriptor cd=arraycd.getSuperDesc();
1312 type = checkarraysupertype(cd, arraytd);
1314 type += state.numClasses();
1321 it_sifs = arraycd != null? arraycd.getSuperInterfaces() : null;
1322 while(it_sifs != null && it_sifs.hasNext()) {
1323 ClassDescriptor ifcd = (ClassDescriptor)it_sifs.next();
1324 int type = checkarraysupertype(ifcd , arraytd);
1326 type += state.numClasses();
1332 output.println("};");
1335 output.println("int* supertypes[]={");
1336 boolean needcomma=false;
1337 for(int i=0; i<state.numClasses(); i++) {
1338 ClassDescriptor cn=cdarray[i];
1340 output.println(",");
1343 output.print("supertypes" + cn.getSafeSymbol());
1349 for(int i=0; i<state.numArrays(); i++) {
1351 output.println(",");
1353 output.print("supertypes___arraytype___" + (i+state.numClasses()));
1355 output.println("};");
1358 /** Force consistent field ordering between inherited classes. */
1360 protected void printClassStruct(ClassDescriptor cn, PrintWriter classdefout, PrintWriter globaldefout, PrintWriter globaldefprimout) {
1362 ClassDescriptor sp=cn.getSuperDesc();
1364 printClassStruct(sp, classdefout, /*globaldefout*/ null, null);
1366 SymbolTable sitbl = cn.getSuperInterfaceTable();
1367 Iterator it_sifs = sitbl.getDescriptorsIterator();
1368 while(it_sifs.hasNext()) {
1369 ClassDescriptor si = (ClassDescriptor)it_sifs.next();
1370 printClassStruct(si, classdefout, /*globaldefout*/ null, null);
1373 if (!fieldorder.containsKey(cn)) {
1374 Vector fields=new Vector();
1375 fieldorder.put(cn,fields);
1377 Vector fieldvec=cn.getFieldVec();
1378 for(int i=0; i<fieldvec.size(); i++) {
1379 FieldDescriptor fd=(FieldDescriptor)fieldvec.get(i);
1380 if((sp != null) && sp.getFieldTable().contains(fd.getSymbol())) {
1383 it_sifs = sitbl.getDescriptorsIterator();
1384 boolean hasprinted = false;
1385 while(it_sifs.hasNext()) {
1386 ClassDescriptor si = (ClassDescriptor)it_sifs.next();
1387 if(si.getFieldTable().contains(fd.getSymbol())) {
1393 // this field has been defined in the super class
1400 //Vector fields=(Vector)fieldorder.get(cn);
1402 Vector fields = cn.getFieldVec();
1404 for(int i=0; i<fields.size(); i++) {
1405 FieldDescriptor fd=(FieldDescriptor)fields.get(i);
1406 String fstring = fd.getSafeSymbol();
1407 if(printedfieldstbl.containsKey(fstring)) {
1408 printedfieldstbl.put(fstring, cn);
1411 printedfieldstbl.put(fstring, cn);
1413 if (fd.getType().isClass()
1414 && fd.getType().getClassDesc().isEnum()) {
1415 classdefout.println(" int " + fd.getSafeSymbol() + ";");
1416 } else if (fd.getType().isClass()||fd.getType().isArray()) {
1417 if (fd.isStatic()) {
1418 // TODO add version for normal Java later
1420 if(globaldefout != null) {
1421 if(fd.isVolatile()) {
1422 globaldefout.println(" volatile struct "+fd.getType().getSafeSymbol()+ " * "+fd.getSafeSymbol()+";");
1424 globaldefout.println(" struct "+fd.getType().getSafeSymbol()+ " * "+fd.getSafeSymbol()+";");
1428 } else if (fd.isVolatile()) {
1430 classdefout.println(" volatile struct "+fd.getType().getSafeSymbol()+ " * "+fd.getSafeSymbol()+";");
1432 classdefout.println(" struct "+fd.getType().getSafeSymbol()+" * "+fd.getSafeSymbol()+";");
1434 } else if (fd.isStatic()) {
1435 // TODO add version for normal Java later
1437 if(globaldefout != null) {
1438 if(fd.isVolatile()) {
1439 globaldefprimout.println(" volatile "+fd.getType().getSafeSymbol()+ " "+fd.getSafeSymbol()+";");
1441 globaldefprimout.println(" "+fd.getType().getSafeSymbol()+ " "+fd.getSafeSymbol()+";");
1445 } else if (fd.isVolatile()) {
1447 classdefout.println(" volatile "+fd.getType().getSafeSymbol()+ " "+fd.getSafeSymbol()+";");
1449 classdefout.println(" "+fd.getType().getSafeSymbol()+" "+fd.getSafeSymbol()+";");
1454 /* Map flags to integers consistently between inherited
1457 protected void mapFlags(ClassDescriptor cn) {
1458 ClassDescriptor sp=cn.getSuperDesc();
1462 if (!flagorder.containsKey(cn)) {
1463 Hashtable flags=new Hashtable();
1464 flagorder.put(cn,flags);
1466 Hashtable superflags=(Hashtable)flagorder.get(sp);
1467 Iterator superflagit=superflags.keySet().iterator();
1468 while(superflagit.hasNext()) {
1469 FlagDescriptor fd=(FlagDescriptor)superflagit.next();
1470 Integer number=(Integer)superflags.get(fd);
1471 flags.put(fd, number);
1472 if ((number.intValue()+1)>max)
1473 max=number.intValue()+1;
1477 Iterator flagit=cn.getFlags();
1478 while(flagit.hasNext()) {
1479 FlagDescriptor fd=(FlagDescriptor)flagit.next();
1480 if (sp==null||!sp.getFlagTable().contains(fd.getSymbol()))
1481 flags.put(fd, new Integer(max++));
1487 /** This function outputs (1) structures that parameters are
1488 * passed in (when PRECISE GC is enabled) and (2) function
1489 * prototypes for the methods */
1491 protected void generateCallStructs(ClassDescriptor cn, PrintWriter classdefout, PrintWriter output, PrintWriter headersout, PrintWriter globaldefout, PrintWriter globaldefprimout) {
1492 /* Output class structure */
1493 classdefout.println("struct "+cn.getSafeSymbol()+" {");
1494 classdefout.println(" int type;");
1497 additionalClassObjectFields(classdefout);
1500 if (state.EVENTMONITOR) {
1501 classdefout.println(" int objuid;");
1504 classdefout.println(" pthread_t tid;");
1505 classdefout.println(" void * lockentry;");
1506 classdefout.println(" int lockcount;");
1509 classdefout.println(" int mutex;");
1510 classdefout.println(" volatile int notifycount;");
1511 classdefout.println(" int objlock;");
1512 if(state.MULTICOREGC) {
1513 classdefout.println(" int marked;");
1517 classdefout.println(" int flag;");
1518 if((!state.MULTICORE) || (cn.getSymbol().equals("TagDescriptor"))) {
1519 classdefout.println(" void * flagptr;");
1520 } else if (state.MULTICORE) {
1521 classdefout.println(" int version;");
1522 classdefout.println(" int * lock;"); // lock entry for this obj
1523 classdefout.println(" int mutex;");
1524 classdefout.println(" int lockcount;");
1525 if(state.MULTICOREGC) {
1526 classdefout.println(" int marked;");
1529 if (state.OPTIONAL) {
1530 classdefout.println(" int numfses;");
1531 classdefout.println(" int * fses;");
1534 printClassStruct(cn, classdefout, globaldefout, globaldefprimout);
1535 printedfieldstbl.clear(); // = new Hashtable<String, ClassDescriptor>();
1536 classdefout.println("};\n");
1537 generateCallStructsMethods(cn, output, headersout);
1541 protected void generateCallStructsMethods(ClassDescriptor cn, PrintWriter output, PrintWriter headersout) {
1542 for(Iterator methodit=cn.getMethods(); methodit.hasNext(); ) {
1543 MethodDescriptor md=(MethodDescriptor)methodit.next();
1544 generateMethod(cn, md, headersout, output);
1548 protected void generateMethodParam(ClassDescriptor cn, MethodDescriptor md, PrintWriter output) {
1549 /* Output parameter structure */
1550 if ((GENERATEPRECISEGC) || (this.state.MULTICOREGC)) {
1551 if(md.isInvokedByStatic() && !md.isStaticBlock() && !md.getModifiers().isNative()) {
1552 // generate the staticinit version
1553 String mdstring = md.getSafeMethodDescriptor() + "staticinit";
1555 ParamsObject objectparams=(ParamsObject) paramstable.get(md);
1556 output.println("struct "+cn.getSafeSymbol()+md.getSafeSymbol()+"_"+mdstring+"_params {");
1557 output.println(" int size;");
1558 output.println(" void * next;");
1559 for(int i=0; i<objectparams.numPointers(); i++) {
1560 TempDescriptor temp=objectparams.getPointer(i);
1561 if(temp.getType().isClass() && temp.getType().getClassDesc().isEnum()) {
1562 output.println(" int " + temp.getSafeSymbol() + ";");
1564 output.println(" struct "+temp.getType().getSafeSymbol()+" * "+temp.getSafeSymbol()+";");
1567 output.println("};\n");
1570 ParamsObject objectparams=(ParamsObject) paramstable.get(md);
1571 output.println("struct "+cn.getSafeSymbol()+md.getSafeSymbol()+"_"+md.getSafeMethodDescriptor()+"_params {");
1572 output.println(" int size;");
1573 output.println(" void * next;");
1574 for(int i=0; i<objectparams.numPointers(); i++) {
1575 TempDescriptor temp=objectparams.getPointer(i);
1576 if(temp.getType().isClass() && temp.getType().getClassDesc().isEnum()) {
1577 output.println(" int " + temp.getSafeSymbol() + ";");
1579 output.println(" struct "+temp.getType().getSafeSymbol()+" * "+temp.getSafeSymbol()+";");
1582 output.println("};\n");
1586 protected void generateMethod(ClassDescriptor cn, MethodDescriptor md, PrintWriter headersout, PrintWriter output) {
1587 FlatMethod fm=state.getMethodFlat(md);
1588 generateTempStructs(fm);
1590 ParamsObject objectparams=(ParamsObject) paramstable.get(md);
1591 TempObject objecttemps=(TempObject) tempstable.get(md);
1593 boolean printcomma = false;
1595 generateMethodParam(cn, md, output);
1597 if(md.isInvokedByStatic()) {
1598 // generate the staticinit version
1599 String mdstring = md.getSafeMethodDescriptor() + "staticinit";
1601 /* Output temp structure */
1602 if ((GENERATEPRECISEGC) || (this.state.MULTICOREGC)) {
1603 output.println("struct "+cn.getSafeSymbol()+md.getSafeSymbol()+"_"+mdstring+"_locals {");
1604 output.println(" int size;");
1605 output.println(" void * next;");
1606 for(int i=0; i<objecttemps.numPointers(); i++) {
1607 TempDescriptor temp=objecttemps.getPointer(i);
1608 if (temp.getType().isNull())
1609 output.println(" void * "+temp.getSafeSymbol()+";");
1611 output.println(" struct "+temp.getType().getSafeSymbol()+" * "+temp.getSafeSymbol()+";");
1613 output.println("};\n");
1616 headersout.println("#define D"+cn.getSafeSymbol()+md.getSafeSymbol()+"_"+mdstring+" 1");
1617 /* First the return type */
1618 if (md.getReturnType()!=null) {
1619 if(md.getReturnType().isClass() && md.getReturnType().getClassDesc().isEnum()) {
1620 headersout.println(" int ");
1621 } else if (md.getReturnType().isClass()||md.getReturnType().isArray())
1622 headersout.print("struct " + md.getReturnType().getSafeSymbol()+" * ");
1624 headersout.print(md.getReturnType().getSafeSymbol()+" ");
1626 //catch the constructor case
1627 headersout.print("void ");
1629 /* Next the method name */
1630 headersout.print(cn.getSafeSymbol()+md.getSafeSymbol()+"_"+mdstring+"(");
1632 if ((GENERATEPRECISEGC) || (this.state.MULTICOREGC)) {
1633 headersout.print("struct "+cn.getSafeSymbol()+md.getSafeSymbol()+"_"+mdstring+"_params * "+paramsprefix);
1637 /* Output parameter list*/
1638 for(int i=0; i<objectparams.numPrimitives(); i++) {
1639 TempDescriptor temp=objectparams.getPrimitive(i);
1641 headersout.print(", ");
1643 if(temp.getType().isClass() && temp.getType().getClassDesc().isEnum()) {
1644 headersout.print("int " + temp.getSafeSymbol());
1645 } else if (temp.getType().isClass()||temp.getType().isArray())
1646 headersout.print("struct " + temp.getType().getSafeSymbol()+" * "+temp.getSafeSymbol());
1648 headersout.print(temp.getType().getSafeSymbol()+" "+temp.getSafeSymbol());
1650 headersout.println(");\n");
1653 /* Output temp structure */
1654 if ((GENERATEPRECISEGC) || (this.state.MULTICOREGC)) {
1655 output.println("struct "+cn.getSafeSymbol()+md.getSafeSymbol()+"_"+md.getSafeMethodDescriptor()+"_locals {");
1656 output.println(" int size;");
1657 output.println(" void * next;");
1658 for(int i=0; i<objecttemps.numPointers(); i++) {
1659 TempDescriptor temp=objecttemps.getPointer(i);
1660 if (temp.getType().isNull())
1661 output.println(" void * "+temp.getSafeSymbol()+";");
1663 output.println(" struct "+temp.getType().getSafeSymbol()+" * "+temp.getSafeSymbol()+";");
1665 output.println("};\n");
1668 /********* Output method declaration ***********/
1669 headersout.println("#define D"+cn.getSafeSymbol()+md.getSafeSymbol()+"_"+md.getSafeMethodDescriptor()+" 1");
1670 /* First the return type */
1671 if (md.getReturnType()!=null) {
1672 if(md.getReturnType().isClass() && md.getReturnType().getClassDesc().isEnum()) {
1673 headersout.println(" int ");
1674 } else if (md.getReturnType().isClass()||md.getReturnType().isArray())
1675 headersout.print("struct " + md.getReturnType().getSafeSymbol()+" * ");
1677 headersout.print(md.getReturnType().getSafeSymbol()+" ");
1679 //catch the constructor case
1680 headersout.print("void ");
1682 /* Next the method name */
1683 headersout.print(cn.getSafeSymbol()+md.getSafeSymbol()+"_"+md.getSafeMethodDescriptor()+"(");
1685 if ((GENERATEPRECISEGC) || (this.state.MULTICOREGC)) {
1686 headersout.print("struct "+cn.getSafeSymbol()+md.getSafeSymbol()+"_"+md.getSafeMethodDescriptor()+"_params * "+paramsprefix);
1690 /* Output parameter list*/
1691 for(int i=0; i<objectparams.numPrimitives(); i++) {
1692 TempDescriptor temp=objectparams.getPrimitive(i);
1694 headersout.print(", ");
1696 if(temp.getType().isClass() && temp.getType().getClassDesc().isEnum()) {
1697 headersout.print("int " + temp.getSafeSymbol());
1698 } else if (temp.getType().isClass()||temp.getType().isArray())
1699 headersout.print("struct " + temp.getType().getSafeSymbol()+" * "+temp.getSafeSymbol());
1701 headersout.print(temp.getType().getSafeSymbol()+" "+temp.getSafeSymbol());
1703 headersout.println(");\n");
1707 /** This function outputs (1) structures that parameters are
1708 * passed in (when PRECISE GC is enabled) and (2) function
1709 * prototypes for the tasks */
1711 protected void generateTaskStructs(PrintWriter output, PrintWriter headersout) {
1712 /* Cycle through tasks */
1713 Iterator taskit=state.getTaskSymbolTable().getDescriptorsIterator();
1715 while(taskit.hasNext()) {
1716 /* Classify parameters */
1717 TaskDescriptor task=(TaskDescriptor)taskit.next();
1718 FlatMethod fm=state.getMethodFlat(task);
1719 generateTempStructs(fm);
1721 ParamsObject objectparams=(ParamsObject) paramstable.get(task);
1722 TempObject objecttemps=(TempObject) tempstable.get(task);
1724 /* Output parameter structure */
1725 if ((GENERATEPRECISEGC) || (this.state.MULTICOREGC)) {
1726 output.println("struct "+task.getSafeSymbol()+"_params {");
1727 output.println(" int size;");
1728 output.println(" void * next;");
1729 for(int i=0; i<objectparams.numPointers(); i++) {
1730 TempDescriptor temp=objectparams.getPointer(i);
1731 output.println(" struct "+temp.getType().getSafeSymbol()+" * "+temp.getSafeSymbol()+";");
1734 output.println("};\n");
1735 if ((objectparams.numPointers()+fm.numTags())>maxtaskparams) {
1736 maxtaskparams=objectparams.numPointers()+fm.numTags();
1740 /* Output temp structure */
1741 if ((GENERATEPRECISEGC) || (this.state.MULTICOREGC)) {
1742 output.println("struct "+task.getSafeSymbol()+"_locals {");
1743 output.println(" int size;");
1744 output.println(" void * next;");
1745 for(int i=0; i<objecttemps.numPointers(); i++) {
1746 TempDescriptor temp=objecttemps.getPointer(i);
1747 if (temp.getType().isNull())
1748 output.println(" void * "+temp.getSafeSymbol()+";");
1749 else if(temp.getType().isTag())
1750 output.println(" struct "+
1751 (new TypeDescriptor(typeutil.getClass(TypeUtil.TagClass))).getSafeSymbol()+" * "+temp.getSafeSymbol()+";");
1753 output.println(" struct "+temp.getType().getSafeSymbol()+" * "+temp.getSafeSymbol()+";");
1755 output.println("};\n");
1758 /* Output task declaration */
1759 headersout.print("void " + task.getSafeSymbol()+"(");
1761 boolean printcomma=false;
1762 if ((GENERATEPRECISEGC) || (this.state.MULTICOREGC)) {
1763 headersout.print("struct "+task.getSafeSymbol()+"_params * "+paramsprefix);
1765 headersout.print("void * parameterarray[]");
1766 headersout.println(");\n");
1770 protected void generateFlatMethod(FlatMethod fm, PrintWriter output) {
1771 if (State.PRINTFLAT)
1772 System.out.println(fm.printMethod());
1773 MethodDescriptor md=fm.getMethod();
1774 TaskDescriptor task=fm.getTask();
1775 ClassDescriptor cn=md!=null ? md.getClassDesc() : null;
1776 ParamsObject objectparams=(ParamsObject)paramstable.get(md!=null ? md : task);
1778 if((md != null) && md.isInvokedByStatic() && !md.isStaticBlock()) {
1779 // generate a special static init version
1780 mgcstaticinit = true;
1781 String mdstring = md.getSafeMethodDescriptor() + "staticinit";
1783 generateHeader(fm, md!=null ? md : task,output);
1784 TempObject objecttemp=(TempObject) tempstable.get(md!=null ? md : task);
1786 if ((GENERATEPRECISEGC) || (this.state.MULTICOREGC)) {
1787 output.print(" struct "+cn.getSafeSymbol()+md.getSafeSymbol()+"_"+mdstring+"_locals "+localsprefix+"={");
1788 output.print(objecttemp.numPointers()+",");
1789 output.print(paramsprefix);
1790 for(int j=0; j<objecttemp.numPointers(); j++)
1791 output.print(", NULL");
1792 output.println("};");
1795 for(int i=0; i<objecttemp.numPrimitives(); i++) {
1796 TempDescriptor td=objecttemp.getPrimitive(i);
1797 TypeDescriptor type=td.getType();
1798 if (type.isNull() && !type.isArray())
1799 output.println(" void * "+td.getSafeSymbol()+";");
1800 else if (type.isClass() && type.getClassDesc().isEnum()) {
1801 output.println(" int " + td.getSafeSymbol() + ";");
1802 } else if (type.isClass()||type.isArray())
1803 output.println(" struct "+type.getSafeSymbol()+" * "+td.getSafeSymbol()+";");
1805 output.println(" "+type.getSafeSymbol()+" "+td.getSafeSymbol()+";");
1808 additionalCodeAtTopFlatMethodBody(output, fm);
1810 /* Check to see if we need to do a GC if this is a
1811 * multi-threaded program...*/
1813 if (((state.OOOJAVA||state.THREAD)&&GENERATEPRECISEGC)
1814 || this.state.MULTICOREGC) {
1815 //Don't bother if we aren't in recursive methods...The loops case will catch it
1816 if (callgraph.getAllMethods(md).contains(md)) {
1817 if (this.state.MULTICOREGC) {
1818 output.println("if(gcflag) gc("+localsprefixaddr+");");
1820 output.println("if (unlikely(needtocollect)) checkcollect("+localsprefixaddr+");");
1825 generateCode(fm.getNext(0), fm, null, output);
1827 output.println("}\n\n");
1829 mgcstaticinit = false;
1832 generateHeader(fm, md!=null ? md : task,output);
1833 TempObject objecttemp=(TempObject) tempstable.get(md!=null ? md : task);
1835 if((md != null) && (md.isStaticBlock())) {
1836 mgcstaticinit = true;
1839 if ((GENERATEPRECISEGC) || (this.state.MULTICOREGC)) {
1841 output.print(" struct "+cn.getSafeSymbol()+md.getSafeSymbol()+"_"+md.getSafeMethodDescriptor()+"_locals "+localsprefix+"={");
1843 output.print(" struct "+task.getSafeSymbol()+"_locals "+localsprefix+"={");
1844 output.print(objecttemp.numPointers()+",");
1845 output.print(paramsprefix);
1846 for(int j=0; j<objecttemp.numPointers(); j++)
1847 output.print(", NULL");
1848 output.println("};");
1851 for(int i=0; i<objecttemp.numPrimitives(); i++) {
1852 TempDescriptor td=objecttemp.getPrimitive(i);
1853 TypeDescriptor type=td.getType();
1854 if (type.isNull() && !type.isArray())
1855 output.println(" void * "+td.getSafeSymbol()+";");
1856 else if (type.isClass() && type.getClassDesc().isEnum()) {
1857 output.println(" int " + td.getSafeSymbol() + ";");
1858 } else if (type.isClass()||type.isArray())
1859 output.println(" struct "+type.getSafeSymbol()+" * "+td.getSafeSymbol()+";");
1861 output.println(" "+type.getSafeSymbol()+" "+td.getSafeSymbol()+";");
1864 additionalCodeAtTopFlatMethodBody(output, fm);
1866 /* Check to see if we need to do a GC if this is a
1867 * multi-threaded program...*/
1869 if (((state.OOOJAVA||state.THREAD)&&GENERATEPRECISEGC)
1870 || this.state.MULTICOREGC) {
1871 //Don't bother if we aren't in recursive methods...The loops case will catch it
1872 if (callgraph.getAllMethods(md).contains(md)) {
1873 if (this.state.MULTICOREGC) {
1874 output.println("if(gcflag) gc("+localsprefixaddr+");");
1876 output.println("if (unlikely(needtocollect)) checkcollect("+localsprefixaddr+");");
1881 if(fm.getMethod().isStaticBlock()) {
1882 // a static block, check if it has been executed
1883 output.println(" if(global_defsprim_p->" + cn.getSafeSymbol()+"static_block_exe_flag != 0) {");
1884 output.println(" return;");
1885 output.println(" }");
1889 generateCode(fm.getNext(0), fm, null, output);
1891 output.println("}\n\n");
1893 mgcstaticinit = false;
1896 protected void generateCode(FlatNode first,
1898 Set<FlatNode> stopset,
1899 PrintWriter output) {
1901 /* Assign labels to FlatNode's if necessary.*/
1903 Hashtable<FlatNode, Integer> nodetolabel;
1905 nodetolabel=assignLabels(first, stopset);
1907 Set<FlatNode> storeset=null;
1908 HashSet<FlatNode> genset=null;
1909 HashSet<FlatNode> refset=null;
1910 Set<FlatNode> unionset=null;
1912 /* Do the actual code generation */
1913 FlatNode current_node=null;
1914 HashSet tovisit=new HashSet();
1915 HashSet visited=new HashSet();
1917 while(current_node!=null||!tovisit.isEmpty()) {
1918 if (current_node==null) {
1919 current_node=(FlatNode)tovisit.iterator().next();
1920 tovisit.remove(current_node);
1921 } else if (tovisit.contains(current_node)) {
1922 tovisit.remove(current_node);
1924 visited.add(current_node);
1925 if (nodetolabel.containsKey(current_node)) {
1926 output.println("L"+nodetolabel.get(current_node)+":");
1928 if (state.INSTRUCTIONFAILURE) {
1930 output.println("if ((++instructioncount)>failurecount) {instructioncount=0;injectinstructionfailure();}");
1932 output.println("if ((--instructioncount)==0) injectinstructionfailure();");
1934 if (current_node.numNext()==0||stopset!=null&&stopset.contains(current_node)) {
1936 generateFlatNode(fm, current_node, output);
1938 if (state.OOOJAVA && stopset!=null) {
1939 assert first.getPrev(0) instanceof FlatSESEEnterNode;
1940 assert current_node instanceof FlatSESEExitNode;
1941 FlatSESEEnterNode fsen = (FlatSESEEnterNode) first.getPrev(0);
1942 FlatSESEExitNode fsxn = (FlatSESEExitNode) current_node;
1943 assert fsen.getFlatExit().equals(fsxn);
1944 assert fsxn.getFlatEnter().equals(fsen);
1946 if (current_node.kind()!=FKind.FlatReturnNode) {
1947 if((fm.getMethod() != null) && (fm.getMethod().isStaticBlock())) {
1948 // a static block, check if it has been executed
1949 output.println(" global_defsprim_p->" + fm.getMethod().getClassDesc().getSafeSymbol()+"static_block_exe_flag = 1;");
1952 output.println(" return;");
1955 } else if(current_node.numNext()==1) {
1957 if (state.OOOJAVA &&
1958 current_node.kind()==FKind.FlatSESEEnterNode) {
1959 FlatSESEEnterNode fsen = (FlatSESEEnterNode)current_node;
1960 generateFlatNode(fm, current_node, output);
1961 nextnode=fsen.getFlatExit().getNext(0);
1964 generateFlatNode(fm, current_node, output);
1965 nextnode=current_node.getNext(0);
1967 if (visited.contains(nextnode)) {
1968 output.println("goto L"+nodetolabel.get(nextnode)+";");
1971 current_node=nextnode;
1972 } else if (current_node.numNext()==2) {
1975 generateFlatCondBranch(fm, (FlatCondBranch)current_node, "L"+nodetolabel.get(current_node.getNext(1)), output);
1976 if (!visited.contains(current_node.getNext(1)))
1977 tovisit.add(current_node.getNext(1));
1978 if (visited.contains(current_node.getNext(0))) {
1979 output.println("goto L"+nodetolabel.get(current_node.getNext(0))+";");
1982 current_node=current_node.getNext(0);
1983 } else throw new Error();
1987 protected Hashtable<FlatNode, Integer> assignLabels(FlatNode first, Set<FlatNode> lastset) {
1988 HashSet tovisit=new HashSet();
1989 HashSet visited=new HashSet();
1991 Hashtable<FlatNode, Integer> nodetolabel=new Hashtable<FlatNode, Integer>();
1994 /*Assign labels first. A node needs a label if the previous
1995 * node has two exits or this node is a join point. */
1997 while(!tovisit.isEmpty()) {
1998 FlatNode fn=(FlatNode)tovisit.iterator().next();
2003 if(lastset!=null&&lastset.contains(fn)) {
2004 // if last is not null and matches, don't go
2005 // any further for assigning labels
2009 for(int i=0; i<fn.numNext(); i++) {
2010 FlatNode nn=fn.getNext(i);
2013 //1) Edge >1 of node
2014 nodetolabel.put(nn,new Integer(labelindex++));
2016 if (!visited.contains(nn)&&!tovisit.contains(nn)) {
2020 nodetolabel.put(nn,new Integer(labelindex++));
2027 /** Generate text string that corresponds to the TempDescriptor td. */
2028 protected String generateTemp(FlatMethod fm, TempDescriptor td) {
2029 MethodDescriptor md=fm.getMethod();
2030 TaskDescriptor task=fm.getTask();
2031 TempObject objecttemps=(TempObject) tempstable.get(md!=null ? md : task);
2033 if (objecttemps.isLocalPrim(td)||objecttemps.isParamPrim(td)) {
2034 return td.getSafeSymbol();
2037 if (objecttemps.isLocalPtr(td)) {
2038 return localsprefixderef+td.getSafeSymbol();
2041 if (objecttemps.isParamPtr(td)) {
2042 return paramsprefix+"->"+td.getSafeSymbol();
2050 protected void generateFlatNode(FlatMethod fm, FlatNode fn, PrintWriter output) {
2051 additionalCodePreNode(fm, fn, output);
2055 case FKind.FlatAtomicEnterNode:
2056 generateFlatAtomicEnterNode(fm, (FlatAtomicEnterNode) fn, output);
2059 case FKind.FlatAtomicExitNode:
2060 generateFlatAtomicExitNode(fm, (FlatAtomicExitNode) fn, output);
2063 case FKind.FlatInstanceOfNode:
2064 generateFlatInstanceOfNode(fm, (FlatInstanceOfNode)fn, output);
2067 case FKind.FlatSESEEnterNode:
2068 generateFlatSESEEnterNode(fm, (FlatSESEEnterNode)fn, output);
2071 case FKind.FlatSESEExitNode:
2072 generateFlatSESEExitNode(fm, (FlatSESEExitNode)fn, output);
2075 case FKind.FlatWriteDynamicVarNode:
2076 generateFlatWriteDynamicVarNode(fm, (FlatWriteDynamicVarNode)fn, output);
2079 case FKind.FlatGlobalConvNode:
2080 generateFlatGlobalConvNode(fm, (FlatGlobalConvNode) fn, output);
2083 case FKind.FlatTagDeclaration:
2084 generateFlatTagDeclaration(fm, (FlatTagDeclaration) fn,output);
2087 case FKind.FlatCall:
2088 generateFlatCall(fm, (FlatCall) fn,output);
2091 case FKind.FlatFieldNode:
2092 generateFlatFieldNode(fm, (FlatFieldNode) fn,output);
2095 case FKind.FlatElementNode:
2096 generateFlatElementNode(fm, (FlatElementNode) fn,output);
2099 case FKind.FlatSetElementNode:
2100 generateFlatSetElementNode(fm, (FlatSetElementNode) fn,output);
2103 case FKind.FlatSetFieldNode:
2104 generateFlatSetFieldNode(fm, (FlatSetFieldNode) fn,output);
2108 generateFlatNew(fm, (FlatNew) fn,output);
2111 case FKind.FlatOpNode:
2112 generateFlatOpNode(fm, (FlatOpNode) fn,output);
2115 case FKind.FlatCastNode:
2116 generateFlatCastNode(fm, (FlatCastNode) fn,output);
2119 case FKind.FlatLiteralNode:
2120 generateFlatLiteralNode(fm, (FlatLiteralNode) fn,output);
2123 case FKind.FlatReturnNode:
2124 generateFlatReturnNode(fm, (FlatReturnNode) fn,output);
2128 output.println("/* nop */");
2131 case FKind.FlatGenReachNode:
2132 // this node is just for generating a reach graph
2133 // in disjointness analysis at a particular program point
2136 case FKind.FlatExit:
2137 output.println("/* exit */");
2140 case FKind.FlatBackEdge:
2141 generateFlatBackEdge(fm, (FlatBackEdge)fn, output);
2144 case FKind.FlatCheckNode:
2145 generateFlatCheckNode(fm, (FlatCheckNode) fn, output);
2148 case FKind.FlatFlagActionNode:
2149 generateFlatFlagActionNode(fm, (FlatFlagActionNode) fn, output);
2152 case FKind.FlatPrefetchNode:
2153 generateFlatPrefetchNode(fm, (FlatPrefetchNode) fn, output);
2156 case FKind.FlatOffsetNode:
2157 generateFlatOffsetNode(fm, (FlatOffsetNode)fn, output);
2164 additionalCodePostNode(fm, fn, output);
2167 public void generateFlatBackEdge(FlatMethod fm, FlatBackEdge fn, PrintWriter output) {
2168 if (((state.OOOJAVA||state.THREAD)&&GENERATEPRECISEGC)
2169 || (this.state.MULTICOREGC)) {
2170 if(this.state.MULTICOREGC) {
2171 output.println("if (gcflag) gc("+localsprefixaddr+");");
2173 output.println("if (unlikely(needtocollect)) checkcollect("+localsprefixaddr+");");
2176 output.println("/* nop */");
2179 public void generateFlatOffsetNode(FlatMethod fm, FlatOffsetNode fofn, PrintWriter output) {
2180 output.println("/* FlatOffsetNode */");
2181 FieldDescriptor fd=fofn.getField();
2182 if(!fd.isStatic()) {
2183 output.println(generateTemp(fm, fofn.getDst())+ " = (short)(int) (&((struct "+fofn.getClassType().getSafeSymbol() +" *)0)->"+
2184 fd.getSafeSymbol()+");");
2186 output.println("/* offset */");
2189 public void generateFlatPrefetchNode(FlatMethod fm, FlatPrefetchNode fpn, PrintWriter output) {
2192 public void generateFlatGlobalConvNode(FlatMethod fm, FlatGlobalConvNode fgcn, PrintWriter output) {
2195 public void generateFlatInstanceOfNode(FlatMethod fm, FlatInstanceOfNode fion, PrintWriter output) {
2198 if (fion.getType().isArray()) {
2199 type=state.getArrayNumber(fion.getType())+state.numClasses();
2201 type=fion.getType().getClassDesc().getId();
2203 if (fion.getSrc().getType().isArray()) {
2204 otype=state.getArrayNumber(fion.getSrc().getType())+state.numClasses();
2206 otype=fion.getSrc().getType().getClassDesc().getId();
2209 if (fion.getType().getSymbol().equals(TypeUtil.ObjectClass))
2210 output.println(generateTemp(fm, fion.getDst())+"=(" + generateTemp(fm,fion.getSrc()) + "!= NULL);");
2212 output.println(generateTemp(fm, fion.getDst())+"=instanceof("+generateTemp(fm,fion.getSrc())+","+type+");");
2216 public void generateFlatAtomicEnterNode(FlatMethod fm, FlatAtomicEnterNode faen, PrintWriter output) {
2219 public void generateFlatAtomicExitNode(FlatMethod fm, FlatAtomicExitNode faen, PrintWriter output) {
2222 public void generateFlatSESEEnterNode(FlatMethod fm,
2223 FlatSESEEnterNode fsen,
2224 PrintWriter output) {
2225 // if OOOJAVA flag is off, okay that SESE nodes are in IR graph,
2226 // just skip over them and code generates exactly the same
2229 public void generateFlatSESEExitNode(FlatMethod fm,
2230 FlatSESEExitNode fsexn,
2231 PrintWriter output) {
2232 // if OOOJAVA flag is off, okay that SESE nodes are in IR graph,
2233 // just skip over them and code generates exactly the same
2236 public void generateFlatWriteDynamicVarNode(FlatMethod fm,
2237 FlatWriteDynamicVarNode fwdvn,
2238 PrintWriter output) {
2242 protected void generateFlatCheckNode(FlatMethod fm, FlatCheckNode fcn, PrintWriter output) {
2243 if (state.CONSCHECK) {
2244 String specname=fcn.getSpec();
2245 String varname="repairstate___";
2246 output.println("{");
2247 output.println("struct "+specname+"_state * "+varname+"=allocate"+specname+"_state();");
2249 TempDescriptor[] temps=fcn.getTemps();
2250 String[] vars=fcn.getVars();
2251 for(int i=0; i<temps.length; i++) {
2252 output.println(varname+"->"+vars[i]+"=(unsigned int)"+generateTemp(fm, temps[i])+";");
2255 output.println("if (doanalysis"+specname+"("+varname+")) {");
2256 output.println("free"+specname+"_state("+varname+");");
2257 output.println("} else {");
2258 output.println("/* Bad invariant */");
2259 output.println("free"+specname+"_state("+varname+");");
2260 output.println("abort_task();");
2261 output.println("}");
2262 output.println("}");
2266 protected void generateFlatCall(FlatMethod fm, FlatCall fc, PrintWriter output) {
2267 MethodDescriptor md=fc.getMethod();
2268 ParamsObject objectparams=(ParamsObject)paramstable.get(md);
2269 ClassDescriptor cn=md.getClassDesc();
2270 String mdstring = md.getSafeMethodDescriptor();
2271 if(mgcstaticinit && !md.getModifiers().isNative()) {
2272 mdstring += "staticinit";
2275 // if the called method is a static block or a static method or a constructor
2276 // need to check if it can be invoked inside some static block
2277 if((md.isStatic() || md.isStaticBlock() || md.isConstructor()) &&
2278 ((fm.getMethod().isStaticBlock()) || (fm.getMethod().isInvokedByStatic()))) {
2279 if(!md.isInvokedByStatic()) {
2280 System.err.println("Error: a method that is invoked inside a static block is not tagged!");
2282 // is a static block or is invoked in some static block
2283 ClassDescriptor cd = fm.getMethod().getClassDesc();
2285 // the same class, do nothing
2286 } else if(mgcstaticinit) {
2287 // generate static init check code if it has not done static init in main()
2288 if((cn.getNumStaticFields() != 0) || (cn.getNumStaticBlocks() != 0)) {
2289 // need to check if the class' static fields have been initialized and/or
2290 // its static blocks have been executed
2291 output.println("if(global_defsprim_p->" + cn.getSafeSymbol()+"static_block_exe_flag == 0) {");
2292 if(cn.getNumStaticBlocks() != 0) {
2293 MethodDescriptor t_md = (MethodDescriptor)cn.getMethodTable().get("staticblocks");
2294 output.println(" "+cn.getSafeSymbol()+t_md.getSafeSymbol()+"_"+t_md.getSafeMethodDescriptor()+"();");
2296 output.println(" global_defsprim_p->" + cn.getSafeSymbol()+"static_block_exe_flag = 1;");
2298 output.println("}");
2302 if((md.getSymbol().equals("MonitorEnter") || md.getSymbol().equals("MonitorExit")) && fc.getThis().getSymbol().equals("classobj")) {
2303 // call MonitorEnter/MonitorExit on a class obj
2304 output.println(" " + cn.getSafeSymbol()+md.getSafeSymbol()+"_"
2305 + md.getSafeMethodDescriptor() + "((struct ___Object___*)(global_defs_p->"
2306 + fc.getThis().getType().getClassDesc().getSafeSymbol() +"classobj));");
2310 output.println("{");
2311 if ((GENERATEPRECISEGC) || (this.state.MULTICOREGC)) {
2312 output.print(" struct "+cn.getSafeSymbol()+md.getSafeSymbol()+"_"+mdstring+"_params __parameterlist__={");
2313 output.print(objectparams.numPointers());
2314 output.print(", "+localsprefixaddr);
2315 if (md.getThis()!=null) {
2317 output.print("(struct "+md.getThis().getType().getSafeSymbol() +" *)"+ generateTemp(fm,fc.getThis()));
2319 if (fc.getThis()!=null&&md.getThis()==null) {
2320 System.out.println("WARNING!!!!!!!!!!!!");
2321 System.out.println("Source code calls static method "+md+" on an object in "+fm.getMethod()+"!");
2325 for(int i=0; i<fc.numArgs(); i++) {
2326 Descriptor var=md.getParameter(i);
2327 TempDescriptor paramtemp=(TempDescriptor)temptovar.get(var);
2328 if (objectparams.isParamPtr(paramtemp)) {
2329 TempDescriptor targ=fc.getArg(i);
2331 TypeDescriptor td=md.getParamType(i);
2333 output.print("(struct "+(new TypeDescriptor(typeutil.getClass(TypeUtil.TagClass))).getSafeSymbol() +" *)"+generateTemp(fm, targ));
2335 output.print("(struct "+md.getParamType(i).getSafeSymbol() +" *)"+generateTemp(fm, targ));
2338 output.println("};");
2343 if (fc.getReturnTemp()!=null)
2344 output.print(generateTemp(fm,fc.getReturnTemp())+"=");
2346 /* Do we need to do virtual dispatch? */
2347 if (md.isStatic()||md.getReturnType()==null||singleCall(fc.getThis().getType().getClassDesc(),md)) {
2349 output.print(cn.getSafeSymbol()+md.getSafeSymbol()+"_"+mdstring);
2353 if (md.getReturnType().isClass() && md.getReturnType().getClassDesc().isEnum()) {
2354 output.print("int ");
2355 } else if (md.getReturnType().isClass()||md.getReturnType().isArray())
2356 output.print("struct " + md.getReturnType().getSafeSymbol()+" * ");
2358 output.print(md.getReturnType().getSafeSymbol()+" ");
2359 output.print("(*)(");
2361 boolean printcomma=false;
2362 if ((GENERATEPRECISEGC) || (this.state.MULTICOREGC)) {
2363 output.print("struct "+cn.getSafeSymbol()+md.getSafeSymbol()+"_"+mdstring+"_params * ");
2367 for(int i=0; i<objectparams.numPrimitives(); i++) {
2368 TempDescriptor temp=objectparams.getPrimitive(i);
2372 if (temp.getType().isClass() && temp.getType().getClassDesc().isEnum()) {
2373 output.print("int ");
2374 } else if (temp.getType().isClass()||temp.getType().isArray())
2375 output.print("struct " + temp.getType().getSafeSymbol()+" * ");
2377 output.print(temp.getType().getSafeSymbol());
2381 output.print("))virtualtable["+generateTemp(fm,fc.getThis())+"->type*"+maxcount+"+"+virtualcalls.getMethodNumber(md).elementAt(0)+"])");
2385 boolean needcomma=false;
2386 if ((GENERATEPRECISEGC) || (this.state.MULTICOREGC)) {
2387 output.print("&__parameterlist__");
2391 if (!GENERATEPRECISEGC && !this.state.MULTICOREGC) {
2392 if (fc.getThis()!=null) {
2393 TypeDescriptor ptd=null;
2394 if(md.getThis() != null) {
2395 ptd = md.getThis().getType();
2397 ptd = fc.getThis().getType();
2401 if(ptd.isClass() && ptd.getClassDesc().isEnum()) {
2403 } else if (ptd.isClass()&&!ptd.isArray())
2404 output.print("(struct "+ptd.getSafeSymbol()+" *) ");
2405 output.print(generateTemp(fm,fc.getThis()));
2410 for(int i=0; i<fc.numArgs(); i++) {
2411 Descriptor var=md.getParameter(i);
2412 TempDescriptor paramtemp=(TempDescriptor)temptovar.get(var);
2413 if (objectparams.isParamPrim(paramtemp)) {
2414 TempDescriptor targ=fc.getArg(i);
2418 TypeDescriptor ptd=md.getParamType(i);
2419 if (ptd.isClass() && ptd.getClassDesc().isEnum()) {
2421 } else if (ptd.isClass()&&!ptd.isArray())
2422 output.print("(struct "+ptd.getSafeSymbol()+" *) ");
2423 output.print(generateTemp(fm, targ));
2427 output.println(");");
2428 output.println(" }");
2431 protected boolean singleCall(ClassDescriptor thiscd, MethodDescriptor md) {
2432 if(thiscd.isInterface()) {
2433 // for interfaces, always need virtual dispatch
2436 Set subclasses=typeutil.getSubClasses(thiscd);
2437 if (subclasses==null)
2439 for(Iterator classit=subclasses.iterator(); classit.hasNext(); ) {
2440 ClassDescriptor cd=(ClassDescriptor)classit.next();
2441 Set possiblematches=cd.getMethodTable().getSetFromSameScope(md.getSymbol());
2442 for(Iterator matchit=possiblematches.iterator(); matchit.hasNext(); ) {
2443 MethodDescriptor matchmd=(MethodDescriptor)matchit.next();
2444 if (md.matches(matchmd))
2452 protected void generateFlatFieldNode(FlatMethod fm, FlatFieldNode ffn, PrintWriter output) {
2453 if(ffn.getField().isStatic()) {
2455 if((fm.getMethod().isStaticBlock()) || (fm.getMethod().isInvokedByStatic())) {
2456 // is a static block or is invoked in some static block
2457 ClassDescriptor cd = fm.getMethod().getClassDesc();
2458 ClassDescriptor cn = ffn.getSrc().getType().getClassDesc();
2460 // the same class, do nothing
2461 } else if(mgcstaticinit) {
2462 // generate the static init check code if has not done the static init in main()
2463 if((cn.getNumStaticFields() != 0) || (cn.getNumStaticBlocks() != 0)) {
2464 // need to check if the class' static fields have been initialized and/or
2465 // its static blocks have been executed
2466 output.println("if(global_defsprim_p->" + cn.getSafeSymbol()+"static_block_exe_flag == 0) {");
2467 if(cn.getNumStaticBlocks() != 0) {
2468 MethodDescriptor t_md = (MethodDescriptor)cn.getMethodTable().get("staticblocks");
2469 output.println(" "+cn.getSafeSymbol()+t_md.getSafeSymbol()+"_"+t_md.getSafeMethodDescriptor()+"();");
2471 output.println(" global_defsprim_p->" + cn.getSafeSymbol()+"static_block_exe_flag = 1;");
2473 output.println("}");
2477 // redirect to the global_defs_p structure
2478 if((ffn.getField().isStatic()) || (ffn.getSrc().getType().isClassNameRef())) {
2479 // reference to the static field with Class name
2480 if (ffn.getField().getType().isPtr())
2481 output.println(generateTemp(fm, ffn.getDst())+"=global_defs_p->"+ffn.getField().getSafeSymbol()+";");
2483 output.println(generateTemp(fm, ffn.getDst())+"=global_defsprim_p->"+ffn.getField().getSafeSymbol()+";");
2485 output.println(generateTemp(fm, ffn.getDst())+"=*"+ generateTemp(fm,ffn.getSrc())+"->"+ ffn.getField().getSafeSymbol()+";");
2487 } else if (ffn.getField().isEnum()) {
2488 // an Enum value, directly replace the field access as int
2489 output.println(generateTemp(fm, ffn.getDst()) + "=" + ffn.getField().enumValue() + ";");
2491 output.println(generateTemp(fm, ffn.getDst())+"="+ generateTemp(fm,ffn.getSrc())+"->"+ ffn.getField().getSafeSymbol()+";");
2496 protected void generateFlatSetFieldNode(FlatMethod fm, FlatSetFieldNode fsfn, PrintWriter output) {
2497 if (fsfn.getField().getSymbol().equals("length")&&fsfn.getDst().getType().isArray())
2498 throw new Error("Can't set array length");
2499 if (state.FASTCHECK) {
2500 String dst=generateTemp(fm, fsfn.getDst());
2501 output.println("if(!"+dst+"->"+localcopystr+") {");
2502 /* Link object into list */
2503 if (GENERATEPRECISEGC || this.state.MULTICOREGC)
2504 output.println("COPY_OBJ((struct garbagelist *)"+localsprefixaddr+",(struct ___Object___ *)"+dst+");");
2506 output.println("COPY_OBJ("+dst+");");
2507 output.println(dst+"->"+nextobjstr+"="+fcrevert+";");
2508 output.println(fcrevert+"=(struct ___Object___ *)"+dst+";");
2509 output.println("}");
2512 if(fsfn.getField().isStatic()) {
2514 if((fm.getMethod().isStaticBlock()) || (fm.getMethod().isInvokedByStatic()/* && mgcstaticinit*/)) {
2515 // is a static block or is invoked in some static block
2516 ClassDescriptor cd = fm.getMethod().getClassDesc();
2517 ClassDescriptor cn = fsfn.getDst().getType().getClassDesc();
2519 // the same class, do nothing
2520 } else if(mgcstaticinit){
2521 // generate static init check code if has not done the static init in main()
2522 if((cn.getNumStaticFields() != 0) || (cn.getNumStaticBlocks() != 0)) {
2523 // need to check if the class' static fields have been initialized and/or
2524 // its static blocks have been executed
2525 output.println("if(global_defsprim_p->" + cn.getSafeSymbol()+"static_block_exe_flag == 0) {");
2526 if(cn.getNumStaticBlocks() != 0) {
2527 MethodDescriptor t_md = (MethodDescriptor)cn.getMethodTable().get("staticblocks");
2528 output.println(" "+cn.getSafeSymbol()+t_md.getSafeSymbol()+"_"+t_md.getSafeMethodDescriptor()+"();");
2530 output.println(" global_defsprim_p->" + cn.getSafeSymbol()+"static_block_exe_flag = 1;");
2532 output.println("}");
2536 // redirect to the global_defs_p structure
2537 if((fsfn.getDst().getType().isClassNameRef()) || (fsfn.getField().isStatic())) {
2538 // reference to the static field with Class name
2539 if (fsfn.getField().getType().isPtr())
2540 output.println("global_defs_p->" +
2541 fsfn.getField().getSafeSymbol()+"="+ generateTemp(fm,fsfn.getSrc())+";");
2543 output.println("global_defsprim_p->" +
2544 fsfn.getField().getSafeSymbol()+"="+ generateTemp(fm,fsfn.getSrc())+";");
2546 output.println("*"+generateTemp(fm, fsfn.getDst())+"->"+
2547 fsfn.getField().getSafeSymbol()+"="+ generateTemp(fm,fsfn.getSrc())+";");
2550 output.println(generateTemp(fm, fsfn.getDst())+"->"+
2551 fsfn.getField().getSafeSymbol()+"="+ generateTemp(fm,fsfn.getSrc())+";");
2556 protected void generateFlatElementNode(FlatMethod fm, FlatElementNode fen, PrintWriter output) {
2557 TypeDescriptor elementtype=fen.getSrc().getType().dereference();
2560 if (elementtype.isClass() && elementtype.getClassDesc().isEnum()) {
2562 } else if (elementtype.isArray()||elementtype.isClass())
2565 type=elementtype.getSafeSymbol()+" ";
2567 if (this.state.ARRAYBOUNDARYCHECK && fen.needsBoundsCheck()) {
2568 output.println("if (unlikely(((unsigned int)"+generateTemp(fm, fen.getIndex())+") >= "+generateTemp(fm,fen.getSrc()) + "->___length___))");
2569 output.println("failedboundschk();");
2571 output.println(generateTemp(fm, fen.getDst())+"=(("+ type+"*)(((char *) &("+ generateTemp(fm,fen.getSrc())+"->___length___))+sizeof(int)))["+generateTemp(fm, fen.getIndex())+"];");
2574 protected void generateFlatSetElementNode(FlatMethod fm, FlatSetElementNode fsen, PrintWriter output) {
2575 //TODO: need dynamic check to make sure this assignment is actually legal
2576 //Because Object[] could actually be something more specific...ie. Integer[]
2578 TypeDescriptor elementtype=fsen.getDst().getType().dereference();
2581 if (elementtype.isClass() && elementtype.getClassDesc().isEnum()) {
2583 } else if (elementtype.isArray()||elementtype.isClass() || (elementtype.isNull()))
2586 type=elementtype.getSafeSymbol()+" ";
2588 if (this.state.ARRAYBOUNDARYCHECK && fsen.needsBoundsCheck()) {
2589 output.println("if (unlikely(((unsigned int)"+generateTemp(fm, fsen.getIndex())+") >= "+generateTemp(fm,fsen.getDst()) + "->___length___))");
2590 output.println("failedboundschk();");
2592 if (state.FASTCHECK) {
2593 String dst=generateTemp(fm, fsen.getDst());
2594 output.println("if(!"+dst+"->"+localcopystr+") {");
2595 /* Link object into list */
2596 if (GENERATEPRECISEGC || this.state.MULTICOREGC)
2597 output.println("COPY_OBJ((struct garbagelist *)"+localsprefixaddr+",(struct ___Object___ *)"+dst+");");
2599 output.println("COPY_OBJ("+dst+");");
2600 output.println(dst+"->"+nextobjstr+"="+fcrevert+";");
2601 output.println(fcrevert+"=(struct ___Object___ *)"+dst+";");
2602 output.println("}");
2604 output.println("(("+type +"*)(((char *) &("+ generateTemp(fm,fsen.getDst())+"->___length___))+sizeof(int)))["+generateTemp(fm, fsen.getIndex())+"]="+generateTemp(fm,fsen.getSrc())+";");
2608 protected void generateFlatNew(FlatMethod fm, FlatNew fn, PrintWriter output) {
2609 if (fn.getType().isArray()) {
2610 int arrayid=state.getArrayNumber(fn.getType())+state.numClasses();
2611 if ((GENERATEPRECISEGC) || (this.state.MULTICOREGC)) {
2612 output.println(generateTemp(fm,fn.getDst())+"=allocate_newarray("+localsprefixaddr+", "+arrayid+", "+generateTemp(fm, fn.getSize())+");");
2614 output.println(generateTemp(fm,fn.getDst())+"=allocate_newarray("+arrayid+", "+generateTemp(fm, fn.getSize())+");");
2617 if ((GENERATEPRECISEGC) || (this.state.MULTICOREGC)) {
2618 output.println(generateTemp(fm,fn.getDst())+"=allocate_new("+localsprefixaddr+", "+fn.getType().getClassDesc().getId()+");");
2620 output.println(generateTemp(fm,fn.getDst())+"=allocate_new("+fn.getType().getClassDesc().getId()+");");
2623 if (state.FASTCHECK) {
2624 String dst=generateTemp(fm,fn.getDst());
2625 output.println(dst+"->___localcopy___=(struct ___Object___*)1;");
2626 output.println(dst+"->"+nextobjstr+"="+fcrevert+";");
2627 output.println(fcrevert+"=(struct ___Object___ *)"+dst+";");
2631 protected void generateFlatTagDeclaration(FlatMethod fm, FlatTagDeclaration fn, PrintWriter output) {
2632 if ((GENERATEPRECISEGC) || (this.state.MULTICOREGC)) {
2633 output.println(generateTemp(fm,fn.getDst())+"=allocate_tag("+localsprefixaddr+", "+state.getTagId(fn.getType())+");");
2635 output.println(generateTemp(fm,fn.getDst())+"=allocate_tag("+state.getTagId(fn.getType())+");");
2639 protected void generateFlatOpNode(FlatMethod fm, FlatOpNode fon, PrintWriter output) {
2640 if (fon.getRight()!=null) {
2641 if (fon.getOp().getOp()==Operation.URIGHTSHIFT) {
2642 if (fon.getLeft().getType().isLong())
2643 output.println(generateTemp(fm, fon.getDest())+" = ((unsigned long long)"+generateTemp(fm, fon.getLeft())+")>>"+generateTemp(fm,fon.getRight())+";");
2645 output.println(generateTemp(fm, fon.getDest())+" = ((unsigned int)"+generateTemp(fm, fon.getLeft())+")>>"+generateTemp(fm,fon.getRight())+";");
2648 output.println(generateTemp(fm, fon.getDest())+" = "+generateTemp(fm, fon.getLeft())+fon.getOp().toString()+generateTemp(fm,fon.getRight())+";");
2649 } else if (fon.getOp().getOp()==Operation.ASSIGN)
2650 output.println(generateTemp(fm, fon.getDest())+" = "+generateTemp(fm, fon.getLeft())+";");
2651 else if (fon.getOp().getOp()==Operation.UNARYPLUS)
2652 output.println(generateTemp(fm, fon.getDest())+" = "+generateTemp(fm, fon.getLeft())+";");
2653 else if (fon.getOp().getOp()==Operation.UNARYMINUS)
2654 output.println(generateTemp(fm, fon.getDest())+" = -"+generateTemp(fm, fon.getLeft())+";");
2655 else if (fon.getOp().getOp()==Operation.LOGIC_NOT)
2656 output.println(generateTemp(fm, fon.getDest())+" = !"+generateTemp(fm, fon.getLeft())+";");
2657 else if (fon.getOp().getOp()==Operation.COMP)
2658 output.println(generateTemp(fm, fon.getDest())+" = ~"+generateTemp(fm, fon.getLeft())+";");
2659 else if (fon.getOp().getOp()==Operation.ISAVAILABLE) {
2660 output.println(generateTemp(fm, fon.getDest())+" = "+generateTemp(fm, fon.getLeft())+"->fses==NULL;");
2662 output.println(generateTemp(fm, fon.getDest())+fon.getOp().toString()+generateTemp(fm, fon.getLeft())+";");
2665 protected void generateFlatCastNode(FlatMethod fm, FlatCastNode fcn, PrintWriter output) {
2666 /* TODO: Do type check here */
2667 if (fcn.getType().isArray()) {
2668 output.println(generateTemp(fm,fcn.getDst())+"=(struct ArrayObject *)"+generateTemp(fm,fcn.getSrc())+";");
2669 } else if (fcn.getType().isClass() && fcn.getType().getClassDesc().isEnum()) {
2670 output.println(generateTemp(fm,fcn.getDst())+"=(int)"+generateTemp(fm,fcn.getSrc())+";");
2671 } else if (fcn.getType().isClass())
2672 output.println(generateTemp(fm,fcn.getDst())+"=(struct "+fcn.getType().getSafeSymbol()+" *)"+generateTemp(fm,fcn.getSrc())+";");
2674 output.println(generateTemp(fm,fcn.getDst())+"=("+fcn.getType().getSafeSymbol()+")"+generateTemp(fm,fcn.getSrc())+";");
2677 protected void generateFlatLiteralNode(FlatMethod fm, FlatLiteralNode fln, PrintWriter output) {
2678 if (fln.getValue()==null)
2679 output.println(generateTemp(fm, fln.getDst())+"=0;");
2680 else if (fln.getType().getSymbol().equals(TypeUtil.StringClass)) {
2681 if ((GENERATEPRECISEGC) || (this.state.MULTICOREGC)) {
2682 output.println(generateTemp(fm, fln.getDst())+"=NewString("+localsprefixaddr+", \""+FlatLiteralNode.escapeString((String)fln.getValue())+"\","+((String)fln.getValue()).length()+");");
2684 output.println(generateTemp(fm, fln.getDst())+"=NewString(\""+FlatLiteralNode.escapeString((String)fln.getValue())+"\","+((String)fln.getValue()).length()+");");
2686 } else if (fln.getType().isBoolean()) {
2687 if (((Boolean)fln.getValue()).booleanValue())
2688 output.println(generateTemp(fm, fln.getDst())+"=1;");
2690 output.println(generateTemp(fm, fln.getDst())+"=0;");
2691 } else if (fln.getType().isChar()) {
2692 String st=FlatLiteralNode.escapeString(fln.getValue().toString());
2693 output.println(generateTemp(fm, fln.getDst())+"='"+st+"';");
2694 } else if (fln.getType().isLong()) {
2695 output.println(generateTemp(fm, fln.getDst())+"="+fln.getValue()+"LL;");
2697 output.println(generateTemp(fm, fln.getDst())+"="+fln.getValue()+";");
2700 protected void generateFlatReturnNode(FlatMethod fm, FlatReturnNode frn, PrintWriter output) {
2701 if((fm.getMethod() != null) && (fm.getMethod().isStaticBlock())) {
2702 // a static block, check if it has been executed
2703 output.println(" global_defsprim_p->" + fm.getMethod().getClassDesc().getSafeSymbol()+"static_block_exe_flag = 1;");
2707 if (frn.getReturnTemp()!=null) {
2708 if (frn.getReturnTemp().getType().isPtr())
2709 output.println("return (struct "+fm.getMethod().getReturnType().getSafeSymbol()+"*)"+generateTemp(fm, frn.getReturnTemp())+";");
2711 output.println("return "+generateTemp(fm, frn.getReturnTemp())+";");
2713 output.println("return;");
2717 protected void generateFlatCondBranch(FlatMethod fm, FlatCondBranch fcb, String label, PrintWriter output) {
2718 output.println("if (!"+generateTemp(fm, fcb.getTest())+") goto "+label+";");
2721 /** This method generates header information for the method or
2722 * task referenced by the Descriptor des. */
2723 protected void generateHeader(FlatMethod fm, Descriptor des, PrintWriter output) {
2724 generateHeader(fm, des, output, false);
2727 protected void generateHeader(FlatMethod fm, Descriptor des, PrintWriter output, boolean addSESErecord) {
2729 ParamsObject objectparams=(ParamsObject)paramstable.get(des);
2730 MethodDescriptor md=null;
2731 TaskDescriptor task=null;
2732 if (des instanceof MethodDescriptor)
2733 md=(MethodDescriptor) des;
2735 task=(TaskDescriptor) des;
2736 String mdstring = md != null ? md.getSafeMethodDescriptor() : null;
2738 ClassDescriptor cn=md!=null ? md.getClassDesc() : null;
2740 if (md!=null&&md.getReturnType()!=null) {
2741 if (md.getReturnType().isClass() && md.getReturnType().getClassDesc().isEnum()) {
2742 output.print("int ");
2743 } else if (md.getReturnType().isClass()||md.getReturnType().isArray())
2744 output.print("struct " + md.getReturnType().getSafeSymbol()+" * ");
2746 output.print(md.getReturnType().getSafeSymbol()+" ");
2748 //catch the constructor case
2749 output.print("void ");
2752 mdstring += "staticinit";
2754 output.print(cn.getSafeSymbol()+md.getSafeSymbol()+"_"+mdstring+"(");
2756 output.print(task.getSafeSymbol()+"(");
2758 boolean printcomma=false;
2759 if ((GENERATEPRECISEGC) || (this.state.MULTICOREGC)) {
2761 output.print("struct "+cn.getSafeSymbol()+md.getSafeSymbol()+"_"+mdstring+"_params * "+paramsprefix);
2763 output.print("struct "+task.getSafeSymbol()+"_params * "+paramsprefix);
2769 for(int i=0; i<objectparams.numPrimitives(); i++) {
2770 TempDescriptor temp=objectparams.getPrimitive(i);
2774 if(temp.getType().isClass() && temp.getType().getClassDesc().isEnum()) {
2775 output.print("int " + temp.getSafeSymbol());
2776 } else if (temp.getType().isClass()||temp.getType().isArray())
2777 output.print("struct "+temp.getType().getSafeSymbol()+" * "+temp.getSafeSymbol());
2779 output.print(temp.getType().getSafeSymbol()+" "+temp.getSafeSymbol());
2781 output.println(") {");
2782 } else if (!GENERATEPRECISEGC && !this.state.MULTICOREGC) {
2783 /* Imprecise Task */
2784 output.println("void * parameterarray[]) {");
2785 /* Unpack variables */
2786 for(int i=0; i<objectparams.numPrimitives(); i++) {
2787 TempDescriptor temp=objectparams.getPrimitive(i);
2788 if(temp.getType().isClass() && temp.getType().getClassDesc().isEnum()) {
2789 output.print("int " + temp.getSafeSymbol() + "=parameterarray["+i+"];");
2791 output.println("struct "+temp.getType().getSafeSymbol()+" * "+temp.getSafeSymbol()+"=parameterarray["+i+"];");
2794 for(int i=0; i<fm.numTags(); i++) {
2795 TempDescriptor temp=fm.getTag(i);
2796 int offset=i+objectparams.numPrimitives();
2797 output.println("struct ___TagDescriptor___ * "+temp.getSafeSymbol()+"=parameterarray["+offset+"];");
2800 if ((objectparams.numPrimitives()+fm.numTags())>maxtaskparams)
2801 maxtaskparams=objectparams.numPrimitives()+fm.numTags();
2802 } else output.println(") {");
2805 public void generateFlatFlagActionNode(FlatMethod fm, FlatFlagActionNode ffan, PrintWriter output) {
2806 output.println("/* FlatFlagActionNode */");
2809 /* Process tag changes */
2810 Relation tagsettable=new Relation();
2811 Relation tagcleartable=new Relation();
2813 Iterator tagsit=ffan.getTempTagPairs();
2814 while (tagsit.hasNext()) {
2815 TempTagPair ttp=(TempTagPair) tagsit.next();
2816 TempDescriptor objtmp=ttp.getTemp();
2817 TagDescriptor tag=ttp.getTag();
2818 TempDescriptor tagtmp=ttp.getTagTemp();
2819 boolean tagstatus=ffan.getTagChange(ttp);
2821 tagsettable.put(objtmp, tagtmp);
2823 tagcleartable.put(objtmp, tagtmp);
2828 Hashtable flagandtable=new Hashtable();
2829 Hashtable flagortable=new Hashtable();
2831 /* Process flag changes */
2832 Iterator flagsit=ffan.getTempFlagPairs();
2833 while(flagsit.hasNext()) {
2834 TempFlagPair tfp=(TempFlagPair)flagsit.next();
2835 TempDescriptor temp=tfp.getTemp();
2836 Hashtable flagtable=(Hashtable)flagorder.get(temp.getType().getClassDesc());
2837 FlagDescriptor flag=tfp.getFlag();
2839 //Newly allocate objects that don't set any flags case
2840 if (flagortable.containsKey(temp)) {
2844 flagortable.put(temp,new Integer(mask));
2846 int flagid=1<<((Integer)flagtable.get(flag)).intValue();
2847 boolean flagstatus=ffan.getFlagChange(tfp);
2850 if (flagortable.containsKey(temp)) {
2851 mask=((Integer)flagortable.get(temp)).intValue();
2854 flagortable.put(temp,new Integer(mask));
2856 int mask=0xFFFFFFFF;
2857 if (flagandtable.containsKey(temp)) {
2858 mask=((Integer)flagandtable.get(temp)).intValue();
2860 mask&=(0xFFFFFFFF^flagid);
2861 flagandtable.put(temp,new Integer(mask));
2867 HashSet flagtagset=new HashSet();
2868 flagtagset.addAll(flagortable.keySet());
2869 flagtagset.addAll(flagandtable.keySet());
2870 flagtagset.addAll(tagsettable.keySet());
2871 flagtagset.addAll(tagcleartable.keySet());
2873 Iterator ftit=flagtagset.iterator();
2874 while(ftit.hasNext()) {
2875 TempDescriptor temp=(TempDescriptor)ftit.next();
2878 Set tagtmps=tagcleartable.get(temp);
2879 if (tagtmps!=null) {
2880 Iterator tagit=tagtmps.iterator();
2881 while(tagit.hasNext()) {
2882 TempDescriptor tagtmp=(TempDescriptor)tagit.next();
2883 if ((GENERATEPRECISEGC) || (this.state.MULTICOREGC))
2884 output.println("tagclear("+localsprefixaddr+", (struct ___Object___ *)"+generateTemp(fm, temp)+", "+generateTemp(fm,tagtmp)+");");
2886 output.println("tagclear((struct ___Object___ *)"+generateTemp(fm, temp)+", "+generateTemp(fm,tagtmp)+");");
2890 tagtmps=tagsettable.get(temp);
2891 if (tagtmps!=null) {
2892 Iterator tagit=tagtmps.iterator();
2893 while(tagit.hasNext()) {
2894 TempDescriptor tagtmp=(TempDescriptor)tagit.next();
2895 if ((GENERATEPRECISEGC) || (this.state.MULTICOREGC))
2896 output.println("tagset("+localsprefixaddr+", (struct ___Object___ *)"+generateTemp(fm, temp)+", "+generateTemp(fm,tagtmp)+");");
2898 output.println("tagset((struct ___Object___ *)"+generateTemp(fm, temp)+", "+generateTemp(fm,tagtmp)+");");
2903 int andmask=0xFFFFFFF;
2905 if (flagortable.containsKey(temp))
2906 ormask=((Integer)flagortable.get(temp)).intValue();
2907 if (flagandtable.containsKey(temp))
2908 andmask=((Integer)flagandtable.get(temp)).intValue();
2909 generateFlagOrAnd(ffan, fm, temp, output, ormask, andmask);
2910 generateObjectDistribute(ffan, fm, temp, output);
2914 protected void generateFlagOrAnd(FlatFlagActionNode ffan, FlatMethod fm, TempDescriptor temp,
2915 PrintWriter output, int ormask, int andmask) {
2916 if (ffan.getTaskType()==FlatFlagActionNode.NEWOBJECT) {
2917 output.println("flagorandinit("+generateTemp(fm, temp)+", 0x"+Integer.toHexString(ormask)+", 0x"+Integer.toHexString(andmask)+");");
2919 output.println("flagorand("+generateTemp(fm, temp)+", 0x"+Integer.toHexString(ormask)+", 0x"+Integer.toHexString(andmask)+");");
2923 protected void generateObjectDistribute(FlatFlagActionNode ffan, FlatMethod fm, TempDescriptor temp, PrintWriter output) {
2924 output.println("enqueueObject("+generateTemp(fm, temp)+");");
2927 void generateOptionalHeader(PrintWriter headers) {
2930 headers.println("#include \"task.h\"\n\n");
2931 headers.println("#ifndef _OPTIONAL_STRUCT_");
2932 headers.println("#define _OPTIONAL_STRUCT_");
2934 //STRUCT PREDICATEMEMBER
2935 headers.println("struct predicatemember{");
2936 headers.println("int type;");
2937 headers.println("int numdnfterms;");
2938 headers.println("int * flags;");
2939 headers.println("int numtags;");
2940 headers.println("int * tags;\n};\n\n");
2942 //STRUCT OPTIONALTASKDESCRIPTOR
2943 headers.println("struct optionaltaskdescriptor{");
2944 headers.println("struct taskdescriptor * task;");
2945 headers.println("int index;");
2946 headers.println("int numenterflags;");
2947 headers.println("int * enterflags;");
2948 headers.println("int numpredicatemembers;");
2949 headers.println("struct predicatemember ** predicatememberarray;");
2950 headers.println("};\n\n");
2952 //STRUCT TASKFAILURE
2953 headers.println("struct taskfailure {");
2954 headers.println("struct taskdescriptor * task;");
2955 headers.println("int index;");
2956 headers.println("int numoptionaltaskdescriptors;");
2957 headers.println("struct optionaltaskdescriptor ** optionaltaskdescriptorarray;\n};\n\n");
2959 //STRUCT FSANALYSISWRAPPER
2960 headers.println("struct fsanalysiswrapper{");
2961 headers.println("int flags;");
2962 headers.println("int numtags;");
2963 headers.println("int * tags;");
2964 headers.println("int numtaskfailures;");
2965 headers.println("struct taskfailure ** taskfailurearray;");
2966 headers.println("int numoptionaltaskdescriptors;");
2967 headers.println("struct optionaltaskdescriptor ** optionaltaskdescriptorarray;\n};\n\n");
2969 //STRUCT CLASSANALYSISWRAPPER
2970 headers.println("struct classanalysiswrapper{");
2971 headers.println("int type;");
2972 headers.println("int numotd;");
2973 headers.println("struct optionaltaskdescriptor ** otdarray;");
2974 headers.println("int numfsanalysiswrappers;");
2975 headers.println("struct fsanalysiswrapper ** fsanalysiswrapperarray;\n};");
2977 headers.println("extern struct classanalysiswrapper * classanalysiswrapperarray[];");
2979 Iterator taskit=state.getTaskSymbolTable().getDescriptorsIterator();
2980 while(taskit.hasNext()) {
2981 TaskDescriptor td=(TaskDescriptor)taskit.next();
2982 headers.println("extern struct taskdescriptor task_"+td.getSafeSymbol()+";");
2987 //CHECK OVER THIS -- THERE COULD BE SOME ERRORS HERE
2988 int generateOptionalPredicate(Predicate predicate, OptionalTaskDescriptor otd, ClassDescriptor cdtemp, PrintWriter output) {
2989 int predicateindex = 0;
2990 //iterate through the classes concerned by the predicate
2991 Set c_vard = predicate.vardescriptors;
2992 Hashtable<TempDescriptor, Integer> slotnumber=new Hashtable<TempDescriptor, Integer>();
2995 for(Iterator vard_it = c_vard.iterator(); vard_it.hasNext(); ) {
2996 VarDescriptor vard = (VarDescriptor)vard_it.next();
2997 TypeDescriptor typed = vard.getType();
2999 //generate for flags
3000 HashSet fen_hashset = predicate.flags.get(vard.getSymbol());
3001 output.println("int predicateflags_"+predicateindex+"_OTD"+otd.getuid()+"_"+cdtemp.getSafeSymbol()+"[]={");
3003 if (fen_hashset!=null) {
3004 for (Iterator fen_it = fen_hashset.iterator(); fen_it.hasNext(); ) {
3005 FlagExpressionNode fen = (FlagExpressionNode)fen_it.next();
3007 DNFFlag dflag=fen.getDNF();
3008 numberterms+=dflag.size();
3010 Hashtable flags=(Hashtable)flagorder.get(typed.getClassDesc());
3012 for(int j=0; j<dflag.size(); j++) {
3014 output.println(",");
3015 Vector term=dflag.get(j);
3018 for(int k=0; k<term.size(); k++) {
3019 DNFFlagAtom dfa=(DNFFlagAtom)term.get(k);
3020 FlagDescriptor fd=dfa.getFlag();
3021 boolean negated=dfa.getNegated();
3022 int flagid=1<<((Integer)flags.get(fd)).intValue();
3027 output.print("/*andmask*/0x"+Integer.toHexString(andmask)+", /*checkmask*/0x"+Integer.toHexString(checkmask));
3032 output.println("};\n");
3035 TagExpressionList tagel = predicate.tags.get(vard.getSymbol());
3036 output.println("int predicatetags_"+predicateindex+"_OTD"+otd.getuid()+"_"+cdtemp.getSafeSymbol()+"[]={");
3039 for(int j=0; j<tagel.numTags(); j++) {
3041 output.println(",");
3042 TempDescriptor tmp=tagel.getTemp(j);
3043 if (!slotnumber.containsKey(tmp)) {
3044 Integer slotint=new Integer(current_slot++);
3045 slotnumber.put(tmp,slotint);
3047 int slot=slotnumber.get(tmp).intValue();
3048 output.println("/* slot */"+ slot+", /*tagid*/"+state.getTagId(tmp.getTag()));
3050 numtags = tagel.numTags();
3052 output.println("};");
3054 //store the result into a predicatemember struct
3055 output.println("struct predicatemember predicatemember_"+predicateindex+"_OTD"+otd.getuid()+"_"+cdtemp.getSafeSymbol()+"={");
3056 output.println("/*type*/"+typed.getClassDesc().getId()+",");
3057 output.println("/* number of dnf terms */"+numberterms+",");
3058 output.println("predicateflags_"+predicateindex+"_OTD"+otd.getuid()+"_"+cdtemp.getSafeSymbol()+",");
3059 output.println("/* number of tag */"+numtags+",");
3060 output.println("predicatetags_"+predicateindex+"_OTD"+otd.getuid()+"_"+cdtemp.getSafeSymbol()+",");
3061 output.println("};\n");
3066 //generate an array that stores the entire predicate
3067 output.println("struct predicatemember * predicatememberarray_OTD"+otd.getuid()+"_"+cdtemp.getSafeSymbol()+"[]={");
3068 for( int j = 0; j<predicateindex; j++) {
3069 if( j != predicateindex-1) output.println("&predicatemember_"+j+"_OTD"+otd.getuid()+"_"+cdtemp.getSafeSymbol()+",");
3070 else output.println("&predicatemember_"+j+"_OTD"+otd.getuid()+"_"+cdtemp.getSafeSymbol());
3072 output.println("};\n");
3073 return predicateindex;
3077 void generateOptionalArrays(PrintWriter output, PrintWriter headers, Hashtable<ClassDescriptor, Hashtable<FlagState, Set<OptionalTaskDescriptor>>> safeexecution, Hashtable optionaltaskdescriptors) {
3078 generateOptionalHeader(headers);
3080 output.println("#include \"optionalstruct.h\"\n\n");
3081 output.println("#include \"stdlib.h\"\n");
3083 HashSet processedcd = new HashSet();
3085 Enumeration e = safeexecution.keys();
3086 while (e.hasMoreElements()) {
3089 ClassDescriptor cdtemp=(ClassDescriptor)e.nextElement();
3090 Hashtable flaginfo=(Hashtable)flagorder.get(cdtemp); //will be used several times
3092 //Generate the struct of optionals
3093 Collection c_otd = ((Hashtable)optionaltaskdescriptors.get(cdtemp)).values();
3094 numotd = c_otd.size();
3095 if(maxotd<numotd) maxotd = numotd;
3096 if( !c_otd.isEmpty() ) {
3097 for(Iterator otd_it = c_otd.iterator(); otd_it.hasNext(); ) {
3098 OptionalTaskDescriptor otd = (OptionalTaskDescriptor)otd_it.next();
3100 //generate the int arrays for the predicate
3101 Predicate predicate = otd.predicate;
3102 int predicateindex = generateOptionalPredicate(predicate, otd, cdtemp, output);
3103 TreeSet<Integer> fsset=new TreeSet<Integer>();
3104 //iterate through possible FSes corresponding to
3105 //the state when entering
3107 for(Iterator fses = otd.enterflagstates.iterator(); fses.hasNext(); ) {
3108 FlagState fs = (FlagState)fses.next();
3110 for(Iterator flags = fs.getFlags(); flags.hasNext(); ) {
3111 FlagDescriptor flagd = (FlagDescriptor)flags.next();
3112 int id=1<<((Integer)flaginfo.get(flagd)).intValue();
3115 fsset.add(new Integer(flagid));
3116 //tag information not needed because tag
3117 //changes are not tolerated.
3120 output.println("int enterflag_OTD"+otd.getuid()+"_"+cdtemp.getSafeSymbol()+"[]={");
3121 boolean needcomma=false;
3122 for(Iterator<Integer> it=fsset.iterator(); it.hasNext(); ) {
3125 output.println(it.next());
3128 output.println("};\n");
3131 //generate optionaltaskdescriptor that actually
3132 //includes exit fses, predicate and the task
3134 output.println("struct optionaltaskdescriptor optionaltaskdescriptor_"+otd.getuid()+"_"+cdtemp.getSafeSymbol()+"={");
3135 output.println("&task_"+otd.td.getSafeSymbol()+",");
3136 output.println("/*index*/"+otd.getIndex()+",");
3137 output.println("/*number of enter flags*/"+fsset.size()+",");
3138 output.println("enterflag_OTD"+otd.getuid()+"_"+cdtemp.getSafeSymbol()+",");
3139 output.println("/*number of members */"+predicateindex+",");
3140 output.println("predicatememberarray_OTD"+otd.getuid()+"_"+cdtemp.getSafeSymbol()+",");
3141 output.println("};\n");
3145 // if there are no optionals, there is no need to build the rest of the struct
3147 output.println("struct optionaltaskdescriptor * otdarray"+cdtemp.getSafeSymbol()+"[]={");
3148 c_otd = ((Hashtable)optionaltaskdescriptors.get(cdtemp)).values();
3149 if( !c_otd.isEmpty() ) {
3150 boolean needcomma=false;
3151 for(Iterator otd_it = c_otd.iterator(); otd_it.hasNext(); ) {
3152 OptionalTaskDescriptor otd = (OptionalTaskDescriptor)otd_it.next();
3154 output.println(",");
3156 output.println("&optionaltaskdescriptor_"+otd.getuid()+"_"+cdtemp.getSafeSymbol());
3159 output.println("};\n");
3161 //get all the possible flagstates reachable by an object
3162 Hashtable hashtbtemp = safeexecution.get(cdtemp);
3164 TreeSet fsts=new TreeSet(new FlagComparator(flaginfo));
3165 fsts.addAll(hashtbtemp.keySet());
3166 for(Iterator fsit=fsts.iterator(); fsit.hasNext(); ) {
3167 FlagState fs = (FlagState)fsit.next();
3170 //get the set of OptionalTaskDescriptors corresponding
3171 HashSet<OptionalTaskDescriptor> availabletasks = (HashSet<OptionalTaskDescriptor>)hashtbtemp.get(fs);
3172 //iterate through the OptionalTaskDescriptors and
3173 //store the pointers to the optionals struct (see on
3174 //top) into an array
3176 output.println("struct optionaltaskdescriptor * optionaltaskdescriptorarray_FS"+fscounter+"_"+cdtemp.getSafeSymbol()+"[] = {");
3177 for(Iterator<OptionalTaskDescriptor> mos = ordertd(availabletasks).iterator(); mos.hasNext(); ) {
3178 OptionalTaskDescriptor mm = mos.next();
3180 output.println("&optionaltaskdescriptor_"+mm.getuid()+"_"+cdtemp.getSafeSymbol());
3182 output.println("&optionaltaskdescriptor_"+mm.getuid()+"_"+cdtemp.getSafeSymbol()+",");
3185 output.println("};\n");
3187 //process flag information (what the flag after failure is) so we know what optionaltaskdescriptors to choose.
3190 for(Iterator flags = fs.getFlags(); flags.hasNext(); ) {
3191 FlagDescriptor flagd = (FlagDescriptor)flags.next();
3192 int id=1<<((Integer)flaginfo.get(flagd)).intValue();
3196 //process tag information
3199 boolean first = true;
3200 Enumeration tag_enum = fs.getTags();
3201 output.println("int tags_FS"+fscounter+"_"+cdtemp.getSafeSymbol()+"[]={");
3202 while(tag_enum.hasMoreElements()) {
3204 TagDescriptor tagd = (TagDescriptor)tag_enum.nextElement();
3208 output.println(", ");
3209 output.println("/*tagid*/"+state.getTagId(tagd));
3211 output.println("};");
3213 Set<TaskIndex> tiset=sa.getTaskIndex(fs);
3214 for(Iterator<TaskIndex> itti=tiset.iterator(); itti.hasNext(); ) {
3215 TaskIndex ti=itti.next();
3219 Set<OptionalTaskDescriptor> otdset=sa.getOptions(fs, ti);
3221 output.print("struct optionaltaskdescriptor * optionaltaskfailure_FS"+fscounter+"_"+ti.getTask().getSafeSymbol()+"_"+ti.getIndex()+"_array[] = {");
3222 boolean needcomma=false;
3223 for(Iterator<OptionalTaskDescriptor> otdit=ordertd(otdset).iterator(); otdit.hasNext(); ) {
3224 OptionalTaskDescriptor otd=otdit.next();
3228 output.println("&optionaltaskdescriptor_"+otd.getuid()+"_"+cdtemp.getSafeSymbol());
3230 output.println("};");
3232 output.print("struct taskfailure taskfailure_FS"+fscounter+"_"+ti.getTask().getSafeSymbol()+"_"+ti.getIndex()+" = {");
3233 output.print("&task_"+ti.getTask().getSafeSymbol()+", ");
3234 output.print(ti.getIndex()+", ");
3235 output.print(otdset.size()+", ");
3236 output.print("optionaltaskfailure_FS"+fscounter+"_"+ti.getTask().getSafeSymbol()+"_"+ti.getIndex()+"_array");
3237 output.println("};");
3240 tiset=sa.getTaskIndex(fs);
3241 boolean needcomma=false;
3243 output.println("struct taskfailure * taskfailurearray"+fscounter+"_"+cdtemp.getSafeSymbol()+"[]={");
3244 for(Iterator<TaskIndex> itti=tiset.iterator(); itti.hasNext(); ) {
3245 TaskIndex ti=itti.next();
3246 if (ti.isRuntime()) {
3253 output.print("&taskfailure_FS"+fscounter+"_"+ti.getTask().getSafeSymbol()+"_"+ti.getIndex());
3255 output.println("};\n");
3257 //Store the result in fsanalysiswrapper
3259 output.println("struct fsanalysiswrapper fsanalysiswrapper_FS"+fscounter+"_"+cdtemp.getSafeSymbol()+"={");
3260 output.println("/*flag*/"+flagid+",");
3261 output.println("/* number of tags*/"+tagcounter+",");
3262 output.println("tags_FS"+fscounter+"_"+cdtemp.getSafeSymbol()+",");
3263 output.println("/* numtask failures */"+(tiset.size()-runtimeti)+",");
3264 output.println("taskfailurearray"+fscounter+"_"+cdtemp.getSafeSymbol()+",");
3265 output.println("/* number of optionaltaskdescriptors */"+availabletasks.size()+",");
3266 output.println("optionaltaskdescriptorarray_FS"+fscounter+"_"+cdtemp.getSafeSymbol());
3267 output.println("};\n");
3271 //Build the array of fsanalysiswrappers
3272 output.println("struct fsanalysiswrapper * fsanalysiswrapperarray_"+cdtemp.getSafeSymbol()+"[] = {");
3273 boolean needcomma=false;
3274 for(int i = 0; i<fscounter; i++) {
3275 if (needcomma) output.print(",");
3276 output.println("&fsanalysiswrapper_FS"+(i+1)+"_"+cdtemp.getSafeSymbol());
3279 output.println("};");
3281 //Build the classanalysiswrapper referring to the previous array
3282 output.println("struct classanalysiswrapper classanalysiswrapper_"+cdtemp.getSafeSymbol()+"={");
3283 output.println("/*type*/"+cdtemp.getId()+",");
3284 output.println("/*numotd*/"+numotd+",");
3285 output.println("otdarray"+cdtemp.getSafeSymbol()+",");
3286 output.println("/* number of fsanalysiswrappers */"+fscounter+",");
3287 output.println("fsanalysiswrapperarray_"+cdtemp.getSafeSymbol()+"};\n");
3288 processedcd.add(cdtemp);
3291 //build an array containing every classes for which code has been build
3292 output.println("struct classanalysiswrapper * classanalysiswrapperarray[]={");
3293 for(int i=0; i<state.numClasses(); i++) {
3294 ClassDescriptor cn=cdarray[i];
3297 if ((cn != null) && (processedcd.contains(cn)))
3298 output.print("&classanalysiswrapper_"+cn.getSafeSymbol());
3300 output.print("NULL");
3302 output.println("};");
3304 output.println("#define MAXOTD "+maxotd);
3305 headers.println("#endif");
3308 public List<OptionalTaskDescriptor> ordertd(Set<OptionalTaskDescriptor> otdset) {
3309 Relation r=new Relation();
3310 for(Iterator<OptionalTaskDescriptor>otdit=otdset.iterator(); otdit.hasNext(); ) {
3311 OptionalTaskDescriptor otd=otdit.next();
3312 TaskIndex ti=new TaskIndex(otd.td, otd.getIndex());
3316 LinkedList<OptionalTaskDescriptor> l=new LinkedList<OptionalTaskDescriptor>();
3317 for(Iterator it=r.keySet().iterator(); it.hasNext(); ) {
3318 Set s=r.get(it.next());
3319 for(Iterator it2=s.iterator(); it2.hasNext(); ) {
3320 OptionalTaskDescriptor otd=(OptionalTaskDescriptor)it2.next();
3328 // override these methods in a subclass of BuildCode
3329 // to generate code for additional systems
3330 protected void printExtraArrayFields(PrintWriter outclassdefs) {
3332 protected void outputTransCode(PrintWriter output) {
3334 protected void buildCodeSetup() {
3336 protected void generateSizeArrayExtensions(PrintWriter outclassdefs) {
3338 protected void additionalIncludesMethodsHeader(PrintWriter outmethodheader) {
3340 protected void preCodeGenInitialization() {
3342 protected void postCodeGenCleanUp() {
3344 protected void additionalCodeGen(PrintWriter outmethodheader,
3345 PrintWriter outstructs,
3346 PrintWriter outmethod) {
3348 protected void additionalCodeAtTopOfMain(PrintWriter outmethod) {
3350 protected void additionalCodeAtBottomOfMain(PrintWriter outmethod) {
3352 protected void additionalIncludesMethodsImplementation(PrintWriter outmethod) {
3354 protected void additionalIncludesStructsHeader(PrintWriter outstructs) {
3356 protected void additionalClassObjectFields(PrintWriter outclassdefs) {
3358 protected void additionalCodeAtTopMethodsImplementation(PrintWriter outmethod) {
3360 protected void additionalCodeAtTopFlatMethodBody(PrintWriter output, FlatMethod fm) {
3362 protected void additionalCodePreNode(FlatMethod fm, FlatNode fn, PrintWriter output) {
3364 protected void additionalCodePostNode(FlatMethod fm, FlatNode fn, PrintWriter output) {