mirror of
https://github.com/wolfpld/tracy.git
synced 2024-11-23 06:44:35 +00:00
Replace frame pointers with callstack frame ids.
This commit is contained in:
parent
664847211c
commit
9fc022346b
@ -197,7 +197,7 @@ enum { CallstackFrameIdSize = sizeof( CallstackFrameId ) };
|
|||||||
|
|
||||||
struct CallstackFrameTree
|
struct CallstackFrameTree
|
||||||
{
|
{
|
||||||
uint64_t frame;
|
CallstackFrameId frame;
|
||||||
uint64_t alloc;
|
uint64_t alloc;
|
||||||
uint32_t count;
|
uint32_t count;
|
||||||
std::vector<CallstackFrameTree> children;
|
std::vector<CallstackFrameTree> children;
|
||||||
|
@ -7,7 +7,7 @@ namespace Version
|
|||||||
{
|
{
|
||||||
enum { Major = 0 };
|
enum { Major = 0 };
|
||||||
enum { Minor = 4 };
|
enum { Minor = 4 };
|
||||||
enum { Patch = 5 };
|
enum { Patch = 6 };
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -4040,7 +4040,7 @@ void DrawZoneTrace( T zone, const std::vector<T>& trace, const Worker& worker, B
|
|||||||
bool found = false;
|
bool found = false;
|
||||||
for( auto& cf : currCs )
|
for( auto& cf : currCs )
|
||||||
{
|
{
|
||||||
if( cf == pf )
|
if( cf.data == pf.data )
|
||||||
{
|
{
|
||||||
idx--;
|
idx--;
|
||||||
found = true;
|
found = true;
|
||||||
@ -6509,7 +6509,7 @@ void View::DrawFindZone()
|
|||||||
{
|
{
|
||||||
ImGui::TextDisabled( "%i.", fidx++ );
|
ImGui::TextDisabled( "%i.", fidx++ );
|
||||||
ImGui::SameLine();
|
ImGui::SameLine();
|
||||||
ImGui::Text( "%p", (void*)entry );
|
ImGui::Text( "%p", (void*)m_worker.GetCanonicalPointer( entry ) );
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
@ -7499,7 +7499,7 @@ void View::DrawCallstackWindow()
|
|||||||
ImGui::Text( "%i", fidx++ );
|
ImGui::Text( "%i", fidx++ );
|
||||||
ImGui::NextColumn();
|
ImGui::NextColumn();
|
||||||
char buf[32];
|
char buf[32];
|
||||||
sprintf( buf, "%p", (void*)entry );
|
sprintf( buf, "%p", (void*)m_worker.GetCanonicalPointer( entry ) );
|
||||||
ImGui::TextUnformatted( buf );
|
ImGui::TextUnformatted( buf );
|
||||||
if( ImGui::IsItemClicked() )
|
if( ImGui::IsItemClicked() )
|
||||||
{
|
{
|
||||||
@ -8564,7 +8564,7 @@ void View::ListMemData( T ptr, T end, std::function<void(T&)> DrawAddress, const
|
|||||||
ImGui::EndChild();
|
ImGui::EndChild();
|
||||||
}
|
}
|
||||||
|
|
||||||
static tracy_force_inline CallstackFrameTree* GetFrameTreeItem( std::vector<CallstackFrameTree>& tree, uint64_t idx, const Worker& worker, bool groupByName )
|
static tracy_force_inline CallstackFrameTree* GetFrameTreeItem( std::vector<CallstackFrameTree>& tree, CallstackFrameId idx, const Worker& worker, bool groupByName )
|
||||||
{
|
{
|
||||||
std::vector<CallstackFrameTree>::iterator it;
|
std::vector<CallstackFrameTree>::iterator it;
|
||||||
if( groupByName )
|
if( groupByName )
|
||||||
@ -8581,7 +8581,7 @@ static tracy_force_inline CallstackFrameTree* GetFrameTreeItem( std::vector<Call
|
|||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
it = std::find_if( tree.begin(), tree.end(), [idx] ( const auto& v ) { return v.frame == idx; } );
|
it = std::find_if( tree.begin(), tree.end(), [idx] ( const auto& v ) { return v.frame.data == idx.data; } );
|
||||||
}
|
}
|
||||||
if( it == tree.end() )
|
if( it == tree.end() )
|
||||||
{
|
{
|
||||||
@ -9515,7 +9515,7 @@ void View::CallstackTooltip( uint32_t idx )
|
|||||||
{
|
{
|
||||||
ImGui::TextDisabled( "%i.", fidx++ );
|
ImGui::TextDisabled( "%i.", fidx++ );
|
||||||
ImGui::SameLine();
|
ImGui::SameLine();
|
||||||
ImGui::Text( "%p", (void*)entry );
|
ImGui::Text( "%p", (void*)m_worker.GetCanonicalPointer( entry ) );
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
|
@ -1018,24 +1018,69 @@ Worker::Worker( FileRead& f, EventType::Type eventMask )
|
|||||||
s_loadProgress.progress.store( LoadProgress::CallStacks, std::memory_order_relaxed );
|
s_loadProgress.progress.store( LoadProgress::CallStacks, std::memory_order_relaxed );
|
||||||
f.Read( sz );
|
f.Read( sz );
|
||||||
m_data.callstackPayload.reserve( sz );
|
m_data.callstackPayload.reserve( sz );
|
||||||
|
if( fileVer >= FileVersion( 0, 4, 6 ) )
|
||||||
|
{
|
||||||
for( uint64_t i=0; i<sz; i++ )
|
for( uint64_t i=0; i<sz; i++ )
|
||||||
{
|
{
|
||||||
uint8_t csz;
|
uint8_t csz;
|
||||||
f.Read( csz );
|
f.Read( csz );
|
||||||
|
|
||||||
const auto memsize = sizeof( VarArray<uint64_t> ) + csz * sizeof( uint64_t );
|
const auto memsize = sizeof( VarArray<CallstackFrameId> ) + csz * sizeof( CallstackFrameId );
|
||||||
auto mem = (char*)m_slab.AllocRaw( memsize );
|
auto mem = (char*)m_slab.AllocRaw( memsize );
|
||||||
|
|
||||||
auto data = (uint64_t*)mem;
|
auto data = (CallstackFrameId*)mem;
|
||||||
f.Read( data, csz * sizeof( uint64_t ) );
|
f.Read( data, csz * sizeof( CallstackFrameId ) );
|
||||||
|
|
||||||
auto arr = (VarArray<uint64_t>*)( mem + csz * sizeof( uint64_t ) );
|
auto arr = (VarArray<CallstackFrameId>*)( mem + csz * sizeof( CallstackFrameId ) );
|
||||||
new(arr) VarArray<uint64_t>( csz, data );
|
new(arr) VarArray<CallstackFrameId>( csz, data );
|
||||||
|
|
||||||
m_data.callstackPayload.push_back_no_space_check( arr );
|
m_data.callstackPayload.push_back_no_space_check( arr );
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
for( uint64_t i=0; i<sz; i++ )
|
||||||
|
{
|
||||||
|
uint8_t csz;
|
||||||
|
f.Read( csz );
|
||||||
|
|
||||||
if( fileVer >= FileVersion( 0, 4, 3 ) )
|
const auto memsize = sizeof( VarArray<CallstackFrameId> ) + csz * sizeof( CallstackFrameId );
|
||||||
|
auto mem = (char*)m_slab.AllocRaw( memsize );
|
||||||
|
|
||||||
|
auto data = (CallstackFrameId*)mem;
|
||||||
|
for( uint8_t j=0; j<csz; j++ )
|
||||||
|
{
|
||||||
|
uint64_t ptr;
|
||||||
|
f.Read( ptr );
|
||||||
|
data[j] = PackPointer( ptr );
|
||||||
|
}
|
||||||
|
|
||||||
|
auto arr = (VarArray<CallstackFrameId>*)( mem + csz * sizeof( CallstackFrameId ) );
|
||||||
|
new(arr) VarArray<CallstackFrameId>( csz, data );
|
||||||
|
|
||||||
|
m_data.callstackPayload.push_back_no_space_check( arr );
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if( fileVer >= FileVersion( 0, 4, 6 ) )
|
||||||
|
{
|
||||||
|
f.Read( sz );
|
||||||
|
m_data.callstackFrameMap.reserve( sz );
|
||||||
|
for( uint64_t i=0; i<sz; i++ )
|
||||||
|
{
|
||||||
|
CallstackFrameId id;
|
||||||
|
f.Read( id );
|
||||||
|
|
||||||
|
auto frameData = m_slab.Alloc<CallstackFrameData>();
|
||||||
|
f.Read( frameData->size );
|
||||||
|
|
||||||
|
frameData->data = m_slab.Alloc<CallstackFrame>( frameData->size );
|
||||||
|
f.Read( frameData->data, sizeof( CallstackFrame ) * frameData->size );
|
||||||
|
|
||||||
|
m_data.callstackFrameMap.emplace( id, frameData );
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else if( fileVer >= FileVersion( 0, 4, 3 ) )
|
||||||
{
|
{
|
||||||
f.Read( sz );
|
f.Read( sz );
|
||||||
m_data.callstackFrameMap.reserve( sz );
|
m_data.callstackFrameMap.reserve( sz );
|
||||||
@ -1050,7 +1095,7 @@ Worker::Worker( FileRead& f, EventType::Type eventMask )
|
|||||||
frameData->data = m_slab.Alloc<CallstackFrame>( frameData->size );
|
frameData->data = m_slab.Alloc<CallstackFrame>( frameData->size );
|
||||||
f.Read( frameData->data, sizeof( CallstackFrame ) * frameData->size );
|
f.Read( frameData->data, sizeof( CallstackFrame ) * frameData->size );
|
||||||
|
|
||||||
m_data.callstackFrameMap.emplace( ptr, frameData );
|
m_data.callstackFrameMap.emplace( PackPointer( ptr ), frameData );
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
@ -1068,7 +1113,7 @@ Worker::Worker( FileRead& f, EventType::Type eventMask )
|
|||||||
frameData->data = m_slab.Alloc<CallstackFrame>();
|
frameData->data = m_slab.Alloc<CallstackFrame>();
|
||||||
f.Read( frameData->data, sizeof( CallstackFrame ) );
|
f.Read( frameData->data, sizeof( CallstackFrame ) );
|
||||||
|
|
||||||
m_data.callstackFrameMap.emplace( ptr, frameData );
|
m_data.callstackFrameMap.emplace( PackPointer( ptr ), frameData );
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -1259,7 +1304,7 @@ std::pair <int, int> Worker::GetFrameRange( const FrameData& fd, int64_t from, i
|
|||||||
return std::make_pair( zbegin, zend );
|
return std::make_pair( zbegin, zend );
|
||||||
}
|
}
|
||||||
|
|
||||||
const CallstackFrameData* Worker::GetCallstackFrame( uint64_t ptr ) const
|
const CallstackFrameData* Worker::GetCallstackFrame( const CallstackFrameId& ptr ) const
|
||||||
{
|
{
|
||||||
auto it = m_data.callstackFrameMap.find( ptr );
|
auto it = m_data.callstackFrameMap.find( ptr );
|
||||||
if( it == m_data.callstackFrameMap.end() )
|
if( it == m_data.callstackFrameMap.end() )
|
||||||
@ -1775,7 +1820,7 @@ uint32_t Worker::ShrinkSourceLocation( uint64_t srcloc )
|
|||||||
|
|
||||||
uint32_t Worker::NewShrinkedSourceLocation( uint64_t srcloc )
|
uint32_t Worker::NewShrinkedSourceLocation( uint64_t srcloc )
|
||||||
{
|
{
|
||||||
const auto sz = m_data.sourceLocationExpand.size();
|
const auto sz = int32_t( m_data.sourceLocationExpand.size() );
|
||||||
m_data.sourceLocationExpand.push_back( srcloc );
|
m_data.sourceLocationExpand.push_back( srcloc );
|
||||||
#ifndef TRACY_NO_STATISTICS
|
#ifndef TRACY_NO_STATISTICS
|
||||||
m_data.sourceLocationZones.emplace( sz, SourceLocationZones() );
|
m_data.sourceLocationZones.emplace( sz, SourceLocationZones() );
|
||||||
@ -2036,18 +2081,24 @@ uint64_t Worker::GetCanonicalPointer( const CallstackFrameId& id ) const
|
|||||||
return ( id.idx & 0x7FFFFFFFFFFFFFFF ) | ( ( id.idx & 0x4000000000000000 ) << 1 );
|
return ( id.idx & 0x7FFFFFFFFFFFFFFF ) | ( ( id.idx & 0x4000000000000000 ) << 1 );
|
||||||
}
|
}
|
||||||
|
|
||||||
void Worker::AddCallstackPayload( uint64_t ptr, char* _data, size_t sz )
|
void Worker::AddCallstackPayload( uint64_t ptr, char* _data, size_t _sz )
|
||||||
{
|
{
|
||||||
assert( m_pendingCallstacks.find( ptr ) == m_pendingCallstacks.end() );
|
assert( m_pendingCallstacks.find( ptr ) == m_pendingCallstacks.end() );
|
||||||
|
|
||||||
const auto memsize = sizeof( VarArray<uint64_t> ) + sz;
|
const auto sz = _sz / sizeof( uint64_t );
|
||||||
|
const auto memsize = sizeof( VarArray<CallstackFrameId> ) + sz * sizeof( CallstackFrameId );
|
||||||
auto mem = (char*)m_slab.AllocRaw( memsize );
|
auto mem = (char*)m_slab.AllocRaw( memsize );
|
||||||
|
|
||||||
auto data = (uint64_t*)mem;
|
auto data = (CallstackFrameId*)mem;
|
||||||
memcpy( data, _data, sz );
|
auto dst = data;
|
||||||
|
auto src = (uint64_t*)_data;
|
||||||
|
for( size_t i=0; i<sz; i++ )
|
||||||
|
{
|
||||||
|
*dst++ = PackPointer( *src++ );
|
||||||
|
}
|
||||||
|
|
||||||
auto arr = (VarArray<uint64_t>*)( mem + sz );
|
auto arr = (VarArray<CallstackFrameId>*)( mem + sz * sizeof( CallstackFrameId ) );
|
||||||
new(arr) VarArray<uint64_t>( sz / sizeof( uint64_t ), data );
|
new(arr) VarArray<CallstackFrameId>( sz, data );
|
||||||
|
|
||||||
uint32_t idx;
|
uint32_t idx;
|
||||||
auto it = m_data.callstackMap.find( arr );
|
auto it = m_data.callstackMap.find( arr );
|
||||||
@ -2063,7 +2114,7 @@ void Worker::AddCallstackPayload( uint64_t ptr, char* _data, size_t sz )
|
|||||||
if( fit == m_data.callstackFrameMap.end() )
|
if( fit == m_data.callstackFrameMap.end() )
|
||||||
{
|
{
|
||||||
m_pendingCallstackFrames++;
|
m_pendingCallstackFrames++;
|
||||||
ServerQuery( ServerQueryCallstackFrame, frame );
|
ServerQuery( ServerQueryCallstackFrame, GetCanonicalPointer( frame ) );
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -3073,7 +3124,7 @@ void Worker::ProcessCallstackFrameSize( const QueueCallstackFrameSize& ev )
|
|||||||
m_pendingCallstackSubframes = ev.size;
|
m_pendingCallstackSubframes = ev.size;
|
||||||
|
|
||||||
// Frames may be duplicated due to recursion
|
// Frames may be duplicated due to recursion
|
||||||
auto fmit = m_data.callstackFrameMap.find( ev.ptr );
|
auto fmit = m_data.callstackFrameMap.find( PackPointer( ev.ptr ) );
|
||||||
if( fmit == m_data.callstackFrameMap.end() )
|
if( fmit == m_data.callstackFrameMap.end() )
|
||||||
{
|
{
|
||||||
m_callstackFrameStaging = m_slab.Alloc<CallstackFrameData>();
|
m_callstackFrameStaging = m_slab.Alloc<CallstackFrameData>();
|
||||||
@ -3103,8 +3154,8 @@ void Worker::ProcessCallstackFrame( const QueueCallstackFrame& ev )
|
|||||||
|
|
||||||
if( --m_pendingCallstackSubframes == 0 )
|
if( --m_pendingCallstackSubframes == 0 )
|
||||||
{
|
{
|
||||||
assert( m_data.callstackFrameMap.find( m_callstackFrameStagingPtr ) == m_data.callstackFrameMap.end() );
|
assert( m_data.callstackFrameMap.find( PackPointer( m_callstackFrameStagingPtr ) ) == m_data.callstackFrameMap.end() );
|
||||||
m_data.callstackFrameMap.emplace( m_callstackFrameStagingPtr, m_callstackFrameStaging );
|
m_data.callstackFrameMap.emplace( PackPointer( m_callstackFrameStagingPtr ), m_callstackFrameStaging );
|
||||||
m_callstackFrameStaging = nullptr;
|
m_callstackFrameStaging = nullptr;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -3803,14 +3854,14 @@ void Worker::Write( FileWrite& f )
|
|||||||
auto cs = m_data.callstackPayload[i];
|
auto cs = m_data.callstackPayload[i];
|
||||||
uint8_t csz = cs->size();
|
uint8_t csz = cs->size();
|
||||||
f.Write( &csz, sizeof( csz ) );
|
f.Write( &csz, sizeof( csz ) );
|
||||||
f.Write( cs->data(), sizeof( uint64_t ) * csz );
|
f.Write( cs->data(), sizeof( CallstackFrameId ) * csz );
|
||||||
}
|
}
|
||||||
|
|
||||||
sz = m_data.callstackFrameMap.size();
|
sz = m_data.callstackFrameMap.size();
|
||||||
f.Write( &sz, sizeof( sz ) );
|
f.Write( &sz, sizeof( sz ) );
|
||||||
for( auto& frame : m_data.callstackFrameMap )
|
for( auto& frame : m_data.callstackFrameMap )
|
||||||
{
|
{
|
||||||
f.Write( &frame.first, sizeof( uint64_t ) );
|
f.Write( &frame.first, sizeof( CallstackFrameId ) );
|
||||||
f.Write( &frame.second->size, sizeof( frame.second->size ) );
|
f.Write( &frame.second->size, sizeof( frame.second->size ) );
|
||||||
f.Write( frame.second->data, sizeof( CallstackFrame ) * frame.second->size );
|
f.Write( frame.second->data, sizeof( CallstackFrame ) * frame.second->size );
|
||||||
}
|
}
|
||||||
|
@ -143,9 +143,9 @@ private:
|
|||||||
flat_hash_map<int32_t, uint64_t> sourceLocationZonesCnt;
|
flat_hash_map<int32_t, uint64_t> sourceLocationZonesCnt;
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
flat_hash_map<VarArray<uint64_t>*, uint32_t, VarArrayHasherPOT<uint64_t>, VarArrayComparator<uint64_t>> callstackMap;
|
flat_hash_map<VarArray<CallstackFrameId>*, uint32_t, VarArrayHasherPOT<CallstackFrameId>, VarArrayComparator<CallstackFrameId>> callstackMap;
|
||||||
Vector<VarArray<uint64_t>*> callstackPayload;
|
Vector<VarArray<CallstackFrameId>*> callstackPayload;
|
||||||
flat_hash_map<uint64_t, CallstackFrameData*> callstackFrameMap;
|
flat_hash_map<CallstackFrameId, CallstackFrameData*, CallstackFrameIdHash, CallstackFrameIdCompare> callstackFrameMap;
|
||||||
|
|
||||||
std::map<uint32_t, LockMap> lockMap;
|
std::map<uint32_t, LockMap> lockMap;
|
||||||
|
|
||||||
@ -244,8 +244,8 @@ public:
|
|||||||
const Vector<ThreadData*>& GetThreadData() const { return m_data.threads; }
|
const Vector<ThreadData*>& GetThreadData() const { return m_data.threads; }
|
||||||
const MemData& GetMemData() const { return m_data.memory; }
|
const MemData& GetMemData() const { return m_data.memory; }
|
||||||
|
|
||||||
const VarArray<uint64_t>& GetCallstack( uint32_t idx ) const { return *m_data.callstackPayload[idx]; }
|
const VarArray<CallstackFrameId>& GetCallstack( uint32_t idx ) const { return *m_data.callstackPayload[idx]; }
|
||||||
const CallstackFrameData* GetCallstackFrame( uint64_t ptr ) const;
|
const CallstackFrameData* GetCallstackFrame( const CallstackFrameId& ptr ) const;
|
||||||
uint64_t GetCanonicalPointer( const CallstackFrameId& id ) const;
|
uint64_t GetCanonicalPointer( const CallstackFrameId& id ) const;
|
||||||
|
|
||||||
const CrashEvent& GetCrashEvent() const { return m_data.m_crashEvent; }
|
const CrashEvent& GetCrashEvent() const { return m_data.m_crashEvent; }
|
||||||
|
Loading…
Reference in New Issue
Block a user