All of lore.kernel.org
 help / color / mirror / Atom feed
From: "Hervé Poussineau" <hpoussin@reactos.org>
To: qemu-devel@nongnu.org
Cc: "Andreas Färber" <andreas.faerber@web.de>,
	"Hervé Poussineau" <hpoussin@reactos.org>
Subject: [Qemu-devel] [RFC v2 6/7] prep: QOM'ify System I/O
Date: Sun, 14 Apr 2013 10:05:59 +0200	[thread overview]
Message-ID: <1365926760-5803-7-git-send-email-hpoussin@reactos.org> (raw)
In-Reply-To: <1365926760-5803-1-git-send-email-hpoussin@reactos.org>

Most of the functionality is extracted from hw/ppc/prep.c.
Also add support for board identification/equipment registers.

Document it for the IBM 43p emulation.

Signed-off-by: Hervé Poussineau <hpoussin@reactos.org>
---
 docs/ibm_43p.cfg       |    5 +
 hw/ppc/Makefile.objs   |    1 +
 hw/ppc/prep_systemio.c |  290 ++++++++++++++++++++++++++++++++++++++++++++++++
 trace-events           |    4 +
 4 files changed, 300 insertions(+)
 create mode 100644 hw/ppc/prep_systemio.c

diff --git a/docs/ibm_43p.cfg b/docs/ibm_43p.cfg
index 0950dd7..a265c01 100644
--- a/docs/ibm_43p.cfg
+++ b/docs/ibm_43p.cfg
@@ -35,3 +35,8 @@
   iobase = "0x170"
   iobase2 = "0x376"
   irq = "15"
+
+[device]
+  driver = "prep-systemio800"
+  ibm-planar-id = "0xc0"
+  equipment = "0xff"
diff --git a/hw/ppc/Makefile.objs b/hw/ppc/Makefile.objs
index be00d1d..cd1eb1b 100644
--- a/hw/ppc/Makefile.objs
+++ b/hw/ppc/Makefile.objs
@@ -9,6 +9,7 @@ obj-y += ppc405_boards.o ppc4xx_devs.o ppc405_uc.o ppc440_bamboo.o
 obj-y += ppc4xx_pci.o
 # PReP
 obj-y += prep.o
+obj-y += prep_systemio.o
 # OldWorld PowerMac
 obj-y += mac_oldworld.o
 # NewWorld PowerMac
diff --git a/hw/ppc/prep_systemio.c b/hw/ppc/prep_systemio.c
new file mode 100644
index 0000000..502338d
--- /dev/null
+++ b/hw/ppc/prep_systemio.c
@@ -0,0 +1,290 @@
+/*
+ * QEMU PReP System I/O emulation
+ *
+ * Copyright (c) 2003-2007 Jocelyn Mayer
+ * Copyright (c) 2010-2012 Herve Poussineau
+ * Copyright (c) 2010-2011 Andreas Faerber
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a copy
+ * of this software and associated documentation files (the "Software"), to deal
+ * in the Software without restriction, including without limitation the rights
+ * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+ * copies of the Software, and to permit persons to whom the Software is
+ * furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included in
+ * all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
+ * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+ * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
+ * THE SOFTWARE.
+ */
+
+#include "hw/isa/isa.h"
+#include "exec/address-spaces.h"
+#include "qemu/error-report.h" /* for error_report() */
+#include "sysemu/sysemu.h" /* for vm_stop() */
+#include "trace.h"
+
+/* Bit as defined in PowerPC Reference Plaform v1.1, sect. 6.1.5, p. 132 */
+#define BIT(n) (1 << (7 - (n)))
+
+typedef struct PrepIo800State {
+    ISADevice dev;
+    MemoryRegion ppc_parity_mem;
+
+    qemu_irq non_contiguous_io_map_irq;
+    uint8_t equipment; /* 0x080c */
+    uint8_t system_control; /* 0x081c */
+    uint8_t iomap_type; /* 0x0850 */
+    uint8_t ibm_planar_id; /* 0x0852 */
+    qemu_irq softreset_irq;
+} PrepIo800State;
+
+/* PORT 0092 -- Special Port 92 (Read/Write) */
+
+enum {
+    PORT0092_SOFTRESET  = BIT(7),
+    PORT0092_LE_MODE    = BIT(6),
+};
+
+static void prep_port0092_write(void *opaque, uint32_t addr, uint32_t val)
+{
+    PrepIo800State *s = opaque;
+
+    trace_prep_systemio_write(addr, val);
+
+    if ((val & PORT0092_SOFTRESET) != 0) {
+        qemu_irq_raise(s->softreset_irq);
+    } else {
+        qemu_irq_lower(s->softreset_irq);
+    }
+
+    if ((val & PORT0092_LE_MODE) != 0) {
+        /* XXX Not supported yet */
+        error_report("little-endian mode not supported");
+        vm_stop(RUN_STATE_PAUSED);
+    } else {
+        /* Nothing to do */
+    }
+}
+
+static uint32_t prep_port0092_read(void *opaque, uint32_t addr)
+{
+    /* XXX LE mode unsupported */
+    trace_prep_systemio_read(addr, 0);
+    return 0;
+}
+
+/* PORT 0808 -- Hardfile Light Register (Write Only) */
+
+enum {
+    PORT0808_HARDFILE_LIGHT_ON  = BIT(7),
+};
+
+static void prep_port0808_write(void *opaque, uint32_t addr, uint32_t val)
+{
+    trace_prep_systemio_write(addr, val);
+}
+
+/* PORT 0810 -- Password Protect 1 Register (Write Only) */
+
+/* reset by port 0x4D in the SIO */
+static void prep_port0810_write(void *opaque, uint32_t addr, uint32_t val)
+{
+    trace_prep_systemio_write(addr, val);
+}
+
+/* PORT 0812 -- Password Protect 2 Register (Write Only) */
+
+/* reset by port 0x4D in the SIO */
+static void prep_port0812_write(void *opaque, uint32_t addr, uint32_t val)
+{
+    trace_prep_systemio_write(addr, val);
+}
+
+/* PORT 0814 -- L2 Invalidate Register (Write Only) */
+
+static void prep_port0814_write(void *opaque, uint32_t addr, uint32_t val)
+{
+    trace_prep_systemio_write(addr, val);
+}
+
+/* PORT 0818 -- Reserved for Keylock (Read Only) */
+
+enum {
+    PORT0818_KEYLOCK_SIGNAL_HIGH    = BIT(7),
+};
+
+static uint32_t prep_port0818_read(void *opaque, uint32_t addr)
+{
+    uint32_t val = 0;
+    trace_prep_systemio_read(addr, val);
+    return val;
+}
+
+/* PORT 080C -- Equipment */
+
+enum {
+    PORT080C_SCSIFUSE               = BIT(1),
+    PORT080C_L2_COPYBACK            = BIT(4),
+    PORT080C_L2_256                 = BIT(5),
+    PORT080C_UPGRADE_CPU            = BIT(6),
+    PORT080C_L2                     = BIT(7),
+};
+
+static uint32_t prep_port080c_read(void *opaque, uint32_t addr)
+{
+    PrepIo800State *s = opaque;
+    trace_prep_systemio_read(addr, s->equipment);
+    return s->equipment;
+}
+
+/* PORT 081C -- System Control Register (Read/Write) */
+
+enum {
+    PORT081C_FLOPPY_MOTOR_INHIBIT   = BIT(3),
+    PORT081C_MASK_TEA               = BIT(2),
+    PORT081C_L2_UPDATE_INHIBIT      = BIT(1),
+    PORT081C_L2_CACHEMISS_INHIBIT   = BIT(0),
+};
+
+static void prep_port081c_write(void *opaque, uint32_t addr, uint32_t val)
+{
+    PrepIo800State *s = opaque;
+    trace_prep_systemio_write(addr, val);
+    s->system_control = val;
+}
+
+static uint32_t prep_port081c_read(void *opaque, uint32_t addr)
+{
+    PrepIo800State *s = opaque;
+    trace_prep_systemio_read(addr, s->system_control);
+    return s->system_control;
+}
+
+/* System Board Identification */
+
+static uint32_t prep_port0852_read(void *opaque, uint32_t addr)
+{
+    PrepIo800State *s = opaque;
+    trace_prep_systemio_read(addr, s->ibm_planar_id);
+    return s->ibm_planar_id;
+}
+
+/* PORT 0850 -- I/O Map Type Register (Read/Write) */
+
+enum {
+    PORT0850_IOMAP_NONCONTIGUOUS    = BIT(7),
+};
+
+static uint32_t prep_port0850_read(void *opaque, uint32_t addr)
+{
+    PrepIo800State *s = opaque;
+    trace_prep_systemio_read(addr, s->iomap_type);
+    return s->iomap_type;
+}
+
+static void prep_port0850_write(void *opaque, uint32_t addr, uint32_t val)
+{
+    PrepIo800State *s = opaque;
+
+    trace_prep_systemio_write(addr, val);
+    qemu_set_irq(s->non_contiguous_io_map_irq,
+                 val & PORT0850_IOMAP_NONCONTIGUOUS ? 1 : 0);
+    s->iomap_type = val;
+}
+
+static const MemoryRegionPortio ppc_io800_port_list[] = {
+    { 0x092, 1, 1, .read = prep_port0092_read,
+                   .write = prep_port0092_write, },
+    { 0x808, 1, 1, .write = prep_port0808_write, },
+    { 0x80c, 1, 1, .read = prep_port080c_read, },
+    { 0x810, 1, 1, .write = prep_port0810_write, },
+    { 0x812, 1, 1, .write = prep_port0812_write, },
+    { 0x814, 1, 1, .write = prep_port0814_write, },
+    { 0x818, 1, 1, .read = prep_port0818_read, },
+    { 0x81c, 1, 1, .read = prep_port081c_read,
+                   .write = prep_port081c_write, },
+    { 0x850, 1, 1, .read = prep_port0850_read,
+                   .write = prep_port0850_write, },
+    { 0x852, 1, 1, .read = prep_port0852_read, },
+    PORTIO_END_OF_LIST()
+};
+
+static uint64_t ppc_parity_error_readl(void *opaque, hwaddr addr,
+                                       unsigned int size)
+{
+    uint32_t val = 0;
+    trace_prep_systemio_read((unsigned int)addr, val);
+    return val;
+}
+
+static const MemoryRegionOps ppc_parity_error_ops = {
+    .read = ppc_parity_error_readl,
+    .valid = {
+        .min_access_size = 4,
+        .max_access_size = 4,
+    },
+};
+
+static int prep_systemio_init(ISADevice *dev)
+{
+    PrepIo800State *s = DO_UPCAST(PrepIo800State, dev, dev);
+    qdev_init_gpio_out(&dev->qdev, &s->non_contiguous_io_map_irq, 1);
+    s->iomap_type = 0; /* contiguous mode XXX 0x1? */
+    s->softreset_irq = first_cpu->irq_inputs[PPC6xx_INPUT_HRESET];
+
+    isa_register_portio_list(dev, 0x0, ppc_io800_port_list, s, "systemio800");
+
+    memory_region_init_io(&s->ppc_parity_mem, &ppc_parity_error_ops, s,
+                          "ppc-parity", 0x4);
+    memory_region_add_subregion(get_system_memory(), 0xbfffeff0,
+                                &s->ppc_parity_mem);
+    return 0;
+}
+
+static const VMStateDescription vmstate_prep_systemio = {
+    .name = "prep_systemio",
+    .version_id = 1,
+    .minimum_version_id = 1,
+    .fields = (VMStateField[]) {
+        VMSTATE_UINT8(system_control, PrepIo800State),
+        VMSTATE_UINT8(iomap_type, PrepIo800State),
+        VMSTATE_END_OF_LIST()
+    },
+};
+
+static Property prep_systemio_properties[] = {
+    DEFINE_PROP_UINT8("ibm-planar-id", PrepIo800State, ibm_planar_id, 0),
+    DEFINE_PROP_UINT8("equipment", PrepIo800State, equipment, 0),
+    DEFINE_PROP_END_OF_LIST()
+};
+
+static void prep_systemio_class_initfn(ObjectClass *klass, void *data)
+{
+    DeviceClass *dc = DEVICE_CLASS(klass);
+    ISADeviceClass *ic = ISA_DEVICE_CLASS(klass);
+    ic->init = prep_systemio_init;
+    dc->vmsd = &vmstate_prep_systemio;
+    dc->props = prep_systemio_properties;
+    dc->no_user = 1;
+}
+
+static TypeInfo prep_systemio800_info = {
+    .name          = "prep-systemio800",
+    .parent        = TYPE_ISA_DEVICE,
+    .instance_size = sizeof(PrepIo800State),
+    .class_init    = prep_systemio_class_initfn,
+};
+
+static void prep_systemio_register_types(void)
+{
+    type_register_static(&prep_systemio800_info);
+}
+
+type_init(prep_systemio_register_types)
diff --git a/trace-events b/trace-events
index 8b0ad9c..ba5b71a 100644
--- a/trace-events
+++ b/trace-events
@@ -761,6 +761,10 @@ pc87312_info_ide(uint32_t base) "base 0x%x"
 pc87312_info_parallel(uint32_t base, uint32_t irq) "base 0x%x, irq %u"
 pc87312_info_serial(int n, uint32_t base, uint32_t irq) "id=%d, base 0x%x, irq %u"
 
+# hw/ppc/prep_systemio.c
+prep_systemio_read(uint32_t addr, uint32_t val) "read addr=%x val=%x"
+prep_systemio_write(uint32_t addr, uint32_t val) "write addr=%x val=%x"
+
 # hw/mpc105.c
 mpc105_unassigned_mem_read(uint64_t addr) "Unassigned mem read %" PRIx64
 mpc105_unassigned_mem_write(uint64_t addr, uint64_t val) "Unassigned mem write %" PRIx64 " = 0x%" PRIx64
-- 
1.7.10.4

  parent reply	other threads:[~2013-04-14  8:05 UTC|newest]

Thread overview: 14+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2013-04-14  8:05 [Qemu-devel] [RFC v2 0/7] ppc/prep: add IBM RS/6000 43p machine Hervé Poussineau
2013-04-14  8:05 ` [Qemu-devel] [RFC v2 1/7] pci: add MPC105 PCI host bridge emulation Hervé Poussineau
2013-04-14  8:05 ` [Qemu-devel] [RFC v2 2/7] m48t59: move ISA ports registration to QOM constructor Hervé Poussineau
2013-04-14  8:05 ` [Qemu-devel] [RFC v2 3/7] m48t59: register a QOM type for each nvram type we support Hervé Poussineau
2013-04-14 21:41   ` Artyom Tarasenko
2013-04-15  5:52     ` Hervé Poussineau
2013-04-20  9:34     ` Blue Swirl
2013-04-20  9:56       ` Artyom Tarasenko
2013-04-20 10:39         ` Blue Swirl
2013-04-27  6:55           ` Artyom Tarasenko
2013-04-14  8:05 ` [Qemu-devel] [RFC v2 4/7] m48t59: use DeviceState in public functions Hervé Poussineau
2013-04-14  8:05 ` [Qemu-devel] [RFC v2 5/7] prep: add IBM RS/6000 7248 (43p) machine emulation Hervé Poussineau
2013-04-14  8:05 ` Hervé Poussineau [this message]
2013-04-14  8:06 ` [Qemu-devel] [RFC v2 7/7] m48t59: hack(?) to make it work on IBM 43p Hervé Poussineau

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=1365926760-5803-7-git-send-email-hpoussin@reactos.org \
    --to=hpoussin@reactos.org \
    --cc=andreas.faerber@web.de \
    --cc=qemu-devel@nongnu.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.