From dbc0773d1c719444e3fef247ee7a047308c9728b Mon Sep 17 00:00:00 2001 Message-Id: In-Reply-To: <1d7d27453d05521b09c5b709aa6f00c682ab81dc.1369899578.git.minovotn@redhat.com> References: <1d7d27453d05521b09c5b709aa6f00c682ab81dc.1369899578.git.minovotn@redhat.com> From: Laszlo Ersek Date: Wed, 22 May 2013 11:31:07 +0200 Subject: [PATCH 08/15] introduce a new qom device to deal with panicked event RH-Author: Laszlo Ersek Message-id: <1369222273-3298-4-git-send-email-lersek@redhat.com> Patchwork-id: 51524 O-Subject: [RHEL-6.5 qemu-kvm PATCH v2 3/9] introduce a new qom device to deal with panicked event Bugzilla: 833530 RH-Acked-by: Andrew Jones RH-Acked-by: Paolo Bonzini RH-Acked-by: Gerd Hoffmann pvpanic device is used to send guest panic event from guest to qemu. When guest panic happens, pvpanic device driver will write a event number to IO port 0x505(which is the IO port occupied by pvpanic device, by default). On receiving the event, pvpanic device will pause guest cpu(s), and send a qmp event QEVENT_GUEST_PANICKED. Signed-off-by: Wen Congyang Signed-off-by: Hu Tao Reviewed-by: Markus Armbruster Message-id: b66077a40235b3531632a05a6ff373850afc7d2e.1366945969.git.hutao@cn.fujitsu.com Signed-off-by: Anthony Liguori RHEL-6 notes: - qom? What is qom? - We still live on the near side of the tree reorganization, affecting eg. Makefiles and #include directives. - No support for log masks, just call qemu_log(). - MemoryRegion? huh? - Manual port of upstream commit eec3d2adc98dd9ef7352823ce6597f88a51cf7cb, starting with "git show eec3d2a:hw/misc/pvpanic.c >hw/pvpanic.c", and heavily ripping off "testdev.c" (commit c9c58ecd922887b1c5657b8b55665a8141bbfe22 from ). Also consulted "hw/watchdog.c". Signed-off-by: Laszlo Ersek --- v2: - PVPANIC_PANICKED and parameter of handle_event() have type "signed int", matching upstream [Paolo Bonzini] Makefile.target | 1 + hw/pvpanic.c | 98 ++++++++++++++++++++++++++++++++++++ default-configs/i386-softmmu.mak | 1 + default-configs/x86_64-softmmu.mak | 1 + 4 files changed, 101 insertions(+), 0 deletions(-) create mode 100644 hw/pvpanic.c Signed-off-by: Michal Novotny --- Makefile.target | 1 + default-configs/i386-softmmu.mak | 1 + default-configs/x86_64-softmmu.mak | 1 + hw/pvpanic.c | 98 ++++++++++++++++++++++++++++++++++++++ 4 files changed, 101 insertions(+) create mode 100644 hw/pvpanic.c diff --git a/Makefile.target b/Makefile.target index d38e5f6..4df5ae5 100644 --- a/Makefile.target +++ b/Makefile.target @@ -279,6 +279,7 @@ obj-i386-$(CONFIG_SPICE) += qxl.o qxl-logger.o qxl-render.o obj-i386-$(CONFIG_VMWARE_VGA) += vmware_vga.o obj-i386-$(CONFIG_VMMOUSE) += vmmouse.o obj-i386-$(CONFIG_VMPORT) += vmport.o +obj-i386-$(CONFIG_PVPANIC) += pvpanic.o # shared objects obj-ppc-y = ppc.o ide/core.o ide/atapi.o ide/qdev.o ide/isa.o ide/pci.o ide/macio.o diff --git a/default-configs/i386-softmmu.mak b/default-configs/i386-softmmu.mak index 243c4bf..0cb1150 100644 --- a/default-configs/i386-softmmu.mak +++ b/default-configs/i386-softmmu.mak @@ -4,3 +4,4 @@ CONFIG_VMWARE_VGA=y CONFIG_VMPORT=y #NOTE: VMMOUSE depends on VMPORT CONFIG_VMMOUSE=y +CONFIG_PVPANIC=y diff --git a/default-configs/x86_64-softmmu.mak b/default-configs/x86_64-softmmu.mak index 7c52ed7..61fa891 100644 --- a/default-configs/x86_64-softmmu.mak +++ b/default-configs/x86_64-softmmu.mak @@ -4,3 +4,4 @@ CONFIG_VMWARE_VGA=y CONFIG_VMPORT=y #NOTE: VMMOUSE depends on VMPORT CONFIG_VMMOUSE=y +CONFIG_PVPANIC=y diff --git a/hw/pvpanic.c b/hw/pvpanic.c new file mode 100644 index 0000000..918c86f --- /dev/null +++ b/hw/pvpanic.c @@ -0,0 +1,98 @@ +/* + * QEMU simulated pvpanic device. + * + * Copyright Red Hat, Inc. 2013 + * Copyright Fujitsu, Corp. 2013 + * + * Authors: + * Laszlo Ersek (RHEL-6 port) + * Wen Congyang + * Hu Tao + * + * This work is licensed under the terms of the GNU GPL, version 2 or later. + * See the COPYING file in the top-level directory. + * + */ + +#include "qobject.h" +#include "qjson.h" +#include "monitor.h" +#include "sysemu.h" +#include "qemu-log.h" + +/* The bit of supported pv event */ +#define PVPANIC_F_PANICKED 0 + +/* The pv event value */ +#define PVPANIC_PANICKED (1 << PVPANIC_F_PANICKED) + + +static void panicked_mon_event(const char *action) +{ + QObject *data; + + data = qobject_from_jsonf("{ 'action': %s }", action); + monitor_protocol_event(QEVENT_GUEST_PANICKED, data); + qobject_decref(data); +} + +static void handle_event(int event) +{ + static bool logged; + + if (event & ~PVPANIC_PANICKED && !logged) { + qemu_log("pvpanic: unknown event %#x.\n", event); + logged = true; + } + + if (event & PVPANIC_PANICKED) { + panicked_mon_event("pause"); + vm_stop(RUN_STATE_GUEST_PANICKED); + return; + } +} + +#include "hw/isa.h" + +typedef struct PVPanicState { + ISADevice isa_dev; + uint16_t ioport; +} PVPanicState; + +/* return supported events on read */ +static uint32_t pvpanic_ioport_read(void *opaque, uint32_t address) +{ + return PVPANIC_PANICKED; +} + +static void pvpanic_ioport_write(void *opaque, uint32_t address, uint32_t data) +{ + handle_event(data); +} + +static int pvpanic_isa_init(ISADevice *dev) +{ + PVPanicState *s = DO_UPCAST(PVPanicState, isa_dev, dev); + + register_ioport_read(s->ioport, 1, 1, &pvpanic_ioport_read, s); + register_ioport_write(s->ioport, 1, 1, &pvpanic_ioport_write, s); + return 0; +} + +static ISADeviceInfo pvpanic_isa_info = { + .qdev.name = "pvpanic", + .qdev.size = sizeof(PVPanicState), + .qdev.no_user = 1, + .qdev.props = (Property[]) { + DEFINE_PROP_UINT16("ioport", PVPanicState, ioport, 0x505), + DEFINE_PROP_END_OF_LIST() + }, + .init = &pvpanic_isa_init +}; + +static void pvpanic_devices(void) +{ + isa_qdev_register(&pvpanic_isa_info); +} + +device_init(pvpanic_devices) -- 1.7.11.7