]> git.apps.os.sepia.ceph.com Git - ceph.git/commitdiff
librbd: diff_iterate should handle callback errors
authorJason Dillaman <dillaman@redhat.com>
Fri, 22 May 2015 02:59:07 +0000 (22:59 -0400)
committerJason Dillaman <dillaman@redhat.com>
Mon, 10 Aug 2015 15:24:08 +0000 (11:24 -0400)
If the diff_iterate callback returns an error, it should
result in diff_iterate being aborted with the error code
propagated.

Fixes: #11593
Signed-off-by: Jason Dillaman <dillaman@redhat.com>
src/librbd/DiffIterate.cc

index 35ebfecb0479dfb4eb253c3ca7bedde774052c17..00a9ebae2b72991c57ad486296384530826d78ae 100644 (file)
@@ -64,8 +64,14 @@ public:
 
       for (Diffs::const_iterator d = diffs.begin(); d != diffs.end(); ++d) {
         m_lock.Unlock();
-        m_callback(d->get<0>(), d->get<1>(), d->get<2>(), m_callback_arg);
+        int r = m_callback(d->get<0>(), d->get<1>(), d->get<2>(),
+                           m_callback_arg);
         m_lock.Lock();
+
+        if (m_return_value == 0 && r < 0) {
+          m_return_value = r;
+          return m_return_value;
+        }
       }
       ++m_waiting_request;
     }
@@ -360,7 +366,10 @@ int DiffIterate::execute() {
                             OBJECT_DIFF_STATE_UPDATED);
           for (std::vector<ObjectExtent>::iterator q = p->second.begin();
                q != p->second.end(); ++q) {
-            m_callback(off + q->offset, q->length, updated, m_callback_arg);
+            r = m_callback(off + q->offset, q->length, updated, m_callback_arg);
+            if (r < 0) {
+              return r;
+            }
           }
         }
       } else {