From 3980f0b9bd25ba09590c24c751e2e1972f90fcc9 Mon Sep 17 00:00:00 2001
From: Juan Quintela <quintela@redhat.com>
Date: Wed, 19 Oct 2011 23:47:39 +0200
Subject: [PATCH 04/19] Reorganize and fix monitor resume after migration

RH-Author: Juan Quintela <quintela@redhat.com>
Message-id: <657e8edcc806bdb4160b708041a5925bbd715b3c.1319066770.git.quintela@redhat.com>
Patchwork-id: 34429
O-Subject: [PATCH qemu-kvm RHEL-6.2 04/16] Reorganize and fix monitor resume after migration
Bugzilla: 669581
RH-Acked-by: Amit Shah <amit.shah@redhat.com>
RH-Acked-by: Markus Armbruster <armbru@redhat.com>
RH-Acked-by: Orit Wasserman <owasserm@redhat.com>
RH-Acked-by: Kevin Wolf <kwolf@redhat.com>

From: Jan Kiszka <jan.kiszka@siemens.com>

If migration failed in migrate_fd_put_buffer, the monitor may have been
resumed not only in the error path of that function but also once again
in migrate_fd_put_ready which is called unconditionally by
migrate_fd_connect.

Fix this by establishing a cleaner policy: the monitor shall be resumed
when the migration file is closed, either via callback
(migrate_fd_close) or in migrate_fd_cleanup if no file is open (i.e. no
callback invoked).

Reported-By: Michael Tokarev <mjt@tls.msk.ru>
Tested-By: Michael Tokarev <mjt@tls.msk.ru>
Signed-off-by: Jan Kiszka <jan.kiszka@siemens.com>
Signed-off-by: Anthony Liguori <aliguori@us.ibm.com>
Signed-off-by: Juan Quintela <quintela@redhat.com>
---
 migration.c |   19 +++++++++----------
 1 files changed, 9 insertions(+), 10 deletions(-)

Signed-off-by: Michal Novotny <minovotn@redhat.com>
---
 migration.c |   19 +++++++++----------
 1 files changed, 9 insertions(+), 10 deletions(-)

diff --git a/migration.c b/migration.c
index 4913557..ee517a8 100644
--- a/migration.c
+++ b/migration.c
@@ -310,18 +310,17 @@ int migrate_fd_cleanup(FdMigrationState *s)
             s->state = MIG_STATE_ERROR;
         }
         s->file = NULL;
+    } else {
+        if (s->mon) {
+            monitor_resume(s->mon);
+        }
     }
 
-    if (s->fd != -1)
+    if (s->fd != -1) {
         close(s->fd);
-
-    /* Don't resume monitor until we've flushed all of the buffers */
-    if (s->mon) {
-        monitor_resume(s->mon);
+        s->fd = -1;
     }
 
-    s->fd = -1;
-
     return ret;
 }
 
@@ -348,9 +347,6 @@ ssize_t migrate_fd_put_buffer(void *opaque, const void *data, size_t size)
     if (ret == -EAGAIN) {
         qemu_set_fd_handler2(s->fd, NULL, NULL, migrate_fd_put_notify, s);
     } else if (ret < 0) {
-        if (s->mon) {
-            monitor_resume(s->mon);
-        }
         s->state = MIG_STATE_ERROR;
         notifier_list_notify(&migration_state_notifiers);
     }
@@ -480,6 +476,9 @@ int migrate_fd_close(void *opaque)
 {
     FdMigrationState *s = opaque;
 
+    if (s->mon) {
+        monitor_resume(s->mon);
+    }
     qemu_set_fd_handler2(s->fd, NULL, NULL, NULL, NULL);
     return s->close(s);
 }
-- 
1.7.4.4

