summaryrefslogtreecommitdiff
path: root/src/mongo/db/catalog_raii.cpp
diff options
context:
space:
mode:
authorLingzhi Deng <lingzhi.deng@mongodb.com>2020-03-03 10:46:39 -0500
committerEvergreen Agent <no-reply@evergreen.mongodb.com>2020-03-13 17:21:07 +0000
commitc15e8ae74071482d69179c7e5e5e6bdc882d2beb (patch)
treea17f28ebb0e53c69f2b1c07f6e4d41dedf78f5fe /src/mongo/db/catalog_raii.cpp
parent46b4b3d8f03e3dfc3ca2ae344bf7848732e986c3 (diff)
downloadmongo-c15e8ae74071482d69179c7e5e5e6bdc882d2beb.tar.gz
SERVER-45626: Introduce AutoGetOplog for consistent oplog locking rules
Diffstat (limited to 'src/mongo/db/catalog_raii.cpp')
-rw-r--r--src/mongo/db/catalog_raii.cpp33
1 files changed, 33 insertions, 0 deletions
diff --git a/src/mongo/db/catalog_raii.cpp b/src/mongo/db/catalog_raii.cpp
index 156727191dd..aacce83a287 100644
--- a/src/mongo/db/catalog_raii.cpp
+++ b/src/mongo/db/catalog_raii.cpp
@@ -182,4 +182,37 @@ ReadSourceScope::~ReadSourceScope() {
}
}
+AutoGetOplog::AutoGetOplog(OperationContext* opCtx, OplogAccessMode mode, Date_t deadline)
+ : _shouldNotConflictWithSecondaryBatchApplicationBlock(opCtx->lockState()) {
+ if (mode == OplogAccessMode::kLogOp) {
+ // Invariant that global lock is already held for kLogOp mode.
+ invariant(opCtx->lockState()->isWriteLocked());
+ } else {
+ _globalLock.emplace(opCtx,
+ mode == OplogAccessMode::kRead ? MODE_IS : MODE_IX,
+ deadline,
+ Lock::InterruptBehavior::kThrow);
+ }
+
+ // Obtain database and collection intent locks for non-document-locking storage engines.
+ if (!opCtx->getServiceContext()->getStorageEngine()->supportsDocLocking()) {
+ auto lockMode = (mode == OplogAccessMode::kRead) ? MODE_IS : MODE_IX;
+
+ // If mode is kLogOp, only acquire the database lock if it is not already held.
+ if (mode != OplogAccessMode::kLogOp ||
+ !opCtx->lockState()->isDbLockedForMode(NamespaceString::kLocalDb, lockMode)) {
+ _dbWriteLock.emplace(opCtx, NamespaceString::kLocalDb, lockMode, deadline);
+ }
+
+ // If mode is kLogOp, only acquire the collection lock if it is not already held.
+ if (mode != OplogAccessMode::kLogOp ||
+ !opCtx->lockState()->isCollectionLockedForMode(NamespaceString::kRsOplogNamespace,
+ lockMode)) {
+ _collWriteLock.emplace(opCtx, NamespaceString::kRsOplogNamespace, lockMode, deadline);
+ }
+ }
+ _oplogInfo = repl::LocalOplogInfo::get(opCtx);
+ _oplog = _oplogInfo->getCollection();
+}
+
} // namespace mongo