Skip to content

Commit

Permalink
hw/ssi/xilinx_spi: Make device endianness configurable
Browse files Browse the repository at this point in the history
Replace the DEVICE_NATIVE_ENDIAN MemoryRegionOps by a pair of
DEVICE_LITTLE_ENDIAN / DEVICE_BIG_ENDIAN.

Add the "endianness" property to select the device endianness.
This property is unspecified by default, and machines need to
set it explicitly.

Set the proper endianness on the single machine using the
device.

Reviewed-by: Thomas Huth <[email protected]>
Signed-off-by: Philippe Mathieu-Daudé <[email protected]>
Reviewed-by: Richard Henderson <[email protected]>
Message-Id: <[email protected]>
  • Loading branch information
philmd committed Feb 16, 2025
1 parent 8a8c92c commit e87c93d
Show file tree
Hide file tree
Showing 2 changed files with 24 additions and 9 deletions.
1 change: 1 addition & 0 deletions hw/microblaze/petalogix_ml605_mmu.c
Original file line number Diff line number Diff line change
Expand Up @@ -177,6 +177,7 @@ petalogix_ml605_init(MachineState *machine)
SSIBus *spi;

dev = qdev_new("xlnx.xps-spi");
qdev_prop_set_enum(dev, "endianness", endianness);
qdev_prop_set_uint8(dev, "num-ss-bits", NUM_SPI_FLASHES);
busdev = SYS_BUS_DEVICE(dev);
sysbus_realize_and_unref(busdev, &error_fatal);
Expand Down
32 changes: 23 additions & 9 deletions hw/ssi/xilinx_spi.c
Original file line number Diff line number Diff line change
Expand Up @@ -25,13 +25,15 @@
*/

#include "qemu/osdep.h"
#include "qapi/error.h"
#include "hw/sysbus.h"
#include "migration/vmstate.h"
#include "qemu/module.h"
#include "qemu/fifo8.h"

#include "hw/irq.h"
#include "hw/qdev-properties.h"
#include "hw/qdev-properties-system.h"
#include "hw/ssi/ssi.h"
#include "qom/object.h"

Expand Down Expand Up @@ -83,6 +85,7 @@ OBJECT_DECLARE_SIMPLE_TYPE(XilinxSPI, XILINX_SPI)
struct XilinxSPI {
SysBusDevice parent_obj;

EndianMode model_endianness;
MemoryRegion mmio;

qemu_irq irq;
Expand Down Expand Up @@ -313,14 +316,17 @@ spi_write(void *opaque, hwaddr addr,
xlx_spi_update_irq(s);
}

static const MemoryRegionOps spi_ops = {
.read = spi_read,
.write = spi_write,
.endianness = DEVICE_NATIVE_ENDIAN,
.valid = {
.min_access_size = 4,
.max_access_size = 4
}
static const MemoryRegionOps spi_ops[2] = {
[0 ... 1] = {
.read = spi_read,
.write = spi_write,
.valid = {
.min_access_size = 4,
.max_access_size = 4,
},
},
[0].endianness = DEVICE_LITTLE_ENDIAN,
[1].endianness = DEVICE_BIG_ENDIAN,
};

static void xilinx_spi_realize(DeviceState *dev, Error **errp)
Expand All @@ -329,6 +335,12 @@ static void xilinx_spi_realize(DeviceState *dev, Error **errp)
XilinxSPI *s = XILINX_SPI(dev);
int i;

if (s->model_endianness == ENDIAN_MODE_UNSPECIFIED) {
error_setg(errp, TYPE_XILINX_SPI " property 'endianness'"
" must be set to 'big' or 'little'");
return;
}

DB_PRINT("\n");

s->spi = ssi_create_bus(dev, "spi");
Expand All @@ -339,7 +351,8 @@ static void xilinx_spi_realize(DeviceState *dev, Error **errp)
sysbus_init_irq(sbd, &s->cs_lines[i]);
}

memory_region_init_io(&s->mmio, OBJECT(s), &spi_ops, s,
memory_region_init_io(&s->mmio, OBJECT(s),
&spi_ops[s->model_endianness == ENDIAN_MODE_BIG], s,
"xilinx-spi", R_MAX * 4);
sysbus_init_mmio(sbd, &s->mmio);

Expand All @@ -362,6 +375,7 @@ static const VMStateDescription vmstate_xilinx_spi = {
};

static const Property xilinx_spi_properties[] = {
DEFINE_PROP_ENDIAN_NODEFAULT("endianness", XilinxSPI, model_endianness),
DEFINE_PROP_UINT8("num-ss-bits", XilinxSPI, num_cs, 1),
};

Expand Down

0 comments on commit e87c93d

Please sign in to comment.