1 /* 2 * Virtio MMIO bindings 3 * 4 * Copyright (c) 2011 Linaro Limited 5 * 6 * Author: 7 * Peter Maydell <peter.maydell@linaro.org> 8 * 9 * This program is free software; you can redistribute it and/or modify 10 * it under the terms of the GNU General Public License; either version 2 11 * of the License, or (at your option) any later version. 12 * 13 * This program is distributed in the hope that it will be useful, 14 * but WITHOUT ANY WARRANTY; without even the implied warranty of 15 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 16 * GNU General Public License for more details. 17 * 18 * You should have received a copy of the GNU General Public License along 19 * with this program; if not, see <http://www.gnu.org/licenses/>. 20 */ 21 22 #include "hw/sysbus.h" 23 #include "hw/virtio/virtio.h" 24 #include "qemu/host-utils.h" 25 #include "hw/virtio/virtio-bus.h" 26 27 /* #define DEBUG_VIRTIO_MMIO */ 28 29 #ifdef DEBUG_VIRTIO_MMIO 30 31 #define DPRINTF(fmt, ...) \ 32 do { printf("virtio_mmio: " fmt , ## __VA_ARGS__); } while (0) 33 #else 34 #define DPRINTF(fmt, ...) do {} while (0) 35 #endif 36 37 /* QOM macros */ 38 /* virtio-mmio-bus */ 39 #define TYPE_VIRTIO_MMIO_BUS "virtio-mmio-bus" 40 #define VIRTIO_MMIO_BUS(obj) \ 41 OBJECT_CHECK(VirtioBusState, (obj), TYPE_VIRTIO_MMIO_BUS) 42 #define VIRTIO_MMIO_BUS_GET_CLASS(obj) \ 43 OBJECT_GET_CLASS(VirtioBusClass, (obj), TYPE_VIRTIO_MMIO_BUS) 44 #define VIRTIO_MMIO_BUS_CLASS(klass) \ 45 OBJECT_CLASS_CHECK(VirtioBusClass, (klass), TYPE_VIRTIO_MMIO_BUS) 46 47 /* virtio-mmio */ 48 #define TYPE_VIRTIO_MMIO "virtio-mmio" 49 #define VIRTIO_MMIO(obj) \ 50 OBJECT_CHECK(VirtIOMMIOProxy, (obj), TYPE_VIRTIO_MMIO) 51 52 /* Memory mapped register offsets */ 53 #define VIRTIO_MMIO_MAGIC 0x0 54 #define VIRTIO_MMIO_VERSION 0x4 55 #define VIRTIO_MMIO_DEVICEID 0x8 56 #define VIRTIO_MMIO_VENDORID 0xc 57 #define VIRTIO_MMIO_HOSTFEATURES 0x10 58 #define VIRTIO_MMIO_HOSTFEATURESSEL 0x14 59 #define VIRTIO_MMIO_GUESTFEATURES 0x20 60 #define VIRTIO_MMIO_GUESTFEATURESSEL 0x24 61 #define VIRTIO_MMIO_GUESTPAGESIZE 0x28 62 #define VIRTIO_MMIO_QUEUESEL 0x30 63 #define VIRTIO_MMIO_QUEUENUMMAX 0x34 64 #define VIRTIO_MMIO_QUEUENUM 0x38 65 #define VIRTIO_MMIO_QUEUEALIGN 0x3c 66 #define VIRTIO_MMIO_QUEUEPFN 0x40 67 #define VIRTIO_MMIO_QUEUENOTIFY 0x50 68 #define VIRTIO_MMIO_INTERRUPTSTATUS 0x60 69 #define VIRTIO_MMIO_INTERRUPTACK 0x64 70 #define VIRTIO_MMIO_STATUS 0x70 71 /* Device specific config space starts here */ 72 #define VIRTIO_MMIO_CONFIG 0x100 73 74 #define VIRT_MAGIC 0x74726976 /* 'virt' */ 75 #define VIRT_VERSION 1 76 #define VIRT_VENDOR 0x554D4551 /* 'QEMU' */ 77 78 typedef struct { 79 /* Generic */ 80 SysBusDevice parent_obj; 81 MemoryRegion iomem; 82 qemu_irq irq; 83 uint32_t host_features; 84 /* Guest accessible state needing migration and reset */ 85 uint32_t host_features_sel; 86 uint32_t guest_features_sel; 87 uint32_t guest_page_shift; 88 /* virtio-bus */ 89 VirtioBusState bus; 90 } VirtIOMMIOProxy; 91 92 static void virtio_mmio_bus_new(VirtioBusState *bus, VirtIOMMIOProxy *dev); 93 94 static uint64_t virtio_mmio_read(void *opaque, hwaddr offset, unsigned size) 95 { 96 VirtIOMMIOProxy *proxy = (VirtIOMMIOProxy *)opaque; 97 VirtIODevice *vdev = proxy->bus.vdev; 98 99 DPRINTF("virtio_mmio_read offset 0x%x\n", (int)offset); 100 101 if (!vdev) { 102 /* If no backend is present, we treat most registers as 103 * read-as-zero, except for the magic number, version and 104 * vendor ID. This is not strictly sanctioned by the virtio 105 * spec, but it allows us to provide transports with no backend 106 * plugged in which don't confuse Linux's virtio code: the 107 * probe won't complain about the bad magic number, but the 108 * device ID of zero means no backend will claim it. 109 */ 110 switch (offset) { 111 case VIRTIO_MMIO_MAGIC: 112 return VIRT_MAGIC; 113 case VIRTIO_MMIO_VERSION: 114 return VIRT_VERSION; 115 case VIRTIO_MMIO_VENDORID: 116 return VIRT_VENDOR; 117 default: 118 return 0; 119 } 120 } 121 122 if (offset >= VIRTIO_MMIO_CONFIG) { 123 offset -= VIRTIO_MMIO_CONFIG; 124 switch (size) { 125 case 1: 126 return virtio_config_readb(vdev, offset); 127 case 2: 128 return virtio_config_readw(vdev, offset); 129 case 4: 130 return virtio_config_readl(vdev, offset); 131 default: 132 abort(); 133 } 134 } 135 if (size != 4) { 136 DPRINTF("wrong size access to register!\n"); 137 return 0; 138 } 139 switch (offset) { 140 case VIRTIO_MMIO_MAGIC: 141 return VIRT_MAGIC; 142 case VIRTIO_MMIO_VERSION: 143 return VIRT_VERSION; 144 case VIRTIO_MMIO_DEVICEID: 145 return vdev->device_id; 146 case VIRTIO_MMIO_VENDORID: 147 return VIRT_VENDOR; 148 case VIRTIO_MMIO_HOSTFEATURES: 149 if (proxy->host_features_sel) { 150 return 0; 151 } 152 return proxy->host_features; 153 case VIRTIO_MMIO_QUEUENUMMAX: 154 return VIRTQUEUE_MAX_SIZE; 155 case VIRTIO_MMIO_QUEUEPFN: 156 return virtio_queue_get_addr(vdev, vdev->queue_sel) 157 >> proxy->guest_page_shift; 158 case VIRTIO_MMIO_INTERRUPTSTATUS: 159 return vdev->isr; 160 case VIRTIO_MMIO_STATUS: 161 return vdev->status; 162 case VIRTIO_MMIO_HOSTFEATURESSEL: 163 case VIRTIO_MMIO_GUESTFEATURES: 164 case VIRTIO_MMIO_GUESTFEATURESSEL: 165 case VIRTIO_MMIO_GUESTPAGESIZE: 166 case VIRTIO_MMIO_QUEUESEL: 167 case VIRTIO_MMIO_QUEUENUM: 168 case VIRTIO_MMIO_QUEUEALIGN: 169 case VIRTIO_MMIO_QUEUENOTIFY: 170 case VIRTIO_MMIO_INTERRUPTACK: 171 DPRINTF("read of write-only register\n"); 172 return 0; 173 default: 174 DPRINTF("bad register offset\n"); 175 return 0; 176 } 177 return 0; 178 } 179 180 static void virtio_mmio_write(void *opaque, hwaddr offset, uint64_t value, 181 unsigned size) 182 { 183 VirtIOMMIOProxy *proxy = (VirtIOMMIOProxy *)opaque; 184 VirtIODevice *vdev = proxy->bus.vdev; 185 186 DPRINTF("virtio_mmio_write offset 0x%x value 0x%" PRIx64 "\n", 187 (int)offset, value); 188 189 if (!vdev) { 190 /* If no backend is present, we just make all registers 191 * write-ignored. This allows us to provide transports with 192 * no backend plugged in. 193 */ 194 return; 195 } 196 197 if (offset >= VIRTIO_MMIO_CONFIG) { 198 offset -= VIRTIO_MMIO_CONFIG; 199 switch (size) { 200 case 1: 201 virtio_config_writeb(vdev, offset, value); 202 break; 203 case 2: 204 virtio_config_writew(vdev, offset, value); 205 break; 206 case 4: 207 virtio_config_writel(vdev, offset, value); 208 break; 209 default: 210 abort(); 211 } 212 return; 213 } 214 if (size != 4) { 215 DPRINTF("wrong size access to register!\n"); 216 return; 217 } 218 switch (offset) { 219 case VIRTIO_MMIO_HOSTFEATURESSEL: 220 proxy->host_features_sel = value; 221 break; 222 case VIRTIO_MMIO_GUESTFEATURES: 223 if (!proxy->guest_features_sel) { 224 virtio_set_features(vdev, value); 225 } 226 break; 227 case VIRTIO_MMIO_GUESTFEATURESSEL: 228 proxy->guest_features_sel = value; 229 break; 230 case VIRTIO_MMIO_GUESTPAGESIZE: 231 proxy->guest_page_shift = ctz32(value); 232 if (proxy->guest_page_shift > 31) { 233 proxy->guest_page_shift = 0; 234 } 235 DPRINTF("guest page size %" PRIx64 " shift %d\n", value, 236 proxy->guest_page_shift); 237 break; 238 case VIRTIO_MMIO_QUEUESEL: 239 if (value < VIRTIO_PCI_QUEUE_MAX) { 240 vdev->queue_sel = value; 241 } 242 break; 243 case VIRTIO_MMIO_QUEUENUM: 244 DPRINTF("mmio_queue write %d max %d\n", (int)value, VIRTQUEUE_MAX_SIZE); 245 virtio_queue_set_num(vdev, vdev->queue_sel, value); 246 break; 247 case VIRTIO_MMIO_QUEUEALIGN: 248 virtio_queue_set_align(vdev, vdev->queue_sel, value); 249 break; 250 case VIRTIO_MMIO_QUEUEPFN: 251 if (value == 0) { 252 virtio_reset(vdev); 253 } else { 254 virtio_queue_set_addr(vdev, vdev->queue_sel, 255 value << proxy->guest_page_shift); 256 } 257 break; 258 case VIRTIO_MMIO_QUEUENOTIFY: 259 if (value < VIRTIO_PCI_QUEUE_MAX) { 260 virtio_queue_notify(vdev, value); 261 } 262 break; 263 case VIRTIO_MMIO_INTERRUPTACK: 264 vdev->isr &= ~value; 265 virtio_update_irq(vdev); 266 break; 267 case VIRTIO_MMIO_STATUS: 268 virtio_set_status(vdev, value & 0xff); 269 if (vdev->status == 0) { 270 virtio_reset(vdev); 271 } 272 break; 273 case VIRTIO_MMIO_MAGIC: 274 case VIRTIO_MMIO_VERSION: 275 case VIRTIO_MMIO_DEVICEID: 276 case VIRTIO_MMIO_VENDORID: 277 case VIRTIO_MMIO_HOSTFEATURES: 278 case VIRTIO_MMIO_QUEUENUMMAX: 279 case VIRTIO_MMIO_INTERRUPTSTATUS: 280 DPRINTF("write to readonly register\n"); 281 break; 282 283 default: 284 DPRINTF("bad register offset\n"); 285 } 286 } 287 288 static const MemoryRegionOps virtio_mem_ops = { 289 .read = virtio_mmio_read, 290 .write = virtio_mmio_write, 291 .endianness = DEVICE_NATIVE_ENDIAN, 292 }; 293 294 static void virtio_mmio_update_irq(DeviceState *opaque, uint16_t vector) 295 { 296 VirtIOMMIOProxy *proxy = VIRTIO_MMIO(opaque); 297 int level; 298 299 if (!proxy->bus.vdev) { 300 return; 301 } 302 level = (proxy->bus.vdev->isr != 0); 303 DPRINTF("virtio_mmio setting IRQ %d\n", level); 304 qemu_set_irq(proxy->irq, level); 305 } 306 307 static unsigned int virtio_mmio_get_features(DeviceState *opaque) 308 { 309 VirtIOMMIOProxy *proxy = VIRTIO_MMIO(opaque); 310 311 return proxy->host_features; 312 } 313 314 static int virtio_mmio_load_config(DeviceState *opaque, QEMUFile *f) 315 { 316 VirtIOMMIOProxy *proxy = VIRTIO_MMIO(opaque); 317 318 proxy->host_features_sel = qemu_get_be32(f); 319 proxy->guest_features_sel = qemu_get_be32(f); 320 proxy->guest_page_shift = qemu_get_be32(f); 321 return 0; 322 } 323 324 static void virtio_mmio_save_config(DeviceState *opaque, QEMUFile *f) 325 { 326 VirtIOMMIOProxy *proxy = VIRTIO_MMIO(opaque); 327 328 qemu_put_be32(f, proxy->host_features_sel); 329 qemu_put_be32(f, proxy->guest_features_sel); 330 qemu_put_be32(f, proxy->guest_page_shift); 331 } 332 333 static void virtio_mmio_reset(DeviceState *d) 334 { 335 VirtIOMMIOProxy *proxy = VIRTIO_MMIO(d); 336 337 virtio_bus_reset(&proxy->bus); 338 proxy->host_features_sel = 0; 339 proxy->guest_features_sel = 0; 340 proxy->guest_page_shift = 0; 341 } 342 343 /* virtio-mmio device */ 344 345 /* This is called by virtio-bus just after the device is plugged. */ 346 static void virtio_mmio_device_plugged(DeviceState *opaque) 347 { 348 VirtIOMMIOProxy *proxy = VIRTIO_MMIO(opaque); 349 350 proxy->host_features |= (0x1 << VIRTIO_F_NOTIFY_ON_EMPTY); 351 proxy->host_features = virtio_bus_get_vdev_features(&proxy->bus, 352 proxy->host_features); 353 } 354 355 static void virtio_mmio_realizefn(DeviceState *d, Error **errp) 356 { 357 VirtIOMMIOProxy *proxy = VIRTIO_MMIO(d); 358 SysBusDevice *sbd = SYS_BUS_DEVICE(d); 359 360 virtio_mmio_bus_new(&proxy->bus, proxy); 361 sysbus_init_irq(sbd, &proxy->irq); 362 memory_region_init_io(&proxy->iomem, OBJECT(d), &virtio_mem_ops, proxy, 363 TYPE_VIRTIO_MMIO, 0x200); 364 sysbus_init_mmio(sbd, &proxy->iomem); 365 } 366 367 static void virtio_mmio_class_init(ObjectClass *klass, void *data) 368 { 369 DeviceClass *dc = DEVICE_CLASS(klass); 370 371 dc->realize = virtio_mmio_realizefn; 372 dc->reset = virtio_mmio_reset; 373 set_bit(DEVICE_CATEGORY_MISC, dc->categories); 374 } 375 376 static const TypeInfo virtio_mmio_info = { 377 .name = TYPE_VIRTIO_MMIO, 378 .parent = TYPE_SYS_BUS_DEVICE, 379 .instance_size = sizeof(VirtIOMMIOProxy), 380 .class_init = virtio_mmio_class_init, 381 }; 382 383 /* virtio-mmio-bus. */ 384 385 static void virtio_mmio_bus_new(VirtioBusState *bus, VirtIOMMIOProxy *dev) 386 { 387 DeviceState *qdev = DEVICE(dev); 388 BusState *qbus; 389 390 qbus_create_inplace((BusState *)bus, TYPE_VIRTIO_MMIO_BUS, qdev, NULL); 391 qbus = BUS(bus); 392 qbus->allow_hotplug = 0; 393 } 394 395 static void virtio_mmio_bus_class_init(ObjectClass *klass, void *data) 396 { 397 BusClass *bus_class = BUS_CLASS(klass); 398 VirtioBusClass *k = VIRTIO_BUS_CLASS(klass); 399 400 k->notify = virtio_mmio_update_irq; 401 k->save_config = virtio_mmio_save_config; 402 k->load_config = virtio_mmio_load_config; 403 k->get_features = virtio_mmio_get_features; 404 k->device_plugged = virtio_mmio_device_plugged; 405 k->has_variable_vring_alignment = true; 406 bus_class->max_dev = 1; 407 } 408 409 static const TypeInfo virtio_mmio_bus_info = { 410 .name = TYPE_VIRTIO_MMIO_BUS, 411 .parent = TYPE_VIRTIO_BUS, 412 .instance_size = sizeof(VirtioBusState), 413 .class_init = virtio_mmio_bus_class_init, 414 }; 415 416 static void virtio_mmio_register_types(void) 417 { 418 type_register_static(&virtio_mmio_bus_info); 419 type_register_static(&virtio_mmio_info); 420 } 421 422 type_init(virtio_mmio_register_types) 423