Skip to content

Commit

Permalink
hw/fsi: Introduce IBM's scratchpad device
Browse files Browse the repository at this point in the history
This is a part of patchset where IBM's Flexible Service Interface is
introduced.

The scratchpad provides a set of non-functional registers. The firmware
is free to use them, hardware does not support any special management
support. The scratchpad registers can be read or written from LBUS
slave. The scratch pad is managed under FSI CFAM state.

Signed-off-by: Andrew Jeffery <andrew@aj.id.au>
Signed-off-by: Ninad Palsule <ninad@linux.ibm.com>
Reviewed-by: Cédric Le Goater <clg@kaod.org>
[ clg: - moved object FSIScratchPad under FSICFAMState
       - moved FSIScratchPad code under cfam.c ]
Signed-off-by: Cédric Le Goater <clg@kaod.org>
  • Loading branch information
ninadpalsule authored and legoater committed Jan 26, 2024
1 parent 4696d96 commit bd6827a
Show file tree
Hide file tree
Showing 3 changed files with 89 additions and 2 deletions.
78 changes: 76 additions & 2 deletions hw/fsi/lbus.c
Original file line number Diff line number Diff line change
Expand Up @@ -8,11 +8,12 @@
#include "qemu/osdep.h"
#include "qapi/error.h"
#include "hw/fsi/lbus.h"

#include "hw/qdev-properties.h"

#include "qemu/log.h"
#include "trace.h"

#define TO_REG(offset) ((offset) >> 2)

static void fsi_lbus_init(Object *o)
{
FSILBus *lbus = FSI_LBUS(o);
Expand All @@ -34,10 +35,83 @@ static const TypeInfo fsi_lbus_device_type_info = {
.abstract = true,
};

static uint64_t fsi_scratchpad_read(void *opaque, hwaddr addr, unsigned size)
{
FSIScratchPad *s = SCRATCHPAD(opaque);
int reg = TO_REG(addr);

trace_fsi_scratchpad_read(addr, size);

if (reg >= FSI_SCRATCHPAD_NR_REGS) {
qemu_log_mask(LOG_GUEST_ERROR,
"%s: Out-of-bounds read at offset 0x%" HWADDR_PRIx "\n",
__func__, addr);
return 0;
}

return s->regs[reg];
}

static void fsi_scratchpad_write(void *opaque, hwaddr addr, uint64_t data,
unsigned size)
{
FSIScratchPad *s = SCRATCHPAD(opaque);

trace_fsi_scratchpad_write(addr, size, data);
int reg = TO_REG(addr);

if (reg >= FSI_SCRATCHPAD_NR_REGS) {
qemu_log_mask(LOG_GUEST_ERROR,
"%s: Out-of-bounds write at offset 0x%" HWADDR_PRIx "\n",
__func__, addr);
return;
}

s->regs[reg] = data;
}

static const struct MemoryRegionOps scratchpad_ops = {
.read = fsi_scratchpad_read,
.write = fsi_scratchpad_write,
.endianness = DEVICE_BIG_ENDIAN,
};

static void fsi_scratchpad_realize(DeviceState *dev, Error **errp)
{
FSILBusDevice *ldev = FSI_LBUS_DEVICE(dev);

memory_region_init_io(&ldev->iomem, OBJECT(ldev), &scratchpad_ops,
ldev, TYPE_FSI_SCRATCHPAD, 0x400);
}

static void fsi_scratchpad_reset(DeviceState *dev)
{
FSIScratchPad *s = SCRATCHPAD(dev);

memset(s->regs, 0, sizeof(s->regs));
}

static void fsi_scratchpad_class_init(ObjectClass *klass, void *data)
{
DeviceClass *dc = DEVICE_CLASS(klass);

dc->bus_type = TYPE_FSI_LBUS;
dc->realize = fsi_scratchpad_realize;
dc->reset = fsi_scratchpad_reset;
}

static const TypeInfo fsi_scratchpad_info = {
.name = TYPE_FSI_SCRATCHPAD,
.parent = TYPE_FSI_LBUS_DEVICE,
.instance_size = sizeof(FSIScratchPad),
.class_init = fsi_scratchpad_class_init,
};

static void fsi_lbus_register_types(void)
{
type_register_static(&fsi_lbus_info);
type_register_static(&fsi_lbus_device_type_info);
type_register_static(&fsi_scratchpad_info);
}

type_init(fsi_lbus_register_types);
2 changes: 2 additions & 0 deletions hw/fsi/trace-events
Original file line number Diff line number Diff line change
@@ -0,0 +1,2 @@
fsi_scratchpad_read(uint64_t addr, uint32_t size) "@0x%" PRIx64 " size=%d"
fsi_scratchpad_write(uint64_t addr, uint32_t size, uint64_t data) "@0x%" PRIx64 " size=%d value=0x%"PRIx64
11 changes: 11 additions & 0 deletions include/hw/fsi/lbus.h
Original file line number Diff line number Diff line change
Expand Up @@ -29,4 +29,15 @@ typedef struct FSILBus {
MemoryRegion mr;
} FSILBus;

#define TYPE_FSI_SCRATCHPAD "fsi.scratchpad"
#define SCRATCHPAD(obj) OBJECT_CHECK(FSIScratchPad, (obj), TYPE_FSI_SCRATCHPAD)

#define FSI_SCRATCHPAD_NR_REGS 4

typedef struct FSIScratchPad {
FSILBusDevice parent;

uint32_t regs[FSI_SCRATCHPAD_NR_REGS];
} FSIScratchPad;

#endif /* FSI_LBUS_H */

0 comments on commit bd6827a

Please sign in to comment.