On Thu, 22 Jul 2010, Owen Smith wrote:
> HVM debug console support for PV drivers
> This patch creates a shared ring buffer and event channel in HVM domains
> that the Windows PV drivers can use to send debug output.
> Modifies the HVM domain builder code to add a shared memory page for the
> ring buffer.
> Modifies the Save/Restore code to store the shared page mfn during
> save/restore
> Note: VMs saved on this patch will not restore prior to this patch. VMs saved
> prior
> to this patch will restore on this patch, without the shared console ring.
>
> # HG changeset patch
> # User Owen Smith <owen.smith@xxxxxxxxxx>
> # Date 1279633192 -3600
> # Node ID 9776b8917a3d1d75a866ed65ffc82dae8826ad76
> # Parent 12f0618400de62279bc9b111c4e2ad73e1673ca1
> imported patch pv-debug-console
>
> diff --git a/tools/libxc/xc_domain_restore.c b/tools/libxc/xc_domain_restore.c
> --- a/tools/libxc/xc_domain_restore.c
> +++ b/tools/libxc/xc_domain_restore.c
> @@ -640,6 +640,7 @@
> uint64_t vcpumap;
> uint64_t identpt;
> uint64_t vm86_tss;
> + uint64_t console_pfn;
> } pagebuf_t;
>
> static int pagebuf_init(pagebuf_t* buf)
> @@ -737,6 +738,16 @@
> return -1;
> }
> return pagebuf_get_one(xch, ctx, buf, fd, dom);
> + } else if (count == -8 ) {
> + /* Skip padding 4 bytes then read the console pfn location. */
> + if ( read_exact(fd, &buf->console_pfn, sizeof(uint32_t)) ||
> + read_exact(fd, &buf->console_pfn, sizeof(uint64_t)) )
> + {
> + PERROR("error read the address of the console pfn");
> + return -1;
> + }
> + // DPRINTF("console pfn location: %llx\n", buf->console_pfn);
> + return pagebuf_get_one(xch, ctx, buf, fd, dom);
> } else if ( (count > MAX_BATCH_SIZE) || (count < 0) ) {
> ERROR("Max batch size exceeded (%d). Giving up.", count);
> errno = EMSGSIZE;
> @@ -1055,6 +1066,7 @@
> pagebuf_t pagebuf;
> tailbuf_t tailbuf, tmptail;
> void* vcpup;
> + uint64_t console_pfn = 0;
>
> static struct restore_ctx _ctx = {
> .live_p2m = NULL,
> @@ -1207,6 +1219,8 @@
> xc_set_hvm_param(xch, dom, HVM_PARAM_IDENT_PT,
> pagebuf.identpt);
> if ( pagebuf.vm86_tss )
> xc_set_hvm_param(xch, dom, HVM_PARAM_VM86_TSS,
> pagebuf.vm86_tss);
> + if ( pagebuf.console_pfn )
> + console_pfn = pagebuf.console_pfn;
> break; /* our work here is done */
> }
>
> @@ -1715,6 +1731,19 @@
> }
> *store_mfn = tailbuf.u.hvm.magicpfns[2];
>
> + if ( console_pfn ) {
> + if ( xc_clear_domain_page(xch, dom, console_pfn) ) {
> + PERROR("error zeroing console page");
> + goto out;
> + }
> + if ( (frc = xc_set_hvm_param(xch, dom,
> + HVM_PARAM_CONSOLE_PFN, console_pfn)) ) {
> + PERROR("error setting HVM param: %i", frc);
> + goto out;
> + }
> + *console_mfn = console_pfn;
> + }
> +
> frc = xc_domain_hvm_setcontext(xch, dom, tailbuf.u.hvm.hvmbuf,
> tailbuf.u.hvm.reclen);
> if ( frc )
> diff --git a/tools/libxc/xc_domain_save.c b/tools/libxc/xc_domain_save.c
> --- a/tools/libxc/xc_domain_save.c
> +++ b/tools/libxc/xc_domain_save.c
> @@ -1587,6 +1587,17 @@
> PERROR("Error when writing the vm86 TSS for guest");
> goto out;
> }
> +
> + chunk.id = -8;
> + xc_get_hvm_param(xch, dom, HVM_PARAM_CONSOLE_PFN,
> + (unsigned long *)&chunk.data);
> +
> + if ( (chunk.data != 0) &&
> + wrexact(io_fd, &chunk, sizeof(chunk)) )
> + {
> + PERROR("Error when writing the console pfn for guest");
> + goto out;
> + }
> }
>
> /* Zero terminate */
> diff --git a/tools/libxc/xc_hvm_build.c b/tools/libxc/xc_hvm_build.c
> --- a/tools/libxc/xc_hvm_build.c
> +++ b/tools/libxc/xc_hvm_build.c
> @@ -29,7 +29,8 @@
> #define SPECIALPAGE_IOREQ 2
> #define SPECIALPAGE_IDENT_PT 3
> #define SPECIALPAGE_SHINFO 4
> -#define NR_SPECIAL_PAGES 5
> +#define SPECIALPAGE_CONSOLE 5
> +#define NR_SPECIAL_PAGES 6
> #define special_pfn(x) (0xff000u - NR_SPECIAL_PAGES + (x))
>
> static void build_hvm_info(void *hvm_info_page, uint64_t mem_size)
> @@ -375,6 +376,8 @@
> special_pfn(SPECIALPAGE_BUFIOREQ));
> xc_set_hvm_param(xch, dom, HVM_PARAM_IOREQ_PFN,
> special_pfn(SPECIALPAGE_IOREQ));
> + xc_set_hvm_param(xch, dom, HVM_PARAM_CONSOLE_PFN,
> + special_pfn(SPECIALPAGE_CONSOLE));
>
> /*
> * Identity-map page table is required for running with CR0.PG=0 when
> diff --git a/tools/libxl/libxl.c b/tools/libxl/libxl.c
> --- a/tools/libxl/libxl.c
> +++ b/tools/libxl/libxl.c
> @@ -283,6 +283,12 @@
> vments[3] = "hvm";
> vments[4] = "start_time";
> vments[5] = libxl_sprintf(ctx, "%lu.%02d",
> start_time.tv_sec,(int)start_time.tv_usec/10000);
> + // add debug channel info
> + localents = libxl_calloc(ctx, 5, sizeof(char *));
> + localents[0] = "console/port";
> + localents[1] = libxl_sprintf(ctx, "%"PRIu32, state->console_port);
> + localents[2] = "console/ring-ref";
> + localents[3] = libxl_sprintf(ctx, "%lu", state->console_mfn);
> } else {
> ret = build_pv(ctx, domid, info, state);
> if (ret) goto out;
> @@ -337,6 +343,12 @@
> vments[3] = "hvm";
> vments[4] = "start_time";
> vments[5] = libxl_sprintf(ctx, "%lu.%02d",
> start_time.tv_sec,(int)start_time.tv_usec/10000);
> + // add debug channel info
> + localents = libxl_calloc(ctx, 5, sizeof(char *));
> + localents[0] = "console/port";
> + localents[1] = libxl_sprintf(ctx, "%"PRIu32, state->console_port);
> + localents[2] = "console/ring-ref";
> + localents[3] = libxl_sprintf(ctx, "%lu", state->console_mfn);
> } else {
> vments = libxl_calloc(ctx, 11, sizeof(char *));
> i = 0;
You should use libxl_device_console_add to create the PV console
xenstore entries, like in the normal PV case: look at xl_cmdimpl.c:1247.
Make sure init_console_info and libxl_device_console_add are called in
the hvm case too.
_______________________________________________
Xen-devel mailing list
Xen-devel@xxxxxxxxxxxxxxxxxxx
http://lists.xensource.com/xen-devel
|