All of lore.kernel.org
 help / color / mirror / Atom feed
From: zhanghailiang <zhang.zhanghailiang@huawei.com>
To: qemu-devel@nongnu.org
Cc: amit.shah@redhat.com, quintela@redhat.com, dgilbert@redhat.com,
	peter.huangpeng@huawei.com, eddie.dong@intel.com,
	wency@cn.fujitsu.com, lizhijian@cn.fujitsu.com,
	zhangchen.fnst@cn.fujitsu.com, xiecl.fnst@cn.fujitsu.com,
	zhanghailiang <zhang.zhanghailiang@huawei.com>,
	Gonglei <arei.gonglei@huawei.com>
Subject: [Qemu-devel] [PATCH COLO-Frame v18 09/34] COLO: Save PVM state to secondary side when do checkpoint
Date: Wed, 3 Aug 2016 20:25:47 +0800	[thread overview]
Message-ID: <1470227172-13704-10-git-send-email-zhang.zhanghailiang@huawei.com> (raw)
In-Reply-To: <1470227172-13704-1-git-send-email-zhang.zhanghailiang@huawei.com>

The main process of the checkpoint is to synchronize SVM with PVM.
VM's state includes ram and device state. So we will migrate PVM's
state to SVM when do checkpoint, just like migration does.

We will cache PVM's state in slave, we use QEMUSizedBuffer
to store the data, we need to know the size of VM state, so in master,
we use qsb to store VM state temporarily, get the data size by call qsb_get_length()
and then migrate the data to the qsb in the secondary side.

Signed-off-by: zhanghailiang <zhang.zhanghailiang@huawei.com>
Signed-off-by: Gonglei <arei.gonglei@huawei.com>
Signed-off-by: Li Zhijian <lizhijian@cn.fujitsu.com>
Reviewed-by: Dr. David Alan Gilbert <dgilbert@redhat.com>
Cc: Dr. David Alan Gilbert <dgilbert@redhat.com>
---
v17:
- Rebase to master, use the new channel-buffer API
v16:
- Rename colo_put_cmd_value() to colo_send_message_value()
v13:
- Refactor colo_put_cmd_value() to use 'Error **errp' to indicate success
  or failure.
v12:
- Replace the old colo_ctl_get() with the new helper function colo_put_cmd_value()
v11:
- Add Reviewed-by tag
---
 migration/colo.c | 83 ++++++++++++++++++++++++++++++++++++++++++++++++++------
 migration/ram.c  | 39 +++++++++++++++++++-------
 2 files changed, 104 insertions(+), 18 deletions(-)

diff --git a/migration/colo.c b/migration/colo.c
index 1cf0159..ec43250 100644
--- a/migration/colo.c
+++ b/migration/colo.c
@@ -13,10 +13,13 @@
 #include "qemu/osdep.h"
 #include "sysemu/sysemu.h"
 #include "migration/colo.h"
+#include "io/channel-buffer.h"
 #include "trace.h"
 #include "qemu/error-report.h"
 #include "qapi/error.h"
 
+#define COLO_BUFFER_BASE_SIZE (4 * 1024 * 1024)
+
 bool colo_supported(void)
 {
     return true;
@@ -55,6 +58,27 @@ static void colo_send_message(QEMUFile *f, COLOMessage msg,
     trace_colo_send_message(COLOMessage_lookup[msg]);
 }
 
+static void colo_send_message_value(QEMUFile *f, COLOMessage msg,
+                                    uint64_t value, Error **errp)
+{
+    Error *local_err = NULL;
+    int ret;
+
+    colo_send_message(f, msg, &local_err);
+    if (local_err) {
+        error_propagate(errp, local_err);
+        return;
+    }
+    qemu_put_be64(f, value);
+    qemu_fflush(f);
+
+    ret = qemu_file_get_error(f);
+    if (ret < 0) {
+        error_setg_errno(errp, -ret, "Failed to send value for message:%s",
+                         COLOMessage_lookup[msg]);
+    }
+}
+
 static COLOMessage colo_receive_message(QEMUFile *f, Error **errp)
 {
     COLOMessage msg;
@@ -91,9 +115,12 @@ static void colo_receive_check_message(QEMUFile *f, COLOMessage expect_msg,
     }
 }
 
-static int colo_do_checkpoint_transaction(MigrationState *s)
+static int colo_do_checkpoint_transaction(MigrationState *s,
+                                          QIOChannelBuffer *bioc,
+                                          QEMUFile *fb)
 {
     Error *local_err = NULL;
+    int ret = -1;
 
     colo_send_message(s->to_dst_file, COLO_MESSAGE_CHECKPOINT_REQUEST,
                       &local_err);
@@ -106,15 +133,46 @@ static int colo_do_checkpoint_transaction(MigrationState *s)
     if (local_err) {
         goto out;
     }
+    /* Reset channel-buffer directly */
+    qio_channel_io_seek(QIO_CHANNEL(bioc), 0, 0, NULL);
+    bioc->usage = 0;
+
+    qemu_mutex_lock_iothread();
+    vm_stop_force_state(RUN_STATE_COLO);
+    qemu_mutex_unlock_iothread();
+    trace_colo_vm_state_change("run", "stop");
 
-    /* TODO: suspend and save vm state to colo buffer */
+    /* Disable block migration */
+    s->params.blk = 0;
+    s->params.shared = 0;
+    qemu_savevm_state_header(fb);
+    qemu_savevm_state_begin(fb, &s->params);
+    qemu_mutex_lock_iothread();
+    qemu_savevm_state_complete_precopy(fb, false);
+    qemu_mutex_unlock_iothread();
+
+    qemu_fflush(fb);
 
     colo_send_message(s->to_dst_file, COLO_MESSAGE_VMSTATE_SEND, &local_err);
     if (local_err) {
         goto out;
     }
+    /*
+     * We need the size of the VMstate data in Secondary side,
+     * With which we can decide how much data should be read.
+     */
+    colo_send_message_value(s->to_dst_file, COLO_MESSAGE_VMSTATE_SIZE,
+                            bioc->usage, &local_err);
+    if (local_err) {
+        goto out;
+    }
 
-    /* TODO: send vmstate to Secondary */
+    qemu_put_buffer(s->to_dst_file, bioc->data, bioc->usage);
+    qemu_fflush(s->to_dst_file);
+    ret = qemu_file_get_error(s->to_dst_file);
+    if (ret < 0) {
+        goto out;
+    }
 
     colo_receive_check_message(s->rp_state.from_dst_file,
                        COLO_MESSAGE_VMSTATE_RECEIVED, &local_err);
@@ -128,18 +186,24 @@ static int colo_do_checkpoint_transaction(MigrationState *s)
         goto out;
     }
 
-    /* TODO: resume Primary */
+    ret = 0;
+
+    qemu_mutex_lock_iothread();
+    vm_start();
+    qemu_mutex_unlock_iothread();
+    trace_colo_vm_state_change("stop", "run");
 
-    return 0;
 out:
     if (local_err) {
         error_report_err(local_err);
     }
-    return -EINVAL;
+    return ret;
 }
 
 static void colo_process_checkpoint(MigrationState *s)
 {
+    QIOChannelBuffer *bioc;
+    QEMUFile *fb = NULL;
     Error *local_err = NULL;
     int ret;
 
@@ -158,6 +222,9 @@ static void colo_process_checkpoint(MigrationState *s)
     if (local_err) {
         goto out;
     }
+    bioc = qio_channel_buffer_new(COLO_BUFFER_BASE_SIZE);
+    fb = qemu_fopen_channel_output(QIO_CHANNEL(bioc));
+    object_unref(OBJECT(bioc));
 
     qemu_mutex_lock_iothread();
     vm_start();
@@ -165,7 +232,7 @@ static void colo_process_checkpoint(MigrationState *s)
     trace_colo_vm_state_change("stop", "run");
 
     while (s->state == MIGRATION_STATUS_COLO) {
-        ret = colo_do_checkpoint_transaction(s);
+        ret = colo_do_checkpoint_transaction(s, bioc, fb);
         if (ret < 0) {
             goto out;
         }
@@ -178,7 +245,7 @@ out:
     }
     migrate_set_state(&s->state, MIGRATION_STATUS_COLO,
                       MIGRATION_STATUS_COMPLETED);
-
+    qemu_fclose(fb);
     if (s->rp_state.from_dst_file) {
         qemu_fclose(s->rp_state.from_dst_file);
     }
diff --git a/migration/ram.c b/migration/ram.c
index 815bc0e..e9067c5 100644
--- a/migration/ram.c
+++ b/migration/ram.c
@@ -43,6 +43,7 @@
 #include "trace.h"
 #include "exec/ram_addr.h"
 #include "qemu/rcu_queue.h"
+#include "migration/colo.h"
 
 #ifdef DEBUG_MIGRATION_RAM
 #define DPRINTF(fmt, ...) \
@@ -1868,16 +1869,8 @@ err:
     return ret;
 }
 
-
-/* Each of ram_save_setup, ram_save_iterate and ram_save_complete has
- * long-running RCU critical section.  When rcu-reclaims in the code
- * start to become numerous it will be necessary to reduce the
- * granularity of these critical sections.
- */
-
-static int ram_save_setup(QEMUFile *f, void *opaque)
+static int ram_save_init_globals(void)
 {
-    RAMBlock *block;
     int64_t ram_bitmap_pages; /* Size of bitmap in pages, including gaps */
 
     dirty_rate_high_cnt = 0;
@@ -1943,6 +1936,31 @@ static int ram_save_setup(QEMUFile *f, void *opaque)
     migration_bitmap_sync();
     qemu_mutex_unlock_ramlist();
     qemu_mutex_unlock_iothread();
+    rcu_read_unlock();
+
+    return 0;
+}
+
+/* Each of ram_save_setup, ram_save_iterate and ram_save_complete has
+ * long-running RCU critical section.  When rcu-reclaims in the code
+ * start to become numerous it will be necessary to reduce the
+ * granularity of these critical sections.
+ */
+
+static int ram_save_setup(QEMUFile *f, void *opaque)
+{
+    RAMBlock *block;
+
+    /*
+     * migration has already setup the bitmap, reuse it.
+     */
+    if (!migration_in_colo_state()) {
+        if (ram_save_init_globals() < 0) {
+            return -1;
+         }
+    }
+
+    rcu_read_lock();
 
     qemu_put_be64(f, ram_bytes_total() | RAM_SAVE_FLAG_MEM_SIZE);
 
@@ -2044,7 +2062,8 @@ static int ram_save_complete(QEMUFile *f, void *opaque)
     while (true) {
         int pages;
 
-        pages = ram_find_and_save_block(f, true, &bytes_transferred);
+        pages = ram_find_and_save_block(f, !migration_in_colo_state(),
+                                        &bytes_transferred);
         /* no more blocks to sent */
         if (pages == 0) {
             break;
-- 
1.8.3.1

  parent reply	other threads:[~2016-08-03 12:27 UTC|newest]

Thread overview: 48+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2016-08-03 12:25 [Qemu-devel] [PATCH COLO-Frame v18 00/34] COarse-grain LOck-stepping(COLO) Virtual Machines for Non-stop Service (FT) zhanghailiang
2016-08-03 12:25 ` [Qemu-devel] [PATCH COLO-Frame v18 01/34] configure: Add parameter for configure to enable/disable COLO support zhanghailiang
2016-08-25 21:45   ` Amit Shah
2016-09-01  3:26     ` Hailiang Zhang
2016-08-03 12:25 ` [Qemu-devel] [PATCH COLO-Frame v18 02/34] migration: Introduce capability 'x-colo' to migration zhanghailiang
2016-08-25 21:47   ` Amit Shah
2016-09-01  3:27     ` Hailiang Zhang
2016-08-03 12:25 ` [Qemu-devel] [PATCH COLO-Frame v18 03/34] COLO: migrate colo related info to secondary node zhanghailiang
2016-08-03 12:25 ` [Qemu-devel] [PATCH COLO-Frame v18 04/34] migration: Integrate COLO checkpoint process into migration zhanghailiang
2016-08-03 12:25 ` [Qemu-devel] [PATCH COLO-Frame v18 05/34] migration: Integrate COLO checkpoint process into loadvm zhanghailiang
2016-08-03 12:25 ` [Qemu-devel] [PATCH COLO-Frame v18 06/34] COLO/migration: Create a new communication path from destination to source zhanghailiang
2016-08-03 12:25 ` [Qemu-devel] [PATCH COLO-Frame v18 07/34] COLO: Implement COLO checkpoint protocol zhanghailiang
2016-08-03 12:25 ` [Qemu-devel] [PATCH COLO-Frame v18 08/34] COLO: Add a new RunState RUN_STATE_COLO zhanghailiang
2016-08-03 12:25 ` zhanghailiang [this message]
2016-08-03 12:25 ` [Qemu-devel] [PATCH COLO-Frame v18 10/34] COLO: Load PVM's dirty pages into SVM's RAM cache temporarily zhanghailiang
2016-08-03 12:25 ` [Qemu-devel] [PATCH COLO-Frame v18 11/34] ram/COLO: Record the dirty pages that SVM received zhanghailiang
2016-08-03 12:25 ` [Qemu-devel] [PATCH COLO-Frame v18 12/34] COLO: Load VMState into buffer before restore it zhanghailiang
2016-08-05 17:53   ` Dr. David Alan Gilbert
2016-08-08  8:52     ` Daniel P. Berrange
2016-08-03 12:25 ` [Qemu-devel] [PATCH COLO-Frame v18 13/34] COLO: Flush PVM's cached RAM into SVM's memory zhanghailiang
2016-08-03 12:25 ` [Qemu-devel] [PATCH COLO-Frame v18 14/34] COLO: Add checkpoint-delay parameter for migrate-set-parameters zhanghailiang
2016-08-03 12:25 ` [Qemu-devel] [PATCH COLO-Frame v18 15/34] COLO: Synchronize PVM's state to SVM periodically zhanghailiang
2016-08-03 12:25 ` [Qemu-devel] [PATCH COLO-Frame v18 16/34] COLO failover: Introduce a new command to trigger a failover zhanghailiang
2016-08-03 12:25 ` [Qemu-devel] [PATCH COLO-Frame v18 17/34] COLO failover: Introduce state to record failover process zhanghailiang
2016-08-09  9:17   ` Dr. David Alan Gilbert
2016-08-10  4:07     ` Hailiang Zhang
2016-08-03 12:25 ` [Qemu-devel] [PATCH COLO-Frame v18 18/34] COLO: Implement failover work for Primary VM zhanghailiang
2016-08-03 12:25 ` [Qemu-devel] [PATCH COLO-Frame v18 19/34] COLO: Implement failover work for Secondary VM zhanghailiang
2016-08-03 12:25 ` [Qemu-devel] [PATCH COLO-Frame v18 20/34] qmp event: Add COLO_EXIT event to notify users while exited from COLO zhanghailiang
2016-08-03 12:25 ` [Qemu-devel] [PATCH COLO-Frame v18 21/34] COLO failover: Shutdown related socket fd when do failover zhanghailiang
2016-08-03 12:26 ` [Qemu-devel] [PATCH COLO-Frame v18 22/34] COLO failover: Don't do failover during loading VM's state zhanghailiang
2016-08-03 12:26 ` [Qemu-devel] [PATCH COLO-Frame v18 23/34] COLO: Process shutdown command for VM in COLO state zhanghailiang
2016-08-03 12:26 ` [Qemu-devel] [PATCH COLO-Frame v18 24/34] COLO: Update the global runstate after going into colo state zhanghailiang
2016-08-03 12:26 ` [Qemu-devel] [PATCH COLO-Frame v18 25/34] savevm: Introduce two helper functions for save/find loadvm_handlers entry zhanghailiang
2016-08-03 12:26 ` [Qemu-devel] [PATCH COLO-Frame v18 26/34] migration/savevm: Add new helpers to process the different stages of loadvm zhanghailiang
2016-08-03 12:26 ` [Qemu-devel] [PATCH COLO-Frame v18 27/34] migration/savevm: Export two helper functions for savevm process zhanghailiang
2016-08-03 12:26 ` [Qemu-devel] [PATCH COLO-Frame v18 28/34] COLO: Separate the process of saving/loading ram and device state zhanghailiang
2016-08-03 12:26 ` [Qemu-devel] [PATCH COLO-Frame v18 29/34] COLO: Split qemu_savevm_state_begin out of checkpoint process zhanghailiang
2016-08-03 12:26 ` [Qemu-devel] [PATCH COLO-Frame v18 30/34] filter-buffer: Accept zero interval zhanghailiang
2016-08-03 12:26 ` [Qemu-devel] [PATCH COLO-Frame v18 31/34] net: Add notifier/callback for netdev init zhanghailiang
2016-08-03 12:26 ` [Qemu-devel] [PATCH COLO-Frame v18 32/34] COLO/filter: Add each netdev a buffer filter zhanghailiang
2016-08-03 12:26 ` [Qemu-devel] [PATCH COLO-Frame v18 33/34] COLO: Control the status of buffer filters for PVM zhanghailiang
2016-08-03 12:26 ` [Qemu-devel] [PATCH COLO-Frame v18 34/34] COLO: Add block replication into colo process zhanghailiang
2016-08-16  0:00 ` [Qemu-devel] [PATCH COLO-Frame v18 00/34] COarse-grain LOck-stepping(COLO) Virtual Machines for Non-stop Service (FT) Changlong Xie
2016-08-16 10:51   ` Hailiang Zhang
     [not found] ` <CAEH94Lju9VSjxo_32yX2iTJngapfDiKQrSXVHa6G6S05yCFWeg@mail.gmail.com>
2016-08-17  5:46   ` Changlong Xie
2016-08-25 21:52 ` Amit Shah
2016-09-01  8:03   ` Hailiang Zhang

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=1470227172-13704-10-git-send-email-zhang.zhanghailiang@huawei.com \
    --to=zhang.zhanghailiang@huawei.com \
    --cc=amit.shah@redhat.com \
    --cc=arei.gonglei@huawei.com \
    --cc=dgilbert@redhat.com \
    --cc=eddie.dong@intel.com \
    --cc=lizhijian@cn.fujitsu.com \
    --cc=peter.huangpeng@huawei.com \
    --cc=qemu-devel@nongnu.org \
    --cc=quintela@redhat.com \
    --cc=wency@cn.fujitsu.com \
    --cc=xiecl.fnst@cn.fujitsu.com \
    --cc=zhangchen.fnst@cn.fujitsu.com \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.