diff --git a/src/gfxstream/guest/connection-manager/GfxStreamConnectionManager.cpp b/src/gfxstream/guest/connection-manager/GfxStreamConnectionManager.cpp index 8139853e923..c341318db30 100644 --- a/src/gfxstream/guest/connection-manager/GfxStreamConnectionManager.cpp +++ b/src/gfxstream/guest/connection-manager/GfxStreamConnectionManager.cpp @@ -12,15 +12,60 @@ #include "VirtGpu.h" #include "VirtioGpuAddressSpaceStream.h" #include "VirtioGpuPipeStream.h" +#include "c11/threads.h" #include "util/log.h" #define STREAM_BUFFER_SIZE (4 * 1024 * 1024) -struct ThreadInfo { - std::unique_ptr mgr; -}; +static tss_t gfxstream_connection_manager_tls_key; +static bool gfxstream_connection_manager_tls_key_valid; -static thread_local ThreadInfo sThreadInfo; +static void gfxstream_connection_manager_tls_free(void* tls) { + if (tls) { + delete ((GfxStreamConnectionManager*)tls); + } +} + +static void gfxstream_connection_manager_tls_key_create_once(void) { + gfxstream_connection_manager_tls_key_valid = + tss_create(&gfxstream_connection_manager_tls_key, gfxstream_connection_manager_tls_free) == + thrd_success; + if (!gfxstream_connection_manager_tls_key_valid) { + mesa_loge("WARNING: failed to create gfxstream_connection_manager_tls_key"); + } +} + +GfxStreamConnectionManager* GfxStreamConnectionManager::getThreadLocalInstance( + GfxStreamTransportType type, VirtGpuCapset capset) { + static once_flag once = ONCE_FLAG_INIT; + call_once(&once, gfxstream_connection_manager_tls_key_create_once); + if (unlikely(!gfxstream_connection_manager_tls_key_valid)) { + return nullptr; + } + + GfxStreamConnectionManager* tls = + (GfxStreamConnectionManager*)tss_get(gfxstream_connection_manager_tls_key); + if (likely(tls)) { + return tls; + } + + tls = new GfxStreamConnectionManager(type, capset); + if (!tls) { + return nullptr; + } + + if (!tls->initialize()) { + delete tls; + return nullptr; + } + + if (tss_set(gfxstream_connection_manager_tls_key, tls) != thrd_success) { + delete tls; + return nullptr; + } + + return tls; +} GfxStreamConnectionManager::GfxStreamConnectionManager(GfxStreamTransportType type, VirtGpuCapset capset) @@ -96,27 +141,6 @@ bool GfxStreamConnectionManager::initialize() { return true; } -GfxStreamConnectionManager* GfxStreamConnectionManager::getThreadLocalInstance( - GfxStreamTransportType type, VirtGpuCapset capset) { - if (sThreadInfo.mgr == nullptr) { - sThreadInfo.mgr = std::make_unique(type, capset); - if (!sThreadInfo.mgr->initialize()) { - sThreadInfo.mgr = nullptr; - return nullptr; - } - } - - return sThreadInfo.mgr.get(); -} - -void GfxStreamConnectionManager::threadLocalExit() { - if (sThreadInfo.mgr == nullptr) { - return; - } - - sThreadInfo.mgr.reset(); -} - int32_t GfxStreamConnectionManager::addConnection(GfxStreamConnectionType type, std::unique_ptr connection) { if (mConnections.find(type) != mConnections.end()) { diff --git a/src/gfxstream/guest/connection-manager/GfxStreamConnectionManager.h b/src/gfxstream/guest/connection-manager/GfxStreamConnectionManager.h index c6243419bbc..0ed114eaebe 100644 --- a/src/gfxstream/guest/connection-manager/GfxStreamConnectionManager.h +++ b/src/gfxstream/guest/connection-manager/GfxStreamConnectionManager.h @@ -29,12 +29,11 @@ enum GfxStreamTransportType { class GfxStreamConnectionManager { public: - GfxStreamConnectionManager(GfxStreamTransportType type, VirtGpuCapset capset); - ~GfxStreamConnectionManager(); - static GfxStreamConnectionManager* getThreadLocalInstance(GfxStreamTransportType type, VirtGpuCapset capset); - void threadLocalExit(); + + GfxStreamConnectionManager(GfxStreamTransportType type, VirtGpuCapset capset); + ~GfxStreamConnectionManager(); bool initialize(); int32_t addConnection(GfxStreamConnectionType type, diff --git a/src/gfxstream/guest/vulkan/gfxstream_vk_device.cpp b/src/gfxstream/guest/vulkan/gfxstream_vk_device.cpp index 596b155f21d..e63bc50c437 100644 --- a/src/gfxstream/guest/vulkan/gfxstream_vk_device.cpp +++ b/src/gfxstream/guest/vulkan/gfxstream_vk_device.cpp @@ -417,8 +417,6 @@ void gfxstream_vk_DestroyInstance(VkInstance _instance, const VkAllocationCallba // To make End2EndTests happy, since now the host connection is statically linked to // libvulkan_ranchu.so [separate HostConnections now]. #if defined(END2END_TESTS) - GfxStreamConnectionManager* mgr = getConnectionManager(); - mgr->threadLocalExit(); VirtGpuDevice::resetInstance(); gSeqno = 0; #endif