- Revision
- 280349
- Author
- [email protected]
- Date
- 2021-07-27 14:36:17 -0700 (Tue, 27 Jul 2021)
Log Message
3.5 MB system-wide footprint impact due to thread-locals in libANGLE
https://bugs.webkit.org/show_bug.cgi?id=228240
rdar://79504783
Reviewed by Ken Russell and Geoff Garen.
Apple's dyld has a bug where thread_local variables are dirtied on
process launch, causing a memory regression. Work around this
temporarily in ANGLE by using pthread thread local storage.
I don't expect this to be upstreamed to ANGLE unless they
want it. If it isn't, this patch will have to be applied until
the dyld bug is fixed.
* src/libANGLE/Context.cpp: Implement some methods to get/set what was
the global variable gCurrentValidContext.
(gl::GetCurrentValidContextTLSIndex):
(gl::GetCurrentValidContextTLS):
(gl::SetCurrentValidContextTLS):
(gl::Context::setContextLost):
* src/libANGLE/Context.h:
* src/libGLESv2/global_state.cpp: Ditto, but for gCurrentThread.
(egl::GetCurrentThreadTLSIndex):
(egl::GetCurrentThreadTLS):
(egl::SetCurrentThreadTLS):
(egl::GetCurrentThread):
(egl::SetContextCurrent):
* src/libGLESv2/global_state.h:
(gl::GetGlobalContext):
(gl::GetValidGlobalContext):
Modified Paths
Diff
Modified: trunk/Source/ThirdParty/ANGLE/ChangeLog (280348 => 280349)
--- trunk/Source/ThirdParty/ANGLE/ChangeLog 2021-07-27 18:55:14 UTC (rev 280348)
+++ trunk/Source/ThirdParty/ANGLE/ChangeLog 2021-07-27 21:36:17 UTC (rev 280349)
@@ -1,3 +1,36 @@
+2021-07-23 Dean Jackson <[email protected]>
+
+ 3.5 MB system-wide footprint impact due to thread-locals in libANGLE
+ https://bugs.webkit.org/show_bug.cgi?id=228240
+ rdar://79504783
+
+ Reviewed by Ken Russell and Geoff Garen.
+
+ Apple's dyld has a bug where thread_local variables are dirtied on
+ process launch, causing a memory regression. Work around this
+ temporarily in ANGLE by using pthread thread local storage.
+
+ I don't expect this to be upstreamed to ANGLE unless they
+ want it. If it isn't, this patch will have to be applied until
+ the dyld bug is fixed.
+
+ * src/libANGLE/Context.cpp: Implement some methods to get/set what was
+ the global variable gCurrentValidContext.
+ (gl::GetCurrentValidContextTLSIndex):
+ (gl::GetCurrentValidContextTLS):
+ (gl::SetCurrentValidContextTLS):
+ (gl::Context::setContextLost):
+ * src/libANGLE/Context.h:
+ * src/libGLESv2/global_state.cpp: Ditto, but for gCurrentThread.
+ (egl::GetCurrentThreadTLSIndex):
+ (egl::GetCurrentThreadTLS):
+ (egl::SetCurrentThreadTLS):
+ (egl::GetCurrentThread):
+ (egl::SetContextCurrent):
+ * src/libGLESv2/global_state.h:
+ (gl::GetGlobalContext):
+ (gl::GetValidGlobalContext):
+
2021-07-16 Kyle Piddington <[email protected]>
Build Default Metal library offline
Modified: trunk/Source/ThirdParty/ANGLE/src/libANGLE/Context.cpp (280348 => 280349)
--- trunk/Source/ThirdParty/ANGLE/src/libANGLE/Context.cpp 2021-07-27 18:55:14 UTC (rev 280348)
+++ trunk/Source/ThirdParty/ANGLE/src/libANGLE/Context.cpp 2021-07-27 21:36:17 UTC (rev 280349)
@@ -46,6 +46,11 @@
#include "libANGLE/renderer/Format.h"
#include "libANGLE/validationES.h"
+#if defined(ANGLE_PLATFORM_APPLE)
+#include "common/tls.h"
+#include <dispatch/dispatch.h>
+#endif
+
namespace gl
{
namespace
@@ -283,7 +288,40 @@
}
} // anonymous namespace
+#if defined(ANGLE_PLATFORM_APPLE)
+
+// NOTE: Due to a bug in Apple's dyld loader, `thread_local` will cause
+// excessive memory use. Temporarily avoid it by using pthread's thread
+// local storage instead.
+
+static TLSIndex GetCurrentValidContextTLSIndex()
+{
+ static TLSIndex CurrentValidContextIndex = TLS_INVALID_INDEX;
+ static dispatch_once_t once;
+ dispatch_once(&once, ^{
+ ASSERT(CurrentValidContextIndex == TLS_INVALID_INDEX);
+ CurrentValidContextIndex = CreateTLSIndex();
+ });
+ return CurrentValidContextIndex;
+}
+
+Context *GetCurrentValidContextTLS()
+{
+ TLSIndex CurrentValidContextIndex = GetCurrentValidContextTLSIndex();
+ ASSERT(CurrentValidContextIndex != TLS_INVALID_INDEX);
+ return static_cast<Context *>(GetTLSValue(CurrentValidContextIndex));
+}
+
+void SetCurrentValidContextTLS(Context *context)
+{
+ TLSIndex CurrentValidContextIndex = GetCurrentValidContextTLSIndex();
+ ASSERT(CurrentValidContextIndex != TLS_INVALID_INDEX);
+ SetTLSValue(CurrentValidContextIndex, context);
+}
+
+#else
thread_local Context *gCurrentValidContext = nullptr;
+#endif
Context::Context(egl::Display *display,
const egl::Config *config,
@@ -2567,7 +2605,11 @@
mSkipValidation = false;
// Make sure we update TLS.
+#if defined(ANGLE_PLATFORM_APPLE)
+ SetCurrentValidContextTLS(nullptr);
+#else
gCurrentValidContext = nullptr;
+#endif
}
GLenum Context::getGraphicsResetStatus()
@@ -9164,4 +9206,5 @@
(context->getState().getProgramExecutable() &&
context->getState().getProgramExecutable()->hasVertexAndFragmentShader()));
}
+
} // namespace gl
Modified: trunk/Source/ThirdParty/ANGLE/src/libANGLE/Context.h (280348 => 280349)
--- trunk/Source/ThirdParty/ANGLE/src/libANGLE/Context.h 2021-07-27 18:55:14 UTC (rev 280348)
+++ trunk/Source/ThirdParty/ANGLE/src/libANGLE/Context.h 2021-07-27 21:36:17 UTC (rev 280349)
@@ -804,7 +804,12 @@
};
// Thread-local current valid context bound to the thread.
+#if defined(ANGLE_PLATFORM_APPLE)
+extern Context *GetCurrentValidContextTLS();
+extern void SetCurrentValidContextTLS(Context *context);
+#else
extern thread_local Context *gCurrentValidContext;
+#endif
} // namespace gl
Modified: trunk/Source/ThirdParty/ANGLE/src/libGLESv2/global_state.cpp (280348 => 280349)
--- trunk/Source/ThirdParty/ANGLE/src/libGLESv2/global_state.cpp 2021-07-27 18:55:14 UTC (rev 280348)
+++ trunk/Source/ThirdParty/ANGLE/src/libGLESv2/global_state.cpp 2021-07-27 21:36:17 UTC (rev 280349)
@@ -16,6 +16,10 @@
#include <atomic>
+#if defined(ANGLE_PLATFORM_APPLE)
+#include <dispatch/dispatch.h>
+#endif
+
namespace egl
{
namespace
@@ -38,13 +42,23 @@
Thread *AllocateCurrentThread()
{
- gCurrentThread = new Thread();
+ Thread *thread = new Thread();
+#if defined(ANGLE_PLATFORM_APPLE)
+ SetCurrentThreadTLS(thread);
+#else
+ gCurrentThread = thread;
+#endif
// Initialize fast TLS slot
SetContextToAndroidOpenGLTLSSlot(nullptr);
+
+#if defined(ANGLE_PLATFORM_APPLE)
+ gl::SetCurrentValidContextTLS(nullptr);
+#else
gl::gCurrentValidContext = nullptr;
+#endif
- return gCurrentThread;
+ return thread;
}
void AllocateDebug()
@@ -71,7 +85,39 @@
} // anonymous namespace
+#if defined(ANGLE_PLATFORM_APPLE)
+
+// NOTE: Due to a bug in Apple's dyld loader, `thread_local` will cause
+// excessive memory use. Temporarily avoid it by using pthread's thread
+// local storage instead.
+
+static TLSIndex GetCurrentThreadTLSIndex()
+{
+ static TLSIndex CurrentThreadIndex = TLS_INVALID_INDEX;
+ static dispatch_once_t once;
+ dispatch_once(&once, ^{
+ ASSERT(CurrentThreadIndex == TLS_INVALID_INDEX);
+ CurrentThreadIndex = CreateTLSIndex();
+ });
+ return CurrentThreadIndex;
+}
+
+Thread *GetCurrentThreadTLS()
+{
+ TLSIndex CurrentThreadIndex = GetCurrentThreadTLSIndex();
+ ASSERT(CurrentThreadIndex != TLS_INVALID_INDEX);
+ return static_cast<Thread *>(GetTLSValue(CurrentThreadIndex));
+}
+
+void SetCurrentThreadTLS(Thread *thread)
+{
+ TLSIndex CurrentThreadIndex = GetCurrentThreadTLSIndex();
+ ASSERT(CurrentThreadIndex != TLS_INVALID_INDEX);
+ SetTLSValue(CurrentThreadIndex, thread);
+}
+#else
thread_local Thread *gCurrentThread = nullptr;
+#endif
angle::GlobalMutex &GetGlobalMutex()
{
@@ -81,7 +127,11 @@
Thread *GetCurrentThread()
{
+#if defined(ANGLE_PLATFORM_APPLE)
+ Thread *current = GetCurrentThreadTLS();
+#else
Thread *current = gCurrentThread;
+#endif
return (current ? current : AllocateCurrentThread());
}
@@ -93,10 +143,19 @@
void SetContextCurrent(Thread *thread, gl::Context *context)
{
- ASSERT(gCurrentThread);
- gCurrentThread->setCurrent(context);
+#if defined(ANGLE_PLATFORM_APPLE)
+ Thread *currentThread = GetCurrentThreadTLS();
+#else
+ Thread *currentThread = gCurrentThread;
+#endif
+ ASSERT(currentThread);
+ currentThread->setCurrent(context);
SetContextToAndroidOpenGLTLSSlot(context);
+#if defined(ANGLE_PLATFORM_APPLE)
+ gl::SetCurrentValidContextTLS(context);
+#else
gl::gCurrentValidContext = context;
+#endif
}
} // namespace egl
Modified: trunk/Source/ThirdParty/ANGLE/src/libGLESv2/global_state.h (280348 => 280349)
--- trunk/Source/ThirdParty/ANGLE/src/libGLESv2/global_state.h 2021-07-27 18:55:14 UTC (rev 280348)
+++ trunk/Source/ThirdParty/ANGLE/src/libGLESv2/global_state.h 2021-07-27 21:36:17 UTC (rev 280349)
@@ -14,6 +14,10 @@
#include "libANGLE/Thread.h"
#include "libANGLE/features.h"
+#if defined(ANGLE_PLATFORM_APPLE)
+#include "common/tls.h"
+#endif
+
#include <mutex>
namespace angle
@@ -89,7 +93,12 @@
class Debug;
class Thread;
+#if defined(ANGLE_PLATFORM_APPLE)
+extern Thread *GetCurrentThreadTLS();
+extern void SetCurrentThreadTLS(Thread *thread);
+#else
extern thread_local Thread *gCurrentThread;
+#endif
angle::GlobalMutex &GetGlobalMutex();
Thread *GetCurrentThread();
@@ -112,8 +121,13 @@
}
#endif
- ASSERT(egl::gCurrentThread);
- return egl::gCurrentThread->getContext();
+#if defined(ANGLE_PLATFORM_APPLE)
+ egl::Thread *currentThread = egl::GetCurrentThreadTLS();
+#else
+ egl::Thread *currentThread = egl::gCurrentThread;
+#endif
+ ASSERT(currentThread);
+ return currentThread->getContext();
}
ANGLE_INLINE Context *GetValidGlobalContext()
@@ -131,7 +145,11 @@
}
#endif
+#if defined(ANGLE_PLATFORM_APPLE)
+ return GetCurrentValidContextTLS();
+#else
return gCurrentValidContext;
+#endif
}
// Generate a context lost error on the context if it is non-null and lost.