|
35 | 35 | # include "itkOpenCLSetup.h" |
36 | 36 | #endif |
37 | 37 |
|
| 38 | +#include <mutex> |
| 39 | + |
| 40 | + |
38 | 41 | namespace |
39 | 42 | { |
40 | 43 | /** |
@@ -139,6 +142,47 @@ xoutManager::xoutManager(const std::string & logFileName, const bool setupLoggin |
139 | 142 | } |
140 | 143 | } |
141 | 144 |
|
| 145 | + |
| 146 | +std::shared_ptr<const xoutManager> |
| 147 | +xoutManager::GetSharedManager(const std::string & logFileName, const bool setupLogging, const bool setupCout) |
| 148 | +{ |
| 149 | + const auto makeManagerPtrPair = [](const std::string & logFileName, const bool setupLogging, const bool setupCout) { |
| 150 | + std::shared_ptr<const xoutManager> sharedPtr(new xoutManager(logFileName, setupLogging, setupCout)); |
| 151 | + std::weak_ptr<const xoutManager> weakPtr(sharedPtr); |
| 152 | + return std::make_pair(sharedPtr, weakPtr); |
| 153 | + }; |
| 154 | + |
| 155 | + // Note that the initialization of this static variable is thread-safe, |
| 156 | + // as supported by C++11 "magic statics". |
| 157 | + static auto managerPtrPair = makeManagerPtrPair(logFileName, setupLogging, setupCout); |
| 158 | + |
| 159 | + const struct ResetGuard |
| 160 | + { |
| 161 | + std::shared_ptr<const xoutManager> & sharedPtr; |
| 162 | + ~ResetGuard() { sharedPtr.reset(); } |
| 163 | + } resetGuard{ managerPtrPair.first }; |
| 164 | + |
| 165 | + const auto lockedSharedPtr = managerPtrPair.second.lock(); |
| 166 | + |
| 167 | + if (lockedSharedPtr == nullptr) |
| 168 | + { |
| 169 | + // Apply the "double-checked locking" design pattern. |
| 170 | + static std::mutex managerMutex; |
| 171 | + const std::lock_guard<std::mutex> lock(managerMutex); |
| 172 | + |
| 173 | + const auto doubleCheckedLockedSharedPtr = managerPtrPair.second.lock(); |
| 174 | + |
| 175 | + if (doubleCheckedLockedSharedPtr == nullptr) |
| 176 | + { |
| 177 | + managerPtrPair = makeManagerPtrPair(logFileName, setupLogging, setupCout); |
| 178 | + return managerPtrPair.second.lock(); |
| 179 | + } |
| 180 | + return doubleCheckedLockedSharedPtr; |
| 181 | + } |
| 182 | + return lockedSharedPtr; |
| 183 | +} |
| 184 | + |
| 185 | + |
142 | 186 | xoutManager::Guard::~Guard() |
143 | 187 | { |
144 | 188 | g_data = {}; |
|
0 commit comments