/* * Terminate a thread. */ kern_return_t thread_terminate( thread_t thread) { kern_return_t result; if (thread == THREAD_NULL) return (KERN_INVALID_ARGUMENT); if ( thread->task == kernel_task && thread != current_thread() ) return (KERN_FAILURE); result = thread_terminate_internal(thread); /* * If a kernel thread is terminating itself, force an AST here. * Kernel threads don't normally pass through the AST checking * code - and all threads finish their own termination in the * special handler APC. */ if (thread->task == kernel_task) { ml_set_interrupts_enabled(FALSE); ast_taken(AST_APC, TRUE); panic("thread_terminate"); } return (result); }
/* * Terminate a thread. */ kern_return_t thread_terminate( thread_t thread) { if (thread == THREAD_NULL) return (KERN_INVALID_ARGUMENT); /* Kernel threads can't be terminated without their own cooperation */ if (thread->task == kernel_task && thread != current_thread()) return (KERN_FAILURE); kern_return_t result = thread_terminate_internal(thread); /* * If a kernel thread is terminating itself, force handle the APC_AST here. * Kernel threads don't pass through the return-to-user AST checking code, * but all threads must finish their own termination in thread_apc_ast. */ if (thread->task == kernel_task) { assert(thread->active == FALSE); thread_ast_clear(thread, AST_APC); thread_apc_ast(thread); panic("thread_terminate"); /* NOTREACHED */ } return (result); }