]> git.apps.os.sepia.ceph.com Git - ceph.git/commitdiff
Reduce ObjectCacher flush overhead
authorHaomai Wang <haomaiwang@gmail.com>
Mon, 14 Jul 2014 06:32:57 +0000 (14:32 +0800)
committerHaomai Wang <haomaiwang@gmail.com>
Sun, 27 Jul 2014 05:33:38 +0000 (13:33 +0800)
Flush op in ObjectCacher will iterate the whole active object set, each
dirty object also may own several BufferHead. If the object set is large,
it will consume too much time.

Use dirty_bh instead to reduce overhead. Now only dirty BufferHead will
be checked.

Signed-off-by: Haomai Wang <haomaiwang@gmail.com>
src/osdc/ObjectCacher.cc

index d3626884fcd2b639eafbd3b0e30289ff9d285c6a..b52de928a678007df5e1cbeafc717f0984800a4f 100644 (file)
@@ -1613,22 +1613,28 @@ bool ObjectCacher::flush_set(ObjectSet *oset, Context *onfinish)
 
   // we'll need to wait for all objects to flush!
   C_GatherBuilder gather(cct);
+  set<Object*> waitfor_commit;
+
+  set<BufferHead*>::iterator next, it;
+  next = it = dirty_bh.begin();
+  while (it != dirty_bh.end()) {
+    next++;
+    BufferHead *bh = *it;
+    waitfor_commit.insert(bh->ob);
+    bh_write(bh);
+    it = next;
+  }
 
-  for (xlist<Object*>::iterator i = oset->objects.begin();
-       !i.end(); ++i) {
+  for (set<Object*>::iterator i = waitfor_commit.begin();
+       i != waitfor_commit.end(); ++i) {
     Object *ob = *i;
 
-    if (ob->dirty_or_tx == 0)
-      continue;
-
-    if (!flush(ob, 0, 0)) {
-      // we'll need to gather...
-      ldout(cct, 10) << "flush_set " << oset << " will wait for ack tid " 
-               << ob->last_write_tid 
-               << " on " << *ob
-               << dendl;
-      ob->waitfor_commit[ob->last_write_tid].push_back(gather.new_sub());
-    }
+    // we'll need to gather...
+    ldout(cct, 10) << "flush_set " << oset << " will wait for ack tid "
+             << ob->last_write_tid
+             << " on " << *ob
+             << dendl;
+    ob->waitfor_commit[ob->last_write_tid].push_back(gather.new_sub());
   }
 
   return _flush_set_finish(&gather, onfinish);