diff --git a/lib/ClientImpl.cc b/lib/ClientImpl.cc index 043d6d42..acac66c2 100644 --- a/lib/ClientImpl.cc +++ b/lib/ClientImpl.cc @@ -78,11 +78,12 @@ void invokeLegacyCallback(const std::function& callback, static const char hexDigits[] = {'0', '1', '2', '3', '4', '5', '6', '7', '8', '9', 'a', 'b', 'c', 'd', 'e', 'f'}; -static std::uniform_int_distribution<> hexDigitsDist(0, sizeof(hexDigits) - 1); -static std::mt19937 randomEngine = - std::mt19937(std::chrono::high_resolution_clock::now().time_since_epoch().count()); std::string generateRandomName() { + // Called concurrently by all the clients of the process, so the generator state must not be shared. + thread_local std::uniform_int_distribution<> hexDigitsDist(0, sizeof(hexDigits) - 1); + thread_local std::mt19937 randomEngine(std::random_device{}()); + const int randomNameLength = 10; std::string randomName; diff --git a/lib/ConnectionPool.h b/lib/ConnectionPool.h index 201c1d01..8acfa329 100644 --- a/lib/ConnectionPool.h +++ b/lib/ConnectionPool.h @@ -96,7 +96,11 @@ class PULSAR_PUBLIC ConnectionPool { return getConnectionAsync(address, address); } - size_t generateRandomIndex() { return randomDistribution_(randomEngine_); } + size_t generateRandomIndex() { + // Handlers are created concurrently from the caller and executor threads. + std::lock_guard lock(randomMutex_); + return randomDistribution_(randomEngine_); + } private: const AtomicSharedPtr& serviceInfo_; @@ -110,6 +114,7 @@ class PULSAR_PUBLIC ConnectionPool { std::uniform_int_distribution<> randomDistribution_; std::mt19937 randomEngine_; + std::mutex randomMutex_; auto releaseConnections() { decltype(pool_) pool;