Update readme
[c11tester.git] / threads.cc
index 93160310466d6539d0863118c048e69ebbf7621d..bd1b624959629d3613e76afda0b72a58e795d122 100644 (file)
@@ -16,8 +16,9 @@
 #include "schedule.h"
 #include "clockvector.h"
 
-#ifdef TLS
 #include <dlfcn.h>
+
+#ifdef TLS
 uintptr_t get_tls_addr() {
        uintptr_t addr;
        asm ("mov %%fs:0, %0" : "=r" (addr));
@@ -60,6 +61,19 @@ Thread * thread_current(void)
        return model->get_current_thread();
 }
 
+/**
+ * @brief Get the current Thread id
+ *
+ * Must be called from a user context
+ *
+ * @return The id of the currently executing thread
+ */
+thread_id_t thread_current_id(void)
+{
+       ASSERT(model);
+       return model->get_current_thread_id();
+}
+
 void modelexit() {
        model->switch_thread(new ModelAction(THREAD_FINISH, std::memory_order_seq_cst, thread_current()));
 }
@@ -97,6 +111,13 @@ void thread_startup()
 #endif
 }
 
+
+static int (*real_epoll_wait_p)(int epfd, struct epoll_event *events, int maxevents, int timeout) = NULL;
+
+int real_epoll_wait(int epfd, struct epoll_event *events, int maxevents, int timeout) {
+       return real_epoll_wait_p(epfd, events, maxevents, timeout);
+}
+
 static int (*pthread_mutex_init_p)(pthread_mutex_t *__mutex, const pthread_mutexattr_t *__mutexattr) = NULL;
 
 int real_pthread_mutex_init(pthread_mutex_t *__mutex, const pthread_mutexattr_t *__mutexattr) {
@@ -135,6 +156,13 @@ void real_pthread_exit (void * value_ptr) {
 
 void real_init_all() {
        char * error;
+       if (!real_epoll_wait_p) {
+               real_epoll_wait_p = (int (*)(int epfd, struct epoll_event *events, int maxevents, int timeout))dlsym(RTLD_NEXT, "epoll_wait");
+               if ((error = dlerror()) != NULL) {
+                       fputs(error, stderr);
+                       exit(EXIT_FAILURE);
+               }
+       }
        if (!pthread_mutex_init_p) {
                pthread_mutex_init_p = (int (*)(pthread_mutex_t *__mutex, const pthread_mutexattr_t *__mutexattr))dlsym(RTLD_NEXT, "pthread_mutex_init");
                if ((error = dlerror()) != NULL) {
@@ -333,7 +361,6 @@ int Thread::swap(ucontext_t *ctxt, Thread *t)
 
 int Thread::swap(Thread *t, Thread *t2)
 {
-       t->set_state(THREAD_READY);
        t2->set_state(THREAD_RUNNING);
        if (t == t2)
                return 0;
@@ -358,12 +385,12 @@ void Thread::freeResources() {
                stack_free(stack);
 #ifdef TLS
        if (this != model->getInitThread()) {
-               ASSERT(thread_current()==NULL);
                real_pthread_mutex_unlock(&mutex2);
                real_pthread_join(thread, NULL);
                stack_free(helper_stack);
        }
 #endif
+       state = THREAD_FREED;
 }
 
 /**
@@ -379,6 +406,7 @@ Thread::Thread(thread_id_t tid) :
        acq_fence_cv(new ClockVector()),
        creation(NULL),
        pending(NULL),
+       wakeup_state(false),
        start_routine(NULL),
        arg(NULL),
        stack(NULL),
@@ -391,6 +419,8 @@ Thread::Thread(thread_id_t tid) :
        last_action_val(0),
        model_thread(true)
 {
+       // real_memset is not defined when
+       // the model thread is constructed
        memset(&context, 0, sizeof(context));
 }
 
@@ -405,6 +435,7 @@ Thread::Thread(thread_id_t tid, thrd_t *t, void (*func)(void *), void *a, Thread
        acq_fence_cv(new ClockVector()),
        creation(NULL),
        pending(NULL),
+       wakeup_state(false),
        start_routine(func),
        pstart_routine(NULL),
        arg(a),
@@ -438,6 +469,7 @@ Thread::Thread(thread_id_t tid, thrd_t *t, void *(*func)(void *), void *a, Threa
        acq_fence_cv(new ClockVector()),
        creation(NULL),
        pending(NULL),
+       wakeup_state(false),
        start_routine(NULL),
        pstart_routine(func),
        arg(a),
@@ -493,13 +525,15 @@ Thread * Thread::waiting_on() const
        if (!pending)
                return NULL;
 
-       if (pending->get_type() == THREAD_JOIN)
-               return pending->get_thread_operand();
-       else if (pending->get_type() == PTHREAD_JOIN)
-               return pending->get_thread_operand();
-       else if (pending->is_lock())
-               return (Thread *)pending->get_mutex()->get_state()->locked;
-       return NULL;
+       switch (pending->get_type()) {
+               case THREAD_JOIN:
+               case PTHREAD_JOIN:
+                       return pending->get_thread_operand();
+               case ATOMIC_LOCK:
+                       return (Thread *)pending->get_mutex()->get_state()->locked;
+               default:
+                       return NULL;
+       }
 }
 
 /**