All of lore.kernel.org
 help / color / mirror / Atom feed
From: Andrew Cooper <andrew.cooper3@citrix.com>
To: Xen-devel <xen-devel@lists.xen.org>
Cc: Andrew Cooper <andrew.cooper3@citrix.com>
Subject: [Patch v6 10/13] tools/libxc: x86 HVM save code
Date: Mon, 7 Jul 2014 18:37:59 +0100	[thread overview]
Message-ID: <1404754682-28379-11-git-send-email-andrew.cooper3@citrix.com> (raw)
In-Reply-To: <1404754682-28379-1-git-send-email-andrew.cooper3@citrix.com>

Save the x86 HVM specific parts of the domain.  This is considerably simpler
than an x86 PV domain.  Only the HVM_CONTEXT and HVM_PARAMS records are
needed.

There is no need for any page normalisation.

Signed-off-by: Andrew Cooper <andrew.cooper3@citrix.com>
---
 tools/libxc/saverestore/common.h       |    1 +
 tools/libxc/saverestore/save_x86_hvm.c |  255 ++++++++++++++++++++++++++++++++
 2 files changed, 256 insertions(+)
 create mode 100644 tools/libxc/saverestore/save_x86_hvm.c

diff --git a/tools/libxc/saverestore/common.h b/tools/libxc/saverestore/common.h
index 7536b08..8d125f9 100644
--- a/tools/libxc/saverestore/common.h
+++ b/tools/libxc/saverestore/common.h
@@ -238,6 +238,7 @@ struct xc_sr_context
 };
 
 extern struct xc_sr_save_ops save_ops_x86_pv;
+extern struct xc_sr_save_ops save_ops_x86_hvm;
 
 extern struct xc_sr_restore_ops restore_ops_x86_pv;
 
diff --git a/tools/libxc/saverestore/save_x86_hvm.c b/tools/libxc/saverestore/save_x86_hvm.c
new file mode 100644
index 0000000..5c8052f
--- /dev/null
+++ b/tools/libxc/saverestore/save_x86_hvm.c
@@ -0,0 +1,255 @@
+#include <assert.h>
+
+#include "common_x86.h"
+
+#include <xen/hvm/params.h>
+
+/*
+ * Query for the HVM context and write an HVM_CONTEXT record into the stream.
+ */
+static int write_hvm_context(struct xc_sr_context *ctx)
+{
+    xc_interface *xch = ctx->xch;
+    unsigned long hvm_buf_size;
+    int rc;
+    struct xc_sr_record hvm_rec =
+    {
+        .type = REC_TYPE_HVM_CONTEXT,
+    };
+
+    hvm_buf_size = xc_domain_hvm_getcontext(xch, ctx->domid, 0, 0);
+    if ( hvm_buf_size == -1 )
+    {
+        PERROR("Couldn't get HVM context size from Xen");
+        rc = -1;
+        goto out;
+    }
+
+    hvm_rec.data = malloc(hvm_buf_size);
+    if ( !hvm_rec.data )
+    {
+        PERROR("Couldn't allocate memory");
+        rc = -1;
+        goto out;
+    }
+
+    hvm_rec.length = xc_domain_hvm_getcontext(xch, ctx->domid,
+                                              hvm_rec.data, hvm_buf_size);
+    if ( hvm_rec.length < 0 )
+    {
+        PERROR("HVM:Could not get hvm buffer");
+        rc = -1;
+        goto out;
+    }
+
+    rc = write_record(ctx, &hvm_rec);
+    if ( rc < 0 )
+    {
+        PERROR("error write HVM_CONTEXT record");
+        goto out;
+    }
+
+ out:
+    free(hvm_rec.data);
+    return rc;
+}
+
+/*
+ * Query for a range of HVM parameters and write an HVM_PARAMS record into the
+ * stream.
+ */
+static int write_hvm_params(struct xc_sr_context *ctx)
+{
+    static const unsigned int params[] = {
+        HVM_PARAM_STORE_PFN,
+        HVM_PARAM_IOREQ_PFN,
+        HVM_PARAM_BUFIOREQ_PFN,
+        HVM_PARAM_PAGING_RING_PFN,
+        HVM_PARAM_ACCESS_RING_PFN,
+        HVM_PARAM_SHARING_RING_PFN,
+        HVM_PARAM_VM86_TSS,
+        HVM_PARAM_CONSOLE_PFN,
+        HVM_PARAM_ACPI_IOPORTS_LOCATION,
+        HVM_PARAM_VIRIDIAN,
+        HVM_PARAM_IDENT_PT,
+        HVM_PARAM_PAE_ENABLED,
+        HVM_PARAM_VM_GENERATION_ID_ADDR,
+        HVM_PARAM_IOREQ_SERVER_PFN,
+        HVM_PARAM_NR_IOREQ_SERVER_PAGES,
+    };
+
+    xc_interface *xch = ctx->xch;
+    struct xc_sr_rec_hvm_params_entry entries[ARRAY_SIZE(params)];
+    struct xc_sr_rec_hvm_params hdr = {
+        .count = 0,
+    };
+    struct xc_sr_record rec = {
+        .type   = REC_TYPE_HVM_PARAMS,
+        .length = sizeof(hdr),
+        .data   = &hdr,
+    };
+    unsigned int i;
+    int rc;
+
+    for ( i = 0; i < ARRAY_SIZE(params); i++ )
+    {
+        uint32_t index = params[i];
+        uint64_t value;
+
+        rc = xc_get_hvm_param(xch, ctx->domid, index, (unsigned long *)&value);
+        if ( rc )
+        {
+            /* Gross XenServer hack. Consider HVM_PARAM_CONSOLE_PFN failure
+             * nonfatal. This is related to the fact it is impossible to
+             * distinguish "no console" from a console at pfn/evtchn 0.
+             *
+             * TODO - find a compatible way to fix this.
+             */
+            if ( index == HVM_PARAM_CONSOLE_PFN )
+                continue;
+
+            PERROR("Failed to get HVMPARAM at index %u", index);
+            return rc;
+        }
+
+        if ( value != 0 )
+        {
+            entries[hdr.count].index = index;
+            entries[hdr.count].value = value;
+            hdr.count++;
+        }
+    }
+
+    rc = write_split_record(ctx, &rec, entries, hdr.count * sizeof(*entries));
+    if ( rc )
+        PERROR("Failed to write HVM_PARAMS record");
+
+    return rc;
+}
+
+/* TODO - remove. */
+static int write_toolstack(struct xc_sr_context *ctx)
+{
+    xc_interface *xch = ctx->xch;
+    struct xc_sr_record rec = {
+        .type = REC_TYPE_TOOLSTACK,
+        .length = 0,
+    };
+    uint8_t *buf;
+    uint32_t len;
+    int rc;
+
+    if ( !ctx->save.callbacks || !ctx->save.callbacks->toolstack_save )
+        return 0;
+
+    if ( ctx->save.callbacks->toolstack_save(ctx->domid, &buf, &len, ctx->save.callbacks->data) < 0 )
+    {
+        PERROR("Error calling toolstack_save");
+        return -1;
+    }
+
+    rc = write_split_record(ctx, &rec, buf, len);
+    if ( rc < 0 )
+        PERROR("Error writing TOOLSTACK record");
+    free(buf);
+    return rc;
+}
+
+static xen_pfn_t x86_hvm_pfn_to_gfn(const struct xc_sr_context *ctx, xen_pfn_t pfn)
+{
+    /* identify map */
+    return pfn;
+}
+
+static int x86_hvm_normalise_page(struct xc_sr_context *ctx, xen_pfn_t type, void **page)
+{
+    /* no-op */
+    return 0;
+}
+
+static int x86_hvm_setup(struct xc_sr_context *ctx)
+{
+    xc_interface *xch = ctx->xch;
+
+    if ( !ctx->save.callbacks->switch_qemu_logdirty )
+    {
+        ERROR("No switch_qemu_logdirty callback provided");
+        errno = EINVAL;
+        return -1;
+    }
+
+    if ( ctx->save.callbacks->switch_qemu_logdirty(
+             ctx->domid, 1, ctx->save.callbacks->data) )
+    {
+        PERROR("Couldn't enable qemu log-dirty mode");
+        return -1;
+    }
+
+    return 0;
+}
+
+static int x86_hvm_start_of_stream(struct xc_sr_context *ctx)
+{
+    /* no-op */
+    return 0;
+}
+
+static int x86_hvm_end_of_stream(struct xc_sr_context *ctx)
+{
+    int rc;
+
+    rc = write_tsc_info(ctx);
+    if ( rc )
+        return rc;
+
+    /* TODO - remove. */
+    rc = write_toolstack(ctx);
+    if ( rc )
+        return rc;
+
+    /* Write the HVM_CONTEXT record. */
+    rc = write_hvm_context(ctx);
+    if ( rc )
+        return rc;
+
+    /* Write HVM_PARAMS record contains applicable HVM params. */
+    rc = write_hvm_params(ctx);
+    if ( rc )
+        return rc;
+
+    return rc;
+}
+
+static int x86_hvm_cleanup(struct xc_sr_context *ctx)
+{
+    xc_interface *xch = ctx->xch;
+
+    if ( ctx->save.callbacks->switch_qemu_logdirty(
+             ctx->domid, 0, ctx->save.callbacks->data) )
+    {
+        PERROR("Couldn't disable qemu log-dirty mode");
+        return -1;
+    }
+
+    return 0;
+}
+
+struct xc_sr_save_ops save_ops_x86_hvm =
+{
+    .pfn_to_gfn      = x86_hvm_pfn_to_gfn,
+    .normalise_page  = x86_hvm_normalise_page,
+    .setup           = x86_hvm_setup,
+    .start_of_stream = x86_hvm_start_of_stream,
+    .end_of_stream   = x86_hvm_end_of_stream,
+    .cleanup         = x86_hvm_cleanup,
+};
+
+/*
+ * Local variables:
+ * mode: C
+ * c-file-style: "BSD"
+ * c-basic-offset: 4
+ * tab-width: 4
+ * indent-tabs-mode: nil
+ * End:
+ */
-- 
1.7.10.4

  parent reply	other threads:[~2014-07-07 17:37 UTC|newest]

Thread overview: 38+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2014-07-07 17:37 [PATCH v6 0/13] Migration Stream v2 Andrew Cooper
2014-07-07 17:37 ` [Patch v6 01/13] docs: libxc migration stream specification Andrew Cooper
2014-07-08  3:53   ` Hongyang Yang
2014-07-08  8:48     ` Andrew Cooper
2014-07-08  8:59       ` Hongyang Yang
2014-07-08  9:36   ` David Vrabel
2014-07-08 10:48     ` Andrew Cooper
2014-07-07 17:37 ` [Patch v6 02/13] tools/python: Scripts relating to migrationv2 streams Andrew Cooper
2014-07-28 15:20   ` Ian Campbell
2014-07-28 15:38     ` Andrew Cooper
2014-07-28 15:58       ` Ian Campbell
2014-07-29 13:55         ` Jon Ludlam
2014-07-07 17:37 ` [Patch v6 03/13] [HACK] tools/libxc: save/restore v2 framework Andrew Cooper
2014-07-07 17:37 ` [Patch v6 04/13] tools/libxc: C implementation of stream format Andrew Cooper
2014-07-07 17:37 ` [Patch v6 05/13] tools/libxc: noarch common code Andrew Cooper
2014-07-07 17:37 ` [Patch v6 06/13] tools/libxc: x86 " Andrew Cooper
2014-07-07 17:37 ` [Patch v6 07/13] tools/libxc: x86 PV " Andrew Cooper
2014-07-07 17:37 ` [Patch v6 08/13] tools/libxc: x86 PV save code Andrew Cooper
2014-07-07 17:37 ` [Patch v6 09/13] tools/libxc: x86 PV restore code Andrew Cooper
2014-07-07 17:37 ` Andrew Cooper [this message]
2014-07-07 17:38 ` [Patch v6 11/13] tools/libxc: x86 HVM " Andrew Cooper
2014-07-18 14:38   ` Wen Congyang
2014-07-18 15:09     ` Andrew Cooper
2014-07-18 15:42       ` Paul Durrant
2014-07-18 16:13         ` Wen Congyang
2014-07-07 17:38 ` [Patch v6 12/13] tools/libxc: noarch save code Andrew Cooper
2014-07-07 17:38 ` [Patch v6 13/13] tools/libxc: noarch restore code Andrew Cooper
2014-07-08 10:50 ` [PATCH v6 0/13] Migration Stream v2 David Vrabel
2014-07-08 11:10   ` Ian Campbell
2014-07-08 16:35 ` Konrad Rzeszutek Wilk
2014-07-08 17:35   ` Andrew Cooper
2014-07-09  6:01     ` Hongyang Yang
2014-07-09  9:40       ` Andrew Cooper
2014-07-09 15:27         ` Konrad Rzeszutek Wilk
2014-07-10 10:19           ` Andrew Cooper
2014-07-28 15:01 ` Ian Campbell
2014-07-28 15:02   ` Andrew Cooper
2014-07-28 15:20     ` Ian Campbell

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=1404754682-28379-11-git-send-email-andrew.cooper3@citrix.com \
    --to=andrew.cooper3@citrix.com \
    --cc=xen-devel@lists.xen.org \
    /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.