summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorRye <rye@lindenlab.com>2024-11-05 22:57:25 -0500
committerRye <rye@lindenlab.com>2024-11-05 22:57:25 -0500
commitc092782cf76f90d42aa21fed318126f3f094d793 (patch)
treeb3e8e03ec64990111488dc4ea9b6f18f1dd61064
parent65c80ed68615e4fd06b0c68f77ae6acca41ed584 (diff)
Fix Tracy memory profiling on macos
-rw-r--r--indra/llcommon/linden_common.h6
-rw-r--r--indra/llcommon/llcommon.cpp72
-rw-r--r--indra/llcommon/llmemory.h51
-rw-r--r--indra/llcommon/llprofiler.h12
-rw-r--r--indra/newview/llappviewermacosx.cpp5
5 files changed, 85 insertions, 61 deletions
diff --git a/indra/llcommon/linden_common.h b/indra/llcommon/linden_common.h
index a918caa2e8..a41af153fe 100644
--- a/indra/llcommon/linden_common.h
+++ b/indra/llcommon/linden_common.h
@@ -28,12 +28,6 @@
#define LL_LINDEN_COMMON_H
#include "llprofiler.h"
-#if TRACY_ENABLE && !defined(LL_PROFILER_ENABLE_TRACY_OPENGL) // hooks for memory profiling
-void *tracy_aligned_malloc(size_t size, size_t alignment);
-void tracy_aligned_free(void *memblock);
-#define _aligned_malloc(X, Y) tracy_aligned_malloc((X), (Y))
-#define _aligned_free(X) tracy_aligned_free((X))
-#endif
// *NOTE: Please keep includes here to a minimum!
//
diff --git a/indra/llcommon/llcommon.cpp b/indra/llcommon/llcommon.cpp
index f1f3958fe0..832a7a2b0a 100644
--- a/indra/llcommon/llcommon.cpp
+++ b/indra/llcommon/llcommon.cpp
@@ -33,23 +33,23 @@
#include "lltracethreadrecorder.h"
#include "llcleanup.h"
-thread_local bool gProfilerEnabled = false;
-
-#if (TRACY_ENABLE)
+#if LL_PROFILER_CONFIGURATION > 1 && TRACY_ENABLE && !LL_PROFILER_ENABLE_TRACY_OPENGL
// Override new/delete for tracy memory profiling
void* ll_tracy_new(size_t size)
{
- void* ptr;
- if (gProfilerEnabled)
- {
- //LL_PROFILE_ZONE_SCOPED_CATEGORY_MEMORY;
- ptr = (malloc)(size);
- }
- else
+ void* ptr = (malloc)(size);
+ if (!ptr)
{
- ptr = (malloc)(size);
+ throw std::bad_alloc();
}
+ TracyAlloc(ptr, size);
+ return ptr;
+}
+
+void* ll_tracy_aligned_new(size_t size, size_t alignment)
+{
+ void* ptr = ll_aligned_malloc_fallback(size, alignment);
if (!ptr)
{
throw std::bad_alloc();
@@ -58,6 +58,18 @@ void* ll_tracy_new(size_t size)
return ptr;
}
+void ll_tracy_delete(void* ptr)
+{
+ TracyFree(ptr);
+ (free)(ptr);
+}
+
+void ll_tracy_aligned_delete(void* ptr)
+{
+ TracyFree(ptr);
+ ll_aligned_free_fallback(ptr);
+}
+
void* operator new(size_t size)
{
return ll_tracy_new(size);
@@ -68,18 +80,14 @@ void* operator new[](std::size_t count)
return ll_tracy_new(count);
}
-void ll_tracy_delete(void* ptr)
+void* operator new(size_t size, std::align_val_t align)
{
- TracyFree(ptr);
- if (gProfilerEnabled)
- {
- //LL_PROFILE_ZONE_SCOPED_CATEGORY_MEMORY;
- (free)(ptr);
- }
- else
- {
- (free)(ptr);
- }
+ return ll_tracy_aligned_new(size, (size_t)align);
+}
+
+void* operator new[](std::size_t count, std::align_val_t align)
+{
+ return ll_tracy_aligned_new(count, (size_t)align);
}
void operator delete(void *ptr) noexcept
@@ -92,27 +100,17 @@ void operator delete[](void* ptr) noexcept
ll_tracy_delete(ptr);
}
-// C-style malloc/free can't be so easily overridden, so we define tracy versions and use
-// a pre-processor #define in linden_common.h to redirect to them. The parens around the native
-// functions below prevents recursive substitution by the preprocessor.
-//
-// Unaligned mallocs are rare in LL code but hooking them causes problems in 3p lib code (looking at
-// you, Havok), so we'll only capture the aligned version.
-
-void *tracy_aligned_malloc(size_t size, size_t alignment)
+void operator delete(void *ptr, std::align_val_t align) noexcept
{
- auto ptr = ll_aligned_malloc_fallback(size, alignment);
- if (ptr) TracyAlloc(ptr, size);
- return ptr;
+ ll_tracy_aligned_delete(ptr);
}
-void tracy_aligned_free(void *memblock)
+void operator delete[](void* ptr, std::align_val_t align) noexcept
{
- TracyFree(memblock);
- ll_aligned_free_fallback(memblock);
+ ll_tracy_aligned_delete(ptr);
}
-#endif
+#endif // TRACY_ENABLE && !LL_PROFILER_ENABLE_TRACY_OPENGL
//static
bool LLCommon::sAprInitialized = false;
diff --git a/indra/llcommon/llmemory.h b/indra/llcommon/llmemory.h
index 80cfe554c4..72aec57080 100644
--- a/indra/llcommon/llmemory.h
+++ b/indra/llcommon/llmemory.h
@@ -222,7 +222,7 @@ inline void* ll_aligned_realloc_16(void* ptr, size_t size, size_t old_size) // r
ll_aligned_free_16(ptr);
}
#endif
- LL_PROFILE_ALLOC(ptr, size);
+ LL_PROFILE_ALLOC(ret, size);
return ret;
}
@@ -231,8 +231,6 @@ inline void* ll_aligned_malloc_32(size_t size) // returned hunk MUST be freed wi
LL_PROFILE_ZONE_SCOPED_CATEGORY_MEMORY;
#if defined(LL_WINDOWS)
void* ret = _aligned_malloc(size, 32);
-#elif defined(LL_DARWIN)
- void* ret = ll_aligned_malloc_fallback( size, 32 );
#else
void *ret;
if (0 != posix_memalign(&ret, 32, size))
@@ -248,8 +246,31 @@ inline void ll_aligned_free_32(void *p)
LL_PROFILE_FREE(p);
#if defined(LL_WINDOWS)
_aligned_free(p);
-#elif defined(LL_DARWIN)
- ll_aligned_free_fallback( p );
+#else
+ free(p); // posix_memalign() is compatible with heap deallocator
+#endif
+}
+
+inline void* ll_aligned_malloc_64(size_t size) // returned hunk MUST be freed with ll_aligned_free_32().
+{
+ LL_PROFILE_ZONE_SCOPED_CATEGORY_MEMORY;
+#if defined(LL_WINDOWS)
+ void* ret = _aligned_malloc(size, 64);
+#else
+ void *ret;
+ if (0 != posix_memalign(&ret, 64, size))
+ return nullptr;
+#endif
+ LL_PROFILE_ALLOC(ret, size);
+ return ret;
+}
+
+inline void ll_aligned_free_64(void *p)
+{
+ LL_PROFILE_ZONE_SCOPED_CATEGORY_MEMORY;
+ LL_PROFILE_FREE(p);
+#if defined(LL_WINDOWS)
+ _aligned_free(p);
#else
free(p); // posix_memalign() is compatible with heap deallocator
#endif
@@ -261,19 +282,23 @@ LL_FORCE_INLINE void* ll_aligned_malloc(size_t size)
{
LL_PROFILE_ZONE_SCOPED_CATEGORY_MEMORY;
void* ret;
- if (LL_DEFAULT_HEAP_ALIGN % ALIGNMENT == 0)
+ if constexpr (LL_DEFAULT_HEAP_ALIGN % ALIGNMENT == 0)
{
ret = malloc(size);
LL_PROFILE_ALLOC(ret, size);
}
- else if (ALIGNMENT == 16)
+ else if constexpr (ALIGNMENT == 16)
{
ret = ll_aligned_malloc_16(size);
}
- else if (ALIGNMENT == 32)
+ else if constexpr (ALIGNMENT == 32)
{
ret = ll_aligned_malloc_32(size);
}
+ else if constexpr (ALIGNMENT == 64)
+ {
+ ret = ll_aligned_malloc_64(size);
+ }
else
{
ret = ll_aligned_malloc_fallback(size, ALIGNMENT);
@@ -285,16 +310,20 @@ template<size_t ALIGNMENT>
LL_FORCE_INLINE void ll_aligned_free(void* ptr)
{
LL_PROFILE_ZONE_SCOPED_CATEGORY_MEMORY;
- if (ALIGNMENT == LL_DEFAULT_HEAP_ALIGN)
+ if constexpr (ALIGNMENT == LL_DEFAULT_HEAP_ALIGN)
{
LL_PROFILE_FREE(ptr);
free(ptr);
}
- else if (ALIGNMENT == 16)
+ else if constexpr (ALIGNMENT == 16)
{
ll_aligned_free_16(ptr);
}
- else if (ALIGNMENT == 32)
+ else if constexpr (ALIGNMENT == 32)
+ {
+ return ll_aligned_free_32(ptr);
+ }
+ else if constexpr (ALIGNMENT == 64)
{
return ll_aligned_free_32(ptr);
}
diff --git a/indra/llcommon/llprofiler.h b/indra/llcommon/llprofiler.h
index f6a4d24747..e5cde192d9 100644
--- a/indra/llcommon/llprofiler.h
+++ b/indra/llcommon/llprofiler.h
@@ -74,8 +74,6 @@
#define LL_PROFILER_CONFIGURATION LL_PROFILER_CONFIG_FAST_TIMER
#endif
-extern thread_local bool gProfilerEnabled;
-
#if defined(LL_PROFILER_CONFIGURATION) && (LL_PROFILER_CONFIGURATION > LL_PROFILER_CONFIG_NONE)
#if LL_PROFILER_CONFIGURATION == LL_PROFILER_CONFIG_TRACY || LL_PROFILER_CONFIGURATION == LL_PROFILER_CONFIG_TRACY_FAST_TIMER
#include "tracy/Tracy.hpp"
@@ -90,7 +88,7 @@ extern thread_local bool gProfilerEnabled;
#if LL_PROFILER_CONFIGURATION == LL_PROFILER_CONFIG_TRACY
#define LL_PROFILER_FRAME_END FrameMark
- #define LL_PROFILER_SET_THREAD_NAME( name ) tracy::SetThreadName( name ); gProfilerEnabled = true;
+ #define LL_PROFILER_SET_THREAD_NAME( name ) tracy::SetThreadName( name );
#define LL_RECORD_BLOCK_TIME(name) ZoneScoped // Want descriptive names; was: ZoneNamedN( ___tracy_scoped_zone, #name, true );
#define LL_PROFILE_ZONE_NAMED(name) ZoneNamedN( ___tracy_scoped_zone, name, true );
#define LL_PROFILE_ZONE_NAMED_COLOR(name,color) ZoneNamedNC( ___tracy_scopped_zone, name, color, true ) // RGB
@@ -133,7 +131,7 @@ extern thread_local bool gProfilerEnabled;
#endif
#if LL_PROFILER_CONFIGURATION == LL_PROFILER_CONFIG_TRACY_FAST_TIMER
#define LL_PROFILER_FRAME_END FrameMark
- #define LL_PROFILER_SET_THREAD_NAME( name ) tracy::SetThreadName( name ); gProfilerEnabled = true;
+ #define LL_PROFILER_SET_THREAD_NAME( name ) tracy::SetThreadName( name );
#define LL_RECORD_BLOCK_TIME(name) ZoneNamedN(___tracy_scoped_zone, #name, true); const LLTrace::BlockTimer& LL_GLUE_TOKENS(block_time_recorder, __LINE__)(LLTrace::timeThisBlock(name)); (void)LL_GLUE_TOKENS(block_time_recorder, __LINE__);
#define LL_PROFILE_ZONE_NAMED(name) ZoneNamedN( ___tracy_scoped_zone, #name, true );
#define LL_PROFILE_ZONE_NAMED_COLOR(name,color) ZoneNamedNC( ___tracy_scopped_zone, name, color, true ) // RGB
@@ -163,7 +161,7 @@ extern thread_local bool gProfilerEnabled;
#define LL_PROFILER_GPU_COLLECT TracyGpuCollect
#define LL_PROFILER_GPU_CONTEXT TracyGpuContext
-// disable memory tracking (incompatible with GPU tracing
+// disable memory tracking (incompatible with GPU tracing)
#define LL_PROFILE_ALLOC(ptr, size) (void)(ptr); (void)(size);
#define LL_PROFILE_FREE(ptr) (void)(ptr);
#else
@@ -174,7 +172,7 @@ extern thread_local bool gProfilerEnabled;
#define LL_LABEL_OBJECT_GL(type, name, length, label)
-#if !LL_DARWIN && LL_PROFILER_CONFIGURATION > 1
+#if LL_PROFILER_CONFIGURATION > 1
#define LL_PROFILE_ALLOC(ptr, size) TracyAlloc(ptr, size)
#define LL_PROFILE_FREE(ptr) TracyFree(ptr)
#else
@@ -182,7 +180,7 @@ extern thread_local bool gProfilerEnabled;
#define LL_PROFILE_FREE(ptr) (void)(ptr);
#endif
-#endif
+#endif // LL_PROFILER_ENABLE_TRACY_OPENGL
#if LL_PROFILER_ENABLE_RENDER_DOC
#define LL_LABEL_OBJECT_GL(type, name, length, label) glObjectLabel(type, name, length, label)
diff --git a/indra/newview/llappviewermacosx.cpp b/indra/newview/llappviewermacosx.cpp
index 4162c0479a..f497a3cdf3 100644
--- a/indra/newview/llappviewermacosx.cpp
+++ b/indra/newview/llappviewermacosx.cpp
@@ -231,6 +231,11 @@ void infos(const std::string& message)
int main( int argc, char **argv )
{
+ // Call Tracy first thing to have it allocate memory
+ // https://github.com/wolfpld/tracy/issues/196
+ LL_PROFILER_FRAME_END;
+ LL_PROFILER_SET_THREAD_NAME("App");
+
// Store off the command line args for use later.
gArgC = argc;
gArgV = argv;