From 077f0f3dade3dcb38f43cc728fa26c4f6affcdd0 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Philippe=20Mathieu-Daud=C3=A9?= Date: Mon, 1 Oct 2018 22:27:22 +0200 Subject: [PATCH 01/16] hw/sparc/sun4m: Use UnimplementedDevice for I/O devices MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit These devices are not slots on a bus, but real I/O devices that we do not implement. As the ISDN ROM would be a ROMD device, also model it as UnimplementedDevice. Reviewed-by: Artyom Tarasenko Message-Id: <20200510152840.13558-2-f4bug@amsat.org> Signed-off-by: Philippe Mathieu-Daudé --- hw/sparc/Kconfig | 1 + hw/sparc/sun4m.c | 11 +++++++---- 2 files changed, 8 insertions(+), 4 deletions(-) diff --git a/hw/sparc/Kconfig b/hw/sparc/Kconfig index 22aff2f5b7..91805afab6 100644 --- a/hw/sparc/Kconfig +++ b/hw/sparc/Kconfig @@ -5,6 +5,7 @@ config SUN4M select CS4231 select ECCMEMCTL select EMPTY_SLOT + select UNIMP select ESCC select ESP select FDC diff --git a/hw/sparc/sun4m.c b/hw/sparc/sun4m.c index 8dda3f7292..fa3dd7775f 100644 --- a/hw/sparc/sun4m.c +++ b/hw/sparc/sun4m.c @@ -47,6 +47,7 @@ #include "hw/nvram/fw_cfg.h" #include "hw/char/escc.h" #include "hw/empty_slot.h" +#include "hw/misc/unimp.h" #include "hw/irq.h" #include "hw/loader.h" #include "elf.h" @@ -968,7 +969,7 @@ static void sun4m_hw_init(const struct sun4m_hwdef *hwdef, } if (hwdef->sx_base) { - empty_slot_init(hwdef->sx_base, 0x2000); + create_unimplemented_device("SUNW,sx", hwdef->sx_base, 0x2000); } nvram = m48t59_init(slavio_irq[0], hwdef->nvram_base, 0, 0x2000, 1968, 8); @@ -1031,14 +1032,16 @@ static void sun4m_hw_init(const struct sun4m_hwdef *hwdef, if (hwdef->dbri_base) { /* ISDN chip with attached CS4215 audio codec */ /* prom space */ - empty_slot_init(hwdef->dbri_base+0x1000, 0x30); + create_unimplemented_device("SUNW,DBRI.prom", + hwdef->dbri_base + 0x1000, 0x30); /* reg space */ - empty_slot_init(hwdef->dbri_base+0x10000, 0x100); + create_unimplemented_device("SUNW,DBRI", + hwdef->dbri_base + 0x10000, 0x100); } if (hwdef->bpp_base) { /* parallel port */ - empty_slot_init(hwdef->bpp_base, 0x20); + create_unimplemented_device("SUNW,bpp", hwdef->bpp_base, 0x20); } initrd_size = 0; From 6c339493c8dbb709c98f471144eebf74c4cca1ad Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Philippe=20Mathieu-Daud=C3=A9?= Date: Mon, 24 Jun 2019 17:20:37 +0200 Subject: [PATCH 02/16] hw/misc/empty_slot: Lower address space priority MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Empty slots model RAZ/WI access on a bus. Since we can still (hot) plug devices on the bus, lower the slot priority, so device added later is accessed first. Signed-off-by: Philippe Mathieu-Daudé Acked-by: Artyom Tarasenko Message-Id: <20200510152840.13558-3-f4bug@amsat.org> --- hw/core/empty_slot.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/hw/core/empty_slot.c b/hw/core/empty_slot.c index 3ba450e1ca..5ab426e965 100644 --- a/hw/core/empty_slot.c +++ b/hw/core/empty_slot.c @@ -67,7 +67,7 @@ void empty_slot_init(hwaddr addr, uint64_t slot_size) qdev_init_nofail(dev); - sysbus_mmio_map(s, 0, addr); + sysbus_mmio_map_overlap(s, 0, addr, -10000); } } From 4bbadef0e3da3f455374e83cb9249c2afe497b24 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Philippe=20Mathieu-Daud=C3=A9?= Date: Mon, 24 Jun 2019 17:19:22 +0200 Subject: [PATCH 03/16] hw/misc/empty_slot: Convert 'size' field as qdev property MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: Philippe Mathieu-Daudé Acked-by: Artyom Tarasenko Message-Id: <20200510152840.13558-4-f4bug@amsat.org> --- hw/core/empty_slot.c | 15 +++++++++------ 1 file changed, 9 insertions(+), 6 deletions(-) diff --git a/hw/core/empty_slot.c b/hw/core/empty_slot.c index 5ab426e965..0df086fe98 100644 --- a/hw/core/empty_slot.c +++ b/hw/core/empty_slot.c @@ -12,6 +12,7 @@ #include "qemu/osdep.h" #include "hw/sysbus.h" #include "qemu/module.h" +#include "hw/qdev-properties.h" #include "hw/empty_slot.h" //#define DEBUG_EMPTY_SLOT @@ -57,17 +58,13 @@ void empty_slot_init(hwaddr addr, uint64_t slot_size) if (slot_size > 0) { /* Only empty slots larger than 0 byte need handling. */ DeviceState *dev; - SysBusDevice *s; - EmptySlot *e; dev = qdev_create(NULL, TYPE_EMPTY_SLOT); - s = SYS_BUS_DEVICE(dev); - e = EMPTY_SLOT(dev); - e->size = slot_size; + qdev_prop_set_uint64(dev, "size", slot_size); qdev_init_nofail(dev); - sysbus_mmio_map_overlap(s, 0, addr, -10000); + sysbus_mmio_map_overlap(SYS_BUS_DEVICE(dev), 0, addr, -10000); } } @@ -80,11 +77,17 @@ static void empty_slot_realize(DeviceState *dev, Error **errp) sysbus_init_mmio(SYS_BUS_DEVICE(dev), &s->iomem); } +static Property empty_slot_properties[] = { + DEFINE_PROP_UINT64("size", EmptySlot, size, 0), + DEFINE_PROP_END_OF_LIST(), +}; + static void empty_slot_class_init(ObjectClass *klass, void *data) { DeviceClass *dc = DEVICE_CLASS(klass); dc->realize = empty_slot_realize; + device_class_set_props(dc, empty_slot_properties); } static const TypeInfo empty_slot_info = { From 07ddf5cbe2e9499cc2d238e5c864ac3f5bdd25ce Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Philippe=20Mathieu-Daud=C3=A9?= Date: Mon, 24 Jun 2019 17:23:31 +0200 Subject: [PATCH 04/16] hw/misc/empty_slot: Add a 'name' qdev property MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Add a 'name' qdev property so when multiple slots are accessed, we can notice which one is accessed. Signed-off-by: Philippe Mathieu-Daudé Acked-by: Artyom Tarasenko Message-Id: <20200510152840.13558-5-f4bug@amsat.org> --- hw/core/empty_slot.c | 7 ++++++- 1 file changed, 6 insertions(+), 1 deletion(-) diff --git a/hw/core/empty_slot.c b/hw/core/empty_slot.c index 0df086fe98..576b276c4b 100644 --- a/hw/core/empty_slot.c +++ b/hw/core/empty_slot.c @@ -31,6 +31,7 @@ typedef struct EmptySlot { SysBusDevice parent_obj; MemoryRegion iomem; + char *name; uint64_t size; } EmptySlot; @@ -72,13 +73,17 @@ static void empty_slot_realize(DeviceState *dev, Error **errp) { EmptySlot *s = EMPTY_SLOT(dev); + if (s->name == NULL) { + s->name = g_strdup("empty-slot"); + } memory_region_init_io(&s->iomem, OBJECT(s), &empty_slot_ops, s, - "empty-slot", s->size); + s->name, s->size); sysbus_init_mmio(SYS_BUS_DEVICE(dev), &s->iomem); } static Property empty_slot_properties[] = { DEFINE_PROP_UINT64("size", EmptySlot, size, 0), + DEFINE_PROP_STRING("name", EmptySlot, name), DEFINE_PROP_END_OF_LIST(), }; From c0e43084dd63daf63e8f7f5a866f2861a5e8d630 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Philippe=20Mathieu-Daud=C3=A9?= Date: Mon, 24 Jun 2019 17:23:48 +0200 Subject: [PATCH 05/16] hw/misc/empty_slot: Convert debug printf() to trace event MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: Philippe Mathieu-Daudé Acked-by: Artyom Tarasenko Message-Id: <20200510152840.13558-6-f4bug@amsat.org> --- hw/core/empty_slot.c | 19 ++++++++----------- hw/core/trace-events | 4 ++++ 2 files changed, 12 insertions(+), 11 deletions(-) diff --git a/hw/core/empty_slot.c b/hw/core/empty_slot.c index 576b276c4b..d28f7f99c9 100644 --- a/hw/core/empty_slot.c +++ b/hw/core/empty_slot.c @@ -14,15 +14,7 @@ #include "qemu/module.h" #include "hw/qdev-properties.h" #include "hw/empty_slot.h" - -//#define DEBUG_EMPTY_SLOT - -#ifdef DEBUG_EMPTY_SLOT -#define DPRINTF(fmt, ...) \ - do { printf("empty_slot: " fmt , ## __VA_ARGS__); } while (0) -#else -#define DPRINTF(fmt, ...) do {} while (0) -#endif +#include "trace.h" #define TYPE_EMPTY_SLOT "empty_slot" #define EMPTY_SLOT(obj) OBJECT_CHECK(EmptySlot, (obj), TYPE_EMPTY_SLOT) @@ -38,14 +30,19 @@ typedef struct EmptySlot { static uint64_t empty_slot_read(void *opaque, hwaddr addr, unsigned size) { - DPRINTF("read from " TARGET_FMT_plx "\n", addr); + EmptySlot *s = EMPTY_SLOT(opaque); + + trace_empty_slot_write(addr, size << 1, 0, size, s->name); + return 0; } static void empty_slot_write(void *opaque, hwaddr addr, uint64_t val, unsigned size) { - DPRINTF("write 0x%x to " TARGET_FMT_plx "\n", (unsigned)val, addr); + EmptySlot *s = EMPTY_SLOT(opaque); + + trace_empty_slot_write(addr, size << 1, val, size, s->name); } static const MemoryRegionOps empty_slot_ops = { diff --git a/hw/core/trace-events b/hw/core/trace-events index 1ac60ede6b..bbb68fb6f0 100644 --- a/hw/core/trace-events +++ b/hw/core/trace-events @@ -34,3 +34,7 @@ clock_disconnect(const char *clk) "'%s'" clock_set(const char *clk, uint64_t old, uint64_t new) "'%s', ns=%"PRIu64"->%"PRIu64 clock_propagate(const char *clk) "'%s'" clock_update(const char *clk, const char *src, uint64_t val, int cb) "'%s', src='%s', ns=%"PRIu64", cb=%d" + +# empty_slot.c +empty_slot_read(uint64_t addr, unsigned width, uint64_t value, unsigned size, const char *name) "rd addr:0x%04"PRIx64" data:0x%0*"PRIx64" size %u [%s]" +empty_slot_write(uint64_t addr, unsigned width, uint64_t value, unsigned size, const char *name) "wr addr:0x%04"PRIx64" data:0x%0*"PRIx64" size %u [%s]" From 6007523a80bc5100c22a1caf642a9e8a3ea7bd15 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Philippe=20Mathieu-Daud=C3=A9?= Date: Mon, 24 Jun 2019 17:17:32 +0200 Subject: [PATCH 06/16] hw/misc/empty_slot: Move the 'hw/misc' and cover in MAINTAINERS MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Add an entry for the 'empty_slot' device. Signed-off-by: Philippe Mathieu-Daudé Acked-by: Artyom Tarasenko Message-Id: <20200510152840.13558-7-f4bug@amsat.org> --- MAINTAINERS | 7 +++++++ hw/core/Makefile.objs | 1 - hw/core/trace-events | 4 ---- hw/mips/malta.c | 2 +- hw/misc/Makefile.objs | 1 + hw/{core => misc}/empty_slot.c | 4 ++-- hw/misc/trace-events | 4 ++++ hw/sparc/sun4m.c | 2 +- include/hw/empty_slot.h | 9 --------- include/hw/misc/empty_slot.h | 19 +++++++++++++++++++ 10 files changed, 35 insertions(+), 18 deletions(-) rename hw/{core => misc}/empty_slot.c (96%) delete mode 100644 include/hw/empty_slot.h create mode 100644 include/hw/misc/empty_slot.h diff --git a/MAINTAINERS b/MAINTAINERS index 6e7890ce82..3abe3faa4e 100644 --- a/MAINTAINERS +++ b/MAINTAINERS @@ -1864,6 +1864,13 @@ S: Maintained F: include/hw/misc/unimp.h F: hw/misc/unimp.c +Empty slot +M: Artyom Tarasenko +R: Philippe Mathieu-Daudé +S: Maintained +F: include/hw/misc/empty_slot.h +F: hw/misc/empty_slot.c + Standard VGA M: Gerd Hoffmann S: Maintained diff --git a/hw/core/Makefile.objs b/hw/core/Makefile.objs index 1d540ed6e7..d8fee8effe 100644 --- a/hw/core/Makefile.objs +++ b/hw/core/Makefile.objs @@ -24,7 +24,6 @@ common-obj-$(CONFIG_SOFTMMU) += numa.o common-obj-$(CONFIG_SOFTMMU) += clock-vmstate.o obj-$(CONFIG_SOFTMMU) += machine-qmp-cmds.o -common-obj-$(CONFIG_EMPTY_SLOT) += empty_slot.o common-obj-$(CONFIG_XILINX_AXI) += stream.o common-obj-$(CONFIG_PTIMER) += ptimer.o common-obj-$(CONFIG_FITLOADER) += loader-fit.o diff --git a/hw/core/trace-events b/hw/core/trace-events index bbb68fb6f0..1ac60ede6b 100644 --- a/hw/core/trace-events +++ b/hw/core/trace-events @@ -34,7 +34,3 @@ clock_disconnect(const char *clk) "'%s'" clock_set(const char *clk, uint64_t old, uint64_t new) "'%s', ns=%"PRIu64"->%"PRIu64 clock_propagate(const char *clk) "'%s'" clock_update(const char *clk, const char *src, uint64_t val, int cb) "'%s', src='%s', ns=%"PRIu64", cb=%d" - -# empty_slot.c -empty_slot_read(uint64_t addr, unsigned width, uint64_t value, unsigned size, const char *name) "rd addr:0x%04"PRIx64" data:0x%0*"PRIx64" size %u [%s]" -empty_slot_write(uint64_t addr, unsigned width, uint64_t value, unsigned size, const char *name) "wr addr:0x%04"PRIx64" data:0x%0*"PRIx64" size %u [%s]" diff --git a/hw/mips/malta.c b/hw/mips/malta.c index 636c95d1fe..c973c76b2a 100644 --- a/hw/mips/malta.c +++ b/hw/mips/malta.c @@ -52,7 +52,7 @@ #include "sysemu/runstate.h" #include "qapi/error.h" #include "qemu/error-report.h" -#include "hw/empty_slot.h" +#include "hw/misc/empty_slot.h" #include "sysemu/kvm.h" #include "hw/semihosting/semihost.h" #include "hw/mips/cps.h" diff --git a/hw/misc/Makefile.objs b/hw/misc/Makefile.objs index 60a9d80b74..5aaca8a039 100644 --- a/hw/misc/Makefile.objs +++ b/hw/misc/Makefile.objs @@ -10,6 +10,7 @@ common-obj-$(CONFIG_EDU) += edu.o common-obj-$(CONFIG_PCA9552) += pca9552.o common-obj-$(CONFIG_UNIMP) += unimp.o +common-obj-$(CONFIG_EMPTY_SLOT) += empty_slot.o common-obj-$(CONFIG_FW_CFG_DMA) += vmcoreinfo.o # ARM devices diff --git a/hw/core/empty_slot.c b/hw/misc/empty_slot.c similarity index 96% rename from hw/core/empty_slot.c rename to hw/misc/empty_slot.c index d28f7f99c9..54be085189 100644 --- a/hw/core/empty_slot.c +++ b/hw/misc/empty_slot.c @@ -11,9 +11,8 @@ #include "qemu/osdep.h" #include "hw/sysbus.h" -#include "qemu/module.h" #include "hw/qdev-properties.h" -#include "hw/empty_slot.h" +#include "hw/misc/empty_slot.h" #include "trace.h" #define TYPE_EMPTY_SLOT "empty_slot" @@ -90,6 +89,7 @@ static void empty_slot_class_init(ObjectClass *klass, void *data) dc->realize = empty_slot_realize; device_class_set_props(dc, empty_slot_properties); + set_bit(DEVICE_CATEGORY_MISC, dc->categories); } static const TypeInfo empty_slot_info = { diff --git a/hw/misc/trace-events b/hw/misc/trace-events index a5862b2bed..0cb4c64ae7 100644 --- a/hw/misc/trace-events +++ b/hw/misc/trace-events @@ -39,6 +39,10 @@ ecc_mem_readl_ecr1(uint32_t ret) "Read event count 2 0x%08x" ecc_diag_mem_writeb(uint64_t addr, uint32_t val) "Write diagnostic %"PRId64" = 0x%02x" ecc_diag_mem_readb(uint64_t addr, uint32_t ret) "Read diagnostic %"PRId64"= 0x%02x" +# empty_slot.c +empty_slot_read(uint64_t addr, unsigned width, uint64_t value, unsigned size, const char *name) "rd addr:0x%04"PRIx64" data:0x%0*"PRIx64" size %u [%s]" +empty_slot_write(uint64_t addr, unsigned width, uint64_t value, unsigned size, const char *name) "wr addr:0x%04"PRIx64" data:0x%0*"PRIx64" size %u [%s]" + # slavio_misc.c slavio_misc_update_irq_raise(void) "Raise IRQ" slavio_misc_update_irq_lower(void) "Lower IRQ" diff --git a/hw/sparc/sun4m.c b/hw/sparc/sun4m.c index fa3dd7775f..a16e667bee 100644 --- a/hw/sparc/sun4m.c +++ b/hw/sparc/sun4m.c @@ -46,7 +46,7 @@ #include "hw/nvram/chrp_nvram.h" #include "hw/nvram/fw_cfg.h" #include "hw/char/escc.h" -#include "hw/empty_slot.h" +#include "hw/misc/empty_slot.h" #include "hw/misc/unimp.h" #include "hw/irq.h" #include "hw/loader.h" diff --git a/include/hw/empty_slot.h b/include/hw/empty_slot.h deleted file mode 100644 index cb9a221aa6..0000000000 --- a/include/hw/empty_slot.h +++ /dev/null @@ -1,9 +0,0 @@ -#ifndef HW_EMPTY_SLOT_H -#define HW_EMPTY_SLOT_H - -#include "exec/hwaddr.h" - -/* empty_slot.c */ -void empty_slot_init(hwaddr addr, uint64_t slot_size); - -#endif diff --git a/include/hw/misc/empty_slot.h b/include/hw/misc/empty_slot.h new file mode 100644 index 0000000000..b023bc2d91 --- /dev/null +++ b/include/hw/misc/empty_slot.h @@ -0,0 +1,19 @@ +/* + * QEMU Empty Slot + * + * The empty_slot device emulates known to a bus but not connected devices. + * + * Copyright (c) 2010 Artyom Tarasenko + * + * This code is licensed under the GNU GPL v2 or (at your option) any later + * version. + */ + +#ifndef HW_EMPTY_SLOT_H +#define HW_EMPTY_SLOT_H + +#include "exec/hwaddr.h" + +void empty_slot_init(hwaddr addr, uint64_t slot_size); + +#endif From 28c78fe818257eb1229448ac672e9f350b37437d Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Philippe=20Mathieu-Daud=C3=A9?= Date: Mon, 24 Jun 2019 18:55:47 +0200 Subject: [PATCH 07/16] hw/misc/empty_slot: Name the slots when created MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Directly set the slot name when creating the device, to display the device name in trace events. Signed-off-by: Philippe Mathieu-Daudé Acked-by: Artyom Tarasenko Message-Id: <20200510152840.13558-8-f4bug@amsat.org> --- hw/mips/malta.c | 2 +- hw/misc/empty_slot.c | 2 +- hw/sparc/sun4m.c | 10 +++++++--- include/hw/misc/empty_slot.h | 2 +- 4 files changed, 10 insertions(+), 6 deletions(-) diff --git a/hw/mips/malta.c b/hw/mips/malta.c index c973c76b2a..62063b2305 100644 --- a/hw/mips/malta.c +++ b/hw/mips/malta.c @@ -1241,7 +1241,7 @@ void mips_malta_init(MachineState *machine) * exception when accessing invalid memory. Create an empty slot to * emulate this feature. */ - empty_slot_init(0, 0x20000000); + empty_slot_init("GT64120", 0, 0x20000000); qdev_init_nofail(dev); diff --git a/hw/misc/empty_slot.c b/hw/misc/empty_slot.c index 54be085189..b568ae202b 100644 --- a/hw/misc/empty_slot.c +++ b/hw/misc/empty_slot.c @@ -50,7 +50,7 @@ static const MemoryRegionOps empty_slot_ops = { .endianness = DEVICE_NATIVE_ENDIAN, }; -void empty_slot_init(hwaddr addr, uint64_t slot_size) +void empty_slot_init(const char *name, hwaddr addr, uint64_t slot_size) { if (slot_size > 0) { /* Only empty slots larger than 0 byte need handling. */ diff --git a/hw/sparc/sun4m.c b/hw/sparc/sun4m.c index a16e667bee..249f7ba7ea 100644 --- a/hw/sparc/sun4m.c +++ b/hw/sparc/sun4m.c @@ -884,7 +884,8 @@ static void sun4m_hw_init(const struct sun4m_hwdef *hwdef, /* models without ECC don't trap when missing ram is accessed */ if (!hwdef->ecc_base) { - empty_slot_init(machine->ram_size, hwdef->max_mem - machine->ram_size); + empty_slot_init("ecc", machine->ram_size, + hwdef->max_mem - machine->ram_size); } prom_init(hwdef->slavio_base, bios_name); @@ -915,7 +916,8 @@ static void sun4m_hw_init(const struct sun4m_hwdef *hwdef, Software shouldn't use aliased addresses, neither should it crash when does. Using empty_slot instead of aliasing can help with debugging such accesses */ - empty_slot_init(hwdef->iommu_pad_base,hwdef->iommu_pad_len); + empty_slot_init("iommu.alias", + hwdef->iommu_pad_base, hwdef->iommu_pad_len); } sparc32_dma_init(hwdef->dma_base, @@ -964,7 +966,9 @@ static void sun4m_hw_init(const struct sun4m_hwdef *hwdef, for (i = 0; i < MAX_VSIMMS; i++) { /* vsimm registers probed by OBP */ if (hwdef->vsimm[i].reg_base) { - empty_slot_init(hwdef->vsimm[i].reg_base, 0x2000); + char *name = g_strdup_printf("vsimm[%d]", i); + empty_slot_init(name, hwdef->vsimm[i].reg_base, 0x2000); + g_free(name); } } diff --git a/include/hw/misc/empty_slot.h b/include/hw/misc/empty_slot.h index b023bc2d91..dec56e56ae 100644 --- a/include/hw/misc/empty_slot.h +++ b/include/hw/misc/empty_slot.h @@ -14,6 +14,6 @@ #include "exec/hwaddr.h" -void empty_slot_init(hwaddr addr, uint64_t slot_size); +void empty_slot_init(const char *name, hwaddr addr, uint64_t slot_size); #endif From acd2a001e0a1658b90c912f7aaf7beb1e341b1d2 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Philippe=20Mathieu-Daud=C3=A9?= Date: Sun, 1 Dec 2019 21:35:24 +0100 Subject: [PATCH 08/16] hw/sparc/leon3: Map the UART device unconditionally MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit The UART is present on the chipset regardless there is a character device connected to it. Map it unconditionally. Signed-off-by: Philippe Mathieu-Daudé Acked-by: Artyom Tarasenko Reviewed-by: KONRAD Frederic Message-Id: <20200608172144.20461-2-f4bug@amsat.org> --- hw/sparc/leon3.c | 18 ++++++++---------- 1 file changed, 8 insertions(+), 10 deletions(-) diff --git a/hw/sparc/leon3.c b/hw/sparc/leon3.c index 8f024dab7b..cc55117dec 100644 --- a/hw/sparc/leon3.c +++ b/hw/sparc/leon3.c @@ -339,16 +339,14 @@ static void leon3_generic_hw_init(MachineState *machine) 0, LEON3_TIMER_IRQ, GRLIB_APBIO_AREA); /* Allocate uart */ - if (serial_hd(0)) { - dev = qdev_create(NULL, TYPE_GRLIB_APB_UART); - qdev_prop_set_chr(dev, "chrdev", serial_hd(0)); - qdev_init_nofail(dev); - sysbus_mmio_map(SYS_BUS_DEVICE(dev), 0, LEON3_UART_OFFSET); - sysbus_connect_irq(SYS_BUS_DEVICE(dev), 0, cpu_irqs[LEON3_UART_IRQ]); - grlib_apb_pnp_add_entry(apb_pnp, LEON3_UART_OFFSET, 0xFFF, - GRLIB_VENDOR_GAISLER, GRLIB_APBUART_DEV, 1, - LEON3_UART_IRQ, GRLIB_APBIO_AREA); - } + dev = qdev_create(NULL, TYPE_GRLIB_APB_UART); + qdev_prop_set_chr(dev, "chrdev", serial_hd(0)); + qdev_init_nofail(dev); + sysbus_mmio_map(SYS_BUS_DEVICE(dev), 0, LEON3_UART_OFFSET); + sysbus_connect_irq(SYS_BUS_DEVICE(dev), 0, cpu_irqs[LEON3_UART_IRQ]); + grlib_apb_pnp_add_entry(apb_pnp, LEON3_UART_OFFSET, 0xFFF, + GRLIB_VENDOR_GAISLER, GRLIB_APBUART_DEV, 1, + LEON3_UART_IRQ, GRLIB_APBIO_AREA); } static void leon3_generic_machine_init(MachineClass *mc) From bec6e07afde3bffb52f1a9d26a90ccbdfff13690 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Philippe=20Mathieu-Daud=C3=A9?= Date: Sun, 1 Dec 2019 21:35:24 +0100 Subject: [PATCH 09/16] hw/sparc64/niagara: Map the UART device unconditionally MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit The UART is present on the machine regardless there is a character device connected to it. Map it unconditionally. Signed-off-by: Philippe Mathieu-Daudé Reviewed-by: Artyom Tarasenko Message-Id: <20200608172144.20461-4-f4bug@amsat.org> --- hw/sparc64/niagara.c | 6 ++---- 1 file changed, 2 insertions(+), 4 deletions(-) diff --git a/hw/sparc64/niagara.c b/hw/sparc64/niagara.c index ab5ef8c5b3..148a26890e 100644 --- a/hw/sparc64/niagara.c +++ b/hw/sparc64/niagara.c @@ -152,10 +152,8 @@ static void niagara_init(MachineState *machine) exit(1); } } - if (serial_hd(0)) { - serial_mm_init(sysmem, NIAGARA_UART_BASE, 0, NULL, 115200, - serial_hd(0), DEVICE_BIG_ENDIAN); - } + serial_mm_init(sysmem, NIAGARA_UART_BASE, 0, NULL, + 115200, serial_hd(0), DEVICE_BIG_ENDIAN); create_unimplemented_device("sun4v-iob", NIAGARA_IOBBASE, NIAGARA_IOBSIZE); sun4v_rtc_init(NIAGARA_RTC_BASE); } From aceeb71306b41ab0ad2eb82d15a2beb6d8ea0e49 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Philippe=20Mathieu-Daud=C3=A9?= Date: Mon, 8 Jun 2020 19:14:37 +0200 Subject: [PATCH 10/16] hw/sparc64/niagara: Remove duplicated NIAGARA_UART_BASE definition MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit NIAGARA_UART_BASE is already defined few lines earlier. Signed-off-by: Philippe Mathieu-Daudé Reviewed-by: Artyom Tarasenko Message-Id: <20200608172144.20461-3-f4bug@amsat.org> --- hw/sparc64/niagara.c | 1 - 1 file changed, 1 deletion(-) diff --git a/hw/sparc64/niagara.c b/hw/sparc64/niagara.c index 148a26890e..a87d55f6bb 100644 --- a/hw/sparc64/niagara.c +++ b/hw/sparc64/niagara.c @@ -68,7 +68,6 @@ typedef struct NiagaraBoardState { #define NIAGARA_VDISK_BASE 0x1f40000000ULL #define NIAGARA_RTC_BASE 0xfff0c1fff8ULL -#define NIAGARA_UART_BASE 0x1f10000000ULL /* Firmware layout * From bb15013ef34617eb1344f5276292cadd326c21b2 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Philippe=20Mathieu-Daud=C3=A9?= Date: Tue, 31 Mar 2020 11:56:22 +0200 Subject: [PATCH 11/16] hw/misc/grlib_ahb_apb_pnp: Avoid crash when writing to AHB PnP registers MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Similarly to commit 158b659451 with the APB PnP registers, guests can crash QEMU when writting to the AHB PnP registers: $ echo 'writeb 0xfffff042 69' | qemu-system-sparc -M leon3_generic -S -bios /etc/magic -qtest stdio [I 1571938309.932255] OPENED [R +0.063474] writeb 0xfffff042 69 Segmentation fault (core dumped) (gdb) bt #0 0x0000000000000000 in () #1 0x0000562999110df4 in memory_region_write_with_attrs_accessor (mr=mr@entry=0x56299aa28ea0, addr=66, value=value@entry=0x7fff6abe13b8, size=size@entry=1, shift=, mask=mask@entry=255, attrs=...) at memory.c:503 #2 0x000056299911095e in access_with_adjusted_size (addr=addr@entry=66, value=value@entry=0x7fff6abe13b8, size=size@entry=1, access_size_min=, access_size_max=, access_fn=access_fn@entry= 0x562999110d70 , mr=0x56299aa28ea0, attrs=...) at memory.c:539 #3 0x0000562999114fba in memory_region_dispatch_write (mr=mr@entry=0x56299aa28ea0, addr=66, data=, op=, attrs=attrs@entry=...) at memory.c:1482 #4 0x00005629990c0860 in flatview_write_continue (fv=fv@entry=0x56299aa7d8a0, addr=addr@entry=4294963266, attrs=..., ptr=ptr@entry=0x7fff6abe1540, len=len@entry=1, addr1=, l=, mr=0x56299aa28ea0) at include/qemu/host-utils.h:164 #5 0x00005629990c0a76 in flatview_write (fv=0x56299aa7d8a0, addr=4294963266, attrs=..., buf=0x7fff6abe1540, len=1) at exec.c:3165 #6 0x00005629990c4c1b in address_space_write (as=, addr=, attrs=..., attrs@entry=..., buf=buf@entry=0x7fff6abe1540, len=len@entry=1) at exec.c:3256 #7 0x000056299910f807 in qtest_process_command (chr=chr@entry=0x5629995ee920 , words=words@entry=0x56299acfcfa0) at qtest.c:437 Instead of crashing, log the access as unimplemented. Signed-off-by: Philippe Mathieu-Daudé Reviewed-by: KONRAD Frederic Message-Id: <20200331105048.27989-3-f4bug@amsat.org> --- hw/misc/grlib_ahb_apb_pnp.c | 7 +++++++ 1 file changed, 7 insertions(+) diff --git a/hw/misc/grlib_ahb_apb_pnp.c b/hw/misc/grlib_ahb_apb_pnp.c index e230e25363..72a8764776 100644 --- a/hw/misc/grlib_ahb_apb_pnp.c +++ b/hw/misc/grlib_ahb_apb_pnp.c @@ -136,8 +136,15 @@ static uint64_t grlib_ahb_pnp_read(void *opaque, hwaddr offset, unsigned size) return ahb_pnp->regs[offset >> 2]; } +static void grlib_ahb_pnp_write(void *opaque, hwaddr addr, + uint64_t val, unsigned size) +{ + qemu_log_mask(LOG_UNIMP, "%s not implemented\n", __func__); +} + static const MemoryRegionOps grlib_ahb_pnp_ops = { .read = grlib_ahb_pnp_read, + .write = grlib_ahb_pnp_write, .endianness = DEVICE_BIG_ENDIAN, }; From 1a5a5570889df9cdd42dd85223e03a5f35025a86 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Philippe=20Mathieu-Daud=C3=A9?= Date: Tue, 31 Mar 2020 11:59:49 +0200 Subject: [PATCH 12/16] hw/misc/grlib_ahb_apb_pnp: Fix AHB PnP 8-bit accesses MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit The Plug & Play region of the AHB/APB bridge can be accessed by various word size, however the implementation is clearly restricted to 32-bit: static uint64_t grlib_ahb_pnp_read(void *opaque, hwaddr offset, unsigned size) { AHBPnp *ahb_pnp = GRLIB_AHB_PNP(opaque); return ahb_pnp->regs[offset >> 2]; } Similarly to commit 0fbe394a64 with the APB PnP registers, set the MemoryRegionOps::impl min/max fields to 32-bit, so memory.c::access_with_adjusted_size() can adjust when the access is not 32-bit. Signed-off-by: Philippe Mathieu-Daudé Reviewed-by: KONRAD Frederic Message-Id: <20200331105048.27989-4-f4bug@amsat.org> --- hw/misc/grlib_ahb_apb_pnp.c | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/hw/misc/grlib_ahb_apb_pnp.c b/hw/misc/grlib_ahb_apb_pnp.c index 72a8764776..d22ed00206 100644 --- a/hw/misc/grlib_ahb_apb_pnp.c +++ b/hw/misc/grlib_ahb_apb_pnp.c @@ -146,6 +146,10 @@ static const MemoryRegionOps grlib_ahb_pnp_ops = { .read = grlib_ahb_pnp_read, .write = grlib_ahb_pnp_write, .endianness = DEVICE_BIG_ENDIAN, + .impl = { + .min_access_size = 4, + .max_access_size = 4, + }, }; static void grlib_ahb_pnp_realize(DeviceState *dev, Error **errp) From d15188ddcffe0239295f48756bab31e76d88007a Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Philippe=20Mathieu-Daud=C3=A9?= Date: Tue, 31 Mar 2020 12:02:47 +0200 Subject: [PATCH 13/16] hw/misc/grlib_ahb_apb_pnp: Add trace events on read accesses MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: Philippe Mathieu-Daudé Reviewed-by: KONRAD Frederic Message-Id: <20200331105048.27989-5-f4bug@amsat.org> --- hw/misc/grlib_ahb_apb_pnp.c | 13 +++++++++++-- hw/misc/trace-events | 4 ++++ 2 files changed, 15 insertions(+), 2 deletions(-) diff --git a/hw/misc/grlib_ahb_apb_pnp.c b/hw/misc/grlib_ahb_apb_pnp.c index d22ed00206..43e001c3c7 100644 --- a/hw/misc/grlib_ahb_apb_pnp.c +++ b/hw/misc/grlib_ahb_apb_pnp.c @@ -25,6 +25,7 @@ #include "qemu/log.h" #include "hw/sysbus.h" #include "hw/misc/grlib_ahb_apb_pnp.h" +#include "trace.h" #define GRLIB_PNP_VENDOR_SHIFT (24) #define GRLIB_PNP_VENDOR_SIZE (8) @@ -132,8 +133,12 @@ void grlib_ahb_pnp_add_entry(AHBPnp *dev, uint32_t address, uint32_t mask, static uint64_t grlib_ahb_pnp_read(void *opaque, hwaddr offset, unsigned size) { AHBPnp *ahb_pnp = GRLIB_AHB_PNP(opaque); + uint32_t val; - return ahb_pnp->regs[offset >> 2]; + val = ahb_pnp->regs[offset >> 2]; + trace_grlib_ahb_pnp_read(offset, val); + + return val; } static void grlib_ahb_pnp_write(void *opaque, hwaddr addr, @@ -239,8 +244,12 @@ void grlib_apb_pnp_add_entry(APBPnp *dev, uint32_t address, uint32_t mask, static uint64_t grlib_apb_pnp_read(void *opaque, hwaddr offset, unsigned size) { APBPnp *apb_pnp = GRLIB_APB_PNP(opaque); + uint32_t val; - return apb_pnp->regs[offset >> 2]; + val = apb_pnp->regs[offset >> 2]; + trace_grlib_apb_pnp_read(offset, val); + + return val; } static void grlib_apb_pnp_write(void *opaque, hwaddr addr, diff --git a/hw/misc/trace-events b/hw/misc/trace-events index 0cb4c64ae7..5561746866 100644 --- a/hw/misc/trace-events +++ b/hw/misc/trace-events @@ -202,3 +202,7 @@ via1_rtc_cmd_pram_read(int addr, int value) "addr=%u value=0x%02x" via1_rtc_cmd_pram_write(int addr, int value) "addr=%u value=0x%02x" via1_rtc_cmd_pram_sect_read(int sector, int offset, int addr, int value) "sector=%u offset=%u addr=%d value=0x%02x" via1_rtc_cmd_pram_sect_write(int sector, int offset, int addr, int value) "sector=%u offset=%u addr=%d value=0x%02x" + +# grlib_ahb_apb_pnp.c +grlib_ahb_pnp_read(uint64_t addr, uint32_t value) "AHB PnP read addr:0x%03"PRIx64" data:0x%08x" +grlib_apb_pnp_read(uint64_t addr, uint32_t value) "APB PnP read addr:0x%03"PRIx64" data:0x%08x" From 8e071cd40143d86e987b3616a63ccf1275750530 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Philippe=20Mathieu-Daud=C3=A9?= Date: Tue, 31 Mar 2020 11:38:01 +0200 Subject: [PATCH 14/16] hw/timer/grlib_gptimer: Display frequency in decimal MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: Philippe Mathieu-Daudé Reviewed-by: KONRAD Frederic Message-Id: <20200331105048.27989-6-f4bug@amsat.org> --- hw/timer/trace-events | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/hw/timer/trace-events b/hw/timer/trace-events index 80ea197594..866c9f546a 100644 --- a/hw/timer/trace-events +++ b/hw/timer/trace-events @@ -19,7 +19,7 @@ slavio_timer_mem_writel_invalid(uint64_t addr) "invalid write address 0x%"PRIx64 grlib_gptimer_enable(int id, uint32_t count) "timer:%d set count 0x%x and run" grlib_gptimer_disabled(int id, uint32_t config) "timer:%d Timer disable config 0x%x" grlib_gptimer_restart(int id, uint32_t reload) "timer:%d reload val: 0x%x" -grlib_gptimer_set_scaler(uint32_t scaler, uint32_t freq) "scaler:0x%x freq: 0x%x" +grlib_gptimer_set_scaler(uint32_t scaler, uint32_t freq) "scaler:0x%x freq:%uHz" grlib_gptimer_hit(int id) "timer:%d HIT" grlib_gptimer_readl(int id, uint64_t addr, uint32_t val) "timer:%d addr 0x%"PRIx64" 0x%x" grlib_gptimer_writel(int id, uint64_t addr, uint32_t val) "timer:%d addr 0x%"PRIx64" 0x%x" From 304c1c8aa5e948ea11aa64acca0e485a185cedc9 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Philippe=20Mathieu-Daud=C3=A9?= Date: Tue, 31 Mar 2020 11:38:15 +0200 Subject: [PATCH 15/16] target/sparc/int32_helper: Remove DEBUG_PCALL definition MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit We define DEBUG_PCALL since b884fc5e (2012-10-06). 7.5 years later it is safe to assume we can remove it :) Signed-off-by: Philippe Mathieu-Daudé Reviewed-by: KONRAD Frederic Message-Id: <20200331105048.27989-7-f4bug@amsat.org> --- target/sparc/int32_helper.c | 5 ----- 1 file changed, 5 deletions(-) diff --git a/target/sparc/int32_helper.c b/target/sparc/int32_helper.c index 813b47dbb2..c56dd3df18 100644 --- a/target/sparc/int32_helper.c +++ b/target/sparc/int32_helper.c @@ -23,9 +23,7 @@ #include "exec/log.h" #include "sysemu/runstate.h" -#define DEBUG_PCALL -#ifdef DEBUG_PCALL static const char * const excp_names[0x80] = { [TT_TFAULT] = "Instruction Access Fault", [TT_ILL_INSN] = "Illegal Instruction", @@ -58,7 +56,6 @@ static const char * const excp_names[0x80] = { [TT_DIV_ZERO] = "Division By Zero", [TT_NCP_INSN] = "Coprocessor Disabled", }; -#endif void sparc_cpu_do_interrupt(CPUState *cs) { @@ -71,7 +68,6 @@ void sparc_cpu_do_interrupt(CPUState *cs) cpu_get_psr(env); } -#ifdef DEBUG_PCALL if (qemu_loglevel_mask(CPU_LOG_INT)) { static int count; const char *name; @@ -104,7 +100,6 @@ void sparc_cpu_do_interrupt(CPUState *cs) #endif count++; } -#endif #if !defined(CONFIG_USER_ONLY) if (env->psret == 0) { if (cs->exception_index == 0x80 && From 86e8c353f705f14f2f2fd7a6195cefa431aa24d9 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Philippe=20Mathieu-Daud=C3=A9?= Date: Tue, 31 Mar 2020 11:49:11 +0200 Subject: [PATCH 16/16] target/sparc/int32_helper: Extract and use excp_name_str() MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Improve exception error report: Before: qemu: fatal: Trap 0x06 while interrupts disabled, Error state After: qemu: fatal: Trap 0x06 (Window Underflow) while interrupts disabled, Error state Signed-off-by: Philippe Mathieu-Daudé Reviewed-by: KONRAD Frederic Message-Id: <20200331105048.27989-8-f4bug@amsat.org> --- target/sparc/int32_helper.c | 18 ++++++++++++------ 1 file changed, 12 insertions(+), 6 deletions(-) diff --git a/target/sparc/int32_helper.c b/target/sparc/int32_helper.c index c56dd3df18..9a71e1abd8 100644 --- a/target/sparc/int32_helper.c +++ b/target/sparc/int32_helper.c @@ -57,6 +57,14 @@ static const char * const excp_names[0x80] = { [TT_NCP_INSN] = "Coprocessor Disabled", }; +static const char *excp_name_str(int32_t exception_index) +{ + if (exception_index < 0 || exception_index >= ARRAY_SIZE(excp_names)) { + return "Unknown"; + } + return excp_names[exception_index]; +} + void sparc_cpu_do_interrupt(CPUState *cs) { SPARCCPU *cpu = SPARC_CPU(cs); @@ -77,10 +85,7 @@ void sparc_cpu_do_interrupt(CPUState *cs) } else if (intno >= 0x80) { name = "Trap Instruction"; } else { - name = excp_names[intno]; - if (!name) { - name = "Unknown"; - } + name = excp_name_str(intno); } qemu_log("%6d: %s (v=%02x)\n", count, name, intno); @@ -106,8 +111,9 @@ void sparc_cpu_do_interrupt(CPUState *cs) env->def.features & CPU_FEATURE_TA0_SHUTDOWN) { qemu_system_shutdown_request(SHUTDOWN_CAUSE_GUEST_SHUTDOWN); } else { - cpu_abort(cs, "Trap 0x%02x while interrupts disabled, Error state", - cs->exception_index); + cpu_abort(cs, "Trap 0x%02x (%s) while interrupts disabled, " + "Error state", + cs->exception_index, excp_name_str(cs->exception_index)); } return; }