void tested_threads_init(int mode){ tested_thread_sturct_t *tts; jobject monitor; jrawMonitorID raw_monitor; JNIEnv * jni_env; IDATA status; int i; jni_env = jthread_get_JNI_env(jthread_self()); if (mode != TTS_INIT_DIFFERENT_MONITORS){ monitor = new_jobject(); status = jthread_monitor_init(monitor); tf_assert_same_v(status, TM_ERROR_NONE); } status = jthread_raw_monitor_create(&raw_monitor); tf_assert_same_v(status, TM_ERROR_NONE); reset_tested_thread_iterator(&tts); for (i = 0; i < MAX_TESTED_THREAD_NUMBER; i++){ tts = &tested_threads[i]; tts->my_index = i; tts->java_thread = new_jobject_thread(jni_env); tts->native_thread = NULL; tts->jvmti_start_proc_arg = &tts->jvmti_start_proc_arg; hysem_create(&tts->started, 0, 1); hysem_create(&tts->running, 0, 1); hysem_create(&tts->stop_request, 0, 1); hysem_create(&tts->ended, 0, 1); tts->phase = TT_PHASE_NONE; if (mode == TTS_INIT_DIFFERENT_MONITORS){ monitor = new_jobject(); status = jthread_monitor_init(monitor); tf_assert_same_v(status, TM_ERROR_NONE); } tts->monitor = monitor; tts->raw_monitor = raw_monitor; tts->excn = NULL; } }
int test_jthread_holds_lock(void) { tested_thread_sturct_t *tts; tested_thread_sturct_t *critical_tts = NULL; int blocked_count; int i; hysem_create(&mon_enter, 0, 1); // Initialize tts structures and run all tested threads tested_threads_run(run_for_test_jthread_holds_lock); for (i = 0; i < MAX_TESTED_THREAD_NUMBER; i++){ blocked_count = 0; critical_tts = NULL; hysem_wait(mon_enter); reset_tested_thread_iterator(&tts); while(next_tested_thread(&tts)){ while(tts->phase == TT_PHASE_NONE) { // thread is not started yet hythread_yield(); } if (tts->phase == TT_PHASE_IN_CRITICAL_SECTON){ tf_assert(jthread_holds_lock(tts->java_thread, tts->monitor) > 0); tf_assert_null(critical_tts); critical_tts = tts; } else if (tts->phase != TT_PHASE_DEAD){ check_tested_thread_phase(tts, TT_PHASE_WAITING_ON_MONITOR); tf_assert(jthread_holds_lock(tts->java_thread, tts->monitor) == 0); if (tts->phase == TT_PHASE_WAITING_ON_MONITOR){ blocked_count++; } } } tf_assert(critical_tts); // thread in critical section found tf_assert_same(blocked_count, MAX_TESTED_THREAD_NUMBER - i - 1); tested_thread_send_stop_request(critical_tts); tested_thread_wait_ended(critical_tts); check_tested_thread_phase(critical_tts, TT_PHASE_DEAD); } // Terminate all threads and clear tts structures tested_threads_destroy(); return TEST_PASSED; }
int test_jthread_get_owned_monitors(void) { tested_thread_sturct_t *tts; tested_thread_sturct_t *critical_tts; int i; jint owned_monitors_count; jobject *owned_monitors = NULL; hysem_create(&mon_enter, 0, 1); // Initialize tts structures and run all tested threads tested_threads_run(run_for_test_jthread_get_owned_monitors); for (i = 0; i < MAX_TESTED_THREAD_NUMBER; i++){ critical_tts = NULL; hysem_wait(mon_enter); reset_tested_thread_iterator(&tts); while(next_tested_thread(&tts)) { while(tts->phase == TT_PHASE_NONE) { // thread is not started yet hythread_yield(); } if (tts->phase == TT_PHASE_IN_CRITICAL_SECTON){ tf_assert_same(jthread_get_owned_monitors (tts->java_thread, &owned_monitors_count, &owned_monitors), TM_ERROR_NONE); tf_assert(critical_tts == NULL); critical_tts = tts; tf_assert_same(owned_monitors_count, 1); tf_assert_same(owned_monitors[0]->object, tts->monitor->object); } else if (tts->phase == TT_PHASE_WAITING_ON_MONITOR){ tf_assert_same(jthread_get_owned_monitors (tts->java_thread, &owned_monitors_count, &owned_monitors), TM_ERROR_NONE); tf_assert_same(owned_monitors_count, 0); } } tf_assert(critical_tts); tested_thread_send_stop_request(critical_tts); tested_thread_wait_ended(critical_tts); } // Terminate all threads and clear tts structures tested_threads_destroy(); return TEST_PASSED; }
int test_jthread_get_contended_monitor(void) { tested_thread_sturct_t *tts; tested_thread_sturct_t *critical_tts = NULL; jobject contended_monitor; int i; hysem_create(&mon_enter, 0, 1); // Initialize tts structures and run all tested threads tested_threads_run(run_for_test_jthread_get_contended_monitor); for (i = 0; i < MAX_TESTED_THREAD_NUMBER; i++){ critical_tts = NULL; hysem_wait(mon_enter); reset_tested_thread_iterator(&tts); while(next_tested_thread(&tts)){ while(tts->phase == TT_PHASE_NONE) { // thread is not started yet hythread_yield(); } if (tts->phase == TT_PHASE_IN_CRITICAL_SECTON){ tf_assert_same(jthread_get_contended_monitor(tts->java_thread, &contended_monitor), TM_ERROR_NONE); tf_assert_null(contended_monitor); tf_assert_null(critical_tts); critical_tts = tts; } else if (tts->phase != TT_PHASE_DEAD) { check_tested_thread_phase(tts, TT_PHASE_WAITING_ON_MONITOR); // This can't be guaranteed //tf_assert(vm_objects_are_equal(contended_monitor, tts->monitor)); } } tested_thread_send_stop_request(critical_tts); tested_thread_wait_ended(critical_tts); check_tested_thread_phase(critical_tts, TT_PHASE_DEAD); } // Terminate all threads and clear tts structures tested_threads_destroy(); return TEST_PASSED; }
/** * Initializes a new thread structure. */ IDATA VMCALL hythread_struct_init(hythread_t new_thread) { char jstatus; IDATA status; assert(new_thread); jstatus = new_thread->java_status; if (!new_thread->os_handle) { // new thread, create thread primitives memset(new_thread, 0, sizeof(HyThread)); status = hysem_create(&new_thread->resume_event, 0, 1); assert(status == TM_ERROR_NONE); status = port_mutex_create(&new_thread->mutex, APR_THREAD_MUTEX_NESTED); assert(status == TM_ERROR_NONE); status = hythread_monitor_init(&new_thread->monitor, 0); assert(status == TM_ERROR_NONE); } else { // old thread, reset structure int result; hysem_t resume; osmutex_t mutex; hythread_monitor_t monitor; // release thread OS handle result = port_thread_free_handle(new_thread->os_handle); assert(0 == result); resume = new_thread->resume_event; mutex = new_thread->mutex; monitor = new_thread->monitor; // zero new thread memset(new_thread, 0, sizeof(HyThread)); new_thread->resume_event = resume; new_thread->mutex = mutex; new_thread->monitor = monitor; } assert(new_thread->os_handle == 0); new_thread->java_status = jstatus; new_thread->priority = HYTHREAD_PRIORITY_NORMAL; #ifdef ORDER new_thread->alloc_count = 0; new_thread->thread_create_count = 0; new_thread->p_tid = 0; new_thread->p_count = 0; // new_thread->isInVMRegistry = 0; #endif port_mutex_lock(&new_thread->mutex); new_thread->state = TM_THREAD_STATE_NEW; port_mutex_unlock(&new_thread->mutex); status = hysem_set(new_thread->resume_event, 0); assert(status == TM_ERROR_NONE); return TM_ERROR_NONE; }