From: Samuel Just Date: Wed, 16 Apr 2014 17:37:01 +0000 (-0700) Subject: ReplicatedPG::do_op: check for blocked snapset obj X-Git-Tag: v0.80-rc1~12^2 X-Git-Url: http://git-server-git.apps.pok.os.sepia.ceph.com/?a=commitdiff_plain;h=95394b60b84a10ab7031f71dedf57d03d4dfe56e;p=ceph.git ReplicatedPG::do_op: check for blocked snapset obj Otherwise, we might use an invalid snapset in find_object_context. Signed-off-by: Samuel Just --- diff --git a/src/osd/ReplicatedPG.cc b/src/osd/ReplicatedPG.cc index 9274893a597a..7f8a6f00b5dd 100644 --- a/src/osd/ReplicatedPG.cc +++ b/src/osd/ReplicatedPG.cc @@ -472,6 +472,30 @@ void ReplicatedPG::wait_for_degraded_object(const hobject_t& soid, OpRequestRef op->mark_delayed("waiting for degraded object"); } +bool ReplicatedPG::maybe_await_blocked_snapset( + const hobject_t &hoid, + OpRequestRef op) +{ + ObjectContextRef obc; + if (obc = object_contexts.lookup(hoid.get_head())) { + if (obc->is_blocked()) { + wait_for_blocked_object(obc->obs.oi.soid, op); + return true; + } else { + return false; + } + } + if (obc = object_contexts.lookup(hoid.get_snapdir())) { + if (obc->is_blocked()) { + wait_for_blocked_object(obc->obs.oi.soid, op); + return true; + } else { + return false; + } + } + return false; +} + void ReplicatedPG::wait_for_blocked_object(const hobject_t& soid, OpRequestRef op) { dout(10) << __func__ << " " << soid << " " << op << dendl; @@ -1262,6 +1286,13 @@ void ReplicatedPG::do_op(OpRequestRef op) m->get_pg().ps(), m->get_object_locator().get_pool(), m->get_object_locator().nspace); + + // io blocked on obc? + if (((m->get_flags() & CEPH_OSD_FLAG_FLUSH) == 0) && + maybe_await_blocked_snapset(oid, op)) { + return; + } + int r = find_object_context( oid, &obc, can_create, m->get_flags() & CEPH_OSD_FLAG_MAP_SNAP_CLONE, @@ -7130,10 +7161,12 @@ int ReplicatedPG::find_object_context(const hobject_t& oid, } SnapSetContext *ssc = get_snapset_context(oid, can_create); - if (!ssc) { + if (!ssc || !(ssc->exists)) { dout(20) << __func__ << " " << oid << " no snapset" << dendl; if (pmissing) *pmissing = head; // start by getting the head + if (ssc) + put_snapset_context(ssc); return -ENOENT; } diff --git a/src/osd/ReplicatedPG.h b/src/osd/ReplicatedPG.h index a59242d32943..86071dc2f6b2 100644 --- a/src/osd/ReplicatedPG.h +++ b/src/osd/ReplicatedPG.h @@ -1367,6 +1367,7 @@ public: bool is_degraded_object(const hobject_t& oid); void wait_for_degraded_object(const hobject_t& oid, OpRequestRef op); + bool maybe_await_blocked_snapset(const hobject_t &soid, OpRequestRef op); void wait_for_blocked_object(const hobject_t& soid, OpRequestRef op); void kick_object_context_blocked(ObjectContextRef obc);