aboutsummaryrefslogtreecommitdiffstats
path: root/drivers
diff options
context:
space:
mode:
Diffstat (limited to 'drivers')
-rw-r--r--drivers/block/virtio_blk.c21
-rw-r--r--drivers/virtio/Kconfig11
-rw-r--r--drivers/virtio/virtio.c11
-rw-r--r--drivers/virtio/virtio_balloon.c33
-rw-r--r--drivers/virtio/virtio_mmio.c163
5 files changed, 207 insertions, 32 deletions
diff --git a/drivers/block/virtio_blk.c b/drivers/block/virtio_blk.c
index 0d39f2f4294a..693187df7601 100644
--- a/drivers/block/virtio_blk.c
+++ b/drivers/block/virtio_blk.c
@@ -29,9 +29,6 @@ struct virtio_blk
29 /* The disk structure for the kernel. */ 29 /* The disk structure for the kernel. */
30 struct gendisk *disk; 30 struct gendisk *disk;
31 31
32 /* Request tracking. */
33 struct list_head reqs;
34
35 mempool_t *pool; 32 mempool_t *pool;
36 33
37 /* Process context for config space updates */ 34 /* Process context for config space updates */
@@ -55,7 +52,6 @@ struct virtio_blk
55 52
56struct virtblk_req 53struct virtblk_req
57{ 54{
58 struct list_head list;
59 struct request *req; 55 struct request *req;
60 struct virtio_blk_outhdr out_hdr; 56 struct virtio_blk_outhdr out_hdr;
61 struct virtio_scsi_inhdr in_hdr; 57 struct virtio_scsi_inhdr in_hdr;
@@ -99,7 +95,6 @@ static void blk_done(struct virtqueue *vq)
99 } 95 }
100 96
101 __blk_end_request_all(vbr->req, error); 97 __blk_end_request_all(vbr->req, error);
102 list_del(&vbr->list);
103 mempool_free(vbr, vblk->pool); 98 mempool_free(vbr, vblk->pool);
104 } 99 }
105 /* In case queue is stopped waiting for more buffers. */ 100 /* In case queue is stopped waiting for more buffers. */
@@ -184,7 +179,6 @@ static bool do_req(struct request_queue *q, struct virtio_blk *vblk,
184 return false; 179 return false;
185 } 180 }
186 181
187 list_add_tail(&vbr->list, &vblk->reqs);
188 return true; 182 return true;
189} 183}
190 184
@@ -437,7 +431,6 @@ static int __devinit virtblk_probe(struct virtio_device *vdev)
437 goto out_free_index; 431 goto out_free_index;
438 } 432 }
439 433
440 INIT_LIST_HEAD(&vblk->reqs);
441 spin_lock_init(&vblk->lock); 434 spin_lock_init(&vblk->lock);
442 vblk->vdev = vdev; 435 vblk->vdev = vdev;
443 vblk->sg_elems = sg_elems; 436 vblk->sg_elems = sg_elems;
@@ -583,21 +576,29 @@ static void __devexit virtblk_remove(struct virtio_device *vdev)
583{ 576{
584 struct virtio_blk *vblk = vdev->priv; 577 struct virtio_blk *vblk = vdev->priv;
585 int index = vblk->index; 578 int index = vblk->index;
579 struct virtblk_req *vbr;
580 unsigned long flags;
586 581
587 /* Prevent config work handler from accessing the device. */ 582 /* Prevent config work handler from accessing the device. */
588 mutex_lock(&vblk->config_lock); 583 mutex_lock(&vblk->config_lock);
589 vblk->config_enable = false; 584 vblk->config_enable = false;
590 mutex_unlock(&vblk->config_lock); 585 mutex_unlock(&vblk->config_lock);
591 586
592 /* Nothing should be pending. */
593 BUG_ON(!list_empty(&vblk->reqs));
594
595 /* Stop all the virtqueues. */ 587 /* Stop all the virtqueues. */
596 vdev->config->reset(vdev); 588 vdev->config->reset(vdev);
597 589
598 flush_work(&vblk->config_work); 590 flush_work(&vblk->config_work);
599 591
600 del_gendisk(vblk->disk); 592 del_gendisk(vblk->disk);
593
594 /* Abort requests dispatched to driver. */
595 spin_lock_irqsave(&vblk->lock, flags);
596 while ((vbr = virtqueue_detach_unused_buf(vblk->vq))) {
597 __blk_end_request_all(vbr->req, -EIO);
598 mempool_free(vbr, vblk->pool);
599 }
600 spin_unlock_irqrestore(&vblk->lock, flags);
601
601 blk_cleanup_queue(vblk->disk->queue); 602 blk_cleanup_queue(vblk->disk->queue);
602 put_disk(vblk->disk); 603 put_disk(vblk->disk);
603 mempool_destroy(vblk->pool); 604 mempool_destroy(vblk->pool);
diff --git a/drivers/virtio/Kconfig b/drivers/virtio/Kconfig
index 1a61939b85fc..f38b17a86c35 100644
--- a/drivers/virtio/Kconfig
+++ b/drivers/virtio/Kconfig
@@ -46,4 +46,15 @@ config VIRTIO_BALLOON
46 46
47 If unsure, say N. 47 If unsure, say N.
48 48
49config VIRTIO_MMIO_CMDLINE_DEVICES
50 bool "Memory mapped virtio devices parameter parsing"
51 depends on VIRTIO_MMIO
52 ---help---
53 Allow virtio-mmio devices instantiation via the kernel command line
54 or module parameters. Be aware that using incorrect parameters (base
55 address in particular) can crash your system - you have been warned.
56 See Documentation/kernel-parameters.txt for details.
57
58 If unsure, say 'N'.
59
49endmenu 60endmenu
diff --git a/drivers/virtio/virtio.c b/drivers/virtio/virtio.c
index 984c501c258f..f3558070e375 100644
--- a/drivers/virtio/virtio.c
+++ b/drivers/virtio/virtio.c
@@ -2,9 +2,10 @@
2#include <linux/spinlock.h> 2#include <linux/spinlock.h>
3#include <linux/virtio_config.h> 3#include <linux/virtio_config.h>
4#include <linux/module.h> 4#include <linux/module.h>
5#include <linux/idr.h>
5 6
6/* Unique numbering for virtio devices. */ 7/* Unique numbering for virtio devices. */
7static unsigned int dev_index; 8static DEFINE_IDA(virtio_index_ida);
8 9
9static ssize_t device_show(struct device *_d, 10static ssize_t device_show(struct device *_d,
10 struct device_attribute *attr, char *buf) 11 struct device_attribute *attr, char *buf)
@@ -193,7 +194,11 @@ int register_virtio_device(struct virtio_device *dev)
193 dev->dev.bus = &virtio_bus; 194 dev->dev.bus = &virtio_bus;
194 195
195 /* Assign a unique device index and hence name. */ 196 /* Assign a unique device index and hence name. */
196 dev->index = dev_index++; 197 err = ida_simple_get(&virtio_index_ida, 0, 0, GFP_KERNEL);
198 if (err < 0)
199 goto out;
200
201 dev->index = err;
197 dev_set_name(&dev->dev, "virtio%u", dev->index); 202 dev_set_name(&dev->dev, "virtio%u", dev->index);
198 203
199 /* We always start by resetting the device, in case a previous 204 /* We always start by resetting the device, in case a previous
@@ -208,6 +213,7 @@ int register_virtio_device(struct virtio_device *dev)
208 /* device_register() causes the bus infrastructure to look for a 213 /* device_register() causes the bus infrastructure to look for a
209 * matching driver. */ 214 * matching driver. */
210 err = device_register(&dev->dev); 215 err = device_register(&dev->dev);
216out:
211 if (err) 217 if (err)
212 add_status(dev, VIRTIO_CONFIG_S_FAILED); 218 add_status(dev, VIRTIO_CONFIG_S_FAILED);
213 return err; 219 return err;
@@ -217,6 +223,7 @@ EXPORT_SYMBOL_GPL(register_virtio_device);
217void unregister_virtio_device(struct virtio_device *dev) 223void unregister_virtio_device(struct virtio_device *dev)
218{ 224{
219 device_unregister(&dev->dev); 225 device_unregister(&dev->dev);
226 ida_simple_remove(&virtio_index_ida, dev->index);
220} 227}
221EXPORT_SYMBOL_GPL(unregister_virtio_device); 228EXPORT_SYMBOL_GPL(unregister_virtio_device);
222 229
diff --git a/drivers/virtio/virtio_balloon.c b/drivers/virtio/virtio_balloon.c
index 8807fe501d20..bfbc15ca38dd 100644
--- a/drivers/virtio/virtio_balloon.c
+++ b/drivers/virtio/virtio_balloon.c
@@ -381,21 +381,25 @@ out:
381 return err; 381 return err;
382} 382}
383 383
384static void __devexit virtballoon_remove(struct virtio_device *vdev) 384static void remove_common(struct virtio_balloon *vb)
385{ 385{
386 struct virtio_balloon *vb = vdev->priv;
387
388 kthread_stop(vb->thread);
389
390 /* There might be pages left in the balloon: free them. */ 386 /* There might be pages left in the balloon: free them. */
391 while (vb->num_pages) 387 while (vb->num_pages)
392 leak_balloon(vb, vb->num_pages); 388 leak_balloon(vb, vb->num_pages);
393 update_balloon_size(vb); 389 update_balloon_size(vb);
394 390
395 /* Now we reset the device so we can clean up the queues. */ 391 /* Now we reset the device so we can clean up the queues. */
396 vdev->config->reset(vdev); 392 vb->vdev->config->reset(vb->vdev);
397 393
398 vdev->config->del_vqs(vdev); 394 vb->vdev->config->del_vqs(vb->vdev);
395}
396
397static void __devexit virtballoon_remove(struct virtio_device *vdev)
398{
399 struct virtio_balloon *vb = vdev->priv;
400
401 kthread_stop(vb->thread);
402 remove_common(vb);
399 kfree(vb); 403 kfree(vb);
400} 404}
401 405
@@ -409,17 +413,11 @@ static int virtballoon_freeze(struct virtio_device *vdev)
409 * function is called. 413 * function is called.
410 */ 414 */
411 415
412 while (vb->num_pages) 416 remove_common(vb);
413 leak_balloon(vb, vb->num_pages);
414 update_balloon_size(vb);
415
416 /* Ensure we don't get any more requests from the host */
417 vdev->config->reset(vdev);
418 vdev->config->del_vqs(vdev);
419 return 0; 417 return 0;
420} 418}
421 419
422static int restore_common(struct virtio_device *vdev) 420static int virtballoon_restore(struct virtio_device *vdev)
423{ 421{
424 struct virtio_balloon *vb = vdev->priv; 422 struct virtio_balloon *vb = vdev->priv;
425 int ret; 423 int ret;
@@ -432,11 +430,6 @@ static int restore_common(struct virtio_device *vdev)
432 update_balloon_size(vb); 430 update_balloon_size(vb);
433 return 0; 431 return 0;
434} 432}
435
436static int virtballoon_restore(struct virtio_device *vdev)
437{
438 return restore_common(vdev);
439}
440#endif 433#endif
441 434
442static unsigned int features[] = { 435static unsigned int features[] = {
diff --git a/drivers/virtio/virtio_mmio.c b/drivers/virtio/virtio_mmio.c
index 01d6dc250d5c..453db0c403d8 100644
--- a/drivers/virtio/virtio_mmio.c
+++ b/drivers/virtio/virtio_mmio.c
@@ -6,6 +6,50 @@
6 * This module allows virtio devices to be used over a virtual, memory mapped 6 * This module allows virtio devices to be used over a virtual, memory mapped
7 * platform device. 7 * platform device.
8 * 8 *
9 * The guest device(s) may be instantiated in one of three equivalent ways:
10 *
11 * 1. Static platform device in board's code, eg.:
12 *
13 * static struct platform_device v2m_virtio_device = {
14 * .name = "virtio-mmio",
15 * .id = -1,
16 * .num_resources = 2,
17 * .resource = (struct resource []) {
18 * {
19 * .start = 0x1001e000,
20 * .end = 0x1001e0ff,
21 * .flags = IORESOURCE_MEM,
22 * }, {
23 * .start = 42 + 32,
24 * .end = 42 + 32,
25 * .flags = IORESOURCE_IRQ,
26 * },
27 * }
28 * };
29 *
30 * 2. Device Tree node, eg.:
31 *
32 * virtio_block@1e000 {
33 * compatible = "virtio,mmio";
34 * reg = <0x1e000 0x100>;
35 * interrupts = <42>;
36 * }
37 *
38 * 3. Kernel module (or command line) parameter. Can be used more than once -
39 * one device will be created for each one. Syntax:
40 *
41 * [virtio_mmio.]device=<size>@<baseaddr>:<irq>[:<id>]
42 * where:
43 * <size> := size (can use standard suffixes like K, M or G)
44 * <baseaddr> := physical base address
45 * <irq> := interrupt number (as passed to request_irq())
46 * <id> := (optional) platform device id
47 * eg.:
48 * virtio_mmio.device=0x100@0x100b0000:48 \
49 * virtio_mmio.device=1K@0x1001e000:74
50 *
51 *
52 *
9 * Registers layout (all 32-bit wide): 53 * Registers layout (all 32-bit wide):
10 * 54 *
11 * offset d. name description 55 * offset d. name description
@@ -42,6 +86,8 @@
42 * See the COPYING file in the top-level directory. 86 * See the COPYING file in the top-level directory.
43 */ 87 */
44 88
89#define pr_fmt(fmt) "virtio-mmio: " fmt
90
45#include <linux/highmem.h> 91#include <linux/highmem.h>
46#include <linux/interrupt.h> 92#include <linux/interrupt.h>
47#include <linux/io.h> 93#include <linux/io.h>
@@ -449,6 +495,122 @@ static int __devexit virtio_mmio_remove(struct platform_device *pdev)
449 495
450 496
451 497
498/* Devices list parameter */
499
500#if defined(CONFIG_VIRTIO_MMIO_CMDLINE_DEVICES)
501
502static struct device vm_cmdline_parent = {
503 .init_name = "virtio-mmio-cmdline",
504};
505
506static int vm_cmdline_parent_registered;
507static int vm_cmdline_id;
508
509static int vm_cmdline_set(const char *device,
510 const struct kernel_param *kp)
511{
512 int err;
513 struct resource resources[2] = {};
514 char *str;
515 long long int base;
516 int processed, consumed = 0;
517 struct platform_device *pdev;
518
519 resources[0].flags = IORESOURCE_MEM;
520 resources[1].flags = IORESOURCE_IRQ;
521
522 resources[0].end = memparse(device, &str) - 1;
523
524 processed = sscanf(str, "@%lli:%u%n:%d%n",
525 &base, &resources[1].start, &consumed,
526 &vm_cmdline_id, &consumed);
527
528 if (processed < 2 || processed > 3 || str[consumed])
529 return -EINVAL;
530
531 resources[0].start = base;
532 resources[0].end += base;
533 resources[1].end = resources[1].start;
534
535 if (!vm_cmdline_parent_registered) {
536 err = device_register(&vm_cmdline_parent);
537 if (err) {
538 pr_err("Failed to register parent device!\n");
539 return err;
540 }
541 vm_cmdline_parent_registered = 1;
542 }
543
544 pr_info("Registering device virtio-mmio.%d at 0x%llx-0x%llx, IRQ %d.\n",
545 vm_cmdline_id,
546 (unsigned long long)resources[0].start,
547 (unsigned long long)resources[0].end,
548 (int)resources[1].start);
549
550 pdev = platform_device_register_resndata(&vm_cmdline_parent,
551 "virtio-mmio", vm_cmdline_id++,
552 resources, ARRAY_SIZE(resources), NULL, 0);
553 if (IS_ERR(pdev))
554 return PTR_ERR(pdev);
555
556 return 0;
557}
558
559static int vm_cmdline_get_device(struct device *dev, void *data)
560{
561 char *buffer = data;
562 unsigned int len = strlen(buffer);
563 struct platform_device *pdev = to_platform_device(dev);
564
565 snprintf(buffer + len, PAGE_SIZE - len, "0x%llx@0x%llx:%llu:%d\n",
566 pdev->resource[0].end - pdev->resource[0].start + 1ULL,
567 (unsigned long long)pdev->resource[0].start,
568 (unsigned long long)pdev->resource[1].start,
569 pdev->id);
570 return 0;
571}
572
573static int vm_cmdline_get(char *buffer, const struct kernel_param *kp)
574{
575 buffer[0] = '\0';
576 device_for_each_child(&vm_cmdline_parent, buffer,
577 vm_cmdline_get_device);
578 return strlen(buffer) + 1;
579}
580
581static struct kernel_param_ops vm_cmdline_param_ops = {
582 .set = vm_cmdline_set,
583 .get = vm_cmdline_get,
584};
585
586device_param_cb(device, &vm_cmdline_param_ops, NULL, S_IRUSR);
587
588static int vm_unregister_cmdline_device(struct device *dev,
589 void *data)
590{
591 platform_device_unregister(to_platform_device(dev));
592
593 return 0;
594}
595
596static void vm_unregister_cmdline_devices(void)
597{
598 if (vm_cmdline_parent_registered) {
599 device_for_each_child(&vm_cmdline_parent, NULL,
600 vm_unregister_cmdline_device);
601 device_unregister(&vm_cmdline_parent);
602 vm_cmdline_parent_registered = 0;
603 }
604}
605
606#else
607
608static void vm_unregister_cmdline_devices(void)
609{
610}
611
612#endif
613
452/* Platform driver */ 614/* Platform driver */
453 615
454static struct of_device_id virtio_mmio_match[] = { 616static struct of_device_id virtio_mmio_match[] = {
@@ -475,6 +637,7 @@ static int __init virtio_mmio_init(void)
475static void __exit virtio_mmio_exit(void) 637static void __exit virtio_mmio_exit(void)
476{ 638{
477 platform_driver_unregister(&virtio_mmio_driver); 639 platform_driver_unregister(&virtio_mmio_driver);
640 vm_unregister_cmdline_devices();
478} 641}
479 642
480module_init(virtio_mmio_init); 643module_init(virtio_mmio_init);