From: Kyle Fox <kylefoxaustin.github@gmail.com>
To: qemu-devel@nongnu.org
Cc: Kyle Fox <kylefoxaustin.github@gmail.com>,
Paolo Bonzini <pbonzini@redhat.com>,
qemu-arm@nongnu.org (open list:MCIMX95-19X19-EVK...)
Subject: [PATCH 12/16] hw/misc: add i.MX 95 PMIC (PF09/PF53/PCAL6408A) and xcache controllers
Date: Wed, 19 Aug 2026 21:48:30 -0500 [thread overview]
Message-ID: <20260820024834.3286721-13-kylefoxaustin.github@gmail.com> (raw)
In-Reply-To: <20260820024834.3286721-1-kylefoxaustin.github@gmail.com>
The i.MX 95 EVK power devices on LPI2C - the PF09 and PF53 regulators
and the PCAL6408A IO expander that the SM firmware sequences during
power-up - modelled as I2C-slave register files, plus the xcache (cache
controller) register block.
Signed-off-by: Kyle Fox <kylefoxaustin.github@gmail.com>
---
hw/misc/Kconfig | 7 +
hw/misc/imx95_pmic.c | 357 +++++++++++++++++++++++++++++++++++++++++
hw/misc/imx95_xcache.c | 185 +++++++++++++++++++++
hw/misc/meson.build | 2 +
hw/misc/trace-events | 8 +
5 files changed, 559 insertions(+)
create mode 100644 hw/misc/imx95_pmic.c
create mode 100644 hw/misc/imx95_xcache.c
diff --git a/hw/misc/Kconfig b/hw/misc/Kconfig
index 1e1cae92f6f..e1b8c390312 100644
--- a/hw/misc/Kconfig
+++ b/hw/misc/Kconfig
@@ -283,3 +283,10 @@ config IMX95_GPC
config IMX95_SRC
bool
+
+config IMX95_PMIC
+ bool
+ select I2C
+
+config IMX95_XCACHE
+ bool
diff --git a/hw/misc/imx95_pmic.c b/hw/misc/imx95_pmic.c
new file mode 100644
index 00000000000..e7101f1ed06
--- /dev/null
+++ b/hw/misc/imx95_pmic.c
@@ -0,0 +1,357 @@
+/*
+ * Minimal I2C device models for the i.MX 95 EVK System Manager:
+ * - PF09 (PF0900) PMIC (TYPE_PF09_PMIC, addr 0x08, CRC'd)
+ * - PCAL6408A 8-bit IO expander (TYPE_PCAL6408A, addr 0x20)
+ * - PF53 buck regulator (TYPE_PF53_PMIC, addr 0x2a/0x29)
+ *
+ * Copyright (c) 2026, Kyle Fox
+ *
+ * SPDX-License-Identifier: GPL-2.0-or-later
+ *
+ * The NXP SM firmware probes/configures both over LPI2C1 during board
+ * init (BRD_SM_SerialDevicesInit); a failed transfer aborts SM init.
+ * These are register-file models: writes store, reads return the stored
+ * byte. The PF09 driver protects each transfer with a J1850 CRC, so the
+ * PF09 read path appends the CRC the driver expects
+ * (CRC_J1850((devAddr<<1)|1, reg, data)); without it PF09_Init fails.
+ * No actual PMIC/regulator or GPIO behaviour is modelled.
+ */
+
+#include "qemu/osdep.h"
+#include "qemu/module.h"
+#include "hw/i2c/i2c.h"
+#include "migration/vmstate.h"
+#include "trace.h"
+
+/* ---- J1850 CRC (matches imx-sm components/crc/crc.c CRC_J1850) ---- */
+#define CRC_J1850_POLY 0x1Du
+
+static uint8_t crc_j1850(const uint8_t *p, unsigned n)
+{
+ uint32_t crc = 0xffu;
+
+ for (unsigned i = 0; i < n; i++) {
+ crc ^= p[i];
+ for (unsigned b = 0; b < 8; b++) {
+ crc = (crc & 0x80u) ? ((crc << 1) ^ CRC_J1850_POLY)
+ : ((crc << 1) & 0xffu);
+ }
+ }
+ return (uint8_t)crc;
+}
+
+/* ============================ PF09 PMIC ============================ */
+
+#define TYPE_PF09_PMIC "pf09-pmic"
+OBJECT_DECLARE_SIMPLE_TYPE(PF09State, PF09_PMIC)
+
+#define PF09_NUM_REG 256
+
+struct PF09State {
+ I2CSlave parent_obj;
+
+ uint8_t regs[PF09_NUM_REG];
+ uint8_t cur_reg;
+ uint32_t wcount; /* bytes received since START(write) */
+ uint32_t rcount; /* bytes returned since START(read) */
+};
+
+static int pf09_event(I2CSlave *i2c, enum i2c_event event)
+{
+ PF09State *s = PF09_PMIC(i2c);
+
+ switch (event) {
+ case I2C_START_SEND:
+ s->wcount = 0;
+ break;
+ case I2C_START_RECV:
+ s->rcount = 0;
+ break;
+ default:
+ break;
+ }
+ return 0; /* ACK */
+}
+
+static int pf09_send(I2CSlave *i2c, uint8_t data)
+{
+ PF09State *s = PF09_PMIC(i2c);
+
+ if (s->wcount == 0) {
+ s->cur_reg = data; /* register address */
+ } else if (s->wcount == 1) {
+ s->regs[s->cur_reg] = data; /* data byte */
+ trace_pf09_reg_write(s->cur_reg, data);
+ }
+ /* wcount >= 2 is the trailing CRC byte: accept and ignore. */
+ s->wcount++;
+ return 0; /* ACK */
+}
+
+static uint8_t pf09_recv(I2CSlave *i2c)
+{
+ PF09State *s = PF09_PMIC(i2c);
+ uint8_t val;
+
+ if (s->rcount == 0) {
+ val = s->regs[s->cur_reg];
+ trace_pf09_reg_read(s->cur_reg, val);
+ } else {
+ /* CRC over (devAddr<<1)|1, reg, data - what PF09_PmicRead checks. */
+ uint8_t buf[3] = {
+ (uint8_t)((i2c->address << 1) | 1u),
+ s->cur_reg,
+ s->regs[s->cur_reg],
+ };
+ val = crc_j1850(buf, 3);
+ }
+ s->rcount++;
+ return val;
+}
+
+static void pf09_reset_hold(Object *obj, ResetType type)
+{
+ PF09State *s = PF09_PMIC(obj);
+
+ memset(s->regs, 0, sizeof(s->regs));
+ s->cur_reg = 0;
+ s->wcount = 0;
+ s->rcount = 0;
+ /* REV_ID >= 0x20 lets PF09_Init skip the STANDBY-monitor write. */
+ s->regs[0x00] = 0x20;
+}
+
+static const VMStateDescription vmstate_pf09 = {
+ .name = TYPE_PF09_PMIC,
+ .version_id = 1,
+ .minimum_version_id = 1,
+ .fields = (const VMStateField[]) {
+ VMSTATE_I2C_SLAVE(parent_obj, PF09State),
+ VMSTATE_UINT8_ARRAY(regs, PF09State, PF09_NUM_REG),
+ VMSTATE_UINT8(cur_reg, PF09State),
+ VMSTATE_UINT32(wcount, PF09State),
+ VMSTATE_UINT32(rcount, PF09State),
+ VMSTATE_END_OF_LIST()
+ },
+};
+
+static void pf09_class_init(ObjectClass *klass, const void *data)
+{
+ DeviceClass *dc = DEVICE_CLASS(klass);
+ ResettableClass *rc = RESETTABLE_CLASS(klass);
+ I2CSlaveClass *k = I2C_SLAVE_CLASS(klass);
+
+ k->event = pf09_event;
+ k->recv = pf09_recv;
+ k->send = pf09_send;
+ dc->vmsd = &vmstate_pf09;
+ rc->phases.hold = pf09_reset_hold;
+ dc->desc = "NXP PF09 PMIC (i.MX95 SM stub)";
+}
+
+static const TypeInfo pf09_info = {
+ .name = TYPE_PF09_PMIC,
+ .parent = TYPE_I2C_SLAVE,
+ .instance_size = sizeof(PF09State),
+ .class_init = pf09_class_init,
+};
+
+/* ========================== PCAL6408A ============================= */
+
+#define TYPE_PCAL6408A "pcal6408a"
+OBJECT_DECLARE_SIMPLE_TYPE(PCAL6408AState, PCAL6408A)
+
+#define PCAL6408A_NUM_REG 256
+
+struct PCAL6408AState {
+ I2CSlave parent_obj;
+
+ uint8_t regs[PCAL6408A_NUM_REG];
+ uint8_t cur_reg;
+ uint32_t wcount;
+};
+
+static int pcal6408a_event(I2CSlave *i2c, enum i2c_event event)
+{
+ PCAL6408AState *s = PCAL6408A(i2c);
+
+ if (event == I2C_START_SEND) {
+ s->wcount = 0;
+ }
+ return 0;
+}
+
+static int pcal6408a_send(I2CSlave *i2c, uint8_t data)
+{
+ PCAL6408AState *s = PCAL6408A(i2c);
+
+ if (s->wcount == 0) {
+ s->cur_reg = data;
+ } else {
+ trace_pcal6408a_reg_write(s->cur_reg, data);
+ s->regs[s->cur_reg++] = data;
+ }
+ s->wcount++;
+ return 0;
+}
+
+static uint8_t pcal6408a_recv(I2CSlave *i2c)
+{
+ PCAL6408AState *s = PCAL6408A(i2c);
+ uint8_t val = s->regs[s->cur_reg];
+
+ trace_pcal6408a_reg_read(s->cur_reg, val);
+ s->cur_reg++;
+ return val;
+}
+
+static void pcal6408a_reset_hold(Object *obj, ResetType type)
+{
+ PCAL6408AState *s = PCAL6408A(obj);
+
+ memset(s->regs, 0, sizeof(s->regs));
+ s->cur_reg = 0;
+ s->wcount = 0;
+}
+
+static const VMStateDescription vmstate_pcal6408a = {
+ .name = TYPE_PCAL6408A,
+ .version_id = 1,
+ .minimum_version_id = 1,
+ .fields = (const VMStateField[]) {
+ VMSTATE_I2C_SLAVE(parent_obj, PCAL6408AState),
+ VMSTATE_UINT8_ARRAY(regs, PCAL6408AState, PCAL6408A_NUM_REG),
+ VMSTATE_UINT8(cur_reg, PCAL6408AState),
+ VMSTATE_UINT32(wcount, PCAL6408AState),
+ VMSTATE_END_OF_LIST()
+ },
+};
+
+static void pcal6408a_class_init(ObjectClass *klass, const void *data)
+{
+ DeviceClass *dc = DEVICE_CLASS(klass);
+ ResettableClass *rc = RESETTABLE_CLASS(klass);
+ I2CSlaveClass *k = I2C_SLAVE_CLASS(klass);
+
+ k->event = pcal6408a_event;
+ k->recv = pcal6408a_recv;
+ k->send = pcal6408a_send;
+ dc->vmsd = &vmstate_pcal6408a;
+ rc->phases.hold = pcal6408a_reset_hold;
+ dc->desc = "NXP PCAL6408A IO expander (i.MX95 SM stub)";
+}
+
+static const TypeInfo pcal6408a_info = {
+ .name = TYPE_PCAL6408A,
+ .parent = TYPE_I2C_SLAVE,
+ .instance_size = sizeof(PCAL6408AState),
+ .class_init = pcal6408a_class_init,
+};
+
+/* ============================ PF53 PMIC ============================ */
+
+/*
+ * PF5301 / PF5302 (PF53-family) buck regulators on the same LPI2C bus.
+ * BRD_SM_SerialDevicesInit calls PF53_Init() on each, which only reads
+ * the DEV_ID register and checks that the transfer ACKs (it does not
+ * validate the value, and the SM configures crcEn=false for these). So a
+ * plain register file that ACKs is sufficient to get past SM init.
+ */
+#define TYPE_PF53_PMIC "pf53-pmic"
+OBJECT_DECLARE_SIMPLE_TYPE(PF53State, PF53_PMIC)
+
+#define PF53_NUM_REG 256
+
+struct PF53State {
+ I2CSlave parent_obj;
+
+ uint8_t regs[PF53_NUM_REG];
+ uint8_t cur_reg;
+ uint32_t wcount;
+};
+
+static int pf53_event(I2CSlave *i2c, enum i2c_event event)
+{
+ PF53State *s = PF53_PMIC(i2c);
+
+ if (event == I2C_START_SEND) {
+ s->wcount = 0;
+ }
+ return 0;
+}
+
+static int pf53_send(I2CSlave *i2c, uint8_t data)
+{
+ PF53State *s = PF53_PMIC(i2c);
+
+ if (s->wcount == 0) {
+ s->cur_reg = data;
+ } else {
+ trace_pf53_reg_write(s->cur_reg, data);
+ s->regs[s->cur_reg++] = data;
+ }
+ s->wcount++;
+ return 0;
+}
+
+static uint8_t pf53_recv(I2CSlave *i2c)
+{
+ PF53State *s = PF53_PMIC(i2c);
+ uint8_t val = s->regs[s->cur_reg];
+
+ trace_pf53_reg_read(s->cur_reg, val);
+ s->cur_reg++;
+ return val;
+}
+
+static void pf53_reset_hold(Object *obj, ResetType type)
+{
+ PF53State *s = PF53_PMIC(obj);
+
+ memset(s->regs, 0, sizeof(s->regs));
+ s->cur_reg = 0;
+ s->wcount = 0;
+}
+
+static const VMStateDescription vmstate_pf53 = {
+ .name = TYPE_PF53_PMIC,
+ .version_id = 1,
+ .minimum_version_id = 1,
+ .fields = (const VMStateField[]) {
+ VMSTATE_I2C_SLAVE(parent_obj, PF53State),
+ VMSTATE_UINT8_ARRAY(regs, PF53State, PF53_NUM_REG),
+ VMSTATE_UINT8(cur_reg, PF53State),
+ VMSTATE_UINT32(wcount, PF53State),
+ VMSTATE_END_OF_LIST()
+ },
+};
+
+static void pf53_class_init(ObjectClass *klass, const void *data)
+{
+ DeviceClass *dc = DEVICE_CLASS(klass);
+ ResettableClass *rc = RESETTABLE_CLASS(klass);
+ I2CSlaveClass *k = I2C_SLAVE_CLASS(klass);
+
+ k->event = pf53_event;
+ k->recv = pf53_recv;
+ k->send = pf53_send;
+ dc->vmsd = &vmstate_pf53;
+ rc->phases.hold = pf53_reset_hold;
+ dc->desc = "NXP PF53 PMIC (i.MX95 SM stub)";
+}
+
+static const TypeInfo pf53_info = {
+ .name = TYPE_PF53_PMIC,
+ .parent = TYPE_I2C_SLAVE,
+ .instance_size = sizeof(PF53State),
+ .class_init = pf53_class_init,
+};
+
+static void imx95_pmic_register_types(void)
+{
+ type_register_static(&pf09_info);
+ type_register_static(&pcal6408a_info);
+ type_register_static(&pf53_info);
+}
+
+type_init(imx95_pmic_register_types)
diff --git a/hw/misc/imx95_xcache.c b/hw/misc/imx95_xcache.c
new file mode 100644
index 00000000000..ef7752a6201
--- /dev/null
+++ b/hw/misc/imx95_xcache.c
@@ -0,0 +1,185 @@
+/*
+ * NXP i.MX 95 XCACHE controller stub model
+ *
+ * Copyright (c) 2026, Kyle Fox
+ *
+ * SPDX-License-Identifier: GPL-2.0-or-later
+ *
+ * Minimal model of the M33 XCACHE controller (the two instances at
+ * 0x44400000 "PC" and 0x44400800 "PS"). The NXP System Manager firmware
+ * enables and invalidates its caches early in init by writing the cache
+ * control register (CCR): it sets ENCACHE plus the invalidate/push
+ * command bits and the GO bit, then polls.
+ *
+ * QEMU has no cache to model, so the only behaviour that matters is the
+ * self-clearing of the command bits: real hardware clears GO and the
+ * INVWn/PUSHWn bits once the (instantaneous, for us) operation completes,
+ * and leaves ENCACHE/config bits set. A plain RAM stub would leave GO set
+ * forever (the SM's "wait for GO to clear" loop would hang); a zero-return
+ * stub would leave ENCACHE clear (an "is cache enabled" check would hang).
+ * So CCR persists everything except the command bits, which read back 0.
+ * The line-maintenance registers (CLCR/CSAR/CCVR) are plain storage.
+ */
+
+#include "qemu/osdep.h"
+#include "qemu/log.h"
+#include "qemu/module.h"
+#include "hw/core/sysbus.h"
+#include "migration/vmstate.h"
+#include "trace.h"
+
+#define TYPE_IMX95_XCACHE "imx95.xcache"
+OBJECT_DECLARE_SIMPLE_TYPE(IMX95XCacheState, IMX95_XCACHE)
+
+/* Each instance owns 0x800 (the two M33 instances are 0x800 apart). */
+#define IMX95_XCACHE_REG_SIZE 0x800
+
+#define XCACHE_CCR 0x00
+#define XCACHE_CLCR 0x04
+#define XCACHE_CSAR 0x08
+#define XCACHE_CCVR 0x0C
+
+/* CCR bits that self-clear when the cache command completes. */
+#define CCR_GO 0x80000000u
+#define CCR_PUSHW1 0x08000000u
+#define CCR_INVW1 0x04000000u
+#define CCR_PUSHW0 0x02000000u
+#define CCR_INVW0 0x01000000u
+#define CCR_CMD_BITS \
+ (CCR_GO | CCR_PUSHW1 | CCR_INVW1 | CCR_PUSHW0 | CCR_INVW0)
+
+struct IMX95XCacheState {
+ SysBusDevice parent_obj;
+ MemoryRegion iomem;
+
+ uint32_t ccr;
+ uint32_t clcr;
+ uint32_t csar;
+ uint32_t ccvr;
+};
+
+static uint64_t imx95_xcache_read(void *opaque, hwaddr offset, unsigned size)
+{
+ IMX95XCacheState *s = opaque;
+
+ trace_imx95_xcache_read(offset);
+
+ switch (offset) {
+ case XCACHE_CCR:
+ return s->ccr;
+ case XCACHE_CLCR:
+ return s->clcr;
+ case XCACHE_CSAR:
+ return s->csar;
+ case XCACHE_CCVR:
+ return s->ccvr;
+ default:
+ qemu_log_mask(LOG_GUEST_ERROR,
+ "%s: bad read offset 0x%" HWADDR_PRIx "\n",
+ __func__, offset);
+ return 0;
+ }
+}
+
+static void imx95_xcache_write(void *opaque, hwaddr offset,
+ uint64_t value, unsigned size)
+{
+ IMX95XCacheState *s = opaque;
+
+ trace_imx95_xcache_write(offset, value);
+
+ switch (offset) {
+ case XCACHE_CCR:
+ /* Command bits complete instantly: store everything else. */
+ s->ccr = (uint32_t)value & ~CCR_CMD_BITS;
+ break;
+ case XCACHE_CLCR:
+ s->clcr = value;
+ break;
+ case XCACHE_CSAR:
+ s->csar = value;
+ break;
+ case XCACHE_CCVR:
+ s->ccvr = value;
+ break;
+ default:
+ qemu_log_mask(LOG_GUEST_ERROR,
+ "%s: bad write offset 0x%" HWADDR_PRIx
+ " value 0x%" PRIx64 "\n",
+ __func__, offset, value);
+ break;
+ }
+}
+
+static const MemoryRegionOps imx95_xcache_ops = {
+ .read = imx95_xcache_read,
+ .write = imx95_xcache_write,
+ .endianness = DEVICE_LITTLE_ENDIAN,
+ .impl = {
+ .min_access_size = 4,
+ .max_access_size = 4,
+ },
+ .valid = {
+ .min_access_size = 4,
+ .max_access_size = 4,
+ },
+};
+
+static void imx95_xcache_reset_hold(Object *obj, ResetType type)
+{
+ IMX95XCacheState *s = IMX95_XCACHE(obj);
+
+ s->ccr = 0;
+ s->clcr = 0;
+ s->csar = 0;
+ s->ccvr = 0;
+}
+
+static void imx95_xcache_init(Object *obj)
+{
+ SysBusDevice *sbd = SYS_BUS_DEVICE(obj);
+ IMX95XCacheState *s = IMX95_XCACHE(obj);
+
+ memory_region_init_io(&s->iomem, obj, &imx95_xcache_ops, s,
+ TYPE_IMX95_XCACHE, IMX95_XCACHE_REG_SIZE);
+ sysbus_init_mmio(sbd, &s->iomem);
+}
+
+static const VMStateDescription vmstate_imx95_xcache = {
+ .name = TYPE_IMX95_XCACHE,
+ .version_id = 1,
+ .minimum_version_id = 1,
+ .fields = (const VMStateField[]) {
+ VMSTATE_UINT32(ccr, IMX95XCacheState),
+ VMSTATE_UINT32(clcr, IMX95XCacheState),
+ VMSTATE_UINT32(csar, IMX95XCacheState),
+ VMSTATE_UINT32(ccvr, IMX95XCacheState),
+ VMSTATE_END_OF_LIST()
+ },
+};
+
+static void imx95_xcache_class_init(ObjectClass *klass, const void *data)
+{
+ DeviceClass *dc = DEVICE_CLASS(klass);
+ ResettableClass *rc = RESETTABLE_CLASS(klass);
+
+ dc->vmsd = &vmstate_imx95_xcache;
+ rc->phases.hold = imx95_xcache_reset_hold;
+ set_bit(DEVICE_CATEGORY_MISC, dc->categories);
+ dc->desc = "NXP i.MX 95 XCACHE controller (stub)";
+}
+
+static const TypeInfo imx95_xcache_info = {
+ .name = TYPE_IMX95_XCACHE,
+ .parent = TYPE_SYS_BUS_DEVICE,
+ .instance_size = sizeof(IMX95XCacheState),
+ .instance_init = imx95_xcache_init,
+ .class_init = imx95_xcache_class_init,
+};
+
+static void imx95_xcache_register_types(void)
+{
+ type_register_static(&imx95_xcache_info);
+}
+
+type_init(imx95_xcache_register_types)
diff --git a/hw/misc/meson.build b/hw/misc/meson.build
index 0b7f5e4382d..d7d283a191b 100644
--- a/hw/misc/meson.build
+++ b/hw/misc/meson.build
@@ -178,3 +178,5 @@ system_ss.add(when: 'CONFIG_IMX95_ANATOP', if_true: files('imx95_anatop.c'))
system_ss.add(when: 'CONFIG_IMX95_AONMIX', if_true: files('imx95_aonmix.c'))
system_ss.add(when: 'CONFIG_IMX95_GPC', if_true: files('imx95_gpc.c'))
system_ss.add(when: 'CONFIG_IMX95_SRC', if_true: files('imx95_src.c'))
+system_ss.add(when: 'CONFIG_IMX95_PMIC', if_true: files('imx95_pmic.c'))
+system_ss.add(when: 'CONFIG_IMX95_XCACHE', if_true: files('imx95_xcache.c'))
diff --git a/hw/misc/trace-events b/hw/misc/trace-events
index 15fab0596c2..0555b15a1f3 100644
--- a/hw/misc/trace-events
+++ b/hw/misc/trace-events
@@ -458,3 +458,11 @@ imx95_aonmix_m7_gate(int run) "M7 wait gate -> run=%d"
imx95_gpc_mode(uint64_t offset, uint32_t target) "CMC_MODE_CTRL off 0x%" PRIx64 " target %u"
imx95_src_m7mix_release(void) "SRC_GEN.SCR M7MIX reset released"
imx95_src_slice_ctrl(uint64_t offset, uint32_t value) "SLICE_SW_CTRL off 0x%" PRIx64 " <- 0x%08x"
+imx95_xcache_read(uint64_t offset) "read off 0x%" PRIx64
+imx95_xcache_write(uint64_t offset, uint64_t value) "write off 0x%" PRIx64 " <- 0x%08" PRIx64
+pf09_reg_read(uint8_t reg, uint8_t val) "PF09 reg 0x%02x -> 0x%02x"
+pf09_reg_write(uint8_t reg, uint8_t val) "PF09 reg 0x%02x <- 0x%02x"
+pcal6408a_reg_read(uint8_t reg, uint8_t val) "PCAL6408A reg 0x%02x -> 0x%02x"
+pcal6408a_reg_write(uint8_t reg, uint8_t val) "PCAL6408A reg 0x%02x <- 0x%02x"
+pf53_reg_read(uint8_t reg, uint8_t val) "PF53 reg 0x%02x -> 0x%02x"
+pf53_reg_write(uint8_t reg, uint8_t val) "PF53 reg 0x%02x <- 0x%02x"
--
2.34.1
next prev parent reply other threads:[~2026-08-20 2:51 UTC|newest]
Thread overview: 15+ messages / expand[flat|nested] mbox.gz Atom feed top
[not found] <20260820024834.3286721-1-kylefoxaustin.github@gmail.com>
2026-08-20 2:48 ` [PATCH 02/16] hw/arm/boot: let a board preset initrd_start Kyle Fox
2026-08-20 2:48 ` [PATCH 03/16] target/arm: opt-in align-down for a misaligned PMSAv7 MPU RBAR Kyle Fox
2026-08-20 2:48 ` [PATCH 04/16] hw/arm/armv7m: forward pmsav7-rbar-align-down to the CPU Kyle Fox
2026-08-20 2:48 ` [PATCH 05/16] hw/char: add i.MX LPUART Kyle Fox
2026-08-20 2:48 ` [PATCH 06/16] hw/i2c: add i.MX LPI2C Kyle Fox
2026-08-20 2:48 ` [PATCH 07/16] hw/misc: add i.MX Messaging Unit (MU v2) Kyle Fox
2026-08-20 2:48 ` [PATCH 08/16] hw/misc: add NXP EdgeLock Enclave (ELE) responder Kyle Fox
2026-08-20 2:48 ` [PATCH 09/16] hw/timer: add i.MX 95 system counter Kyle Fox
2026-08-20 2:48 ` [PATCH 10/16] hw/misc: add i.MX 95 watchdog Kyle Fox
2026-08-20 2:48 ` [PATCH 11/16] hw/misc: add i.MX 95 ANATOP/AONMIX/GPC/SRC power and clock blocks Kyle Fox
2026-08-20 2:48 ` Kyle Fox [this message]
2026-08-20 2:48 ` [PATCH 13/16] hw/misc: add i.MX 95 DPU command-sequencer stub (headless) Kyle Fox
2026-08-20 2:48 ` [PATCH 14/16] hw/arm: add i.MX 95 SoC container (fsl-imx95) Kyle Fox
2026-08-20 2:48 ` [PATCH 15/16] hw/arm: add i.MX 95 19x19 EVK board Kyle Fox
2026-08-20 2:48 ` [PATCH 16/16] docs, MAINTAINERS, tests/functional: add i.MX 95 EVK Kyle Fox
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=20260820024834.3286721-13-kylefoxaustin.github@gmail.com \
--to=kylefoxaustin.github@gmail.com \
--cc=pbonzini@redhat.com \
--cc=qemu-arm@nongnu.org \
--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 a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox