From 26cee8acf0a0efb6d26ed98e132986d80a73e56b Mon Sep 17 00:00:00 2001 From: Bartosz Taudul Date: Wed, 26 Feb 2020 22:35:15 +0100 Subject: [PATCH] Perform symbol information queries. --- client/TracyProfiler.cpp | 25 +++++++++++++++++++++++++ client/TracyProfiler.hpp | 1 + common/TracyProtocol.hpp | 3 ++- common/TracyQueue.hpp | 2 ++ server/TracyEvent.hpp | 7 +++++++ server/TracyWorker.cpp | 34 +++++++++++++++++++++++++++++++++- server/TracyWorker.hpp | 3 +++ 7 files changed, 73 insertions(+), 2 deletions(-) diff --git a/client/TracyProfiler.cpp b/client/TracyProfiler.cpp index 3a934e70..6782dbe4 100644 --- a/client/TracyProfiler.cpp +++ b/client/TracyProfiler.cpp @@ -2301,6 +2301,9 @@ bool Profiler::HandleServerQuery() case ServerQueryParameter: HandleParameter( ptr ); break; + case ServerQuerySymbol: + HandleSymbolQuery( ptr ); + break; default: assert( false ); break; @@ -2677,6 +2680,28 @@ void Profiler::HandleParameter( uint64_t payload ) m_paramCallback( idx, val ); } +void Profiler::HandleSymbolQuery( uint64_t symbol ) +{ +#ifdef TRACY_HAS_CALLSTACK + const auto sym = DecodeSymbolAddress( symbol ); + + SendString( uint64_t( sym.file ), sym.file, QueueType::CustomStringData ); + SendString( uint64_t( sym.name ), sym.name, QueueType::CustomStringData ); + + QueueItem item; + MemWrite( &item.hdr.type, QueueType::SymbolInformation ); + MemWrite( &item.callstackFrame.file, uint64_t( sym.file ) ); + MemWrite( &item.callstackFrame.name, uint64_t( sym.name ) ); + MemWrite( &item.callstackFrame.line, sym.line ); + MemWrite( &item.callstackFrame.symAddr, symbol ); + + AppendData( &item, QueueDataSize[(int)QueueType::SymbolInformation] ); + + tracy_free( (void*)sym.file ); + tracy_free( (void*)sym.name ); +#endif +} + } #ifdef __cplusplus diff --git a/client/TracyProfiler.hpp b/client/TracyProfiler.hpp index 7cb6670a..4fa499b0 100644 --- a/client/TracyProfiler.hpp +++ b/client/TracyProfiler.hpp @@ -557,6 +557,7 @@ private: bool HandleServerQuery(); void HandleDisconnect(); void HandleParameter( uint64_t payload ); + void HandleSymbolQuery( uint64_t symbol ); void CalibrateTimer(); void CalibrateDelay(); diff --git a/common/TracyProtocol.hpp b/common/TracyProtocol.hpp index 2cf85d5f..56ffba5a 100644 --- a/common/TracyProtocol.hpp +++ b/common/TracyProtocol.hpp @@ -47,7 +47,8 @@ enum ServerQuery : uint8_t ServerQueryFrameName, ServerQueryDisconnect, ServerQueryExternalName, - ServerQueryParameter + ServerQueryParameter, + ServerQuerySymbol }; struct ServerQueryPacket diff --git a/common/TracyQueue.hpp b/common/TracyQueue.hpp index c636f902..963acb26 100644 --- a/common/TracyQueue.hpp +++ b/common/TracyQueue.hpp @@ -21,6 +21,7 @@ enum class QueueType : uint8_t Callstack, CallstackAlloc, CallstackSample, + SymbolInformation, FrameImage, ZoneBegin, ZoneBeginCallstack, @@ -448,6 +449,7 @@ static constexpr size_t QueueDataSize[] = { sizeof( QueueHeader ) + sizeof( QueueCallstack ), sizeof( QueueHeader ) + sizeof( QueueCallstackAlloc ), sizeof( QueueHeader ) + sizeof( QueueCallstackSample ), + sizeof( QueueHeader ) + sizeof( QueueCallstackFrame ), // symbol information sizeof( QueueHeader ) + sizeof( QueueFrameImage ), sizeof( QueueHeader ) + sizeof( QueueZoneBegin ), sizeof( QueueHeader ) + sizeof( QueueZoneBegin ), // callstack diff --git a/server/TracyEvent.hpp b/server/TracyEvent.hpp index fa01a199..fb8436bd 100644 --- a/server/TracyEvent.hpp +++ b/server/TracyEvent.hpp @@ -326,7 +326,14 @@ struct CallstackFrame : public CallstackFrameBasic uint64_t symAddr; }; +struct SymbolData : public CallstackFrameBasic +{ + StringIdx imageName; +}; + +enum { CallstackFrameBasicSize = sizeof( CallstackFrameBasic ) }; enum { CallstackFrameSize = sizeof( CallstackFrame ) }; +enum { SymbolDataSize = sizeof( SymbolData ) }; struct CallstackFrameData { diff --git a/server/TracyWorker.cpp b/server/TracyWorker.cpp index d6c138ab..c68be959 100644 --- a/server/TracyWorker.cpp +++ b/server/TracyWorker.cpp @@ -2501,7 +2501,8 @@ void Worker::Exec() { if( m_pendingStrings != 0 || m_pendingThreads != 0 || m_pendingSourceLocation != 0 || m_pendingCallstackFrames != 0 || !m_pendingCustomStrings.empty() || m_data.plots.IsPending() || m_pendingCallstackPtr != 0 || - m_pendingExternalNames != 0 || m_pendingCallstackSubframes != 0 || !m_pendingFrameImageData.empty() ) + m_pendingExternalNames != 0 || m_pendingCallstackSubframes != 0 || !m_pendingFrameImageData.empty() || + !m_pendingSymbols.empty() ) { continue; } @@ -3461,6 +3462,9 @@ bool Worker::Process( const QueueItem& ev ) case QueueType::CallstackFrame: ProcessCallstackFrame( ev.callstackFrame ); break; + case QueueType::SymbolInformation: + ProcessSymbolInformation( ev.callstackFrame ); + break; case QueueType::Terminate: m_terminate = true; break; @@ -4723,6 +4727,12 @@ void Worker::ProcessCallstackFrame( const QueueCallstackFrame& ev ) m_callstackFrameStaging->data[idx].line = ev.line; m_callstackFrameStaging->data[idx].symAddr = ev.symAddr; + if( ev.symAddr != 0 && m_data.symbolMap.find( ev.symAddr ) == m_data.symbolMap.end() && m_pendingSymbols.find( ev.symAddr ) == m_pendingSymbols.end() ) + { + m_pendingSymbols.emplace( ev.symAddr, m_callstackFrameStaging->imageName ); + Query( ServerQuerySymbol, ev.symAddr ); + } + if( --m_pendingCallstackSubframes == 0 ) { assert( m_data.callstackFrameMap.find( PackPointer( m_callstackFrameStagingPtr ) ) == m_data.callstackFrameMap.end() ); @@ -4739,6 +4749,28 @@ void Worker::ProcessCallstackFrame( const QueueCallstackFrame& ev ) m_pendingCustomStrings.erase( m_pendingCustomStrings.find( ev.file ) ); } +void Worker::ProcessSymbolInformation( const QueueCallstackFrame& ev ) +{ + auto it = m_pendingSymbols.find( ev.symAddr ); + assert( it != m_pendingSymbols.end() ); + + auto nit = m_pendingCustomStrings.find( ev.name ); + assert( nit != m_pendingCustomStrings.end() ); + auto fit = m_pendingCustomStrings.find( ev.file ); + assert( fit != m_pendingCustomStrings.end() ); + + SymbolData sd; + sd.name = StringIdx( nit->second.idx ); + sd.file = StringIdx( fit->second.idx ); + sd.line = ev.line; + sd.imageName = it->second; + m_data.symbolMap.emplace( ev.symAddr, std::move( sd ) ); + + m_pendingSymbols.erase( it ); + m_pendingCustomStrings.erase( nit ); + m_pendingCustomStrings.erase( m_pendingCustomStrings.find( ev.file ) ); +} + void Worker::ProcessCrashReport( const QueueCrashReport& ev ) { CheckString( ev.text ); diff --git a/server/TracyWorker.hpp b/server/TracyWorker.hpp index 72ef4ec3..75a5a1ba 100644 --- a/server/TracyWorker.hpp +++ b/server/TracyWorker.hpp @@ -217,6 +217,7 @@ private: Vector>> callstackPayload; unordered_flat_map callstackFrameMap; unordered_flat_map revFrameMap; + unordered_flat_map symbolMap; unordered_flat_map lockMap; @@ -517,6 +518,7 @@ private: tracy_force_inline void ProcessCallstackSample( const QueueCallstackSample& ev ); tracy_force_inline void ProcessCallstackFrameSize( const QueueCallstackFrameSize& ev ); tracy_force_inline void ProcessCallstackFrame( const QueueCallstackFrame& ev ); + tracy_force_inline void ProcessSymbolInformation( const QueueCallstackFrame& ev ); tracy_force_inline void ProcessCrashReport( const QueueCrashReport& ev ); tracy_force_inline void ProcessSysTime( const QueueSysTime& ev ); tracy_force_inline void ProcessContextSwitch( const QueueContextSwitch& ev ); @@ -693,6 +695,7 @@ private: unordered_flat_map m_threadMap; unordered_flat_map m_nextCallstack; unordered_flat_map m_pendingFrameImageData; + unordered_flat_map m_pendingSymbols; uint32_t m_pendingStrings; uint32_t m_pendingThreads;