876 lines · c
1// SPDX-License-Identifier: GPL-2.0-or-later2/*3 * Virtio memory mapped device driver4 *5 * Copyright 2011-2014, ARM Ltd.6 *7 * This module allows virtio devices to be used over a virtual, memory mapped8 * platform device.9 *10 * The guest device(s) may be instantiated in one of three equivalent ways:11 *12 * 1. Static platform device in board's code, eg.:13 *14 * static struct platform_device v2m_virtio_device = {15 * .name = "virtio-mmio",16 * .id = -1,17 * .num_resources = 2,18 * .resource = (struct resource []) {19 * {20 * .start = 0x1001e000,21 * .end = 0x1001e0ff,22 * .flags = IORESOURCE_MEM,23 * }, {24 * .start = 42 + 32,25 * .end = 42 + 32,26 * .flags = IORESOURCE_IRQ,27 * },28 * }29 * };30 *31 * 2. Device Tree node, eg.:32 *33 * virtio_block@1e000 {34 * compatible = "virtio,mmio";35 * reg = <0x1e000 0x100>;36 * interrupts = <42>;37 * }38 *39 * 3. Kernel module (or command line) parameter. Can be used more than once -40 * one device will be created for each one. Syntax:41 *42 * [virtio_mmio.]device=<size>@<baseaddr>:<irq>[:<id>]43 * where:44 * <size> := size (can use standard suffixes like K, M or G)45 * <baseaddr> := physical base address46 * <irq> := interrupt number (as passed to request_irq())47 * <id> := (optional) platform device id48 * eg.:49 * virtio_mmio.device=0x100@0x100b0000:48 \50 * virtio_mmio.device=1K@0x1001e000:7451 *52 * Based on Virtio PCI driver by Anthony Liguori, copyright IBM Corp. 200753 */54 55#define pr_fmt(fmt) "virtio-mmio: " fmt56 57#include <linux/acpi.h>58#include <linux/dma-mapping.h>59#include <linux/highmem.h>60#include <linux/interrupt.h>61#include <linux/io.h>62#include <linux/list.h>63#include <linux/module.h>64#include <linux/of.h>65#include <linux/platform_device.h>66#include <linux/pm.h>67#include <linux/slab.h>68#include <linux/spinlock.h>69#include <linux/virtio.h>70#include <linux/virtio_config.h>71#include <uapi/linux/virtio_mmio.h>72#include <linux/virtio_ring.h>73 74 75 76/* The alignment to use between consumer and producer parts of vring.77 * Currently hardcoded to the page size. */78#define VIRTIO_MMIO_VRING_ALIGN PAGE_SIZE79 80 81 82#define to_virtio_mmio_device(_plat_dev) \83 container_of(_plat_dev, struct virtio_mmio_device, vdev)84 85struct virtio_mmio_device {86 struct virtio_device vdev;87 struct platform_device *pdev;88 89 void __iomem *base;90 unsigned long version;91 92 /* a list of queues so we can dispatch IRQs */93 spinlock_t lock;94 struct list_head virtqueues;95};96 97struct virtio_mmio_vq_info {98 /* the actual virtqueue */99 struct virtqueue *vq;100 101 /* the list node for the virtqueues list */102 struct list_head node;103};104 105 106 107/* Configuration interface */108 109static u64 vm_get_features(struct virtio_device *vdev)110{111 struct virtio_mmio_device *vm_dev = to_virtio_mmio_device(vdev);112 u64 features;113 114 writel(1, vm_dev->base + VIRTIO_MMIO_DEVICE_FEATURES_SEL);115 features = readl(vm_dev->base + VIRTIO_MMIO_DEVICE_FEATURES);116 features <<= 32;117 118 writel(0, vm_dev->base + VIRTIO_MMIO_DEVICE_FEATURES_SEL);119 features |= readl(vm_dev->base + VIRTIO_MMIO_DEVICE_FEATURES);120 121 return features;122}123 124static int vm_finalize_features(struct virtio_device *vdev)125{126 struct virtio_mmio_device *vm_dev = to_virtio_mmio_device(vdev);127 128 /* Give virtio_ring a chance to accept features. */129 vring_transport_features(vdev);130 131 /* Make sure there are no mixed devices */132 if (vm_dev->version == 2 &&133 !__virtio_test_bit(vdev, VIRTIO_F_VERSION_1)) {134 dev_err(&vdev->dev, "New virtio-mmio devices (version 2) must provide VIRTIO_F_VERSION_1 feature!\n");135 return -EINVAL;136 }137 138 writel(1, vm_dev->base + VIRTIO_MMIO_DRIVER_FEATURES_SEL);139 writel((u32)(vdev->features >> 32),140 vm_dev->base + VIRTIO_MMIO_DRIVER_FEATURES);141 142 writel(0, vm_dev->base + VIRTIO_MMIO_DRIVER_FEATURES_SEL);143 writel((u32)vdev->features,144 vm_dev->base + VIRTIO_MMIO_DRIVER_FEATURES);145 146 return 0;147}148 149static void vm_get(struct virtio_device *vdev, unsigned int offset,150 void *buf, unsigned int len)151{152 struct virtio_mmio_device *vm_dev = to_virtio_mmio_device(vdev);153 void __iomem *base = vm_dev->base + VIRTIO_MMIO_CONFIG;154 u8 b;155 __le16 w;156 __le32 l;157 158 if (vm_dev->version == 1) {159 u8 *ptr = buf;160 int i;161 162 for (i = 0; i < len; i++)163 ptr[i] = readb(base + offset + i);164 return;165 }166 167 switch (len) {168 case 1:169 b = readb(base + offset);170 memcpy(buf, &b, sizeof b);171 break;172 case 2:173 w = cpu_to_le16(readw(base + offset));174 memcpy(buf, &w, sizeof w);175 break;176 case 4:177 l = cpu_to_le32(readl(base + offset));178 memcpy(buf, &l, sizeof l);179 break;180 case 8:181 l = cpu_to_le32(readl(base + offset));182 memcpy(buf, &l, sizeof l);183 l = cpu_to_le32(ioread32(base + offset + sizeof l));184 memcpy(buf + sizeof l, &l, sizeof l);185 break;186 default:187 BUG();188 }189}190 191static void vm_set(struct virtio_device *vdev, unsigned int offset,192 const void *buf, unsigned int len)193{194 struct virtio_mmio_device *vm_dev = to_virtio_mmio_device(vdev);195 void __iomem *base = vm_dev->base + VIRTIO_MMIO_CONFIG;196 u8 b;197 __le16 w;198 __le32 l;199 200 if (vm_dev->version == 1) {201 const u8 *ptr = buf;202 int i;203 204 for (i = 0; i < len; i++)205 writeb(ptr[i], base + offset + i);206 207 return;208 }209 210 switch (len) {211 case 1:212 memcpy(&b, buf, sizeof b);213 writeb(b, base + offset);214 break;215 case 2:216 memcpy(&w, buf, sizeof w);217 writew(le16_to_cpu(w), base + offset);218 break;219 case 4:220 memcpy(&l, buf, sizeof l);221 writel(le32_to_cpu(l), base + offset);222 break;223 case 8:224 memcpy(&l, buf, sizeof l);225 writel(le32_to_cpu(l), base + offset);226 memcpy(&l, buf + sizeof l, sizeof l);227 writel(le32_to_cpu(l), base + offset + sizeof l);228 break;229 default:230 BUG();231 }232}233 234static u32 vm_generation(struct virtio_device *vdev)235{236 struct virtio_mmio_device *vm_dev = to_virtio_mmio_device(vdev);237 238 if (vm_dev->version == 1)239 return 0;240 else241 return readl(vm_dev->base + VIRTIO_MMIO_CONFIG_GENERATION);242}243 244static u8 vm_get_status(struct virtio_device *vdev)245{246 struct virtio_mmio_device *vm_dev = to_virtio_mmio_device(vdev);247 248 return readl(vm_dev->base + VIRTIO_MMIO_STATUS) & 0xff;249}250 251static void vm_set_status(struct virtio_device *vdev, u8 status)252{253 struct virtio_mmio_device *vm_dev = to_virtio_mmio_device(vdev);254 255 /* We should never be setting status to 0. */256 BUG_ON(status == 0);257 258 /*259 * Per memory-barriers.txt, wmb() is not needed to guarantee260 * that the cache coherent memory writes have completed261 * before writing to the MMIO region.262 */263 writel(status, vm_dev->base + VIRTIO_MMIO_STATUS);264}265 266static void vm_reset(struct virtio_device *vdev)267{268 struct virtio_mmio_device *vm_dev = to_virtio_mmio_device(vdev);269 270 /* 0 status means a reset. */271 writel(0, vm_dev->base + VIRTIO_MMIO_STATUS);272}273 274 275 276/* Transport interface */277 278/* the notify function used when creating a virt queue */279static bool vm_notify(struct virtqueue *vq)280{281 struct virtio_mmio_device *vm_dev = to_virtio_mmio_device(vq->vdev);282 283 /* We write the queue's selector into the notification register to284 * signal the other end */285 writel(vq->index, vm_dev->base + VIRTIO_MMIO_QUEUE_NOTIFY);286 return true;287}288 289static bool vm_notify_with_data(struct virtqueue *vq)290{291 struct virtio_mmio_device *vm_dev = to_virtio_mmio_device(vq->vdev);292 u32 data = vring_notification_data(vq);293 294 writel(data, vm_dev->base + VIRTIO_MMIO_QUEUE_NOTIFY);295 296 return true;297}298 299/* Notify all virtqueues on an interrupt. */300static irqreturn_t vm_interrupt(int irq, void *opaque)301{302 struct virtio_mmio_device *vm_dev = opaque;303 struct virtio_mmio_vq_info *info;304 unsigned long status;305 unsigned long flags;306 irqreturn_t ret = IRQ_NONE;307 308 /* Read and acknowledge interrupts */309 status = readl(vm_dev->base + VIRTIO_MMIO_INTERRUPT_STATUS);310 writel(status, vm_dev->base + VIRTIO_MMIO_INTERRUPT_ACK);311 312 if (unlikely(status & VIRTIO_MMIO_INT_CONFIG)) {313 virtio_config_changed(&vm_dev->vdev);314 ret = IRQ_HANDLED;315 }316 317 if (likely(status & VIRTIO_MMIO_INT_VRING)) {318 spin_lock_irqsave(&vm_dev->lock, flags);319 list_for_each_entry(info, &vm_dev->virtqueues, node)320 ret |= vring_interrupt(irq, info->vq);321 spin_unlock_irqrestore(&vm_dev->lock, flags);322 }323 324 return ret;325}326 327 328 329static void vm_del_vq(struct virtqueue *vq)330{331 struct virtio_mmio_device *vm_dev = to_virtio_mmio_device(vq->vdev);332 struct virtio_mmio_vq_info *info = vq->priv;333 unsigned long flags;334 unsigned int index = vq->index;335 336 spin_lock_irqsave(&vm_dev->lock, flags);337 list_del(&info->node);338 spin_unlock_irqrestore(&vm_dev->lock, flags);339 340 /* Select and deactivate the queue */341 writel(index, vm_dev->base + VIRTIO_MMIO_QUEUE_SEL);342 if (vm_dev->version == 1) {343 writel(0, vm_dev->base + VIRTIO_MMIO_QUEUE_PFN);344 } else {345 writel(0, vm_dev->base + VIRTIO_MMIO_QUEUE_READY);346 WARN_ON(readl(vm_dev->base + VIRTIO_MMIO_QUEUE_READY));347 }348 349 vring_del_virtqueue(vq);350 351 kfree(info);352}353 354static void vm_del_vqs(struct virtio_device *vdev)355{356 struct virtio_mmio_device *vm_dev = to_virtio_mmio_device(vdev);357 struct virtqueue *vq, *n;358 359 list_for_each_entry_safe(vq, n, &vdev->vqs, list)360 vm_del_vq(vq);361 362 free_irq(platform_get_irq(vm_dev->pdev, 0), vm_dev);363}364 365static void vm_synchronize_cbs(struct virtio_device *vdev)366{367 struct virtio_mmio_device *vm_dev = to_virtio_mmio_device(vdev);368 369 synchronize_irq(platform_get_irq(vm_dev->pdev, 0));370}371 372static struct virtqueue *vm_setup_vq(struct virtio_device *vdev, unsigned int index,373 void (*callback)(struct virtqueue *vq),374 const char *name, bool ctx)375{376 struct virtio_mmio_device *vm_dev = to_virtio_mmio_device(vdev);377 bool (*notify)(struct virtqueue *vq);378 struct virtio_mmio_vq_info *info;379 struct virtqueue *vq;380 unsigned long flags;381 unsigned int num;382 int err;383 384 if (__virtio_test_bit(vdev, VIRTIO_F_NOTIFICATION_DATA))385 notify = vm_notify_with_data;386 else387 notify = vm_notify;388 389 if (!name)390 return NULL;391 392 /* Select the queue we're interested in */393 writel(index, vm_dev->base + VIRTIO_MMIO_QUEUE_SEL);394 395 /* Queue shouldn't already be set up. */396 if (readl(vm_dev->base + (vm_dev->version == 1 ?397 VIRTIO_MMIO_QUEUE_PFN : VIRTIO_MMIO_QUEUE_READY))) {398 err = -ENOENT;399 goto error_available;400 }401 402 /* Allocate and fill out our active queue description */403 info = kmalloc(sizeof(*info), GFP_KERNEL);404 if (!info) {405 err = -ENOMEM;406 goto error_kmalloc;407 }408 409 num = readl(vm_dev->base + VIRTIO_MMIO_QUEUE_NUM_MAX);410 if (num == 0) {411 err = -ENOENT;412 goto error_new_virtqueue;413 }414 415 /* Create the vring */416 vq = vring_create_virtqueue(index, num, VIRTIO_MMIO_VRING_ALIGN, vdev,417 true, true, ctx, notify, callback, name);418 if (!vq) {419 err = -ENOMEM;420 goto error_new_virtqueue;421 }422 423 vq->num_max = num;424 425 /* Activate the queue */426 writel(virtqueue_get_vring_size(vq), vm_dev->base + VIRTIO_MMIO_QUEUE_NUM);427 if (vm_dev->version == 1) {428 u64 q_pfn = virtqueue_get_desc_addr(vq) >> PAGE_SHIFT;429 430 /*431 * virtio-mmio v1 uses a 32bit QUEUE PFN. If we have something432 * that doesn't fit in 32bit, fail the setup rather than433 * pretending to be successful.434 */435 if (q_pfn >> 32) {436 dev_err(&vdev->dev,437 "platform bug: legacy virtio-mmio must not be used with RAM above 0x%llxGB\n",438 0x1ULL << (32 + PAGE_SHIFT - 30));439 err = -E2BIG;440 goto error_bad_pfn;441 }442 443 writel(PAGE_SIZE, vm_dev->base + VIRTIO_MMIO_QUEUE_ALIGN);444 writel(q_pfn, vm_dev->base + VIRTIO_MMIO_QUEUE_PFN);445 } else {446 u64 addr;447 448 addr = virtqueue_get_desc_addr(vq);449 writel((u32)addr, vm_dev->base + VIRTIO_MMIO_QUEUE_DESC_LOW);450 writel((u32)(addr >> 32),451 vm_dev->base + VIRTIO_MMIO_QUEUE_DESC_HIGH);452 453 addr = virtqueue_get_avail_addr(vq);454 writel((u32)addr, vm_dev->base + VIRTIO_MMIO_QUEUE_AVAIL_LOW);455 writel((u32)(addr >> 32),456 vm_dev->base + VIRTIO_MMIO_QUEUE_AVAIL_HIGH);457 458 addr = virtqueue_get_used_addr(vq);459 writel((u32)addr, vm_dev->base + VIRTIO_MMIO_QUEUE_USED_LOW);460 writel((u32)(addr >> 32),461 vm_dev->base + VIRTIO_MMIO_QUEUE_USED_HIGH);462 463 writel(1, vm_dev->base + VIRTIO_MMIO_QUEUE_READY);464 }465 466 vq->priv = info;467 info->vq = vq;468 469 spin_lock_irqsave(&vm_dev->lock, flags);470 list_add(&info->node, &vm_dev->virtqueues);471 spin_unlock_irqrestore(&vm_dev->lock, flags);472 473 return vq;474 475error_bad_pfn:476 vring_del_virtqueue(vq);477error_new_virtqueue:478 if (vm_dev->version == 1) {479 writel(0, vm_dev->base + VIRTIO_MMIO_QUEUE_PFN);480 } else {481 writel(0, vm_dev->base + VIRTIO_MMIO_QUEUE_READY);482 WARN_ON(readl(vm_dev->base + VIRTIO_MMIO_QUEUE_READY));483 }484 kfree(info);485error_kmalloc:486error_available:487 return ERR_PTR(err);488}489 490static int vm_find_vqs(struct virtio_device *vdev, unsigned int nvqs,491 struct virtqueue *vqs[],492 struct virtqueue_info vqs_info[],493 struct irq_affinity *desc)494{495 struct virtio_mmio_device *vm_dev = to_virtio_mmio_device(vdev);496 int irq = platform_get_irq(vm_dev->pdev, 0);497 int i, err, queue_idx = 0;498 499 if (irq < 0)500 return irq;501 502 err = request_irq(irq, vm_interrupt, IRQF_SHARED,503 dev_name(&vdev->dev), vm_dev);504 if (err)505 return err;506 507 if (of_property_read_bool(vm_dev->pdev->dev.of_node, "wakeup-source"))508 enable_irq_wake(irq);509 510 for (i = 0; i < nvqs; ++i) {511 struct virtqueue_info *vqi = &vqs_info[i];512 513 if (!vqi->name) {514 vqs[i] = NULL;515 continue;516 }517 518 vqs[i] = vm_setup_vq(vdev, queue_idx++, vqi->callback,519 vqi->name, vqi->ctx);520 if (IS_ERR(vqs[i])) {521 vm_del_vqs(vdev);522 return PTR_ERR(vqs[i]);523 }524 }525 526 return 0;527}528 529static const char *vm_bus_name(struct virtio_device *vdev)530{531 struct virtio_mmio_device *vm_dev = to_virtio_mmio_device(vdev);532 533 return vm_dev->pdev->name;534}535 536static bool vm_get_shm_region(struct virtio_device *vdev,537 struct virtio_shm_region *region, u8 id)538{539 struct virtio_mmio_device *vm_dev = to_virtio_mmio_device(vdev);540 u64 len, addr;541 542 /* Select the region we're interested in */543 writel(id, vm_dev->base + VIRTIO_MMIO_SHM_SEL);544 545 /* Read the region size */546 len = (u64) readl(vm_dev->base + VIRTIO_MMIO_SHM_LEN_LOW);547 len |= (u64) readl(vm_dev->base + VIRTIO_MMIO_SHM_LEN_HIGH) << 32;548 549 region->len = len;550 551 /* Check if region length is -1. If that's the case, the shared memory552 * region does not exist and there is no need to proceed further.553 */554 if (len == ~(u64)0)555 return false;556 557 /* Read the region base address */558 addr = (u64) readl(vm_dev->base + VIRTIO_MMIO_SHM_BASE_LOW);559 addr |= (u64) readl(vm_dev->base + VIRTIO_MMIO_SHM_BASE_HIGH) << 32;560 561 region->addr = addr;562 563 return true;564}565 566static const struct virtio_config_ops virtio_mmio_config_ops = {567 .get = vm_get,568 .set = vm_set,569 .generation = vm_generation,570 .get_status = vm_get_status,571 .set_status = vm_set_status,572 .reset = vm_reset,573 .find_vqs = vm_find_vqs,574 .del_vqs = vm_del_vqs,575 .get_features = vm_get_features,576 .finalize_features = vm_finalize_features,577 .bus_name = vm_bus_name,578 .get_shm_region = vm_get_shm_region,579 .synchronize_cbs = vm_synchronize_cbs,580};581 582#ifdef CONFIG_PM_SLEEP583static int virtio_mmio_freeze(struct device *dev)584{585 struct virtio_mmio_device *vm_dev = dev_get_drvdata(dev);586 587 return virtio_device_freeze(&vm_dev->vdev);588}589 590static int virtio_mmio_restore(struct device *dev)591{592 struct virtio_mmio_device *vm_dev = dev_get_drvdata(dev);593 594 if (vm_dev->version == 1)595 writel(PAGE_SIZE, vm_dev->base + VIRTIO_MMIO_GUEST_PAGE_SIZE);596 597 return virtio_device_restore(&vm_dev->vdev);598}599 600static const struct dev_pm_ops virtio_mmio_pm_ops = {601 SET_SYSTEM_SLEEP_PM_OPS(virtio_mmio_freeze, virtio_mmio_restore)602};603#endif604 605static void virtio_mmio_release_dev(struct device *_d)606{607 struct virtio_device *vdev =608 container_of(_d, struct virtio_device, dev);609 struct virtio_mmio_device *vm_dev = to_virtio_mmio_device(vdev);610 611 kfree(vm_dev);612}613 614/* Platform device */615 616static int virtio_mmio_probe(struct platform_device *pdev)617{618 struct virtio_mmio_device *vm_dev;619 unsigned long magic;620 int rc;621 622 vm_dev = kzalloc(sizeof(*vm_dev), GFP_KERNEL);623 if (!vm_dev)624 return -ENOMEM;625 626 vm_dev->vdev.dev.parent = &pdev->dev;627 vm_dev->vdev.dev.release = virtio_mmio_release_dev;628 vm_dev->vdev.config = &virtio_mmio_config_ops;629 vm_dev->pdev = pdev;630 INIT_LIST_HEAD(&vm_dev->virtqueues);631 spin_lock_init(&vm_dev->lock);632 633 vm_dev->base = devm_platform_ioremap_resource(pdev, 0);634 if (IS_ERR(vm_dev->base)) {635 rc = PTR_ERR(vm_dev->base);636 goto free_vm_dev;637 }638 639 /* Check magic value */640 magic = readl(vm_dev->base + VIRTIO_MMIO_MAGIC_VALUE);641 if (magic != ('v' | 'i' << 8 | 'r' << 16 | 't' << 24)) {642 dev_warn(&pdev->dev, "Wrong magic value 0x%08lx!\n", magic);643 rc = -ENODEV;644 goto free_vm_dev;645 }646 647 /* Check device version */648 vm_dev->version = readl(vm_dev->base + VIRTIO_MMIO_VERSION);649 if (vm_dev->version < 1 || vm_dev->version > 2) {650 dev_err(&pdev->dev, "Version %ld not supported!\n",651 vm_dev->version);652 rc = -ENXIO;653 goto free_vm_dev;654 }655 656 vm_dev->vdev.id.device = readl(vm_dev->base + VIRTIO_MMIO_DEVICE_ID);657 if (vm_dev->vdev.id.device == 0) {658 /*659 * virtio-mmio device with an ID 0 is a (dummy) placeholder660 * with no function. End probing now with no error reported.661 */662 rc = -ENODEV;663 goto free_vm_dev;664 }665 vm_dev->vdev.id.vendor = readl(vm_dev->base + VIRTIO_MMIO_VENDOR_ID);666 667 if (vm_dev->version == 1) {668 writel(PAGE_SIZE, vm_dev->base + VIRTIO_MMIO_GUEST_PAGE_SIZE);669 670 rc = dma_set_mask(&pdev->dev, DMA_BIT_MASK(64));671 /*672 * In the legacy case, ensure our coherently-allocated virtio673 * ring will be at an address expressable as a 32-bit PFN.674 */675 if (!rc)676 dma_set_coherent_mask(&pdev->dev,677 DMA_BIT_MASK(32 + PAGE_SHIFT));678 } else {679 rc = dma_set_mask_and_coherent(&pdev->dev, DMA_BIT_MASK(64));680 }681 if (rc)682 rc = dma_set_mask_and_coherent(&pdev->dev, DMA_BIT_MASK(32));683 if (rc)684 dev_warn(&pdev->dev, "Failed to enable 64-bit or 32-bit DMA. Trying to continue, but this might not work.\n");685 686 platform_set_drvdata(pdev, vm_dev);687 688 rc = register_virtio_device(&vm_dev->vdev);689 if (rc)690 put_device(&vm_dev->vdev.dev);691 692 return rc;693 694free_vm_dev:695 kfree(vm_dev);696 return rc;697}698 699static void virtio_mmio_remove(struct platform_device *pdev)700{701 struct virtio_mmio_device *vm_dev = platform_get_drvdata(pdev);702 unregister_virtio_device(&vm_dev->vdev);703}704 705 706 707/* Devices list parameter */708 709#if defined(CONFIG_VIRTIO_MMIO_CMDLINE_DEVICES)710 711static struct device vm_cmdline_parent = {712 .init_name = "virtio-mmio-cmdline",713};714 715static int vm_cmdline_parent_registered;716static int vm_cmdline_id;717 718static int vm_cmdline_set(const char *device,719 const struct kernel_param *kp)720{721 int err;722 struct resource resources[2] = {};723 char *str;724 long long base, size;725 unsigned int irq;726 int processed, consumed = 0;727 struct platform_device *pdev;728 729 /* Consume "size" part of the command line parameter */730 size = memparse(device, &str);731 732 /* Get "@<base>:<irq>[:<id>]" chunks */733 processed = sscanf(str, "@%lli:%u%n:%d%n",734 &base, &irq, &consumed,735 &vm_cmdline_id, &consumed);736 737 /*738 * sscanf() must process at least 2 chunks; also there739 * must be no extra characters after the last chunk, so740 * str[consumed] must be '\0'741 */742 if (processed < 2 || str[consumed] || irq == 0)743 return -EINVAL;744 745 resources[0].flags = IORESOURCE_MEM;746 resources[0].start = base;747 resources[0].end = base + size - 1;748 749 resources[1].flags = IORESOURCE_IRQ;750 resources[1].start = resources[1].end = irq;751 752 if (!vm_cmdline_parent_registered) {753 err = device_register(&vm_cmdline_parent);754 if (err) {755 put_device(&vm_cmdline_parent);756 pr_err("Failed to register parent device!\n");757 return err;758 }759 vm_cmdline_parent_registered = 1;760 }761 762 pr_info("Registering device virtio-mmio.%d at 0x%llx-0x%llx, IRQ %d.\n",763 vm_cmdline_id,764 (unsigned long long)resources[0].start,765 (unsigned long long)resources[0].end,766 (int)resources[1].start);767 768 pdev = platform_device_register_resndata(&vm_cmdline_parent,769 "virtio-mmio", vm_cmdline_id++,770 resources, ARRAY_SIZE(resources), NULL, 0);771 772 return PTR_ERR_OR_ZERO(pdev);773}774 775static int vm_cmdline_get_device(struct device *dev, void *data)776{777 char *buffer = data;778 unsigned int len = strlen(buffer);779 struct platform_device *pdev = to_platform_device(dev);780 781 snprintf(buffer + len, PAGE_SIZE - len, "0x%llx@0x%llx:%llu:%d\n",782 pdev->resource[0].end - pdev->resource[0].start + 1ULL,783 (unsigned long long)pdev->resource[0].start,784 (unsigned long long)pdev->resource[1].start,785 pdev->id);786 return 0;787}788 789static int vm_cmdline_get(char *buffer, const struct kernel_param *kp)790{791 buffer[0] = '\0';792 device_for_each_child(&vm_cmdline_parent, buffer,793 vm_cmdline_get_device);794 return strlen(buffer) + 1;795}796 797static const struct kernel_param_ops vm_cmdline_param_ops = {798 .set = vm_cmdline_set,799 .get = vm_cmdline_get,800};801 802device_param_cb(device, &vm_cmdline_param_ops, NULL, S_IRUSR);803 804static int vm_unregister_cmdline_device(struct device *dev,805 void *data)806{807 platform_device_unregister(to_platform_device(dev));808 809 return 0;810}811 812static void vm_unregister_cmdline_devices(void)813{814 if (vm_cmdline_parent_registered) {815 device_for_each_child(&vm_cmdline_parent, NULL,816 vm_unregister_cmdline_device);817 device_unregister(&vm_cmdline_parent);818 vm_cmdline_parent_registered = 0;819 }820}821 822#else823 824static void vm_unregister_cmdline_devices(void)825{826}827 828#endif829 830/* Platform driver */831 832static const struct of_device_id virtio_mmio_match[] = {833 { .compatible = "virtio,mmio", },834 {},835};836MODULE_DEVICE_TABLE(of, virtio_mmio_match);837 838#ifdef CONFIG_ACPI839static const struct acpi_device_id virtio_mmio_acpi_match[] = {840 { "LNRO0005", },841 { }842};843MODULE_DEVICE_TABLE(acpi, virtio_mmio_acpi_match);844#endif845 846static struct platform_driver virtio_mmio_driver = {847 .probe = virtio_mmio_probe,848 .remove_new = virtio_mmio_remove,849 .driver = {850 .name = "virtio-mmio",851 .of_match_table = virtio_mmio_match,852 .acpi_match_table = ACPI_PTR(virtio_mmio_acpi_match),853#ifdef CONFIG_PM_SLEEP854 .pm = &virtio_mmio_pm_ops,855#endif856 },857};858 859static int __init virtio_mmio_init(void)860{861 return platform_driver_register(&virtio_mmio_driver);862}863 864static void __exit virtio_mmio_exit(void)865{866 platform_driver_unregister(&virtio_mmio_driver);867 vm_unregister_cmdline_devices();868}869 870module_init(virtio_mmio_init);871module_exit(virtio_mmio_exit);872 873MODULE_AUTHOR("Pawel Moll <pawel.moll@arm.com>");874MODULE_DESCRIPTION("Platform bus driver for memory mapped virtio devices");875MODULE_LICENSE("GPL");876