+
+ void generateOptionalArrays(PrintWriter output, PrintWriter headers, Hashtable<ClassDescriptor, Hashtable<FlagState, HashSet>> safeexecution, Hashtable optionaltaskdescriptors) {
+
+ //GENERATE HEADERS
+ headers.println("#include \"task.h\"\n\n");
+
+
+
+ //STRUCT PREDICATEMEMBER
+ headers.println("struct predicatemember{");
+ headers.println("int type;");
+ headers.println("int numdnfterms;");
+ headers.println("int * flags;");
+ headers.println("int numtags;");
+ headers.println("int * tags;\n};\n\n");
+
+ //STRUCT EXITFLAGSTATE
+ headers.println("struct exitflagstate{");
+ headers.println("int numflags;");
+ headers.println("int * flags;");
+ /*
+ headers.println("int numtags;");
+ headers.println("int * tags;");
+ */
+ headers.println("\n};\n\n");
+
+ //STRUCT EXITSTATES
+ headers.println("struct exitstates{");
+ headers.println("int numexitflagstates;");
+ headers.println("struct exitflagstate * exitflagstatearray;\n};\n\n");
+
+ //STRUCT OPTIONALTASKDESCRIPTOR
+ headers.println("struct optionaltaskdescriptor{");
+ headers.println("struct taskdescriptor * task;");
+ headers.println("int numpredicatemembers;");
+ headers.println("struct predicatemember * predicatememberarray;");
+ headers.println("int numexitstates;");
+ headers.println("struct existates * exitstatesarray;\n};\n\n");
+
+ //STRUCT FSANALYSISWRAPPER
+ headers.println("struct fsanalysiswrapper{");
+ headers.println("int numflags;");
+ headers.println("int * flags;");
+ headers.println("int numtags;");
+ headers.println("int * tags;");
+ headers.println("int numoptionaltaskdescriptors;");
+ headers.println("struct optionaltaskdescriptor * optionaltaskdescriptorarray;\n};\n\n");
+
+ //STRUCT CLASSANALYSISWRAPPER
+ headers.println("struct classanalyiswrapper{");
+ headers.println("int type;");
+ headers.println("int numfsanalysiswrappers;");
+ headers.println("struct fsanalysiswrapper * fsanalysiswrapperarray;\n};\n\n");
+
+ Iterator taskit=state.getTaskSymbolTable().getDescriptorsIterator();
+ while(taskit.hasNext()) {
+ TaskDescriptor td=(TaskDescriptor)taskit.next();
+ headers.println("extern struct taskdescriptor task_"+td.getSafeSymbol()+";");
+ }
+
+
+
+ //GENERATE STRUCTS
+ output.println("#include \"optionalstruct.h\"\n\n");
+ HashSet processedcd = new HashSet();
+
+
+ Enumeration e = safeexecution.keys();
+ while (e.hasMoreElements()) {
+
+ //get the class
+ ClassDescriptor cdtemp=(ClassDescriptor)e.nextElement();
+ Hashtable flaginfo=(Hashtable)flagorder.get(cdtemp);//will be used several times
+
+ //Generate the struct of optionals
+ if((Hashtable)optionaltaskdescriptors.get(cdtemp)==null) System.out.println("Was in cd :"+cdtemp.getSymbol());
+ Collection c_otd = ((Hashtable)optionaltaskdescriptors.get(cdtemp)).values();
+ if( !c_otd.isEmpty() ){
+ for(Iterator otd_it = c_otd.iterator(); otd_it.hasNext();){
+ OptionalTaskDescriptor otd = (OptionalTaskDescriptor)otd_it.next();
+
+ //generate the int arrays for the predicate
+ Predicate predicate = otd.predicate;
+ int predicateindex = 0;
+ //iterate through the classes concerned by the predicate
+ Collection c_vard = predicate.vardescriptors.values();
+ for(Iterator vard_it = c_vard.iterator(); vard_it.hasNext();){
+ VarDescriptor vard = (VarDescriptor)vard_it.next();
+ TypeDescriptor typed = vard.getType();
+
+ //generate for flags
+ HashSet fen_hashset = predicate.flags.get(vard.getSymbol());
+ output.println("int predicateflags_"+predicateindex+"_OTD"+otd.getuid()+"_"+cdtemp.getSafeSymbol()+"[]={");
+ int numberterms=0;
+ if (fen_hashset!=null){
+ for (Iterator fen_it = fen_hashset.iterator(); fen_it.hasNext();){
+ FlagExpressionNode fen = (FlagExpressionNode)fen_it.next();
+ if (fen==null) {
+ //output.println("0x0, 0x0 };");
+ //numberterms+=1;
+ }
+ else {
+
+ DNFFlag dflag=fen.getDNF();
+ numberterms+=dflag.size();
+
+ Hashtable flags=(Hashtable)flagorder.get(typed.getClassDesc());
+
+ for(int j=0;j<dflag.size();j++) {
+ if (j!=0)
+ output.println(",");
+ Vector term=dflag.get(j);
+ int andmask=0;
+ int checkmask=0;
+ for(int k=0;k<term.size();k++) {
+ DNFFlagAtom dfa=(DNFFlagAtom)term.get(k);
+ FlagDescriptor fd=dfa.getFlag();
+ boolean negated=dfa.getNegated();
+ int flagid=1<<((Integer)flags.get(fd)).intValue();
+ andmask|=flagid;
+ if (!negated)
+ checkmask|=flagid;
+ }
+ output.print("/*andmask*/0x"+Integer.toHexString(andmask)+", /*checkmask*/0x"+Integer.toHexString(checkmask));
+ }
+ }
+ }
+ }
+ output.println("};\n");
+
+ //generate for tags
+ TagExpressionList tagel = predicate.tags.get(vard.getSymbol());
+ output.println("int predicatetags_"+predicateindex+"_OTD"+otd.getuid()+"_"+cdtemp.getSafeSymbol()+"[]={");
+ //BUG...added next line to fix, test with any task program
+ int numtags = 0;
+ if (tagel!=null){
+ for(int j=0;j<tagel.numTags();j++) {
+ if (j!=0)
+ output.println(",");
+ /* for each tag we need */
+ /* which slot it is */
+ /* what type it is */
+ //TagVarDescriptor tvd=(TagVarDescriptor)task.getParameterTable().get(tagel.getName(j));
+ TempDescriptor tmp=tagel.getTemp(j);
+ //got rid of slot
+ output.println("/*tagid*/"+state.getTagId(tmp.getTag()));
+ }
+ numtags = tagel.numTags();
+ }
+ output.println("};");
+
+ //store the result into a predicatemember struct
+ output.println("struct predicatemember predicatemember_"+predicateindex+"_OTD"+otd.getuid()+"_"+cdtemp.getSafeSymbol()+"={");
+ output.println("/*type*/"+typed.getClassDesc().getId()+",");
+ output.println("/* number of dnf terms */"+numberterms+",");
+ output.println("predicateflags_"+predicateindex+"_OTD"+otd.getuid()+"_"+cdtemp.getSafeSymbol()+",");
+ output.println("/* number of tag */"+numtags+",");
+ output.println("predicatetags_"+predicateindex+"_OTD"+otd.getuid()+"_"+cdtemp.getSafeSymbol()+",");
+ output.println("};\n");
+ predicateindex++;
+ }
+
+
+ //generate an array that stores the entire predicate
+ output.println("struct predicatemember * predicatememberarray_OTD"+otd.getuid()+"_"+cdtemp.getSafeSymbol()+"[]={");
+ for( int j = 0; j<predicateindex; j++){
+ if( j != predicateindex-1)output.println("&predicatemember_"+j+"_OTD"+otd.getuid()+"_"+cdtemp.getSafeSymbol()+",");
+ else output.println("&predicatemember_"+j+"_OTD"+otd.getuid()+"_"+cdtemp.getSafeSymbol()+"};\n");
+ }
+
+ //generate the struct for possible exitfses
+ HashSet<HashSet> exitfses = otd.exitfses;
+ int exitindex = 0;
+ int nbexit = exitfses.size();
+ int fsnumber;
+
+ //iterate through possible exits
+ for(Iterator exitfseshash = exitfses.iterator(); exitfseshash.hasNext();){
+ HashSet temp_hashset = (HashSet)exitfseshash.next();
+ fsnumber = 0 ;
+
+ //iterate through possible FSes corresponding to the exit
+ for(Iterator exfses = temp_hashset.iterator(); exfses.hasNext();){
+ FlagState fs = (FlagState)exfses.next();
+ fsnumber++;
+ output.println("int flags"+fsnumber+"_EXIT"+exitindex+"_OTD"+otd.getuid()+"_"+cdtemp.getSafeSymbol()+"[]={");
+ int counterflag = 0;
+ for(Iterator flags = fs.getFlags(); flags.hasNext();){
+ FlagDescriptor flagd = (FlagDescriptor)flags.next();
+ int flagid=1<<((Integer)flaginfo.get(flagd)).intValue();
+ if( flags.hasNext() ) output.print("0x"+Integer.toHexString(flagid)+" /*"+Integer.toBinaryString(flagid)+"*/,");
+ else output.print("0x"+Integer.toHexString(flagid)+" /*"+Integer.toBinaryString(flagid)+"*/");
+ counterflag++;
+ }
+ output.println("};\n");
+ //do the same for tags;
+ //maybe not needed because no tag changes tolerated.
+
+ //store the information into a struct
+ output.println("struct exitflagstate exitflagstate"+fsnumber+"_EXIT"+exitindex+"_OTD"+otd.getuid()+"_"+cdtemp.getSafeSymbol()+"={");
+ output.println("/*number of flags*/"+counterflag+",");
+ output.println("flags"+fsnumber+"_EXIT"+exitindex+"_OTD"+otd.getuid()+"_"+cdtemp.getSafeSymbol());
+ output.println("};\n");
+ }
+
+ //store fses corresponding to this exit into an array
+ output.println("struct exitflagstate * exitflagstatearray"+"_EXIT"+exitindex+"_OTD"+otd.getuid()+"_"+cdtemp.getSafeSymbol()+" [] = {");
+ for( int j = 0; j<fsnumber; j++){
+ if( j != fsnumber-1)output.println("&exitflagstate"+(j+1)+"_EXIT"+exitindex+"_OTD"+otd.getuid()+"_"+cdtemp.getSafeSymbol()+"'");
+ else output.println("&exitflagstate"+(j+1)+"_EXIT"+exitindex+"_OTD"+otd.getuid()+"_"+cdtemp.getSafeSymbol()+"};\n");
+ }
+
+ //store that information in a struct
+ output.println("struct exitstates exitstates"+exitindex+"_OTD"+otd.getuid()+"_"+cdtemp.getSafeSymbol()+"={");
+ output.println("/*number of exitflagstate*/"+fsnumber+",");
+ output.println("exitflagstatearray"+"_EXIT"+exitindex+"_OTD"+otd.getuid()+"_"+cdtemp.getSafeSymbol());
+ output.println("};\n");
+
+ exitindex++;
+ }
+
+ //store the information concerning all exits into an array
+ output.println("struct exitstates * exitstatesarray_OTD"+otd.getuid()+"_"+cdtemp.getSafeSymbol()+"[]={");
+ for( int j = 0; j<nbexit; j++){
+ if( j != nbexit-1)output.println("&exitstates"+j+"_OTD"+otd.getuid()+"_"+cdtemp.getSafeSymbol()+",");
+ else output.println("&exitstates"+j+"_OTD"+otd.getuid()+"_"+cdtemp.getSafeSymbol()+"};\n");
+ }
+
+
+ //generate optionaltaskdescriptor that actually includes exit fses, predicate and the task concerned
+ output.println("struct optionaltaskdescriptor optionaltaskdescriptor_"+otd.getuid()+"_"+cdtemp.getSafeSymbol()+"={");
+ output.println("task_"+otd.td.getSafeSymbol()+",");
+ output.println("/*number of members */"+predicateindex+",");
+ output.println("predicatememberarray_OTD"+otd.getuid()+"_"+cdtemp.getSafeSymbol()+",");
+ output.println("/*number of exit fses */"+nbexit+",");
+ output.println("exitstatearray_OTD"+otd.getuid()+"_"+cdtemp.getSafeSymbol());
+ output.println("};\n");
+ }
+ }
+ else continue; // if there is no optionals, there is no need to build the rest of the struct
+
+ //get all the possible falgstates reachable by an object
+ Hashtable hashtbtemp = safeexecution.get(cdtemp);
+ Enumeration fses = hashtbtemp.keys();
+ int fscounter = 0;
+ while(fses.hasMoreElements()){
+ FlagState fs = (FlagState)fses.nextElement();
+ fscounter++;
+
+ //get the set of OptionalTaskDescriptors corresponding
+ HashSet availabletasks = (HashSet)hashtbtemp.get(fs);
+ //iterate through the OptionalTaskDescriptors and store the pointers to the optionals struct (see on top) into an array
+
+ output.println("struct optionaltaskdescriptor * optionaltaskdescriptorarray_FS"+fscounter+"_"+cdtemp.getSafeSymbol()+"[] = {");
+ for(Iterator mos = availabletasks.iterator(); mos.hasNext();){
+ OptionalTaskDescriptor mm = (OptionalTaskDescriptor)mos.next();
+ if(!mos.hasNext()) output.println("&optionaltaskdescriptor_"+mm.getuid()+"_"+cdtemp.getSafeSymbol()+"};\n");
+
+ else output.println("&optionaltaskdescriptor_"+mm.getuid()+"_"+cdtemp.getSafeSymbol()+",");
+ }
+
+ //process flag information (what the flag after failure is) so we know what optionaltaskdescriptors to choose.
+
+ output.println("int flags_FS"+fscounter+"_"+cdtemp.getSafeSymbol()+"[]={");
+ for(Iterator flags = fs.getFlags(); flags.hasNext();){
+ FlagDescriptor flagd = (FlagDescriptor)flags.next();
+ int flagid=1<<((Integer)flaginfo.get(flagd)).intValue();
+ if( flags.hasNext() ) output.print("0x"+Integer.toHexString(flagid)+" /*"+Integer.toBinaryString(flagid)+"*/,");
+ else output.print("0x"+Integer.toHexString(flagid)+" /*"+Integer.toBinaryString(flagid)+"*/");
+
+ }
+ //process tag information
+
+ int tagcounter = 0;
+ //TagExpressionList tagel = fs.getTags();
+ //output.println("int predicatetags_"+predicateindex+"_OTD"+otd.getuid()+"_"+cdtemp.getSafeSymbol()+"[]={");
+ //BUG...added next line to fix, test with any task program
+
+ //if (tagel!=null){
+ // for(int j=0;j<tagel.numTags();j++) {
+ // if (j!=0)
+ // output.println(",");
+ // TempDescriptor tmp=tagel.getTemp(j);
+ // output.println("/*tagid*/"+state.getTagId(tmp.getTag()));
+ // }
+ // numtags = tagel.numTags();
+ //}
+ //output.println("};");
+
+
+ //Store the result in fsanalysiswrapper
+ output.println("};\n");
+ output.println("struct fsanalysiswrapper fsanalysiswrapper_FS"+fscounter+"_"+cdtemp.getSafeSymbol()+"={");
+ output.println("/* number of flags*/"+fs.numFlags()+",");
+ output.println("flags_FS"+fscounter+"_"+cdtemp.getSafeSymbol()+",");
+ output.println("/* number of tags*/"+tagcounter+",");
+ output.println("tags_FS"+fscounter+"_"+cdtemp.getSafeSymbol()+",");
+ output.println("/* number of optionaltaskdescriptors */"+availabletasks.size()+",");
+ output.println("optionaltaskdescriptorarray_FS"+fscounter+"_"+cdtemp.getSafeSymbol());
+ output.println("};\n");
+
+ }
+
+ //Build the array of fsanalysiswrappers
+ output.println("struct fsanalysiswrapper * fsanalysiswrapperarray_"+cdtemp.getSafeSymbol()+"[] = {");
+ for(int i = 0; i<fscounter; i++){
+ if(i==fscounter-1) output.println("&fsanalysiswrapper_FS"+(i+1)+"_"+cdtemp.getSafeSymbol()+"};\n");
+
+ else output.println("&fsanalysiswrapper_FS"+(i+1)+"_"+cdtemp.getSafeSymbol()+",");
+ }
+
+ //Build the classanalysiswrapper referring to the previous array
+ output.println("struct classanalysiswrapper classanalysiswrapper_"+cdtemp.getSafeSymbol()+"={");
+ output.println("/*type*/"+cdtemp.getId()+",");
+ output.println("/* number of fsanalysiswrappers */"+fscounter+",");
+ output.println("fsanalysiswrapperarray_"+cdtemp.getSafeSymbol()+"};\n");
+ fscounter = 0;
+ processedcd.add(cdtemp);
+ }
+
+ //build an array containing every classes for which code has been build
+ output.println("struct classanalysiswrapper * classanalysiswrapperarray[]={");
+ for(Iterator classit = processedcd.iterator(); classit.hasNext();){
+ ClassDescriptor cdtemp=(ClassDescriptor)classit.next();
+ if(!classit.hasNext()) output.println("&classanalysiswrapper_"+cdtemp.getSafeSymbol()+"};\n");
+ else output.println("&classanalysiswrapper_"+cdtemp.getSafeSymbol()+",");
+ }
+ output.println("int numclasses = "+processedcd.size()+";");
+
+ }
+