void* Thread::run(void* ptr) { VM* vm = reinterpret_cast<VM*>(ptr); State state_obj(vm), *state = &state_obj; vm->set_stack_bounds(THREAD_STACK_SIZE); vm->set_current_thread(); RUBINIUS_THREAD_START( const_cast<RBX_DTRACE_CHAR_P>(vm->name().c_str()), vm->thread_id(), 0); vm->thread->pid(state, Fixnum::from(gettid())); logger::write("start thread: %s, %d, %#x", vm->name().c_str(), vm->thread->pid()->to_native(), (unsigned int)thread_debug_self()); NativeMethod::init_thread(state); state->vm()->become_managed(); vm->shared.tool_broker()->thread_start(state); Object* value = vm->thread->function()(state); vm->set_call_frame(NULL); vm->shared.tool_broker()->thread_stop(state); vm->thread->join_lock_.lock(); vm->thread->stopped(); memory::LockedObjects& locked_objects = state->vm()->locked_objects(); for(memory::LockedObjects::iterator i = locked_objects.begin(); i != locked_objects.end(); ++i) { (*i)->unlock_for_terminate(state); } locked_objects.clear(); vm->thread->join_cond_.broadcast(); vm->thread->join_lock_.unlock(); NativeMethod::cleanup_thread(state); logger::write("exit thread: %s", vm->name().c_str()); vm->become_unmanaged(); if(vm->main_thread_p() || (!value && vm->thread_state()->raise_reason() == cExit)) { state->shared().signals()->system_exit(vm->thread_state()->raise_value()); } vm->set_zombie(state); RUBINIUS_THREAD_STOP( const_cast<RBX_DTRACE_CHAR_P>(vm->name().c_str()), vm->thread_id(), 0); return 0; }