From: Matt Evans <matt@ozlabs.org>
To: kvm@vger.kernel.org, kvm-ppc@vger.kernel.org
Subject: [PATCH 4/8] kvm tools: Add SPAPR PPC64 HV console
Date: Tue, 06 Dec 2011 04:06:24 +0000 [thread overview]
Message-ID: <4EDD94C0.2000906@ozlabs.org> (raw)
In-Reply-To: <cover.1323143103.git.matt@ozlabs.org>
This adds the console code, plus VIO HV terminal nodes are added to
the device tree so the guest kernel will pick it up.
Signed-off-by: Matt Evans <matt@ozlabs.org>
---
tools/kvm/Makefile | 1 +
tools/kvm/powerpc/kvm.c | 31 ++++++++++++
tools/kvm/powerpc/spapr_hvcons.c | 101 ++++++++++++++++++++++++++++++++++++++
tools/kvm/powerpc/spapr_hvcons.h | 19 +++++++
4 files changed, 152 insertions(+), 0 deletions(-)
create mode 100644 tools/kvm/powerpc/spapr_hvcons.c
create mode 100644 tools/kvm/powerpc/spapr_hvcons.h
diff --git a/tools/kvm/Makefile b/tools/kvm/Makefile
index 0f24104..76cce3a 100644
--- a/tools/kvm/Makefile
+++ b/tools/kvm/Makefile
@@ -130,6 +130,7 @@ ifeq ($(uname_M), ppc64)
OBJS += powerpc/kvm-cpu.o
OBJS += powerpc/spapr_hcall.o
OBJS += powerpc/spapr_rtas.o
+ OBJS += powerpc/spapr_hvcons.o
ARCH_INCLUDE := powerpc/include
CFLAGS += -m64
LIBS += -lfdt
diff --git a/tools/kvm/powerpc/kvm.c b/tools/kvm/powerpc/kvm.c
index 2f0a921..8614538 100644
--- a/tools/kvm/powerpc/kvm.c
+++ b/tools/kvm/powerpc/kvm.c
@@ -15,6 +15,7 @@
#include "kvm/util.h"
#include "spapr.h"
+#include "spapr_hvcons.h"
#include <linux/kvm.h>
@@ -159,6 +160,8 @@ void kvm__arch_init(struct kvm *kvm, const char *kvm_dev, const char *hugetlbfs_
/* Do these before FDT setup, IRQ setup, etc. */
hypercall_init();
register_core_rtas();
+ /* Now that hypercalls are initialised, register a couple for the console: */
+ spapr_hvcons_init();
}
void kvm__irq_line(struct kvm *kvm, int irq, int level)
@@ -172,6 +175,11 @@ void kvm__irq_trigger(struct kvm *kvm, int irq)
kvm__irq_line(kvm, irq, 0);
}
+void kvm__arch_periodic_poll(struct kvm *kvm)
+{
+ spapr_hvcons_poll(kvm);
+}
+
int load_flat_binary(struct kvm *kvm, int fd_kernel, int fd_initrd, const char *kernel_cmdline)
{
void *p;
@@ -297,6 +305,13 @@ static void setup_fdt(struct kvm *kvm)
&ird_end_prop, sizeof(ird_end_prop)));
}
+ /* stdout-path: This is assuming we're using the HV console. Also, the
+ * address is hardwired until we do a VIO bus.
+ */
+ _FDT(fdt_property_string(fdt, "linux,stdout-path",
+ "/vdevice/vty@30000000"));
+ _FDT(fdt_end_node(fdt));
+
/* Memory: We don't alloc. a separate RMA yet. If we ever need to
* (CAP_PPC_RMA = 2) then have one memory node for 0->RMAsize, and
* another RMAsize->endOfMem.
@@ -369,6 +384,22 @@ static void setup_fdt(struct kvm *kvm)
}
_FDT(fdt_end_node(fdt));
+ /* VIO: See comment in linux,stdout-path; we don't yet represent a VIO
+ * bus/address allocation so addresses are hardwired here.
+ */
+ _FDT(fdt_begin_node(fdt, "vdevice"));
+ _FDT(fdt_property_cell(fdt, "#address-cells", 0x1));
+ _FDT(fdt_property_cell(fdt, "#size-cells", 0x0));
+ _FDT(fdt_property_string(fdt, "device_type", "vdevice"));
+ _FDT(fdt_property_string(fdt, "compatible", "IBM,vdevice"));
+ _FDT(fdt_begin_node(fdt, "vty@30000000"));
+ _FDT(fdt_property_string(fdt, "name", "vty"));
+ _FDT(fdt_property_string(fdt, "device_type", "serial"));
+ _FDT(fdt_property_string(fdt, "compatible", "hvterm1"));
+ _FDT(fdt_property_cell(fdt, "reg", 0x30000000));
+ _FDT(fdt_end_node(fdt));
+ _FDT(fdt_end_node(fdt));
+
/* Finalise: */
_FDT(fdt_end_node(fdt)); /* Root node */
_FDT(fdt_finish(fdt));
diff --git a/tools/kvm/powerpc/spapr_hvcons.c b/tools/kvm/powerpc/spapr_hvcons.c
new file mode 100644
index 0000000..97902ac
--- /dev/null
+++ b/tools/kvm/powerpc/spapr_hvcons.c
@@ -0,0 +1,101 @@
+/*
+ * SPAPR HV console
+ *
+ * Borrowed lightly from QEMU's spapr_vty.c, Copyright (c) 2010 David Gibson,
+ * IBM Corporation.
+ *
+ * Copyright (c) 2011 Matt Evans <matt@ozlabs.org>, IBM Corporation.
+ *
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 as published
+ * by the Free Software Foundation.
+ */
+
+#include "kvm/term.h"
+#include "kvm/kvm.h"
+#include "kvm/kvm-cpu.h"
+#include "kvm/util.h"
+#include "spapr.h"
+#include "spapr_hvcons.h"
+
+#include <stdio.h>
+#include <sys/uio.h>
+#include <errno.h>
+
+#include <linux/byteorder.h>
+
+union hv_chario {
+ struct {
+ uint64_t char0_7;
+ uint64_t char8_15;
+ } a;
+ uint8_t buf[16];
+};
+
+static unsigned long h_put_term_char(struct kvm_cpu *vcpu, unsigned long opcode, unsigned long *args)
+{
+ /* To do: Read register from args[0], and check it. */
+ unsigned long len = args[1];
+ union hv_chario data;
+ struct iovec iov;
+
+ if (len > 16) {
+ return H_PARAMETER;
+ }
+ data.a.char0_7 = cpu_to_be64(args[2]);
+ data.a.char8_15 = cpu_to_be64(args[3]);
+
+ iov.iov_base = data.buf;
+ iov.iov_len = len;
+ do {
+ int ret;
+
+ ret = term_putc_iov(CONSOLE_HV, &iov, 1, 0);
+ if (ret < 0) {
+ die("term_putc_iov error %d!\n", errno);
+ }
+ iov.iov_base += ret;
+ iov.iov_len -= ret;
+ } while (iov.iov_len > 0);
+
+ return H_SUCCESS;
+}
+
+
+static unsigned long h_get_term_char(struct kvm_cpu *vcpu, unsigned long opcode, unsigned long *args)
+{
+ /* To do: Read register from args[0], and check it. */
+ unsigned long *len = args + 0;
+ unsigned long *char0_7 = args + 1;
+ unsigned long *char8_15 = args + 2;
+ union hv_chario data;
+ struct iovec iov;
+
+ if (term_readable(CONSOLE_HV, 0)) {
+ iov.iov_base = data.buf;
+ iov.iov_len = 16;
+
+ *len = term_getc_iov(CONSOLE_HV, &iov, 1, 0);
+ *char0_7 = be64_to_cpu(data.a.char0_7);
+ *char8_15 = be64_to_cpu(data.a.char8_15);
+ } else {
+ *len = 0;
+ }
+
+ return H_SUCCESS;
+}
+
+void spapr_hvcons_poll(struct kvm *kvm)
+{
+ if (term_readable(CONSOLE_HV, 0)) {
+ /* We can inject an IRQ to guest here if we want.
+ * The guest will happily poll, though, so not required.
+ */
+ }
+}
+
+void spapr_hvcons_init(void)
+{
+ spapr_register_hypercall(H_PUT_TERM_CHAR, h_put_term_char);
+ spapr_register_hypercall(H_GET_TERM_CHAR, h_get_term_char);
+}
diff --git a/tools/kvm/powerpc/spapr_hvcons.h b/tools/kvm/powerpc/spapr_hvcons.h
new file mode 100644
index 0000000..d3e4414
--- /dev/null
+++ b/tools/kvm/powerpc/spapr_hvcons.h
@@ -0,0 +1,19 @@
+/*
+ * SPAPR HV console
+ *
+ * Copyright (c) 2011 Matt Evans <matt@ozlabs.org>, IBM Corporation.
+ *
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 as published
+ * by the Free Software Foundation.
+ */
+
+#ifndef spapr_hvcons_H
+#define spapr_hvcons_H
+
+#include "kvm/kvm.h"
+
+void spapr_hvcons_init(void);
+void spapr_hvcons_poll(struct kvm *kvm);
+
+#endif
WARNING: multiple messages have this Message-ID (diff)
From: Matt Evans <matt@ozlabs.org>
To: kvm@vger.kernel.org, kvm-ppc@vger.kernel.org
Subject: [PATCH 4/8] kvm tools: Add SPAPR PPC64 HV console
Date: Tue, 06 Dec 2011 15:06:24 +1100 [thread overview]
Message-ID: <4EDD94C0.2000906@ozlabs.org> (raw)
In-Reply-To: <cover.1323143103.git.matt@ozlabs.org>
This adds the console code, plus VIO HV terminal nodes are added to
the device tree so the guest kernel will pick it up.
Signed-off-by: Matt Evans <matt@ozlabs.org>
---
tools/kvm/Makefile | 1 +
tools/kvm/powerpc/kvm.c | 31 ++++++++++++
tools/kvm/powerpc/spapr_hvcons.c | 101 ++++++++++++++++++++++++++++++++++++++
tools/kvm/powerpc/spapr_hvcons.h | 19 +++++++
4 files changed, 152 insertions(+), 0 deletions(-)
create mode 100644 tools/kvm/powerpc/spapr_hvcons.c
create mode 100644 tools/kvm/powerpc/spapr_hvcons.h
diff --git a/tools/kvm/Makefile b/tools/kvm/Makefile
index 0f24104..76cce3a 100644
--- a/tools/kvm/Makefile
+++ b/tools/kvm/Makefile
@@ -130,6 +130,7 @@ ifeq ($(uname_M), ppc64)
OBJS += powerpc/kvm-cpu.o
OBJS += powerpc/spapr_hcall.o
OBJS += powerpc/spapr_rtas.o
+ OBJS += powerpc/spapr_hvcons.o
ARCH_INCLUDE := powerpc/include
CFLAGS += -m64
LIBS += -lfdt
diff --git a/tools/kvm/powerpc/kvm.c b/tools/kvm/powerpc/kvm.c
index 2f0a921..8614538 100644
--- a/tools/kvm/powerpc/kvm.c
+++ b/tools/kvm/powerpc/kvm.c
@@ -15,6 +15,7 @@
#include "kvm/util.h"
#include "spapr.h"
+#include "spapr_hvcons.h"
#include <linux/kvm.h>
@@ -159,6 +160,8 @@ void kvm__arch_init(struct kvm *kvm, const char *kvm_dev, const char *hugetlbfs_
/* Do these before FDT setup, IRQ setup, etc. */
hypercall_init();
register_core_rtas();
+ /* Now that hypercalls are initialised, register a couple for the console: */
+ spapr_hvcons_init();
}
void kvm__irq_line(struct kvm *kvm, int irq, int level)
@@ -172,6 +175,11 @@ void kvm__irq_trigger(struct kvm *kvm, int irq)
kvm__irq_line(kvm, irq, 0);
}
+void kvm__arch_periodic_poll(struct kvm *kvm)
+{
+ spapr_hvcons_poll(kvm);
+}
+
int load_flat_binary(struct kvm *kvm, int fd_kernel, int fd_initrd, const char *kernel_cmdline)
{
void *p;
@@ -297,6 +305,13 @@ static void setup_fdt(struct kvm *kvm)
&ird_end_prop, sizeof(ird_end_prop)));
}
+ /* stdout-path: This is assuming we're using the HV console. Also, the
+ * address is hardwired until we do a VIO bus.
+ */
+ _FDT(fdt_property_string(fdt, "linux,stdout-path",
+ "/vdevice/vty@30000000"));
+ _FDT(fdt_end_node(fdt));
+
/* Memory: We don't alloc. a separate RMA yet. If we ever need to
* (CAP_PPC_RMA == 2) then have one memory node for 0->RMAsize, and
* another RMAsize->endOfMem.
@@ -369,6 +384,22 @@ static void setup_fdt(struct kvm *kvm)
}
_FDT(fdt_end_node(fdt));
+ /* VIO: See comment in linux,stdout-path; we don't yet represent a VIO
+ * bus/address allocation so addresses are hardwired here.
+ */
+ _FDT(fdt_begin_node(fdt, "vdevice"));
+ _FDT(fdt_property_cell(fdt, "#address-cells", 0x1));
+ _FDT(fdt_property_cell(fdt, "#size-cells", 0x0));
+ _FDT(fdt_property_string(fdt, "device_type", "vdevice"));
+ _FDT(fdt_property_string(fdt, "compatible", "IBM,vdevice"));
+ _FDT(fdt_begin_node(fdt, "vty@30000000"));
+ _FDT(fdt_property_string(fdt, "name", "vty"));
+ _FDT(fdt_property_string(fdt, "device_type", "serial"));
+ _FDT(fdt_property_string(fdt, "compatible", "hvterm1"));
+ _FDT(fdt_property_cell(fdt, "reg", 0x30000000));
+ _FDT(fdt_end_node(fdt));
+ _FDT(fdt_end_node(fdt));
+
/* Finalise: */
_FDT(fdt_end_node(fdt)); /* Root node */
_FDT(fdt_finish(fdt));
diff --git a/tools/kvm/powerpc/spapr_hvcons.c b/tools/kvm/powerpc/spapr_hvcons.c
new file mode 100644
index 0000000..97902ac
--- /dev/null
+++ b/tools/kvm/powerpc/spapr_hvcons.c
@@ -0,0 +1,101 @@
+/*
+ * SPAPR HV console
+ *
+ * Borrowed lightly from QEMU's spapr_vty.c, Copyright (c) 2010 David Gibson,
+ * IBM Corporation.
+ *
+ * Copyright (c) 2011 Matt Evans <matt@ozlabs.org>, IBM Corporation.
+ *
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 as published
+ * by the Free Software Foundation.
+ */
+
+#include "kvm/term.h"
+#include "kvm/kvm.h"
+#include "kvm/kvm-cpu.h"
+#include "kvm/util.h"
+#include "spapr.h"
+#include "spapr_hvcons.h"
+
+#include <stdio.h>
+#include <sys/uio.h>
+#include <errno.h>
+
+#include <linux/byteorder.h>
+
+union hv_chario {
+ struct {
+ uint64_t char0_7;
+ uint64_t char8_15;
+ } a;
+ uint8_t buf[16];
+};
+
+static unsigned long h_put_term_char(struct kvm_cpu *vcpu, unsigned long opcode, unsigned long *args)
+{
+ /* To do: Read register from args[0], and check it. */
+ unsigned long len = args[1];
+ union hv_chario data;
+ struct iovec iov;
+
+ if (len > 16) {
+ return H_PARAMETER;
+ }
+ data.a.char0_7 = cpu_to_be64(args[2]);
+ data.a.char8_15 = cpu_to_be64(args[3]);
+
+ iov.iov_base = data.buf;
+ iov.iov_len = len;
+ do {
+ int ret;
+
+ ret = term_putc_iov(CONSOLE_HV, &iov, 1, 0);
+ if (ret < 0) {
+ die("term_putc_iov error %d!\n", errno);
+ }
+ iov.iov_base += ret;
+ iov.iov_len -= ret;
+ } while (iov.iov_len > 0);
+
+ return H_SUCCESS;
+}
+
+
+static unsigned long h_get_term_char(struct kvm_cpu *vcpu, unsigned long opcode, unsigned long *args)
+{
+ /* To do: Read register from args[0], and check it. */
+ unsigned long *len = args + 0;
+ unsigned long *char0_7 = args + 1;
+ unsigned long *char8_15 = args + 2;
+ union hv_chario data;
+ struct iovec iov;
+
+ if (term_readable(CONSOLE_HV, 0)) {
+ iov.iov_base = data.buf;
+ iov.iov_len = 16;
+
+ *len = term_getc_iov(CONSOLE_HV, &iov, 1, 0);
+ *char0_7 = be64_to_cpu(data.a.char0_7);
+ *char8_15 = be64_to_cpu(data.a.char8_15);
+ } else {
+ *len = 0;
+ }
+
+ return H_SUCCESS;
+}
+
+void spapr_hvcons_poll(struct kvm *kvm)
+{
+ if (term_readable(CONSOLE_HV, 0)) {
+ /* We can inject an IRQ to guest here if we want.
+ * The guest will happily poll, though, so not required.
+ */
+ }
+}
+
+void spapr_hvcons_init(void)
+{
+ spapr_register_hypercall(H_PUT_TERM_CHAR, h_put_term_char);
+ spapr_register_hypercall(H_GET_TERM_CHAR, h_get_term_char);
+}
diff --git a/tools/kvm/powerpc/spapr_hvcons.h b/tools/kvm/powerpc/spapr_hvcons.h
new file mode 100644
index 0000000..d3e4414
--- /dev/null
+++ b/tools/kvm/powerpc/spapr_hvcons.h
@@ -0,0 +1,19 @@
+/*
+ * SPAPR HV console
+ *
+ * Copyright (c) 2011 Matt Evans <matt@ozlabs.org>, IBM Corporation.
+ *
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 as published
+ * by the Free Software Foundation.
+ */
+
+#ifndef spapr_hvcons_H
+#define spapr_hvcons_H
+
+#include "kvm/kvm.h"
+
+void spapr_hvcons_init(void);
+void spapr_hvcons_poll(struct kvm *kvm);
+
+#endif
next prev parent reply other threads:[~2011-12-06 4:06 UTC|newest]
Thread overview: 28+ messages / expand[flat|nested] mbox.gz Atom feed top
[not found] <cover.1323143103.git.matt@ozlabs.org>
2011-12-06 4:05 ` [PATCH 1/8] kvm tools: Add initial SPAPR PPC64 architecture support Matt Evans
2011-12-06 4:05 ` Matt Evans
2011-12-06 18:03 ` Scott Wood
2011-12-06 18:03 ` Scott Wood
2011-12-06 18:33 ` Pekka Enberg
2011-12-06 18:33 ` Pekka Enberg
2011-12-06 18:54 ` Scott Wood
2011-12-06 18:54 ` Scott Wood
2011-12-07 7:35 ` Matt Evans
2011-12-07 7:35 ` Matt Evans
2011-12-07 18:31 ` Scott Wood
2011-12-07 18:31 ` Scott Wood
2011-12-08 2:57 ` Matt Evans
2011-12-08 2:57 ` Matt Evans
2011-12-06 4:06 ` [PATCH 2/8] kvm tools: Generate SPAPR PPC64 guest device tree Matt Evans
2011-12-06 4:06 ` Matt Evans
2011-12-06 4:06 ` [PATCH 3/8] kvm tools: Add SPAPR PPC64 hcall & rtascall structure Matt Evans
2011-12-06 4:06 ` Matt Evans
2011-12-06 4:06 ` Matt Evans [this message]
2011-12-06 4:06 ` [PATCH 4/8] kvm tools: Add SPAPR PPC64 HV console Matt Evans
2011-12-06 4:06 ` [PATCH 5/8] kvm tools: Add PPC64 XICS interrupt controller support Matt Evans
2011-12-06 4:06 ` Matt Evans
2011-12-06 4:06 ` [PATCH 6/8] kvm tools: Add PPC64 PCI Host Bridge Matt Evans
2011-12-06 4:06 ` Matt Evans
2011-12-06 4:06 ` [PATCH 7/8] kvm tools: Add PPC64 kvm_cpu__emulate_io() Matt Evans
2011-12-06 4:06 ` Matt Evans
2011-12-06 4:06 ` [PATCH 8/8] kvm tools: Make virtio-pci's ioeventfd__add_event() fall Matt Evans
2011-12-06 4:06 ` [PATCH 8/8] kvm tools: Make virtio-pci's ioeventfd__add_event() fall back gracefully if ioeventfds unavailable Matt Evans
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=4EDD94C0.2000906@ozlabs.org \
--to=matt@ozlabs.org \
--cc=kvm-ppc@vger.kernel.org \
--cc=kvm@vger.kernel.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.