summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorTommaso Tocci <tommaso.tocci@mongodb.com>2022-05-25 08:26:24 +0000
committerEvergreen Agent <no-reply@evergreen.mongodb.com>2022-07-11 19:25:40 +0000
commitb9a8d8bc44181a0fe9b39525abb98620b9440c90 (patch)
tree0b8fccab641f3acafb20b807d41d8536c041b92a
parent5dcd267b09a726ef041be925a0b970bfa25ca6ff (diff)
downloadmongo-b9a8d8bc44181a0fe9b39525abb98620b9440c90.tar.gz
SERVER-66658 Shard registry might be accessed before initialization
(cherry picked from commit 4851768e1d7c54e576300c75a976910e96703458)
-rw-r--r--src/mongo/s/client/shard_registry.cpp33
-rw-r--r--src/mongo/s/client/shard_registry.h2
2 files changed, 17 insertions, 18 deletions
diff --git a/src/mongo/s/client/shard_registry.cpp b/src/mongo/s/client/shard_registry.cpp
index 922f9f7a387..0983bb49896 100644
--- a/src/mongo/s/client/shard_registry.cpp
+++ b/src/mongo/s/client/shard_registry.cpp
@@ -139,12 +139,8 @@ ShardRegistry::Cache::LookupResult ShardRegistry::_lookup(OperationContext* opCt
// Check if we need to refresh from the configsvrs. If so, then do that and get the results,
// otherwise (this is a lookup only to incorporate updated connection strings from the RSM),
// then get the equivalent values from the previously cached data.
- auto [returnData,
- returnTopologyTime,
- returnForceReloadIncrement,
- removedShards,
- fetchedFromConfigServers] = [&]()
- -> std::tuple<ShardRegistryData, Timestamp, Increment, ShardRegistryData::ShardMap, bool> {
+ auto [returnData, returnTopologyTime, returnForceReloadIncrement, removedShards] =
+ [&]() -> std::tuple<ShardRegistryData, Timestamp, Increment, ShardRegistryData::ShardMap> {
if (timeInStore.topologyTime > cachedData.getTime().topologyTime ||
timeInStore.forceReloadIncrement > cachedData.getTime().forceReloadIncrement) {
auto [reloadedData, maxTopologyTime] =
@@ -160,14 +156,12 @@ ShardRegistry::Cache::LookupResult ShardRegistry::_lookup(OperationContext* opCt
auto [mergedData, removedShards] =
ShardRegistryData::mergeExisting(*cachedData, reloadedData);
- return {
- mergedData, maxTopologyTime, timeInStore.forceReloadIncrement, removedShards, true};
+ return {mergedData, maxTopologyTime, timeInStore.forceReloadIncrement, removedShards};
} else {
return {*cachedData,
cachedData.getTime().topologyTime,
cachedData.getTime().forceReloadIncrement,
- {},
- false};
+ {}};
}
}();
@@ -202,11 +196,6 @@ ShardRegistry::Cache::LookupResult ShardRegistry::_lookup(OperationContext* opCt
}
}
- // The registry is "up" once there has been a successful lookup from the config servers.
- if (fetchedFromConfigServers) {
- _isUp.store(true);
- }
-
Time returnTime{returnTopologyTime, rsmIncrementForConnStrings, returnForceReloadIncrement};
LOGV2_DEBUG(4620251,
2,
@@ -396,8 +385,18 @@ std::unique_ptr<Shard> ShardRegistry::createConnection(const ConnectionString& c
return _shardFactory->createUniqueShard(ShardId("<unnamed>"), connStr);
}
-bool ShardRegistry::isUp() const {
- return _isUp.load();
+bool ShardRegistry::isUp() {
+ if (_isUp.load())
+ return true;
+
+ // Before the first lookup is completed, the latest cached value is either empty or it is
+ // associated to the default constructed time
+ const auto latestCached = _cache->peekLatestCached(_kSingleton);
+ if (latestCached && latestCached.getTime() != Time()) {
+ _isUp.store(true);
+ return true;
+ }
+ return false;
}
void ShardRegistry::toBSON(BSONObjBuilder* result) const {
diff --git a/src/mongo/s/client/shard_registry.h b/src/mongo/s/client/shard_registry.h
index 0bb6196d2c3..98ca89de2c2 100644
--- a/src/mongo/s/client/shard_registry.h
+++ b/src/mongo/s/client/shard_registry.h
@@ -272,7 +272,7 @@ public:
* The ShardRegistry is "up" once a successful lookup from the config servers has been
* completed.
*/
- bool isUp() const;
+ bool isUp();
void toBSON(BSONObjBuilder* result) const;