get Fission w/ array support working
authorbdemsky <bdemsky>
Sat, 24 Oct 2009 01:25:38 +0000 (01:25 +0000)
committerbdemsky <bdemsky>
Sat, 24 Oct 2009 01:25:38 +0000 (01:25 +0000)
Robust/src/IR/Flat/BuildCode.java
Robust/src/Runtime/STM/array.h
Robust/src/Runtime/STM/commit.c
Robust/src/Runtime/STM/delaycomp.h
Robust/src/Runtime/STM/stmlookup.c
Robust/src/Runtime/STM/stmlookup.h
Robust/src/Runtime/STM/tm.h

index cb9e364256a93f57369d7367b44cabc611491d4c..240fb7f1f749b9bbb5d310a9d66abe668a6dd750 100644 (file)
@@ -2357,15 +2357,15 @@ public class BuildCode {
       String dst=generateTemp(fm, fsen.getDst(), lb);
       String src=generateTemp(fm, fsen.getSrc(), lb);
       String index=generateTemp(fm, fsen.getIndex(), lb);      
+      TypeDescriptor elementtype=fsen.getDst().getType().dereference();
+      String type="";
+      if (elementtype.isArray()||elementtype.isClass())
+       type="void *";
+      else
+       type=elementtype.getSafeSymbol()+" ";
       if (firstpass) {
-       output.println("STOREARRAY("+dst+","+index+")");
+       output.println("STOREARRAY("+dst+","+index+","+type+")");
       } else {
-       TypeDescriptor elementtype=fsen.getDst().getType().dereference();
-       String type="";
-       if (elementtype.isArray()||elementtype.isClass())
-         type="void *";
-       else
-         type=elementtype.getSafeSymbol()+" ";
        output.println("{");
        output.println("  struct ArrayObject *array;");
        output.println("  int index;");
@@ -2377,16 +2377,16 @@ public class BuildCode {
       FlatElementNode fen=(FlatElementNode) fn;
       String src=generateTemp(fm, fen.getSrc(), lb);
       String index=generateTemp(fm, fen.getIndex(), lb);
+      TypeDescriptor elementtype=fen.getSrc().getType().dereference();
+      String dst=generateTemp(fm, fen.getDst(), lb);
+      String type="";
+      if (elementtype.isArray()||elementtype.isClass())
+       type="void *";
+      else
+       type=elementtype.getSafeSymbol()+" ";
       if (firstpass) {
-       output.println("STOREARRAY("+src+","+index+");");
+       output.println("STOREARRAY("+src+","+index+","+type+");");
       } else {
-       TypeDescriptor elementtype=fen.getSrc().getType().dereference();
-       String dst=generateTemp(fm, fen.getDst(), lb);
-       String type="";
-       if (elementtype.isArray()||elementtype.isClass())
-         type="void *";
-       else
-         type=elementtype.getSafeSymbol()+" ";
        output.println("{");
        output.println("  struct ArrayObject *array;");
        output.println("  int index;");
index 33b9fa642ee2f5e79b2906b51214b06ac957158f..7a31bb87a66849208141ba319c25c3c2c91df4e2 100644 (file)
@@ -2,7 +2,7 @@
 #define ARRAY_H
 
 /* Array layout */
-#define INDEXSHIFT 4   //must be at least 3 for doubles
+#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
index 34a8aaa898522a09749b2d73e418f65df3adacf3..229a4e2610d2a6b0320af81afe88293c09d1e4de 100644 (file)
 #define STATASSIGN
 #endif
 
+#if defined(STMARRAY)&&defined(DELAYCOMP)
+#define ARRAYDELAYWRAP(x) x
+#define ARRAYDELAYWRAP1(x) ,x
+#else
+#define ARRAYDELAYWRAP(x)
+#define ARRAYDELAYWRAP1(x)
+#endif
+
 /* ================================================================
  * transCommit
  * - This function initiates the transaction commit process
@@ -32,6 +40,7 @@
  * - a final response
  * ================================================================
  */
+
 #ifdef DELAYCOMP
 int transCommit(void (*commitmethod)(void *, void *, void *), void * primitives, void * locals, void * params) {
 #else
@@ -144,6 +153,7 @@ int transCommit() {
   }                                         \
   if (t_numelements>=200) {                 \
     free(oidwrlocked);                      \
+    STMARRAYDELAYFREE;                      \
   }
 #else
 #define freearrays   if (c_numelements>=200) { \
@@ -156,71 +166,73 @@ int transCommit() {
 #endif
 
 #ifdef DELAYCOMP
-#define allocarrays int t_numelements=c_numelements+dc_c_numelements; \
-  if (t_numelements<200) { \
+#define allocarrays int t_numelements=c_numelements+dc_c_numelements;  \
+  if (t_numelements<200) {                                             \
     oidwrlocked=(struct garbagelist *) &wrlocked;                      \
-  } else { \
-    oidwrlocked=malloc(2*sizeof(INTPTR)+t_numelements*sizeof(void *)); \
-  } \
-  if (c_numelements<200) { \
-    oidrdlocked=rdlocked; \
-    oidrdversion=rdversion; \
-    STATASSIGN;                    \
-    STMARRAYASSIGN;        \
-  } else { \
-    int size=c_numelements*sizeof(void*); \
-    oidrdlocked=malloc(size); \
-    oidrdversion=malloc(size); \
-    STATALLOC;                \
-    STMARRAYALLOC;            \
-  }\
+    STMARRAYDELAYASSIGN;                                               \
+  } else {                                                             \
+    oidwrlocked=malloc(2*sizeof(INTPTR)+t_numelements*(sizeof(void *))); \
+    STMARRAYDELAYALLOC;                                                        \
+  }                                                                    \
+  if (c_numelements<200) {                                             \
+    oidrdlocked=rdlocked;                                              \
+    oidrdversion=rdversion;                                            \
+    STATASSIGN;                                                                \
+    STMARRAYASSIGN;                                                    \
+  } else {                                                             \
+    int size=c_numelements*sizeof(void*);                              \
+    oidrdlocked=malloc(size);                                          \
+    oidrdversion=malloc(size);                                         \
+    STATALLOC;                                                         \
+    STMARRAYALLOC;                                                     \
+  }                                                                    \
   dirwrlocked=oidwrlocked->array;
 #else
-#define allocarrays if (c_numelements<200) { \
-    oidrdlocked=rdlocked; \
-    oidrdversion=rdversion; \
+#define allocarrays if (c_numelements<200) {     \
+    oidrdlocked=rdlocked;                        \
+    oidrdversion=rdversion;                      \
     oidwrlocked=(struct garbagelist *) &wrlocked; \
     STATASSIGN;                                          \
     STMARRAYASSIGN;                              \
-  } else { \
-    int size=c_numelements*sizeof(void*); \
-    oidrdlocked=malloc(size); \
-    oidrdversion=malloc(size); \
-    oidwrlocked=malloc(size+2*sizeof(INTPTR)); \
-    STATALLOC;                                 \
-    STMARRAYALLOC;                             \
-  } \
+  } else {                                       \
+    int size=c_numelements*sizeof(void*);        \
+    oidrdlocked=malloc(size);                    \
+    oidrdversion=malloc(size);                   \
+    oidwrlocked=malloc(size+2*sizeof(INTPTR));   \
+    STATALLOC;                                   \
+    STMARRAYALLOC;                               \
+  }                                              \
   dirwrlocked=oidwrlocked->array;
 #endif
 
 #ifdef STMSTATS
-#define ABORTSTAT1 header->abortCount++;       \
-  ObjSeqId = headeraddr->accessCount;                          \
+#define ABORTSTAT1 header->abortCount++;                               \
+  ObjSeqId = headeraddr->accessCount;                                  \
   (typesCausingAbort[TYPE(header)]).numabort++;                                \
   (typesCausingAbort[TYPE(header)]).numaccess+=c_numelements;          \
   (typesCausingAbort[TYPE(header)]).numtrans+=1;                       \
   objtypetraverse[TYPE(header)]=1;                                     \
   if(getTotalAbortCount(i+1, size, (void *)(curr->next), numoidrdlocked, oidrdlocked, oidrdversion, oidrdage, ObjSeqId, header, objtypetraverse)) \
     softabort=0;
-#define ABORTSTAT2                             \
-  ObjSeqId = oidrdage[i];\
-  header->abortCount++;                                        \
-  (typesCausingAbort[TYPE(header)]).numabort++;                        \
-  (typesCausingAbort[TYPE(header)]).numaccess+=c_numelements;  \
-  (typesCausingAbort[TYPE(header)]).numtrans+=1;               \
+#define ABORTSTAT2                                                     \
+  ObjSeqId = oidrdage[i];                                              \
+  header->abortCount++;                                                        \
+  (typesCausingAbort[TYPE(header)]).numabort++;                                \
+  (typesCausingAbort[TYPE(header)]).numaccess+=c_numelements;          \
+  (typesCausingAbort[TYPE(header)]).numtrans+=1;                       \
   objtypetraverse[TYPE(header)]=1;                                     \
   if (getReadAbortCount(i+1, numoidrdlocked, oidrdlocked, oidrdversion, oidrdage, ObjSeqId, header, objtypetraverse)) \
     softabort=0;
-#define ABORTSTAT3                             \
-  header->abortCount++;                                \
-  ObjSeqId = headeraddr->accessCount;          \
-  (typesCausingAbort[TYPE(header)]).numabort++;                        \
-  (typesCausingAbort[TYPE(header)]).numaccess+=c_numelements;  \
-  (typesCausingAbort[TYPE(header)]).numtrans+=1;               \
+#define ABORTSTAT3                                                     \
+  header->abortCount++;                                                        \
+  ObjSeqId = headeraddr->accessCount;                                  \
+  (typesCausingAbort[TYPE(header)]).numabort++;                                \
+  (typesCausingAbort[TYPE(header)]).numaccess+=c_numelements;          \
+  (typesCausingAbort[TYPE(header)]).numtrans+=1;                       \
   objtypetraverse[TYPE(header)]=1;                                     \
   if (getTotalAbortCount2((void *) curr->next, numoidrdlocked, oidrdlocked, oidrdversion, oidrdage, ObjSeqId, header, objtypetraverse)) \
     softabort=0;
-#define ABORTSTAT4 ObjSeqId = oidrdage[i];     \
+#define ABORTSTAT4 ObjSeqId = oidrdage[i];                             \
   header->abortCount++;                                                        \
   getReadAbortCount(i+1, numoidrdlocked, oidrdlocked, oidrdversion, oidrdage, ObjSeqId, header, objtypetraverse);
 #else
@@ -242,6 +254,9 @@ int transCommit() {
 #define STMARRAYFREE free(oidrdlockedarray);
 #define STMARRAYALLOC oidrdlockedarray=malloc(size);
 #define STMARRAYASSIGN oidrdlockedarray=rdlockedarray;
+#define STMARRAYDELAYFREE free(dirwrindex);
+#define STMARRAYDELAYALLOC dirwrindex=malloc(t_numelements*sizeof(int));
+#define STMARRAYDELAYASSIGN dirwrindex=wrindex;
 
 #define ARRAYDEFINES int numoidrdlockedarray=0;        \
   void * rdlockedarray[200];                   \
@@ -255,7 +270,7 @@ int transCommit() {
       write_unlock(lockptr);                                           \
     }                                                                  \
   }                                                                    \
-  transAbortProcess(oidwrlocked, numoidwrlocked);                      \
+  transAbortProcess(oidwrlocked, numoidwrlocked ARRAYDELAYWRAP1(NULL) ARRAYDELAYWRAP1(numoidwrlocked)); \
   freearrays;                                                          \
   if (softabort)                                                       \
     return TRANS_SOFT_ABORT;                                           \
@@ -278,12 +293,12 @@ int transCommit() {
       if (status==STMDIRTY) {                                          \
        unsigned int * lockptr;                                         \
        GETLOCKPTR(lockptr, mainao,j);                                  \
-       if (write_trylock(lockptr)) {                                   \
+       if (likely(write_trylock(lockptr))) {                           \
          unsigned int localversion;                                    \
          unsigned int remoteversion;                                   \
          GETVERSIONVAL(localversion, transao, j);                      \
          GETVERSIONVAL(remoteversion, mainao, j);                      \
-         if (localversion == remoteversion) {                          \
+         if (likely(localversion == remoteversion)) {                  \
            addwrobject=1;                                              \
          } else {                                                      \
            ARRAYABORT;                                                 \
@@ -323,7 +338,7 @@ int transCommit() {
          GETVERSIONVAL(localversion, transao, j);                      \
          GETVERSIONVAL(remoteversion, mainao, j);                      \
          if (localversion != remoteversion) {                          \
-           transAbortProcess(oidwrlocked, NUMWRTOTAL);                 \
+           transAbortProcess(oidwrlocked, NUMWRTOTAL ARRAYDELAYWRAP1(dirwrindex) ARRAYDELAYWRAP1(numoidwrlocked)); \
            freearrays;                                                 \
            return TRANS_ABORT;                                         \
          }                                                             \
@@ -334,7 +349,7 @@ int transCommit() {
          GETVERSIONVAL(remoteversion, mainao, j);                      \
          if (localversion==remoteversion)                              \
            softabort=1;                                                \
-         transAbortProcess(oidwrlocked, NUMWRTOTAL);                   \
+         transAbortProcess(oidwrlocked, NUMWRTOTAL ARRAYDELAYWRAP1(dirwrindex) ARRAYDELAYWRAP1(numoidwrlocked)); \
          freearrays;                                                   \
          if (softabort)                                                \
            return TRANS_SOFT_ABORT;                                    \
@@ -351,8 +366,88 @@ int transCommit() {
 #define STMARRAYFREE
 #define STMARRAYALLOC
 #define STMARRAYASSIGN
+#define STMARRAYDELAYFREE
+#define STMARRAYDELAYALLOC
+#define STMARRAYDELAYASSIGN
 #endif
 
+#ifdef DELAYCOMP
+#ifdef STMARRAY
+#define ARRAYLOCK                                                      \
+  int intkey=dc_curr->intkey;                                          \
+  if (intkey!=-1) {                                                    \
+    unsigned int *lockptr;                                             \
+    GETLOCKPTR(lockptr, objptr, intkey);                               \
+    if (likely(write_trylock(lockptr))) {                              \
+      /*have lock on element */                                                \
+      dirwrlocked[numoidwrtotal]=objptr;                               \
+      dirwrindex[numoidwrtotal++]=intkey;                              \
+    } else {                                                           \
+      unsigned int lockval;                                            \
+      GETLOCKVAL(lockval, valptr, intkey);                             \
+      if (lockval!=STMDIRTY) {                                         \
+       /*have to abort to avoid deadlock*/                             \
+       transAbortProcess(oidwrlocked, numoidwrtotal, dirwrindex, numoidwrlocked); \
+       ABORTSTAT1;                                                     \
+       freearrays;                                                     \
+       if (softabort)                                                  \
+         return TRANS_SOFT_ABORT;                                      \
+       else                                                            \
+         return TRANS_ABORT;                                           \
+      }                                                                        \
+    }                                                                  \
+  } else
+#else
+#define ARRAYLOCK
+#endif
+#define ACCESSLOCKS                                                    \
+  unsigned int numoidwrtotal=numoidwrlocked;                           \
+  dchashlistnode_t *dc_curr = dc_c_list;                               \
+  /* Inner loop to traverse the linked list of the cache lookupTable */ \
+  while(likely(dc_curr != NULL)) {                                     \
+    /*if the first bin in hash table is empty  */                      \
+    void *valptr=dc_curr->val;                                         \
+    objheader_t * headeraddr=&((objheader_t *) valptr)[-1];            \
+    void *objptr=dc_curr->key;                                         \
+    objheader_t *header=(objheader_t *)(((char *)objptr)-sizeof(objheader_t)); \
+    ARRAYLOCK                                                          \
+    if(likely(write_trylock(&header->lock))) { /*can aquire write lock*/ \
+      ARRAYDELAYWRAP(dirwrindex[numoidwrtotal]=-1;)                    \
+      dirwrlocked[numoidwrtotal++] = objptr;                           \
+    } else {                                                           \
+      /* maybe we already have lock*/                                  \
+      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) {                              \
+           goto nextloop;                                              \
+         } else                                                        \
+           break;                                                      \
+       }                                                               \
+       node = node->next;                                              \
+      } while(node != NULL);                                           \
+                                                                       \
+      /*have to abort to avoid deadlock        */                              \
+      transAbortProcess(oidwrlocked, numoidwrtotal ARRAYDELAYWRAP1(dirwrindex) ARRAYDELAYWRAP1(numoidwrlocked)); \
+      ABORTSTAT1;                                                      \
+      freearrays;                                                      \
+      if (softabort)                                                   \
+       return TRANS_SOFT_ABORT;                                        \
+      else                                                             \
+       return TRANS_ABORT;                                             \
+    }                                                                  \
+  nextloop:                                                            \
+    dc_curr = dc_curr->lnext;                                          \
+  }                                                    
+#else
+#define ACCESSLOCKS
+#endif
+
+
+
+
 /* ==================================================
  * traverseCache
  * - goes through the transaction cache and
@@ -361,9 +456,9 @@ int transCommit() {
  */
 
 #ifdef DELAYCOMP
-  int traverseCache(void (*commitmethod)(void *, void *, void *), void * primitives, void * locals, void * params) {
+int traverseCache(void (*commitmethod)(void *, void *, void *), void * primitives, void * locals, void * params) {
 #else
-  int traverseCache() {
+int traverseCache() {
 #endif
   /* Create info to keep track of objects that can be locked */
   int numoidrdlocked=0;
@@ -379,6 +474,10 @@ int transCommit() {
   STMWRAP(int rdage[200];int * oidrdage;int ObjSeqId;int objtypetraverse[TOTALNUMCLASSANDARRAY];);
   struct garbagelist * oidwrlocked;
   void ** dirwrlocked;
+#if defined(STMARRAY)&&defined(DELAYCOMP)
+  int wrindex[200];
+  int * dirwrindex;
+#endif
   allocarrays;
 
   STMWRAP(for(i=0; i<TOTALNUMCLASSANDARRAY; i++) objtypetraverse[i] = 0;);
@@ -403,13 +502,13 @@ int transCommit() {
 
       if(STATUS(headeraddr) & DIRTY) {
        /* Read from the main heap  and compare versions */
-       if(write_trylock(&header->lock)) { //can aquire write lock
-         if (version == header->version) { /* versions match */
+       if(likely(write_trylock(&header->lock))) { //can aquire write lock
+         if (likely(version == header->version)) { /* versions match */
            /* Keep track of objects locked */
            dirwrlocked[numoidwrlocked++] = objptr;
          } else {
            dirwrlocked[numoidwrlocked++] = objptr;
-           transAbortProcess(oidwrlocked, numoidwrlocked);
+           transAbortProcess(oidwrlocked, numoidwrlocked ARRAYDELAYWRAP1(NULL) ARRAYDELAYWRAP1(numoidwrlocked));
            ABORTSTAT1;
            freearrays;
            if (softabort)
@@ -422,7 +521,7 @@ int transCommit() {
            /* versions match */
            softabort=1;
          }
-         transAbortProcess(oidwrlocked, numoidwrlocked);
+         transAbortProcess(oidwrlocked, numoidwrlocked ARRAYDELAYWRAP1(NULL) ARRAYDELAYWRAP1(numoidwrlocked));
          ABORTSTAT1;
          freearrays;
          if (softabort)
@@ -440,51 +539,9 @@ int transCommit() {
     }
   } //end of for
   
-#ifdef DELAYCOMP
-  //acquire access set locks
-  unsigned int numoidwrtotal=numoidwrlocked;
-
-  dchashlistnode_t *dc_curr = dc_c_list;
-  /* Inner loop to traverse the linked list of the cache lookupTable */
-  while(likely(dc_curr != NULL)) {
-    //if the first bin in hash table is empty
-    objheader_t * headeraddr=&((objheader_t *) dc_curr->val)[-1];
-    void *objptr=dc_curr->key;
-    objheader_t *header=(objheader_t *)(((char *)objptr)-sizeof(objheader_t));
-    if(write_trylock(&header->lock)) { //can aquire write lock    
-      dirwrlocked[numoidwrtotal++] = objptr;
-    } else {
-      //maybe we already have lock
-      void * key=dc_curr->key;
-      chashlistnode_t *node = &c_table[(((unsigned INTPTR)key) & c_mask)>>4];
-      
-      do {
-       if(node->key == key) {
-         objheader_t * headeraddr=&((objheader_t *) node->val)[-1];      
-         if(STATUS(headeraddr) & DIRTY) {
-           goto nextloop;
-         } else
-           break;
-       }
-       node = node->next;
-      } while(node != NULL);
-
-      //have to abort to avoid deadlock
-      transAbortProcess(oidwrlocked, numoidwrtotal);
-      ABORTSTAT1;
-      freearrays;
-      if (softabort)
-       return TRANS_SOFT_ABORT;
-      else
-       return TRANS_ABORT;
-    }
-  nextloop:
-    dc_curr = dc_curr->lnext;
-  }
-#endif
+  ACCESSLOCKS;
 
   //THIS IS THE SERIALIZATION END POINT (START POINT IS END OF EXECUTION)*****
-
   READARRAYS;
 
   for(i=0; i<numoidrdlocked; i++) {
@@ -494,7 +551,7 @@ int transCommit() {
     if(header->lock>0) { //not write locked
       CFENCE;
       if(version != header->version) { /* versions do not match */
-       transAbortProcess(oidwrlocked, NUMWRTOTAL);
+       transAbortProcess(oidwrlocked, NUMWRTOTAL ARRAYDELAYWRAP1(dirwrindex) ARRAYDELAYWRAP1(numoidwrlocked));
        ABORTSTAT2;
        freearrays;
        return TRANS_ABORT;
@@ -504,7 +561,7 @@ int transCommit() {
       //couldn't get lock because we already have it
       //check if it is the right version number
       if (version!=header->version) {
-       transAbortProcess(oidwrlocked, numoidwrtotal);
+       transAbortProcess(oidwrlocked, numoidwrtotal ARRAYDELAYWRAP1(dirwrindex) ARRAYDELAYWRAP1(numoidwrlocked));
        ABORTSTAT2;
        freearrays;
        return TRANS_ABORT;
@@ -515,7 +572,7 @@ int transCommit() {
       if(version == header->version) {
        softabort=1;
       }
-      transAbortProcess(oidwrlocked, NUMWRTOTAL);
+      transAbortProcess(oidwrlocked, NUMWRTOTAL ARRAYDELAYWRAP1(dirwrindex) ARRAYDELAYWRAP1(numoidwrlocked));
       ABORTSTAT2;
       freearrays;
       if (softabort)
@@ -536,7 +593,7 @@ int transCommit() {
     if(header->lock>0) { //object is not locked
       if (version!=header->version) {
        //have to abort
-       transAbortProcess(oidwrlocked, NUMWRTOTAL);
+       transAbortProcess(oidwrlocked, NUMWRTOTAL ARRAYDELAYWRAP1(dirwrindex) ARRAYDELAYWRAP1(numoidwrlocked));
        STMWRAP((typesCausingAbort[TYPE(header)])++;);
        freearrays;
        if (softabort)
@@ -574,7 +631,7 @@ int transCommit() {
        }
       }
       //have to abort to avoid deadlock
-      transAbortProcess(oidwrlocked, NUMWRTOTAL);
+      transAbortProcess(oidwrlocked, NUMWRTOTAL ARRAYDELAYWRAP1(dirwrindex) ARRAYDELAYWRAP1(numoidwrlocked));
       STMWRAP((typesCausingAbort[TYPE(header)])++;);
       freearrays;
       if (softabort)
@@ -589,7 +646,7 @@ int transCommit() {
   
   /* Decide the final response */
 #ifdef DELAYCOMP
-  transCommitProcess(oidwrlocked, numoidwrlocked, numoidwrtotal, commitmethod, primitives, locals, params);
+  transCommitProcess(oidwrlocked ARRAYDELAYWRAP1(dirwrindex), numoidwrlocked, numoidwrtotal, commitmethod, primitives, locals, params);
 #else
   transCommitProcess(oidwrlocked, numoidwrlocked);
 #endif
@@ -623,6 +680,10 @@ int alttraverseCache() {
   ARRAYDEFINES;
   struct garbagelist * oidwrlocked;
   void ** dirwrlocked;
+#if defined(STMARRAY)&&defined(DELAYCOMP)
+  int wrindex[200];
+  int * dirwrindex;
+#endif
   allocarrays;
 
   STMWRAP(for(i=0; i<TOTALNUMCLASSANDARRAY; i++) objtypetraverse[i] = 0;);
@@ -647,7 +708,7 @@ int alttraverseCache() {
          dirwrlocked[numoidwrlocked++] = objptr;
        } else {
          dirwrlocked[numoidwrlocked++] = objptr;
-         transAbortProcess(oidwrlocked, numoidwrlocked);
+         transAbortProcess(oidwrlocked, numoidwrlocked ARRAYDELAYWRAP1(NULL) ARRAYDELAYWRAP1(numoidwrlocked));
          ABORTSTAT3;
          freearrays;
          return TRANS_ABORT;
@@ -657,7 +718,7 @@ int alttraverseCache() {
          /* versions match */
          softabort=1;
        }
-       transAbortProcess(oidwrlocked, numoidwrlocked);
+       transAbortProcess(oidwrlocked, numoidwrlocked ARRAYDELAYWRAP1(NULL) ARRAYDELAYWRAP1(numoidwrlocked));
        ABORTSTAT3;
        freearrays;
        if (softabort)
@@ -673,46 +734,7 @@ int alttraverseCache() {
     curr = curr->lnext;
   }
 
-#ifdef DELAYCOMP
-  //acquire other locks
-  unsigned int numoidwrtotal=numoidwrlocked;
-  dchashlistnode_t *dc_curr = dc_c_list;
-  /* Inner loop to traverse the linked list of the cache lookupTable */
-  while(likely(dc_curr != NULL)) {
-    //if the first bin in hash table is empty
-    objheader_t * headeraddr=&((objheader_t *) dc_curr->val)[-1];
-    void *objptr=dc_curr->key;
-    objheader_t *header=(objheader_t *)(((char *)objptr)-sizeof(objheader_t));
-    if(write_trylock(&header->lock)) { //can aquire write lock
-      dirwrlocked[numoidwrtotal++] = objptr;
-    } else {
-      //maybe we already have lock
-      void * key=dc_curr->key;
-      chashlistnode_t *node = &c_table[(((unsigned INTPTR)key) & c_mask)>>4];
-      
-      do {
-       if(node->key == key) {
-         objheader_t * headeraddr=&((objheader_t *) node->val)[-1];
-         if(STATUS(headeraddr) & DIRTY) {
-           goto nextloop;
-         }
-       }
-       node = node->next;
-      } while(node != NULL);
-
-      //have to abort to avoid deadlock
-      transAbortProcess(oidwrlocked, numoidwrtotal);
-      ABORTSTAT3;
-      freearrays;
-      if (softabort)
-       return TRANS_SOFT_ABORT;
-      else
-       return TRANS_ABORT;
-    }
-  nextloop:
-    dc_curr = dc_curr->lnext;
-  }
-#endif
+  ACCESSLOCKS;
 
   //THIS IS THE SERIALIZATION END POINT (START POINT IS END OF EXECUTION)*****
   READARRAYS;
@@ -723,7 +745,7 @@ int alttraverseCache() {
     if(header->lock>0) {
       CFENCE;
       if(version != header->version) {
-       transAbortProcess(oidwrlocked, NUMWRTOTAL);
+       transAbortProcess(oidwrlocked, NUMWRTOTAL ARRAYDELAYWRAP1(dirwrindex) ARRAYDELAYWRAP1(numoidwrlocked));
        ABORTSTAT2;
        freearrays;
        return TRANS_ABORT;
@@ -733,7 +755,7 @@ int alttraverseCache() {
       //couldn't get lock because we already have it
       //check if it is the right version number
       if (version!=header->version) {
-       transAbortProcess(oidwrlocked, numoidwrtotal);
+       transAbortProcess(oidwrlocked, numoidwrtotal ARRAYDELAYWRAP1(dirwrindex) ARRAYDELAYWRAP1(numoidwrlocked));
        ABORTSTAT4;
        freearrays;
        return TRANS_ABORT;
@@ -743,7 +765,7 @@ int alttraverseCache() {
       if(version == header->version) {
        softabort=1;
       }
-      transAbortProcess(oidwrlocked, NUMWRTOTAL);
+      transAbortProcess(oidwrlocked, NUMWRTOTAL ARRAYDELAYWRAP1(dirwrindex) ARRAYDELAYWRAP1(numoidwrlocked));
       ABORTSTAT2;
       freearrays;
       if (softabort)
@@ -764,7 +786,7 @@ int alttraverseCache() {
     if(header->lock>0) { //object is not locked
       if (version!=header->version) {
        //have to abort
-       transAbortProcess(oidwrlocked, NUMWRTOTAL);
+       transAbortProcess(oidwrlocked, NUMWRTOTAL ARRAYDELAYWRAP1(dirwrindex) ARRAYDELAYWRAP1(numoidwrlocked));
        STMWRAP((typesCausingAbort[TYPE(header)])++;);
        freearrays;
        if (softabort)
@@ -801,7 +823,7 @@ int alttraverseCache() {
        }
       }
       //have to abort to avoid deadlock
-      transAbortProcess(oidwrlocked, NUMWRTOTAL);
+      transAbortProcess(oidwrlocked, NUMWRTOTAL ARRAYDELAYWRAP1(dirwrindex) ARRAYDELAYWRAP1(numoidwrlocked));
       STMWRAP((typesCausingAbort[TYPE(header)])++;);
       freearrays;
       if (softabort)
@@ -816,7 +838,7 @@ int alttraverseCache() {
 
   /* Decide the final response */
 #ifdef DELAYCOMP
-  transCommitProcess(oidwrlocked, numoidwrlocked, numoidwrtotal, commitmethod, primitives, locals, params);
+  transCommitProcess(oidwrlocked ARRAYDELAYWRAP1(dirwrindex), numoidwrlocked, numoidwrtotal, commitmethod, primitives, locals, params);
 #else
   transCommitProcess(oidwrlocked, numoidwrlocked);
 #endif
@@ -831,8 +853,12 @@ int alttraverseCache() {
  */
 
 int logflag=1;
-
+#if defined(STMARRAY)&&defined(DELAYCOMP)
+void transAbortProcess(struct garbagelist *oidwrlocked, int numoidwrtotal, int * dirwrindex, int numoidwrlocked) {
+#else
 void transAbortProcess(struct garbagelist *oidwrlocked, int numoidwrlocked) {
+#endif
   int i;
   objheader_t *header;
   /* Release read locks */
@@ -864,6 +890,26 @@ void transAbortProcess(struct garbagelist *oidwrlocked, int numoidwrlocked) {
 #endif
     write_unlock(&header->lock);
   }
+#if defined(STMARRAY)&&defined(DELAYCOMP)
+  //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
+      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
 #ifdef STMSTATS
   /* clear trec and then release objects locked */
   struct objlist *ptr=lockedobjs;
@@ -885,7 +931,7 @@ void transAbortProcess(struct garbagelist *oidwrlocked, int numoidwrlocked) {
  * =================================
  */
 #ifdef DELAYCOMP
- void transCommitProcess(struct garbagelist * oidwrlocked, int numoidwrlocked, int numoidwrtotal, void (*commitmethod)(void *, void *, void *), void * primitives, void * locals, void * params) {
+void transCommitProcess(struct garbagelist * oidwrlocked ARRAYDELAYWRAP1(int * dirwrindex), int numoidwrlocked, int numoidwrtotal, void (*commitmethod)(void *, void *, void *), void * primitives, void * locals, void * params) {
 #else
 void transCommitProcess(struct garbagelist * oidwrlocked, int numoidwrlocked) {
 #endif
@@ -955,7 +1001,11 @@ void transCommitProcess(struct garbagelist * oidwrlocked, int numoidwrlocked) {
 #endif
 
   /* Release write locks */
+#if defined(STMARRAY)&&defined(DELAYCOMP)
+  for(i=numoidwrlocked-1; i>=0; i--) {
+#else
   for(i=NUMWRTOTAL-1; i>=0; i--) {
+#endif
     struct ___Object___ * dst=dirwrlocked[i];
     header = &((objheader_t *)dst)[-1];
 #ifdef STMARRAY
@@ -985,7 +1035,26 @@ void transCommitProcess(struct garbagelist * oidwrlocked, int numoidwrlocked) {
       write_unlock(&header->lock);
     }
   }
-
+#if defined(STMARRAY)&&defined(DELAYCOMP)
+  //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
+      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
 #ifdef STMSTATS
   /* clear trec and then release objects locked */
   ptr=lockedobjs;
index 11be68a9eab5e279ea67c7210f048c3c2164c69b..3cfd6413adc4f27761bf8c6af30bb9a663388383 100644 (file)
@@ -47,11 +47,11 @@ extern __thread struct arraylist arraystack;
 
 #define RESTOREARRAY(x,z) {x=arraystack.array[arraystack.maxcount];z=arraystack.index[arraystack.maxcount++];}
 
-#define STOREARRAY(x,z) {void * y=COMPOID(x); arraystack.array[arraystack.count]=y; arraystack.index[arraystack.count++]=z; dc_t_chashInsertOnceArray(y,y,z);}
+#define STOREARRAY(x,z,t) {void * y=COMPOID(x); int ii=z;arraystack.array[arraystack.count]=y; arraystack.index[arraystack.count++]=ii; dc_t_chashInsertOnceArray(y,(ii*sizeof(t))>>INDEXSHIFT,y);}
 
 #define STOREARRAYNOLOCK(x,z) {void * y=COMPOID(x); arraystack.array[arraystack.count]=y; arraystack.index[arraystack.count++]=z;}
 
-#define STOREARRAYNOTRANS(x,z) {void * y=x; arraystack.array[arraystack.count]=y; arraystack.index[arraystack.count++]=z; dc_t_chashInsertOnceArray(y,y,z);}
+#define STOREARRAYNOTRANS(x,z,t) {void * y=x; int ii=z; arraystack.array[arraystack.count]=y; arraystack.index[arraystack.count++]=ii; dc_t_chashInsertOnceArray(y,(ii*sizeof(t))>>INDEXSHIFT,y);}
 
 #define STOREARRAYNOLOCKNOTRANS(x,z) {void * y=x; arraystack.array[arraystack.count]=y; arraystack.index[arraystack.count++]=z; }
 
index 594e3aeb53e298908641d335fc93cb49c4a95eba..77277f784be9400af2066e8797e37917c92254ec 100644 (file)
@@ -1,5 +1,6 @@
 #include "stmlookup.h"
 #include "strings.h"
+#include "tm.h"
 
 __thread chashlistnode_t *c_table;
 __thread chashlistnode_t *c_list;
@@ -274,6 +275,9 @@ void dc_t_chashInsertOnce(void * key, void *val) {
   if(ptr->key==0) {
     ptr->key=key;
     ptr->val=val;
+#ifdef STMARRAY
+    ptr->intkey=-1;
+#endif
     ptr->lnext=dc_c_list;
     dc_c_list=ptr;
     dc_c_numelements++;
@@ -301,6 +305,9 @@ void dc_t_chashInsertOnce(void * key, void *val) {
       node=&tcl->array[0];
       tcl->num=1;
     }
+#ifdef STMARRAY
+    node->intkey=-1;
+#endif
     node->key = key;
     node->val = val;
     node->next = ptr->next;
@@ -315,16 +322,16 @@ void dc_t_chashInsertOnce(void * key, void *val) {
 void dc_t_chashInsertOnceArray(void * key, unsigned int intkey, void *val) {
   dchashlistnode_t *ptr;
 
-  if (key==NULL)
+  if (unlikely(key==NULL))
     return;
 
-  if(dc_c_numelements > (dc_c_threshold)) {
+  if(unlikely(dc_c_numelements > dc_c_threshold)) {
     //Resize
     unsigned int newsize = dc_c_size << 1;
     dc_t_chashResize(newsize);
   }
 
-  ptr = &dc_c_table[(((unsigned INTPTR)key^intkey)&dc_c_mask)>>4];
+  ptr = &dc_c_table[(((unsigned INTPTR)key^(intkey<<4))&dc_c_mask)>>4];
 
   if(ptr->key==0) {
     ptr->key=key;
@@ -346,7 +353,7 @@ void dc_t_chashInsertOnceArray(void * key, unsigned int intkey, void *val) {
     } while(search != NULL);
 
     dc_c_numelements++;
-    if (dc_c_structs->num<NUMCLIST) {
+    if (likely(dc_c_structs->num<NUMCLIST)) {
       node=&dc_c_structs->array[dc_c_structs->num];
       dc_c_structs->num++;
     } else {
@@ -404,7 +411,7 @@ unsigned int dc_t_chashResize(unsigned int newsize) {
       }
 #ifdef STMARRAY
       intkey=curr->intkey;
-      index = (((unsigned INTPTR)key^intkey) & mask) >>4;
+      index = (((unsigned INTPTR)key^(intkey<<4)) & mask) >>4;
 #else
       index = (((unsigned INTPTR)key) & mask) >>4;
 #endif
index 0d74e46ffcf7aa26c98d3cfb06c7bb692af6cf92..2b83dde009fd0be424aa020d18e235f5fd271300 100644 (file)
@@ -93,7 +93,9 @@ void rd_t_chashreset();
 
 typedef struct dchashlistnode {
   void * key;
+#ifdef STMARRAY
   unsigned int intkey;
+#endif
   void * val;     //this can be cast to another type or used to point to a larger structure
   struct dchashlistnode *next;
   struct dchashlistnode *lnext;
index 250c4246522a5fc63a7ca617aa0b8b93169daa78..3690a42ed34e5b140501029c1e58788566588ccf 100644 (file)
@@ -204,7 +204,11 @@ __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
+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);
+#endif
 #else
 int transCommit();
 int traverseCache();
@@ -212,7 +216,11 @@ int alttraverseCache();
 void transCommitProcess(struct garbagelist *, int);
 #endif
 int altalttraverseCache();
+#if defined(STMARRAY)&&defined(DELAYCOMP)
+void transAbortProcess(struct garbagelist *oidwrlocked, int numoidwrtotal, int * dirwrindex, int numoidwrlocked);
+#else
 void transAbortProcess(struct garbagelist *, int);
+#endif
 void randomdelay(int);
 #if defined(STMSTATS)||defined(SOFTABORT)
 int getTotalAbortCount(int, int, void *, int, void*, int*, int*, int, objheader_t*, int*);
@@ -252,8 +260,8 @@ extern __thread struct objlist * lockedobjs;
 extern __thread int t_objnumcount;
 #endif
 
-#define likely(x) x
-#define unlikely(x) x
+#define likely(x) __builtin_expect((x),1)
+#define unlikely(x) __builtin_expect((x),0)
 
 extern void * curr_heapbase;
 extern void * curr_heapptr;