void print_info_task(){ if(is_program_finished() || get_thread_status(PRINT_INFO_THREAD)==PAUSED){ return; } tick_counter++; if(tick_counter>=(MIN_WAIT+get_time_slice(PRINT_INFO_THREAD)*SLICE_MULT)){ tick_counter=0; info_color++; if(info_color==NUM_COLORS){ info_color=BLACK; } print_info_str(info_x, info_y, info_color); } }
/** * Get the next thread to run * * @return the pointer to the `struct thread` to run * */ thread_t get_next_thread (void){ uintmax_t next_run, next_run_start; irqstatus_t irqstatus; thread_t *runqueue; // there are no thread to run if(BASE_GLOBAL->thread.runnable_num == 1) return 0; /* start_servers() or test_servers() */ runqueue = BASE_GLOBAL->thread.runqueue; irqstatus = spin_lock_noirq(&BASE_GLOBAL->thread.runqueue_lock); next_run = BASE_GLOBAL->thread.next_run; next_run_start = next_run; for(; next_run < BASE_GLOBAL->thread.runqueue_num; next_run++){ if(get_thread_status(runqueue[next_run]) == THREAD_RUNNABLE) goto return_next_thread; } next_run = 1; for(; next_run < next_run_start; next_run++){ if(get_thread_status(runqueue[next_run]) == THREAD_RUNNABLE) goto return_next_thread; } PANIC("failed to pick a next thread to run"); return_next_thread: BASE_GLOBAL->thread.next_run = next_run + 1; if(BASE_GLOBAL->thread.next_run == BASE_GLOBAL->thread.runqueue_num) BASE_GLOBAL->thread.next_run = 1; /* skip #0 */ spin_unlock_restoreirq(&BASE_GLOBAL->thread.runqueue_lock, irqstatus); return runqueue[next_run]; }
/* Release the threads that are held */ int release_threads(void) { int i, ret = 0; char state; /* Detach the process to be dumped */ for (i = 0; i < cp.thread_count; i++) { state = get_thread_status(cp.t_id[i]); if (state == 't') { ret += ptrace(PTRACE_DETACH, cp.t_id[i], 0, 0); if (ret) gencore_log("Could not detach from thread: %d\n", cp.t_id[i]); } } /* Successful detach on all threads makes ret = 0 */ return ret; }
/* Wait for threads to stop */ int wait_for_threads_to_stop(void) { int i; char state; /* * We check for the process to stop infinitely now. We need * to break out after some definite time. Need to work on * that. */ for (i = 0; i < cp.thread_count; i++) { do { state = get_thread_status(cp.t_id[i]); if (state != 't') sched_yield(); } while (state != 't' && state!='Z' && state != -1); if (state == -1) return -1; } return 0; }
// Exception callback static void JNICALL callbackException(jvmtiEnv *jvmti, JNIEnv* env, jthread thr, jmethodID method, jlocation location, jobject exception, jmethodID catch_method, jlocation catch_location) { enter_critical_section(jvmti); { jvmtiError err, err1, err2, error; jvmtiThreadInfo info, info1; jvmtiThreadGroupInfo groupInfo; jint num_monitors; jobject *arr_monitors; jint count; jint flag = 0; jint thr_st_ptr;//œfl≥Ã◊¥Ã¨÷∏’Î jint thr_count;//œfl≥à ˝¡ø jthread *thr_ptr; jvmtiError err3; char *name; char *sig; char *gsig; err3 = (*jvmti)->GetMethodName(jvmti, method, &name, &sig, &gsig); // err3 = (*jvmti).GetMethodName( method, &name, &sig, &gsig); if (err3 != JVMTI_ERROR_NONE) { printf("GetMethodName:%d\n", err3); return; } printf("Got Exception from Method:%s%s\n", name, sig); err = (*jvmti)->GetThreadInfo(jvmti, thr, &info); if (err != JVMTI_ERROR_NONE) { printf("(GetThreadInfo) Error expected: %d, got: %d\n", JVMTI_ERROR_NONE, err); describe(err); jvmtiPhase phase; jvmtiError phaseStat; phaseStat = (*jvmti)->GetPhase(jvmti, &phase); printf(" current phase is %d\n", phase); printf("\n"); } if (err == JVMTI_ERROR_NONE) { err1 = (*jvmti)->GetThreadGroupInfo(jvmti, info.thread_group, &groupInfo); if (err1 != JVMTI_ERROR_NONE) { printf("(GetThreadGroupInfo) Error expected: %d, got: %d\n", JVMTI_ERROR_NONE, err); describe(err); printf("\n"); } else { printf("Current Thread is : %s and it belongs to Thread Group : %s\n", info.name, groupInfo.name); } } err = (*jvmti)->GetOwnedMonitorInfo(jvmti, thr, &num_monitors, &arr_monitors); if (err != JVMTI_ERROR_NONE) { printf("(GetThreadInfo) Error expected: %d, got: %d\n", JVMTI_ERROR_NONE, err); describe(err); printf("\n"); } printf("Number of Monitors Owned by this thread : %d\n", num_monitors); // Get Thread Status get_thread_status(jvmti, thr, &info, flag, &thr_st_ptr); // Get All Threads get_all_thread(jvmti, &err, &err1, &err2, &info1, &thr_count, &thr_ptr); // Get Stack Trace show_statck_trace(jvmti, thr, &count); } exit_critical_section(jvmti); }
/* * Read the directory /proc/pid/task again and again * till we find no new threads. */ int scan_threads(int pid) { DIR *dir; struct dirent *entry; int tmp_tid, ret = 0, k = 0; char state; char filename[40]; snprintf(filename, 40, "/proc/%d/task", pid); dir = opendir(filename); while ((entry = readdir(dir))) { if (entry->d_type == DT_DIR && entry->d_name[0] != '.') { tmp_tid = atoi(entry->d_name); /* * Search for the thread, if not present, seize, interrupt * and insert it in cp.t_id. */ if (!search(tmp_tid, cp.thread_count)) { k++; ret = ptrace(PTRACE_SEIZE, tmp_tid, 0, 0); if (ret) { state = get_thread_status(tmp_tid); if (state == 'Z') goto assign; status = errno; gencore_log("Could not seize thread: %d\n", tmp_tid); break; } ret = ptrace(PTRACE_INTERRUPT, tmp_tid, 0, 0); if (ret) { state = get_thread_status(tmp_tid); if (state == 'Z') goto assign; status = errno; gencore_log("Could not interrupt thread: %d\n", tmp_tid); break; } assign: cp.t_id = (char *) realloc(cp.t_id, (cp.thread_count + 1) * sizeof(int)); if (!cp.t_id) { status = errno; gencore_log("Could not allocate memory for thread_ids.\n"); return -1; } insert(tmp_tid, cp.thread_count); cp.thread_count ++; } } } closedir(dir); if (!k) return 1; return ret; }