more stm options
authorbdemsky <bdemsky>
Tue, 27 Oct 2009 00:58:20 +0000 (00:58 +0000)
committerbdemsky <bdemsky>
Tue, 27 Oct 2009 00:58:20 +0000 (00:58 +0000)
19 files changed:
Robust/src/Analysis/Locality/DelayComputation.java
Robust/src/Analysis/Locality/DiscoverConflicts.java
Robust/src/IR/Flat/BuildCode.java
Robust/src/IR/State.java
Robust/src/Main/Main.java
Robust/src/Runtime/STM/array.h
Robust/src/Runtime/STM/commit.c
Robust/src/Runtime/STM/delaycomp.h
Robust/src/Runtime/STM/sandbox.c
Robust/src/Runtime/STM/stm.c
Robust/src/Runtime/STM/stmlock.h
Robust/src/Runtime/STM/stmlookup.c
Robust/src/Runtime/STM/stmlookup.h
Robust/src/Runtime/STM/tm.h
Robust/src/Runtime/garbage.c
Robust/src/Runtime/garbage.h
Robust/src/Runtime/runtime.c
Robust/src/Runtime/thread.c
Robust/src/Runtime/thread.h

index 590e5c6595835a425fe9d3046d6acae476f47120..4d67cb50c88373e3d0e8f25897ca3c277a0a63c3 100644 (file)
@@ -34,7 +34,7 @@ public class DelayComputation {
     this.gft=gft;
     this.notreadymap=new Hashtable<LocalityBinding, HashSet<FlatNode>>();
     this.cannotdelaymap=new Hashtable<LocalityBinding, HashSet<FlatNode>>();
-    if (state.STMARRAY)
+    if (state.STMARRAY&&!state.DUALVIEW)
       this.derefmap=new Hashtable<LocalityBinding, HashSet<FlatNode>>();
     this.othermap=new Hashtable<LocalityBinding, HashSet<FlatNode>>();
   }
@@ -286,7 +286,7 @@ public class DelayComputation {
 
     HashSet<FlatNode> delayedset=notreadymap.get(lb);
     HashSet<FlatNode> derefset=null;
-    if (state.STMARRAY) 
+    if (state.STMARRAY&&!state.DUALVIEW
       derefset=derefmap.get(lb);
     HashSet<FlatNode> otherset=othermap.get(lb);
     HashSet<FlatNode> cannotdelayset=cannotdelaymap.get(lb);
@@ -374,7 +374,7 @@ public class DelayComputation {
       }
 
       if (delayedset.contains(fn)) {
-       if(state.STMARRAY&&derefset.contains(fn)) {
+       if(state.STMARRAY&&!state.DUALVIEW&&derefset.contains(fn)) {
          //FlatElementNodes don't read anything...
          if (fn.kind()==FKind.FlatSetElementNode) {
            //check only the source read tmp
@@ -555,7 +555,7 @@ public class DelayComputation {
        Set<FlatNode> branchset=revbranchmap.get((FlatCondBranch)fn);
        for(Iterator<FlatNode> brit=branchset.iterator();brit.hasNext();) {
          FlatNode branchnode=brit.next();
-         if (cannotdelay.contains(branchnode)||(state.STMARRAY&&derefset.contains(branchnode))) {
+         if (cannotdelay.contains(branchnode)||(state.STMARRAY&&!state.DUALVIEW&&derefset.contains(branchnode))) {
            isnodelay=true;
            break;
          }
@@ -663,7 +663,7 @@ public class DelayComputation {
          if (oldtemps.contains(fsen.getDst())) {
            nodelaytempset.add(fsen.getDst());
            //Word Array support requires index
-           if (state.STMARRAY) {
+           if (state.STMARRAY&&!state.DUALVIEW) {
              nodelaytempset.add(fsen.getIndex());
              derefset.add(fsen);
            }
@@ -684,7 +684,7 @@ public class DelayComputation {
              dcopts.getArrays().contains(fen.getSrc().getType())) {
            nodelaytempset.add(fen.getSrc());
            //Word Array support requires index
-           if (state.STMARRAY) {
+           if (state.STMARRAY&&!state.DUALVIEW) {
              nodelaytempset.add(fen.getIndex());
              derefset.add(fen);
            }
@@ -736,7 +736,7 @@ public class DelayComputation {
     }//end of while loop
 
     if (lb.getHasAtomic()) {
-      if (state.STMARRAY)
+      if (state.STMARRAY&&!state.DUALVIEW)
        derefmap.put(lb, derefset);
       cannotdelaymap.put(lb, cannotdelay);
     }
index 775c87ebaab3c7c4bc151f8a120ca0e9d4e88384..ac58bf469f0e034d70460df67c8001052860d140 100644 (file)
@@ -169,7 +169,9 @@ public class DiscoverConflicts {
   }
 
   public boolean getNeedWriteTrans(LocalityBinding lb, FlatNode fn) {
-    return twritemap.get(lb).contains(fn);
+    if (gft!=null)
+      return twritemap.get(lb).contains(fn);
+    else throw new Error();
   }
 
   public Hashtable<FlatNode, Hashtable<TempDescriptor, Set<TempFlatPair>>> getMap(LocalityBinding lb) {
index 240fb7f1f749b9bbb5d310a9d66abe668a6dd750..d174ec6594695a7063e909c4e6351dad4d063179 100644 (file)
@@ -71,6 +71,8 @@ public class BuildCode {
   DiscoverConflicts recorddc;
   DelayComputation delaycomp;
   CallGraph callgraph;
+  boolean versionincrement;
+
 
   public BuildCode(State st, Hashtable temptovar, TypeUtil typeutil, SafetyAnalysis sa, PrefetchAnalysis pa) {
     this(st, temptovar, typeutil, null, sa, pa, null);
@@ -107,7 +109,8 @@ public class BuildCode {
     }
     if (state.SINGLETM&&state.DCOPTS) {
       TypeAnalysis typeanalysis=new TypeAnalysis(locality, st, typeutil,callgraph);
-      this.dc=new DiscoverConflicts(locality, st, typeanalysis, null);
+      GlobalFieldType gft=new GlobalFieldType(callgraph, st, typeutil.getMain());
+      this.dc=new DiscoverConflicts(locality, st, typeanalysis, gft);
       dc.doAnalysis();
     }
     if (state.DELAYCOMP) {
@@ -637,7 +640,6 @@ public class BuildCode {
       outclassdefs.println("  int lowindex;");
       outclassdefs.println("  int highindex;");
     }
-
     if (state.ARRAYPAD)
       outclassdefs.println("  int paddingforarray;");
 
@@ -1652,7 +1654,11 @@ public class BuildCode {
          //turn off write barrier generation
          wb.turnoff();
          state.SINGLETM=false;
+         if (state.DUALVIEW)
+           versionincrement=true;
          generateCode(faen, fm, lb, exitset, output, false);
+         if (state.DUALVIEW)
+           versionincrement=false;
          state.SINGLETM=true;
          //turn on write barrier generation
          wb.turnon();
@@ -1737,8 +1743,10 @@ public class BuildCode {
        if (state.DSM&&lb.isAtomic())
          output.println("if (needtocollect) checkcollect2("+localsprefixaddr+");");
        else if (this.state.MULTICOREGC) {
-      output.println("if(gcflag) gc("+localsprefixaddr+");");
-    } else
+         output.println("if(gcflag) gc("+localsprefixaddr+");");
+       } else if (state.SINGLETM) {
+         output.println("if (unlikely(needtocollect)) checkcollect("+localsprefixaddr+");");
+       } else
          output.println("if (needtocollect) checkcollect("+localsprefixaddr+");");
       }
     }
@@ -2075,7 +2083,9 @@ public class BuildCode {
       if (callgraph.getAllMethods(md).contains(md)) {
         if(this.state.MULTICOREGC) {
           output.println("if(gcflag) gc("+localsprefixaddr+");");
-        } else {
+        } else if (state.SINGLETM) {
+         output.println("if (unlikely(needtocollect)) checkcollect("+localsprefixaddr+");");
+       } else {
           output.println("if (needtocollect) checkcollect("+localsprefixaddr+");");
         }
       }
@@ -2155,7 +2165,7 @@ public class BuildCode {
     if (state.DELAYCOMP&&!lb.isAtomic()&&lb.getHasAtomic()) {
       storeset=delaycomp.livecode(lb);
       genset=new HashSet<FlatNode>();
-      if (state.STMARRAY) {
+      if (state.STMARRAY&&!state.DUALVIEW) {
        refset=new HashSet<FlatNode>();
        refset.addAll(delaycomp.getDeref(lb));
        refset.removeAll(delaycomp.getCannotDelay(lb));
@@ -2166,14 +2176,14 @@ public class BuildCode {
        genset.addAll(delaycomp.getOther(lb));
       } else {
        genset.addAll(delaycomp.getNotReady(lb));
-       if (state.STMARRAY) {
+       if (state.STMARRAY&&!state.DUALVIEW) {
          genset.removeAll(refset);
        }
       }
       unionset=new HashSet<FlatNode>();
       unionset.addAll(storeset);
       unionset.addAll(genset);
-      if (state.STMARRAY)
+      if (state.STMARRAY&&!state.DUALVIEW)
        unionset.addAll(refset);
     }
     
@@ -2248,7 +2258,7 @@ public class BuildCode {
 
          if (genset==null||genset.contains(current_node)||specialprimitive)
            generateFlatNode(fm, lb, current_node, output);
-         if (state.STMARRAY&&refset!=null&&refset.contains(current_node)) {
+         if (state.STMARRAY&&!state.DUALVIEW&&refset!=null&&refset.contains(current_node)) {
            //need to acquire lock
            handleArrayDeref(fm, lb, current_node, output, firstpass);
          }
@@ -2259,7 +2269,7 @@ public class BuildCode {
              if (wrtmp.getType().isPtr()) {
                //only lock the objects that may actually need locking
                if (recorddc.getNeedTrans(lb, current_node)&&
-                   (!state.STMARRAY||!wrtmp.getType().isArray()||
+                   (!state.STMARRAY||state.DUALVIEW||!wrtmp.getType().isArray()||
                     wrtmp.getType().getSymbol().equals(TypeUtil.ObjectClass))) {
                  output.println("STOREPTR("+generateTemp(fm, wrtmp,lb)+");/* "+current_node.nodeid+" */");
                } else {
@@ -2370,7 +2380,7 @@ public class BuildCode {
        output.println("  struct ArrayObject *array;");
        output.println("  int index;");
        output.println("  RESTOREARRAY(array,index);");
-       output.println("  (("+type+"*)(((char *)&array->___length___)+sizeof(int)))[index]="+fsen.getSrc()+";");
+       output.println("  (("+type+"*)(((char *)&array->___length___)+sizeof(int)))[index]="+src+";");
        output.println("}");
       }
     } else if (fn.kind()==FKind.FlatElementNode) {
@@ -2645,7 +2655,7 @@ public class BuildCode {
 
     case FKind.FlatBackEdge:
       if (state.SINGLETM&&state.SANDBOX&&(locality.getAtomic(lb).get(fn).intValue()>0)) {
-       output.println("if ((--transaction_check_counter)<=0) checkObjects();");
+       output.println("if (unlikely((--transaction_check_counter)<=0)) checkObjects();");
       }
       if (((state.THREAD||state.DSM||state.SINGLETM)&&GENERATEPRECISEGC)
           || (this.state.MULTICOREGC)) {
@@ -2653,6 +2663,8 @@ public class BuildCode {
          output.println("if (needtocollect) checkcollect2("+localsprefixaddr+");");
        } else if(this.state.MULTICOREGC) {
          output.println("if (gcflag) gc("+localsprefixaddr+");");
+       } else if (state.SINGLETM) {
+         output.println("if (unlikely(needtocollect)) checkcollect("+localsprefixaddr+");");
        } else
          output.println("if (needtocollect) checkcollect("+localsprefixaddr+");");
       } else
@@ -2907,7 +2919,15 @@ public class BuildCode {
   public void generateFlatAtomicEnterNode(FlatMethod fm,  LocalityBinding lb, FlatAtomicEnterNode faen, PrintWriter output) {
     /* Check to see if we need to generate code for this atomic */
     if (locality==null) {
-      output.println("pthread_mutex_lock(&atomiclock);");
+      if (GENERATEPRECISEGC) {
+       output.println("if (pthread_mutex_trylock(&atomiclock)!=0) {");
+       output.println("stopforgc((struct garbagelist *) &___locals___);");
+       output.println("pthread_mutex_lock(&atomiclock);");
+       output.println("restartaftergc();");
+       output.println("}");
+      } else {
+       output.println("pthread_mutex_lock(&atomiclock);");
+      }
       return;
     }
 
@@ -3873,6 +3893,9 @@ public class BuildCode {
       }
       output.println("(("+type +"*)(((char *) &("+ generateTemp(fm,fsen.getDst(),lb)+"->___length___))+sizeof(int)))["+generateTemp(fm, fsen.getIndex(),lb)+"]="+generateTemp(fm,fsen.getSrc(),lb)+";");
     }
+    if (versionincrement) {
+      output.println("VERSIONINCREMENT("+generateTemp(fm, fsen.getDst(),lb)+","+generateTemp(fm, fsen.getIndex(),lb)+","+type+");");
+    }
   }
 
   protected void generateFlatNew(FlatMethod fm, LocalityBinding lb, FlatNew fn, PrintWriter output) {
index 2e4c037c926c64f4b2eb457cdea3eae69d11697b..5cb080ecaca629586662103aa1121f6f1f71a408 100644 (file)
@@ -100,6 +100,7 @@ public class State {
   public boolean SANDBOX=false;
   public boolean DCOPTS=false;
   public boolean DELAYCOMP=false;
+  public boolean DUALVIEW=false;
   //Other options
   public int CORENUM = 1;
   public String structfile;
index 4b70f6e75e9bdf032f78415aec2d9a1b1b13734f..776542382c48d8f87f36e6b8aefff2f7f5126aa0 100644 (file)
@@ -120,6 +120,8 @@ public class Main {
        state.TAGSTATE=true;
       else if (option.equals("-stmarray"))
        state.STMARRAY=true;
+      else if (option.equals("-dualview"))
+       state.DUALVIEW=true;
       else if (option.equals("-flatirtasks")) {
        state.FLATIRGRAPH=true;
        state.FLATIRGRAPHTASKS=true;
index 7a31bb87a66849208141ba319c25c3c2c91df4e2..23aaa18f81e88fa8eba559bd7db8346111bf50f3 100644 (file)
@@ -3,7 +3,6 @@
 
 /* Array layout */
 #define INDEXSHIFT 5   //must be at least 3 for doubles
-//#define DBLINDEXSHIFT INDEXSHIFT-1   //must be at least 3 for doubles
 #define INDEXLENGTH (1<<INDEXSHIFT)
 #define LOWMASK (INDEXLENGTH-1) //mast off low order bits
 #define HIGHMASK ~(LOWMASK) //mask off high order bits
@@ -62,3 +61,9 @@
     ((type *)(((char *) lengthoff)+sizeof(int)))[index]=src;           \
   }
 #endif
+
+#define VERSIONINCREMENT(array, index, type) {                 \
+    unsigned int * versionptr;                                 \
+    GETVERSIONPTR(versionptr, array,((sizeof(type)*index)>>INDEXSHIFT)); \
+    (*versionptr)++;                                           \
+}
index 229a4e2610d2a6b0320af81afe88293c09d1e4de..8e47228dd8271236fe4940cebbaf36335258dc3f 100644 (file)
 #define ARRAYDELAYWRAP1(x)
 #endif
 
+#ifdef DUALVIEW
+#define DUALVIEWWRAP(x) x
+#else
+#define DUALVIEWWRAP(x)
+#endif
+
 /* ================================================================
  * transCommit
  * - This function initiates the transaction commit process
@@ -79,7 +85,7 @@ int transCommit() {
       ptrstack.count=0;
       primstack.count=0;
       branchstack.count=0;
-#ifdef STMARRAY
+#if defined(STMARRAY)&&!defined(DUALVIEW)
       arraystack.count=0;
 #endif
 #endif
@@ -102,7 +108,7 @@ int transCommit() {
       ptrstack.count=0;
       primstack.count=0;
       branchstack.count=0;
-#ifdef STMARRAY
+#if defined(STMARRAY)&&!defined(DUALVIEW)
       arraystack.count=0;
 #endif
 #endif
@@ -131,7 +137,7 @@ int transCommit() {
        ptrstack.count=0;
        primstack.count=0;
        branchstack.count=0;
-#ifdef STMARRAY
+#if defined(STMARRAY)&&!defined(DUALVIEW)
       arraystack.count=0;
 #endif
 #endif
@@ -250,10 +256,12 @@ int transCommit() {
 #define NUMWRTOTAL numoidwrlocked
 #endif
 
-#ifdef STMARRAY
+#if defined(STMARRAY)
 #define STMARRAYFREE free(oidrdlockedarray);
 #define STMARRAYALLOC oidrdlockedarray=malloc(size);
 #define STMARRAYASSIGN oidrdlockedarray=rdlockedarray;
+
+//allocation statements for dirwrindex
 #define STMARRAYDELAYFREE free(dirwrindex);
 #define STMARRAYDELAYALLOC dirwrindex=malloc(t_numelements*sizeof(int));
 #define STMARRAYDELAYASSIGN dirwrindex=wrindex;
@@ -262,6 +270,15 @@ int transCommit() {
   void * rdlockedarray[200];                   \
   void ** oidrdlockedarray;
 
+#define ABORT                                  \
+  transAbortProcess(oidwrlocked, numoidwrlocked ARRAYDELAYWRAP1(NULL) ARRAYDELAYWRAP1(numoidwrlocked)); \
+  freearrays;                                                          \
+  if (softabort)                                                       \
+    return TRANS_SOFT_ABORT;                                           \
+  else                                                                 \
+    return TRANS_ABORT;
+  
+
 #define ARRAYABORT                                                     \
   for(;j>=lowoffset;j--) {                                             \
     GETLOCKVAL(status, transao, j);                                    \
@@ -270,19 +287,52 @@ int transCommit() {
       write_unlock(lockptr);                                           \
     }                                                                  \
   }                                                                    \
-  transAbortProcess(oidwrlocked, numoidwrlocked ARRAYDELAYWRAP1(NULL) ARRAYDELAYWRAP1(numoidwrlocked)); \
-  freearrays;                                                          \
-  if (softabort)                                                       \
-    return TRANS_SOFT_ABORT;                                           \
-  else                                                                 \
-    return TRANS_ABORT;
-  
+  ABORT
+
+#ifdef DUALVIEW
+#define DVGETLOCK(x)                                           \
+  unsigned int * objlock=&(&((objheader_t *)x)[-1])->lock;             \
+  if(!rwread_trylock(objlock)) {                               \
+    ABORT;                                                     \
+  }
+
+//not finished...if we can't get the lock, it is okay if it is in our access set
+#define DVCHECKLOCK(x)                                                 \
+  unsigned int * objlock=&(&((objheader_t *)x)[-1])->lock;                     \
+  if (objlock<=0) {                                                    \
+    if (dc_t_chashSearch(x)==NULL) {                                   \
+      ABORT;                                                           \
+    }                                                                  \
+  }
+#else
+#define DVGETLOCK(x)
+#define DVCHECKLOCK(x)
+#endif
+
+#if defined(DELAYCOMP)&&!defined(DUALVIEW)
+#define READCHECK                                                      \
+  else if (dc_t_chashSearchArray(mainao,j)) {                          \
+    CFENCE;                                                            \
+    unsigned int localversion;                                         \
+    unsigned int remoteversion;                                                \
+    GETVERSIONVAL(localversion, transao, j);                           \
+    GETVERSIONVAL(remoteversion, mainao, j);                           \
+    if (localversion != remoteversion) {                               \
+      transAbortProcess(oidwrlocked, NUMWRTOTAL ARRAYDELAYWRAP1(dirwrindex) ARRAYDELAYWRAP1(numoidwrlocked)); \
+      freearrays;                                                      \
+      return TRANS_ABORT;                                              \
+    }                                                                  \
+  }
+#else
+#define READCHECK
+#endif
 
 #define PROCESSARRAY                                                   \
   int type=((int *)cachedobj)[0];                                      \
   if (type>=NUMCLASSES) {                                              \
     struct ArrayObject *transao=(struct ArrayObject *) cachedobj;      \
     struct ArrayObject *mainao=(struct ArrayObject *) objptr;          \
+    DVGETLOCK(mainao);                                                 \
     int lowoffset=(transao->lowindex)>>INDEXSHIFT;                     \
     int highoffset=(transao->highindex)>>INDEXSHIFT;                   \
     int j;                                                             \
@@ -313,6 +363,7 @@ int transCommit() {
     }                                                                  \
     if (addwrobject) {                                                 \
       dirwrlocked[numoidwrlocked++] = objptr;                          \
+      DUALVIEWWRAP(transao->___objstatus___ |=DIRTY;)                  \
     }                                                                  \
     if (addrdobject) {                                                 \
       oidrdlockedarray[numoidrdlockedarray++]=objptr;                  \
@@ -323,6 +374,7 @@ int transCommit() {
   for(i=0; i<numoidrdlockedarray; i++) {                               \
     struct ArrayObject * transao=(struct ArrayObject *) oidrdlockedarray[i]; \
     struct ArrayObject * mainao=(struct ArrayObject *) transao->___objlocation___; \
+    DVCHECKLOCK(mainao);                                               \
     int lowoffset=(transao->lowindex)>>INDEXSHIFT;                     \
     int highoffset=(transao->highindex)>>INDEXSHIFT;                   \
     int j;                                                             \
@@ -342,7 +394,9 @@ int transCommit() {
            freearrays;                                                 \
            return TRANS_ABORT;                                         \
          }                                                             \
-       } else {                                                        \
+       }                                                               \
+       READCHECK                                                       \
+       else {                                                          \
          unsigned int localversion;                                    \
          unsigned int remoteversion;                                   \
          GETVERSIONVAL(localversion, transao, j);                      \
@@ -358,7 +412,7 @@ int transCommit() {
        }                                                               \
       }                                                                        \
     }                                                                  \
-  }                                                                   
+  }
 #else
 #define ARRAYDEFINES
 #define PROCESSARRAY
@@ -372,7 +426,7 @@ int transCommit() {
 #endif
 
 #ifdef DELAYCOMP
-#ifdef STMARRAY
+#if defined(STMARRAY)&&!defined(DUALVIEW)
 #define ARRAYLOCK                                                      \
   int intkey=dc_curr->intkey;                                          \
   if (intkey!=-1) {                                                    \
@@ -397,9 +451,37 @@ int transCommit() {
       }                                                                        \
     }                                                                  \
   } else
+
+#elif defined(STMARRAY)&&defined(DUALVIEW)
+#define ARRAYLOCK                                                      \
+  if (((struct ___Object___ *)objptr)->type>=NUMCLASSES) {             \
+    if (!rwwrite_trylock(&header->lock)) {                             \
+      ARRAYDELAYWRAP(dirwrindex[numoidwrtotal]=0;);                    \
+      dirwrlocked[numoidwrtotal++] = objptr;                           \
+    } else {                                                           \
+      chashlistnode_t *node = &c_table[(((unsigned INTPTR)objptr) & c_mask)>>4]; \
+      do {                                                             \
+       if(node->key == objptr) {                                       \
+         objheader_t * headeraddr=&((objheader_t *) node->val)[-1];    \
+         if(STATUS(headeraddr) & DIRTY) {                              \
+           if (rwconvert_trylock(&header->lock)) {                     \
+             ARRAYDELAYWRAP(dirwrindex[numoidwrtotal]=1;);             \
+             dirwrlocked[numoidwrtotal++] = objptr;                    \
+             goto nextloop;                                            \
+           }                                                           \
+         }                                                             \
+         break;                                                        \
+       }                                                               \
+       node = node->next;                                              \
+      } while(node != NULL);                                           \
+      ABORT;                                                           \
+    }                                                                  \
+  } else
 #else
 #define ARRAYLOCK
 #endif
+
+
 #define ACCESSLOCKS                                                    \
   unsigned int numoidwrtotal=numoidwrlocked;                           \
   dchashlistnode_t *dc_curr = dc_c_list;                               \
@@ -445,9 +527,6 @@ int transCommit() {
 #define ACCESSLOCKS
 #endif
 
-
-
-
 /* ==================================================
  * traverseCache
  * - goes through the transaction cache and
@@ -886,11 +965,15 @@ void transAbortProcess(struct garbagelist *oidwrlocked, int numoidwrlocked) {
          write_unlock(lockptr);
        }
       }
+#ifdef DUALVIEW
+      //release object array lock
+      rwread_unlock(&header->lock);
+#endif
     } else
 #endif
     write_unlock(&header->lock);
   }
-#if defined(STMARRAY)&&defined(DELAYCOMP)
+#if defined(STMARRAY)&&defined(DELAYCOMP)&&!defined(DUALVIEW)
   //release access locks
   for(i=numoidwrtotal-1; i>=numoidwrlocked; i--) {
     struct ___Object___ * dst=dirwrlocked[i];
@@ -898,18 +981,32 @@ void transAbortProcess(struct garbagelist *oidwrlocked, int numoidwrlocked) {
     int wrindex=dirwrindex[i];
     if (wrindex==-1) {
       //normal object
-      header->version++;
       write_unlock(&header->lock);
     } else {
       //array element
       unsigned int *intptr;
-      GETVERSIONPTR(intptr, ((struct ArrayObject *)dst), wrindex);
-      (*intptr)++;
       GETLOCKPTR(intptr, ((struct ArrayObject *)dst), wrindex);
       write_unlock(intptr);
     }
   }
 #endif
+#if defined(STMARRAY)&&defined(DELAYCOMP)&&defined(DUALVIEW)
+  //release access locks
+  for(i=numoidwrtotal-1; i>=numoidwrlocked; i--) {
+    struct ___Object___ * dst=dirwrlocked[i];
+    header = &((objheader_t *)dst)[-1];
+    int wrindex=dirwrindex[i];
+    if (wrindex==-1) {
+      //normal object
+      write_unlock(&header->lock);
+    } else if (wrindex==0) {
+      //array element
+      rwwrite_unlock(&header->lock);
+    } else {
+      rwconvert_unlock(&header->lock);
+    }
+  }
+#endif
 #ifdef STMSTATS
   /* clear trec and then release objects locked */
   struct objlist *ptr=lockedobjs;
@@ -989,14 +1086,15 @@ void transCommitProcess(struct garbagelist * oidwrlocked, int numoidwrlocked) {
   ptrstack.maxcount=0;
   primstack.count=0;
   branchstack.count=0;
-#ifdef STMARRAY
+#if defined(STMARRAY)&&!defined(DUALVIEW)
   arraystack.maxcount=0;
 #endif
   //splice oidwrlocked in
   oidwrlocked->size=numoidwrtotal;
   oidwrlocked->next=params;
   ((struct garbagelist *)locals)->next=oidwrlocked;
-  commitmethod(params, locals, primitives);
+  if (commitmethod!=NULL)
+    commitmethod(params, locals, primitives);
   ((struct garbagelist *)locals)->next=params;
 #endif
 
@@ -1028,6 +1126,9 @@ void transCommitProcess(struct garbagelist * oidwrlocked, int numoidwrlocked) {
          write_unlock(intptr);
        }
       }
+#ifdef DUALVIEW
+      rwread_unlock(&header->lock);
+#endif
     } else
 #endif
     {
@@ -1035,7 +1136,25 @@ void transCommitProcess(struct garbagelist * oidwrlocked, int numoidwrlocked) {
       write_unlock(&header->lock);
     }
   }
-#if defined(STMARRAY)&&defined(DELAYCOMP)
+#if defined(STMARRAY)&&defined(DELAYCOMP)&&defined(DUALVIEW)
+  //release access locks
+  for(i=numoidwrtotal-1; i>=numoidwrlocked; i--) {
+    struct ___Object___ * dst=dirwrlocked[i];
+    int wrlock=dirwrindex[i];
+    header = &((objheader_t *)dst)[-1];
+    if (wrlock==-1) {
+      //problem...what if we are double locked
+      header->version++;
+      write_unlock(&header->lock);
+    } else if (wrlock==0) {
+      rwwrite_unlock(&header->lock);
+    } else {
+      //normal object
+      rwconvert_unlock(&header->lock);
+    }
+  }
+#endif
+#if defined(STMARRAY)&&defined(DELAYCOMP)&&!defined(DUALVIEW)
   //release access locks
   for(i=numoidwrtotal-1; i>=numoidwrlocked; i--) {
     struct ___Object___ * dst=dirwrlocked[i];
@@ -1069,4 +1188,3 @@ void transCommitProcess(struct garbagelist * oidwrlocked, int numoidwrlocked) {
   }
 #endif
 }
-
index 3cfd6413adc4f27761bf8c6af30bb9a663388383..4f5d9588fb3d8c780c9f9ae1bd26210ba03988f5 100644 (file)
@@ -31,7 +31,7 @@ struct branchlist {
 extern __thread struct pointerlist ptrstack;
 extern __thread struct primitivelist primstack;
 extern __thread struct branchlist branchstack;
-#ifdef STMARRAY
+#if defined(STMARRAY)&&!defined(DUALVIEW)
 struct arraylist {
   int count;
   void * prev;
index c3d9ccf34ae0901cdfb50fb3632de1ffcb011eb9..e504b83ab76c7c2685e17c7bff8c2d6820066335 100644 (file)
@@ -29,7 +29,7 @@ void checkObjects() {
     ptrstack.count=0;
     primstack.count=0;
     branchstack.count=0;
-#ifdef STMARRAY
+#if defined(STMARRAY)&&!defined(DUALVIEW)
     arraystack.count=0;
 #endif
 #endif
@@ -56,7 +56,7 @@ void CALL11(___System______Assert____Z, int ___status___, int ___status___) {
       ptrstack.count=0;
       primstack.count=0;
       branchstack.count=0;
-#ifdef STMARRAY
+#if defined(STMARRAY)&&!defined(DUALVIEW)
       arraystack.count=0;
 #endif
 #endif
@@ -90,7 +90,7 @@ void errorhandler(int sig, struct sigcontext ctx) {
     ptrstack.count=0;
     primstack.count=0;
     branchstack.count=0;
-#ifdef STMARRAY
+#if defined(STMARRAY)&&!defined(DUALVIEW)
     arraystack.count=0;
 #endif
 #endif
index e8a8aaab80cd38bf2cd658fb1181fd2471a59005..fb37e3f226b7ec65db428d4ab8db93b87a4e56af 100644 (file)
@@ -27,7 +27,7 @@ __thread struct objlist * newobjs;
 __thread struct pointerlist ptrstack;
 __thread struct primitivelist primstack;
 __thread struct branchlist branchstack;
-#ifdef STMARRAY
+#if defined(STMARRAY)&&!defined(DUALVIEW)
 __thread struct arraylist arraystack;
 #endif
 #endif
@@ -93,7 +93,15 @@ objheader_t *transCreateObj(void * ptr, unsigned int size) {
   objheader_t *tmp = mygcmalloc(ptr, (sizeof(objheader_t) + size));
 #endif
   objheader_t *retval=tmp+1;
+#ifdef DUALVIEW
+  if (bytelength==0) {
+    tmp->lock=SWAP_LOCK_BIAS;
+  } else {
+    tmp->lock=RW_LOCK_BIAS;
+  }
+#else
   tmp->lock=SWAP_LOCK_BIAS;
+#endif
   tmp->version = 1;
   //initialize obj lock to the header
   STATUS(tmp)=NEW;
index fda204553bff72b33f75942a97c58dbb700b3f1f..19230fe4b61b77961daf4a0ff6c3a3c5703d0799 100644 (file)
@@ -52,6 +52,11 @@ static inline void rwwrite_unlock(volatile unsigned int *rw) {
                         : "+m" (*rw) : "i" (RW_LOCK_BIAS) : "memory");
 }
 
+static inline void rwconvert_unlock(volatile unsigned int *rw) {
+  __asm__ __volatile__ (LOCK_PREFIX "addl %1, %0"
+                        : "+m" (*rw) : "i" (RW_LOCK_BIAS-1) : "memory");
+}
+
 static inline void atomic_dec(volatile unsigned int *v) {
   __asm__ __volatile__ (LOCK_PREFIX "decl %0"
                         : "+m" (*v));
@@ -88,4 +93,12 @@ static inline int rwwrite_trylock(volatile unsigned int  *lock) {
   atomic_add(RW_LOCK_BIAS, lock);
   return 0; // failed to acquire a write lock
 }
+
+static inline int rwconvert_trylock(volatile unsigned int  *lock) {
+  if (atomic_sub_and_test((RW_LOCK_BIAS-1), lock)) {
+    return 1; // get a write lock
+  }
+  atomic_add((RW_LOCK_BIAS-1), lock);
+  return 0; // failed to acquire a write lock
+}
 #endif
index 77277f784be9400af2066e8797e37917c92254ec..97131b307fb76f276517d61df5c5121042b3555b 100644 (file)
@@ -275,7 +275,7 @@ void dc_t_chashInsertOnce(void * key, void *val) {
   if(ptr->key==0) {
     ptr->key=key;
     ptr->val=val;
-#ifdef STMARRAY
+#if defined(STMARRAY)&&!defined(DUALVIEW)
     ptr->intkey=-1;
 #endif
     ptr->lnext=dc_c_list;
@@ -305,7 +305,7 @@ void dc_t_chashInsertOnce(void * key, void *val) {
       node=&tcl->array[0];
       tcl->num=1;
     }
-#ifdef STMARRAY
+#if defined(STMARRAY)&&!defined(DUALVIEW)
     node->intkey=-1;
 #endif
     node->key = key;
@@ -317,7 +317,7 @@ void dc_t_chashInsertOnce(void * key, void *val) {
   }
 }
 
-#ifdef STMARRAY
+#if defined(STMARRAY)&&!defined(DUALVIEW)
 //Store objects and their pointers into hash
 void dc_t_chashInsertOnceArray(void * key, unsigned int intkey, void *val) {
   dchashlistnode_t *ptr;
@@ -401,7 +401,7 @@ unsigned int dc_t_chashResize(unsigned int newsize) {
     isfirst = 1;
     do {                      //Inner loop to go through linked lists
       void * key;
-#ifdef STMARRAY
+#if defined(STMARRAY)&&!defined(DUALVIEW)
       unsigned int intkey;
 #endif
       dchashlistnode_t *tmp,*next;
@@ -409,7 +409,7 @@ unsigned int dc_t_chashResize(unsigned int newsize) {
       if ((key=curr->key) == 0) {             //Exit inner loop if there the first element is 0
        break;                  //key = val =0 for element if not present within the hash table
       }
-#ifdef STMARRAY
+#if defined(STMARRAY)&&!defined(DUALVIEW)
       intkey=curr->intkey;
       index = (((unsigned INTPTR)key^(intkey<<4)) & mask) >>4;
 #else
@@ -420,7 +420,7 @@ unsigned int dc_t_chashResize(unsigned int newsize) {
       // Insert into the new table
       if(tmp->key == 0) {
        tmp->key = key;
-#ifdef STMARRAY
+#if defined(STMARRAY)&!defined(DUALVIEW)
        tmp->intkey = intkey;
 #endif
        tmp->val = curr->val;
@@ -482,7 +482,7 @@ INLINE void * dc_t_chashSearch(void * key) {
   return NULL;
 }
 
-#ifdef STMARRAY
+#if defined(STMARRAY)&!defined(DUALVIEW)
 // Search for an address for a given oid
 INLINE void * dc_t_chashSearchArray(void * key, unsigned int intkey) {
   //REMOVE HASH FUNCTION CALL TO MAKE SURE IT IS INLINED HERE
index 2b83dde009fd0be424aa020d18e235f5fd271300..e25292875070f39da7969e991bdb363179bd8aa5 100644 (file)
@@ -93,7 +93,7 @@ void rd_t_chashreset();
 
 typedef struct dchashlistnode {
   void * key;
-#ifdef STMARRAY
+#if defined(STMARRAY)&&!defined(DUALVIEW)
   unsigned int intkey;
 #endif
   void * val;     //this can be cast to another type or used to point to a larger structure
index 3690a42ed34e5b140501029c1e58788566588ccf..edfba6f7dcc71e4d8092ca820fca3cbffe35435c 100644 (file)
@@ -189,7 +189,7 @@ void objstrReset();
 void objstrDelete(objstr_t *store);
 objstr_t *objstrCreate(unsigned int size);
 void transStart();
-#ifdef STMARRAY
+#if defined(STMARRAY)
 objheader_t *transCreateObj(void * ptr, unsigned int size, int bytelength);
 #else
 objheader_t *transCreateObj(void * ptr, unsigned int size);
@@ -204,7 +204,7 @@ __attribute__((pure)) void *transReadOnly(void *);
 int transCommit(void (*commitmethod)(void *, void *, void *), void * primitives, void * locals, void * params);
 int traverseCache(void (*commitmethod)(void *, void *, void *), void * primitives, void * locals, void * params);
 int alttraverseCache(void (*commitmethod)(void *, void *, void *), void * primitives, void * locals, void * params);
-#ifdef STMARRAY
+#if defined(STMARRAY)
 void transCommitProcess(struct garbagelist *, int *, int, int, void (*commitmethod)(void *, void *, void *), void * primitives, void * locals, void * params);
 #else
 void transCommitProcess(struct garbagelist *, int, int, void (*commitmethod)(void *, void *, void *), void * primitives, void * locals, void * params);
index 55135b174b41a2ef1f439baba3a261b8e6197620..7255a3573fed11f49c95c5dd31b3a6c8f28dee7a 100644 (file)
@@ -30,7 +30,7 @@
 
 #define NUMPTRS 100
 
-#define INITIALHEAPSIZE 256*1024*1024L
+#define INITIALHEAPSIZE 512*1024*1024L
 #define GCPOINT(x) ((INTPTR)((x)*0.99))
 /* This define takes in how full the heap is initially and returns a new heap size to use */
 #define HEAPSIZE(x,y) ((INTPTR)(x+y))*2
@@ -207,7 +207,8 @@ void fixtable(chashlistnode_t ** tc_table, chashlistnode_t **tc_list, cliststruc
          int j;
          for(j=lowindex; j<=highindex; j++) {
            unsigned int lockval;
-           if (GETLOCKVAL(lockval, ao, j)==STMDIRY) {
+           GETLOCKVAL(lockval, ao, j);
+           if (lockval==STMDIRTY) {
              int lowi=(j<<INDEXSHIFT)/sizeof(void *);
              int highi=lowi+(INDEXLENGTH/sizeof(void *));
              for(i=lowi; i<highi;i++) {
@@ -219,6 +220,7 @@ void fixtable(chashlistnode_t ** tc_table, chashlistnode_t **tc_list, cliststruc
              }
 #ifdef STMARRAY
            }
+         }
 #endif
        } else {
          INTPTR size=pointer[0];
@@ -318,7 +320,7 @@ void collect(struct garbagelist * stackptr) {
 #ifdef DELAYCOMP
   ptrstack.prev=stackptr;
   stackptr=(struct garbagelist *) &ptrstack;
-#ifdef STMARRAY
+#if defined(STMARRAY)&&!defined(DUALVIEW)
   arraystack.prev=stackptr;
   stackptr=(struct garbagelist *) &arraystack;
 #endif
@@ -354,6 +356,8 @@ void collect(struct garbagelist * stackptr) {
     fixobjlist(lockedobjs);
 #endif
   }
+#endif
+#if defined(STM)||defined(THREADS)
   memorybase=NULL;
 #endif
 
@@ -401,6 +405,8 @@ void collect(struct garbagelist * stackptr) {
       fixobjlist(listptr->lockedlist);
 #endif
     }
+#endif
+#if defined(STM)||defined(THREADS)
     *(listptr->base)=NULL;
 #endif
     stackptr=listptr->stackptr;
@@ -661,7 +667,7 @@ void stopforgc(struct garbagelist * ptr) {
   //just append us to the list
   ptrstack.prev=ptr;
   ptr=(struct garbagelist *) &ptrstack;
-#ifdef STMARRAY
+#if defined(STMARRAY)&&!defined(DUALVIEW)
   arraystack.prev=ptr;
   ptr=(struct garbagelist *) &arraystack;
 #endif
@@ -671,6 +677,9 @@ void stopforgc(struct garbagelist * ptr) {
 #ifdef THREADS
   litem.locklist=pthread_getspecific(threadlocks);
 #endif
+#if defined(STM)||defined(THREADS)
+  litem.base=&memorybase;
+#endif
 #ifdef STM
   litem.tc_size=c_size;
   litem.tc_table=&c_table;
@@ -680,7 +689,6 @@ void stopforgc(struct garbagelist * ptr) {
 #ifdef STMSTATS
   litem.lockedlist=lockedobjs;
 #endif
-  litem.base=&memorybase;
 #endif
 #else
   //handle MAC
index f3428c2eceea6f2df01ecac3c1f611eda16c517f..0a9237476196332ca7980b4e1bf81f46498a615d 100644 (file)
@@ -25,6 +25,8 @@ struct listitem {
 #ifdef STMSTATS
   struct objlist * lockedlist;
 #endif
+#endif
+#if defined(THREADS)||defined(STM)
   char **base;
 #endif
 };
index 245fe9f357261b18af2bbe1f60b3cb21a7aac34f..0eacaa6ff0707212479c21fa4b00928716e2aad8 100644 (file)
@@ -173,6 +173,9 @@ int CALL12(___String______convertdoubletochar____D__AR_C, double ___val___, doub
 void deepArrayCopy(struct ___Object___ * dst, struct ___Object___ * src) {
   int dsttype=((int *)dst)[0];
   int srctype=((int *)src)[0];
+#ifdef STMARRAY
+  src=src->___objlocation___;
+#endif
   if (dsttype<NUMCLASSES||srctype<NUMCLASSES||srctype!=dsttype)
     return;
   struct ArrayObject *aodst=(struct ArrayObject *)dst;
@@ -564,7 +567,11 @@ __attribute__((malloc)) struct ArrayObject * allocate_newarray(void * ptr, int t
   objheader_t *tmp=mygcmalloc((struct garbagelist *) ptr, sizeof(struct ArrayObject)+length*classsize[type]+sizeof(objheader_t));
   struct ArrayObject * v=(struct ArrayObject *) &tmp[1];
 #endif
+#ifdef DUALVIEW
+  tmp->lock=RW_LOCK_BIAS;
+#else
   initdsmlocks(&tmp->lock);
+#endif
   tmp->version=1;
   v->type=type;
   if (length<0) {
index 47704013a92fada38f2c742de698590a999c76b8..02561d59bd7639ebe3e468ebb2d71ff161e9d8c2 100644 (file)
@@ -199,7 +199,7 @@ void initializethreads() {
   ptrstack.count=0;
   primstack.count=0;
   branchstack.count=0;
-#ifdef STMARRAY
+#if defined(STMARRAY)&&!defined(DUALVIEW)
   arraystack.count=0;
 #endif
   int a=mprotect((downpage(&ptrstack.buffer[1024])), 4096, PROT_NONE);
@@ -211,7 +211,7 @@ void initializethreads() {
   a=mprotect(downpage(&branchstack.array[MAXBRANCHES]), 4096, PROT_NONE);
   if (a==-1)
     perror("branchstack");
-#ifdef STMARRAY
+#if defined(STMARRAY)&&!defined(DUALVIEW)
   a=mprotect(downpage(&arraystack.index[MAXARRAY]), 4096, PROT_NONE);
   if (a==-1)
     perror("arraystack");
@@ -300,7 +300,7 @@ void initthread(struct ___Thread___ * ___this___) {
   ptrstack.count=0;
   primstack.count=0;
   branchstack.count=0;
-#ifdef STMARRAY
+#if defined(STMARRAY)&&!defined(DUALVIEW)
   arraystack.count=0;
 #endif
   int a=mprotect(downpage(&ptrstack.buffer[1024]), 4096, PROT_NONE);
@@ -312,7 +312,7 @@ void initthread(struct ___Thread___ * ___this___) {
   a=mprotect(downpage(&branchstack.array[MAXBRANCHES]), 4096, PROT_NONE);
   if (a==-1)
     perror("branchstack");
-#ifdef STMARRAY
+#if defined(STMARRAY)&!defined(DUALVIEW)
   a=mprotect(downpage(&arraystack.index[MAXARRAY]), 4096, PROT_NONE);
   if (a==-1)
     perror("arraystack");
index d2f80dfa5bd38c36f090ac702775ac19513b73ab..4f65bd68b8a92eb0d4579f336e06910da257748c 100644 (file)
@@ -12,6 +12,19 @@ extern pthread_cond_t objcond;
 extern pthread_key_t threadlocks;
 extern pthread_mutex_t atomiclock;
 
+#ifdef PRECISE_GC
+#define ATOMICLOCK if (pthread_mutex_trylock(&atomiclock)!=0) {        \
+    stopforgc((struct garbagelist *) &___locals___);           \
+    pthread_mutex_lock(&atomiclock);                           \
+    restartaftergc();                                          \
+  }
+
+#define ATOMICUNLOCK pthread_mutex_unlock(&atomiclock)
+#else
+#define ATOMICLOCK pthread_mutex_lock(&atomiclock)
+#define ATOMICUNLOCK pthread_mutex_unlock(&atomiclock)
+#endif
+
 #if defined(THREADS)||defined(STM)
 void initthread(struct ___Thread___ * ___this___);
 #endif