summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorMatt Diener <matt.diener@mongodb.com>2022-02-22 19:04:14 +0000
committerEvergreen Agent <no-reply@evergreen.mongodb.com>2022-02-22 19:31:31 +0000
commitc1ce0d4518d9122230c0d0cf373cb488f34af021 (patch)
tree2d01311cd64fa1ae0c896c7a57f8ea9976d135b1
parenta40b0d5ba8edc39568870e179cf9acc1a4df2863 (diff)
downloadmongo-c1ce0d4518d9122230c0d0cf373cb488f34af021.tar.gz
SERVER-62716 Ensure finishWaitingOneOpTime actually progresses
-rw-r--r--src/mongo/db/repl/wait_for_majority_service_test.cpp23
1 files changed, 16 insertions, 7 deletions
diff --git a/src/mongo/db/repl/wait_for_majority_service_test.cpp b/src/mongo/db/repl/wait_for_majority_service_test.cpp
index d2ee9419888..56fafb4b86d 100644
--- a/src/mongo/db/repl/wait_for_majority_service_test.cpp
+++ b/src/mongo/db/repl/wait_for_majority_service_test.cpp
@@ -67,13 +67,22 @@ public:
}
void finishWaitingOneOpTime() {
- stdx::unique_lock<Latch> lk(_mutex);
- _isTestReady = true;
- _isTestReadyCV.notify_one();
-
- while (_isTestReady) {
- _finishWaitingOneOpTimeCV.wait(lk);
- }
+ // There is a safe race condition in WaitForMajorityService where
+ // _periodicallyWaitForMajority can grab the mutex after the request has been marked as
+ // processed, but before it is removed from the queue. In this case, _isTestReady will
+ // flip without actually progressing through an OpTime, so we do the additional OpTime
+ // check.
+ auto opTimeBefore = _lastOpTimeWaited;
+
+ do {
+ stdx::unique_lock<Latch> lk(_mutex);
+ _isTestReady = true;
+ _isTestReadyCV.notify_one();
+
+ while (_isTestReady) {
+ _finishWaitingOneOpTimeCV.wait(lk);
+ }
+ } while (_lastOpTimeWaited == opTimeBefore);
}
Status waitForWriteConcernStub(OperationContext* opCtx, const repl::OpTime& opTime) {