]> git.apps.os.sepia.ceph.com Git - ceph-ci.git/commitdiff
mds: trim cache on regular schedule
authorPatrick Donnelly <pdonnell@redhat.com>
Wed, 7 Aug 2019 17:35:02 +0000 (10:35 -0700)
committerPatrick Donnelly <pdonnell@redhat.com>
Sat, 24 Aug 2019 23:03:46 +0000 (16:03 -0700)
Do this outside the standard tick interval as it needs to be driven more
frequently to keep up with client workloads that generate a lot of
capabilities.

Fixes: https://tracker.ceph.com/issues/41141
Fixes: https://tracker.ceph.com/issues/41140
Signed-off-by: Patrick Donnelly <pdonnell@redhat.com>
src/common/options.cc
src/mds/MDCache.cc
src/mds/MDCache.h
src/mds/MDSRank.cc
src/mds/MDSRank.h

index a819ed38335e70421c23fcb74294e301cb05bd5d..c90b3296c56569c67136368453d42dbcc810d120 100644 (file)
@@ -7682,6 +7682,10 @@ std::vector<Option> get_mds_options() {
     .set_default(64_K)
     .set_description("maximum aggregate size of extended attributes on a file"),
 
+    Option("mds_cache_trim_interval", Option::TYPE_SECS, Option::LEVEL_ADVANCED)
+    .set_default(1)
+    .set_description("interval in seconds between cache trimming"),
+
     Option("mds_cache_size", Option::TYPE_INT, Option::LEVEL_ADVANCED)
     .set_default(0)
     .set_description("maximum number of inodes in MDS cache (<=0 is unlimited)")
index de4bef951b17ed6a8d3cf9c5916a0f0c66a12c5b..4d854fa7be29797f679d15fa4c34f32bb2629698 100644 (file)
@@ -157,6 +157,36 @@ MDCache::MDCache(MDSRank *m, PurgeQueue &purge_queue_) :
   bottom_lru.lru_set_midpoint(0);
 
   decayrate.set_halflife(g_conf()->mds_decay_halflife);
+
+  upkeeper = std::thread([this]() {
+    std::unique_lock lock(upkeep_mutex);
+    while (!upkeep_trim_shutdown.load()) {
+      auto now = clock::now();
+      auto since = now-upkeep_last_trim;
+      auto interval = clock::duration(g_conf().get_val<std::chrono::seconds>("mds_cache_trim_interval"));
+      if (since >= interval*.90) {
+        lock.unlock(); /* mds_lock -> upkeep_mutex */
+        std::scoped_lock mds_lock(mds->mds_lock);
+        lock.lock();
+        if (upkeep_trim_shutdown.load())
+          return;
+        if (mds->is_cache_trimmable()) {
+          dout(20) << "upkeep thread trimming cache; last trim " << since << " ago" << dendl;
+          trim_client_leases();
+          trim();
+          check_memory_usage();
+          mds->server->recall_client_state(nullptr, Server::RecallFlags::ENFORCE_MAX);
+          upkeep_last_trim = clock::now();
+        } else {
+          dout(10) << "cache not ready for trimming" << dendl;
+        }
+      } else {
+        interval -= since;
+      }
+      dout(20) << "upkeep thread waiting interval " << interval << dendl;
+      upkeep_cvar.wait_for(lock, interval);
+    }
+  });
 }
 
 MDCache::~MDCache() 
@@ -164,6 +194,8 @@ MDCache::~MDCache()
   if (logger) {
     g_ceph_context->get_perfcounters_collection()->remove(logger.get());
   }
+  if (upkeeper.joinable())
+    upkeeper.join();
 }
 
 void MDCache::handle_conf_change(const std::set<std::string>& changed, const MDSMap& mdsmap)
@@ -203,6 +235,11 @@ void MDCache::log_stat()
 
 bool MDCache::shutdown()
 {
+  {
+    std::scoped_lock lock(upkeep_mutex);
+    upkeep_trim_shutdown = true;
+    upkeep_cvar.notify_one();
+  }
   if (lru.lru_get_size() > 0) {
     dout(7) << "WARNING: mdcache shutdown with non-empty cache" << dendl;
     //show_cache();
index c3c65e37cf0f86a2cfd0e157b72c19eb101e3cf3..8dec2a372413bdf1f94dbb7fd16d33a80c601f15 100644 (file)
@@ -17,7 +17,9 @@
 #ifndef CEPH_MDCACHE_H
 #define CEPH_MDCACHE_H
 
+#include <atomic>
 #include <string_view>
+#include <thread>
 
 #include "common/DecayCounter.h"
 #include "include/types.h"
@@ -1321,6 +1323,13 @@ public:
   std::set<CInode *> export_pin_delayed_queue;
 
   OpenFileTable open_file_table;
+
+private:
+  std::thread upkeeper;
+  ceph::mutex upkeep_mutex = ceph::make_mutex("MDCache::upkeep_mutex");
+  ceph::condition_variable upkeep_cvar;
+  time upkeep_last_trim = time::min();
+  std::atomic<bool> upkeep_trim_shutdown{false};
 };
 
 class C_MDS_RetryRequest : public MDSInternalContext {
index 46112b9771f6e1f7a107af67bb5acb455291ce5e..46b741439c63172981aebe26a2f1fc75ba48df69 100644 (file)
@@ -746,13 +746,7 @@ void MDSRankDispatcher::tick()
   }
 
   // ...
-  if (is_clientreplay() || is_active() || is_stopping()) {
-    mdcache->trim_client_leases();
-    mdcache->trim();
-    mdcache->check_memory_usage();
-
-    server->recall_client_state(nullptr, Server::RecallFlags::ENFORCE_MAX);
-
+  if (is_cache_trimmable()) {
     server->find_idle_sessions();
     server->evict_cap_revoke_non_responders();
     locker->tick();
index 1ae2c6a3bc6e76c1fc41986e26e7a78dfa2d65d7..eff0d8723031cf747d767d12c333eb47c6242138 100644 (file)
@@ -230,6 +230,10 @@ class MDSRank {
     bool is_cluster_degraded() const { return cluster_degraded; }
     bool allows_multimds_snaps() const { return mdsmap->allows_multimds_snaps(); }
 
+    bool is_cache_trimmable() const {
+      return is_clientreplay() || is_active() || is_stopping();
+    }
+
     void handle_write_error(int err);
 
     void update_mlogger();