Make atomics actually write to memory for compatibility with normal accesses
authorbdemsky <bdemsky@uci.edu>
Tue, 16 Jul 2019 23:34:29 +0000 (16:34 -0700)
committerbdemsky <bdemsky@uci.edu>
Tue, 16 Jul 2019 23:34:29 +0000 (16:34 -0700)
cmodelint.cc
datarace.cc
datarace.h

index c052552..5b37e86 100644 (file)
@@ -8,6 +8,7 @@
 #include "cmodelint.h"
 #include "snapshot-interface.h"
 #include "threads-model.h"
+#include "datarace.h"
 
 memory_order orders[6] = {
        memory_order_relaxed, memory_order_consume, memory_order_acquire,
@@ -98,6 +99,10 @@ void model_rmwc_action_helper(void *obj, int atomic_index, const char *position)
                ensureModel();                                                      \
                model->switch_to_master(new ModelAction(ATOMIC_INIT, position, memory_order_relaxed, obj, (uint64_t) val)); \
                *((uint ## size ## _t *)obj) = val;                                 \
+               thread_id_t tid = thread_current()->get_id();           \
+               for(int i=0;i < size / 8;i++) {                       \
+                       recordWrite(tid, (void *)(((char *)obj)+i));          \
+               }                                                       \
        }
 
 CDSATOMICINT(8)
@@ -119,12 +124,15 @@ CDSATOMICLOAD(32)
 CDSATOMICLOAD(64)
 
 // cds atomic stores
-
 #define CDSATOMICSTORE(size)                                            \
        void cds_atomic_store ## size(void * obj, uint ## size ## _t val, int atomic_index, const char * position) { \
                ensureModel();                                                        \
                model->switch_to_master(new ModelAction(ATOMIC_WRITE, position, orders[atomic_index], obj, (uint64_t) val)); \
-               *((uint ## size ## _t *)obj) = val;                                   \
+               *((uint ## size ## _t *)obj) = val;                     \
+               thread_id_t tid = thread_current()->get_id();           \
+               for(int i=0;i < size / 8;i++) {                       \
+                       recordWrite(tid, (void *)(((char *)obj)+i));          \
+               }                                                       \
        }
 
 CDSATOMICSTORE(8)
@@ -140,6 +148,11 @@ CDSATOMICSTORE(64)
                uint ## size ## _t _val = val;                                            \
                _copy __op__ _val;                                                    \
                model_rmw_action_helper(addr, (uint64_t) _copy, atomic_index, position);        \
+               *((uint ## size ## _t *)addr) = _copy;                  \
+               thread_id_t tid = thread_current()->get_id();           \
+               for(int i=0;i < size / 8;i++) {                       \
+                       recordWrite(tid, (void *)(((char *)addr)+i));         \
+               }                                                       \
                return _old;                                                          \
        })
 
@@ -219,7 +232,13 @@ CDSATOMICXOR(64)
                uint ## size ## _t _expected = expected;                                                          \
                uint ## size ## _t _old = model_rmwrcas_action_helper(addr, atomic_index, _expected, sizeof(_expected), position); \
                if (_old == _expected) {                                                                    \
-                       model_rmw_action_helper(addr, (uint64_t) _desired, atomic_index, position); return _expected; }      \
+                       model_rmw_action_helper(addr, (uint64_t) _desired, atomic_index, position); \
+                       *((uint ## size ## _t *)addr) = desired;                        \
+                       thread_id_t tid = thread_current()->get_id();           \
+                       for(int i=0;i < size / 8;i++) {                       \
+                               recordWrite(tid, (void *)(((char *)addr)+i));         \
+                       }                                                       \
+                       return _expected; }                                     \
                else {                                                                                        \
                        model_rmwc_action_helper(addr, atomic_index, position); _expected = _old; return _old; }              \
        })
index d15ca50..b3ce8ab 100644 (file)
@@ -270,6 +270,42 @@ Exit:
                else model_free(race);
        }
 }
+
+/** This function does race detection for a write on an expanded record. */
+void fullRecordWrite(thread_id_t thread, void *location, uint64_t *shadow, ClockVector *currClock) {
+       struct RaceRecord *record = (struct RaceRecord *)(*shadow);
+       record->numReads = 0;
+       record->writeThread = thread;
+       modelclock_t ourClock = currClock->getClock(thread);
+       record->writeClock = ourClock;
+}
+
+/** This function just updates metadata on atomic write. */
+void recordWrite(thread_id_t thread, void *location) {
+       uint64_t *shadow = lookupAddressEntry(location);
+       uint64_t shadowval = *shadow;
+       ClockVector *currClock = get_execution()->get_cv(thread);
+       /* Do full record */
+       if (shadowval != 0 && !ISSHORTRECORD(shadowval)) {
+               fullRecordWrite(thread, location, shadow, currClock);
+               return;
+       }
+
+       int threadid = id_to_int(thread);
+       modelclock_t ourClock = currClock->getClock(thread);
+
+       /* Thread ID is too large or clock is too large. */
+       if (threadid > MAXTHREADID || ourClock > MAXWRITEVECTOR) {
+               expandRecord(shadow);
+               fullRecordWrite(thread, location, shadow, currClock);
+               return;
+       }
+
+       *shadow = ENCODEOP(0, 0, threadid, ourClock);
+}
+
+
+
 /** This function does race detection on a read for an expanded record. */
 struct DataRace * fullRaceCheckRead(thread_id_t thread, const void *location, uint64_t *shadow, ClockVector *currClock)
 {
index 7e4e68e..7c84121 100644 (file)
@@ -45,6 +45,7 @@ struct DataRace {
 void initRaceDetector();
 void raceCheckWrite(thread_id_t thread, void *location);
 void raceCheckRead(thread_id_t thread, const void *location);
+void recordWrite(thread_id_t thread, void *location);
 bool checkDataRaces();
 void assert_race(struct DataRace *race);