diff options
Diffstat (limited to 'src/mongo')
-rw-r--r-- | src/mongo/db/client.h | 2 | ||||
-rw-r--r-- | src/mongo/db/curop.cpp | 1 | ||||
-rw-r--r-- | src/mongo/db/d_concurrency.cpp | 58 | ||||
-rw-r--r-- | src/mongo/db/d_concurrency.h | 10 | ||||
-rw-r--r-- | src/mongo/util/concurrency/rwlockimpl.cpp | 4 | ||||
-rw-r--r-- | src/mongo/util/concurrency/simplerwlock.h | 3 |
6 files changed, 58 insertions, 20 deletions
diff --git a/src/mongo/db/client.h b/src/mongo/db/client.h index 7dc4376868d..d40d79436db 100644 --- a/src/mongo/db/client.h +++ b/src/mongo/db/client.h @@ -56,6 +56,8 @@ namespace mongo { class Client : public ClientBasic { static Client *syncThread; public: + LockState _ls; + // always be in clientsMutex when manipulating this. killop stuff uses these. static set<Client*>& clients; static mongo::mutex& clientsMutex; diff --git a/src/mongo/db/curop.cpp b/src/mongo/db/curop.cpp index 475b5c46ea8..22de0f47e84 100644 --- a/src/mongo/db/curop.cpp +++ b/src/mongo/db/curop.cpp @@ -150,6 +150,7 @@ namespace mongo { b.append( "threadId" , _client->_threadId ); if ( _client->_connectionId ) b.appendNumber( "connectionId" , _client->_connectionId ); + _client->_ls.reportState(b); } if ( ! _message.empty() ) { diff --git a/src/mongo/db/d_concurrency.cpp b/src/mongo/db/d_concurrency.cpp index db39c12f69f..b6a7385dbdf 100644 --- a/src/mongo/db/d_concurrency.cpp +++ b/src/mongo/db/d_concurrency.cpp @@ -87,8 +87,8 @@ namespace mongo { static void unlocking_w(); static void unlocking_W(); static QLock& q = *new QLock(); - TSP_DECLARE(LockState,ls); - TSP_DEFINE(LockState,ls); + //TSP_DECLARE(LockState,ls); + //TSP_DEFINE(LockState,ls); void runExclusively(void (*f)(void)) { q.runExclusively(f); @@ -122,20 +122,44 @@ namespace mongo { } inline LockState& lockState() { - LockState *p = ls.get(); - if( unlikely( p == 0 ) ) { - ls.reset(p = new LockState()); - } - return *p; - } - LockState::LockState() : recursive(0), - threadState(0), - nestableCount(0), - otherCount(0), - otherLock(NULL), - scopedLk(NULL) - { - whichNestable = Lock::notnestable; + return cc()._ls; + } + + static string kind(int n) { + if( n > 0 ) + return "W"; + if( n < 0 ) + return "R"; + return "?"; + } + /** Note: this is is called by the currentOp command, which is a different + thread. So be careful about thread safety here. For example reading + this->otherName would not be safe as-is! + */ + void LockState::reportState(BSONObjBuilder& res) { + BSONObjBuilder b; + if( threadState ) { + char buf[2]; + buf[0] = threadState; buf[1] = 0; + b.append("^", buf); + } + if( nestableCount ) { + string s = "?"; + if( whichNestable == Lock::local ) + s = "local"; + else if( whichNestable == Lock::admin ) + s = "admin"; + b.append(s, kind(nestableCount)); + } + if( otherCount ) { + SimpleRWLock *k = otherLock; + if( k ) { + b.append(k->name, kind(otherCount)); + } + } + BSONObj o = b.obj(); + if( !o.isEmpty() ) + res.append("locks", o); } void LockState::Dump() { @@ -604,7 +628,7 @@ namespace mongo { mapsf<string,SimpleRWLock*>::ref r(dblocks); SimpleRWLock*& lock = r[db]; if( lock == 0 ) - lock = new SimpleRWLock(); + lock = new SimpleRWLock(db.c_str()); ls.otherLock = lock; } fassert(16134,weLocked==0); diff --git a/src/mongo/db/d_concurrency.h b/src/mongo/db/d_concurrency.h index cb3002bd29b..520253e7502 100644 --- a/src/mongo/db/d_concurrency.h +++ b/src/mongo/db/d_concurrency.h @@ -199,6 +199,7 @@ namespace mongo { LockState(); void dump(); static void Dump(); + void reportState(BSONObjBuilder& b); unsigned recursive; // we allow recursively asking for a lock; we track that here @@ -216,4 +217,13 @@ namespace mongo { Lock::ScopedLock *scopedLk; // for the nonrecursive case. otherwise there would be many }; + inline LockState::LockState() : recursive(0), + threadState(0), + nestableCount(0), + otherCount(0), + otherLock(NULL), + scopedLk(NULL) + { + whichNestable = Lock::notnestable; + } } diff --git a/src/mongo/util/concurrency/rwlockimpl.cpp b/src/mongo/util/concurrency/rwlockimpl.cpp index f397c2a95e5..27f20b66e8c 100644 --- a/src/mongo/util/concurrency/rwlockimpl.cpp +++ b/src/mongo/util/concurrency/rwlockimpl.cpp @@ -23,7 +23,7 @@ using namespace std; namespace mongo { #if defined(_WIN32) - SimpleRWLock::SimpleRWLock(const char *p) { + SimpleRWLock::SimpleRWLock(const char *p) : name(p?p:"") { InitializeSRWLock(&_lock); } # if defined(_DEBUG) @@ -74,7 +74,7 @@ namespace mongo { } # endif #else - SimpleRWLock::SimpleRWLock(const char *p) { } + SimpleRWLock::SimpleRWLock(const char *p) : name(p?p:"") { } void SimpleRWLock::lock() { m.lock(); } void SimpleRWLock::unlock() { m.unlock(); } void SimpleRWLock::lock_shared() { m.lock_shared(); } diff --git a/src/mongo/util/concurrency/simplerwlock.h b/src/mongo/util/concurrency/simplerwlock.h index c2778539fce..03e7fab3795 100644 --- a/src/mongo/util/concurrency/simplerwlock.h +++ b/src/mongo/util/concurrency/simplerwlock.h @@ -18,7 +18,8 @@ namespace mongo { unsigned tid; #endif public: - SimpleRWLock(const char *p = 0); + const string name; + SimpleRWLock(const char *name = 0); void lock(); void unlock(); void lock_shared(); |