summary refs log tree commit diff stats
path: root/hw
diff options
context:
space:
mode:
Diffstat (limited to 'hw')
-rw-r--r--hw/char/spapr_vty.c18
-rw-r--r--hw/net/spapr_llan.c24
-rw-r--r--hw/nvram/spapr_nvram.c10
-rw-r--r--hw/ppc/e500plat.c7
-rw-r--r--hw/ppc/mac_newworld.c2
-rw-r--r--hw/ppc/ppc_booke.c45
-rw-r--r--hw/ppc/spapr.c27
-rw-r--r--hw/ppc/spapr_vio.c41
-rw-r--r--hw/ppc/xics.c2
-rw-r--r--hw/scsi/spapr_vscsi.c15
10 files changed, 141 insertions, 50 deletions
diff --git a/hw/char/spapr_vty.c b/hw/char/spapr_vty.c
index afcec1f182..2993848889 100644
--- a/hw/char/spapr_vty.c
+++ b/hw/char/spapr_vty.c
@@ -12,16 +12,20 @@ typedef struct VIOsPAPRVTYDevice {
     uint8_t buf[VTERM_BUFSIZE];
 } VIOsPAPRVTYDevice;
 
+#define TYPE_VIO_SPAPR_VTY_DEVICE "spapr-vty"
+#define VIO_SPAPR_VTY_DEVICE(obj) \
+     OBJECT_CHECK(VIOsPAPRVTYDevice, (obj), TYPE_VIO_SPAPR_VTY_DEVICE)
+
 static int vty_can_receive(void *opaque)
 {
-    VIOsPAPRVTYDevice *dev = (VIOsPAPRVTYDevice *)opaque;
+    VIOsPAPRVTYDevice *dev = VIO_SPAPR_VTY_DEVICE(opaque);
 
     return (dev->in - dev->out) < VTERM_BUFSIZE;
 }
 
 static void vty_receive(void *opaque, const uint8_t *buf, int size)
 {
-    VIOsPAPRVTYDevice *dev = (VIOsPAPRVTYDevice *)opaque;
+    VIOsPAPRVTYDevice *dev = VIO_SPAPR_VTY_DEVICE(opaque);
     int i;
 
     if ((dev->in == dev->out) && size) {
@@ -36,7 +40,7 @@ static void vty_receive(void *opaque, const uint8_t *buf, int size)
 
 static int vty_getchars(VIOsPAPRDevice *sdev, uint8_t *buf, int max)
 {
-    VIOsPAPRVTYDevice *dev = (VIOsPAPRVTYDevice *)sdev;
+    VIOsPAPRVTYDevice *dev = VIO_SPAPR_VTY_DEVICE(sdev);
     int n = 0;
 
     while ((n < max) && (dev->out != dev->in)) {
@@ -48,7 +52,7 @@ static int vty_getchars(VIOsPAPRDevice *sdev, uint8_t *buf, int max)
 
 void vty_putchars(VIOsPAPRDevice *sdev, uint8_t *buf, int len)
 {
-    VIOsPAPRVTYDevice *dev = (VIOsPAPRVTYDevice *)sdev;
+    VIOsPAPRVTYDevice *dev = VIO_SPAPR_VTY_DEVICE(sdev);
 
     /* FIXME: should check the qemu_chr_fe_write() return value */
     qemu_chr_fe_write(dev->chardev, buf, len);
@@ -56,7 +60,7 @@ void vty_putchars(VIOsPAPRDevice *sdev, uint8_t *buf, int len)
 
 static int spapr_vty_init(VIOsPAPRDevice *sdev)
 {
-    VIOsPAPRVTYDevice *dev = (VIOsPAPRVTYDevice *)sdev;
+    VIOsPAPRVTYDevice *dev = VIO_SPAPR_VTY_DEVICE(sdev);
 
     if (!dev->chardev) {
         fprintf(stderr, "spapr-vty: Can't create vty without a chardev!\n");
@@ -151,7 +155,7 @@ static void spapr_vty_class_init(ObjectClass *klass, void *data)
 }
 
 static const TypeInfo spapr_vty_info = {
-    .name          = "spapr-vty",
+    .name          = TYPE_VIO_SPAPR_VTY_DEVICE,
     .parent        = TYPE_VIO_SPAPR_DEVICE,
     .instance_size = sizeof(VIOsPAPRVTYDevice),
     .class_init    = spapr_vty_class_init,
@@ -177,7 +181,7 @@ VIOsPAPRDevice *spapr_vty_get_default(VIOsPAPRBus *bus)
             continue;
         }
 
-        sdev = DO_UPCAST(VIOsPAPRDevice, qdev, iter);
+        sdev = VIO_SPAPR_DEVICE(iter);
 
         /* First VTY we've found, so it is selected for now */
         if (!selected) {
diff --git a/hw/net/spapr_llan.c b/hw/net/spapr_llan.c
index 34332f2452..3150add3c1 100644
--- a/hw/net/spapr_llan.c
+++ b/hw/net/spapr_llan.c
@@ -73,6 +73,10 @@ typedef uint64_t vlan_bd_t;
 #define VLAN_RX_BDS_OFF      16
 #define VLAN_MAX_BUFS        ((SPAPR_TCE_PAGE_SIZE - VLAN_RX_BDS_OFF) / 8)
 
+#define TYPE_VIO_SPAPR_VLAN_DEVICE "spapr-vlan"
+#define VIO_SPAPR_VLAN_DEVICE(obj) \
+     OBJECT_CHECK(VIOsPAPRVLANDevice, (obj), TYPE_VIO_SPAPR_VLAN_DEVICE)
+
 typedef struct VIOsPAPRVLANDevice {
     VIOsPAPRDevice sdev;
     NICConf nicconf;
@@ -93,8 +97,8 @@ static int spapr_vlan_can_receive(NetClientState *nc)
 static ssize_t spapr_vlan_receive(NetClientState *nc, const uint8_t *buf,
                                   size_t size)
 {
-    VIOsPAPRDevice *sdev = qemu_get_nic_opaque(nc);
-    VIOsPAPRVLANDevice *dev = (VIOsPAPRVLANDevice *)sdev;
+    VIOsPAPRVLANDevice *dev = qemu_get_nic_opaque(nc);
+    VIOsPAPRDevice *sdev = VIO_SPAPR_DEVICE(dev);
     vlan_bd_t rxq_bd = vio_ldq(sdev, dev->buf_list + VLAN_RXQ_BD_OFF);
     vlan_bd_t bd;
     int buf_ptr = dev->use_buf_ptr;
@@ -192,7 +196,7 @@ static NetClientInfo net_spapr_vlan_info = {
 
 static void spapr_vlan_reset(VIOsPAPRDevice *sdev)
 {
-    VIOsPAPRVLANDevice *dev = DO_UPCAST(VIOsPAPRVLANDevice, sdev, sdev);
+    VIOsPAPRVLANDevice *dev = VIO_SPAPR_VLAN_DEVICE(sdev);
 
     dev->buf_list = 0;
     dev->rx_bufs = 0;
@@ -201,7 +205,7 @@ static void spapr_vlan_reset(VIOsPAPRDevice *sdev)
 
 static int spapr_vlan_init(VIOsPAPRDevice *sdev)
 {
-    VIOsPAPRVLANDevice *dev = (VIOsPAPRVLANDevice *)sdev;
+    VIOsPAPRVLANDevice *dev = VIO_SPAPR_VLAN_DEVICE(sdev);
 
     qemu_macaddr_default_if_unset(&dev->nicconf.macaddr);
 
@@ -225,7 +229,7 @@ void spapr_vlan_create(VIOsPAPRBus *bus, NICInfo *nd)
 
 static int spapr_vlan_devnode(VIOsPAPRDevice *dev, void *fdt, int node_off)
 {
-    VIOsPAPRVLANDevice *vdev = (VIOsPAPRVLANDevice *)dev;
+    VIOsPAPRVLANDevice *vdev = VIO_SPAPR_VLAN_DEVICE(dev);
     uint8_t padded_mac[8] = {0, 0};
     int ret;
 
@@ -282,7 +286,7 @@ static target_ulong h_register_logical_lan(PowerPCCPU *cpu,
     target_ulong rec_queue = args[2];
     target_ulong filter_list = args[3];
     VIOsPAPRDevice *sdev = spapr_vio_find_by_reg(spapr->vio_bus, reg);
-    VIOsPAPRVLANDevice *dev = (VIOsPAPRVLANDevice *)sdev;
+    VIOsPAPRVLANDevice *dev = VIO_SPAPR_VLAN_DEVICE(sdev);
     vlan_bd_t filter_list_bd;
 
     if (!dev) {
@@ -341,7 +345,7 @@ static target_ulong h_free_logical_lan(PowerPCCPU *cpu, sPAPREnvironment *spapr,
 {
     target_ulong reg = args[0];
     VIOsPAPRDevice *sdev = spapr_vio_find_by_reg(spapr->vio_bus, reg);
-    VIOsPAPRVLANDevice *dev = (VIOsPAPRVLANDevice *)sdev;
+    VIOsPAPRVLANDevice *dev = VIO_SPAPR_VLAN_DEVICE(sdev);
 
     if (!dev) {
         return H_PARAMETER;
@@ -365,7 +369,7 @@ static target_ulong h_add_logical_lan_buffer(PowerPCCPU *cpu,
     target_ulong reg = args[0];
     target_ulong buf = args[1];
     VIOsPAPRDevice *sdev = spapr_vio_find_by_reg(spapr->vio_bus, reg);
-    VIOsPAPRVLANDevice *dev = (VIOsPAPRVLANDevice *)sdev;
+    VIOsPAPRVLANDevice *dev = VIO_SPAPR_VLAN_DEVICE(sdev);
     vlan_bd_t bd;
 
     dprintf("H_ADD_LOGICAL_LAN_BUFFER(0x" TARGET_FMT_lx
@@ -413,7 +417,7 @@ static target_ulong h_send_logical_lan(PowerPCCPU *cpu, sPAPREnvironment *spapr,
     target_ulong *bufs = args + 1;
     target_ulong continue_token = args[7];
     VIOsPAPRDevice *sdev = spapr_vio_find_by_reg(spapr->vio_bus, reg);
-    VIOsPAPRVLANDevice *dev = (VIOsPAPRVLANDevice *)sdev;
+    VIOsPAPRVLANDevice *dev = VIO_SPAPR_VLAN_DEVICE(sdev);
     unsigned total_len;
     uint8_t *lbuf, *p;
     int i, nbufs;
@@ -511,7 +515,7 @@ static void spapr_vlan_class_init(ObjectClass *klass, void *data)
 }
 
 static const TypeInfo spapr_vlan_info = {
-    .name          = "spapr-vlan",
+    .name          = TYPE_VIO_SPAPR_VLAN_DEVICE,
     .parent        = TYPE_VIO_SPAPR_DEVICE,
     .instance_size = sizeof(VIOsPAPRVLANDevice),
     .class_init    = spapr_vlan_class_init,
diff --git a/hw/nvram/spapr_nvram.c b/hw/nvram/spapr_nvram.c
index 0cc6cba0e3..1eb05c9075 100644
--- a/hw/nvram/spapr_nvram.c
+++ b/hw/nvram/spapr_nvram.c
@@ -36,6 +36,10 @@ typedef struct sPAPRNVRAM {
     BlockDriverState *drive;
 } sPAPRNVRAM;
 
+#define TYPE_VIO_SPAPR_NVRAM "spapr-nvram"
+#define VIO_SPAPR_NVRAM(obj) \
+     OBJECT_CHECK(sPAPRNVRAM, (obj), TYPE_VIO_SPAPR_NVRAM)
+
 #define MIN_NVRAM_SIZE 8192
 #define DEFAULT_NVRAM_SIZE 65536
 #define MAX_NVRAM_SIZE (UINT16_MAX * 16)
@@ -134,7 +138,7 @@ static void rtas_nvram_store(sPAPREnvironment *spapr,
 
 static int spapr_nvram_init(VIOsPAPRDevice *dev)
 {
-    sPAPRNVRAM *nvram = (sPAPRNVRAM *)dev;
+    sPAPRNVRAM *nvram = VIO_SPAPR_NVRAM(dev);
 
     if (nvram->drive) {
         nvram->size = bdrv_getlength(nvram->drive);
@@ -157,7 +161,7 @@ static int spapr_nvram_init(VIOsPAPRDevice *dev)
 
 static int spapr_nvram_devnode(VIOsPAPRDevice *dev, void *fdt, int node_off)
 {
-    sPAPRNVRAM *nvram = (sPAPRNVRAM *)dev;
+    sPAPRNVRAM *nvram = VIO_SPAPR_NVRAM(dev);
 
     return fdt_setprop_cell(fdt, node_off, "#bytes", nvram->size);
 }
@@ -182,7 +186,7 @@ static void spapr_nvram_class_init(ObjectClass *klass, void *data)
 }
 
 static const TypeInfo spapr_nvram_type_info = {
-    .name          = "spapr-nvram",
+    .name          = TYPE_VIO_SPAPR_NVRAM,
     .parent        = TYPE_VIO_SPAPR_DEVICE,
     .instance_size = sizeof(sPAPRNVRAM),
     .class_init    = spapr_nvram_class_init,
diff --git a/hw/ppc/e500plat.c b/hw/ppc/e500plat.c
index 7292ce1290..c85299588c 100644
--- a/hw/ppc/e500plat.c
+++ b/hw/ppc/e500plat.c
@@ -16,6 +16,7 @@
 #include "sysemu/device_tree.h"
 #include "hw/pci/pci.h"
 #include "hw/ppc/openpic.h"
+#include "kvm_ppc.h"
 
 static void e500plat_fixup_devtree(PPCE500Params *params, void *fdt)
 {
@@ -48,6 +49,12 @@ static void e500plat_init(QEMUMachineInitArgs *args)
         .mpic_version = OPENPIC_MODEL_FSL_MPIC_42,
     };
 
+    /* Older KVM versions don't support EPR which breaks guests when we announce
+       MPIC variants that support EPR. Revert to an older one for those */
+    if (kvm_enabled() && !kvmppc_has_cap_epr()) {
+        params.mpic_version = OPENPIC_MODEL_FSL_MPIC_20;
+    }
+
     ppce500_init(&params);
 }
 
diff --git a/hw/ppc/mac_newworld.c b/hw/ppc/mac_newworld.c
index 4a9b8837e3..ce44e95d53 100644
--- a/hw/ppc/mac_newworld.c
+++ b/hw/ppc/mac_newworld.c
@@ -126,6 +126,8 @@ static void ppc_core99_reset(void *opaque)
     PowerPCCPU *cpu = opaque;
 
     cpu_reset(CPU(cpu));
+    /* 970 CPUs want to get their initial IP as part of their boot protocol */
+    cpu->env.nip = PROM_ADDR + 0x100;
 }
 
 /* PowerPC Mac99 hardware initialisation */
diff --git a/hw/ppc/ppc_booke.c b/hw/ppc/ppc_booke.c
index 585f53b912..e41b036b8e 100644
--- a/hw/ppc/ppc_booke.c
+++ b/hw/ppc/ppc_booke.c
@@ -28,6 +28,7 @@
 #include "hw/timer/m48t59.h"
 #include "qemu/log.h"
 #include "hw/loader.h"
+#include "kvm_ppc.h"
 
 
 /* Timer Control Register */
@@ -211,6 +212,7 @@ void store_booke_tsr(CPUPPCState *env, target_ulong val)
     PowerPCCPU *cpu = ppc_env_get_cpu(env);
 
     env->spr[SPR_BOOKE_TSR] &= ~val;
+    kvmppc_clear_tsr_bits(cpu, val);
     booke_update_irq(cpu);
 }
 
@@ -222,6 +224,7 @@ void store_booke_tcr(CPUPPCState *env, target_ulong val)
 
     tb_env = env->tb_env;
     env->spr[SPR_BOOKE_TCR] = val;
+    kvmppc_set_tcr(cpu);
 
     booke_update_irq(cpu);
 
@@ -234,7 +237,6 @@ void store_booke_tcr(CPUPPCState *env, target_ulong val)
                              booke_get_wdt_target(env, tb_env),
                              &booke_timer->wdt_next,
                              booke_timer->wdt_timer);
-
 }
 
 static void ppc_booke_timer_reset_handle(void *opaque)
@@ -242,16 +244,39 @@ static void ppc_booke_timer_reset_handle(void *opaque)
     PowerPCCPU *cpu = opaque;
     CPUPPCState *env = &cpu->env;
 
-    env->spr[SPR_BOOKE_TSR] = 0;
-    env->spr[SPR_BOOKE_TCR] = 0;
+    store_booke_tcr(env, 0);
+    store_booke_tsr(env, -1);
+}
 
-    booke_update_irq(cpu);
+/*
+ * This function will be called whenever the CPU state changes.
+ * CPU states are defined "typedef enum RunState".
+ * Regarding timer, When CPU state changes to running after debug halt
+ * or similar cases which takes time then in between final watchdog
+ * expiry happenes. This will cause exit to QEMU and configured watchdog
+ * action will be taken. To avoid this we always clear the watchdog state when
+ * state changes to running.
+ */
+static void cpu_state_change_handler(void *opaque, int running, RunState state)
+{
+    PowerPCCPU *cpu = opaque;
+    CPUPPCState *env = &cpu->env;
+
+    if (!running) {
+        return;
+    }
+
+    /*
+     * Clear watchdog interrupt condition by clearing TSR.
+     */
+    store_booke_tsr(env, TSR_ENW | TSR_WIS | TSR_WRS_MASK);
 }
 
 void ppc_booke_timers_init(PowerPCCPU *cpu, uint32_t freq, uint32_t flags)
 {
     ppc_tb_t *tb_env;
     booke_timer_t *booke_timer;
+    int ret = 0;
 
     tb_env      = g_malloc0(sizeof(ppc_tb_t));
     booke_timer = g_malloc0(sizeof(booke_timer_t));
@@ -269,5 +294,17 @@ void ppc_booke_timers_init(PowerPCCPU *cpu, uint32_t freq, uint32_t flags)
     booke_timer->wdt_timer =
         qemu_new_timer_ns(vm_clock, &booke_wdt_cb, cpu);
 
+    ret = kvmppc_booke_watchdog_enable(cpu);
+
+    if (ret) {
+        /* TODO: Start the QEMU emulated watchdog if not running on KVM.
+         * Also start the QEMU emulated watchdog if KVM does not support
+         * emulated watchdog or somehow it is not enabled (supported but
+         * not enabled is though some bug and requires debugging :)).
+         */
+    }
+
+    qemu_add_vm_change_state_handler(cpu_state_change_handler, cpu);
+
     qemu_register_reset(ppc_booke_timer_reset_handle, cpu);
 }
diff --git a/hw/ppc/spapr.c b/hw/ppc/spapr.c
index 7a425011da..c96ac8131f 100644
--- a/hw/ppc/spapr.c
+++ b/hw/ppc/spapr.c
@@ -308,6 +308,7 @@ static void *spapr_create_fdt_skel(const char *cpu_model,
 
     for (env = first_cpu; env != NULL; env = env->next_cpu) {
         CPUState *cpu = CPU(ppc_env_get_cpu(env));
+        PowerPCCPUClass *pcc = POWERPC_CPU_GET_CLASS(cpu);
         int index = cpu->cpu_index;
         uint32_t servers_prop[smp_threads];
         uint32_t gservers_prop[smp_threads * 2];
@@ -333,10 +334,26 @@ static void *spapr_create_fdt_skel(const char *cpu_model,
         _FDT((fdt_property_string(fdt, "device_type", "cpu")));
 
         _FDT((fdt_property_cell(fdt, "cpu-version", env->spr[SPR_PVR])));
-        _FDT((fdt_property_cell(fdt, "dcache-block-size",
+        _FDT((fdt_property_cell(fdt, "d-cache-block-size",
                                 env->dcache_line_size)));
-        _FDT((fdt_property_cell(fdt, "icache-block-size",
+        _FDT((fdt_property_cell(fdt, "d-cache-line-size",
+                                env->dcache_line_size)));
+        _FDT((fdt_property_cell(fdt, "i-cache-block-size",
+                                env->icache_line_size)));
+        _FDT((fdt_property_cell(fdt, "i-cache-line-size",
                                 env->icache_line_size)));
+
+        if (pcc->l1_dcache_size) {
+            _FDT((fdt_property_cell(fdt, "d-cache-size", pcc->l1_dcache_size)));
+        } else {
+            fprintf(stderr, "Warning: Unknown L1 dcache size for cpu\n");
+        }
+        if (pcc->l1_icache_size) {
+            _FDT((fdt_property_cell(fdt, "i-cache-size", pcc->l1_icache_size)));
+        } else {
+            fprintf(stderr, "Warning: Unknown L1 icache size for cpu\n");
+        }
+
         _FDT((fdt_property_cell(fdt, "timebase-frequency", tbfreq)));
         _FDT((fdt_property_cell(fdt, "clock-frequency", cpufreq)));
         _FDT((fdt_property_cell(fdt, "ibm,slb-size", env->slb_nr)));
@@ -801,8 +818,10 @@ static void ppc_spapr_init(QEMUMachineInitArgs *args)
         /* Set time-base frequency to 512 MHz */
         cpu_ppc_tb_init(env, TIMEBASE_FREQ);
 
-        /* PAPR always has exception vectors in RAM not ROM */
-        env->hreset_excp_prefix = 0;
+        /* PAPR always has exception vectors in RAM not ROM. To ensure this,
+         * MSR[IP] should never be set.
+         */
+        env->msr_mask &= ~(1 << 6);
 
         /* Tell KVM that we're in PAPR mode */
         if (kvm_enabled()) {
diff --git a/hw/ppc/spapr_vio.c b/hw/ppc/spapr_vio.c
index 4dbc31541b..1405c3202c 100644
--- a/hw/ppc/spapr_vio.c
+++ b/hw/ppc/spapr_vio.c
@@ -53,9 +53,29 @@ static Property spapr_vio_props[] = {
     DEFINE_PROP_END_OF_LIST(),
 };
 
+static char *spapr_vio_get_dev_name(DeviceState *qdev)
+{
+    VIOsPAPRDevice *dev = VIO_SPAPR_DEVICE(qdev);
+    VIOsPAPRDeviceClass *pc = VIO_SPAPR_DEVICE_GET_CLASS(dev);
+    char *name;
+
+    /* Device tree style name device@reg */
+    name = g_strdup_printf("%s@%x", pc->dt_name, dev->reg);
+
+    return name;
+}
+
+static void spapr_vio_bus_class_init(ObjectClass *klass, void *data)
+{
+    BusClass *k = BUS_CLASS(klass);
+
+    k->get_dev_path = spapr_vio_get_dev_name;
+}
+
 static const TypeInfo spapr_vio_bus_info = {
     .name = TYPE_SPAPR_VIO_BUS,
     .parent = TYPE_BUS,
+    .class_init = spapr_vio_bus_class_init,
     .instance_size = sizeof(VIOsPAPRBus),
 };
 
@@ -74,17 +94,6 @@ VIOsPAPRDevice *spapr_vio_find_by_reg(VIOsPAPRBus *bus, uint32_t reg)
     return NULL;
 }
 
-static char *vio_format_dev_name(VIOsPAPRDevice *dev)
-{
-    VIOsPAPRDeviceClass *pc = VIO_SPAPR_DEVICE_GET_CLASS(dev);
-    char *name;
-
-    /* Device tree style name device@reg */
-    name = g_strdup_printf("%s@%x", pc->dt_name, dev->reg);
-
-    return name;
-}
-
 #ifdef CONFIG_FDT
 static int vio_make_devnode(VIOsPAPRDevice *dev,
                             void *fdt)
@@ -98,7 +107,7 @@ static int vio_make_devnode(VIOsPAPRDevice *dev,
         return vdevice_off;
     }
 
-    dt_name = vio_format_dev_name(dev);
+    dt_name = spapr_vio_get_dev_name(DEVICE(dev));
     node_off = fdt_add_subnode(fdt, vdevice_off, dt_name);
     g_free(dt_name);
     if (node_off < 0) {
@@ -379,7 +388,7 @@ static VIOsPAPRDevice *reg_conflict(VIOsPAPRDevice *dev)
      * the given dev might already be in the list.
      */
     QTAILQ_FOREACH(kid, &bus->bus.children, sibling) {
-        other = DO_UPCAST(VIOsPAPRDevice, qdev, kid->child);
+        other = VIO_SPAPR_DEVICE(kid->child);
 
         if (other != dev && other->reg == dev->reg) {
             return other;
@@ -391,7 +400,7 @@ static VIOsPAPRDevice *reg_conflict(VIOsPAPRDevice *dev)
 
 static void spapr_vio_busdev_reset(DeviceState *qdev)
 {
-    VIOsPAPRDevice *dev = DO_UPCAST(VIOsPAPRDevice, qdev, qdev);
+    VIOsPAPRDevice *dev = VIO_SPAPR_DEVICE(qdev);
     VIOsPAPRDeviceClass *pc = VIO_SPAPR_DEVICE_GET_CLASS(dev);
 
     /* Shut down the request queue and TCEs if necessary */
@@ -437,7 +446,7 @@ static int spapr_vio_busdev_init(DeviceState *qdev)
 
     /* Don't overwrite ids assigned on the command line */
     if (!dev->qdev.id) {
-        id = vio_format_dev_name(dev);
+        id = spapr_vio_get_dev_name(DEVICE(dev));
         dev->qdev.id = id;
     }
 
@@ -636,7 +645,7 @@ int spapr_populate_chosen_stdout(void *fdt, VIOsPAPRBus *bus)
         return offset;
     }
 
-    name = vio_format_dev_name(dev);
+    name = spapr_vio_get_dev_name(DEVICE(dev));
     path = g_strdup_printf("/vdevice/%s", name);
 
     ret = fdt_setprop_string(fdt, offset, "linux,stdout-path", path);
diff --git a/hw/ppc/xics.c b/hw/ppc/xics.c
index 8e1e85edfd..1b25075d14 100644
--- a/hw/ppc/xics.c
+++ b/hw/ppc/xics.c
@@ -101,6 +101,7 @@ static void icp_set_cppr(struct icp_state *icp, int server, uint8_t cppr)
         if (XISR(ss) && (cppr <= ss->pending_priority)) {
             old_xisr = XISR(ss);
             ss->xirr &= ~XISR_MASK; /* Clear XISR */
+            ss->pending_priority = 0xff;
             qemu_irq_lower(ss->output);
             ics_reject(icp->ics, old_xisr);
         }
@@ -127,6 +128,7 @@ static uint32_t icp_accept(struct icp_server_state *ss)
 
     qemu_irq_lower(ss->output);
     ss->xirr = ss->pending_priority << 24;
+    ss->pending_priority = 0xff;
 
     trace_xics_icp_accept(xirr, ss->xirr);
 
diff --git a/hw/scsi/spapr_vscsi.c b/hw/scsi/spapr_vscsi.c
index 999a463a84..3d322d5d1e 100644
--- a/hw/scsi/spapr_vscsi.c
+++ b/hw/scsi/spapr_vscsi.c
@@ -91,6 +91,9 @@ typedef struct vscsi_req {
     int                     total_desc;
 } vscsi_req;
 
+#define TYPE_VIO_SPAPR_VSCSI_DEVICE "spapr-vscsi"
+#define VIO_SPAPR_VSCSI_DEVICE(obj) \
+     OBJECT_CHECK(VSCSIState, (obj), TYPE_VIO_SPAPR_VSCSI_DEVICE)
 
 typedef struct {
     VIOsPAPRDevice vdev;
@@ -461,7 +464,7 @@ static int vscsi_preprocess_desc(vscsi_req *req)
 /* Callback to indicate that the SCSI layer has completed a transfer.  */
 static void vscsi_transfer_data(SCSIRequest *sreq, uint32_t len)
 {
-    VSCSIState *s = DO_UPCAST(VSCSIState, vdev.qdev, sreq->bus->qbus.parent);
+    VSCSIState *s = VIO_SPAPR_VSCSI_DEVICE(sreq->bus->qbus.parent);
     vscsi_req *req = sreq->hba_private;
     uint8_t *buf;
     int rc = 0;
@@ -492,7 +495,7 @@ static void vscsi_transfer_data(SCSIRequest *sreq, uint32_t len)
 /* Callback to indicate that the SCSI layer has completed a transfer.  */
 static void vscsi_command_complete(SCSIRequest *sreq, uint32_t status, size_t resid)
 {
-    VSCSIState *s = DO_UPCAST(VSCSIState, vdev.qdev, sreq->bus->qbus.parent);
+    VSCSIState *s = VIO_SPAPR_VSCSI_DEVICE(sreq->bus->qbus.parent);
     vscsi_req *req = sreq->hba_private;
     int32_t res_in = 0, res_out = 0;
 
@@ -827,7 +830,7 @@ static void vscsi_got_payload(VSCSIState *s, vscsi_crq *crq)
 
 static int vscsi_do_crq(struct VIOsPAPRDevice *dev, uint8_t *crq_data)
 {
-    VSCSIState *s = DO_UPCAST(VSCSIState, vdev, dev);
+    VSCSIState *s = VIO_SPAPR_VSCSI_DEVICE(dev);
     vscsi_crq crq;
 
     memcpy(crq.raw, crq_data, 16);
@@ -897,7 +900,7 @@ static const struct SCSIBusInfo vscsi_scsi_info = {
 
 static void spapr_vscsi_reset(VIOsPAPRDevice *dev)
 {
-    VSCSIState *s = DO_UPCAST(VSCSIState, vdev, dev);
+    VSCSIState *s = VIO_SPAPR_VSCSI_DEVICE(dev);
     int i;
 
     memset(s->reqs, 0, sizeof(s->reqs));
@@ -908,7 +911,7 @@ static void spapr_vscsi_reset(VIOsPAPRDevice *dev)
 
 static int spapr_vscsi_init(VIOsPAPRDevice *dev)
 {
-    VSCSIState *s = DO_UPCAST(VSCSIState, vdev, dev);
+    VSCSIState *s = VIO_SPAPR_VSCSI_DEVICE(dev);
 
     dev->crq.SendFunc = vscsi_do_crq;
 
@@ -968,7 +971,7 @@ static void spapr_vscsi_class_init(ObjectClass *klass, void *data)
 }
 
 static const TypeInfo spapr_vscsi_info = {
-    .name          = "spapr-vscsi",
+    .name          = TYPE_VIO_SPAPR_VSCSI_DEVICE,
     .parent        = TYPE_VIO_SPAPR_DEVICE,
     .instance_size = sizeof(VSCSIState),
     .class_init    = spapr_vscsi_class_init,