From 320c25607ca75d82d02393a96c63195779cdaf9b Mon Sep 17 00:00:00 2001 From: Sage Weil Date: Wed, 10 Dec 2014 10:05:57 -0800 Subject: [PATCH] osdc/Objecter: only issue one error per watch; do it through one path Send all errors through C_DoWatchError for simplicity. Only deliver one error per watch. This simplifies callers logic and avoids a very rare case that they need to deal with. Signed-off-by: Sage Weil --- src/osdc/Objecter.cc | 25 +++++++++++++++---------- 1 file changed, 15 insertions(+), 10 deletions(-) diff --git a/src/osdc/Objecter.cc b/src/osdc/Objecter.cc index 88b7d304dbef4..2ae8774c9025b 100644 --- a/src/osdc/Objecter.cc +++ b/src/osdc/Objecter.cc @@ -510,9 +510,11 @@ void Objecter::_linger_reconnect(LingerOp *info, int r) << " (last_error " << info->last_error << ")" << dendl; if (r < 0) { info->watch_lock.get_write(); - info->last_error = r; - if (info->watch_context) - finisher->queue(new C_DoWatchError(info, r)); + if (!info->last_error) { + info->last_error = r; + if (info->watch_context) + finisher->queue(new C_DoWatchError(info, r)); + } info->watch_lock.put_write(); } } @@ -569,7 +571,7 @@ void Objecter::_linger_ping(LingerOp *info, int r, utime_t sent, if (info->register_gen == register_gen) { if (r == 0) { info->watch_valid_thru = sent; - } else if (r < 0) { + } else if (r < 0 && !info->last_error) { info->last_error = r; if (info->watch_context) finisher->queue(new C_DoWatchError(info, r)); @@ -752,9 +754,14 @@ void Objecter::handle_watch_notify(MWatchNotify *m) } RWLock::WLocker wl(info->watch_lock); if (m->opcode == CEPH_WATCH_EVENT_DISCONNECT) { - info->last_error = -ENOTCONN; + if (!info->last_error) { + info->last_error = -ENOTCONN; + if (info->watch_context) + finisher->queue(new C_DoWatchError(info, -ENOTCONN)); + } + } else { + finisher->queue(new C_DoWatchNotify(this, info, m)); } - finisher->queue(new C_DoWatchNotify(this, info, m)); } void Objecter::_do_watch_notify(LingerOp *info, MWatchNotify *m) @@ -783,6 +790,8 @@ void Objecter::_do_watch_notify(LingerOp *info, MWatchNotify *m) assert(info->is_watch); assert(info->watch_context); + assert(m->opcode != CEPH_WATCH_EVENT_DISCONNECT); + rwlock.put_read(); switch (m->opcode) { @@ -790,10 +799,6 @@ void Objecter::_do_watch_notify(LingerOp *info, MWatchNotify *m) info->watch_context->handle_notify(m->notify_id, m->cookie, m->notifier_gid, m->bl); break; - - case CEPH_WATCH_EVENT_DISCONNECT: - info->watch_context->handle_error(m->cookie, -ENOTCONN); - break; } out: -- 2.39.5