If you don’t care about errors propagating from the coroutine to the main thread, then coroutine.wrap is fine; otherwise, use coroutine.create/resume, which calls the function in protected mode (like pcall).
As for when it would return running, presumably the only time that would happen is if you’re calling coroutine.status from inside that coroutine.
Well, I don’t see why there’s a problem with one universal loop. You could store the threads in a more specific manner if it suits you. For example, you could collect a list of threads into another thread which operates on their combined output, then pass that to a “universal loop”.
I assume the reason there’s not already a coroutine.kill method is that nobody really ever uses coroutines in that way.
I just don’t think it’d ever be a good idea to give every single thread its own loop using wait(). Personally I want more control over things like what order my threads run in, and how I handle their combined output. Also, if I only have one loop, then I can control the refresh rate with only one variable. I feel like a general coroutine.kill method should never really be necessary, but do correct me if I’m wrong.