diff --git a/src/bvar/detail/combiner.h b/src/bvar/detail/combiner.h index 3007f50da8..8a03dab641 100644 --- a/src/bvar/detail/combiner.h +++ b/src/bvar/detail/combiner.h @@ -341,7 +341,16 @@ friend class GlobalValue; if (!agent->combiner.expired()) { return agent; } - agent->reset(_element_identity, this->shared_from_this()); + self_shared_type self; + try { + self = this->shared_from_this(); + } catch (const std::bad_weak_ptr&) { + // The combiner is no longer managed by any shared_ptr, which can + // happen when a bvar is being destroyed concurrently with a write. + // Silently skip this recording instead of crashing. + return NULL; + } + agent->reset(_element_identity, self); // TODO: Is uniqueness-checking necessary here? { butil::AutoLock guard(_lock); diff --git a/src/bvar/detail/percentile.cpp b/src/bvar/detail/percentile.cpp index 99de328c42..e0b24a7d1a 100644 --- a/src/bvar/detail/percentile.cpp +++ b/src/bvar/detail/percentile.cpp @@ -108,7 +108,6 @@ Percentile::value_type Percentile::get_value() const { Percentile &Percentile::operator<<(int64_t latency) { agent_type* agent = _combiner->get_or_create_tls_agent(); if (BAIDU_UNLIKELY(!agent)) { - LOG(FATAL) << "Fail to create agent"; return *this; } if (latency < 0) { diff --git a/src/bvar/recorder.h b/src/bvar/recorder.h index b28b6372f6..ce80278dfa 100644 --- a/src/bvar/recorder.h +++ b/src/bvar/recorder.h @@ -269,7 +269,6 @@ inline IntRecorder& IntRecorder::operator<<(int64_t sample) { } agent_type* agent = _combiner->get_or_create_tls_agent(); if (BAIDU_UNLIKELY(!agent)) { - LOG(FATAL) << "Fail to create agent"; return *this; } uint64_t n; diff --git a/src/bvar/reducer.h b/src/bvar/reducer.h index 543e77c8b0..203d5cde0e 100644 --- a/src/bvar/reducer.h +++ b/src/bvar/reducer.h @@ -303,7 +303,6 @@ inline Reducer& Reducer::operator<<( // It's wait-free for most time agent_type* agent = _combiner->get_or_create_tls_agent(); if (__builtin_expect(!agent, 0)) { - LOG(FATAL) << "Fail to create agent"; return *this; } agent->element.modify(_combiner->op(), value);