Signed-off-by: Tomek Grabiec <tgrab...@gmail.com>
---
 Makefile               |    1 +
 include/vm/object.h    |    1 +
 test/arch-x86/Makefile |    1 +
 vm/jato.c              |    1 +
 vm/monitor.c           |  242 ++++++++++++++++++++++++++++++++++++++++++++++++
 vm/object.c            |  191 --------------------------------------
 6 files changed, 246 insertions(+), 191 deletions(-)
 create mode 100644 vm/monitor.c

diff --git a/Makefile b/Makefile
index 00c5522..6dcd736 100644
--- a/Makefile
+++ b/Makefile
@@ -114,6 +114,7 @@ VM_OBJS = \
        vm/jni-interface.o      \
        vm/jni.o                \
        vm/method.o             \
+       vm/monitor.o            \
        vm/natives.o            \
        vm/object.o             \
        vm/preload.o            \
diff --git a/include/vm/object.h b/include/vm/object.h
index 0d4299b..fa918b9 100644
--- a/include/vm/object.h
+++ b/include/vm/object.h
@@ -53,6 +53,7 @@ struct vm_object {
 /* XXX: BUILD_BUG_ON(offsetof(vm_object, class) != 0); */
 
 int init_vm_objects(void);
+int init_vm_monitors(void);
 
 struct vm_object *vm_object_alloc(struct vm_class *class);
 struct vm_object *vm_object_alloc_primitive_array(int type, int count);
diff --git a/test/arch-x86/Makefile b/test/arch-x86/Makefile
index e5cbb63..484d4c7 100644
--- a/test/arch-x86/Makefile
+++ b/test/arch-x86/Makefile
@@ -68,6 +68,7 @@ TOPLEVEL_OBJS := \
        vm/itable.o \
        vm/jni-interface.o \
        vm/method.o \
+       vm/monitor.o \
        vm/object.o \
        vm/static.o \
        vm/string.o \
diff --git a/vm/jato.c b/vm/jato.c
index 1c84ccf..5d0b815 100644
--- a/vm/jato.c
+++ b/vm/jato.c
@@ -1321,6 +1321,7 @@ main(int argc, char *argv[])
        classloader_init();
 
        init_vm_objects();
+       init_vm_monitors();
 
        jit_text_init();
 
diff --git a/vm/monitor.c b/vm/monitor.c
new file mode 100644
index 0000000..4a22584
--- /dev/null
+++ b/vm/monitor.c
@@ -0,0 +1,242 @@
+/*
+ * Copyright (C) 2009 Tomasz Grabiec
+ * 
+ * This file is released under the GPL version 2 with the following
+ * clarification and special exception:
+ *
+ *     Linking this library statically or dynamically with other modules is
+ *     making a combined work based on this library. Thus, the terms and
+ *     conditions of the GNU General Public License cover the whole
+ *     combination.
+ *
+ *     As a special exception, the copyright holders of this library give you
+ *     permission to link this library with independent modules to produce an
+ *     executable, regardless of the license terms of these independent
+ *     modules, and to copy and distribute the resulting executable under terms
+ *     of your choice, provided that you also meet, for each linked independent
+ *     module, the terms and conditions of the license of that module. An
+ *     independent module is a module which is not derived from or based on
+ *     this library. If you modify this library, you may extend this exception
+ *     to your version of the library, but you are not obligated to do so. If
+ *     you do not wish to do so, delete this exception statement from your
+ *     version.
+ *
+ * Please refer to the file LICENSE for details.
+ */
+
+#include <errno.h>
+#include <pthread.h>
+
+#include "jit/exception.h"
+
+#include "vm/object.h"
+#include "vm/preload.h"
+
+static pthread_mutexattr_t monitor_mutexattr;
+
+int init_vm_monitors(void)
+{
+       int err;
+
+       err = pthread_mutexattr_init(&monitor_mutexattr);
+       if (err)
+               return -err;
+
+       err = pthread_mutexattr_settype(&monitor_mutexattr,
+               PTHREAD_MUTEX_RECURSIVE);
+       if (err)
+               return -err;
+
+       return 0;
+}
+
+int vm_monitor_init(struct vm_monitor *mon)
+{
+       if (pthread_mutex_init(&mon->owner_mutex, NULL)) {
+               NOT_IMPLEMENTED;
+               return -1;
+       }
+
+       if (pthread_mutex_init(&mon->mutex, &monitor_mutexattr)) {
+               NOT_IMPLEMENTED;
+               return -1;
+       }
+
+       if (pthread_cond_init(&mon->cond, NULL)) {
+               NOT_IMPLEMENTED;
+               return -1;
+       }
+
+       mon->owner = NULL;
+       mon->lock_count = 0;
+
+       return 0;
+}
+
+struct vm_thread *vm_monitor_get_owner(struct vm_monitor *mon)
+{
+       struct vm_thread *owner;
+
+       pthread_mutex_lock(&mon->owner_mutex);
+       owner = mon->owner;
+       pthread_mutex_unlock(&mon->owner_mutex);
+
+       return owner;
+}
+
+void vm_monitor_set_owner(struct vm_monitor *mon, struct vm_thread *owner)
+{
+       pthread_mutex_lock(&mon->owner_mutex);
+       mon->owner = owner;
+       pthread_mutex_unlock(&mon->owner_mutex);
+}
+
+int vm_monitor_lock(struct vm_monitor *mon)
+{
+       struct vm_thread *self;
+       int err;
+
+       self = vm_thread_self();
+       err = 0;
+
+       if (pthread_mutex_trylock(&mon->mutex)) {
+               /*
+                * XXX: according to Thread.getState() documentation thread
+                * state does not have to be precise, it's used rather
+                * for monitoring.
+                */
+               vm_thread_set_state(self, VM_THREAD_STATE_BLOCKED);
+               err = pthread_mutex_lock(&mon->mutex);
+               vm_thread_set_state(self, VM_THREAD_STATE_RUNNABLE);
+       }
+
+       /* If err is non zero the lock has not been acquired. */
+       if (!err) {
+               vm_monitor_set_owner(mon, self);
+               mon->lock_count++;
+       }
+
+       return err;
+}
+
+int vm_monitor_unlock(struct vm_monitor *mon)
+{
+       if (vm_monitor_get_owner(mon) != vm_thread_self()) {
+               signal_new_exception(vm_java_lang_IllegalMonitorStateException,
+                                    NULL);
+               return -1;
+       }
+
+       if (--mon->lock_count == 0)
+               vm_monitor_set_owner(mon, NULL);
+
+       int err = pthread_mutex_unlock(&mon->mutex);
+
+       /* If err is non zero the lock has not been released. */
+       if (err) {
+               ++mon->lock_count;
+               vm_monitor_set_owner(mon, vm_thread_self());
+       }
+
+       return err;
+}
+
+int vm_monitor_timed_wait(struct vm_monitor *mon, long long ms, int ns)
+{
+       struct vm_thread *self;
+       struct timespec timespec;
+       int old_lock_count;
+       int err;
+
+       if (vm_monitor_get_owner(mon) != vm_thread_self()) {
+               signal_new_exception(vm_java_lang_IllegalMonitorStateException,
+                                    NULL);
+               return -1;
+       }
+
+       /*
+        * XXX: we must use CLOCK_REALTIME here because
+        * pthread_cond_timedwait() uses this clock.
+        */
+       clock_gettime(CLOCK_REALTIME, &timespec);
+
+       timespec.tv_sec += ms / 1000;
+       timespec.tv_nsec += (long)ns + (long)(ms % 1000) * 1000000l;
+
+       if (timespec.tv_nsec >= 1000000000l) {
+               timespec.tv_sec++;
+               timespec.tv_nsec -= 1000000000l;
+       }
+
+       old_lock_count = mon->lock_count;
+
+       mon->lock_count = 0;
+       vm_monitor_set_owner(mon, NULL);
+
+       self = vm_thread_self();
+
+       vm_thread_set_state(self, VM_THREAD_STATE_TIMED_WAITING);
+       err = pthread_cond_timedwait(&mon->cond, &mon->mutex, &timespec);
+       vm_thread_set_state(self, VM_THREAD_STATE_RUNNABLE);
+
+       if (err == ETIMEDOUT)
+               err = 0;
+
+       vm_monitor_set_owner(mon, self);
+       mon->lock_count = old_lock_count;
+
+       /* TODO: check if thread has been interrupted. */
+       return err;
+}
+
+int vm_monitor_wait(struct vm_monitor *mon)
+{
+       struct vm_thread *self;
+       int old_lock_count;
+       int err;
+
+       self = vm_thread_self();
+
+       if (vm_monitor_get_owner(mon) != vm_thread_self()) {
+               signal_new_exception(vm_java_lang_IllegalMonitorStateException,
+                                    NULL);
+               return -1;
+       }
+
+       old_lock_count = mon->lock_count;
+
+       mon->lock_count = 0;
+       vm_monitor_set_owner(mon, NULL);
+
+       vm_thread_set_state(self, VM_THREAD_STATE_WAITING);
+       err = pthread_cond_wait(&mon->cond, &mon->mutex);
+       vm_thread_set_state(self, VM_THREAD_STATE_RUNNABLE);
+
+       vm_monitor_set_owner(mon, self);
+       mon->lock_count = old_lock_count;
+
+       /* TODO: check if thread has been interrupted. */
+       return err;
+}
+
+int vm_monitor_notify(struct vm_monitor *mon)
+{
+       if (vm_monitor_get_owner(mon) != vm_thread_self()) {
+               signal_new_exception(vm_java_lang_IllegalMonitorStateException,
+                                    NULL);
+               return -1;
+       }
+
+       return pthread_cond_signal(&mon->cond);
+}
+
+int vm_monitor_notify_all(struct vm_monitor *mon)
+{
+       if (vm_monitor_get_owner(mon) != vm_get_exec_env()->thread) {
+               signal_new_exception(vm_java_lang_IllegalMonitorStateException,
+                                    NULL);
+               return -1;
+       }
+
+       return pthread_cond_broadcast(&mon->cond);
+}
diff --git a/vm/object.c b/vm/object.c
index 913458d..9b41ec1 100644
--- a/vm/object.c
+++ b/vm/object.c
@@ -568,194 +568,3 @@ char *vm_string_to_cstr(const struct vm_object 
*string_obj)
        free_str(str);
        return result;
 }
-
-int vm_monitor_init(struct vm_monitor *mon)
-{
-       if (pthread_mutex_init(&mon->owner_mutex, NULL)) {
-               NOT_IMPLEMENTED;
-               return -1;
-       }
-
-       if (pthread_mutex_init(&mon->mutex, &obj_mutexattr)) {
-               NOT_IMPLEMENTED;
-               return -1;
-       }
-
-       if (pthread_cond_init(&mon->cond, NULL)) {
-               NOT_IMPLEMENTED;
-               return -1;
-       }
-
-       mon->owner = NULL;
-       mon->lock_count = 0;
-
-       return 0;
-}
-
-struct vm_thread *vm_monitor_get_owner(struct vm_monitor *mon)
-{
-       struct vm_thread *owner;
-
-       pthread_mutex_lock(&mon->owner_mutex);
-       owner = mon->owner;
-       pthread_mutex_unlock(&mon->owner_mutex);
-
-       return owner;
-}
-
-void vm_monitor_set_owner(struct vm_monitor *mon, struct vm_thread *owner)
-{
-       pthread_mutex_lock(&mon->owner_mutex);
-       mon->owner = owner;
-       pthread_mutex_unlock(&mon->owner_mutex);
-}
-
-int vm_monitor_lock(struct vm_monitor *mon)
-{
-       struct vm_thread *self;
-       int err;
-
-       self = vm_thread_self();
-       err = 0;
-
-       if (pthread_mutex_trylock(&mon->mutex)) {
-               /*
-                * XXX: according to Thread.getState() documentation thread
-                * state does not have to be precise, it's used rather
-                * for monitoring.
-                */
-               vm_thread_set_state(self, VM_THREAD_STATE_BLOCKED);
-               err = pthread_mutex_lock(&mon->mutex);
-               vm_thread_set_state(self, VM_THREAD_STATE_RUNNABLE);
-       }
-
-       /* If err is non zero the lock has not been acquired. */
-       if (!err) {
-               vm_monitor_set_owner(mon, self);
-               mon->lock_count++;
-       }
-
-       return err;
-}
-
-int vm_monitor_unlock(struct vm_monitor *mon)
-{
-       if (vm_monitor_get_owner(mon) != vm_thread_self()) {
-               signal_new_exception(vm_java_lang_IllegalMonitorStateException,
-                                    NULL);
-               return -1;
-       }
-
-       if (--mon->lock_count == 0)
-               vm_monitor_set_owner(mon, NULL);
-
-       int err = pthread_mutex_unlock(&mon->mutex);
-
-       /* If err is non zero the lock has not been released. */
-       if (err) {
-               ++mon->lock_count;
-               vm_monitor_set_owner(mon, vm_thread_self());
-       }
-
-       return err;
-}
-
-int vm_monitor_timed_wait(struct vm_monitor *mon, long long ms, int ns)
-{
-       struct vm_thread *self;
-       struct timespec timespec;
-       int old_lock_count;
-       int err;
-
-       if (vm_monitor_get_owner(mon) != vm_thread_self()) {
-               signal_new_exception(vm_java_lang_IllegalMonitorStateException,
-                                    NULL);
-               return -1;
-       }
-
-       /*
-        * XXX: we must use CLOCK_REALTIME here because
-        * pthread_cond_timedwait() uses this clock.
-        */
-       clock_gettime(CLOCK_REALTIME, &timespec);
-
-       timespec.tv_sec += ms / 1000;
-       timespec.tv_nsec += (long)ns + (long)(ms % 1000) * 1000000l;
-
-       if (timespec.tv_nsec >= 1000000000l) {
-               timespec.tv_sec++;
-               timespec.tv_nsec -= 1000000000l;
-       }
-
-       old_lock_count = mon->lock_count;
-
-       mon->lock_count = 0;
-       vm_monitor_set_owner(mon, NULL);
-
-       self = vm_thread_self();
-
-       vm_thread_set_state(self, VM_THREAD_STATE_TIMED_WAITING);
-       err = pthread_cond_timedwait(&mon->cond, &mon->mutex, &timespec);
-       vm_thread_set_state(self, VM_THREAD_STATE_RUNNABLE);
-
-       if (err == ETIMEDOUT)
-               err = 0;
-
-       vm_monitor_set_owner(mon, self);
-       mon->lock_count = old_lock_count;
-
-       /* TODO: check if thread has been interrupted. */
-       return err;
-}
-
-int vm_monitor_wait(struct vm_monitor *mon)
-{
-       struct vm_thread *self;
-       int old_lock_count;
-       int err;
-
-       self = vm_thread_self();
-
-       if (vm_monitor_get_owner(mon) != vm_thread_self()) {
-               signal_new_exception(vm_java_lang_IllegalMonitorStateException,
-                                    NULL);
-               return -1;
-       }
-
-       old_lock_count = mon->lock_count;
-
-       mon->lock_count = 0;
-       vm_monitor_set_owner(mon, NULL);
-
-       vm_thread_set_state(self, VM_THREAD_STATE_WAITING);
-       err = pthread_cond_wait(&mon->cond, &mon->mutex);
-       vm_thread_set_state(self, VM_THREAD_STATE_RUNNABLE);
-
-       vm_monitor_set_owner(mon, self);
-       mon->lock_count = old_lock_count;
-
-       /* TODO: check if thread has been interrupted. */
-       return err;
-}
-
-int vm_monitor_notify(struct vm_monitor *mon)
-{
-       if (vm_monitor_get_owner(mon) != vm_thread_self()) {
-               signal_new_exception(vm_java_lang_IllegalMonitorStateException,
-                                    NULL);
-               return -1;
-       }
-
-       return pthread_cond_signal(&mon->cond);
-}
-
-int vm_monitor_notify_all(struct vm_monitor *mon)
-{
-       if (vm_monitor_get_owner(mon) != vm_get_exec_env()->thread) {
-               signal_new_exception(vm_java_lang_IllegalMonitorStateException,
-                                    NULL);
-               return -1;
-       }
-
-       return pthread_cond_broadcast(&mon->cond);
-}
-- 
1.6.0.4


------------------------------------------------------------------------------
Come build with us! The BlackBerry(R) Developer Conference in SF, CA
is the only developer event you need to attend this year. Jumpstart your
developing skills, take BlackBerry mobile applications to market and stay 
ahead of the curve. Join us from November 9 - 12, 2009. Register now!
http://p.sf.net/sfu/devconference
_______________________________________________
Jatovm-devel mailing list
Jatovm-devel@lists.sourceforge.net
https://lists.sourceforge.net/lists/listinfo/jatovm-devel

Reply via email to