diff options
author | Dianna Hohensee <dianna.hohensee@10gen.com> | 2018-05-04 08:45:36 -0400 |
---|---|---|
committer | Dianna Hohensee <dianna.hohensee@10gen.com> | 2018-05-07 12:48:31 -0400 |
commit | 8a41a08818c38c4f79a1c4ba2dfe453e8e547dd0 (patch) | |
tree | e4bdc4c1b23807d8d78d96d8924d3ac59aac22f6 /src/mongo/db/repl/drop_pending_collection_reaper.cpp | |
parent | 36a7e1c06554522aa96e41378688568fb16754c2 (diff) | |
download | mongo-8a41a08818c38c4f79a1c4ba2dfe453e8e547dd0.tar.gz |
SERVER-34829 Drop pending reaper must not delete the _dropPendingNamespaces entry until after the drop occurs
Diffstat (limited to 'src/mongo/db/repl/drop_pending_collection_reaper.cpp')
-rw-r--r-- | src/mongo/db/repl/drop_pending_collection_reaper.cpp | 47 |
1 files changed, 32 insertions, 15 deletions
diff --git a/src/mongo/db/repl/drop_pending_collection_reaper.cpp b/src/mongo/db/repl/drop_pending_collection_reaper.cpp index 7cd7d47a33d..709f30d64c8 100644 --- a/src/mongo/db/repl/drop_pending_collection_reaper.cpp +++ b/src/mongo/db/repl/drop_pending_collection_reaper.cpp @@ -135,10 +135,10 @@ void DropPendingCollectionReaper::dropCollectionsOlderThan(OperationContext* opC DropPendingNamespaces toDrop; { stdx::lock_guard<stdx::mutex> lock(_mutex); - auto it = _dropPendingNamespaces.cbegin(); - while (it != _dropPendingNamespaces.cend() && it->first <= opTime) { + for (auto it = _dropPendingNamespaces.cbegin(); + it != _dropPendingNamespaces.cend() && it->first <= opTime; + ++it) { toDrop.insert(*it); - it = _dropPendingNamespaces.erase(it); } } @@ -146,19 +146,36 @@ void DropPendingCollectionReaper::dropCollectionsOlderThan(OperationContext* opC return; } - // Every node cleans up its own drop-pending collections. We should never replicate these drops - // because these are internal operations. - UnreplicatedWritesBlock uwb(opCtx); + { + // Every node cleans up its own drop-pending collections. We should never replicate these + // drops because these are internal operations. + UnreplicatedWritesBlock uwb(opCtx); + + for (const auto& opTimeAndNamespace : toDrop) { + const auto& dropOpTime = opTimeAndNamespace.first; + const auto& nss = opTimeAndNamespace.second; + log() << "Completing collection drop for " << nss << " with drop optime " << dropOpTime + << " (notification optime: " << opTime << ")"; + auto status = _storageInterface->dropCollection(opCtx, nss); + if (!status.isOK()) { + warning() << "Failed to remove drop-pending collection " << nss + << " with drop optime " << dropOpTime + << " (notification optime: " << opTime << "): " << status; + } + } + } - for (const auto& opTimeAndNamespace : toDrop) { - const auto& dropOpTime = opTimeAndNamespace.first; - const auto& nss = opTimeAndNamespace.second; - log() << "Completing collection drop for " << nss << " with drop optime " << dropOpTime - << " (notification optime: " << opTime << ")"; - auto status = _storageInterface->dropCollection(opCtx, nss); - if (!status.isOK()) { - warning() << "Failed to remove drop-pending collection " << nss << " with drop optime " - << dropOpTime << " (notification optime: " << opTime << "): " << status; + { + // Entries must be removed AFTER drops are completed, so that getEarliestDropOpTime() + // returns appropriate results. + stdx::lock_guard<stdx::mutex> lock(_mutex); + auto it = _dropPendingNamespaces.cbegin(); + while (it != _dropPendingNamespaces.cend() && it->first <= opTime) { + if (toDrop.find(it->first) != toDrop.cend()) { + it = _dropPendingNamespaces.erase(it); + } else { + ++it; + } } } } |