From b09b368e2945a5e9c4ea6dd9252a6b19c31b5836 Mon Sep 17 00:00:00 2001 From: Eliza Weisman Date: Sun, 19 Sep 2021 12:37:15 -0700 Subject: [PATCH] subscriber: clear `enabled` filter map when short circuiting (#1575) This is essentially the same change as #1569, but for `enabled` states rather than `register_callsite`. When a global filter returns `false` from `enabled`, ensure that the per-layer filter `FilterMap` and debug counters are cleared, so that they are empty on the next `enabled` call. See #1563 --- tracing-subscriber/src/filter/layer_filters.rs | 16 ++++++++++++++++ tracing-subscriber/src/layer/layered.rs | 7 +++++++ 2 files changed, 23 insertions(+) diff --git a/tracing-subscriber/src/filter/layer_filters.rs b/tracing-subscriber/src/filter/layer_filters.rs index 69549062f1..9b23419493 100644 --- a/tracing-subscriber/src/filter/layer_filters.rs +++ b/tracing-subscriber/src/filter/layer_filters.rs @@ -709,6 +709,22 @@ impl FilterState { } } + /// Clears the current in-progress filter state. + /// + /// This resets the [`FilterMap`] and current [`Interest`] as well as + /// clearing the debug counters. + pub(crate) fn clear_enabled() { + // Drop the `Result` returned by `try_with` --- if we are in the middle + // a panic and the thread-local has been torn down, that's fine, just + // ignore it ratehr than panicking. + let _ = FILTERING.try_with(|filtering| { + filtering.enabled.set(FilterMap::default()); + + #[cfg(debug_assertions)] + filtering.counters.in_filter_pass.set(0); + }); + } + pub(crate) fn take_interest() -> Option { FILTERING .try_with(|filtering| { diff --git a/tracing-subscriber/src/layer/layered.rs b/tracing-subscriber/src/layer/layered.rs index 8d6c6747da..39b478c973 100644 --- a/tracing-subscriber/src/layer/layered.rs +++ b/tracing-subscriber/src/layer/layered.rs @@ -80,6 +80,13 @@ where self.inner.enabled(metadata) } else { // otherwise, the callsite is disabled by the layer + + // If per-layer filters are in use, and we are short-circuiting + // (rather than calling into the inner type), clear the current + // per-layer filter `enabled` state. + #[cfg(feature = "registry")] + filter::FilterState::clear_enabled(); + false } }