diff options
author | Sage Weil <sage@inktank.com> | 2013-04-05 22:28:38 -0700 |
---|---|---|
committer | Sage Weil <sage@inktank.com> | 2013-04-05 22:28:38 -0700 |
commit | 79b71441f8c2a1b282fa0e85badcb7d410c8005d (patch) | |
tree | 691012f7d1ece5197b075a47dc956c37df619a5d | |
parent | b083dece36a050ec15ac41a275aeef0ece1ac009 (diff) | |
download | ceph-79b71441f8c2a1b282fa0e85badcb7d410c8005d.tar.gz |
librbd: fix DiffIterateStress test
If we write to an interval that didn't previously exist and then discard
it so that it again doesn't exist, all during the same interval, then we
should not include it in the 'written' set (or exists set, obviously).
Similarly, when we got to look at a merged diff, we can ignore extents
that were written (and possibly zeroed) if they neither existed before nor
after.
Bump up the iteration count to get more confidence that this is actually
correct.
Signed-off-by: Sage Weil <sage@inktank.com>
-rw-r--r-- | src/test/librbd/test_librbd.cc | 43 |
1 files changed, 34 insertions, 9 deletions
diff --git a/src/test/librbd/test_librbd.cc b/src/test/librbd/test_librbd.cc index ae65bd5027d..38bfbb6cf91 100644 --- a/src/test/librbd/test_librbd.cc +++ b/src/test/librbd/test_librbd.cc @@ -1515,21 +1515,37 @@ void scribble(librbd::Image& image, int n, int max, interval_set<uint64_t> *exis { uint64_t size; image.size(&size); + interval_set<uint64_t> exists_at_start = *exists; for (int i=0; i<n; i++) { uint64_t off = rand() % (size - max + 1); uint64_t len = 1 + rand() % max; - interval_set<uint64_t> w; - w.insert(off, len); if (rand() % 4 == 0) { ASSERT_EQ((int)len, image.discard(off, len)); - w.intersection_of(*exists); - what->union_of(w); + interval_set<uint64_t> w; + w.insert(off, len); + + // the zeroed bit no longer exists... + w.intersection_of(*exists); exists->subtract(w); + + // the bits we discarded are no long written... + interval_set<uint64_t> w2 = w; + w2.intersection_of(*what); + what->subtract(w2); + + // except for the extents that existed at the start that we overwrote. + interval_set<uint64_t> w3; + w3.insert(off, len); + w3.intersection_of(exists_at_start); + what->union_of(w3); + } else { bufferlist bl; bl.append(buffer::create(len)); bl.zero(); ASSERT_EQ((int)len, image.write(off, len, bl)); + interval_set<uint64_t> w; + w.insert(off, len); what->union_of(w); exists->union_of(w); } @@ -1695,27 +1711,36 @@ TEST(LibRBD, DiffIterateStress) ASSERT_EQ(0, create_image_pp(rbd, ioctx, name, size, &order)); ASSERT_EQ(0, rbd.open(ioctx, image, name, NULL)); - interval_set<uint64_t> exists; + interval_set<uint64_t> curexists; vector<interval_set<uint64_t> > wrote; + vector<interval_set<uint64_t> > exists; vector<string> snap; - int n = 10; + int n = 20; for (int i=0; i<n; i++) { interval_set<uint64_t> w; - scribble(image, 10, 8192000, &exists, &w); - cout << " i=" << i << " exists " << exists << " wrote " << w << std::endl; + scribble(image, 10, 8192000, &curexists, &w); + cout << " i=" << i << " exists " << curexists << " wrote " << w << std::endl; string s = "snap" + stringify(i); ASSERT_EQ(0, image.snap_create(s.c_str())); wrote.push_back(w); + exists.push_back(curexists); snap.push_back(s); } for (int i=0; i<n-1; i++) { for (int j=i+1; j<n; j++) { - interval_set<uint64_t> diff, actual; + interval_set<uint64_t> diff, actual, uex; for (int k=i+1; k<=j; k++) diff.union_of(wrote[k]); cout << "from " << i << " to " << j << " diff " << diff << std::endl; + // limit to extents that exists both at the beginning and at the end + uex = exists[j]; + if (i) + uex.union_of(exists[i-1]); + diff.intersection_of(uex); + cout << " limited diff " << diff << std::endl; + image.snap_set(snap[j].c_str()); ASSERT_EQ(0, image.diff_iterate(snap[i].c_str(), 0, size, iterate_cb, (void *)&actual)); cout << " actual was " << actual << std::endl; |