diff options
Diffstat (limited to 'db/repl')
-rw-r--r-- | db/repl/connections.h | 16 | ||||
-rw-r--r-- | db/repl/rs_config.cpp | 23 | ||||
-rw-r--r-- | db/repl/rs_config.h | 11 | ||||
-rw-r--r-- | db/repl/rs_rollback.cpp | 18 | ||||
-rw-r--r-- | db/repl/rs_sync.cpp | 2 |
5 files changed, 54 insertions, 16 deletions
diff --git a/db/repl/connections.h b/db/repl/connections.h index 61c581b..3ada71c 100644 --- a/db/repl/connections.h +++ b/db/repl/connections.h @@ -72,7 +72,8 @@ namespace mongo { struct X { mongo::mutex z; DBClientConnection cc; - X() : z("X"), cc(/*reconnect*/ true, 0, /*timeout*/ 10.0) { + bool connected; + X() : z("X"), cc(/*reconnect*/ true, 0, /*timeout*/ 10.0), connected(false) { cc._logLevel = 2; } } *x; @@ -88,6 +89,7 @@ namespace mongo { log() << "couldn't connect to " << _hostport << ": " << err << rsLog; return false; } + x->connected = true; // if we cannot authenticate against a member, then either its key file // or our key file has to change. if our key file has to change, we'll @@ -113,11 +115,19 @@ namespace mongo { connLock.reset( new scoped_lock(x->z) ); } } - if( !first ) { - connLock.reset( new scoped_lock(x->z) ); + + // already locked connLock above + if (first) { + connect(); + return; + } + + connLock.reset( new scoped_lock(x->z) ); + if (x->connected) { return; } + // Keep trying to connect if we're not yet connected connect(); } diff --git a/db/repl/rs_config.cpp b/db/repl/rs_config.cpp index 13352b1..c451d46 100644 --- a/db/repl/rs_config.cpp +++ b/db/repl/rs_config.cpp @@ -296,6 +296,26 @@ namespace mongo { _ok = false; } + void ReplSetConfig::setMajority() { + int total = members.size(); + int nonArbiters = total; + int strictMajority = total/2+1; + + for (vector<MemberCfg>::iterator it = members.begin(); it < members.end(); it++) { + if ((*it).arbiterOnly) { + nonArbiters--; + } + } + + // majority should be all "normal" members if we have something like 4 + // arbiters & 3 normal members + _majority = (strictMajority > nonArbiters) ? nonArbiters : strictMajority; + } + + int ReplSetConfig::getMajority() const { + return _majority; + } + void ReplSetConfig::checkRsConfig() const { uassert(13132, "nonmatching repl set name in _id field; check --replSet command line", @@ -533,6 +553,9 @@ namespace mongo { try { getLastErrorDefaults = settings["getLastErrorDefaults"].Obj().copy(); } catch(...) { } } + + // figure out the majority for this config + setMajority(); } static inline void configAssert(bool expr) { diff --git a/db/repl/rs_config.h b/db/repl/rs_config.h index b22b61e..da6552a 100644 --- a/db/repl/rs_config.h +++ b/db/repl/rs_config.h @@ -135,9 +135,20 @@ namespace mongo { BSONObj asBson() const; + /** + * Getter and setter for _majority. This is almost always + * members.size()/2+1, but can be the number of non-arbiter members if + * there are more arbiters than non-arbiters (writing to 3 out of 7 + * servers is safe if 4 of the servers are arbiters). + */ + void setMajority(); + int getMajority() const; + bool _constructed; private: bool _ok; + int _majority; + void from(BSONObj); void clear(); diff --git a/db/repl/rs_rollback.cpp b/db/repl/rs_rollback.cpp index f012e65..97a910e 100644 --- a/db/repl/rs_rollback.cpp +++ b/db/repl/rs_rollback.cpp @@ -388,24 +388,18 @@ namespace mongo { for( set<string>::iterator i = h.collectionsToResync.begin(); i != h.collectionsToResync.end(); i++ ) { string ns = *i; sethbmsg(str::stream() << "rollback 4.1 coll resync " << ns); - Client::Context c(*i); - try { + + Client::Context c(ns); + { bob res; string errmsg; dropCollection(ns, errmsg, res); { dbtemprelease r; - bool ok = copyCollectionFromRemote(them->getServerAddress(), ns, bo(), errmsg, false, true, false); - if( !ok ) { - log() << "replSet rollback error resyncing collection " << ns << ' ' << errmsg << rsLog; - throw "rollback error resyncing rollection [1]"; - } + bool ok = copyCollectionFromRemote(them->getServerAddress(), ns, errmsg); + uassert(15909, str::stream() << "replSet rollback error resyncing collection " << ns << ' ' << errmsg, ok); } } - catch(...) { - log() << "replset rollback error resyncing collection " << ns << rsLog; - throw "rollback error resyncing rollection [2]"; - } } /* we did more reading from primary, so check it again for a rollback (which would mess us up), and @@ -423,7 +417,7 @@ namespace mongo { setMinValid(newMinValid); } } - catch(...) { + catch (DBException& e) { err = "can't get/set minvalid"; } if( h.rbid != getRBID(r.conn()) ) { diff --git a/db/repl/rs_sync.cpp b/db/repl/rs_sync.cpp index 8cd3e14..c86dbbb 100644 --- a/db/repl/rs_sync.cpp +++ b/db/repl/rs_sync.cpp @@ -161,7 +161,7 @@ namespace mongo { } catch (DBException& e) { // skip duplicate key exceptions - if( e.getCode() == 11000 || e.getCode() == 11001 ) { + if( e.getCode() == 11000 || e.getCode() == 11001 || e.getCode() == 12582) { continue; } |