xref: /openbmc/qemu/hw/misc/max78000_icc.c (revision 0edc2afe0c8197bbcb98f948c609fb74c9b1ffd5)
1*3ec680e6SJackson Donaldson /*
2*3ec680e6SJackson Donaldson  * MAX78000 Instruction Cache
3*3ec680e6SJackson Donaldson  *
4*3ec680e6SJackson Donaldson  * Copyright (c) 2025 Jackson Donaldson <jcksn@duck.com>
5*3ec680e6SJackson Donaldson  *
6*3ec680e6SJackson Donaldson  * SPDX-License-Identifier: GPL-2.0-or-later
7*3ec680e6SJackson Donaldson  */
8*3ec680e6SJackson Donaldson 
9*3ec680e6SJackson Donaldson #include "qemu/osdep.h"
10*3ec680e6SJackson Donaldson #include "qemu/log.h"
11*3ec680e6SJackson Donaldson #include "trace.h"
12*3ec680e6SJackson Donaldson #include "hw/irq.h"
13*3ec680e6SJackson Donaldson #include "migration/vmstate.h"
14*3ec680e6SJackson Donaldson #include "hw/misc/max78000_icc.h"
15*3ec680e6SJackson Donaldson 
16*3ec680e6SJackson Donaldson 
max78000_icc_read(void * opaque,hwaddr addr,unsigned int size)17*3ec680e6SJackson Donaldson static uint64_t max78000_icc_read(void *opaque, hwaddr addr,
18*3ec680e6SJackson Donaldson                                     unsigned int size)
19*3ec680e6SJackson Donaldson {
20*3ec680e6SJackson Donaldson     Max78000IccState *s = opaque;
21*3ec680e6SJackson Donaldson     switch (addr) {
22*3ec680e6SJackson Donaldson     case ICC_INFO:
23*3ec680e6SJackson Donaldson         return s->info;
24*3ec680e6SJackson Donaldson 
25*3ec680e6SJackson Donaldson     case ICC_SZ:
26*3ec680e6SJackson Donaldson         return s->sz;
27*3ec680e6SJackson Donaldson 
28*3ec680e6SJackson Donaldson     case ICC_CTRL:
29*3ec680e6SJackson Donaldson         return s->ctrl;
30*3ec680e6SJackson Donaldson 
31*3ec680e6SJackson Donaldson     default:
32*3ec680e6SJackson Donaldson         qemu_log_mask(LOG_GUEST_ERROR,
33*3ec680e6SJackson Donaldson                       "%s: Bad offset 0x%" HWADDR_PRIx "\n",
34*3ec680e6SJackson Donaldson                       __func__, addr);
35*3ec680e6SJackson Donaldson         return 0;
36*3ec680e6SJackson Donaldson 
37*3ec680e6SJackson Donaldson     }
38*3ec680e6SJackson Donaldson }
39*3ec680e6SJackson Donaldson 
max78000_icc_write(void * opaque,hwaddr addr,uint64_t val64,unsigned int size)40*3ec680e6SJackson Donaldson static void max78000_icc_write(void *opaque, hwaddr addr,
41*3ec680e6SJackson Donaldson                     uint64_t val64, unsigned int size)
42*3ec680e6SJackson Donaldson {
43*3ec680e6SJackson Donaldson     Max78000IccState *s = opaque;
44*3ec680e6SJackson Donaldson 
45*3ec680e6SJackson Donaldson     switch (addr) {
46*3ec680e6SJackson Donaldson     case ICC_CTRL:
47*3ec680e6SJackson Donaldson         s->ctrl = 0x10000 | (val64 & 1);
48*3ec680e6SJackson Donaldson         break;
49*3ec680e6SJackson Donaldson 
50*3ec680e6SJackson Donaldson     case ICC_INVALIDATE:
51*3ec680e6SJackson Donaldson         break;
52*3ec680e6SJackson Donaldson 
53*3ec680e6SJackson Donaldson     default:
54*3ec680e6SJackson Donaldson         qemu_log_mask(LOG_GUEST_ERROR,
55*3ec680e6SJackson Donaldson                       "%s: Bad offset 0x%" HWADDR_PRIx "\n",
56*3ec680e6SJackson Donaldson                       __func__, addr);
57*3ec680e6SJackson Donaldson         break;
58*3ec680e6SJackson Donaldson     }
59*3ec680e6SJackson Donaldson }
60*3ec680e6SJackson Donaldson 
61*3ec680e6SJackson Donaldson static const MemoryRegionOps max78000_icc_ops = {
62*3ec680e6SJackson Donaldson     .read = max78000_icc_read,
63*3ec680e6SJackson Donaldson     .write = max78000_icc_write,
64*3ec680e6SJackson Donaldson     .endianness = DEVICE_LITTLE_ENDIAN,
65*3ec680e6SJackson Donaldson     .valid.min_access_size = 4,
66*3ec680e6SJackson Donaldson     .valid.max_access_size = 4,
67*3ec680e6SJackson Donaldson };
68*3ec680e6SJackson Donaldson 
69*3ec680e6SJackson Donaldson static const VMStateDescription max78000_icc_vmstate = {
70*3ec680e6SJackson Donaldson     .name = TYPE_MAX78000_ICC,
71*3ec680e6SJackson Donaldson     .version_id = 1,
72*3ec680e6SJackson Donaldson     .minimum_version_id = 1,
73*3ec680e6SJackson Donaldson     .fields = (const VMStateField[]) {
74*3ec680e6SJackson Donaldson         VMSTATE_UINT32(info, Max78000IccState),
75*3ec680e6SJackson Donaldson         VMSTATE_UINT32(sz, Max78000IccState),
76*3ec680e6SJackson Donaldson         VMSTATE_UINT32(ctrl, Max78000IccState),
77*3ec680e6SJackson Donaldson         VMSTATE_END_OF_LIST()
78*3ec680e6SJackson Donaldson     }
79*3ec680e6SJackson Donaldson };
80*3ec680e6SJackson Donaldson 
max78000_icc_reset_hold(Object * obj,ResetType type)81*3ec680e6SJackson Donaldson static void max78000_icc_reset_hold(Object *obj, ResetType type)
82*3ec680e6SJackson Donaldson {
83*3ec680e6SJackson Donaldson     Max78000IccState *s = MAX78000_ICC(obj);
84*3ec680e6SJackson Donaldson     s->info = 0;
85*3ec680e6SJackson Donaldson     s->sz = 0x10000010;
86*3ec680e6SJackson Donaldson     s->ctrl = 0x10000;
87*3ec680e6SJackson Donaldson }
88*3ec680e6SJackson Donaldson 
max78000_icc_init(Object * obj)89*3ec680e6SJackson Donaldson static void max78000_icc_init(Object *obj)
90*3ec680e6SJackson Donaldson {
91*3ec680e6SJackson Donaldson     Max78000IccState *s = MAX78000_ICC(obj);
92*3ec680e6SJackson Donaldson 
93*3ec680e6SJackson Donaldson     memory_region_init_io(&s->mmio, obj, &max78000_icc_ops, s,
94*3ec680e6SJackson Donaldson                         TYPE_MAX78000_ICC, 0x800);
95*3ec680e6SJackson Donaldson     sysbus_init_mmio(SYS_BUS_DEVICE(obj), &s->mmio);
96*3ec680e6SJackson Donaldson }
97*3ec680e6SJackson Donaldson 
max78000_icc_class_init(ObjectClass * klass,const void * data)98*3ec680e6SJackson Donaldson static void max78000_icc_class_init(ObjectClass *klass, const void *data)
99*3ec680e6SJackson Donaldson {
100*3ec680e6SJackson Donaldson     DeviceClass *dc = DEVICE_CLASS(klass);
101*3ec680e6SJackson Donaldson     ResettableClass *rc = RESETTABLE_CLASS(klass);
102*3ec680e6SJackson Donaldson 
103*3ec680e6SJackson Donaldson     rc->phases.hold = max78000_icc_reset_hold;
104*3ec680e6SJackson Donaldson     dc->vmsd = &max78000_icc_vmstate;
105*3ec680e6SJackson Donaldson }
106*3ec680e6SJackson Donaldson 
107*3ec680e6SJackson Donaldson static const TypeInfo max78000_icc_info = {
108*3ec680e6SJackson Donaldson     .name          = TYPE_MAX78000_ICC,
109*3ec680e6SJackson Donaldson     .parent        = TYPE_SYS_BUS_DEVICE,
110*3ec680e6SJackson Donaldson     .instance_size = sizeof(Max78000IccState),
111*3ec680e6SJackson Donaldson     .instance_init = max78000_icc_init,
112*3ec680e6SJackson Donaldson     .class_init    = max78000_icc_class_init,
113*3ec680e6SJackson Donaldson };
114*3ec680e6SJackson Donaldson 
max78000_icc_register_types(void)115*3ec680e6SJackson Donaldson static void max78000_icc_register_types(void)
116*3ec680e6SJackson Donaldson {
117*3ec680e6SJackson Donaldson     type_register_static(&max78000_icc_info);
118*3ec680e6SJackson Donaldson }
119*3ec680e6SJackson Donaldson 
120*3ec680e6SJackson Donaldson type_init(max78000_icc_register_types)
121