Index: working_vm/vm/include/open/hythread.h
===================================================================
--- working_vm/vm/include/open/hythread.h (revision 524976)
+++ working_vm/vm/include/open/hythread.h (working copy)
@@ -124,6 +124,8 @@
extern HY_CFUNC void VMCALL
hythread_detach PROTOTYPE((hythread_t thread));
+extern HY_CFUNC void VMCALL
+hythread_detach_shutdownthread PROTOTYPE((hythread_t thread));
extern HY_CFUNC UDATA VMCALL
hythread_lib_set_flags PROTOTYPE((UDATA flags));
extern HY_CFUNC IDATA VMCALL
Index: working_vm/vm/include/open/jthread.h
===================================================================
--- working_vm/vm/include/open/jthread.h (revision 524976)
+++ working_vm/vm/include/open/jthread.h (working copy)
@@ -84,7 +84,8 @@
IDATA jthread_create(JNIEnv * jni_env, jthread thread, jthread_threadattr_t *attrs);
IDATA jthread_create_with_function(JNIEnv * jni_env, jthread thread, jthread_threadattr_t *attrs, jvmtiStartFunction proc, const void* arg);
IDATA jthread_attach(JNIEnv * jni_env, jthread thread, jboolean daemon);
- IDATA jthread_detach(jthread thread);
+IDATA jthread_detach_shutdownthread ( jthread thread );
+ IDATA jthread_detach(jthread thread );
IDATA jthread_join(jthread thread);
IDATA jthread_timed_join(jthread thread, jlong millis, jint nanos);
IDATA jthread_yield();
Index: working_vm/vm/vmcore/src/init/vm_shutdown.cpp
===================================================================
--- working_vm/vm/vmcore/src/init/vm_shutdown.cpp (revision 524976)
+++ working_vm/vm/vmcore/src/init/vm_shutdown.cpp (working copy)
@@ -202,8 +202,9 @@
// TODO: ups we don't stop native threads as well :-((
// We are lucky! Currently, there are no such threads.
- // Detach current thread.
- status = jthread_detach(java_thread);
+ // Detach current shutdowning thread.
+
+ status = jthread_detach_shutdownthread(java_thread);
if (status != TM_ERROR_NONE) return JNI_ERR;
// Call Agent_OnUnload() for agents and unload agents.
Index: working_vm/vm/thread/src/hythr.exp
===================================================================
--- working_vm/vm/thread/src/hythr.exp (revision 524976)
+++ working_vm/vm/thread/src/hythr.exp (working copy)
@@ -1,170 +1,172 @@
-HYTHR_0.1 {
- global :
-get_tls_helper;
-hythread_detach;
-hythread_tls_alloc;
-hythread_sleep_interruptable;
-hythread_cancel;
-hythread_monitor_enter;
-hythread_monitor_notify_all;
-hythread_attach;
-hythread_attach_ex;
-hythread_monitor_destroy;
-hythread_monitor_num_waiting;
-hythread_interrupted;
-hythread_park;
-hythread_monitor_init_with_name;
-hythread_monitor_try_enter;
-hythread_self;
-tm_self_tls;
-hythread_tls_free;
-hythread_yield;
-hythread_suspend;
-hythread_interrupt;
-hythread_tls_set;
-hythread_create;
-hythread_monitor_wait;
-hythread_monitor_wait_interruptable;
-hythread_monitor_exit;
-hythread_set_priority;
-hythread_unpark;
-hythread_sleep;
-hythread_global;
-hythread_tls_alloc_with_finalizer;
-hythread_monitor_wait_timed;
-hythread_resume;
-hythread_monitor_notify;
-hythread_get_priority;
-hythread_tls_get;
-hythread_tls_get_request_offset;
-hythread_tls_get_offset;
-hythread_global_lock;
-hythread_global_unlock;
-hythread_attach_to_group;
-hythread_create_with_group;
-hythread_clear_interrupted_other;
-hythread_join;
-hythread_join_timed;
-hythread_join_interruptable;
-hythread_get_self_id;
-hythread_get_id;
-hythread_get_thread;
-hythread_get_thread_times;
-hythread_struct_init;
-hythread_cancel_all;
-hythread_group_create;
-hythread_group_release;
-hythread_group_get_list;
-hythread_get_private_data;
-hythread_set_private_data;
-hythread_is_suspend_enabled;
-hythread_suspend_enable;
-hythread_suspend_disable;
-hythread_exception_safe_point;
-hythread_safe_point;
-hythread_safe_point_other;
-hythread_suspend_other;
-hythread_set_safepoint_callback;
-hythread_suspend_all;
-hythread_resume_all;
-hythread_iterator_create;
-hythread_iterator_release;
-hythread_iterator_reset;
-hythread_iterator_reset;
-hythread_iterator_next;
-hythread_iterator_has_next;
-hythread_iterator_size;
-hythread_thin_monitor_create;
-hythread_thin_monitor_enter;
-hythread_thin_monitor_try_enter;
-hythread_thin_monitor_exit;
-hythread_thin_monitor_wait;
-hythread_thin_monitor_wait_timed;
-hythread_thin_monitor_wait_interruptable;
-hythread_thin_monitor_notify;
-hythread_thin_monitor_notify_all;
-hythread_thin_monitor_destroy;
-hythread_thin_monitor_get_owner;
-hythread_add_task;
-hythread_get_function_pointer;
-hythread_get_data_pointer;
-hythread_get_next_task;
-hythread_destroy_task_iterator;
-hythread_create_task_iterator;
-hythread_init_task_manager;
-hythread_destroy_task_manager;
-hythread_join_all_task;
-hythread_shutdown_after_execute_all_task;
-hythread_get_thread_count;
-hythread_get_task_count;
-hysem_post;
-hysem_wait;
-hysem_destroy;
-hycond_create;
-hycond_wait;
-hycond_wait_timed;
-hycond_wait_timed_raw;
-hycond_wait_interruptable;
-hycond_notify;
-hycond_notify_all;
-hycond_destroy;
-hylatch_create;
-hylatch_wait;
-hylatch_wait_timed;
-hylatch_wait_interruptable;
-hylatch_set;
-hylatch_count_down;
-hylatch_get_count;
-hylatch_destroy;
-hysem_create;
-hysem_wait_timed;
-hysem_wait_interruptable;
-hysem_getvalue;
-hysem_set;
-hymutex_create;
-hymutex_lock;
-hymutex_trylock;
-hymutex_unlock;
-hymutex_destroy;
-hythread_exit;
-
-hythread_is_alive;
-hythread_init;
-hythread_shutdown;
-hythread_lib_create;
-hythread_lib_destroy;
-hythread_lib_lock;
-hythread_lib_unlock;
-set_safepoint_callback;
-
-release_start_lock;
-acquire_start_lock;
-inflate_lock;
-is_fat_lock;
-owns_thin_lock;
-unreserve_lock;
-set_suspend_disable;
-reset_suspend_disable;
-hythread_is_blocked_on_monitor_enter;
-hythread_is_waiting;
-hythread_is_in_native;
-hythread_is_suspended;
-hythread_is_parked;
-hythread_is_in_monitor_wait;
-hythread_is_sleeping;
-hythread_is_waiting_with_timeout;
-hythread_is_waiting_indefinitely;
-hythread_is_runnable;
-hythread_is_terminated;
-hythread_thin_monitor_get_recursion;
-array_add;
-array_create;
-array_delete;
-array_get;
-get_java_thread_group;
-
-Java_org_apache_harmony_drlvm_thread_ThreadHelper_getThreadIdOffset;
-
-
-local: *;
-};
+HYTHR_0.1 {
+ global :
+get_tls_helper;
+hythread_detach;
+hythread_detach_shutdownthread;
+hythread_tls_alloc;
+hythread_sleep_interruptable;
+hythread_cancel;
+hythread_monitor_enter;
+hythread_monitor_notify_all;
+hythread_attach;
+hythread_attach_ex;
+hythread_monitor_destroy;
+hythread_monitor_num_waiting;
+hythread_interrupted;
+hythread_park;
+hythread_monitor_init_with_name;
+hythread_monitor_try_enter;
+hythread_self;
+tm_self_tls;
+hythread_tls_free;
+hythread_yield;
+hythread_suspend;
+hythread_interrupt;
+hythread_tls_set;
+hythread_create;
+hythread_monitor_wait;
+hythread_monitor_wait_interruptable;
+hythread_monitor_exit;
+hythread_set_priority;
+hythread_unpark;
+hythread_sleep;
+hythread_global;
+hythread_tls_alloc_with_finalizer;
+hythread_monitor_wait_timed;
+hythread_resume;
+hythread_monitor_notify;
+hythread_get_priority;
+hythread_tls_get;
+hythread_tls_get_request_offset;
+hythread_tls_get_offset;
+hythread_global_lock;
+hythread_global_unlock;
+hythread_attach_to_group;
+hythread_create_with_group;
+hythread_clear_interrupted_other;
+hythread_join;
+hythread_join_timed;
+hythread_join_interruptable;
+hythread_get_self_id;
+hythread_get_id;
+hythread_get_thread;
+hythread_get_thread_times;
+hythread_struct_init;
+hythread_cancel_all;
+hythread_group_create;
+hythread_group_release;
+hythread_group_get_list;
+hythread_get_private_data;
+hythread_set_private_data;
+hythread_is_suspend_enabled;
+hythread_suspend_enable;
+hythread_suspend_disable;
+hythread_exception_safe_point;
+hythread_safe_point;
+hythread_safe_point_other;
+hythread_suspend_other;
+hythread_set_safepoint_callback;
+hythread_suspend_all;
+hythread_resume_all;
+hythread_iterator_create;
+hythread_iterator_release;
+hythread_iterator_reset;
+hythread_iterator_reset;
+hythread_iterator_next;
+hythread_iterator_has_next;
+hythread_iterator_size;
+hythread_thin_monitor_create;
+hythread_thin_monitor_enter;
+hythread_thin_monitor_try_enter;
+hythread_thin_monitor_exit;
+hythread_thin_monitor_wait;
+hythread_thin_monitor_wait_timed;
+hythread_thin_monitor_wait_interruptable;
+hythread_thin_monitor_notify;
+hythread_thin_monitor_notify_all;
+hythread_thin_monitor_destroy;
+hythread_thin_monitor_get_owner;
+hythread_add_task;
+hythread_get_function_pointer;
+hythread_get_data_pointer;
+hythread_get_next_task;
+hythread_destroy_task_iterator;
+hythread_create_task_iterator;
+hythread_init_task_manager;
+hythread_destroy_task_manager;
+hythread_join_all_task;
+hythread_shutdown_after_execute_all_task;
+hythread_get_thread_count;
+hythread_get_task_count;
+hysem_post;
+hysem_wait;
+hysem_destroy;
+hycond_create;
+hycond_wait;
+hycond_wait_timed;
+hycond_wait_timed_raw;
+hycond_wait_interruptable;
+hycond_notify;
+hycond_notify_all;
+hycond_destroy;
+hylatch_create;
+hylatch_wait;
+hylatch_wait_timed;
+hylatch_wait_interruptable;
+hylatch_set;
+hylatch_count_down;
+hylatch_get_count;
+hylatch_destroy;
+hysem_create;
+hysem_wait_timed;
+hysem_wait_interruptable;
+hysem_getvalue;
+hysem_set;
+hymutex_create;
+hymutex_lock;
+hymutex_trylock;
+hymutex_unlock;
+hymutex_destroy;
+hythread_exit;
+
+hythread_is_alive;
+hythread_init;
+hythread_shutdown;
+hythread_lib_create;
+hythread_lib_destroy;
+hythread_lib_lock;
+hythread_lib_unlock;
+set_safepoint_callback;
+
+release_start_lock;
+acquire_start_lock;
+inflate_lock;
+is_fat_lock;
+owns_thin_lock;
+unreserve_lock;
+set_suspend_disable;
+reset_suspend_disable;
+hythread_is_blocked_on_monitor_enter;
+hythread_is_waiting;
+hythread_is_in_native;
+hythread_is_suspended;
+hythread_is_parked;
+hythread_is_in_monitor_wait;
+hythread_is_sleeping;
+hythread_is_waiting_with_timeout;
+hythread_is_waiting_indefinitely;
+hythread_is_runnable;
+hythread_is_terminated;
+hythread_thin_monitor_get_recursion;
+array_add;
+array_create;
+array_delete;
+array_get;
+get_java_thread_group;
+
+Java_org_apache_harmony_drlvm_thread_ThreadHelper_getThreadIdOffset;
+
+
+local: *;
+};
+
Index: working_vm/vm/thread/src/hythr.def
===================================================================
--- working_vm/vm/thread/src/hythr.def (revision 524976)
+++ working_vm/vm/thread/src/hythr.def (working copy)
@@ -1,156 +1,157 @@
-LIBRARY HYTHR
-
-EXPORTS
-
-hythread_detach
-hythread_tls_alloc
-hythread_sleep_interruptable
-hythread_cancel
-hythread_monitor_enter
-hythread_monitor_notify_all
-hythread_attach
-hythread_attach_ex
-hythread_monitor_destroy
-hythread_monitor_num_waiting
-hythread_interrupted
-hythread_park
-hythread_monitor_init_with_name
-hythread_monitor_try_enter
-hythread_self
-hythread_self_slow
-hythread_tls_free
-hythread_yield
-hythread_suspend
-hythread_interrupt
-hythread_tls_set
-hythread_create
-hythread_monitor_wait
-hythread_monitor_wait_interruptable
-hythread_monitor_exit
-hythread_set_priority
-hythread_unpark
-hythread_sleep
-hythread_global
-hythread_tls_alloc_with_finalizer
-hythread_monitor_wait_timed
-hythread_resume
-hythread_monitor_notify
-hythread_get_priority
-hythread_tls_get
-hythread_tls_get_request_offset
-hythread_tls_get_offset
-hythread_global_lock
-hythread_global_unlock
-hythread_attach_to_group
-hythread_create_with_group
-hythread_clear_interrupted_other
-hythread_join
-hythread_join_timed
-hythread_join_interruptable
-hythread_get_self_id
-hythread_get_id
-hythread_get_thread
-hythread_get_thread_times
-hythread_struct_init
-hythread_cancel_all
-hythread_group_create
-hythread_group_release
-hythread_group_get_list
-hythread_get_private_data
-hythread_set_private_data
-hythread_is_suspend_enabled
-hythread_suspend_enable
-hythread_suspend_disable
-hythread_exception_safe_point
-hythread_safe_point
-hythread_safe_point_other
-hythread_suspend_other
-hythread_set_safepoint_callback
-hythread_suspend_all
-hythread_resume_all
-hythread_iterator_create
-hythread_iterator_release
-hythread_iterator_reset
-hythread_iterator_next
-hythread_iterator_has_next
-hythread_iterator_size
-hythread_thin_monitor_create
-hythread_thin_monitor_enter
-hythread_thin_monitor_try_enter
-hythread_thin_monitor_exit
-hythread_thin_monitor_wait
-hythread_thin_monitor_wait_timed
-hythread_thin_monitor_wait_interruptable
-hythread_thin_monitor_notify
-hythread_thin_monitor_notify_all
-hythread_thin_monitor_destroy
-hythread_thin_monitor_get_owner
-
-hysem_post
-hysem_wait
-hysem_destroy
-hycond_create
-hycond_wait
-hycond_wait_timed
-hycond_wait_timed_raw
-hycond_wait_interruptable
-hycond_notify
-hycond_notify_all
-hycond_destroy
-hylatch_create
-hylatch_wait
-hylatch_wait_timed
-hylatch_wait_interruptable
-hylatch_set
-hylatch_count_down
-hylatch_get_count
-hylatch_destroy
-hysem_create
-hysem_wait_timed
-hysem_wait_interruptable
-hysem_getvalue
-hysem_set
-hymutex_create
-hymutex_lock
-hymutex_trylock
-hymutex_unlock
-hymutex_destroy
-
-
-hythread_is_alive
-hythread_is_terminated
-hythread_init
-hythread_shutdown
-hythread_lib_create
-hythread_lib_destroy
-hythread_lib_lock
-hythread_lib_unlock
-
-release_start_lock
-acquire_start_lock
-inflate_lock
-is_fat_lock
-owns_thin_lock
-unreserve_lock
-set_suspend_disable
-reset_suspend_disable
-hythread_is_blocked_on_monitor_enter
-hythread_is_waiting
-hythread_is_in_native
-hythread_is_suspended
-hythread_is_parked
-hythread_is_in_monitor_wait
-hythread_is_sleeping
-hythread_is_waiting_with_timeout
-hythread_is_waiting_indefinitely
-hythread_is_runnable
-hythread_thin_monitor_get_recursion
-hythread_exit
-array_add
-array_create
-array_delete
-array_get
-get_java_thread_group
-
-
-Java_org_apache_harmony_drlvm_thread_ThreadHelper_getThreadIdOffset
+LIBRARY HYTHR
+
+EXPORTS
+
+hythread_detach
+hythread_detach_shutdownthread
+hythread_tls_alloc
+hythread_sleep_interruptable
+hythread_cancel
+hythread_monitor_enter
+hythread_monitor_notify_all
+hythread_attach
+hythread_attach_ex
+hythread_monitor_destroy
+hythread_monitor_num_waiting
+hythread_interrupted
+hythread_park
+hythread_monitor_init_with_name
+hythread_monitor_try_enter
+hythread_self
+hythread_self_slow
+hythread_tls_free
+hythread_yield
+hythread_suspend
+hythread_interrupt
+hythread_tls_set
+hythread_create
+hythread_monitor_wait
+hythread_monitor_wait_interruptable
+hythread_monitor_exit
+hythread_set_priority
+hythread_unpark
+hythread_sleep
+hythread_global
+hythread_tls_alloc_with_finalizer
+hythread_monitor_wait_timed
+hythread_resume
+hythread_monitor_notify
+hythread_get_priority
+hythread_tls_get
+hythread_tls_get_request_offset
+hythread_tls_get_offset
+hythread_global_lock
+hythread_global_unlock
+hythread_attach_to_group
+hythread_create_with_group
+hythread_clear_interrupted_other
+hythread_join
+hythread_join_timed
+hythread_join_interruptable
+hythread_get_self_id
+hythread_get_id
+hythread_get_thread
+hythread_get_thread_times
+hythread_struct_init
+hythread_cancel_all
+hythread_group_create
+hythread_group_release
+hythread_group_get_list
+hythread_get_private_data
+hythread_set_private_data
+hythread_is_suspend_enabled
+hythread_suspend_enable
+hythread_suspend_disable
+hythread_exception_safe_point
+hythread_safe_point
+hythread_safe_point_other
+hythread_suspend_other
+hythread_set_safepoint_callback
+hythread_suspend_all
+hythread_resume_all
+hythread_iterator_create
+hythread_iterator_release
+hythread_iterator_reset
+hythread_iterator_next
+hythread_iterator_has_next
+hythread_iterator_size
+hythread_thin_monitor_create
+hythread_thin_monitor_enter
+hythread_thin_monitor_try_enter
+hythread_thin_monitor_exit
+hythread_thin_monitor_wait
+hythread_thin_monitor_wait_timed
+hythread_thin_monitor_wait_interruptable
+hythread_thin_monitor_notify
+hythread_thin_monitor_notify_all
+hythread_thin_monitor_destroy
+hythread_thin_monitor_get_owner
+
+hysem_post
+hysem_wait
+hysem_destroy
+hycond_create
+hycond_wait
+hycond_wait_timed
+hycond_wait_timed_raw
+hycond_wait_interruptable
+hycond_notify
+hycond_notify_all
+hycond_destroy
+hylatch_create
+hylatch_wait
+hylatch_wait_timed
+hylatch_wait_interruptable
+hylatch_set
+hylatch_count_down
+hylatch_get_count
+hylatch_destroy
+hysem_create
+hysem_wait_timed
+hysem_wait_interruptable
+hysem_getvalue
+hysem_set
+hymutex_create
+hymutex_lock
+hymutex_trylock
+hymutex_unlock
+hymutex_destroy
+
+
+hythread_is_alive
+hythread_is_terminated
+hythread_init
+hythread_shutdown
+hythread_lib_create
+hythread_lib_destroy
+hythread_lib_lock
+hythread_lib_unlock
+
+release_start_lock
+acquire_start_lock
+inflate_lock
+is_fat_lock
+owns_thin_lock
+unreserve_lock
+set_suspend_disable
+reset_suspend_disable
+hythread_is_blocked_on_monitor_enter
+hythread_is_waiting
+hythread_is_in_native
+hythread_is_suspended
+hythread_is_parked
+hythread_is_in_monitor_wait
+hythread_is_sleeping
+hythread_is_waiting_with_timeout
+hythread_is_waiting_indefinitely
+hythread_is_runnable
+hythread_thin_monitor_get_recursion
+hythread_exit
+array_add
+array_create
+array_delete
+array_get
+get_java_thread_group
+
+
+Java_org_apache_harmony_drlvm_thread_ThreadHelper_getThreadIdOffset
Index: working_vm/vm/thread/src/thread_native_basic.c
===================================================================
--- working_vm/vm/thread/src/thread_native_basic.c (revision 524976)
+++ working_vm/vm/thread/src/thread_native_basic.c (working copy)
@@ -287,6 +287,44 @@
}
/**
+ * Detaches a thread from the threading library when in shutdown.
+ *
+ * @note Assumes that the thread being detached is already attached.
+ *
+ * If the thread is an attached thread, then detach should only be called by the thread
+ * itself. Internal resources associated with the thread are freed.
+ *
+ * If the thread is already dead, this call will destroy it.
+ *
+ * @param[in] thread a hythread_t representing the thread to be detached.
+ * If this is NULL, the current thread is detached.
+ * @return none
+ *
+ * @see hythread_attach
+ */
+void VMCALL hythread_detach_shutdownthread(hythread_t thread) {
+
+ if (thread == NULL) {
+ thread = hythread_self();
+ }
+
+
+
+ // No actions required in case the specified thread is detached already.
+ if (thread->group != NULL) {
+ assert(thread == tm_self_tls);
+
+ thread_set_self(NULL);
+ fast_thread_array[thread->thread_id] = NULL;
+
+ thread->prev->next = thread->next;
+ thread->next->prev = thread->prev;
+ thread->group->threads_count--;
+ thread->group = NULL;
+ }
+
+}
+/**
* Waits until the selected thread finishes execution.
*
* @param[in] t thread to join
Index: working_vm/vm/thread/src/thread_java_basic.c
===================================================================
--- working_vm/vm/thread/src/thread_java_basic.c (revision 524976)
+++ working_vm/vm/thread/src/thread_java_basic.c (working copy)
@@ -269,7 +269,7 @@
*
* @param[in] java_thread Java thread to be detached
*/
-IDATA jthread_detach(jthread java_thread) {
+IDATA jthread_detach(jthread java_thread ) {
IDATA status;
hythread_t tm_native_thread;
jvmti_thread_t tm_jvmti_thread;
@@ -284,8 +284,7 @@
tm_native_thread = jthread_get_native_thread(java_thread);
tm_jvmti_thread = hythread_get_private_data(tm_native_thread);
jni_env = tm_jvmti_thread->jenv;
-
- if (!tm_jvmti_thread->daemon) {
+ if (!tm_jvmti_thread->daemon ) {
countdown_nondaemon_threads(tm_native_thread);
}
@@ -308,6 +307,51 @@
return TM_ERROR_NONE;
}
+/**
+ * Detaches the shutdown thread from java VM.
+ *
+ * This function will release any resources associated with the given thread.
+ *
+ * @param[in] java_thread Java thread to be detached
+ */
+IDATA jthread_detach_shutdownthread(jthread java_thread ) {
+ IDATA status;
+ hythread_t tm_native_thread;
+ jvmti_thread_t tm_jvmti_thread;
+ JNIEnv * jni_env;
+
+ assert(hythread_is_suspend_enabled());
+
+ // Check input arg
+ assert(java_thread);
+ TRACE(("TM: jthread_detach %x", hythread_self()));
+
+ tm_native_thread = jthread_get_native_thread(java_thread);
+ tm_jvmti_thread = hythread_get_private_data(tm_native_thread);
+ jni_env = tm_jvmti_thread->jenv;
+ // at this stage we don't careabout the countdown
+ // if (!tm_jvmti_thread->daemon ) {
+ // countdown_nondaemon_threads(tm_native_thread);
+ // }
+
+ // Detach from VM.
+ status = vm_detach(java_thread);
+ if (status != JNI_OK) return TM_ERROR_INTERNAL;
+
+ // Delete global reference to current thread object.
+ (*jni_env)->DeleteGlobalRef(jni_env, tm_jvmti_thread->thread_object);
+ // jthread_self() will return NULL now.
+ tm_jvmti_thread->thread_object = NULL;
+
+ // Decrease alive thread counter
+ thread_end_count();
+
+ // Deallocate tm_jvmti_thread
+ //apr_pool_destroy(tm_jvmti_thread->pool);
+
+ assert(hythread_is_suspend_enabled());
+ return TM_ERROR_NONE;
+}
IDATA associate_native_and_java_thread(JNIEnv * jni_env, jthread java_thread, hythread_t tm_native_thread, jobject thread_ref)
{
IDATA status;
Index: working_classlib/modules/portlib/src/main/native/include/shared/hythread.h
===================================================================
--- working_classlib/modules/portlib/src/main/native/include/shared/hythread.h (revision 524970)
+++ working_classlib/modules/portlib/src/main/native/include/shared/hythread.h (working copy)
@@ -99,6 +99,7 @@
} HyThreadMonitorTracing;
extern HY_CFUNC void VMCALL hythread_detach PROTOTYPE ((hythread_t thread));
+ extern HY_CFUNC void VMCALL hythread_detach_shutdownthread PROTOTYPE ((hythread_t thread));
extern HY_CFUNC UDATA VMCALL
hythread_lib_set_flags PROTOTYPE ((UDATA flags));
extern HY_CFUNC IDATA VMCALL
Index: working_classlib/modules/portlib/src/main/native/port/shared/hyport.c
===================================================================
--- working_classlib/modules/portlib/src/main/native/port/shared/hyport.c (revision 524970)
+++ working_classlib/modules/portlib/src/main/native/port/shared/hyport.c (working copy)
@@ -106,8 +106,11 @@
hyport_tls_shutdown (portLibrary);
portLibrary->mem_shutdown (portLibrary);
- hythread_detach (portLibrary->attached_thread);
+ //hythread_detach (portLibrary->attached_thread);
+ // call the shutdown version of detach
+ hythread_detach_shutdownthread (portLibrary->attached_thread);
+
/* Last thing to do. If this port library was self allocated free this memory */
if (NULL != portLibrary->self_handle)
{
Index: working_classlib/modules/portlib/src/main/native/thread/unix/exports.txt
===================================================================
--- working_classlib/modules/portlib/src/main/native/thread/unix/exports.txt (revision 524970)
+++ working_classlib/modules/portlib/src/main/native/thread/unix/exports.txt (working copy)
@@ -39,6 +39,7 @@
hythread_yield
hythread_exit
hythread_detach
+hythread_detach_shutdownthread
hythread_global
hythread_get_flags
hythread_monitor_walk
Index: working_classlib/modules/portlib/src/main/native/thread/shared/hythread.c
===================================================================
--- working_classlib/modules/portlib/src/main/native/thread/shared/hythread.c (revision 524970)
+++ working_classlib/modules/portlib/src/main/native/thread/shared/hythread.c (working copy)
@@ -1512,6 +1512,76 @@
#undef CDEV_CURRENT_FUNCTION
+#define CDEV_CURRENT_FUNCTION hythread_detach_shutdownthread
+/**
+ * Detach a thread from the threading library, shutdown version.
+ *
+ * @note Assumes that the thread being detached is already attached.
+ *
+ * If the thread is an attached thread, then detach should only be called by the thread
+ * itself. Internal resources associated with the thread are freed.
+ *
+ * If the thread is already dead, this call will destroy it.
+ *
+ * @param[in] thread a hythread_t representing the thread to be detached.
+ * If this is NULL, the current thread is detached.
+ * @return none
+ *
+ * @see hythread_attach
+ */
+void VMCALL
+hythread_detach_shutdownthread (hythread_t thread)
+{
+ UDATA destroy = 0;
+ UDATA attached = 0;
+ hythread_t self = MACRO_SELF ();
+
+ if (thread == NULL)
+ {
+ thread = self;
+ }
+ ASSERT (thread);
+
+ THREAD_LOCK (self, thread, CALLER_DETACH);
+ if (thread->attachcount < 1)
+ {
+ /* error! */
+ }
+ else
+ {
+ if (--thread->attachcount == 0)
+ {
+ if (thread->flags & HYTHREAD_FLAG_ATTACHED)
+ {
+ /* this is an attached thread, and it is now fully
+ detached. Mark it dead so that it can be destroyed */
+ thread->flags |= HYTHREAD_FLAG_DEAD;
+ attached = destroy = 1;
+ }
+ else
+ {
+ destroy = thread->flags & HYTHREAD_FLAG_DEAD;
+ }
+ }
+ }
+ THREAD_UNLOCK (self, thread);
+
+ if (destroy)
+ {
+ hythread_library_t library = thread->library;
+
+ tls_finalize (thread);
+
+ destroy_thread (thread, GLOBAL_NOT_LOCKED);
+ if (attached)
+ {
+ TLS_SET (library->self_ptr, NULL);
+ }
+ }
+}
+
+#undef CDEV_CURRENT_FUNCTION
+
#define CDEV_CURRENT_FUNCTION hythread_exit
/**
* Exit the current thread.
Index: working_classlib/modules/portlib/src/main/native/thread/windows/hythr.def
===================================================================
--- working_classlib/modules/portlib/src/main/native/thread/windows/hythr.def (revision 524970)
+++ working_classlib/modules/portlib/src/main/native/thread/windows/hythr.def (working copy)
@@ -45,6 +45,7 @@
hythread_yield
hythread_exit
hythread_detach
+ hythread_detach_shutdownthread
hythread_global
hythread_get_flags
hythread_monitor_walk
Index: working_classlib/modules/portlib/src/main/native/thrstub/shared/hythread.h
===================================================================
--- working_classlib/modules/portlib/src/main/native/thrstub/shared/hythread.h (revision 524970)
+++ working_classlib/modules/portlib/src/main/native/thrstub/shared/hythread.h (working copy)
@@ -201,6 +201,7 @@
#define hythread_attach(param1) privateThreadLibrary->thread_attach(privateThreadLibrary,param1)
#define hythread_create(param1,param2,param3,param4,param5,param6) privateThreadLibrary->thread_create(privateThreadLibrary,param1,param2,param3,param4,param5,param6)
#define hythread_detach(param1) privateThreadLibrary->thread_detach(privateThreadLibrary,param1)
+#define hythread_detach_shutdownthread(param1) privateThreadLibrary->thread_detach(privateThreadLibrary,param1)
#define hythread_exit(param1) privateThreadLibrary->thread_exit(privateThreadLibrary,param1)
#define hythread_global(param1) privateThreadLibrary->thread_global(privateThreadLibrary,param1)