threads_internal: add 'thread_switch_to_master()' internally
authorBrian Norris <banorris@uci.edu>
Tue, 10 Apr 2012 21:09:42 +0000 (14:09 -0700)
committerBrian Norris <banorris@uci.edu>
Tue, 10 Apr 2012 21:09:42 +0000 (14:09 -0700)
In progress: moving more model-checking/thread actions so that they are
performed only by a system thread, not by the user code.

For now, we replace our uses of thread_yield() (which simply switched to the
next user thread) while thread_switch_to_master() (which will later perform
intermediate actions before choosing the next user thread).

Also, we can begin creating internal and external interfaces in
threads_indernal.h and libthreads.h, respectively.

Makefile
libatomic.cc
libthreads.cc
threads_internal.h [new file with mode: 0644]

index 327bbb5..7a442bd 100644 (file)
--- a/Makefile
+++ b/Makefile
@@ -1,7 +1,7 @@
 CC=g++
 BIN=libthreads
 SOURCE=libthreads.cc schedule.cc libatomic.cc userprog.c model.cc malloc.c
-HEADERS=libthreads.h schedule.h common.h libatomic.h model.h
+HEADERS=libthreads.h schedule.h common.h libatomic.h model.h threads_internal.h
 FLAGS=-Wall -ldl
 
 all: ${BIN}
index a00838e..daf058a 100644 (file)
@@ -1,13 +1,13 @@
 #include "libatomic.h"
-#include "libthreads.h"
+#include "threads_internal.h"
 
 void atomic_store_explicit(struct atomic_object *obj, int value, memory_order order)
 {
-       thread_yield();
+       thread_switch_to_master();
 }
 
 int atomic_load_explicit(struct atomic_object *obj, memory_order order)
 {
-       thread_yield();
+       thread_switch_to_master();
        return 0;
 }
index c0439ff..42e9198 100644 (file)
@@ -4,6 +4,7 @@
 #include "libthreads.h"
 #include "schedule.h"
 #include "common.h"
+#include "threads_internal.h"
 
 /* global "model" object */
 #include "model.h"
@@ -97,6 +98,17 @@ static void thread_wait_finish(void)
        while (!thread_system_next());
 }
 
+int thread_switch_to_master()
+{
+       struct thread *old, *next;
+
+       DBG();
+       old = thread_current();
+       old->state = THREAD_READY;
+       next = model->system_thread;
+       return thread_swap(old, next);
+}
+
 /*
  * User program API functions
  */
@@ -126,19 +138,14 @@ int thread_create(struct thread *t, void (*start_routine)(), void *arg)
 
 void thread_join(struct thread *t)
 {
-       while (t->state != THREAD_COMPLETED)
-               thread_yield();
+       int ret = 0;
+       while (t->state != THREAD_COMPLETED && !ret)
+               ret = thread_switch_to_master();
 }
 
 int thread_yield(void)
 {
-       struct thread *old, *next;
-
-       DBG();
-       old = thread_current();
-       old->state = THREAD_READY;
-       next = model->system_thread;
-       return thread_swap(old, next);
+       return thread_switch_to_master();
 }
 
 struct thread *thread_current(void)
diff --git a/threads_internal.h b/threads_internal.h
new file mode 100644 (file)
index 0000000..37b446c
--- /dev/null
@@ -0,0 +1,8 @@
+#ifndef __THREADS_INTERNAL_H__
+#define __THREADS_INTERNAL_H__
+
+#include "libthreads.h"
+
+int thread_switch_to_master();
+
+#endif /* __THREADS_INTERNAL_H__ */