Index: vm/vmcore/src/kernel_classes/native/java_lang_VMThreadManager.h =================================================================== --- vm/vmcore/src/kernel_classes/native/java_lang_VMThreadManager.h (revision 548781) +++ vm/vmcore/src/kernel_classes/native/java_lang_VMThreadManager.h (working copy) @@ -157,6 +157,19 @@ */ JNIEXPORT jlong JNICALL Java_java_lang_VMThreadManager_init (JNIEnv *, jclass, jobject, jobject, jlong); + +/* + * Method: java.lang.VMThreadManager.acquireGlobalLock()v + */ +JNIEXPORT void JNICALL Java_java_lang_VMThreadManager_acquireGlobalLock + (JNIEnv * UNREF jenv, jclass UNREF clazz); + +/* + * Method: java.lang.VMThreadManager.releaseGlobalLock()v + */ +JNIEXPORT void JNICALL Java_java_lang_VMThreadManager_releaseGlobalLock + (JNIEnv * UNREF jenv, jclass UNREF clazz); + #ifdef __cplusplus } #endif Index: vm/vmcore/src/kernel_classes/native/java_lang_VMThreadManager.cpp =================================================================== --- vm/vmcore/src/kernel_classes/native/java_lang_VMThreadManager.cpp (revision 548781) +++ vm/vmcore/src/kernel_classes/native/java_lang_VMThreadManager.cpp (working copy) @@ -261,9 +261,33 @@ return state; } +/* + * Class: java_lang_VMThreadManager + * Method: acquireGlobalLock + * Signature: ()v + */ +JNIEXPORT void JNICALL Java_java_lang_VMThreadManager_acquireGlobalLock + (JNIEnv * UNREF jenv, jclass UNREF clazz) +{ + IDATA stat = hythread_global_lock(); + assert(stat == TM_ERROR_NONE); +} /* * Class: java_lang_VMThreadManager + * Method: releaseGlobalLock + * Signature: ()v + */ +JNIEXPORT void JNICALL Java_java_lang_VMThreadManager_releaseGlobalLock + (JNIEnv * UNREF jenv, jclass UNREF clazz) +{ + IDATA stat = hythread_global_unlock(); + assert(stat == TM_ERROR_NONE); +} + + +/* + * Class: java_lang_VMThreadManager * Method: yield * Signature: ()I */ Index: vm/vmcore/src/kernel_classes/javasrc/java/lang/VMThreadManager.java =================================================================== --- vm/vmcore/src/kernel_classes/javasrc/java/lang/VMThreadManager.java (revision 548781) +++ vm/vmcore/src/kernel_classes/javasrc/java/lang/VMThreadManager.java (working copy) @@ -246,5 +246,17 @@ * @api2vm */ static native int getState(java.lang.Thread thread); + + /** + * Acquires global TM lock + * @api2vm + */ + static native void acquireGlobalLock(); + + /** + * Releases global TM lock + * @api2vm + */ + static native void releaseGlobalLock(); } Index: vm/vmcore/src/kernel_classes/javasrc/java/lang/ThreadGroup.java =================================================================== --- vm/vmcore/src/kernel_classes/javasrc/java/lang/ThreadGroup.java (revision 548781) +++ vm/vmcore/src/kernel_classes/javasrc/java/lang/ThreadGroup.java (working copy) @@ -315,7 +315,7 @@ /** * @com.intel.drl.spec_ref */ - public synchronized final void setMaxPriority(int priority) { + public final void setMaxPriority(int priority) { checkAccess(); /* @@ -330,10 +330,17 @@ this.maxPriority = Thread.MIN_PRIORITY; return; } - this.maxPriority = (parent != null && parent.maxPriority < priority) + int new_priority = (parent != null && parent.maxPriority < priority) ? parent.maxPriority : priority; - nonsecureSetMaxPriority(this.maxPriority); + + // Obtain gloval lock to prevent deadlock + VMThreadManager.acquireGlobalLock(); + + nonsecureSetMaxPriority(new_priority); + + // Release gloval lock + VMThreadManager.releaseGlobalLock(); } /** @@ -633,10 +640,11 @@ * We add this method to avoid calls to the checkAccess() method on subgroups */ private synchronized void nonsecureSetMaxPriority(int priority) { + this.maxPriority = priority; + for (Iterator it = ((List)groups.clone()).iterator(); it.hasNext();) { ((ThreadGroup)it.next()).nonsecureSetMaxPriority(priority); } - this.maxPriority = priority; } /** Index: vm/vmcore/src/thread/thread_generic.cpp =================================================================== --- vm/vmcore/src/thread/thread_generic.cpp (revision 548781) +++ vm/vmcore/src/thread/thread_generic.cpp (working copy) @@ -183,10 +183,16 @@ } exn_clear(); + IDATA stat = hythread_global_lock(); + assert(stat == TM_ERROR_NONE); + hythread_suspend_disable(); vm_execute_java_method_array((jmethodID) detach, 0, args); hythread_suspend_enable(); + stat = hythread_global_unlock(); + assert(stat == TM_ERROR_NONE); + if (exn_raised()) { TRACE("java.lang.Thread.detach(Throwable) method completed with an exception: " << exn_get_name()); return TM_ERROR_INTERNAL;