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