From 3293e263c6606a72b66ce4e9bd566051a4cd3d13 Mon Sep 17 00:00:00 2001 From: Bartosz Taudul Date: Sat, 25 Jul 2026 19:10:12 +0200 Subject: [PATCH] Exclude context switch samples from symbol and child sample maps. Context switch samples are excluded from sampling statistics, as they are not produced by the statistical profiling timer and their stacks are always parked at the scheduler. During live capture this exclusion is structural, as such samples never enter the statistics processing path. On trace load, however, only the job which computes symbol statistics and the instruction pointer map filtered them out. The job which builds the per-symbol sample lists and the child sample map did not, so on a loaded trace these two structures included tens of thousands of context switch samples that a live session would not count. This made range-limited statistics counts exceed the whole-trace counts, inflated child sample costs in the symbol view, and caused the same trace to show different numbers live and after a save and reload. On the test trace, __schedule reported 56 exclusive samples but 32747 entries in its sample list. Apply the same context switch sample filter when building the symbol samples and child samples maps. --- server/TracyWorker.cpp | 7 +++++++ 1 file changed, 7 insertions(+) diff --git a/server/TracyWorker.cpp b/server/TracyWorker.cpp index 25718b70..c34af597 100644 --- a/server/TracyWorker.cpp +++ b/server/TracyWorker.cpp @@ -1923,8 +1923,15 @@ Worker::Worker( FileRead& f, EventType::Type eventMask, bool bgTasks, bool allow for( auto& t : m_data.threads ) { uint16_t tid = CompressThread( t->id ); + auto cit = t->ctxSwitchSamples.begin(); for( auto& v : t->samples ) { + if( cit != t->ctxSwitchSamples.end() ) + { + const auto vt = v.time.Val(); + cit = std::lower_bound( cit, t->ctxSwitchSamples.end(), vt, []( const auto& l, const auto& r ) { return (uint64_t)l.time.Val() < (uint64_t)r; } ); + if( cit != t->ctxSwitchSamples.end() && cit->time.Val() == vt ) continue; + } const auto& time = v.time; const auto cs = v.callstack.Val(); const auto& callstack = GetCallstack( cs );