Merged.
[cacao.git] / src / threads / thread.cpp
index 4d4d4c6440d25fe49eed0429647927590400753f..fefb4a34f662c6465c63b023f1d3416ccf01a849 100644 (file)
 # include "mm/boehm-gc/include/gc.h"
 #endif
 
-#include "native/jni.h"
 #include "native/llni.h"
-#include "native/native.h"
+#include "native/native.hpp"
 
-#include "threads/lock-common.h"
-#include "threads/threadlist.h"
+#include "threads/lock.hpp"
+#include "threads/threadlist.hpp"
 #include "threads/thread.hpp"
 
-#include "vm/builtin.h"
-#include "vm/class.h"
+#include "vm/jit/builtin.hpp"
+#include "vm/class.hpp"
 #include "vm/exceptions.hpp"
 #include "vm/globals.hpp"
 #include "vm/javaobjects.hpp"
-#include "vm/method.h"
+#include "vm/method.hpp"
 #include "vm/options.h"
 #include "vm/string.hpp"
 #include "vm/utf8.h"
@@ -65,9 +64,6 @@
 #include "vm/jit/stacktrace.hpp"
 
 
-// FIXME
-extern "C" {
-
 /* global variables ***********************************************************/
 
 static methodinfo    *thread_method_init;
@@ -409,7 +405,7 @@ static void thread_create_initial_thread(void)
        /* Get the main-thread (NOTE: The main thread is always the first
           thread in the list). */
 
-       t = threadlist_first();
+       t = ThreadList::get_main_thread();
 
        /* The thread name. */
 
@@ -451,21 +447,17 @@ static threadobject *thread_new(void)
        
        /* Lock the thread lists */
 
-       threadlist_lock();
+       ThreadList::lock();
 
-       index = threadlist_get_free_index();
+       index = ThreadList::get_free_thread_index();
 
        /* Allocate a thread data structure. */
 
        /* First, try to get one from the free-list. */
 
-       t = threadlist_free_first();
+       t = ThreadList::get_free_thread();
 
        if (t != NULL) {
-               /* Remove from free list. */
-
-               threadlist_free_remove(t);
-
                /* Equivalent of MZERO on the else path */
 
                threads_impl_thread_clear(t);
@@ -486,6 +478,20 @@ static threadobject *thread_new(void)
 
                MZERO(t, threadobject, 1);
 
+               // Initialize the mutex and the condition.
+               t->flc_lock = new Mutex();
+               t->flc_cond = new Condition();
+
+               t->waitmutex = new Mutex();
+               t->waitcond = new Condition();
+
+               t->suspendmutex = new Mutex();
+               t->suspendcond = new Condition();
+
+#if defined(ENABLE_TLH)
+               tlh_init(&(t->tlh));
+#endif
+
 #if defined(ENABLE_GC_CACAO)
                /* Register reference to java.lang.Thread with the GC. */
                /* FIXME is it ok to do this only once? */
@@ -494,9 +500,7 @@ static threadobject *thread_new(void)
                gc_reference_register(&(t->_exceptionptr), GC_REFTYPE_THREADOBJECT);
 #endif
 
-               /* Initialize the implementation-specific bits. */
-
-               threads_impl_thread_init(t);
+               t->_dumpmemory = new DumpMemory();
        }
 
        /* Pre-compute the thinlock-word. */
@@ -504,7 +508,7 @@ static threadobject *thread_new(void)
        assert(index != 0);
 
        t->index     = index;
-       t->thinlock  = lock_pre_compute_thinlock(t->index);
+       t->thinlock  = Lockword::pre_compute_thinlock(t->index);
        t->flags     = 0;
        t->state     = THREAD_STATE_NEW;
 
@@ -518,11 +522,11 @@ static threadobject *thread_new(void)
 
        /* Add the thread to the thread list. */
 
-       threadlist_add(t);
+       ThreadList::add_to_active_thread_list(t);
 
        /* Unlock the thread lists. */
 
-       threadlist_unlock();
+       ThreadList::unlock();
 
        return t;
 }
@@ -541,29 +545,13 @@ static threadobject *thread_new(void)
 
 void thread_free(threadobject *t)
 {
-       /* Lock the thread lists. */
-
-       threadlist_lock();
-
-       /* Remove the thread from the thread-list. */
-
-       threadlist_remove(t);
-
-       /* Add the thread index to the free list. */
-
-       threadlist_index_add(t->index);
-
        /* Set the reference to the Java object to NULL. */
 
        thread_set_object(t, NULL);
 
-       /* Add the thread data structure to the free list. */
-
-       threadlist_free_add(t);
-
-       /* Unlock the thread lists. */
+       /* Release the thread. */
 
-       threadlist_unlock();
+       ThreadList::release_thread(t);
 }
 
 
@@ -887,7 +875,7 @@ void thread_fprint_name(threadobject *t, FILE *stream)
 #elif defined(WITH_JAVA_RUNTIME_LIBRARY_OPENJDK) || defined(WITH_JAVA_RUNTIME_LIBRARY_CLDC1_1)
 
        /* FIXME: In OpenJDK and CLDC the name is a char[]. */
-       java_chararray_t *name;
+       //java_chararray_t *name;
 
        /* FIXME This prints to stdout. */
        utf_display_printable_ascii(utf_null);
@@ -960,6 +948,12 @@ void thread_print_info(threadobject *t)
        case THREAD_STATE_TIMED_WAITING:
                printf(" waiting on condition");
                break;
+       case THREAD_STATE_PARKED:
+               printf(" parked");
+               break;
+       case THREAD_STATE_TIMED_PARKED:
+               printf(" timed parked");
+               break;
        case THREAD_STATE_TERMINATED:
                printf(" terminated");
                break;
@@ -1006,7 +1000,7 @@ void thread_set_state_runnable(threadobject *t)
 {
        /* Set the state inside a lock. */
 
-       threadlist_lock();
+       ThreadList::lock();
 
        if (t->state != THREAD_STATE_TERMINATED) {
                t->state = THREAD_STATE_RUNNABLE;
@@ -1014,7 +1008,7 @@ void thread_set_state_runnable(threadobject *t)
                DEBUGTHREADS("is RUNNABLE", t);
        }
 
-       threadlist_unlock();
+       ThreadList::unlock();
 }
 
 
@@ -1031,7 +1025,7 @@ void thread_set_state_waiting(threadobject *t)
 {
        /* Set the state inside a lock. */
 
-       threadlist_lock();
+       ThreadList::lock();
 
        if (t->state != THREAD_STATE_TERMINATED) {
                t->state = THREAD_STATE_WAITING;
@@ -1039,7 +1033,7 @@ void thread_set_state_waiting(threadobject *t)
                DEBUGTHREADS("is WAITING", t);
        }
 
-       threadlist_unlock();
+       ThreadList::unlock();
 }
 
 
@@ -1057,7 +1051,7 @@ void thread_set_state_timed_waiting(threadobject *t)
 {
        /* Set the state inside a lock. */
 
-       threadlist_lock();
+       ThreadList::lock();
 
        if (t->state != THREAD_STATE_TERMINATED) {
                t->state = THREAD_STATE_TIMED_WAITING;
@@ -1065,7 +1059,57 @@ void thread_set_state_timed_waiting(threadobject *t)
                DEBUGTHREADS("is TIMED_WAITING", t);
        }
 
-       threadlist_unlock();
+       ThreadList::unlock();
+}
+
+
+/* thread_set_state_parked *****************************************************
+
+   Set the current state of the given thread to THREAD_STATE_PARKED.
+
+   NOTE: If the thread has already terminated, don't set the state.
+         This is important for threads_detach_thread.
+
+*******************************************************************************/
+
+void thread_set_state_parked(threadobject *t)
+{
+       /* Set the state inside a lock. */
+
+       ThreadList::lock();
+
+       if (t->state != THREAD_STATE_TERMINATED) {
+               t->state = THREAD_STATE_PARKED;
+
+               DEBUGTHREADS("is PARKED", t);
+       }
+
+       ThreadList::unlock();
+}
+
+
+/* thread_set_state_timed_parked ***********************************************
+
+   Set the current state of the given thread to THREAD_STATE_TIMED_PARKED.
+
+   NOTE: If the thread has already terminated, don't set the state.
+         This is important for threads_detach_thread.
+
+*******************************************************************************/
+
+void thread_set_state_timed_parked(threadobject *t)
+{
+       /* Set the state inside a lock. */
+
+       ThreadList::lock();
+
+       if (t->state != THREAD_STATE_TERMINATED) {
+               t->state = THREAD_STATE_TIMED_PARKED;
+
+               DEBUGTHREADS("is TIMED_PARKED", t);
+       }
+
+       ThreadList::unlock();
 }
 
 
@@ -1080,13 +1124,13 @@ void thread_set_state_terminated(threadobject *t)
 {
        /* Set the state inside a lock. */
 
-       threadlist_lock();
+       ThreadList::lock();
 
        t->state = THREAD_STATE_TERMINATED;
 
        DEBUGTHREADS("is TERMINATED", t);
 
-       threadlist_unlock();
+       ThreadList::unlock();
 }
 
 
@@ -1112,23 +1156,11 @@ threadobject *thread_get_thread(java_handle_t *h)
 #elif defined(WITH_JAVA_RUNTIME_LIBRARY_OPENJDK)
 
        /* XXX This is just a quick hack. */
-       threadobject* t;
-       bool          equal;
-
-       threadlist_lock();
-
-       for (t = threadlist_first(); t != NULL; t = threadlist_next(t)) {
-               LLNI_equals(t->object, h, equal);
-
-               if (equal == true)
-                       break;
-       }
-
-       threadlist_unlock();
+       threadobject* t = ThreadList::get_thread_from_java_object(h);
 
 #elif defined(WITH_JAVA_RUNTIME_LIBRARY_CLDC1_1)
 
-       log_println("threads_get_thread: IMPLEMENT ME!");
+       log_println("thread_get_thread: IMPLEMENT ME!");
        threadobject* t = NULL;
 
 #else
@@ -1160,6 +1192,8 @@ bool threads_thread_is_alive(threadobject *t)
        case THREAD_STATE_BLOCKED:
        case THREAD_STATE_WAITING:
        case THREAD_STATE_TIMED_WAITING:
+       case THREAD_STATE_PARKED:
+       case THREAD_STATE_TIMED_PARKED:
                return true;
 
        default:
@@ -1172,66 +1206,6 @@ bool threads_thread_is_alive(threadobject *t)
 }
 
 
-/* threads_dump ****************************************************************
-
-   Dumps info for all threads running in the JVM.  This function is
-   called when SIGQUIT (<ctrl>-\) is sent to CACAO.
-
-*******************************************************************************/
-
-void threads_dump(void)
-{
-       threadobject *t;
-
-       /* XXX we should stop the world here */
-
-       /* Lock the thread lists. */
-
-       threadlist_lock();
-
-       printf("Full thread dump CACAO "VERSION":\n");
-
-       /* iterate over all started threads */
-
-       for (t = threadlist_first(); t != NULL; t = threadlist_next(t)) {
-               /* ignore threads which are in state NEW */
-               if (t->state == THREAD_STATE_NEW)
-                       continue;
-
-#if defined(ENABLE_GC_CACAO)
-               /* Suspend the thread. */
-               /* XXX Is the suspend reason correct? */
-
-               if (threads_suspend_thread(t, SUSPEND_REASON_JNI) == false)
-                       vm_abort("threads_dump: threads_suspend_thread failed");
-#endif
-
-               /* Print thread info. */
-
-               printf("\n");
-               thread_print_info(t);
-               printf("\n");
-
-               /* Print trace of thread. */
-
-               stacktrace_print_of_thread(t);
-
-#if defined(ENABLE_GC_CACAO)
-               /* Resume the thread. */
-
-               if (threads_resume_thread(t) == false)
-                       vm_abort("threads_dump: threads_resume_thread failed");
-#endif
-       }
-
-       /* Unlock the thread lists. */
-
-       threadlist_unlock();
-}
-
-} // extern "C"
-
-
 /*
  * These are local overrides for various environment variables in Emacs.
  * Please do not remove this and leave it at the end of the file, where