From: Yan, Zheng Date: Wed, 28 Oct 2015 08:54:21 +0000 (+0800) Subject: objectcacher: make flush_set() only flushes dirty data in ObjectSet X-Git-Tag: v10.0.3~120^2~3 X-Git-Url: http://git-server-git.apps.pok.os.sepia.ceph.com/?a=commitdiff_plain;h=5246e789606b802f8a0e5bc58eb2ec3ac6e481c3;p=ceph.git objectcacher: make flush_set() only flushes dirty data in ObjectSet Buffer heads in dirty_or_tx_bh are sorted in ObjectSet/Object/offset order. So we can find dirty buffer heads in the given ObjectSet and flush them only. Signed-off-by: Yan, Zheng --- diff --git a/src/osdc/ObjectCacher.cc b/src/osdc/ObjectCacher.cc index e358ed73989a..85c5a9b4b25a 100644 --- a/src/osdc/ObjectCacher.cc +++ b/src/osdc/ObjectCacher.cc @@ -1825,17 +1825,46 @@ bool ObjectCacher::flush_set(ObjectSet *oset, Context *onfinish) C_GatherBuilder gather(cct); set waitfor_commit; - set::iterator next, it; - next = it = dirty_or_tx_bh.begin(); - while (it != dirty_or_tx_bh.end()) { - ++next; - BufferHead *bh = *it; - waitfor_commit.insert(bh->ob); + set::iterator it, p, q; + + // Buffer heads in dirty_or_tx_bh are sorted in ObjectSet/Object/offset + // order. But items in oset->objects are not sorted. So the iterator can + // point to any buffer head in the ObjectSet + BufferHead key(*oset->objects.begin()); + it = dirty_or_tx_bh.lower_bound(&key); + p = q = it; + + bool backwards = true; + if (it != dirty_or_tx_bh.begin()) + --it; + else + backwards = false; + for (; p != dirty_or_tx_bh.end(); p = q) { + ++q; + BufferHead *bh = *p; + if (bh->ob->oset != oset) + break; + waitfor_commit.insert(bh->ob); if (bh->is_dirty()) bh_write(bh); + } - it = next; + if (backwards) { + for(p = q = it; true; p = q) { + if (q != dirty_or_tx_bh.begin()) + --q; + else + backwards = false; + BufferHead *bh = *p; + if (bh->ob->oset != oset) + break; + waitfor_commit.insert(bh->ob); + if (bh->is_dirty()) + bh_write(bh); + if (!backwards) + break; + } } for (set::iterator i = waitfor_commit.begin();