mirror of
https://github.com/mongodb/mongo.git
synced 2024-12-01 09:32:32 +01:00
switch to pthread_rw lock on support platforms SERVER-824
This commit is contained in:
parent
c91e3ba456
commit
e8583f2a6b
@ -29,23 +29,12 @@
|
||||
|
||||
#pragma once
|
||||
|
||||
#if BOOST_VERSION >= 103500
|
||||
#include <boost/thread/shared_mutex.hpp>
|
||||
#undef assert
|
||||
#define assert xassert
|
||||
#define HAVE_READLOCK
|
||||
#else
|
||||
#warning built with boost version 1.34 or older - limited concurrency
|
||||
#endif
|
||||
#include "../util/locks.h"
|
||||
|
||||
namespace mongo {
|
||||
|
||||
inline bool readLockSupported(){
|
||||
#ifdef HAVE_READLOCK
|
||||
return true;
|
||||
#else
|
||||
return false;
|
||||
#endif
|
||||
}
|
||||
|
||||
string sayClientState();
|
||||
@ -87,11 +76,9 @@ namespace mongo {
|
||||
}
|
||||
};
|
||||
|
||||
#ifdef HAVE_READLOCK
|
||||
//#if 0
|
||||
class MongoMutex {
|
||||
MutexInfo _minfo;
|
||||
boost::shared_mutex _m;
|
||||
RWLock _m;
|
||||
ThreadLocalValue<int> _state;
|
||||
|
||||
/* we use a separate TLS value for releasedEarly - that is ok as
|
||||
@ -188,10 +175,12 @@ namespace mongo {
|
||||
lock_shared();
|
||||
return true;
|
||||
}
|
||||
|
||||
/*
|
||||
boost::system_time until = get_system_time();
|
||||
until += boost::posix_time::milliseconds(2);
|
||||
bool got = _m.timed_lock_shared( until );
|
||||
*/
|
||||
bool got = _m.lock_shared_try( millis );
|
||||
if ( got )
|
||||
_state.set(-1);
|
||||
return got;
|
||||
@ -216,63 +205,6 @@ namespace mongo {
|
||||
|
||||
MutexInfo& info() { return _minfo; }
|
||||
};
|
||||
#else
|
||||
/* this will be for old versions of boost */
|
||||
class MongoMutex {
|
||||
MutexInfo _minfo;
|
||||
boost::recursive_mutex m;
|
||||
ThreadLocalValue<bool> _releasedEarly;
|
||||
public:
|
||||
MongoMutex() { }
|
||||
void lock() {
|
||||
boost::detail::thread::lock_ops<boost::recursive_mutex>::lock(m);
|
||||
_minfo.entered();
|
||||
}
|
||||
|
||||
void releaseEarly() {
|
||||
assertWriteLocked(); // aso must not be recursive, although we don't verify that in the old boost version
|
||||
assert( !_releasedEarly.get() );
|
||||
_releasedEarly.set(true);
|
||||
_unlock();
|
||||
}
|
||||
|
||||
void _unlock() {
|
||||
_minfo.leaving();
|
||||
boost::detail::thread::lock_ops<boost::recursive_mutex>::unlock(m);
|
||||
}
|
||||
void unlock() {
|
||||
if( _releasedEarly.get() ) {
|
||||
_releasedEarly.set(false);
|
||||
return;
|
||||
}
|
||||
_unlock();
|
||||
}
|
||||
|
||||
void lock_shared() { lock(); }
|
||||
bool lock_shared_try( int millis ) {
|
||||
while ( millis-- ){
|
||||
if ( getState() ){
|
||||
sleepmillis(1);
|
||||
continue;
|
||||
}
|
||||
lock_shared();
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
void unlock_shared() { unlock(); }
|
||||
MutexInfo& info() { return _minfo; }
|
||||
void assertWriteLocked() {
|
||||
assert( info().isLocked() );
|
||||
}
|
||||
void assertAtLeastReadLocked() {
|
||||
assert( info().isLocked() );
|
||||
}
|
||||
bool atLeastReadLocked() { return info().isLocked(); }
|
||||
int getState(){ return info().isLocked() ? 1 : 0; }
|
||||
};
|
||||
#endif
|
||||
|
||||
extern MongoMutex &dbMutex;
|
||||
|
||||
|
120
util/locks.h
Normal file
120
util/locks.h
Normal file
@ -0,0 +1,120 @@
|
||||
// locks.h
|
||||
|
||||
/*
|
||||
* Copyright (C) 2010 10gen 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/>.
|
||||
*/
|
||||
|
||||
//#include "../stdafx.h"
|
||||
|
||||
#if defined(_WIN32)
|
||||
|
||||
#if BOOST_VERSION >= 103500
|
||||
#include <boost/thread/shared_mutex.hpp>
|
||||
#undef assert
|
||||
#define assert xassert
|
||||
#else
|
||||
#error need boost >= 1.35 for windows
|
||||
#endif
|
||||
|
||||
#define BOOST_RWLOCK
|
||||
|
||||
#else
|
||||
|
||||
#include <pthread.h>
|
||||
|
||||
#endif
|
||||
|
||||
namespace mongo {
|
||||
|
||||
#ifdef BOOST_RWLOCK
|
||||
class RWLock {
|
||||
boost::shared_mutex _m;
|
||||
|
||||
public:
|
||||
void lock(){
|
||||
_m.lock();
|
||||
}
|
||||
void unlock(){
|
||||
_m.unlock();
|
||||
}
|
||||
|
||||
void lock_shared(){
|
||||
_m.lock_shared();
|
||||
}
|
||||
|
||||
void unlock_shared(){
|
||||
_m.unlock_shared();
|
||||
}
|
||||
|
||||
bool lock_shared_try( int millis ){
|
||||
boost::system_time until = get_system_time();
|
||||
until += boost::posix_time::milliseconds(2);
|
||||
return _m.timed_lock_shared( until );
|
||||
}
|
||||
};
|
||||
#else
|
||||
class RWLock {
|
||||
pthread_rwlock_t _lock;
|
||||
|
||||
inline void check( int x ){
|
||||
if( x == 0 )
|
||||
return;
|
||||
log() << "pthread rwlock failed: " << x << endl;
|
||||
assert( x == 0 );
|
||||
}
|
||||
|
||||
public:
|
||||
RWLock(){
|
||||
check( pthread_rwlock_init( &_lock , 0 ) );
|
||||
}
|
||||
|
||||
~RWLock(){
|
||||
check( pthread_rwlock_destroy( &_lock ) );
|
||||
}
|
||||
|
||||
void lock(){
|
||||
check( pthread_rwlock_wrlock( &_lock ) );
|
||||
}
|
||||
void unlock(){
|
||||
check( pthread_rwlock_unlock( &_lock ) );
|
||||
}
|
||||
|
||||
void lock_shared(){
|
||||
check( pthread_rwlock_rdlock( &_lock ) );
|
||||
}
|
||||
|
||||
void unlock_shared(){
|
||||
check( pthread_rwlock_unlock( &_lock ) );
|
||||
}
|
||||
|
||||
bool lock_shared_try( int millis ){
|
||||
while ( millis-- ){
|
||||
int x = pthread_rwlock_tryrdlock( &_lock );
|
||||
if ( x == 0 )
|
||||
return true;
|
||||
|
||||
if ( x == EBUSY ){
|
||||
sleepmillis(1);
|
||||
continue;
|
||||
}
|
||||
check(x);
|
||||
}
|
||||
return false;
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
#endif
|
||||
}
|
Loading…
Reference in New Issue
Block a user