|
|
@ -112,19 +112,22 @@ class Thread { |
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
/// The destructor is strictly optional; either the thread never came to life
|
|
|
|
/// The destructor is strictly optional; either the thread never came to life
|
|
|
|
/// and the constructor itself killed it or it has already been joined and
|
|
|
|
/// and the constructor itself killed it, or it has already been joined and
|
|
|
|
/// the Join function kills it. The destructor shouldn't have to do anything.
|
|
|
|
/// the Join function kills it, or it was detached (non-joinable) and it has
|
|
|
|
~Thread() { GPR_ASSERT(impl_ == nullptr); } |
|
|
|
/// run to completion and is now killing itself. The destructor shouldn't have
|
|
|
|
|
|
|
|
/// to do anything.
|
|
|
|
|
|
|
|
~Thread() { GPR_ASSERT(!options_.joinable() || impl_ == nullptr); } |
|
|
|
|
|
|
|
|
|
|
|
void Start() { |
|
|
|
void Start() { |
|
|
|
if (impl_ != nullptr) { |
|
|
|
if (impl_ != nullptr) { |
|
|
|
GPR_ASSERT(state_ == ALIVE); |
|
|
|
GPR_ASSERT(state_ == ALIVE); |
|
|
|
state_ = STARTED; |
|
|
|
state_ = STARTED; |
|
|
|
impl_->Start(); |
|
|
|
impl_->Start(); |
|
|
|
if (!options_.joinable()) { |
|
|
|
// If the Thread is not joinable, then the impl_ will cause the deletion
|
|
|
|
state_ = DONE; |
|
|
|
// of this Thread object when the thread function completes. Since no
|
|
|
|
impl_ = nullptr; |
|
|
|
// other operation is allowed to a detached thread after Start, there is
|
|
|
|
} |
|
|
|
// no need to change the value of the impl_ or state_ . The next operation
|
|
|
|
|
|
|
|
// on this object will be the deletion, which will trigger the destructor.
|
|
|
|
} else { |
|
|
|
} else { |
|
|
|
GPR_ASSERT(state_ == FAILED); |
|
|
|
GPR_ASSERT(state_ == FAILED); |
|
|
|
} |
|
|
|
} |
|
|
|