Currently post_save hook is called without checking its return. If post_save
fails, we need to set an error and propagate it to the caller.

Since post_save hook is called regardless of whether there is a preceeding 
error,
it is possible that we have 2 distict errors, one from the preceeding function
call, and the other from the post_save call.

Return the latest error to the caller.

Signed-off-by: Arun Menon <arme...@redhat.com>
---
 migration/vmstate.c | 18 ++++++++++++++----
 1 file changed, 14 insertions(+), 4 deletions(-)

diff --git a/migration/vmstate.c b/migration/vmstate.c
index 
b725202bfcf69c3c81338f1f5479aa2ddc5db86f..25a819da069b982d4043f287b4562ea402d9eb0e
 100644
--- a/migration/vmstate.c
+++ b/migration/vmstate.c
@@ -418,6 +418,7 @@ int vmstate_save_state_v(QEMUFile *f, const 
VMStateDescription *vmsd,
                          void *opaque, JSONWriter *vmdesc, int version_id, 
Error **errp)
 {
     int ret = 0;
+    int ps_ret = 0;
     const VMStateField *field = vmsd->fields;
 
     trace_vmstate_save_state_top(vmsd->name);
@@ -533,7 +534,14 @@ int vmstate_save_state_v(QEMUFile *f, const 
VMStateDescription *vmsd,
                     error_setg(errp, "Save of field %s/%s failed",
                                 vmsd->name, field->name);
                     if (vmsd->post_save) {
-                        vmsd->post_save(opaque);
+                        ps_ret = vmsd->post_save(opaque);
+                        if (ps_ret) {
+                            ret = ps_ret;
+                            error_free_or_abort(errp);
+                            error_setg(errp,
+                                       "post-save for %s failed, ret: '%d'",
+                                       vmsd->name, ret);
+                        }
                     }
                     return ret;
                 }
@@ -561,10 +569,12 @@ int vmstate_save_state_v(QEMUFile *f, const 
VMStateDescription *vmsd,
     ret = vmstate_subsection_save(f, vmsd, opaque, vmdesc, errp);
 
     if (vmsd->post_save) {
-        int ps_ret = vmsd->post_save(opaque);
-        if (!ret && ps_ret) {
+        ps_ret = vmsd->post_save(opaque);
+        if (ps_ret) {
             ret = ps_ret;
-            error_setg(errp, "post-save failed: %s", vmsd->name);
+            error_free_or_abort(errp);
+            error_setg(errp, "post-save for %s failed, ret: '%d'",
+                       vmsd->name, ret);
         }
     }
     return ret;

-- 
2.50.0


Reply via email to