diff options
author | Andrew Morrow <acm@mongodb.com> | 2015-06-18 15:02:54 -0400 |
---|---|---|
committer | Andrew Morrow <acm@mongodb.com> | 2015-06-19 22:51:28 -0400 |
commit | 1178eff1ddf60a7dac3a8cd71e2fdd278aa01b52 (patch) | |
tree | ee3096045eb4d2e4f69d57ef85c66b3be69e4302 /src/mongo/util | |
parent | 4b5fa5fc711e4cf94291665575fd1c742ad3e7c3 (diff) | |
download | mongo-1178eff1ddf60a7dac3a8cd71e2fdd278aa01b52.tar.gz |
SERVER-19041 Simplify SimpleMutex
Diffstat (limited to 'src/mongo/util')
-rw-r--r-- | src/mongo/util/SConscript | 2 | ||||
-rw-r--r-- | src/mongo/util/background.cpp | 2 | ||||
-rw-r--r-- | src/mongo/util/background_job_test.cpp | 4 | ||||
-rw-r--r-- | src/mongo/util/concurrency/mapsf.h | 8 | ||||
-rw-r--r-- | src/mongo/util/concurrency/mutex.h | 108 | ||||
-rw-r--r-- | src/mongo/util/concurrency/rwlock.h | 1 | ||||
-rw-r--r-- | src/mongo/util/concurrency/simplerwlock.h | 1 | ||||
-rw-r--r-- | src/mongo/util/concurrency/synchronization.h | 4 | ||||
-rw-r--r-- | src/mongo/util/net/message_port.cpp | 2 | ||||
-rw-r--r-- | src/mongo/util/net/ssl_manager.cpp | 6 | ||||
-rw-r--r-- | src/mongo/util/processinfo.h | 2 | ||||
-rw-r--r-- | src/mongo/util/stacktrace_windows.cpp | 4 | ||||
-rw-r--r-- | src/mongo/util/static_observer.cpp (renamed from src/mongo/util/concurrency/mutex.cpp) | 2 | ||||
-rw-r--r-- | src/mongo/util/static_observer.h | 45 | ||||
-rw-r--r-- | src/mongo/util/time_support.cpp | 10 |
15 files changed, 103 insertions, 98 deletions
diff --git a/src/mongo/util/SConscript b/src/mongo/util/SConscript index bc6e9b0d9bd..08f66f615b0 100644 --- a/src/mongo/util/SConscript +++ b/src/mongo/util/SConscript @@ -100,11 +100,11 @@ env.Library( "startup_test.cpp", "touch_pages.cpp", 'assert_util.cpp', - 'concurrency/mutex.cpp', 'exception_filter_win32.cpp', 'file.cpp', 'log.cpp', 'platform_init.cpp', + 'static_observer.cpp', 'system_tick_source.cpp', 'text.cpp', 'thread_safe_string.cpp', diff --git a/src/mongo/util/background.cpp b/src/mongo/util/background.cpp index a7ee913defe..52147e923aa 100644 --- a/src/mongo/util/background.cpp +++ b/src/mongo/util/background.cpp @@ -105,7 +105,7 @@ namespace mongo { // completed. In the former case, we assume no threads are present, so we do not need // to use the mutex. When present, the mutex protects 'runner' and 'runnerDestroyed' // below. - SimpleMutex* const runnerMutex = new SimpleMutex("PeriodicTaskRunner"); + SimpleMutex* const runnerMutex = new SimpleMutex; // A scoped lock like object that only locks/unlocks the mutex if it exists. class ConditionalScopedLock { diff --git a/src/mongo/util/background_job_test.cpp b/src/mongo/util/background_job_test.cpp index 8d3ca7cd356..c13ff444625 100644 --- a/src/mongo/util/background_job_test.cpp +++ b/src/mongo/util/background_job_test.cpp @@ -28,10 +28,10 @@ #include "mongo/platform/basic.h" #include "mongo/db/server_options.h" +#include "mongo/stdx/mutex.h" #include "mongo/stdx/thread.h" #include "mongo/unittest/unittest.h" #include "mongo/util/background.h" -#include "mongo/util/concurrency/mutex.h" #include "mongo/util/concurrency/synchronization.h" #include "mongo/util/time_support.h" @@ -39,7 +39,7 @@ namespace { using mongo::BackgroundJob; using mongo::MsgAssertionException; - using mongo::mutex; + using mongo::stdx::mutex; using mongo::Notification; namespace stdx = mongo::stdx; diff --git a/src/mongo/util/concurrency/mapsf.h b/src/mongo/util/concurrency/mapsf.h index 27e9272f9e7..6aa6617e229 100644 --- a/src/mongo/util/concurrency/mapsf.h +++ b/src/mongo/util/concurrency/mapsf.h @@ -65,16 +65,16 @@ namespace mongo { mapsf() : m("mapsf") { } void swap(M& rhs) { - SimpleMutex::scoped_lock lk(m); + stdx::lock_guard<SimpleMutex> lk(m); val.swap(rhs); } bool empty() { - SimpleMutex::scoped_lock lk(m); + stdx::lock_guard<SimpleMutex> lk(m); return val.empty(); } // safe as we pass by value: mapped_type get(key_type k) { - SimpleMutex::scoped_lock lk(m); + stdx::lock_guard<SimpleMutex> lk(m); const_iterator i = val.find(k); if( i == val.end() ) return mapped_type(); @@ -83,7 +83,7 @@ namespace mongo { // think about deadlocks when using ref. the other methods // above will always be safe as they are "leaf" operations. struct ref { - SimpleMutex::scoped_lock lk; + stdx::lock_guard<SimpleMutex> lk; public: M &r; ref(mapsf &m) : lk(m.m), r(m.val) { } diff --git a/src/mongo/util/concurrency/mutex.h b/src/mongo/util/concurrency/mutex.h index 1d676384311..1e21f81f392 100644 --- a/src/mongo/util/concurrency/mutex.h +++ b/src/mongo/util/concurrency/mutex.h @@ -33,111 +33,69 @@ #include "mongo/platform/windows_basic.h" #endif -#include "mongo/stdx/mutex.h" #include "mongo/util/assert_util.h" -#include "mongo/util/concurrency/threadlocal.h" +#include "mongo/util/static_observer.h" namespace mongo { - // If you create a local static instance of this class, that instance will be destroyed - // before all global static objects are destroyed, so _destroyingStatics will be set - // to true before the global static variables are destroyed. - class StaticObserver { - MONGO_DISALLOW_COPYING(StaticObserver); - public: - static bool _destroyingStatics; - StaticObserver() = default; - ~StaticObserver() { _destroyingStatics = true; } - }; - - using mutex = stdx::mutex; - - /** The concept with SimpleMutex is that it is a basic lock/unlock with no - special functionality (such as try and try timeout). Thus it can be - implemented using OS-specific facilities in all environments (if desired). - On Windows, the implementation below is faster than boost mutex. + /** The concept with SimpleMutex is that it is a basic lock/unlock + * with no special functionality (such as try and try + * timeout). Thus it can be implemented using OS-specific + * facilities in all environments (if desired). On Windows, + * the implementation below is faster than boost mutex. */ #if defined(_WIN32) + class SimpleMutex { MONGO_DISALLOW_COPYING(SimpleMutex); public: - SimpleMutex( StringData ) { InitializeCriticalSection( &_cs ); } + SimpleMutex() { + InitializeCriticalSection( &_cs ); + } + ~SimpleMutex() { if ( ! StaticObserver::_destroyingStatics ) { DeleteCriticalSection(&_cs); } } - void dassertLocked() const { } - void lock() { EnterCriticalSection( &_cs ); } - void unlock() { LeaveCriticalSection( &_cs ); } - class scoped_lock { - SimpleMutex& _m; - public: - scoped_lock( SimpleMutex &m ) : _m(m) { _m.lock(); } - ~scoped_lock() { _m.unlock(); } - const SimpleMutex& m() const { return _m; } - }; + + void lock() { + EnterCriticalSection( &_cs ); + } + void unlock() { + LeaveCriticalSection( &_cs ); + } private: CRITICAL_SECTION _cs; }; + #else + class SimpleMutex { MONGO_DISALLOW_COPYING(SimpleMutex); public: - void dassertLocked() const { } - SimpleMutex(StringData name) { verify( pthread_mutex_init(&_lock,0) == 0 ); } - ~SimpleMutex(){ + SimpleMutex() { + verify( pthread_mutex_init(&_lock,0) == 0 ); + } + + ~SimpleMutex() { if ( ! StaticObserver::_destroyingStatics ) { verify( pthread_mutex_destroy(&_lock) == 0 ); } } - void lock() { verify( pthread_mutex_lock(&_lock) == 0 ); } - void unlock() { verify( pthread_mutex_unlock(&_lock) == 0 ); } - public: - class scoped_lock { - MONGO_DISALLOW_COPYING(scoped_lock); - SimpleMutex& _m; - public: - scoped_lock( SimpleMutex &m ) : _m(m) { _m.lock(); } - ~scoped_lock() { _m.unlock(); } - const SimpleMutex& m() const { return _m; } - }; + void lock() { + verify( pthread_mutex_lock(&_lock) == 0 ); + } + + void unlock() { + verify( pthread_mutex_unlock(&_lock) == 0 ); + } private: pthread_mutex_t _lock; }; #endif - /** This can be used instead of boost recursive mutex. The advantage is the debug checks - * and ability to assertLocked(). This has not yet been tested for speed vs. the boost one. - */ - class RecursiveMutex { - MONGO_DISALLOW_COPYING(RecursiveMutex); - public: - RecursiveMutex(StringData name) : m(name) { } - bool isLocked() const { return n.get() > 0; } - class scoped_lock { - MONGO_DISALLOW_COPYING(scoped_lock); - - RecursiveMutex& rm; - int& nLocksByMe; - public: - scoped_lock( RecursiveMutex &m ) : rm(m), nLocksByMe(rm.n.getRef()) { - if( nLocksByMe++ == 0 ) - rm.m.lock(); - } - ~scoped_lock() { - verify( nLocksByMe > 0 ); - if( --nLocksByMe == 0 ) { - rm.m.unlock(); - } - } - }; - private: - SimpleMutex m; - ThreadLocalValue<int> n; - }; - -} +} // namespace mongo diff --git a/src/mongo/util/concurrency/rwlock.h b/src/mongo/util/concurrency/rwlock.h index bb9426a68f3..22373efd421 100644 --- a/src/mongo/util/concurrency/rwlock.h +++ b/src/mongo/util/concurrency/rwlock.h @@ -33,6 +33,7 @@ #include "mongo/util/concurrency/mutex.h" #include "mongo/util/concurrency/rwlockimpl.h" #include "mongo/util/concurrency/simplerwlock.h" +#include "mongo/util/concurrency/threadlocal.h" #include "mongo/util/debug_util.h" #include "mongo/util/time_support.h" diff --git a/src/mongo/util/concurrency/simplerwlock.h b/src/mongo/util/concurrency/simplerwlock.h index ceee67f50b2..8a8b3171ec9 100644 --- a/src/mongo/util/concurrency/simplerwlock.h +++ b/src/mongo/util/concurrency/simplerwlock.h @@ -31,6 +31,7 @@ #include "mongo/base/string_data.h" #include "mongo/config.h" #include "mongo/platform/atomic_word.h" +#include "mongo/util/concurrency/threadlocal.h" namespace mongo { diff --git a/src/mongo/util/concurrency/synchronization.h b/src/mongo/util/concurrency/synchronization.h index e8c604ad244..b89320bb8c6 100644 --- a/src/mongo/util/concurrency/synchronization.h +++ b/src/mongo/util/concurrency/synchronization.h @@ -78,7 +78,7 @@ namespace mongo { void notifyOne(); private: - mongo::mutex _mutex; // protects state below + stdx::mutex _mutex; // protects state below unsigned long long lookFor; unsigned long long cur; stdx::condition_variable _condition; // cond over _notified being true @@ -111,7 +111,7 @@ namespace mongo { unsigned nWaiting() const { return _nWaiting; } private: - mongo::mutex _mutex; + stdx::mutex _mutex; stdx::condition_variable _condition; When _lastDone; When _lastReturned; diff --git a/src/mongo/util/net/message_port.cpp b/src/mongo/util/net/message_port.cpp index f35a4883d0d..b4e062456c9 100644 --- a/src/mongo/util/net/message_port.cpp +++ b/src/mongo/util/net/message_port.cpp @@ -113,7 +113,7 @@ namespace mongo { class Ports { std::set<MessagingPort*> ports; - mongo::mutex m; + stdx::mutex m; public: Ports() : ports() {} void closeAll(unsigned skip_mask) { diff --git a/src/mongo/util/net/ssl_manager.cpp b/src/mongo/util/net/ssl_manager.cpp index b2f1df6aa1f..be5165b97b8 100644 --- a/src/mongo/util/net/ssl_manager.cpp +++ b/src/mongo/util/net/ssl_manager.cpp @@ -153,7 +153,7 @@ namespace mongo { //////////////////////////////////////////////////////////////// - SimpleMutex sslManagerMtx("SSL Manager"); + SimpleMutex sslManagerMtx; SSLManagerInterface* theSSLManager = NULL; static const int BUFFER_SIZE = 8*1024; static const int DATE_LEN = 128; @@ -323,7 +323,7 @@ namespace mongo { MONGO_INITIALIZER_WITH_PREREQUISITES(SSLManager, ("SetupOpenSSL")) (InitializerContext*) { - SimpleMutex::scoped_lock lck(sslManagerMtx); + stdx::lock_guard<SimpleMutex> lck(sslManagerMtx); if (sslGlobalParams.sslMode.load() != SSLParams::SSLMode_disabled) { theSSLManager = new SSLManager(sslGlobalParams, isSSLServer); } @@ -336,7 +336,7 @@ namespace mongo { } SSLManagerInterface* getSSLManager() { - SimpleMutex::scoped_lock lck(sslManagerMtx); + stdx::lock_guard<SimpleMutex> lck(sslManagerMtx); if (theSSLManager) return theSSLManager; return NULL; diff --git a/src/mongo/util/processinfo.h b/src/mongo/util/processinfo.h index 367d4c5f0e4..ad0a3fbb6a7 100644 --- a/src/mongo/util/processinfo.h +++ b/src/mongo/util/processinfo.h @@ -199,7 +199,7 @@ namespace mongo { }; ProcessId _pid; - static mongo::mutex _sysInfoLock; + static stdx::mutex _sysInfoLock; static bool checkNumaEnabled(); diff --git a/src/mongo/util/stacktrace_windows.cpp b/src/mongo/util/stacktrace_windows.cpp index b11ae1d630e..e99f0c4d87a 100644 --- a/src/mongo/util/stacktrace_windows.cpp +++ b/src/mongo/util/stacktrace_windows.cpp @@ -174,7 +174,7 @@ namespace mongo { printWindowsStackTrace( context, os ); } - static SimpleMutex _stackTraceMutex( "stackTraceMutex" ); + static SimpleMutex _stackTraceMutex; /** * Print stack trace (using a specified stack context) to "os" @@ -183,7 +183,7 @@ namespace mongo { * @param os ostream& to receive printed stack backtrace */ void printWindowsStackTrace( CONTEXT& context, std::ostream& os ) { - SimpleMutex::scoped_lock lk(_stackTraceMutex); + stdx::lock_guard<SimpleMutex> lk(_stackTraceMutex); HANDLE process = GetCurrentProcess(); BOOL ret = SymInitialize(process, getSymbolSearchPath(process), TRUE); if ( ret == FALSE ) { diff --git a/src/mongo/util/concurrency/mutex.cpp b/src/mongo/util/static_observer.cpp index e881ac2272c..7ce63da0e42 100644 --- a/src/mongo/util/concurrency/mutex.cpp +++ b/src/mongo/util/static_observer.cpp @@ -28,7 +28,7 @@ #include "mongo/platform/basic.h" -#include "mongo/util/concurrency/mutex.h" +#include "mongo/util/static_observer.h" namespace mongo { diff --git a/src/mongo/util/static_observer.h b/src/mongo/util/static_observer.h new file mode 100644 index 00000000000..eec10d52437 --- /dev/null +++ b/src/mongo/util/static_observer.h @@ -0,0 +1,45 @@ +/* Copyright 2015 MongoDB Inc. + * + * This program is free software: you can redistribute it and/or modify + * it under the terms of the GNU Affero General Public License, version 3, + * as published by the Free Software Foundation. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU Affero General Public License for more details. + * + * You should have received a copy of the GNU Affero General Public License + * along with this program. If not, see <http://www.gnu.org/licenses/>. + * + * As a special exception, the copyright holders give permission to link the + * code of portions of this program with the OpenSSL library under certain + * conditions as described in each individual source file and distribute + * linked combinations including the program with the OpenSSL library. You + * must comply with the GNU Affero General Public License in all respects + * for all of the code used other than as permitted herein. If you modify + * file(s) with this exception, you may extend this exception to your + * version of the file(s), but you are not obligated to do so. If you do not + * wish to do so, delete this exception statement from your version. If you + * delete this exception statement from all source files in the program, + * then also delete it in the license file. + */ + +#pragma once + +#include "mongo/base/disallow_copying.h" + +namespace mongo { + + // If you create a local static instance of this class, that instance will be destroyed + // before all global static objects are destroyed, so _destroyingStatics will be set + // to true before the global static variables are destroyed. + class StaticObserver { + MONGO_DISALLOW_COPYING(StaticObserver); + public: + static bool _destroyingStatics; + StaticObserver() = default; + ~StaticObserver() { _destroyingStatics = true; } + }; + +} // namespace mongo diff --git a/src/mongo/util/time_support.cpp b/src/mongo/util/time_support.cpp index e72158f7e0c..7d44ce64972 100644 --- a/src/mongo/util/time_support.cpp +++ b/src/mongo/util/time_support.cpp @@ -924,8 +924,8 @@ namespace { static unsigned long long baseFiletime = 0; static unsigned long long basePerfCounter = 0; static unsigned long long resyncInterval = 0; - static SimpleMutex _curTimeMicros64ReadMutex("curTimeMicros64Read"); - static SimpleMutex _curTimeMicros64ResyncMutex("curTimeMicros64Resync"); + static SimpleMutex _curTimeMicros64ReadMutex; + static SimpleMutex _curTimeMicros64ResyncMutex; typedef WINBASEAPI VOID (WINAPI *pGetSystemTimePreciseAsFileTime) (_Out_ LPFILETIME lpSystemTimeAsFileTime); @@ -943,7 +943,7 @@ namespace { } static unsigned long long resyncTime() { - SimpleMutex::scoped_lock lkResync(_curTimeMicros64ResyncMutex); + stdx::lock_guard<SimpleMutex> lkResync(_curTimeMicros64ResyncMutex); unsigned long long ftOld; unsigned long long ftNew; ftOld = ftNew = getFiletime(); @@ -955,7 +955,7 @@ namespace { // Make sure that we use consistent values for baseFiletime and basePerfCounter. // - SimpleMutex::scoped_lock lkRead(_curTimeMicros64ReadMutex); + stdx::lock_guard<SimpleMutex> lkRead(_curTimeMicros64ReadMutex); baseFiletime = ftNew; basePerfCounter = newPerfCounter; resyncInterval = 60 * SystemTickSource::get()->getTicksPerSecond(); @@ -986,7 +986,7 @@ namespace { // Make sure that we use consistent values for baseFiletime and basePerfCounter. // - SimpleMutex::scoped_lock lkRead(_curTimeMicros64ReadMutex); + stdx::lock_guard<SimpleMutex> lkRead(_curTimeMicros64ReadMutex); // Compute the current time in FILETIME format by adding our base FILETIME and an offset // from that time based on QueryPerformanceCounter. The math is (logically) to compute the |