linux-kernel.vger.kernel.org archive mirror
 help / color / mirror / Atom feed
* [PATCH v4 00/25] virtio: fix spec compliance issues
@ 2014-10-13  7:48 Michael S. Tsirkin
  2014-10-13  7:48 ` [PATCH v4 01/25] virtio_pci: fix virtio spec compliance on restore Michael S. Tsirkin
                   ` (24 more replies)
  0 siblings, 25 replies; 43+ messages in thread
From: Michael S. Tsirkin @ 2014-10-13  7:48 UTC (permalink / raw)
  To: linux-kernel
  Cc: Rusty Russell, virtualization, linux-scsi, linux-s390,
	v9fs-developer, netdev, kvm, Amit Shah, Cornelia Huck,
	Christian Borntraeger, David S. Miller, Paolo Bonzini

Changes from v4:
	rename virtio_enable_vqs_early() to virtio_device_ready()
Note: Rusty requested we add a BUG_ON in the virtio_ring code.
	This can be done by a separate patch on top.
	Good for bisectability in case BUG_ON starts triggering :)

Rusty, please review this, and consider for this merge window.

This fixes the following virtio spec compliance issues:
1. on restore, drivers use device before setting ACKNOWLEDGE and DRIVER bits
2. on probe, drivers aren't prepared to handle config interrupts
   arriving before probe returns
3. on probe, drivers use device before DRIVER_OK it set

Note that 1 is a clear violation of virtio spec 0.9 and 1.0,
so I am proposing the fix for stable. OTOH 2 is against 1.0 rules but
is a known documented bug in many drivers, so let's fix it going
forward, but it does not seem to be worth it to backport
the changes.

An error handling bugfix for virtio-net and a fix for a
theoretical race condition in virtio scsi is also included.

2 is merely a theoretical race condition, but it seems important
to address to make sure that changes to address 3 do not introduce
instability.

I also included patch to drop scan callback use from virtio
scsi: using this callback creates asymmetry between probe
and resume, and we actually had to add code comments so
people can figure out the flow. Code flow becomes clearer
with the new API.

After this change, the only user of the scan callback is virtio rng.
It's possible to modify it trivially and then drop scan callback
from core, but I'm rather inclined to look at ways to
make some rng core changes so that we don't need to
have so many variables tracking device state.
So this is deferred for now.

Michael S. Tsirkin (24):
  virtio_pci: fix virtio spec compliance on restore
  virtio: unify config_changed handling
  virtio-pci: move freeze/restore to virtio core
  virtio: defer config changed notifications
  virtio_blk: drop config_enable
  virtio-blk: drop config_mutex
  virtio_net: drop config_enable
  virtio-net: drop config_mutex
  virtio_net: minor cleanup
  virtio: add API to enable VQs early
  virtio_net: enable VQs early
  virtio_blk: enable VQs early
  virtio_console: enable VQs early
  9p/trans_virtio: enable VQs early
  virtio_net: fix use after free on allocation failure
  virtio_scsi: move kick event out from virtscsi_init
  virtio_blk: enable VQs early on restore
  virtio_scsi: enable VQs early on restore
  virtio_console: enable VQs early on restore
  virtio_net: enable VQs early on restore
  virtio_scsi: fix race on device removal
  virtio_balloon: enable VQs early on restore
  virtio_scsi: drop scan callback
  virtio-rng: refactor probe error handling

Paolo Bonzini (1):
  virito_scsi: use freezable WQ for events

 include/linux/virtio.h              |  14 +++++
 include/linux/virtio_config.h       |  17 ++++++
 drivers/block/virtio_blk.c          |  40 ++++----------
 drivers/char/hw_random/virtio-rng.c |  15 +++---
 drivers/char/virtio_console.c       |   4 ++
 drivers/misc/mic/card/mic_virtio.c  |   6 +--
 drivers/net/virtio_net.c            |  44 +++++-----------
 drivers/s390/kvm/kvm_virtio.c       |   9 +---
 drivers/s390/kvm/virtio_ccw.c       |   6 +--
 drivers/scsi/virtio_scsi.c          |  42 +++++++++------
 drivers/virtio/virtio.c             | 102 ++++++++++++++++++++++++++++++++++++
 drivers/virtio/virtio_balloon.c     |   2 +
 drivers/virtio/virtio_mmio.c        |   7 +--
 drivers/virtio/virtio_pci.c         |  33 ++----------
 net/9p/trans_virtio.c               |   2 +
 15 files changed, 206 insertions(+), 137 deletions(-)

-- 
MST



^ permalink raw reply	[flat|nested] 43+ messages in thread

* [PATCH v4 01/25] virtio_pci: fix virtio spec compliance on restore
  2014-10-13  7:48 [PATCH v4 00/25] virtio: fix spec compliance issues Michael S. Tsirkin
@ 2014-10-13  7:48 ` Michael S. Tsirkin
  2014-10-13  7:48 ` [PATCH v4 02/25] virtio: unify config_changed handling Michael S. Tsirkin
                   ` (23 subsequent siblings)
  24 siblings, 0 replies; 43+ messages in thread
From: Michael S. Tsirkin @ 2014-10-13  7:48 UTC (permalink / raw)
  To: linux-kernel
  Cc: Rusty Russell, virtualization, linux-scsi, linux-s390,
	v9fs-developer, netdev, kvm, Amit Shah, Cornelia Huck,
	Christian Borntraeger, David S. Miller, Paolo Bonzini, stable

On restore, virtio pci does the following:
+ set features
+ init vqs etc - device can be used at this point!
+ set ACKNOWLEDGE,DRIVER and DRIVER_OK status bits

This is in violation of the virtio spec, which
requires the following order:
- ACKNOWLEDGE
- DRIVER
- init vqs
- DRIVER_OK

This behaviour will break with hypervisors that assume spec compliant
behaviour.  It seems like a good idea to have this patch applied to
stable branches to reduce the support butden for the hypervisors.

Cc: stable@vger.kernel.org
Cc: Amit Shah <amit.shah@redhat.com>
Signed-off-by: Michael S. Tsirkin <mst@redhat.com>
---
 drivers/virtio/virtio_pci.c | 33 ++++++++++++++++++++++++++++++---
 1 file changed, 30 insertions(+), 3 deletions(-)

diff --git a/drivers/virtio/virtio_pci.c b/drivers/virtio/virtio_pci.c
index 3d1463c..add40d0 100644
--- a/drivers/virtio/virtio_pci.c
+++ b/drivers/virtio/virtio_pci.c
@@ -789,6 +789,7 @@ static int virtio_pci_restore(struct device *dev)
 	struct pci_dev *pci_dev = to_pci_dev(dev);
 	struct virtio_pci_device *vp_dev = pci_get_drvdata(pci_dev);
 	struct virtio_driver *drv;
+	unsigned status = 0;
 	int ret;
 
 	drv = container_of(vp_dev->vdev.dev.driver,
@@ -799,14 +800,40 @@ static int virtio_pci_restore(struct device *dev)
 		return ret;
 
 	pci_set_master(pci_dev);
+	/* We always start by resetting the device, in case a previous
+	 * driver messed it up. */
+	vp_reset(&vp_dev->vdev);
+
+	/* Acknowledge that we've seen the device. */
+	status |= VIRTIO_CONFIG_S_ACKNOWLEDGE;
+	vp_set_status(&vp_dev->vdev, status);
+
+	/* Maybe driver failed before freeze.
+	 * Restore the failed status, for debugging. */
+	status |= vp_dev->saved_status & VIRTIO_CONFIG_S_FAILED;
+	vp_set_status(&vp_dev->vdev, status);
+
+	if (!drv)
+		return 0;
+
+	/* We have a driver! */
+	status |= VIRTIO_CONFIG_S_DRIVER;
+	vp_set_status(&vp_dev->vdev, status);
+
 	vp_finalize_features(&vp_dev->vdev);
 
-	if (drv && drv->restore)
+	if (drv->restore) {
 		ret = drv->restore(&vp_dev->vdev);
+		if (ret) {
+			status |= VIRTIO_CONFIG_S_FAILED;
+			vp_set_status(&vp_dev->vdev, status);
+			return ret;
+		}
+	}
 
 	/* Finally, tell the device we're all set */
-	if (!ret)
-		vp_set_status(&vp_dev->vdev, vp_dev->saved_status);
+	status |= VIRTIO_CONFIG_S_DRIVER_OK;
+	vp_set_status(&vp_dev->vdev, status);
 
 	return ret;
 }
-- 
MST



^ permalink raw reply related	[flat|nested] 43+ messages in thread

* [PATCH v4 02/25] virtio: unify config_changed handling
  2014-10-13  7:48 [PATCH v4 00/25] virtio: fix spec compliance issues Michael S. Tsirkin
  2014-10-13  7:48 ` [PATCH v4 01/25] virtio_pci: fix virtio spec compliance on restore Michael S. Tsirkin
@ 2014-10-13  7:48 ` Michael S. Tsirkin
  2014-10-13  7:48 ` [PATCH v4 03/25] virtio-pci: move freeze/restore to virtio core Michael S. Tsirkin
                   ` (22 subsequent siblings)
  24 siblings, 0 replies; 43+ messages in thread
From: Michael S. Tsirkin @ 2014-10-13  7:48 UTC (permalink / raw)
  To: linux-kernel
  Cc: Rusty Russell, virtualization, linux-scsi, linux-s390,
	v9fs-developer, netdev, kvm, Amit Shah, Cornelia Huck,
	Christian Borntraeger, David S. Miller, Paolo Bonzini, linux390,
	Martin Schwidefsky, Heiko Carstens, Sudeep Dutt, Ashutosh Dixit,
	Greg Kroah-Hartman, Nikhil Rao, Andrew Morton, Siva Yerramreddy,
	Wolfram Sang, Heinz Graalfs

Replace duplicated code in all transports with a single wrapper in
virtio.c.

The only functional change is in virtio_mmio.c: if a buggy device sends
us an interrupt before driver is set, we previously returned IRQ_NONE,
now we return IRQ_HANDLED.

As this must not happen in practice, this does not look like a big deal.

See also commit 3fff0179e33cd7d0a688dab65700c46ad089e934
	virtio-pci: do not oops on config change if driver not loaded.
for the original motivation behind the driver check.

Signed-off-by: Michael S. Tsirkin <mst@redhat.com>
Reviewed-by: Cornelia Huck <cornelia.huck@de.ibm.com>
---
 include/linux/virtio.h             | 2 ++
 drivers/misc/mic/card/mic_virtio.c | 6 +-----
 drivers/s390/kvm/kvm_virtio.c      | 9 +--------
 drivers/s390/kvm/virtio_ccw.c      | 6 +-----
 drivers/virtio/virtio.c            | 9 +++++++++
 drivers/virtio/virtio_mmio.c       | 7 ++-----
 drivers/virtio/virtio_pci.c        | 6 +-----
 7 files changed, 17 insertions(+), 28 deletions(-)

diff --git a/include/linux/virtio.h b/include/linux/virtio.h
index b46671e..3c19bd3 100644
--- a/include/linux/virtio.h
+++ b/include/linux/virtio.h
@@ -108,6 +108,8 @@ void unregister_virtio_device(struct virtio_device *dev);
 
 void virtio_break_device(struct virtio_device *dev);
 
+void virtio_config_changed(struct virtio_device *dev);
+
 /**
  * virtio_driver - operations for a virtio I/O driver
  * @driver: underlying device driver (populate name and owner).
diff --git a/drivers/misc/mic/card/mic_virtio.c b/drivers/misc/mic/card/mic_virtio.c
index f14b600..e647947 100644
--- a/drivers/misc/mic/card/mic_virtio.c
+++ b/drivers/misc/mic/card/mic_virtio.c
@@ -462,16 +462,12 @@ static void mic_handle_config_change(struct mic_device_desc __iomem *d,
 	struct mic_device_ctrl __iomem *dc
 		= (void __iomem *)d + mic_aligned_desc_size(d);
 	struct mic_vdev *mvdev = (struct mic_vdev *)ioread64(&dc->vdev);
-	struct virtio_driver *drv;
 
 	if (ioread8(&dc->config_change) != MIC_VIRTIO_PARAM_CONFIG_CHANGED)
 		return;
 
 	dev_dbg(mdrv->dev, "%s %d\n", __func__, __LINE__);
-	drv = container_of(mvdev->vdev.dev.driver,
-				struct virtio_driver, driver);
-	if (drv->config_changed)
-		drv->config_changed(&mvdev->vdev);
+	virtio_config_changed(&mvdev->vdev);
 	iowrite8(1, &dc->guest_ack);
 }
 
diff --git a/drivers/s390/kvm/kvm_virtio.c b/drivers/s390/kvm/kvm_virtio.c
index a134965..6431290 100644
--- a/drivers/s390/kvm/kvm_virtio.c
+++ b/drivers/s390/kvm/kvm_virtio.c
@@ -406,15 +406,8 @@ static void kvm_extint_handler(struct ext_code ext_code,
 
 	switch (param) {
 	case VIRTIO_PARAM_CONFIG_CHANGED:
-	{
-		struct virtio_driver *drv;
-		drv = container_of(vq->vdev->dev.driver,
-				   struct virtio_driver, driver);
-		if (drv->config_changed)
-			drv->config_changed(vq->vdev);
-
+		virtio_config_changed(vq->vdev);
 		break;
-	}
 	case VIRTIO_PARAM_DEV_ADD:
 		schedule_work(&hotplug_work);
 		break;
diff --git a/drivers/s390/kvm/virtio_ccw.c b/drivers/s390/kvm/virtio_ccw.c
index d2c0b44..6cbe6ef 100644
--- a/drivers/s390/kvm/virtio_ccw.c
+++ b/drivers/s390/kvm/virtio_ccw.c
@@ -940,11 +940,7 @@ static void virtio_ccw_int_handler(struct ccw_device *cdev,
 		vring_interrupt(0, vq);
 	}
 	if (test_bit(0, &vcdev->indicators2)) {
-		drv = container_of(vcdev->vdev.dev.driver,
-				   struct virtio_driver, driver);
-
-		if (drv && drv->config_changed)
-			drv->config_changed(&vcdev->vdev);
+		virtio_config_changed(&vcdev->vdev);
 		clear_bit(0, &vcdev->indicators2);
 	}
 }
diff --git a/drivers/virtio/virtio.c b/drivers/virtio/virtio.c
index fed0ce1..3980687 100644
--- a/drivers/virtio/virtio.c
+++ b/drivers/virtio/virtio.c
@@ -239,6 +239,15 @@ void unregister_virtio_device(struct virtio_device *dev)
 }
 EXPORT_SYMBOL_GPL(unregister_virtio_device);
 
+void virtio_config_changed(struct virtio_device *dev)
+{
+	struct virtio_driver *drv = drv_to_virtio(dev->dev.driver);
+
+	if (drv && drv->config_changed)
+		drv->config_changed(dev);
+}
+EXPORT_SYMBOL_GPL(virtio_config_changed);
+
 static int virtio_init(void)
 {
 	if (bus_register(&virtio_bus) != 0)
diff --git a/drivers/virtio/virtio_mmio.c b/drivers/virtio/virtio_mmio.c
index c600ccf..ef9a165 100644
--- a/drivers/virtio/virtio_mmio.c
+++ b/drivers/virtio/virtio_mmio.c
@@ -234,8 +234,6 @@ static irqreturn_t vm_interrupt(int irq, void *opaque)
 {
 	struct virtio_mmio_device *vm_dev = opaque;
 	struct virtio_mmio_vq_info *info;
-	struct virtio_driver *vdrv = container_of(vm_dev->vdev.dev.driver,
-			struct virtio_driver, driver);
 	unsigned long status;
 	unsigned long flags;
 	irqreturn_t ret = IRQ_NONE;
@@ -244,9 +242,8 @@ static irqreturn_t vm_interrupt(int irq, void *opaque)
 	status = readl(vm_dev->base + VIRTIO_MMIO_INTERRUPT_STATUS);
 	writel(status, vm_dev->base + VIRTIO_MMIO_INTERRUPT_ACK);
 
-	if (unlikely(status & VIRTIO_MMIO_INT_CONFIG)
-			&& vdrv && vdrv->config_changed) {
-		vdrv->config_changed(&vm_dev->vdev);
+	if (unlikely(status & VIRTIO_MMIO_INT_CONFIG)) {
+		virtio_config_changed(&vm_dev->vdev);
 		ret = IRQ_HANDLED;
 	}
 
diff --git a/drivers/virtio/virtio_pci.c b/drivers/virtio/virtio_pci.c
index add40d0..f39f4e7 100644
--- a/drivers/virtio/virtio_pci.c
+++ b/drivers/virtio/virtio_pci.c
@@ -211,12 +211,8 @@ static bool vp_notify(struct virtqueue *vq)
 static irqreturn_t vp_config_changed(int irq, void *opaque)
 {
 	struct virtio_pci_device *vp_dev = opaque;
-	struct virtio_driver *drv;
-	drv = container_of(vp_dev->vdev.dev.driver,
-			   struct virtio_driver, driver);
 
-	if (drv && drv->config_changed)
-		drv->config_changed(&vp_dev->vdev);
+	virtio_config_changed(&vp_dev->vdev);
 	return IRQ_HANDLED;
 }
 
-- 
MST



^ permalink raw reply related	[flat|nested] 43+ messages in thread

* [PATCH v4 03/25] virtio-pci: move freeze/restore to virtio core
  2014-10-13  7:48 [PATCH v4 00/25] virtio: fix spec compliance issues Michael S. Tsirkin
  2014-10-13  7:48 ` [PATCH v4 01/25] virtio_pci: fix virtio spec compliance on restore Michael S. Tsirkin
  2014-10-13  7:48 ` [PATCH v4 02/25] virtio: unify config_changed handling Michael S. Tsirkin
@ 2014-10-13  7:48 ` Michael S. Tsirkin
  2014-10-15  7:05   ` Paul Bolle
  2014-10-13  7:50 ` [PATCH v4 04/25] virtio: defer config changed notifications Michael S. Tsirkin
                   ` (21 subsequent siblings)
  24 siblings, 1 reply; 43+ messages in thread
From: Michael S. Tsirkin @ 2014-10-13  7:48 UTC (permalink / raw)
  To: linux-kernel
  Cc: Rusty Russell, virtualization, linux-scsi, linux-s390,
	v9fs-developer, netdev, kvm, Amit Shah, Cornelia Huck,
	Christian Borntraeger, David S. Miller, Paolo Bonzini,
	Heinz Graalfs

This is in preparation to extending config changed event handling
in core.
Wrapping these in an API also seems to make for a cleaner code.

Signed-off-by: Michael S. Tsirkin <mst@redhat.com>
Reviewed-by: Cornelia Huck <cornelia.huck@de.ibm.com>
---
 include/linux/virtio.h      |  6 +++++
 drivers/virtio/virtio.c     | 54 +++++++++++++++++++++++++++++++++++++++++++++
 drivers/virtio/virtio_pci.c | 54 ++-------------------------------------------
 3 files changed, 62 insertions(+), 52 deletions(-)

diff --git a/include/linux/virtio.h b/include/linux/virtio.h
index 3c19bd3..8df7ba8 100644
--- a/include/linux/virtio.h
+++ b/include/linux/virtio.h
@@ -78,6 +78,7 @@ bool virtqueue_is_broken(struct virtqueue *vq);
 /**
  * virtio_device - representation of a device using virtio
  * @index: unique position on the virtio bus
+ * @failed: saved value for CONFIG_S_FAILED bit (for restore)
  * @dev: underlying device.
  * @id: the device type identification (used to match it with a driver).
  * @config: the configuration ops for this device.
@@ -88,6 +89,7 @@ bool virtqueue_is_broken(struct virtqueue *vq);
  */
 struct virtio_device {
 	int index;
+	bool failed;
 	struct device dev;
 	struct virtio_device_id id;
 	const struct virtio_config_ops *config;
@@ -109,6 +111,10 @@ void unregister_virtio_device(struct virtio_device *dev);
 void virtio_break_device(struct virtio_device *dev);
 
 void virtio_config_changed(struct virtio_device *dev);
+#ifdef CONFIG_PM_SLEEP
+int virtio_device_freeze(struct virtio_device *dev);
+int virtio_device_restore(struct virtio_device *dev);
+#endif
 
 /**
  * virtio_driver - operations for a virtio I/O driver
diff --git a/drivers/virtio/virtio.c b/drivers/virtio/virtio.c
index 3980687..8216b73 100644
--- a/drivers/virtio/virtio.c
+++ b/drivers/virtio/virtio.c
@@ -248,6 +248,60 @@ void virtio_config_changed(struct virtio_device *dev)
 }
 EXPORT_SYMBOL_GPL(virtio_config_changed);
 
+#ifdef CONFIG_PM_SLEEP
+int virtio_device_freeze(struct virtio_device *dev)
+{
+	struct virtio_driver *drv = drv_to_virtio(dev->dev.driver);
+
+	dev->failed = dev->config->get_status(dev) & VIRTIO_CONFIG_S_FAILED;
+
+	if (drv && drv->freeze)
+		return drv->freeze(dev);
+
+	return 0;
+}
+EXPORT_SYMBOL_GPL(virtio_device_freeze);
+
+int virtio_device_restore(struct virtio_device *dev)
+{
+	struct virtio_driver *drv = drv_to_virtio(dev->dev.driver);
+
+	/* We always start by resetting the device, in case a previous
+	 * driver messed it up. */
+	dev->config->reset(dev);
+
+	/* Acknowledge that we've seen the device. */
+	add_status(dev, VIRTIO_CONFIG_S_ACKNOWLEDGE);
+
+	/* Maybe driver failed before freeze.
+	 * Restore the failed status, for debugging. */
+	if (dev->failed)
+		add_status(dev, VIRTIO_CONFIG_S_FAILED);
+
+	if (!drv)
+		return 0;
+
+	/* We have a driver! */
+	add_status(dev, VIRTIO_CONFIG_S_DRIVER);
+
+	dev->config->finalize_features(dev);
+
+	if (drv->restore) {
+		int ret = drv->restore(dev);
+		if (ret) {
+			add_status(dev, VIRTIO_CONFIG_S_FAILED);
+			return ret;
+		}
+	}
+
+	/* Finally, tell the device we're all set */
+	add_status(dev, VIRTIO_CONFIG_S_DRIVER_OK);
+
+	return 0;
+}
+EXPORT_SYMBOL_GPL(virtio_device_restore);
+#endif
+
 static int virtio_init(void)
 {
 	if (bus_register(&virtio_bus) != 0)
diff --git a/drivers/virtio/virtio_pci.c b/drivers/virtio/virtio_pci.c
index f39f4e7..d34ebfa 100644
--- a/drivers/virtio/virtio_pci.c
+++ b/drivers/virtio/virtio_pci.c
@@ -57,9 +57,6 @@ struct virtio_pci_device
 	/* Vectors allocated, excluding per-vq vectors if any */
 	unsigned msix_used_vectors;
 
-	/* Status saved during hibernate/restore */
-	u8 saved_status;
-
 	/* Whether we have vector per vq */
 	bool per_vq_vectors;
 };
@@ -764,16 +761,9 @@ static int virtio_pci_freeze(struct device *dev)
 {
 	struct pci_dev *pci_dev = to_pci_dev(dev);
 	struct virtio_pci_device *vp_dev = pci_get_drvdata(pci_dev);
-	struct virtio_driver *drv;
 	int ret;
 
-	drv = container_of(vp_dev->vdev.dev.driver,
-			   struct virtio_driver, driver);
-
-	ret = 0;
-	vp_dev->saved_status = vp_get_status(&vp_dev->vdev);
-	if (drv && drv->freeze)
-		ret = drv->freeze(&vp_dev->vdev);
+	ret = virtio_device_freeze(&vp_dev->vdev);
 
 	if (!ret)
 		pci_disable_device(pci_dev);
@@ -784,54 +774,14 @@ static int virtio_pci_restore(struct device *dev)
 {
 	struct pci_dev *pci_dev = to_pci_dev(dev);
 	struct virtio_pci_device *vp_dev = pci_get_drvdata(pci_dev);
-	struct virtio_driver *drv;
-	unsigned status = 0;
 	int ret;
 
-	drv = container_of(vp_dev->vdev.dev.driver,
-			   struct virtio_driver, driver);
-
 	ret = pci_enable_device(pci_dev);
 	if (ret)
 		return ret;
 
 	pci_set_master(pci_dev);
-	/* We always start by resetting the device, in case a previous
-	 * driver messed it up. */
-	vp_reset(&vp_dev->vdev);
-
-	/* Acknowledge that we've seen the device. */
-	status |= VIRTIO_CONFIG_S_ACKNOWLEDGE;
-	vp_set_status(&vp_dev->vdev, status);
-
-	/* Maybe driver failed before freeze.
-	 * Restore the failed status, for debugging. */
-	status |= vp_dev->saved_status & VIRTIO_CONFIG_S_FAILED;
-	vp_set_status(&vp_dev->vdev, status);
-
-	if (!drv)
-		return 0;
-
-	/* We have a driver! */
-	status |= VIRTIO_CONFIG_S_DRIVER;
-	vp_set_status(&vp_dev->vdev, status);
-
-	vp_finalize_features(&vp_dev->vdev);
-
-	if (drv->restore) {
-		ret = drv->restore(&vp_dev->vdev);
-		if (ret) {
-			status |= VIRTIO_CONFIG_S_FAILED;
-			vp_set_status(&vp_dev->vdev, status);
-			return ret;
-		}
-	}
-
-	/* Finally, tell the device we're all set */
-	status |= VIRTIO_CONFIG_S_DRIVER_OK;
-	vp_set_status(&vp_dev->vdev, status);
-
-	return ret;
+	return virtio_device_restore(&vp_dev->vdev);
 }
 
 static const struct dev_pm_ops virtio_pci_pm_ops = {
-- 
MST



^ permalink raw reply related	[flat|nested] 43+ messages in thread

* [PATCH v4 04/25] virtio: defer config changed notifications
  2014-10-13  7:48 [PATCH v4 00/25] virtio: fix spec compliance issues Michael S. Tsirkin
                   ` (2 preceding siblings ...)
  2014-10-13  7:48 ` [PATCH v4 03/25] virtio-pci: move freeze/restore to virtio core Michael S. Tsirkin
@ 2014-10-13  7:50 ` Michael S. Tsirkin
  2014-10-14  0:31   ` Rusty Russell
  2014-10-13  7:50 ` [PATCH v4 05/25] virtio_blk: drop config_enable Michael S. Tsirkin
                   ` (20 subsequent siblings)
  24 siblings, 1 reply; 43+ messages in thread
From: Michael S. Tsirkin @ 2014-10-13  7:50 UTC (permalink / raw)
  To: linux-kernel
  Cc: Rusty Russell, virtualization, linux-scsi, linux-s390,
	v9fs-developer, netdev, kvm, Amit Shah, Cornelia Huck,
	Christian Borntraeger, David S. Miller, Paolo Bonzini,
	Heinz Graalfs

Defer config changed notifications that arrive during
probe/scan/freeze/restore.

This will allow drivers to set DRIVER_OK earlier, without worrying about
racing with config change interrupts.

This change will also benefit old hypervisors (before 2009)
that send interrupts without checking DRIVER_OK: previously,
the callback could race with driver-specific initialization.

This will also help simplify drivers.

Signed-off-by: Michael S. Tsirkin <mst@redhat.com>
Reviewed-by: Cornelia Huck <cornelia.huck@de.ibm.com>
---
 include/linux/virtio.h  |  6 ++++++
 drivers/virtio/virtio.c | 57 +++++++++++++++++++++++++++++++++++++++++--------
 2 files changed, 54 insertions(+), 9 deletions(-)

diff --git a/include/linux/virtio.h b/include/linux/virtio.h
index 8df7ba8..5636b11 100644
--- a/include/linux/virtio.h
+++ b/include/linux/virtio.h
@@ -79,6 +79,9 @@ bool virtqueue_is_broken(struct virtqueue *vq);
  * virtio_device - representation of a device using virtio
  * @index: unique position on the virtio bus
  * @failed: saved value for CONFIG_S_FAILED bit (for restore)
+ * @config_enabled: configuration change reporting enabled
+ * @config_changed: configuration change reported while disabled
+ * @config_lock: protects configuration change reporting
  * @dev: underlying device.
  * @id: the device type identification (used to match it with a driver).
  * @config: the configuration ops for this device.
@@ -90,6 +93,9 @@ bool virtqueue_is_broken(struct virtqueue *vq);
 struct virtio_device {
 	int index;
 	bool failed;
+	bool config_enabled;
+	bool config_changed;
+	spinlock_t config_lock;
 	struct device dev;
 	struct virtio_device_id id;
 	const struct virtio_config_ops *config;
diff --git a/drivers/virtio/virtio.c b/drivers/virtio/virtio.c
index 8216b73..2536701 100644
--- a/drivers/virtio/virtio.c
+++ b/drivers/virtio/virtio.c
@@ -117,6 +117,42 @@ void virtio_check_driver_offered_feature(const struct virtio_device *vdev,
 }
 EXPORT_SYMBOL_GPL(virtio_check_driver_offered_feature);
 
+static void __virtio_config_changed(struct virtio_device *dev)
+{
+	struct virtio_driver *drv = drv_to_virtio(dev->dev.driver);
+
+	if (!dev->config_enabled)
+		dev->config_changed = true;
+	else if (drv && drv->config_changed)
+		drv->config_changed(dev);
+}
+
+void virtio_config_changed(struct virtio_device *dev)
+{
+	unsigned long flags;
+
+	spin_lock_irqsave(&dev->config_lock, flags);
+	__virtio_config_changed(dev);
+	spin_unlock_irqrestore(&dev->config_lock, flags);
+}
+EXPORT_SYMBOL_GPL(virtio_config_changed);
+
+static void virtio_config_disable(struct virtio_device *dev)
+{
+	spin_lock_irq(&dev->config_lock);
+	dev->config_enabled = false;
+	spin_unlock_irq(&dev->config_lock);
+}
+
+static void virtio_config_enable(struct virtio_device *dev)
+{
+	spin_lock_irq(&dev->config_lock);
+	dev->config_enabled = true;
+	__virtio_config_changed(dev);
+	dev->config_changed = false;
+	spin_unlock_irq(&dev->config_lock);
+}
+
 static int virtio_dev_probe(struct device *_d)
 {
 	int err, i;
@@ -153,6 +189,8 @@ static int virtio_dev_probe(struct device *_d)
 		add_status(dev, VIRTIO_CONFIG_S_DRIVER_OK);
 		if (drv->scan)
 			drv->scan(dev);
+
+		virtio_config_enable(dev);
 	}
 
 	return err;
@@ -163,6 +201,8 @@ static int virtio_dev_remove(struct device *_d)
 	struct virtio_device *dev = dev_to_virtio(_d);
 	struct virtio_driver *drv = drv_to_virtio(dev->dev.driver);
 
+	virtio_config_disable(dev);
+
 	drv->remove(dev);
 
 	/* Driver should have reset device. */
@@ -211,6 +251,10 @@ int register_virtio_device(struct virtio_device *dev)
 	dev->index = err;
 	dev_set_name(&dev->dev, "virtio%u", dev->index);
 
+	spin_lock_init(&dev->config_lock);
+	dev->config_enabled = false;
+	dev->config_changed = false;
+
 	/* We always start by resetting the device, in case a previous
 	 * driver messed it up.  This also tests that code path a little. */
 	dev->config->reset(dev);
@@ -239,20 +283,13 @@ void unregister_virtio_device(struct virtio_device *dev)
 }
 EXPORT_SYMBOL_GPL(unregister_virtio_device);
 
-void virtio_config_changed(struct virtio_device *dev)
-{
-	struct virtio_driver *drv = drv_to_virtio(dev->dev.driver);
-
-	if (drv && drv->config_changed)
-		drv->config_changed(dev);
-}
-EXPORT_SYMBOL_GPL(virtio_config_changed);
-
 #ifdef CONFIG_PM_SLEEP
 int virtio_device_freeze(struct virtio_device *dev)
 {
 	struct virtio_driver *drv = drv_to_virtio(dev->dev.driver);
 
+	virtio_config_disable(dev);
+
 	dev->failed = dev->config->get_status(dev) & VIRTIO_CONFIG_S_FAILED;
 
 	if (drv && drv->freeze)
@@ -297,6 +334,8 @@ int virtio_device_restore(struct virtio_device *dev)
 	/* Finally, tell the device we're all set */
 	add_status(dev, VIRTIO_CONFIG_S_DRIVER_OK);
 
+	virtio_config_enable(dev);
+
 	return 0;
 }
 EXPORT_SYMBOL_GPL(virtio_device_restore);
-- 
MST



^ permalink raw reply related	[flat|nested] 43+ messages in thread

* [PATCH v4 05/25] virtio_blk: drop config_enable
  2014-10-13  7:48 [PATCH v4 00/25] virtio: fix spec compliance issues Michael S. Tsirkin
                   ` (3 preceding siblings ...)
  2014-10-13  7:50 ` [PATCH v4 04/25] virtio: defer config changed notifications Michael S. Tsirkin
@ 2014-10-13  7:50 ` Michael S. Tsirkin
  2014-10-13  7:50 ` [PATCH v4 06/25] virtio-blk: drop config_mutex Michael S. Tsirkin
                   ` (19 subsequent siblings)
  24 siblings, 0 replies; 43+ messages in thread
From: Michael S. Tsirkin @ 2014-10-13  7:50 UTC (permalink / raw)
  To: linux-kernel
  Cc: Rusty Russell, virtualization, linux-scsi, linux-s390,
	v9fs-developer, netdev, kvm, Amit Shah, Cornelia Huck,
	Christian Borntraeger, David S. Miller, Paolo Bonzini

Now that virtio core ensures config changes don't
arrive during probing, drop config_enable flag
in virtio blk.
On removal, flush is now sufficient to guarantee that
no change work is queued.

This help simplify the driver, and will allow
setting DRIVER_OK earlier without losing config
change notifications.

Signed-off-by: Michael S. Tsirkin <mst@redhat.com>
Reviewed-by: Cornelia Huck <cornelia.huck@de.ibm.com>
---
 drivers/block/virtio_blk.c | 23 ++++-------------------
 1 file changed, 4 insertions(+), 19 deletions(-)

diff --git a/drivers/block/virtio_blk.c b/drivers/block/virtio_blk.c
index 0a58140..91272f1a 100644
--- a/drivers/block/virtio_blk.c
+++ b/drivers/block/virtio_blk.c
@@ -44,9 +44,6 @@ struct virtio_blk
 	/* Lock for config space updates */
 	struct mutex config_lock;
 
-	/* enable config space updates */
-	bool config_enable;
-
 	/* What host tells us, plus 2 for header & tailer. */
 	unsigned int sg_elems;
 
@@ -348,8 +345,6 @@ static void virtblk_config_changed_work(struct work_struct *work)
 	u64 capacity, size;
 
 	mutex_lock(&vblk->config_lock);
-	if (!vblk->config_enable)
-		goto done;
 
 	/* Host must always specify the capacity. */
 	virtio_cread(vdev, struct virtio_blk_config, capacity, &capacity);
@@ -374,7 +369,7 @@ static void virtblk_config_changed_work(struct work_struct *work)
 	set_capacity(vblk->disk, capacity);
 	revalidate_disk(vblk->disk);
 	kobject_uevent_env(&disk_to_dev(vblk->disk)->kobj, KOBJ_CHANGE, envp);
-done:
+
 	mutex_unlock(&vblk->config_lock);
 }
 
@@ -609,7 +604,6 @@ static int virtblk_probe(struct virtio_device *vdev)
 	mutex_init(&vblk->config_lock);
 
 	INIT_WORK(&vblk->config_work, virtblk_config_changed_work);
-	vblk->config_enable = true;
 
 	err = init_vq(vblk);
 	if (err)
@@ -771,10 +765,8 @@ static void virtblk_remove(struct virtio_device *vdev)
 	int index = vblk->index;
 	int refc;
 
-	/* Prevent config work handler from accessing the device. */
-	mutex_lock(&vblk->config_lock);
-	vblk->config_enable = false;
-	mutex_unlock(&vblk->config_lock);
+	/* Make sure no work handler is accessing the device. */
+	flush_work(&vblk->config_work);
 
 	del_gendisk(vblk->disk);
 	blk_cleanup_queue(vblk->disk->queue);
@@ -784,8 +776,6 @@ static void virtblk_remove(struct virtio_device *vdev)
 	/* Stop all the virtqueues. */
 	vdev->config->reset(vdev);
 
-	flush_work(&vblk->config_work);
-
 	refc = atomic_read(&disk_to_dev(vblk->disk)->kobj.kref.refcount);
 	put_disk(vblk->disk);
 	vdev->config->del_vqs(vdev);
@@ -805,11 +795,7 @@ static int virtblk_freeze(struct virtio_device *vdev)
 	/* Ensure we don't receive any more interrupts */
 	vdev->config->reset(vdev);
 
-	/* Prevent config work handler from accessing the device. */
-	mutex_lock(&vblk->config_lock);
-	vblk->config_enable = false;
-	mutex_unlock(&vblk->config_lock);
-
+	/* Make sure no work handler is accessing the device. */
 	flush_work(&vblk->config_work);
 
 	blk_mq_stop_hw_queues(vblk->disk->queue);
@@ -823,7 +809,6 @@ static int virtblk_restore(struct virtio_device *vdev)
 	struct virtio_blk *vblk = vdev->priv;
 	int ret;
 
-	vblk->config_enable = true;
 	ret = init_vq(vdev->priv);
 	if (!ret)
 		blk_mq_start_stopped_hw_queues(vblk->disk->queue, true);
-- 
MST



^ permalink raw reply related	[flat|nested] 43+ messages in thread

* [PATCH v4 06/25] virtio-blk: drop config_mutex
  2014-10-13  7:48 [PATCH v4 00/25] virtio: fix spec compliance issues Michael S. Tsirkin
                   ` (4 preceding siblings ...)
  2014-10-13  7:50 ` [PATCH v4 05/25] virtio_blk: drop config_enable Michael S. Tsirkin
@ 2014-10-13  7:50 ` Michael S. Tsirkin
  2014-10-13  7:50 ` [PATCH v4 07/25] virtio_net: drop config_enable Michael S. Tsirkin
                   ` (18 subsequent siblings)
  24 siblings, 0 replies; 43+ messages in thread
From: Michael S. Tsirkin @ 2014-10-13  7:50 UTC (permalink / raw)
  To: linux-kernel
  Cc: Rusty Russell, virtualization, linux-scsi, linux-s390,
	v9fs-developer, netdev, kvm, Amit Shah, Cornelia Huck,
	Christian Borntraeger, David S. Miller, Paolo Bonzini

config_mutex served two purposes: prevent multiple concurrent config
change handlers, and synchronize access to config_enable flag.

Since commit dbf2576e37da0fcc7aacbfbb9fd5d3de7888a3c1
    workqueue: make all workqueues non-reentrant
all workqueues are non-reentrant, and config_enable
is now gone.

Get rid of the unnecessary lock.

Signed-off-by: Michael S. Tsirkin <mst@redhat.com>
Reviewed-by: Cornelia Huck <cornelia.huck@de.ibm.com>
---
 drivers/block/virtio_blk.c | 8 --------
 1 file changed, 8 deletions(-)

diff --git a/drivers/block/virtio_blk.c b/drivers/block/virtio_blk.c
index 91272f1a..89ba8d6 100644
--- a/drivers/block/virtio_blk.c
+++ b/drivers/block/virtio_blk.c
@@ -41,9 +41,6 @@ struct virtio_blk
 	/* Process context for config space updates */
 	struct work_struct config_work;
 
-	/* Lock for config space updates */
-	struct mutex config_lock;
-
 	/* What host tells us, plus 2 for header & tailer. */
 	unsigned int sg_elems;
 
@@ -344,8 +341,6 @@ static void virtblk_config_changed_work(struct work_struct *work)
 	char *envp[] = { "RESIZE=1", NULL };
 	u64 capacity, size;
 
-	mutex_lock(&vblk->config_lock);
-
 	/* Host must always specify the capacity. */
 	virtio_cread(vdev, struct virtio_blk_config, capacity, &capacity);
 
@@ -369,8 +364,6 @@ static void virtblk_config_changed_work(struct work_struct *work)
 	set_capacity(vblk->disk, capacity);
 	revalidate_disk(vblk->disk);
 	kobject_uevent_env(&disk_to_dev(vblk->disk)->kobj, KOBJ_CHANGE, envp);
-
-	mutex_unlock(&vblk->config_lock);
 }
 
 static void virtblk_config_changed(struct virtio_device *vdev)
@@ -601,7 +594,6 @@ static int virtblk_probe(struct virtio_device *vdev)
 
 	vblk->vdev = vdev;
 	vblk->sg_elems = sg_elems;
-	mutex_init(&vblk->config_lock);
 
 	INIT_WORK(&vblk->config_work, virtblk_config_changed_work);
 
-- 
MST



^ permalink raw reply related	[flat|nested] 43+ messages in thread

* [PATCH v4 07/25] virtio_net: drop config_enable
  2014-10-13  7:48 [PATCH v4 00/25] virtio: fix spec compliance issues Michael S. Tsirkin
                   ` (5 preceding siblings ...)
  2014-10-13  7:50 ` [PATCH v4 06/25] virtio-blk: drop config_mutex Michael S. Tsirkin
@ 2014-10-13  7:50 ` Michael S. Tsirkin
  2014-10-13  7:50 ` [PATCH v4 08/25] virtio-net: drop config_mutex Michael S. Tsirkin
                   ` (17 subsequent siblings)
  24 siblings, 0 replies; 43+ messages in thread
From: Michael S. Tsirkin @ 2014-10-13  7:50 UTC (permalink / raw)
  To: linux-kernel
  Cc: Rusty Russell, virtualization, linux-scsi, linux-s390,
	v9fs-developer, netdev, kvm, Amit Shah, Cornelia Huck,
	Christian Borntraeger, David S. Miller, Paolo Bonzini

Now that virtio core ensures config changes don't arrive during probing,
drop config_enable flag in virtio net.
On removal, flush is now sufficient to guarantee that no change work is
queued.

This help simplify the driver, and will allow setting DRIVER_OK earlier
without losing config change notifications.

Signed-off-by: Michael S. Tsirkin <mst@redhat.com>
Reviewed-by: Cornelia Huck <cornelia.huck@de.ibm.com>
---
 drivers/net/virtio_net.c | 27 ++++-----------------------
 1 file changed, 4 insertions(+), 23 deletions(-)

diff --git a/drivers/net/virtio_net.c b/drivers/net/virtio_net.c
index 59caa06..743fb04 100644
--- a/drivers/net/virtio_net.c
+++ b/drivers/net/virtio_net.c
@@ -123,9 +123,6 @@ struct virtnet_info {
 	/* Host can handle any s/g split between our header and packet data */
 	bool any_header_sg;
 
-	/* enable config space updates */
-	bool config_enable;
-
 	/* Active statistics */
 	struct virtnet_stats __percpu *stats;
 
@@ -1408,9 +1405,6 @@ static void virtnet_config_changed_work(struct work_struct *work)
 	u16 v;
 
 	mutex_lock(&vi->config_lock);
-	if (!vi->config_enable)
-		goto done;
-
 	if (virtio_cread_feature(vi->vdev, VIRTIO_NET_F_STATUS,
 				 struct virtio_net_config, status, &v) < 0)
 		goto done;
@@ -1758,7 +1752,6 @@ static int virtnet_probe(struct virtio_device *vdev)
 	}
 
 	mutex_init(&vi->config_lock);
-	vi->config_enable = true;
 	INIT_WORK(&vi->config_work, virtnet_config_changed_work);
 
 	/* If we can receive ANY GSO packets, we must allocate large ones. */
@@ -1875,17 +1868,13 @@ static void virtnet_remove(struct virtio_device *vdev)
 
 	unregister_hotcpu_notifier(&vi->nb);
 
-	/* Prevent config work handler from accessing the device. */
-	mutex_lock(&vi->config_lock);
-	vi->config_enable = false;
-	mutex_unlock(&vi->config_lock);
+	/* Make sure no work handler is accessing the device. */
+	flush_work(&vi->config_work);
 
 	unregister_netdev(vi->dev);
 
 	remove_vq_common(vi);
 
-	flush_work(&vi->config_work);
-
 	free_percpu(vi->stats);
 	free_netdev(vi->dev);
 }
@@ -1898,10 +1887,8 @@ static int virtnet_freeze(struct virtio_device *vdev)
 
 	unregister_hotcpu_notifier(&vi->nb);
 
-	/* Prevent config work handler from accessing the device */
-	mutex_lock(&vi->config_lock);
-	vi->config_enable = false;
-	mutex_unlock(&vi->config_lock);
+	/* Make sure no work handler is accessing the device */
+	flush_work(&vi->config_work);
 
 	netif_device_detach(vi->dev);
 	cancel_delayed_work_sync(&vi->refill);
@@ -1916,8 +1903,6 @@ static int virtnet_freeze(struct virtio_device *vdev)
 
 	remove_vq_common(vi);
 
-	flush_work(&vi->config_work);
-
 	return 0;
 }
 
@@ -1941,10 +1926,6 @@ static int virtnet_restore(struct virtio_device *vdev)
 
 	netif_device_attach(vi->dev);
 
-	mutex_lock(&vi->config_lock);
-	vi->config_enable = true;
-	mutex_unlock(&vi->config_lock);
-
 	rtnl_lock();
 	virtnet_set_queues(vi, vi->curr_queue_pairs);
 	rtnl_unlock();
-- 
MST



^ permalink raw reply related	[flat|nested] 43+ messages in thread

* [PATCH v4 08/25] virtio-net: drop config_mutex
  2014-10-13  7:48 [PATCH v4 00/25] virtio: fix spec compliance issues Michael S. Tsirkin
                   ` (6 preceding siblings ...)
  2014-10-13  7:50 ` [PATCH v4 07/25] virtio_net: drop config_enable Michael S. Tsirkin
@ 2014-10-13  7:50 ` Michael S. Tsirkin
  2014-10-13  7:50 ` [PATCH v4 09/25] virtio_net: minor cleanup Michael S. Tsirkin
                   ` (16 subsequent siblings)
  24 siblings, 0 replies; 43+ messages in thread
From: Michael S. Tsirkin @ 2014-10-13  7:50 UTC (permalink / raw)
  To: linux-kernel
  Cc: Rusty Russell, virtualization, linux-scsi, linux-s390,
	v9fs-developer, netdev, kvm, Amit Shah, Cornelia Huck,
	Christian Borntraeger, David S. Miller, Paolo Bonzini

config_mutex served two purposes: prevent multiple concurrent config
change handlers, and synchronize access to config_enable flag.

Since commit dbf2576e37da0fcc7aacbfbb9fd5d3de7888a3c1
    workqueue: make all workqueues non-reentrant
all workqueues are non-reentrant, and config_enable
is now gone.

Get rid of the unnecessary lock.

Signed-off-by: Michael S. Tsirkin <mst@redhat.com>
Reviewed-by: Cornelia Huck <cornelia.huck@de.ibm.com>
---
 drivers/net/virtio_net.c | 7 +------
 1 file changed, 1 insertion(+), 6 deletions(-)

diff --git a/drivers/net/virtio_net.c b/drivers/net/virtio_net.c
index 743fb04..23e4a69 100644
--- a/drivers/net/virtio_net.c
+++ b/drivers/net/virtio_net.c
@@ -132,9 +132,6 @@ struct virtnet_info {
 	/* Work struct for config space updates */
 	struct work_struct config_work;
 
-	/* Lock for config space updates */
-	struct mutex config_lock;
-
 	/* Does the affinity hint is set for virtqueues? */
 	bool affinity_hint_set;
 
@@ -1404,7 +1401,6 @@ static void virtnet_config_changed_work(struct work_struct *work)
 		container_of(work, struct virtnet_info, config_work);
 	u16 v;
 
-	mutex_lock(&vi->config_lock);
 	if (virtio_cread_feature(vi->vdev, VIRTIO_NET_F_STATUS,
 				 struct virtio_net_config, status, &v) < 0)
 		goto done;
@@ -1430,7 +1426,7 @@ static void virtnet_config_changed_work(struct work_struct *work)
 		netif_tx_stop_all_queues(vi->dev);
 	}
 done:
-	mutex_unlock(&vi->config_lock);
+	return;
 }
 
 static void virtnet_config_changed(struct virtio_device *vdev)
@@ -1751,7 +1747,6 @@ static int virtnet_probe(struct virtio_device *vdev)
 		u64_stats_init(&virtnet_stats->rx_syncp);
 	}
 
-	mutex_init(&vi->config_lock);
 	INIT_WORK(&vi->config_work, virtnet_config_changed_work);
 
 	/* If we can receive ANY GSO packets, we must allocate large ones. */
-- 
MST



^ permalink raw reply related	[flat|nested] 43+ messages in thread

* [PATCH v4 09/25] virtio_net: minor cleanup
  2014-10-13  7:48 [PATCH v4 00/25] virtio: fix spec compliance issues Michael S. Tsirkin
                   ` (7 preceding siblings ...)
  2014-10-13  7:50 ` [PATCH v4 08/25] virtio-net: drop config_mutex Michael S. Tsirkin
@ 2014-10-13  7:50 ` Michael S. Tsirkin
  2014-10-13  7:50 ` [PATCH v4 10/25] virtio: add API to enable VQs early Michael S. Tsirkin
                   ` (15 subsequent siblings)
  24 siblings, 0 replies; 43+ messages in thread
From: Michael S. Tsirkin @ 2014-10-13  7:50 UTC (permalink / raw)
  To: linux-kernel
  Cc: Rusty Russell, virtualization, linux-scsi, linux-s390,
	v9fs-developer, netdev, kvm, Amit Shah, Cornelia Huck,
	Christian Borntraeger, David S. Miller, Paolo Bonzini

	goto done;
done:
	return;
is ugly, it was put there to make diff review easier.
replace by open-coded return.

Signed-off-by: Michael S. Tsirkin <mst@redhat.com>
Acked-by: Cornelia Huck <cornelia.huck@de.ibm.com>
---
 drivers/net/virtio_net.c | 6 ++----
 1 file changed, 2 insertions(+), 4 deletions(-)

diff --git a/drivers/net/virtio_net.c b/drivers/net/virtio_net.c
index 23e4a69..ef04d23 100644
--- a/drivers/net/virtio_net.c
+++ b/drivers/net/virtio_net.c
@@ -1403,7 +1403,7 @@ static void virtnet_config_changed_work(struct work_struct *work)
 
 	if (virtio_cread_feature(vi->vdev, VIRTIO_NET_F_STATUS,
 				 struct virtio_net_config, status, &v) < 0)
-		goto done;
+		return;
 
 	if (v & VIRTIO_NET_S_ANNOUNCE) {
 		netdev_notify_peers(vi->dev);
@@ -1414,7 +1414,7 @@ static void virtnet_config_changed_work(struct work_struct *work)
 	v &= VIRTIO_NET_S_LINK_UP;
 
 	if (vi->status == v)
-		goto done;
+		return;
 
 	vi->status = v;
 
@@ -1425,8 +1425,6 @@ static void virtnet_config_changed_work(struct work_struct *work)
 		netif_carrier_off(vi->dev);
 		netif_tx_stop_all_queues(vi->dev);
 	}
-done:
-	return;
 }
 
 static void virtnet_config_changed(struct virtio_device *vdev)
-- 
MST



^ permalink raw reply related	[flat|nested] 43+ messages in thread

* [PATCH v4 10/25] virtio: add API to enable VQs early
  2014-10-13  7:48 [PATCH v4 00/25] virtio: fix spec compliance issues Michael S. Tsirkin
                   ` (8 preceding siblings ...)
  2014-10-13  7:50 ` [PATCH v4 09/25] virtio_net: minor cleanup Michael S. Tsirkin
@ 2014-10-13  7:50 ` Michael S. Tsirkin
  2014-11-11  0:45   ` Andy Grover
  2014-10-13  7:50 ` [PATCH v4 11/25] virtio_net: " Michael S. Tsirkin
                   ` (14 subsequent siblings)
  24 siblings, 1 reply; 43+ messages in thread
From: Michael S. Tsirkin @ 2014-10-13  7:50 UTC (permalink / raw)
  To: linux-kernel
  Cc: Rusty Russell, virtualization, linux-scsi, linux-s390,
	v9fs-developer, netdev, kvm, Amit Shah, Cornelia Huck,
	Christian Borntraeger, David S. Miller, Paolo Bonzini

virtio spec 0.9.X requires DRIVER_OK to be set before
VQs are used, but some drivers use VQs before probe
function returns.
Since DRIVER_OK is set after probe, this violates the spec.

Even though under virtio 1.0 transitional devices support this
behaviour, we want to make it possible for those early callers to become
spec compliant and eventually support non-transitional devices.

Add API for drivers to call before using VQs.

Sets DRIVER_OK internally.

Signed-off-by: Michael S. Tsirkin <mst@redhat.com>
Reviewed-by: Cornelia Huck <cornelia.huck@de.ibm.com>
---
 include/linux/virtio_config.h | 17 +++++++++++++++++
 1 file changed, 17 insertions(+)

diff --git a/include/linux/virtio_config.h b/include/linux/virtio_config.h
index e8f8f71..e36403b 100644
--- a/include/linux/virtio_config.h
+++ b/include/linux/virtio_config.h
@@ -109,6 +109,23 @@ struct virtqueue *virtio_find_single_vq(struct virtio_device *vdev,
 	return vq;
 }
 
+/**
+ * virtio_device_ready - enable vq use in probe function
+ * @vdev: the device
+ *
+ * Driver must call this to use vqs in the probe function.
+ *
+ * Note: vqs are enabled automatically after probe returns.
+ */
+static inline
+void virtio_device_ready(struct virtio_device *dev)
+{
+	unsigned status = dev->config->get_status(dev);
+
+	BUG_ON(status & VIRTIO_CONFIG_S_DRIVER_OK);
+	dev->config->set_status(dev, status | VIRTIO_CONFIG_S_DRIVER_OK);
+}
+
 static inline
 const char *virtio_bus_name(struct virtio_device *vdev)
 {
-- 
MST



^ permalink raw reply related	[flat|nested] 43+ messages in thread

* [PATCH v4 11/25] virtio_net: enable VQs early
  2014-10-13  7:48 [PATCH v4 00/25] virtio: fix spec compliance issues Michael S. Tsirkin
                   ` (9 preceding siblings ...)
  2014-10-13  7:50 ` [PATCH v4 10/25] virtio: add API to enable VQs early Michael S. Tsirkin
@ 2014-10-13  7:50 ` Michael S. Tsirkin
  2014-10-13  7:50 ` [PATCH v4 12/25] virtio_blk: " Michael S. Tsirkin
                   ` (13 subsequent siblings)
  24 siblings, 0 replies; 43+ messages in thread
From: Michael S. Tsirkin @ 2014-10-13  7:50 UTC (permalink / raw)
  To: linux-kernel
  Cc: Rusty Russell, virtualization, linux-scsi, linux-s390,
	v9fs-developer, netdev, kvm, Amit Shah, Cornelia Huck,
	Christian Borntraeger, David S. Miller, Paolo Bonzini

virtio spec requires drivers to set DRIVER_OK before using VQs.
This is set automatically after probe returns, virtio net violated this
rule by using receive VQs within probe.

To fix, call virtio_device_ready before using VQs.

Signed-off-by: Michael S. Tsirkin <mst@redhat.com>
Reviewed-by: Cornelia Huck <cornelia.huck@de.ibm.com>
---
 drivers/net/virtio_net.c | 2 ++
 1 file changed, 2 insertions(+)

diff --git a/drivers/net/virtio_net.c b/drivers/net/virtio_net.c
index ef04d23..430f3ae 100644
--- a/drivers/net/virtio_net.c
+++ b/drivers/net/virtio_net.c
@@ -1792,6 +1792,8 @@ static int virtnet_probe(struct virtio_device *vdev)
 		goto free_vqs;
 	}
 
+	virtio_device_ready(vdev);
+
 	/* Last of all, set up some receive buffers. */
 	for (i = 0; i < vi->curr_queue_pairs; i++) {
 		try_fill_recv(&vi->rq[i], GFP_KERNEL);
-- 
MST



^ permalink raw reply related	[flat|nested] 43+ messages in thread

* [PATCH v4 12/25] virtio_blk: enable VQs early
  2014-10-13  7:48 [PATCH v4 00/25] virtio: fix spec compliance issues Michael S. Tsirkin
                   ` (10 preceding siblings ...)
  2014-10-13  7:50 ` [PATCH v4 11/25] virtio_net: " Michael S. Tsirkin
@ 2014-10-13  7:50 ` Michael S. Tsirkin
  2014-10-13  7:50 ` [PATCH v4 13/25] virtio_console: " Michael S. Tsirkin
                   ` (12 subsequent siblings)
  24 siblings, 0 replies; 43+ messages in thread
From: Michael S. Tsirkin @ 2014-10-13  7:50 UTC (permalink / raw)
  To: linux-kernel
  Cc: Rusty Russell, virtualization, linux-scsi, linux-s390,
	v9fs-developer, netdev, kvm, Amit Shah, Cornelia Huck,
	Christian Borntraeger, David S. Miller, Paolo Bonzini

virtio spec requires drivers to set DRIVER_OK before using VQs.
This is set automatically after probe returns, virtio block violated this
rule by calling add_disk, which causes the VQ to be used directly within
probe.

To fix, call virtio_device_ready before using VQs.

Signed-off-by: Michael S. Tsirkin <mst@redhat.com>
Reviewed-by: Cornelia Huck <cornelia.huck@de.ibm.com>
---
 drivers/block/virtio_blk.c | 2 ++
 1 file changed, 2 insertions(+)

diff --git a/drivers/block/virtio_blk.c b/drivers/block/virtio_blk.c
index 89ba8d6..46b04bf 100644
--- a/drivers/block/virtio_blk.c
+++ b/drivers/block/virtio_blk.c
@@ -719,6 +719,8 @@ static int virtblk_probe(struct virtio_device *vdev)
 	if (!err && opt_io_size)
 		blk_queue_io_opt(q, blk_size * opt_io_size);
 
+	virtio_device_ready(vdev);
+
 	add_disk(vblk->disk);
 	err = device_create_file(disk_to_dev(vblk->disk), &dev_attr_serial);
 	if (err)
-- 
MST



^ permalink raw reply related	[flat|nested] 43+ messages in thread

* [PATCH v4 13/25] virtio_console: enable VQs early
  2014-10-13  7:48 [PATCH v4 00/25] virtio: fix spec compliance issues Michael S. Tsirkin
                   ` (11 preceding siblings ...)
  2014-10-13  7:50 ` [PATCH v4 12/25] virtio_blk: " Michael S. Tsirkin
@ 2014-10-13  7:50 ` Michael S. Tsirkin
  2014-10-20 12:07   ` Thomas Graf
  2014-10-13  7:50 ` [PATCH v4 14/25] 9p/trans_virtio: " Michael S. Tsirkin
                   ` (11 subsequent siblings)
  24 siblings, 1 reply; 43+ messages in thread
From: Michael S. Tsirkin @ 2014-10-13  7:50 UTC (permalink / raw)
  To: linux-kernel
  Cc: Rusty Russell, virtualization, linux-scsi, linux-s390,
	v9fs-developer, netdev, kvm, Amit Shah, Cornelia Huck,
	Christian Borntraeger, David S. Miller, Paolo Bonzini,
	Arnd Bergmann, Greg Kroah-Hartman

virtio spec requires drivers to set DRIVER_OK before using VQs.
This is set automatically after probe returns, virtio console violated this
rule by adding inbufs, which causes the VQ to be used directly within
probe.

To fix, call virtio_device_ready before using VQs.

Signed-off-by: Michael S. Tsirkin <mst@redhat.com>
---
 drivers/char/virtio_console.c | 2 ++
 1 file changed, 2 insertions(+)

diff --git a/drivers/char/virtio_console.c b/drivers/char/virtio_console.c
index b585b47..6ebe8f6 100644
--- a/drivers/char/virtio_console.c
+++ b/drivers/char/virtio_console.c
@@ -1449,6 +1449,8 @@ static int add_port(struct ports_device *portdev, u32 id)
 	spin_lock_init(&port->outvq_lock);
 	init_waitqueue_head(&port->waitqueue);
 
+	virtio_device_ready(portdev->vdev);
+
 	/* Fill the in_vq with buffers so the host can send us data. */
 	nr_added_bufs = fill_queue(port->in_vq, &port->inbuf_lock);
 	if (!nr_added_bufs) {
-- 
MST



^ permalink raw reply related	[flat|nested] 43+ messages in thread

* [PATCH v4 14/25] 9p/trans_virtio: enable VQs early
  2014-10-13  7:48 [PATCH v4 00/25] virtio: fix spec compliance issues Michael S. Tsirkin
                   ` (12 preceding siblings ...)
  2014-10-13  7:50 ` [PATCH v4 13/25] virtio_console: " Michael S. Tsirkin
@ 2014-10-13  7:50 ` Michael S. Tsirkin
  2014-10-13  7:50 ` [PATCH v4 15/25] virtio_net: fix use after free on allocation failure Michael S. Tsirkin
                   ` (10 subsequent siblings)
  24 siblings, 0 replies; 43+ messages in thread
From: Michael S. Tsirkin @ 2014-10-13  7:50 UTC (permalink / raw)
  To: linux-kernel
  Cc: Rusty Russell, virtualization, linux-scsi, linux-s390,
	v9fs-developer, netdev, kvm, Amit Shah, Cornelia Huck,
	Christian Borntraeger, David S. Miller, Paolo Bonzini,
	Eric Van Hensbergen, Ron Minnich, Latchesar Ionkov

virtio spec requires drivers to set DRIVER_OK before using VQs.
This is set automatically after probe returns, but virtio 9p device
adds self to channel list within probe, at which point VQ can be
used in violation of the spec.

To fix, call virtio_device_ready before using VQs.

Signed-off-by: Michael S. Tsirkin <mst@redhat.com>
---
 net/9p/trans_virtio.c | 2 ++
 1 file changed, 2 insertions(+)

diff --git a/net/9p/trans_virtio.c b/net/9p/trans_virtio.c
index 6940d8f..766ba48 100644
--- a/net/9p/trans_virtio.c
+++ b/net/9p/trans_virtio.c
@@ -575,6 +575,8 @@ static int p9_virtio_probe(struct virtio_device *vdev)
 	/* Ceiling limit to avoid denial of service attacks */
 	chan->p9_max_pages = nr_free_buffer_pages()/4;
 
+	virtio_device_ready(vdev);
+
 	mutex_lock(&virtio_9p_lock);
 	list_add_tail(&chan->chan_list, &virtio_chan_list);
 	mutex_unlock(&virtio_9p_lock);
-- 
MST



^ permalink raw reply related	[flat|nested] 43+ messages in thread

* [PATCH v4 15/25] virtio_net: fix use after free on allocation failure
  2014-10-13  7:48 [PATCH v4 00/25] virtio: fix spec compliance issues Michael S. Tsirkin
                   ` (13 preceding siblings ...)
  2014-10-13  7:50 ` [PATCH v4 14/25] 9p/trans_virtio: " Michael S. Tsirkin
@ 2014-10-13  7:50 ` Michael S. Tsirkin
  2014-10-13  7:51 ` [PATCH v4 16/25] virtio_scsi: move kick event out from virtscsi_init Michael S. Tsirkin
                   ` (9 subsequent siblings)
  24 siblings, 0 replies; 43+ messages in thread
From: Michael S. Tsirkin @ 2014-10-13  7:50 UTC (permalink / raw)
  To: linux-kernel
  Cc: Rusty Russell, virtualization, linux-scsi, linux-s390,
	v9fs-developer, netdev, kvm, Amit Shah, Cornelia Huck,
	Christian Borntraeger, David S. Miller, Paolo Bonzini

In the extremely unlikely event that driver initialization fails after
RX buffers are added, virtio net frees RX buffers while VQs are
still active, potentially causing device to use a freed buffer.

To fix, reset device first - same as we do on device removal.

Signed-off-by: Michael S. Tsirkin <mst@redhat.com>
Reviewed-by: Cornelia Huck <cornelia.huck@de.ibm.com>
---
 drivers/net/virtio_net.c | 2 ++
 1 file changed, 2 insertions(+)

diff --git a/drivers/net/virtio_net.c b/drivers/net/virtio_net.c
index 430f3ae..3551417 100644
--- a/drivers/net/virtio_net.c
+++ b/drivers/net/virtio_net.c
@@ -1830,6 +1830,8 @@ static int virtnet_probe(struct virtio_device *vdev)
 	return 0;
 
 free_recv_bufs:
+	vi->vdev->config->reset(vdev);
+
 	free_receive_bufs(vi);
 	unregister_netdev(dev);
 free_vqs:
-- 
MST



^ permalink raw reply related	[flat|nested] 43+ messages in thread

* [PATCH v4 16/25] virtio_scsi: move kick event out from virtscsi_init
  2014-10-13  7:48 [PATCH v4 00/25] virtio: fix spec compliance issues Michael S. Tsirkin
                   ` (14 preceding siblings ...)
  2014-10-13  7:50 ` [PATCH v4 15/25] virtio_net: fix use after free on allocation failure Michael S. Tsirkin
@ 2014-10-13  7:51 ` Michael S. Tsirkin
  2014-10-13  7:51 ` [PATCH v4 17/25] virtio_blk: enable VQs early on restore Michael S. Tsirkin
                   ` (8 subsequent siblings)
  24 siblings, 0 replies; 43+ messages in thread
From: Michael S. Tsirkin @ 2014-10-13  7:51 UTC (permalink / raw)
  To: linux-kernel
  Cc: Rusty Russell, virtualization, linux-scsi, linux-s390,
	v9fs-developer, netdev, kvm, Amit Shah, Cornelia Huck,
	Christian Borntraeger, David S. Miller, Paolo Bonzini,
	James E.J. Bottomley

We currently kick event within virtscsi_init,
before host is fully initialized.

This can in theory confuse guest if device
consumes the buffers immediately.

To fix,  move virtscsi_kick_event_all out to scan/restore.

Signed-off-by: Michael S. Tsirkin <mst@redhat.com>
---
 drivers/scsi/virtio_scsi.c | 16 +++++++++++-----
 1 file changed, 11 insertions(+), 5 deletions(-)

diff --git a/drivers/scsi/virtio_scsi.c b/drivers/scsi/virtio_scsi.c
index eee1bc0..0642ce3 100644
--- a/drivers/scsi/virtio_scsi.c
+++ b/drivers/scsi/virtio_scsi.c
@@ -853,7 +853,11 @@ static void virtscsi_init_vq(struct virtio_scsi_vq *virtscsi_vq,
 
 static void virtscsi_scan(struct virtio_device *vdev)
 {
-	struct Scsi_Host *shost = (struct Scsi_Host *)vdev->priv;
+	struct Scsi_Host *shost = virtio_scsi_host(vdev);
+	struct virtio_scsi *vscsi = shost_priv(shost);
+
+	if (virtio_has_feature(vdev, VIRTIO_SCSI_F_HOTPLUG))
+		virtscsi_kick_event_all(vscsi);
 
 	scsi_scan_host(shost);
 }
@@ -916,9 +920,6 @@ static int virtscsi_init(struct virtio_device *vdev,
 	virtscsi_config_set(vdev, cdb_size, VIRTIO_SCSI_CDB_SIZE);
 	virtscsi_config_set(vdev, sense_size, VIRTIO_SCSI_SENSE_SIZE);
 
-	if (virtio_has_feature(vdev, VIRTIO_SCSI_F_HOTPLUG))
-		virtscsi_kick_event_all(vscsi);
-
 	err = 0;
 
 out:
@@ -1048,8 +1049,13 @@ static int virtscsi_restore(struct virtio_device *vdev)
 		return err;
 
 	err = register_hotcpu_notifier(&vscsi->nb);
-	if (err)
+	if (err) {
 		vdev->config->del_vqs(vdev);
+		return err;
+	}
+
+	if (virtio_has_feature(vdev, VIRTIO_SCSI_F_HOTPLUG))
+		virtscsi_kick_event_all(vscsi);
 
 	return err;
 }
-- 
MST



^ permalink raw reply related	[flat|nested] 43+ messages in thread

* [PATCH v4 17/25] virtio_blk: enable VQs early on restore
  2014-10-13  7:48 [PATCH v4 00/25] virtio: fix spec compliance issues Michael S. Tsirkin
                   ` (15 preceding siblings ...)
  2014-10-13  7:51 ` [PATCH v4 16/25] virtio_scsi: move kick event out from virtscsi_init Michael S. Tsirkin
@ 2014-10-13  7:51 ` Michael S. Tsirkin
  2014-10-13  7:51 ` [PATCH v4 18/25] virtio_scsi: " Michael S. Tsirkin
                   ` (7 subsequent siblings)
  24 siblings, 0 replies; 43+ messages in thread
From: Michael S. Tsirkin @ 2014-10-13  7:51 UTC (permalink / raw)
  To: linux-kernel
  Cc: Rusty Russell, virtualization, linux-scsi, linux-s390,
	v9fs-developer, netdev, kvm, Amit Shah, Cornelia Huck,
	Christian Borntraeger, David S. Miller, Paolo Bonzini

virtio spec requires drivers to set DRIVER_OK before using VQs.
This is set automatically after restore returns, virtio block violated
this rule on restore by restarting queues, which might in theory
cause the VQ to be used directly within restore.

To fix, call virtio_device_ready before using starting queues.

Signed-off-by: Michael S. Tsirkin <mst@redhat.com>
---
 drivers/block/virtio_blk.c | 9 ++++++---
 1 file changed, 6 insertions(+), 3 deletions(-)

diff --git a/drivers/block/virtio_blk.c b/drivers/block/virtio_blk.c
index 46b04bf..1c95af5 100644
--- a/drivers/block/virtio_blk.c
+++ b/drivers/block/virtio_blk.c
@@ -804,10 +804,13 @@ static int virtblk_restore(struct virtio_device *vdev)
 	int ret;
 
 	ret = init_vq(vdev->priv);
-	if (!ret)
-		blk_mq_start_stopped_hw_queues(vblk->disk->queue, true);
+	if (ret)
+		return ret;
+
+	virtio_device_ready(vdev);
 
-	return ret;
+	blk_mq_start_stopped_hw_queues(vblk->disk->queue, true);
+	return 0;
 }
 #endif
 
-- 
MST



^ permalink raw reply related	[flat|nested] 43+ messages in thread

* [PATCH v4 18/25] virtio_scsi: enable VQs early on restore
  2014-10-13  7:48 [PATCH v4 00/25] virtio: fix spec compliance issues Michael S. Tsirkin
                   ` (16 preceding siblings ...)
  2014-10-13  7:51 ` [PATCH v4 17/25] virtio_blk: enable VQs early on restore Michael S. Tsirkin
@ 2014-10-13  7:51 ` Michael S. Tsirkin
  2014-10-13  7:51 ` [PATCH v4 19/25] virtio_console: " Michael S. Tsirkin
                   ` (6 subsequent siblings)
  24 siblings, 0 replies; 43+ messages in thread
From: Michael S. Tsirkin @ 2014-10-13  7:51 UTC (permalink / raw)
  To: linux-kernel
  Cc: Rusty Russell, virtualization, linux-scsi, linux-s390,
	v9fs-developer, netdev, kvm, Amit Shah, Cornelia Huck,
	Christian Borntraeger, David S. Miller, Paolo Bonzini,
	James E.J. Bottomley

virtio spec requires drivers to set DRIVER_OK before using VQs.
This is set automatically after restore returns, virtio scsi violated
this rule on restore by kicking event vq within restore.

To fix, call virtio_device_ready before using event queue.

Signed-off-by: Michael S. Tsirkin <mst@redhat.com>
---
 drivers/scsi/virtio_scsi.c | 2 ++
 1 file changed, 2 insertions(+)

diff --git a/drivers/scsi/virtio_scsi.c b/drivers/scsi/virtio_scsi.c
index 0642ce3..2b565b3 100644
--- a/drivers/scsi/virtio_scsi.c
+++ b/drivers/scsi/virtio_scsi.c
@@ -1054,6 +1054,8 @@ static int virtscsi_restore(struct virtio_device *vdev)
 		return err;
 	}
 
+	virtio_device_ready(vdev);
+
 	if (virtio_has_feature(vdev, VIRTIO_SCSI_F_HOTPLUG))
 		virtscsi_kick_event_all(vscsi);
 
-- 
MST



^ permalink raw reply related	[flat|nested] 43+ messages in thread

* [PATCH v4 19/25] virtio_console: enable VQs early on restore
  2014-10-13  7:48 [PATCH v4 00/25] virtio: fix spec compliance issues Michael S. Tsirkin
                   ` (17 preceding siblings ...)
  2014-10-13  7:51 ` [PATCH v4 18/25] virtio_scsi: " Michael S. Tsirkin
@ 2014-10-13  7:51 ` Michael S. Tsirkin
  2014-10-13  7:51 ` [PATCH v4 20/25] virtio_net: " Michael S. Tsirkin
                   ` (5 subsequent siblings)
  24 siblings, 0 replies; 43+ messages in thread
From: Michael S. Tsirkin @ 2014-10-13  7:51 UTC (permalink / raw)
  To: linux-kernel
  Cc: Rusty Russell, virtualization, linux-scsi, linux-s390,
	v9fs-developer, netdev, kvm, Amit Shah, Cornelia Huck,
	Christian Borntraeger, David S. Miller, Paolo Bonzini,
	Arnd Bergmann, Greg Kroah-Hartman

virtio spec requires drivers to set DRIVER_OK before using VQs.
This is set automatically after resume returns, virtio console violated this
rule by adding inbufs, which causes the VQ to be used directly within
restore.

To fix, call virtio_device_ready before using VQs.

Signed-off-by: Michael S. Tsirkin <mst@redhat.com>
---
 drivers/char/virtio_console.c | 2 ++
 1 file changed, 2 insertions(+)

diff --git a/drivers/char/virtio_console.c b/drivers/char/virtio_console.c
index 6ebe8f6..2ae843f 100644
--- a/drivers/char/virtio_console.c
+++ b/drivers/char/virtio_console.c
@@ -2184,6 +2184,8 @@ static int virtcons_restore(struct virtio_device *vdev)
 	if (ret)
 		return ret;
 
+	virtio_device_ready(portdev->vdev);
+
 	if (use_multiport(portdev))
 		fill_queue(portdev->c_ivq, &portdev->c_ivq_lock);
 
-- 
MST



^ permalink raw reply related	[flat|nested] 43+ messages in thread

* [PATCH v4 20/25] virtio_net: enable VQs early on restore
  2014-10-13  7:48 [PATCH v4 00/25] virtio: fix spec compliance issues Michael S. Tsirkin
                   ` (18 preceding siblings ...)
  2014-10-13  7:51 ` [PATCH v4 19/25] virtio_console: " Michael S. Tsirkin
@ 2014-10-13  7:51 ` Michael S. Tsirkin
  2014-10-13  7:51 ` [PATCH v4 21/25] virito_scsi: use freezable WQ for events Michael S. Tsirkin
                   ` (4 subsequent siblings)
  24 siblings, 0 replies; 43+ messages in thread
From: Michael S. Tsirkin @ 2014-10-13  7:51 UTC (permalink / raw)
  To: linux-kernel
  Cc: Rusty Russell, virtualization, linux-scsi, linux-s390,
	v9fs-developer, netdev, kvm, Amit Shah, Cornelia Huck,
	Christian Borntraeger, David S. Miller, Paolo Bonzini

virtio spec requires drivers to set DRIVER_OK before using VQs.
This is set automatically after restore returns, virtio net violated this
rule by using receive VQs within restore.

To fix, call virtio_device_ready before using VQs.

Signed-off-by: Michael S. Tsirkin <mst@redhat.com>
Reviewed-by: Cornelia Huck <cornelia.huck@de.ibm.com>
---
 drivers/net/virtio_net.c | 2 ++
 1 file changed, 2 insertions(+)

diff --git a/drivers/net/virtio_net.c b/drivers/net/virtio_net.c
index 3551417..6b6e136 100644
--- a/drivers/net/virtio_net.c
+++ b/drivers/net/virtio_net.c
@@ -1912,6 +1912,8 @@ static int virtnet_restore(struct virtio_device *vdev)
 	if (err)
 		return err;
 
+	virtio_device_ready(vdev);
+
 	if (netif_running(vi->dev)) {
 		for (i = 0; i < vi->curr_queue_pairs; i++)
 			if (!try_fill_recv(&vi->rq[i], GFP_KERNEL))
-- 
MST



^ permalink raw reply related	[flat|nested] 43+ messages in thread

* [PATCH v4 21/25] virito_scsi: use freezable WQ for events
  2014-10-13  7:48 [PATCH v4 00/25] virtio: fix spec compliance issues Michael S. Tsirkin
                   ` (19 preceding siblings ...)
  2014-10-13  7:51 ` [PATCH v4 20/25] virtio_net: " Michael S. Tsirkin
@ 2014-10-13  7:51 ` Michael S. Tsirkin
  2014-10-13  7:51 ` [PATCH v4 22/25] virtio_scsi: fix race on device removal Michael S. Tsirkin
                   ` (3 subsequent siblings)
  24 siblings, 0 replies; 43+ messages in thread
From: Michael S. Tsirkin @ 2014-10-13  7:51 UTC (permalink / raw)
  To: linux-kernel
  Cc: Rusty Russell, virtualization, linux-scsi, linux-s390,
	v9fs-developer, netdev, kvm, Amit Shah, Cornelia Huck,
	Christian Borntraeger, David S. Miller, Paolo Bonzini,
	James E.J. Bottomley

From: Paolo Bonzini <pbonzini@redhat.com>

Michael S. Tsirkin noticed a race condition:
we reset device on freeze, but system WQ is still
running so it might try adding bufs to a VQ meanwhile.

To fix, switch to handling events from the freezable WQ.

Reported-by: Michael S. Tsirkin <mst@redhat.com>
Signed-off-by: Paolo Bonzini <pbonzini@redhat.com>
Signed-off-by: Michael S. Tsirkin <mst@redhat.com>
---
 drivers/scsi/virtio_scsi.c | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/drivers/scsi/virtio_scsi.c b/drivers/scsi/virtio_scsi.c
index 2b565b3..501838d 100644
--- a/drivers/scsi/virtio_scsi.c
+++ b/drivers/scsi/virtio_scsi.c
@@ -390,7 +390,7 @@ static void virtscsi_complete_event(struct virtio_scsi *vscsi, void *buf)
 {
 	struct virtio_scsi_event_node *event_node = buf;
 
-	schedule_work(&event_node->work);
+	queue_work(system_freezable_wq, &event_node->work);
 }
 
 static void virtscsi_event_done(struct virtqueue *vq)
-- 
MST



^ permalink raw reply related	[flat|nested] 43+ messages in thread

* [PATCH v4 22/25] virtio_scsi: fix race on device removal
  2014-10-13  7:48 [PATCH v4 00/25] virtio: fix spec compliance issues Michael S. Tsirkin
                   ` (20 preceding siblings ...)
  2014-10-13  7:51 ` [PATCH v4 21/25] virito_scsi: use freezable WQ for events Michael S. Tsirkin
@ 2014-10-13  7:51 ` Michael S. Tsirkin
  2014-10-13  7:51 ` [PATCH v4 23/25] virtio_balloon: enable VQs early on restore Michael S. Tsirkin
                   ` (2 subsequent siblings)
  24 siblings, 0 replies; 43+ messages in thread
From: Michael S. Tsirkin @ 2014-10-13  7:51 UTC (permalink / raw)
  To: linux-kernel
  Cc: Rusty Russell, virtualization, linux-scsi, linux-s390,
	v9fs-developer, netdev, kvm, Amit Shah, Cornelia Huck,
	Christian Borntraeger, David S. Miller, Paolo Bonzini,
	James E.J. Bottomley

We cancel event work on device removal, but an interrupt
could trigger immediately after this, and queue it
again.

To fix, set a flag.

Loosely based on patch by Paolo Bonzini

Signed-off-by: Paolo Bonzini <pbonzini@redhat.com>
Signed-off-by: Michael S. Tsirkin <mst@redhat.com>
---
 drivers/scsi/virtio_scsi.c | 11 ++++++++++-
 1 file changed, 10 insertions(+), 1 deletion(-)

diff --git a/drivers/scsi/virtio_scsi.c b/drivers/scsi/virtio_scsi.c
index 501838d..327eba0 100644
--- a/drivers/scsi/virtio_scsi.c
+++ b/drivers/scsi/virtio_scsi.c
@@ -110,6 +110,9 @@ struct virtio_scsi {
 	/* CPU hotplug notifier */
 	struct notifier_block nb;
 
+	/* Protected by event_vq lock */
+	bool stop_events;
+
 	struct virtio_scsi_vq ctrl_vq;
 	struct virtio_scsi_vq event_vq;
 	struct virtio_scsi_vq req_vqs[];
@@ -303,6 +306,11 @@ static void virtscsi_cancel_event_work(struct virtio_scsi *vscsi)
 {
 	int i;
 
+	/* Stop scheduling work before calling cancel_work_sync.  */
+	spin_lock_irq(&vscsi->event_vq.vq_lock);
+	vscsi->stop_events = true;
+	spin_unlock_irq(&vscsi->event_vq.vq_lock);
+
 	for (i = 0; i < VIRTIO_SCSI_EVENT_LEN; i++)
 		cancel_work_sync(&vscsi->event_list[i].work);
 }
@@ -390,7 +398,8 @@ static void virtscsi_complete_event(struct virtio_scsi *vscsi, void *buf)
 {
 	struct virtio_scsi_event_node *event_node = buf;
 
-	queue_work(system_freezable_wq, &event_node->work);
+	if (!vscsi->stop_events)
+		queue_work(system_freezable_wq, &event_node->work);
 }
 
 static void virtscsi_event_done(struct virtqueue *vq)
-- 
MST



^ permalink raw reply related	[flat|nested] 43+ messages in thread

* [PATCH v4 23/25] virtio_balloon: enable VQs early on restore
  2014-10-13  7:48 [PATCH v4 00/25] virtio: fix spec compliance issues Michael S. Tsirkin
                   ` (21 preceding siblings ...)
  2014-10-13  7:51 ` [PATCH v4 22/25] virtio_scsi: fix race on device removal Michael S. Tsirkin
@ 2014-10-13  7:51 ` Michael S. Tsirkin
  2014-10-13  7:51 ` [PATCH v4 24/25] virtio_scsi: drop scan callback Michael S. Tsirkin
  2014-10-13  7:51 ` [PATCH v4 25/25] virtio-rng: refactor probe error handling Michael S. Tsirkin
  24 siblings, 0 replies; 43+ messages in thread
From: Michael S. Tsirkin @ 2014-10-13  7:51 UTC (permalink / raw)
  To: linux-kernel
  Cc: Rusty Russell, virtualization, linux-scsi, linux-s390,
	v9fs-developer, netdev, kvm, Amit Shah, Cornelia Huck,
	Christian Borntraeger, David S. Miller, Paolo Bonzini

virtio spec requires drivers to set DRIVER_OK before using VQs.
This is set automatically after resume returns, virtio balloon
violated this rule by adding bufs, which causes the VQ to be used
directly within restore.

To fix, call virtio_device_ready before using VQ.

Signed-off-by: Michael S. Tsirkin <mst@redhat.com>
---
 drivers/virtio/virtio_balloon.c | 2 ++
 1 file changed, 2 insertions(+)

diff --git a/drivers/virtio/virtio_balloon.c b/drivers/virtio/virtio_balloon.c
index 25ebe8e..9629fad 100644
--- a/drivers/virtio/virtio_balloon.c
+++ b/drivers/virtio/virtio_balloon.c
@@ -538,6 +538,8 @@ static int virtballoon_restore(struct virtio_device *vdev)
 	if (ret)
 		return ret;
 
+	virtio_device_ready(vdev);
+
 	fill_balloon(vb, towards_target(vb));
 	update_balloon_size(vb);
 	return 0;
-- 
MST



^ permalink raw reply related	[flat|nested] 43+ messages in thread

* [PATCH v4 24/25] virtio_scsi: drop scan callback
  2014-10-13  7:48 [PATCH v4 00/25] virtio: fix spec compliance issues Michael S. Tsirkin
                   ` (22 preceding siblings ...)
  2014-10-13  7:51 ` [PATCH v4 23/25] virtio_balloon: enable VQs early on restore Michael S. Tsirkin
@ 2014-10-13  7:51 ` Michael S. Tsirkin
  2014-10-13  7:51 ` [PATCH v4 25/25] virtio-rng: refactor probe error handling Michael S. Tsirkin
  24 siblings, 0 replies; 43+ messages in thread
From: Michael S. Tsirkin @ 2014-10-13  7:51 UTC (permalink / raw)
  To: linux-kernel
  Cc: Rusty Russell, virtualization, linux-scsi, linux-s390,
	v9fs-developer, netdev, kvm, Amit Shah, Cornelia Huck,
	Christian Borntraeger, David S. Miller, Paolo Bonzini,
	James E.J. Bottomley

Enable VQs early like we do for restore.
This makes it possible to drop the scan callback,
moving scanning into the probe function, and making
code simpler.

Signed-off-by: Michael S. Tsirkin <mst@redhat.com>
---
 drivers/scsi/virtio_scsi.c | 23 +++++++----------------
 1 file changed, 7 insertions(+), 16 deletions(-)

diff --git a/drivers/scsi/virtio_scsi.c b/drivers/scsi/virtio_scsi.c
index 327eba0..5f022ff 100644
--- a/drivers/scsi/virtio_scsi.c
+++ b/drivers/scsi/virtio_scsi.c
@@ -860,17 +860,6 @@ static void virtscsi_init_vq(struct virtio_scsi_vq *virtscsi_vq,
 	virtscsi_vq->vq = vq;
 }
 
-static void virtscsi_scan(struct virtio_device *vdev)
-{
-	struct Scsi_Host *shost = virtio_scsi_host(vdev);
-	struct virtio_scsi *vscsi = shost_priv(shost);
-
-	if (virtio_has_feature(vdev, VIRTIO_SCSI_F_HOTPLUG))
-		virtscsi_kick_event_all(vscsi);
-
-	scsi_scan_host(shost);
-}
-
 static void virtscsi_remove_vqs(struct virtio_device *vdev)
 {
 	struct Scsi_Host *sh = virtio_scsi_host(vdev);
@@ -1007,10 +996,13 @@ static int virtscsi_probe(struct virtio_device *vdev)
 	err = scsi_add_host(shost, &vdev->dev);
 	if (err)
 		goto scsi_add_host_failed;
-	/*
-	 * scsi_scan_host() happens in virtscsi_scan() via virtio_driver->scan()
-	 * after VIRTIO_CONFIG_S_DRIVER_OK has been set..
-	 */
+
+	virtio_device_ready(vdev);
+
+	if (virtio_has_feature(vdev, VIRTIO_SCSI_F_HOTPLUG))
+		virtscsi_kick_event_all(vscsi);
+
+	scsi_scan_host(shost);
 	return 0;
 
 scsi_add_host_failed:
@@ -1090,7 +1082,6 @@ static struct virtio_driver virtio_scsi_driver = {
 	.driver.owner = THIS_MODULE,
 	.id_table = id_table,
 	.probe = virtscsi_probe,
-	.scan = virtscsi_scan,
 #ifdef CONFIG_PM_SLEEP
 	.freeze = virtscsi_freeze,
 	.restore = virtscsi_restore,
-- 
MST



^ permalink raw reply related	[flat|nested] 43+ messages in thread

* [PATCH v4 25/25] virtio-rng: refactor probe error handling
  2014-10-13  7:48 [PATCH v4 00/25] virtio: fix spec compliance issues Michael S. Tsirkin
                   ` (23 preceding siblings ...)
  2014-10-13  7:51 ` [PATCH v4 24/25] virtio_scsi: drop scan callback Michael S. Tsirkin
@ 2014-10-13  7:51 ` Michael S. Tsirkin
  24 siblings, 0 replies; 43+ messages in thread
From: Michael S. Tsirkin @ 2014-10-13  7:51 UTC (permalink / raw)
  To: linux-kernel
  Cc: Rusty Russell, virtualization, linux-scsi, linux-s390,
	v9fs-developer, netdev, kvm, Amit Shah, Cornelia Huck,
	Christian Borntraeger, David S. Miller, Paolo Bonzini,
	Matt Mackall, Herbert Xu, Amos Kong, Sasha Levin

Code like
	vi->vq = NULL;
	kfree(vi)
does not make sense.

Clean it up, use goto error labels for cleanup.

Signed-off-by: Michael S. Tsirkin <mst@redhat.com>
---
 drivers/char/hw_random/virtio-rng.c | 15 +++++++++------
 1 file changed, 9 insertions(+), 6 deletions(-)

diff --git a/drivers/char/hw_random/virtio-rng.c b/drivers/char/hw_random/virtio-rng.c
index 132c9cc..72295ea 100644
--- a/drivers/char/hw_random/virtio-rng.c
+++ b/drivers/char/hw_random/virtio-rng.c
@@ -109,8 +109,8 @@ static int probe_common(struct virtio_device *vdev)
 
 	vi->index = index = ida_simple_get(&rng_index_ida, 0, 0, GFP_KERNEL);
 	if (index < 0) {
-		kfree(vi);
-		return index;
+		err = index;
+		goto err_ida;
 	}
 	sprintf(vi->name, "virtio_rng.%d", index);
 	init_completion(&vi->have_data);
@@ -128,13 +128,16 @@ static int probe_common(struct virtio_device *vdev)
 	vi->vq = virtio_find_single_vq(vdev, random_recv_done, "input");
 	if (IS_ERR(vi->vq)) {
 		err = PTR_ERR(vi->vq);
-		vi->vq = NULL;
-		kfree(vi);
-		ida_simple_remove(&rng_index_ida, index);
-		return err;
+		goto err_find;
 	}
 
 	return 0;
+
+err_find:
+	ida_simple_remove(&rng_index_ida, index);
+err_ida:
+	kfree(vi);
+	return err;
 }
 
 static void remove_common(struct virtio_device *vdev)
-- 
MST



^ permalink raw reply related	[flat|nested] 43+ messages in thread

* Re: [PATCH v4 04/25] virtio: defer config changed notifications
  2014-10-13  7:50 ` [PATCH v4 04/25] virtio: defer config changed notifications Michael S. Tsirkin
@ 2014-10-14  0:31   ` Rusty Russell
  2014-10-14  8:59     ` Michael S. Tsirkin
  0 siblings, 1 reply; 43+ messages in thread
From: Rusty Russell @ 2014-10-14  0:31 UTC (permalink / raw)
  To: Michael S. Tsirkin, linux-kernel
  Cc: virtualization, linux-scsi, linux-s390, v9fs-developer, netdev,
	kvm, Amit Shah, Cornelia Huck, Christian Borntraeger,
	David S. Miller, Paolo Bonzini, Heinz Graalfs

"Michael S. Tsirkin" <mst@redhat.com> writes:
> Defer config changed notifications that arrive during
> probe/scan/freeze/restore.
>
> This will allow drivers to set DRIVER_OK earlier, without worrying about
> racing with config change interrupts.
>
> This change will also benefit old hypervisors (before 2009)
> that send interrupts without checking DRIVER_OK: previously,
> the callback could race with driver-specific initialization.
>
> This will also help simplify drivers.

But AFAICT you never *read* dev->config_changed.

You unconditionally trigger a config_changed event in
virtio_config_enable().  That's a bit weird, but probably OK.

How about the following change (on top of your patch).  I
think the renaming is clearer, and note the added if() test in
virtio_config_enable().

If you approve, I'll fold it in.

Cheers,
Rusty.

diff --git a/drivers/virtio/virtio.c b/drivers/virtio/virtio.c
index 2536701b098b..df598dd8c5c8 100644
--- a/drivers/virtio/virtio.c
+++ b/drivers/virtio/virtio.c
@@ -122,7 +122,7 @@ static void __virtio_config_changed(struct virtio_device *dev)
 	struct virtio_driver *drv = drv_to_virtio(dev->dev.driver);
 
 	if (!dev->config_enabled)
-		dev->config_changed = true;
+		dev->config_change_pending = true;
 	else if (drv && drv->config_changed)
 		drv->config_changed(dev);
 }
@@ -148,8 +148,9 @@ static void virtio_config_enable(struct virtio_device *dev)
 {
 	spin_lock_irq(&dev->config_lock);
 	dev->config_enabled = true;
-	__virtio_config_changed(dev);
-	dev->config_changed = false;
+	if (dev->config_change_pending)
+		__virtio_config_changed(dev);
+	dev->config_change_pending = false;
 	spin_unlock_irq(&dev->config_lock);
 }
 
@@ -253,7 +254,7 @@ int register_virtio_device(struct virtio_device *dev)
 
 	spin_lock_init(&dev->config_lock);
 	dev->config_enabled = false;
-	dev->config_changed = false;
+	dev->config_change_pending = false;
 
 	/* We always start by resetting the device, in case a previous
 	 * driver messed it up.  This also tests that code path a little. */
diff --git a/include/linux/virtio.h b/include/linux/virtio.h
index 5636b119dc25..65261a7244fc 100644
--- a/include/linux/virtio.h
+++ b/include/linux/virtio.h
@@ -80,7 +80,7 @@ bool virtqueue_is_broken(struct virtqueue *vq);
  * @index: unique position on the virtio bus
  * @failed: saved value for CONFIG_S_FAILED bit (for restore)
  * @config_enabled: configuration change reporting enabled
- * @config_changed: configuration change reported while disabled
+ * @config_change_pending: configuration change reported while disabled
  * @config_lock: protects configuration change reporting
  * @dev: underlying device.
  * @id: the device type identification (used to match it with a driver).
@@ -94,7 +94,7 @@ struct virtio_device {
 	int index;
 	bool failed;
 	bool config_enabled;
-	bool config_changed;
+	bool config_change_pending;
 	spinlock_t config_lock;
 	struct device dev;
 	struct virtio_device_id id;

^ permalink raw reply related	[flat|nested] 43+ messages in thread

* Re: [PATCH v4 04/25] virtio: defer config changed notifications
  2014-10-14  0:31   ` Rusty Russell
@ 2014-10-14  8:59     ` Michael S. Tsirkin
  0 siblings, 0 replies; 43+ messages in thread
From: Michael S. Tsirkin @ 2014-10-14  8:59 UTC (permalink / raw)
  To: Rusty Russell
  Cc: linux-kernel, virtualization, linux-scsi, linux-s390,
	v9fs-developer, netdev, kvm, Amit Shah, Cornelia Huck,
	Christian Borntraeger, David S. Miller, Paolo Bonzini,
	Heinz Graalfs

On Tue, Oct 14, 2014 at 11:01:12AM +1030, Rusty Russell wrote:
> "Michael S. Tsirkin" <mst@redhat.com> writes:
> > Defer config changed notifications that arrive during
> > probe/scan/freeze/restore.
> >
> > This will allow drivers to set DRIVER_OK earlier, without worrying about
> > racing with config change interrupts.
> >
> > This change will also benefit old hypervisors (before 2009)
> > that send interrupts without checking DRIVER_OK: previously,
> > the callback could race with driver-specific initialization.
> >
> > This will also help simplify drivers.
> 
> But AFAICT you never *read* dev->config_changed.
> 
> You unconditionally trigger a config_changed event in
> virtio_config_enable().  That's a bit weird, but probably OK.
> 
> How about the following change (on top of your patch).  I
> think the renaming is clearer, and note the added if() test in
> virtio_config_enable().
> 
> If you approve, I'll fold it in.
> 
> Cheers,
> Rusty.

Hi Rusty,
I'm okay with both changes.
You can fold it in if you prefer, or just make it a patch on top.

> diff --git a/drivers/virtio/virtio.c b/drivers/virtio/virtio.c
> index 2536701b098b..df598dd8c5c8 100644
> --- a/drivers/virtio/virtio.c
> +++ b/drivers/virtio/virtio.c
> @@ -122,7 +122,7 @@ static void __virtio_config_changed(struct virtio_device *dev)
>  	struct virtio_driver *drv = drv_to_virtio(dev->dev.driver);
>  
>  	if (!dev->config_enabled)
> -		dev->config_changed = true;
> +		dev->config_change_pending = true;
>  	else if (drv && drv->config_changed)
>  		drv->config_changed(dev);
>  }
> @@ -148,8 +148,9 @@ static void virtio_config_enable(struct virtio_device *dev)
>  {
>  	spin_lock_irq(&dev->config_lock);
>  	dev->config_enabled = true;
> -	__virtio_config_changed(dev);
> -	dev->config_changed = false;
> +	if (dev->config_change_pending)
> +		__virtio_config_changed(dev);
> +	dev->config_change_pending = false;
>  	spin_unlock_irq(&dev->config_lock);
>  }
>  
> @@ -253,7 +254,7 @@ int register_virtio_device(struct virtio_device *dev)
>  
>  	spin_lock_init(&dev->config_lock);
>  	dev->config_enabled = false;
> -	dev->config_changed = false;
> +	dev->config_change_pending = false;
>  
>  	/* We always start by resetting the device, in case a previous
>  	 * driver messed it up.  This also tests that code path a little. */
> diff --git a/include/linux/virtio.h b/include/linux/virtio.h
> index 5636b119dc25..65261a7244fc 100644
> --- a/include/linux/virtio.h
> +++ b/include/linux/virtio.h
> @@ -80,7 +80,7 @@ bool virtqueue_is_broken(struct virtqueue *vq);
>   * @index: unique position on the virtio bus
>   * @failed: saved value for CONFIG_S_FAILED bit (for restore)
>   * @config_enabled: configuration change reporting enabled
> - * @config_changed: configuration change reported while disabled
> + * @config_change_pending: configuration change reported while disabled
>   * @config_lock: protects configuration change reporting
>   * @dev: underlying device.
>   * @id: the device type identification (used to match it with a driver).
> @@ -94,7 +94,7 @@ struct virtio_device {
>  	int index;
>  	bool failed;
>  	bool config_enabled;
> -	bool config_changed;
> +	bool config_change_pending;
>  	spinlock_t config_lock;
>  	struct device dev;
>  	struct virtio_device_id id;

^ permalink raw reply	[flat|nested] 43+ messages in thread

* Re: [PATCH v4 03/25] virtio-pci: move freeze/restore to virtio core
  2014-10-13  7:48 ` [PATCH v4 03/25] virtio-pci: move freeze/restore to virtio core Michael S. Tsirkin
@ 2014-10-15  7:05   ` Paul Bolle
  0 siblings, 0 replies; 43+ messages in thread
From: Paul Bolle @ 2014-10-15  7:05 UTC (permalink / raw)
  To: Michael S. Tsirkin
  Cc: Valentin Rothberg, linux-kernel, Rusty Russell, virtualization,
	linux-scsi, linux-s390, v9fs-developer, netdev, kvm, Amit Shah,
	Cornelia Huck, Christian Borntraeger, David S. Miller,
	Paolo Bonzini, Heinz Graalfs

On Mon, 2014-10-13 at 10:48 +0300, Michael S. Tsirkin wrote:
> This is in preparation to extending config changed event handling
> in core.
> Wrapping these in an API also seems to make for a cleaner code.
> 
> Signed-off-by: Michael S. Tsirkin <mst@redhat.com>
> Reviewed-by: Cornelia Huck <cornelia.huck@de.ibm.com>

This patch landed in today's linux-next (next-20141015).

>  include/linux/virtio.h      |  6 +++++
>  drivers/virtio/virtio.c     | 54 +++++++++++++++++++++++++++++++++++++++++++++
>  drivers/virtio/virtio_pci.c | 54 ++-------------------------------------------
>  3 files changed, 62 insertions(+), 52 deletions(-)
> 
> diff --git a/include/linux/virtio.h b/include/linux/virtio.h
> index 3c19bd3..8df7ba8 100644
> --- a/include/linux/virtio.h
> +++ b/include/linux/virtio.h
> @@ -78,6 +78,7 @@ bool virtqueue_is_broken(struct virtqueue *vq);
>  /**
>   * virtio_device - representation of a device using virtio
>   * @index: unique position on the virtio bus
> + * @failed: saved value for CONFIG_S_FAILED bit (for restore)

s/CONFIG_S_FAILED/VIRTIO_CONFIG_S_FAILED/?

>   * @dev: underlying device.
>   * @id: the device type identification (used to match it with a driver).
>   * @config: the configuration ops for this device.


Paul Bolle


^ permalink raw reply	[flat|nested] 43+ messages in thread

* Re: [PATCH v4 13/25] virtio_console: enable VQs early
  2014-10-13  7:50 ` [PATCH v4 13/25] virtio_console: " Michael S. Tsirkin
@ 2014-10-20 12:07   ` Thomas Graf
  2014-10-20 12:42     ` Cornelia Huck
  2014-10-20 13:10     ` Michael S. Tsirkin
  0 siblings, 2 replies; 43+ messages in thread
From: Thomas Graf @ 2014-10-20 12:07 UTC (permalink / raw)
  To: Michael S. Tsirkin
  Cc: linux-kernel, Rusty Russell, virtualization, linux-scsi,
	linux-s390, v9fs-developer, netdev, kvm, Amit Shah,
	Cornelia Huck, Christian Borntraeger, David S. Miller,
	Paolo Bonzini, Arnd Bergmann, Greg Kroah-Hartman

On 10/13/14 at 10:50am, Michael S. Tsirkin wrote:
> virtio spec requires drivers to set DRIVER_OK before using VQs.
> This is set automatically after probe returns, virtio console violated this
> rule by adding inbufs, which causes the VQ to be used directly within
> probe.
> 
> To fix, call virtio_device_ready before using VQs.
> 
> Signed-off-by: Michael S. Tsirkin <mst@redhat.com>
> ---
>  drivers/char/virtio_console.c | 2 ++
>  1 file changed, 2 insertions(+)
> 
> diff --git a/drivers/char/virtio_console.c b/drivers/char/virtio_console.c
> index b585b47..6ebe8f6 100644
> --- a/drivers/char/virtio_console.c
> +++ b/drivers/char/virtio_console.c
> @@ -1449,6 +1449,8 @@ static int add_port(struct ports_device *portdev, u32 id)
>  	spin_lock_init(&port->outvq_lock);
>  	init_waitqueue_head(&port->waitqueue);
>  
> +	virtio_device_ready(portdev->vdev);
> +
>  	/* Fill the in_vq with buffers so the host can send us data. */
>  	nr_added_bufs = fill_queue(port->in_vq, &port->inbuf_lock);
>  	if (!nr_added_bufs) {

Seems like probe and add_port() now both set VIRTIO_CONFIG_S_DRIVER_OK

    1.839658] kernel BUG at include/linux/virtio_config.h:125!
[    1.839995] invalid opcode: 0000 [#1] SMP 
[    1.840169] Modules linked in: serio_raw virtio_balloon pcspkr virtio_net virtio_console soundcore parport_pc floppy pvpanic parport i2c_piix4 nfsd auth_rpcgss nfs_acl lockd grace sunrpc qxl drm_kms_helper ttm drm virtio_blk i2c_core virtio_pci ata_generic virtio_ring virtio pata_acpi
[    1.840169] CPU: 2 PID: 266 Comm: kworker/2:2 Not tainted 3.17.0+ #1
[    1.840169] Hardware name: Bochs Bochs, BIOS Bochs 01/01/2011
[    1.840169] Workqueue: events control_work_handler [virtio_console]
[    1.840169] task: ffff8800364bc840 ti: ffff880078490000 task.ti: ffff880078490000
[    1.840169] RIP: 0010:[<ffffffffa01d92c6>]  [<ffffffffa01d92c6>] virtio_device_ready.part.12+0x4/0x6 [virtio_console]
[    1.840169] RSP: 0018:ffff880078493c78  EFLAGS: 00010202
[    1.840169] RAX: 0000000000000007 RBX: ffff880036406200 RCX: 0000000000006e39
[    1.840169] RDX: 000000000000c0b2 RSI: 0000000000000000 RDI: 000000000001c0b2
[    1.840169] RBP: ffff880078493c78 R08: ffffffff81d2c6f8 R09: 0000000000000000
[    1.840169] R10: 0000000000000001 R11: ffff8800364bd000 R12: ffff880036618400
[    1.840169] R13: 0000000000000001 R14: ffff8800368c6800 R15: ffff880036406220
[    1.840169] FS:  0000000000000000(0000) GS:ffff88007fd00000(0000) knlGS:0000000000000000
[    1.840169] CS:  0010 DS: 0000 ES: 0000 CR0: 000000008005003b
[    1.840169] CR2: 00007f1c31c90000 CR3: 0000000001c14000 CR4: 00000000000006e0
[    1.840169] Stack:
[    1.840169]  ffff880078493ce8 ffffffffa01d886a ffff880000000001 ffffffff810e20cd
[    1.840169]  ffff880078493cb8 0000000000000282 0000000000000000 0000000087f90194
[    1.840169]  ffff880078493ce8 ffff88007ab1d4e0 ffff880036618498 ffff880036618410
[    1.840169] Call Trace:
[    1.840169]  [<ffffffffa01d886a>] add_port+0x40a/0x440 [virtio_console]
[    1.840169]  [<ffffffff810e20cd>] ? trace_hardirqs_on+0xd/0x10
[    1.840169]  [<ffffffffa01d8c6a>] control_work_handler+0x3ca/0x420 [virtio_console]
[    1.840169]  [<ffffffff810b0e7b>] ? process_one_work+0x15b/0x530
[    1.840169]  [<ffffffff810b0ef4>] process_one_work+0x1d4/0x530
[    1.840169]  [<ffffffff810b0e7b>] ? process_one_work+0x15b/0x530
[    1.840169]  [<ffffffff810b136b>] worker_thread+0x11b/0x490
[    1.840169]  [<ffffffff810b1250>] ? process_one_work+0x530/0x530
[    1.840169]  [<ffffffff810b67c3>] kthread+0xf3/0x110
[    1.840169]  [<ffffffff81788f00>] ? _raw_spin_unlock_irq+0x30/0x50
[    1.840169]  [<ffffffff810b66d0>] ? kthread_create_on_node+0x240/0x240
[    1.840169]  [<ffffffff81789a7c>] ret_from_fork+0x7c/0xb0
[    1.840169]  [<ffffffff810b66d0>] ? kthread_create_on_node+0x240/0x240
[    1.840169] Code: ff 49 89 c4 4d 85 e4 0f 8f 25 ff ff ff eb ad 48 c7 c0 f4 ff ff ff e9 17 ff ff ff e8 f5 cd eb e0 90 55 48 89 e5 0f 0b 55 48 89 e5 <0f> 0b 55 48 89 e5 0f 0b 55 48 89 e5 e8 99 e2 ff ff 48 c7 c7 c0 
[    1.840169] RIP  [<ffffffffa01d92c6>] virtio_device_ready.part.12+0x4/0x6 [virtio_console]
[    1.840169]  RSP <ffff880078493c78>


^ permalink raw reply	[flat|nested] 43+ messages in thread

* Re: [PATCH v4 13/25] virtio_console: enable VQs early
  2014-10-20 12:07   ` Thomas Graf
@ 2014-10-20 12:42     ` Cornelia Huck
  2014-10-20 13:10       ` Thomas Graf
  2014-10-20 13:35       ` Michael S. Tsirkin
  2014-10-20 13:10     ` Michael S. Tsirkin
  1 sibling, 2 replies; 43+ messages in thread
From: Cornelia Huck @ 2014-10-20 12:42 UTC (permalink / raw)
  To: Thomas Graf
  Cc: Michael S. Tsirkin, linux-kernel, Rusty Russell, virtualization,
	linux-scsi, linux-s390, v9fs-developer, netdev, kvm, Amit Shah,
	Christian Borntraeger, David S. Miller, Paolo Bonzini,
	Arnd Bergmann, Greg Kroah-Hartman

On Mon, 20 Oct 2014 13:07:50 +0100
Thomas Graf <tgraf@suug.ch> wrote:

> On 10/13/14 at 10:50am, Michael S. Tsirkin wrote:
> > virtio spec requires drivers to set DRIVER_OK before using VQs.
> > This is set automatically after probe returns, virtio console violated this
> > rule by adding inbufs, which causes the VQ to be used directly within
> > probe.
> > 
> > To fix, call virtio_device_ready before using VQs.
> > 
> > Signed-off-by: Michael S. Tsirkin <mst@redhat.com>
> > ---
> >  drivers/char/virtio_console.c | 2 ++
> >  1 file changed, 2 insertions(+)
> > 
> > diff --git a/drivers/char/virtio_console.c b/drivers/char/virtio_console.c
> > index b585b47..6ebe8f6 100644
> > --- a/drivers/char/virtio_console.c
> > +++ b/drivers/char/virtio_console.c
> > @@ -1449,6 +1449,8 @@ static int add_port(struct ports_device *portdev, u32 id)
> >  	spin_lock_init(&port->outvq_lock);
> >  	init_waitqueue_head(&port->waitqueue);
> >  
> > +	virtio_device_ready(portdev->vdev);
> > +
> >  	/* Fill the in_vq with buffers so the host can send us data. */
> >  	nr_added_bufs = fill_queue(port->in_vq, &port->inbuf_lock);
> >  	if (!nr_added_bufs) {
> 
> Seems like probe and add_port() now both set VIRTIO_CONFIG_S_DRIVER_OK

I think we need to set this in the probe function instead, otherwise we
fail for multiqueue (which also wants to use the control queue early).

Completely untested patch below; I can send this with proper s-o-b if
it helps.

diff --git a/drivers/char/virtio_console.c b/drivers/char/virtio_console.c
index bfa6400..cf7a561 100644
--- a/drivers/char/virtio_console.c
+++ b/drivers/char/virtio_console.c
@@ -1449,8 +1449,6 @@ static int add_port(struct ports_device *portdev, u32 id)
 	spin_lock_init(&port->outvq_lock);
 	init_waitqueue_head(&port->waitqueue);
 
-	virtio_device_ready(portdev->vdev);
-
 	/* Fill the in_vq with buffers so the host can send us data. */
 	nr_added_bufs = fill_queue(port->in_vq, &port->inbuf_lock);
 	if (!nr_added_bufs) {
@@ -2026,6 +2024,8 @@ static int virtcons_probe(struct virtio_device *vdev)
 	spin_lock_init(&portdev->ports_lock);
 	INIT_LIST_HEAD(&portdev->ports);
 
+	virtio_device_ready(portdev->vdev);
+
 	if (multiport) {
 		unsigned int nr_added_bufs;
 


^ permalink raw reply related	[flat|nested] 43+ messages in thread

* Re: [PATCH v4 13/25] virtio_console: enable VQs early
  2014-10-20 12:07   ` Thomas Graf
  2014-10-20 12:42     ` Cornelia Huck
@ 2014-10-20 13:10     ` Michael S. Tsirkin
  2014-10-20 13:12       ` Thomas Graf
  2014-10-20 13:14       ` Michael S. Tsirkin
  1 sibling, 2 replies; 43+ messages in thread
From: Michael S. Tsirkin @ 2014-10-20 13:10 UTC (permalink / raw)
  To: Thomas Graf
  Cc: linux-kernel, Rusty Russell, virtualization, linux-scsi,
	linux-s390, v9fs-developer, netdev, kvm, Amit Shah,
	Cornelia Huck, Christian Borntraeger, David S. Miller,
	Paolo Bonzini, Arnd Bergmann, Greg Kroah-Hartman

On Mon, Oct 20, 2014 at 01:07:50PM +0100, Thomas Graf wrote:
> On 10/13/14 at 10:50am, Michael S. Tsirkin wrote:
> > virtio spec requires drivers to set DRIVER_OK before using VQs.
> > This is set automatically after probe returns, virtio console violated this
> > rule by adding inbufs, which causes the VQ to be used directly within
> > probe.
> > 
> > To fix, call virtio_device_ready before using VQs.
> > 
> > Signed-off-by: Michael S. Tsirkin <mst@redhat.com>
> > ---
> >  drivers/char/virtio_console.c | 2 ++
> >  1 file changed, 2 insertions(+)
> > 
> > diff --git a/drivers/char/virtio_console.c b/drivers/char/virtio_console.c
> > index b585b47..6ebe8f6 100644
> > --- a/drivers/char/virtio_console.c
> > +++ b/drivers/char/virtio_console.c
> > @@ -1449,6 +1449,8 @@ static int add_port(struct ports_device *portdev, u32 id)
> >  	spin_lock_init(&port->outvq_lock);
> >  	init_waitqueue_head(&port->waitqueue);
> >  
> > +	virtio_device_ready(portdev->vdev);
> > +
> >  	/* Fill the in_vq with buffers so the host can send us data. */
> >  	nr_added_bufs = fill_queue(port->in_vq, &port->inbuf_lock);
> >  	if (!nr_added_bufs) {

I see Cornelia sent a patch already.
I'd like to reproduce this though - could you send me
the command line please?


> Seems like probe and add_port() now both set VIRTIO_CONFIG_S_DRIVER_OK
> 
>     1.839658] kernel BUG at include/linux/virtio_config.h:125!
> [    1.839995] invalid opcode: 0000 [#1] SMP 
> [    1.840169] Modules linked in: serio_raw virtio_balloon pcspkr virtio_net virtio_console soundcore parport_pc floppy pvpanic parport i2c_piix4 nfsd auth_rpcgss nfs_acl lockd grace sunrpc qxl drm_kms_helper ttm drm virtio_blk i2c_core virtio_pci ata_generic virtio_ring virtio pata_acpi
> [    1.840169] CPU: 2 PID: 266 Comm: kworker/2:2 Not tainted 3.17.0+ #1
> [    1.840169] Hardware name: Bochs Bochs, BIOS Bochs 01/01/2011
> [    1.840169] Workqueue: events control_work_handler [virtio_console]
> [    1.840169] task: ffff8800364bc840 ti: ffff880078490000 task.ti: ffff880078490000
> [    1.840169] RIP: 0010:[<ffffffffa01d92c6>]  [<ffffffffa01d92c6>] virtio_device_ready.part.12+0x4/0x6 [virtio_console]
> [    1.840169] RSP: 0018:ffff880078493c78  EFLAGS: 00010202
> [    1.840169] RAX: 0000000000000007 RBX: ffff880036406200 RCX: 0000000000006e39
> [    1.840169] RDX: 000000000000c0b2 RSI: 0000000000000000 RDI: 000000000001c0b2
> [    1.840169] RBP: ffff880078493c78 R08: ffffffff81d2c6f8 R09: 0000000000000000
> [    1.840169] R10: 0000000000000001 R11: ffff8800364bd000 R12: ffff880036618400
> [    1.840169] R13: 0000000000000001 R14: ffff8800368c6800 R15: ffff880036406220
> [    1.840169] FS:  0000000000000000(0000) GS:ffff88007fd00000(0000) knlGS:0000000000000000
> [    1.840169] CS:  0010 DS: 0000 ES: 0000 CR0: 000000008005003b
> [    1.840169] CR2: 00007f1c31c90000 CR3: 0000000001c14000 CR4: 00000000000006e0
> [    1.840169] Stack:
> [    1.840169]  ffff880078493ce8 ffffffffa01d886a ffff880000000001 ffffffff810e20cd
> [    1.840169]  ffff880078493cb8 0000000000000282 0000000000000000 0000000087f90194
> [    1.840169]  ffff880078493ce8 ffff88007ab1d4e0 ffff880036618498 ffff880036618410
> [    1.840169] Call Trace:
> [    1.840169]  [<ffffffffa01d886a>] add_port+0x40a/0x440 [virtio_console]
> [    1.840169]  [<ffffffff810e20cd>] ? trace_hardirqs_on+0xd/0x10
> [    1.840169]  [<ffffffffa01d8c6a>] control_work_handler+0x3ca/0x420 [virtio_console]
> [    1.840169]  [<ffffffff810b0e7b>] ? process_one_work+0x15b/0x530
> [    1.840169]  [<ffffffff810b0ef4>] process_one_work+0x1d4/0x530
> [    1.840169]  [<ffffffff810b0e7b>] ? process_one_work+0x15b/0x530
> [    1.840169]  [<ffffffff810b136b>] worker_thread+0x11b/0x490
> [    1.840169]  [<ffffffff810b1250>] ? process_one_work+0x530/0x530
> [    1.840169]  [<ffffffff810b67c3>] kthread+0xf3/0x110
> [    1.840169]  [<ffffffff81788f00>] ? _raw_spin_unlock_irq+0x30/0x50
> [    1.840169]  [<ffffffff810b66d0>] ? kthread_create_on_node+0x240/0x240
> [    1.840169]  [<ffffffff81789a7c>] ret_from_fork+0x7c/0xb0
> [    1.840169]  [<ffffffff810b66d0>] ? kthread_create_on_node+0x240/0x240
> [    1.840169] Code: ff 49 89 c4 4d 85 e4 0f 8f 25 ff ff ff eb ad 48 c7 c0 f4 ff ff ff e9 17 ff ff ff e8 f5 cd eb e0 90 55 48 89 e5 0f 0b 55 48 89 e5 <0f> 0b 55 48 89 e5 0f 0b 55 48 89 e5 e8 99 e2 ff ff 48 c7 c7 c0 
> [    1.840169] RIP  [<ffffffffa01d92c6>] virtio_device_ready.part.12+0x4/0x6 [virtio_console]
> [    1.840169]  RSP <ffff880078493c78>

^ permalink raw reply	[flat|nested] 43+ messages in thread

* Re: [PATCH v4 13/25] virtio_console: enable VQs early
  2014-10-20 12:42     ` Cornelia Huck
@ 2014-10-20 13:10       ` Thomas Graf
  2014-10-20 13:35       ` Michael S. Tsirkin
  1 sibling, 0 replies; 43+ messages in thread
From: Thomas Graf @ 2014-10-20 13:10 UTC (permalink / raw)
  To: Cornelia Huck
  Cc: Michael S. Tsirkin, linux-kernel, Rusty Russell, virtualization,
	linux-scsi, linux-s390, v9fs-developer, netdev, kvm, Amit Shah,
	Christian Borntraeger, David S. Miller, Paolo Bonzini,
	Arnd Bergmann, Greg Kroah-Hartman

On 10/20/14 at 02:42pm, Cornelia Huck wrote:
> On Mon, 20 Oct 2014 13:07:50 +0100
> Thomas Graf <tgraf@suug.ch> wrote:
> 
> > On 10/13/14 at 10:50am, Michael S. Tsirkin wrote:
> > > virtio spec requires drivers to set DRIVER_OK before using VQs.
> > > This is set automatically after probe returns, virtio console violated this
> > > rule by adding inbufs, which causes the VQ to be used directly within
> > > probe.
> > > 
> > > To fix, call virtio_device_ready before using VQs.
> > > 
> > > Signed-off-by: Michael S. Tsirkin <mst@redhat.com>
> > > ---
> > >  drivers/char/virtio_console.c | 2 ++
> > >  1 file changed, 2 insertions(+)
> > > 
> > > diff --git a/drivers/char/virtio_console.c b/drivers/char/virtio_console.c
> > > index b585b47..6ebe8f6 100644
> > > --- a/drivers/char/virtio_console.c
> > > +++ b/drivers/char/virtio_console.c
> > > @@ -1449,6 +1449,8 @@ static int add_port(struct ports_device *portdev, u32 id)
> > >  	spin_lock_init(&port->outvq_lock);
> > >  	init_waitqueue_head(&port->waitqueue);
> > >  
> > > +	virtio_device_ready(portdev->vdev);
> > > +
> > >  	/* Fill the in_vq with buffers so the host can send us data. */
> > >  	nr_added_bufs = fill_queue(port->in_vq, &port->inbuf_lock);
> > >  	if (!nr_added_bufs) {
> > 
> > Seems like probe and add_port() now both set VIRTIO_CONFIG_S_DRIVER_OK
> 
> I think we need to set this in the probe function instead, otherwise we
> fail for multiqueue (which also wants to use the control queue early).
> 
> Completely untested patch below; I can send this with proper s-o-b if
> it helps.

virtio_dev_probe() already sets DRIVER_OK if ->probe() returned
without an error. I assume Michael added it to add_port() because
probing doesn't always occur first. Can we just remove the BUG_ON()?

^ permalink raw reply	[flat|nested] 43+ messages in thread

* Re: [PATCH v4 13/25] virtio_console: enable VQs early
  2014-10-20 13:10     ` Michael S. Tsirkin
@ 2014-10-20 13:12       ` Thomas Graf
  2014-10-20 13:14       ` Michael S. Tsirkin
  1 sibling, 0 replies; 43+ messages in thread
From: Thomas Graf @ 2014-10-20 13:12 UTC (permalink / raw)
  To: Michael S. Tsirkin
  Cc: linux-kernel, Rusty Russell, virtualization, linux-scsi,
	linux-s390, v9fs-developer, netdev, kvm, Amit Shah,
	Cornelia Huck, Christian Borntraeger, David S. Miller,
	Paolo Bonzini, Arnd Bergmann, Greg Kroah-Hartman

On 10/20/14 at 04:10pm, Michael S. Tsirkin wrote:
> On Mon, Oct 20, 2014 at 01:07:50PM +0100, Thomas Graf wrote:
> > On 10/13/14 at 10:50am, Michael S. Tsirkin wrote:
> > > virtio spec requires drivers to set DRIVER_OK before using VQs.
> > > This is set automatically after probe returns, virtio console violated this
> > > rule by adding inbufs, which causes the VQ to be used directly within
> > > probe.
> > > 
> > > To fix, call virtio_device_ready before using VQs.
> > > 
> > > Signed-off-by: Michael S. Tsirkin <mst@redhat.com>
> > > ---
> > >  drivers/char/virtio_console.c | 2 ++
> > >  1 file changed, 2 insertions(+)
> > > 
> > > diff --git a/drivers/char/virtio_console.c b/drivers/char/virtio_console.c
> > > index b585b47..6ebe8f6 100644
> > > --- a/drivers/char/virtio_console.c
> > > +++ b/drivers/char/virtio_console.c
> > > @@ -1449,6 +1449,8 @@ static int add_port(struct ports_device *portdev, u32 id)
> > >  	spin_lock_init(&port->outvq_lock);
> > >  	init_waitqueue_head(&port->waitqueue);
> > >  
> > > +	virtio_device_ready(portdev->vdev);
> > > +
> > >  	/* Fill the in_vq with buffers so the host can send us data. */
> > >  	nr_added_bufs = fill_queue(port->in_vq, &port->inbuf_lock);
> > >  	if (!nr_added_bufs) {
> 
> I see Cornelia sent a patch already.
> I'd like to reproduce this though - could you send me
> the command line please?

1. Invoke qemu:

/usr/bin/qemu-system-x86_64 -machine accel=kvm -name f20-2 -S -machine
pc-i440fx-1.4,accel=kvm,usb=off -m 2048 -realtime mlock=off -smp
4,sockets=4,cores=1,threads=1 -uuid
dd45ec4c-7c26-4b73-9b6b-81f2912c5235 -no-user-config -nodefaults
-chardev
socket,id=charmonitor,path=/var/lib/libvirt/qemu/f20-2.monitor,server,nowait
-mon chardev=charmonitor,id=monitor,mode=control -rtc base=utc
-no-shutdown -device piix3-usb-uhci,id=usb,bus=pci.0,addr=0x1.0x2
-device virtio-serial-pci,id=virtio-serial0,bus=pci.0,addr=0x5 -drive
file=/virt/f20n2-clone,if=none,id=drive-virtio-disk0,format=raw
-device
virtio-blk-pci,scsi=off,bus=pci.0,addr=0x6,drive=drive-virtio-disk0,id=virtio-disk0,bootindex=1
-netdev tap,fd=24,id=hostnet0,vhost=on,vhostfd=25 -device
virtio-net-pci,netdev=hostnet0,id=net0,mac=52:54:00:ef:72:4e,bus=pci.0,addr=0x3
-chardev pty,id=charserial0 -device
isa-serial,chardev=charserial0,id=serial0 -chardev
spicevmc,id=charchannel0,name=vdagent -device
virtserialport,bus=virtio-serial0.0,nr=1,chardev=charchannel0,id=channel0,name=com.redhat.spice.0
-device usb-tablet,id=input0 -spice
port=5900,addr=127.0.0.1,disable-ticketing,seamless-migration=on
-device
qxl-vga,id=video0,ram_size=67108864,vram_size=67108864,bus=pci.0,addr=0x2
-device intel-hda,id=sound0,bus=pci.0,addr=0x4 -device
hda-duplex,id=sound0-codec0,bus=sound0.0,cad=0 -device
virtio-balloon-pci,id=balloon0,bus=pci.0,addr=0x7

2. Attach console right away: virsh console f20-2

^ permalink raw reply	[flat|nested] 43+ messages in thread

* Re: [PATCH v4 13/25] virtio_console: enable VQs early
  2014-10-20 13:10     ` Michael S. Tsirkin
  2014-10-20 13:12       ` Thomas Graf
@ 2014-10-20 13:14       ` Michael S. Tsirkin
  1 sibling, 0 replies; 43+ messages in thread
From: Michael S. Tsirkin @ 2014-10-20 13:14 UTC (permalink / raw)
  To: Thomas Graf
  Cc: linux-kernel, Rusty Russell, virtualization, linux-scsi,
	linux-s390, v9fs-developer, netdev, kvm, Amit Shah,
	Cornelia Huck, Christian Borntraeger, David S. Miller,
	Paolo Bonzini, Arnd Bergmann, Greg Kroah-Hartman

On Mon, Oct 20, 2014 at 04:10:16PM +0300, Michael S. Tsirkin wrote:
> On Mon, Oct 20, 2014 at 01:07:50PM +0100, Thomas Graf wrote:
> > On 10/13/14 at 10:50am, Michael S. Tsirkin wrote:
> > > virtio spec requires drivers to set DRIVER_OK before using VQs.
> > > This is set automatically after probe returns, virtio console violated this
> > > rule by adding inbufs, which causes the VQ to be used directly within
> > > probe.
> > > 
> > > To fix, call virtio_device_ready before using VQs.
> > > 
> > > Signed-off-by: Michael S. Tsirkin <mst@redhat.com>
> > > ---
> > >  drivers/char/virtio_console.c | 2 ++
> > >  1 file changed, 2 insertions(+)
> > > 
> > > diff --git a/drivers/char/virtio_console.c b/drivers/char/virtio_console.c
> > > index b585b47..6ebe8f6 100644
> > > --- a/drivers/char/virtio_console.c
> > > +++ b/drivers/char/virtio_console.c
> > > @@ -1449,6 +1449,8 @@ static int add_port(struct ports_device *portdev, u32 id)
> > >  	spin_lock_init(&port->outvq_lock);
> > >  	init_waitqueue_head(&port->waitqueue);
> > >  
> > > +	virtio_device_ready(portdev->vdev);
> > > +
> > >  	/* Fill the in_vq with buffers so the host can send us data. */
> > >  	nr_added_bufs = fill_queue(port->in_vq, &port->inbuf_lock);
> > >  	if (!nr_added_bufs) {
> 
> I see Cornelia sent a patch already.
> I'd like to reproduce this though - could you send me
> the command line please?

Nevermind, the trick is to add a port it seems:

-device virtio-serial -chardev socket,path=/tmp/c1,server,nowait,id=foo
-device virtserialport,chardev=foo,name=org.fedoraproject.port.0

works fine without -device virtserialport.

-- 
MST

^ permalink raw reply	[flat|nested] 43+ messages in thread

* Re: [PATCH v4 13/25] virtio_console: enable VQs early
  2014-10-20 12:42     ` Cornelia Huck
  2014-10-20 13:10       ` Thomas Graf
@ 2014-10-20 13:35       ` Michael S. Tsirkin
  2014-10-20 13:58         ` [PATCH] virtio_console: move early VQ enablement Cornelia Huck
  2014-10-20 14:04         ` [PATCH v4 13/25] virtio_console: enable VQs early Michael S. Tsirkin
  1 sibling, 2 replies; 43+ messages in thread
From: Michael S. Tsirkin @ 2014-10-20 13:35 UTC (permalink / raw)
  To: Cornelia Huck
  Cc: Thomas Graf, linux-kernel, Rusty Russell, virtualization,
	linux-scsi, linux-s390, v9fs-developer, netdev, kvm, Amit Shah,
	Christian Borntraeger, David S. Miller, Paolo Bonzini,
	Arnd Bergmann, Greg Kroah-Hartman

On Mon, Oct 20, 2014 at 02:42:23PM +0200, Cornelia Huck wrote:
> On Mon, 20 Oct 2014 13:07:50 +0100
> Thomas Graf <tgraf@suug.ch> wrote:
> 
> > On 10/13/14 at 10:50am, Michael S. Tsirkin wrote:
> > > virtio spec requires drivers to set DRIVER_OK before using VQs.
> > > This is set automatically after probe returns, virtio console violated this
> > > rule by adding inbufs, which causes the VQ to be used directly within
> > > probe.
> > > 
> > > To fix, call virtio_device_ready before using VQs.
> > > 
> > > Signed-off-by: Michael S. Tsirkin <mst@redhat.com>
> > > ---
> > >  drivers/char/virtio_console.c | 2 ++
> > >  1 file changed, 2 insertions(+)
> > > 
> > > diff --git a/drivers/char/virtio_console.c b/drivers/char/virtio_console.c
> > > index b585b47..6ebe8f6 100644
> > > --- a/drivers/char/virtio_console.c
> > > +++ b/drivers/char/virtio_console.c
> > > @@ -1449,6 +1449,8 @@ static int add_port(struct ports_device *portdev, u32 id)
> > >  	spin_lock_init(&port->outvq_lock);
> > >  	init_waitqueue_head(&port->waitqueue);
> > >  
> > > +	virtio_device_ready(portdev->vdev);
> > > +
> > >  	/* Fill the in_vq with buffers so the host can send us data. */
> > >  	nr_added_bufs = fill_queue(port->in_vq, &port->inbuf_lock);
> > >  	if (!nr_added_bufs) {
> > 
> > Seems like probe and add_port() now both set VIRTIO_CONFIG_S_DRIVER_OK
> 
> I think we need to set this in the probe function instead, otherwise we
> fail for multiqueue (which also wants to use the control queue early).
> 
> Completely untested patch below; I can send this with proper s-o-b if
> it helps.
> 
> diff --git a/drivers/char/virtio_console.c b/drivers/char/virtio_console.c
> index bfa6400..cf7a561 100644
> --- a/drivers/char/virtio_console.c
> +++ b/drivers/char/virtio_console.c
> @@ -1449,8 +1449,6 @@ static int add_port(struct ports_device *portdev, u32 id)
>  	spin_lock_init(&port->outvq_lock);
>  	init_waitqueue_head(&port->waitqueue);
>  
> -	virtio_device_ready(portdev->vdev);
> -
>  	/* Fill the in_vq with buffers so the host can send us data. */
>  	nr_added_bufs = fill_queue(port->in_vq, &port->inbuf_lock);
>  	if (!nr_added_bufs) {
> @@ -2026,6 +2024,8 @@ static int virtcons_probe(struct virtio_device *vdev)
>  	spin_lock_init(&portdev->ports_lock);
>  	INIT_LIST_HEAD(&portdev->ports);
>  
> +	virtio_device_ready(portdev->vdev);
> +
>  	if (multiport) {
>  		unsigned int nr_added_bufs;
>  

I wanted to set DRIVER_OK as late as possible, to both reduce
the chance it can fail after DRIVER_OK and to reduce  the risk of
introducing a regression since old qemu might only start sending
interrupts after DRIVER_OK is set.

So I wanted everything completely initialized before DRIVER_OK.

You patch makes sense to me since nothing can fail,
and we won't get interrupts before we add inbufs.

Reviewed-by: Michael S. Tsirkin <mst@redhat.com>

Testig will report shortly, pls send with sob line.

-- 
MST

^ permalink raw reply	[flat|nested] 43+ messages in thread

* [PATCH] virtio_console: move early VQ enablement
  2014-10-20 13:35       ` Michael S. Tsirkin
@ 2014-10-20 13:58         ` Cornelia Huck
  2014-10-20 14:05           ` Michael S. Tsirkin
  2014-10-20 14:04         ` [PATCH v4 13/25] virtio_console: enable VQs early Michael S. Tsirkin
  1 sibling, 1 reply; 43+ messages in thread
From: Cornelia Huck @ 2014-10-20 13:58 UTC (permalink / raw)
  To: Michael S. Tsirkin, Rusty Russell
  Cc: Thomas Graf, linux-kernel, virtualization, kvm, Cornelia Huck

Commit f5866db6 (virtio_console: enable VQs early) tried to make
sure that DRIVER_OK was set when virtio_console started using its
virtqueues. Doing this in add_port(), however, means that we try
to set DRIVER_OK again when when a port is dynamically added after
the probe function is done.

Let's move virtio_device_ready() to the probe function just before
trying to use the virtqueues instead. This is fine as nothing can
fail inbetween.

Reported-by: Thomas Graf <tgraf@suug.ch>
Reviewed-by: Michael S. Tsirkin <mst@redhat.com>
Signed-off-by: Cornelia Huck <cornelia.huck@de.ibm.com>
---
 drivers/char/virtio_console.c | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/drivers/char/virtio_console.c b/drivers/char/virtio_console.c
index bfa6400..cf7a561 100644
--- a/drivers/char/virtio_console.c
+++ b/drivers/char/virtio_console.c
@@ -1449,8 +1449,6 @@ static int add_port(struct ports_device *portdev, u32 id)
 	spin_lock_init(&port->outvq_lock);
 	init_waitqueue_head(&port->waitqueue);
 
-	virtio_device_ready(portdev->vdev);
-
 	/* Fill the in_vq with buffers so the host can send us data. */
 	nr_added_bufs = fill_queue(port->in_vq, &port->inbuf_lock);
 	if (!nr_added_bufs) {
@@ -2026,6 +2024,8 @@ static int virtcons_probe(struct virtio_device *vdev)
 	spin_lock_init(&portdev->ports_lock);
 	INIT_LIST_HEAD(&portdev->ports);
 
+	virtio_device_ready(portdev->vdev);
+
 	if (multiport) {
 		unsigned int nr_added_bufs;
 
-- 
1.8.5.5


^ permalink raw reply related	[flat|nested] 43+ messages in thread

* Re: [PATCH v4 13/25] virtio_console: enable VQs early
  2014-10-20 13:35       ` Michael S. Tsirkin
  2014-10-20 13:58         ` [PATCH] virtio_console: move early VQ enablement Cornelia Huck
@ 2014-10-20 14:04         ` Michael S. Tsirkin
  1 sibling, 0 replies; 43+ messages in thread
From: Michael S. Tsirkin @ 2014-10-20 14:04 UTC (permalink / raw)
  To: Cornelia Huck
  Cc: Thomas Graf, linux-kernel, Rusty Russell, virtualization,
	linux-scsi, linux-s390, v9fs-developer, netdev, kvm, Amit Shah,
	Christian Borntraeger, David S. Miller, Paolo Bonzini,
	Arnd Bergmann, Greg Kroah-Hartman

On Mon, Oct 20, 2014 at 04:35:55PM +0300, Michael S. Tsirkin wrote:
> On Mon, Oct 20, 2014 at 02:42:23PM +0200, Cornelia Huck wrote:
> > On Mon, 20 Oct 2014 13:07:50 +0100
> > Thomas Graf <tgraf@suug.ch> wrote:
> > 
> > > On 10/13/14 at 10:50am, Michael S. Tsirkin wrote:
> > > > virtio spec requires drivers to set DRIVER_OK before using VQs.
> > > > This is set automatically after probe returns, virtio console violated this
> > > > rule by adding inbufs, which causes the VQ to be used directly within
> > > > probe.
> > > > 
> > > > To fix, call virtio_device_ready before using VQs.
> > > > 
> > > > Signed-off-by: Michael S. Tsirkin <mst@redhat.com>
> > > > ---
> > > >  drivers/char/virtio_console.c | 2 ++
> > > >  1 file changed, 2 insertions(+)
> > > > 
> > > > diff --git a/drivers/char/virtio_console.c b/drivers/char/virtio_console.c
> > > > index b585b47..6ebe8f6 100644
> > > > --- a/drivers/char/virtio_console.c
> > > > +++ b/drivers/char/virtio_console.c
> > > > @@ -1449,6 +1449,8 @@ static int add_port(struct ports_device *portdev, u32 id)
> > > >  	spin_lock_init(&port->outvq_lock);
> > > >  	init_waitqueue_head(&port->waitqueue);
> > > >  
> > > > +	virtio_device_ready(portdev->vdev);
> > > > +
> > > >  	/* Fill the in_vq with buffers so the host can send us data. */
> > > >  	nr_added_bufs = fill_queue(port->in_vq, &port->inbuf_lock);
> > > >  	if (!nr_added_bufs) {
> > > 
> > > Seems like probe and add_port() now both set VIRTIO_CONFIG_S_DRIVER_OK
> > 
> > I think we need to set this in the probe function instead, otherwise we
> > fail for multiqueue (which also wants to use the control queue early).
> > 
> > Completely untested patch below; I can send this with proper s-o-b if
> > it helps.
> > 
> > diff --git a/drivers/char/virtio_console.c b/drivers/char/virtio_console.c
> > index bfa6400..cf7a561 100644
> > --- a/drivers/char/virtio_console.c
> > +++ b/drivers/char/virtio_console.c
> > @@ -1449,8 +1449,6 @@ static int add_port(struct ports_device *portdev, u32 id)
> >  	spin_lock_init(&port->outvq_lock);
> >  	init_waitqueue_head(&port->waitqueue);
> >  
> > -	virtio_device_ready(portdev->vdev);
> > -
> >  	/* Fill the in_vq with buffers so the host can send us data. */
> >  	nr_added_bufs = fill_queue(port->in_vq, &port->inbuf_lock);
> >  	if (!nr_added_bufs) {
> > @@ -2026,6 +2024,8 @@ static int virtcons_probe(struct virtio_device *vdev)
> >  	spin_lock_init(&portdev->ports_lock);
> >  	INIT_LIST_HEAD(&portdev->ports);
> >  
> > +	virtio_device_ready(portdev->vdev);
> > +
> >  	if (multiport) {
> >  		unsigned int nr_added_bufs;
> >  
> 
> I wanted to set DRIVER_OK as late as possible, to both reduce
> the chance it can fail after DRIVER_OK and to reduce  the risk of
> introducing a regression since old qemu might only start sending
> interrupts after DRIVER_OK is set.
> 
> So I wanted everything completely initialized before DRIVER_OK.
> 
> You patch makes sense to me since nothing can fail,
> and we won't get interrupts before we add inbufs.
> 
> Reviewed-by: Michael S. Tsirkin <mst@redhat.com>
> 
> Testig will report shortly, pls send with sob line.

Sure enough, this helps:

Tested-by: Michael S. Tsirkin <mst@redhat.com>
Acked-by: Michael S. Tsirkin <mst@redhat.com>

Pls repost as a top-level patch.

> -- 
> MST

^ permalink raw reply	[flat|nested] 43+ messages in thread

* Re: [PATCH] virtio_console: move early VQ enablement
  2014-10-20 13:58         ` [PATCH] virtio_console: move early VQ enablement Cornelia Huck
@ 2014-10-20 14:05           ` Michael S. Tsirkin
  2014-10-20 17:09             ` Josh Boyer
  0 siblings, 1 reply; 43+ messages in thread
From: Michael S. Tsirkin @ 2014-10-20 14:05 UTC (permalink / raw)
  To: Cornelia Huck
  Cc: Rusty Russell, Thomas Graf, linux-kernel, virtualization, kvm

On Mon, Oct 20, 2014 at 03:58:49PM +0200, Cornelia Huck wrote:
> Commit f5866db6 (virtio_console: enable VQs early) tried to make
> sure that DRIVER_OK was set when virtio_console started using its
> virtqueues. Doing this in add_port(), however, means that we try
> to set DRIVER_OK again when when a port is dynamically added after
> the probe function is done.
> 
> Let's move virtio_device_ready() to the probe function just before
> trying to use the virtqueues instead. This is fine as nothing can
> fail inbetween.
> 
> Reported-by: Thomas Graf <tgraf@suug.ch>
> Reviewed-by: Michael S. Tsirkin <mst@redhat.com>
> Signed-off-by: Cornelia Huck <cornelia.huck@de.ibm.com>

Thanks!

Acked-by: Michael S. Tsirkin <mst@redhat.com>
Tested-by: Michael S. Tsirkin <mst@redhat.com>


> ---
>  drivers/char/virtio_console.c | 4 ++--
>  1 file changed, 2 insertions(+), 2 deletions(-)
> 
> diff --git a/drivers/char/virtio_console.c b/drivers/char/virtio_console.c
> index bfa6400..cf7a561 100644
> --- a/drivers/char/virtio_console.c
> +++ b/drivers/char/virtio_console.c
> @@ -1449,8 +1449,6 @@ static int add_port(struct ports_device *portdev, u32 id)
>  	spin_lock_init(&port->outvq_lock);
>  	init_waitqueue_head(&port->waitqueue);
>  
> -	virtio_device_ready(portdev->vdev);
> -
>  	/* Fill the in_vq with buffers so the host can send us data. */
>  	nr_added_bufs = fill_queue(port->in_vq, &port->inbuf_lock);
>  	if (!nr_added_bufs) {
> @@ -2026,6 +2024,8 @@ static int virtcons_probe(struct virtio_device *vdev)
>  	spin_lock_init(&portdev->ports_lock);
>  	INIT_LIST_HEAD(&portdev->ports);
>  
> +	virtio_device_ready(portdev->vdev);
> +
>  	if (multiport) {
>  		unsigned int nr_added_bufs;
>  
> -- 
> 1.8.5.5

^ permalink raw reply	[flat|nested] 43+ messages in thread

* Re: [PATCH] virtio_console: move early VQ enablement
  2014-10-20 14:05           ` Michael S. Tsirkin
@ 2014-10-20 17:09             ` Josh Boyer
  2014-11-11  2:24               ` Dave Airlie
  0 siblings, 1 reply; 43+ messages in thread
From: Josh Boyer @ 2014-10-20 17:09 UTC (permalink / raw)
  To: Michael S. Tsirkin
  Cc: Cornelia Huck, Rusty Russell, Thomas Graf,
	Linux-Kernel@Vger. Kernel. Org, virtualization, KVM list

On Mon, Oct 20, 2014 at 10:05 AM, Michael S. Tsirkin <mst@redhat.com> wrote:
> On Mon, Oct 20, 2014 at 03:58:49PM +0200, Cornelia Huck wrote:
>> Commit f5866db6 (virtio_console: enable VQs early) tried to make
>> sure that DRIVER_OK was set when virtio_console started using its
>> virtqueues. Doing this in add_port(), however, means that we try
>> to set DRIVER_OK again when when a port is dynamically added after
>> the probe function is done.
>>
>> Let's move virtio_device_ready() to the probe function just before
>> trying to use the virtqueues instead. This is fine as nothing can
>> fail inbetween.
>>
>> Reported-by: Thomas Graf <tgraf@suug.ch>
>> Reviewed-by: Michael S. Tsirkin <mst@redhat.com>
>> Signed-off-by: Cornelia Huck <cornelia.huck@de.ibm.com>
>
> Thanks!
>
> Acked-by: Michael S. Tsirkin <mst@redhat.com>
> Tested-by: Michael S. Tsirkin <mst@redhat.com>

This fixed my KVM guest boot issue with 3.18-rc1.  Thanks for such a quick fix.

Tested-by: Josh Boyer <jwboyer@fedoraproject.org>

josh

>> ---
>>  drivers/char/virtio_console.c | 4 ++--
>>  1 file changed, 2 insertions(+), 2 deletions(-)
>>
>> diff --git a/drivers/char/virtio_console.c b/drivers/char/virtio_console.c
>> index bfa6400..cf7a561 100644
>> --- a/drivers/char/virtio_console.c
>> +++ b/drivers/char/virtio_console.c
>> @@ -1449,8 +1449,6 @@ static int add_port(struct ports_device *portdev, u32 id)
>>       spin_lock_init(&port->outvq_lock);
>>       init_waitqueue_head(&port->waitqueue);
>>
>> -     virtio_device_ready(portdev->vdev);
>> -
>>       /* Fill the in_vq with buffers so the host can send us data. */
>>       nr_added_bufs = fill_queue(port->in_vq, &port->inbuf_lock);
>>       if (!nr_added_bufs) {
>> @@ -2026,6 +2024,8 @@ static int virtcons_probe(struct virtio_device *vdev)
>>       spin_lock_init(&portdev->ports_lock);
>>       INIT_LIST_HEAD(&portdev->ports);
>>
>> +     virtio_device_ready(portdev->vdev);
>> +
>>       if (multiport) {
>>               unsigned int nr_added_bufs;
>>
>> --
>> 1.8.5.5
> --
> To unsubscribe from this list: send the line "unsubscribe linux-kernel" in
> the body of a message to majordomo@vger.kernel.org
> More majordomo info at  http://vger.kernel.org/majordomo-info.html
> Please read the FAQ at  http://www.tux.org/lkml/

^ permalink raw reply	[flat|nested] 43+ messages in thread

* Re: [PATCH v4 10/25] virtio: add API to enable VQs early
  2014-10-13  7:50 ` [PATCH v4 10/25] virtio: add API to enable VQs early Michael S. Tsirkin
@ 2014-11-11  0:45   ` Andy Grover
  2014-11-11  6:15     ` Michael S. Tsirkin
  0 siblings, 1 reply; 43+ messages in thread
From: Andy Grover @ 2014-11-11  0:45 UTC (permalink / raw)
  To: Michael S. Tsirkin, linux-kernel
  Cc: Rusty Russell, virtualization, linux-scsi, linux-s390,
	v9fs-developer, netdev, kvm, Amit Shah, Cornelia Huck,
	Christian Borntraeger, David S. Miller, Paolo Bonzini

On 10/13/2014 12:50 AM, Michael S. Tsirkin wrote:
> virtio spec 0.9.X requires DRIVER_OK to be set before
> VQs are used, but some drivers use VQs before probe
> function returns.
> Since DRIVER_OK is set after probe, this violates the spec.
>
> Even though under virtio 1.0 transitional devices support this
> behaviour, we want to make it possible for those early callers to become
> spec compliant and eventually support non-transitional devices.
>
> Add API for drivers to call before using VQs.
>
> Sets DRIVER_OK internally.
>
> Signed-off-by: Michael S. Tsirkin <mst@redhat.com>
> Reviewed-by: Cornelia Huck <cornelia.huck@de.ibm.com>
> ---
>   include/linux/virtio_config.h | 17 +++++++++++++++++
>   1 file changed, 17 insertions(+)
>
> diff --git a/include/linux/virtio_config.h b/include/linux/virtio_config.h
> index e8f8f71..e36403b 100644
> --- a/include/linux/virtio_config.h
> +++ b/include/linux/virtio_config.h
> @@ -109,6 +109,23 @@ struct virtqueue *virtio_find_single_vq(struct virtio_device *vdev,
>   	return vq;
>   }
>
> +/**
> + * virtio_device_ready - enable vq use in probe function
> + * @vdev: the device
> + *
> + * Driver must call this to use vqs in the probe function.
> + *
> + * Note: vqs are enabled automatically after probe returns.
> + */
> +static inline
> +void virtio_device_ready(struct virtio_device *dev)
> +{
> +	unsigned status = dev->config->get_status(dev);
> +
> +	BUG_ON(status & VIRTIO_CONFIG_S_DRIVER_OK);
> +	dev->config->set_status(dev, status | VIRTIO_CONFIG_S_DRIVER_OK);
> +}

Getting a BUG when booting via KVM, host Fedora 20, guest Fedora 20.

my config is at:

https://fedorapeople.org/~grover/config-20141110



[    0.828494] ------------[ cut here ]------------
[    0.829039] kernel BUG at 
/home/agrover/git/kernel/include/linux/virtio_config.h:125!
[    0.831266] invalid opcode: 0000 [#1] SMP DEBUG_PAGEALLOC
[    0.831266] Modules linked in:
[    0.831266] CPU: 1 PID: 30 Comm: kworker/1:1 Not tainted 3.18.0-rc4 #120
[    0.831266] Hardware name: Bochs Bochs, BIOS Bochs 01/01/2011
[    0.831266] Workqueue: events control_work_handler
[    0.831266] task: ffff88003cd98000 ti: ffff88003cd94000 task.ti: 
ffff88003cd94000
[    0.831266] RIP: 0010:[<ffffffff81445004>]  [<ffffffff81445004>] 
add_port+0x264/0x410
[    0.831266] RSP: 0000:ffff88003cd97c78  EFLAGS: 00010202
[    0.831266] RAX: 0000000000000007 RBX: ffff88003c58c400 RCX: 
0000000000000001
[    0.831266] RDX: 000000000000c132 RSI: ffffffff81a955e9 RDI: 
000000000001c132
[    0.831266] RBP: ffff88003cd97cc8 R08: 0000000000000000 R09: 
0000000000000000
[    0.831266] R10: 0000000000000001 R11: 0000000000000000 R12: 
ffff88003c58be00
[    0.831266] R13: 0000000000000001 R14: ffff8800395ca800 R15: 
ffff88003c58c420
[    0.831266] FS:  0000000000000000(0000) GS:ffff88003fa00000(0000) 
knlGS:0000000000000000
[    0.831266] CS:  0010 DS: 0000 ES: 0000 CR0: 000000008005003b
[    0.831266] CR2: 0000000000000000 CR3: 0000000001c11000 CR4: 
00000000000006e0
[    0.831266] DR0: 0000000000000000 DR1: 0000000000000000 DR2: 
0000000000000000
[    0.831266] DR3: 0000000000000000 DR6: 00000000fffe0ff0 DR7: 
0000000000000400
[    0.831266] Stack:
[    0.831266]  ffff880000000001 0000000000000292 0000000000000000 
0000000000000001
[    0.831266]  ffff88003cd97cc8 ffff88003dfa8a20 ffff88003c58beb8 
ffff88003c58be10
[    0.831266]  ffff8800395a2000 0000000000000000 ffff88003cd97d38 
ffffffff8144531a
[    0.831266] Call Trace:
[    0.831266]  [<ffffffff8144531a>] control_work_handler+0x16a/0x3c0
[    0.831266]  [<ffffffff8108b0c8>] ? process_one_work+0x208/0x500
[    0.831266]  [<ffffffff8108b16c>] process_one_work+0x2ac/0x500
[    0.831266]  [<ffffffff8108b0c8>] ? process_one_work+0x208/0x500
[    0.831266]  [<ffffffff8108b68e>] worker_thread+0x2ce/0x4e0
[    0.831266]  [<ffffffff8108b3c0>] ? process_one_work+0x500/0x500
[    0.831266]  [<ffffffff81090b28>] kthread+0xf8/0x100
[    0.831266]  [<ffffffff810bad7d>] ? trace_hardirqs_on+0xd/0x10
[    0.831266]  [<ffffffff81090a30>] ? kthread_stop+0x140/0x140
[    0.831266]  [<ffffffff816ea92c>] ret_from_fork+0x7c/0xb0
[    0.831266]  [<ffffffff81090a30>] ? kthread_stop+0x140/0x140
[    0.831266] Code: c7 c2 48 31 01 83 48 c7 c6 e9 55 a9 81 e8 55 b4 c6 
ff 4d 8b b4 24 58 01 00 00 49 8b 86 e8 04 00 00 4c 89 f7 ff 50 10 a8 04 
74 0c <0f> 0b 66 2e 0f 1f 84 00 00 00 00 00 49 8b 96 e8 04 00 00 83 c8
[    0.831266] RIP  [<ffffffff81445004>] add_port+0x264/0x410
[    0.831266]  RSP <ffff88003cd97c78>
[    0.878202] ---[ end trace f98fbb172cc7bbf4 ]---

Thanks -- Andy


^ permalink raw reply	[flat|nested] 43+ messages in thread

* Re: [PATCH] virtio_console: move early VQ enablement
  2014-10-20 17:09             ` Josh Boyer
@ 2014-11-11  2:24               ` Dave Airlie
  0 siblings, 0 replies; 43+ messages in thread
From: Dave Airlie @ 2014-11-11  2:24 UTC (permalink / raw)
  To: Josh Boyer
  Cc: Michael S. Tsirkin, Cornelia Huck, Rusty Russell, Thomas Graf,
	Linux-Kernel@Vger. Kernel. Org, virtualization, KVM list

On 21 October 2014 03:09, Josh Boyer <jwboyer@fedoraproject.org> wrote:
> On Mon, Oct 20, 2014 at 10:05 AM, Michael S. Tsirkin <mst@redhat.com> wrote:
>> On Mon, Oct 20, 2014 at 03:58:49PM +0200, Cornelia Huck wrote:
>>> Commit f5866db6 (virtio_console: enable VQs early) tried to make
>>> sure that DRIVER_OK was set when virtio_console started using its
>>> virtqueues. Doing this in add_port(), however, means that we try
>>> to set DRIVER_OK again when when a port is dynamically added after
>>> the probe function is done.
>>>
>>> Let's move virtio_device_ready() to the probe function just before
>>> trying to use the virtqueues instead. This is fine as nothing can
>>> fail inbetween.
>>>
>>> Reported-by: Thomas Graf <tgraf@suug.ch>
>>> Reviewed-by: Michael S. Tsirkin <mst@redhat.com>
>>> Signed-off-by: Cornelia Huck <cornelia.huck@de.ibm.com>
>>
>> Thanks!
>>
>> Acked-by: Michael S. Tsirkin <mst@redhat.com>
>> Tested-by: Michael S. Tsirkin <mst@redhat.com>
>
> This fixed my KVM guest boot issue with 3.18-rc1.  Thanks for such a quick fix.
>
> Tested-by: Josh Boyer <jwboyer@fedoraproject.org>

ping So who's merging this? Rusty?

still happens in -rc4.

Dave.

^ permalink raw reply	[flat|nested] 43+ messages in thread

* Re: [PATCH v4 10/25] virtio: add API to enable VQs early
  2014-11-11  0:45   ` Andy Grover
@ 2014-11-11  6:15     ` Michael S. Tsirkin
  0 siblings, 0 replies; 43+ messages in thread
From: Michael S. Tsirkin @ 2014-11-11  6:15 UTC (permalink / raw)
  To: Andy Grover
  Cc: linux-kernel, Rusty Russell, virtualization, linux-scsi,
	linux-s390, v9fs-developer, netdev, kvm, Amit Shah,
	Cornelia Huck, Christian Borntraeger, David S. Miller,
	Paolo Bonzini

On Mon, Nov 10, 2014 at 04:45:09PM -0800, Andy Grover wrote:
> On 10/13/2014 12:50 AM, Michael S. Tsirkin wrote:
> >virtio spec 0.9.X requires DRIVER_OK to be set before
> >VQs are used, but some drivers use VQs before probe
> >function returns.
> >Since DRIVER_OK is set after probe, this violates the spec.
> >
> >Even though under virtio 1.0 transitional devices support this
> >behaviour, we want to make it possible for those early callers to become
> >spec compliant and eventually support non-transitional devices.
> >
> >Add API for drivers to call before using VQs.
> >
> >Sets DRIVER_OK internally.
> >
> >Signed-off-by: Michael S. Tsirkin <mst@redhat.com>
> >Reviewed-by: Cornelia Huck <cornelia.huck@de.ibm.com>
> >---
> >  include/linux/virtio_config.h | 17 +++++++++++++++++
> >  1 file changed, 17 insertions(+)
> >
> >diff --git a/include/linux/virtio_config.h b/include/linux/virtio_config.h
> >index e8f8f71..e36403b 100644
> >--- a/include/linux/virtio_config.h
> >+++ b/include/linux/virtio_config.h
> >@@ -109,6 +109,23 @@ struct virtqueue *virtio_find_single_vq(struct virtio_device *vdev,
> >  	return vq;
> >  }
> >
> >+/**
> >+ * virtio_device_ready - enable vq use in probe function
> >+ * @vdev: the device
> >+ *
> >+ * Driver must call this to use vqs in the probe function.
> >+ *
> >+ * Note: vqs are enabled automatically after probe returns.
> >+ */
> >+static inline
> >+void virtio_device_ready(struct virtio_device *dev)
> >+{
> >+	unsigned status = dev->config->get_status(dev);
> >+
> >+	BUG_ON(status & VIRTIO_CONFIG_S_DRIVER_OK);
> >+	dev->config->set_status(dev, status | VIRTIO_CONFIG_S_DRIVER_OK);
> >+}
> 
> Getting a BUG when booting via KVM, host Fedora 20, guest Fedora 20.
> 
> my config is at:
> 
> https://fedorapeople.org/~grover/config-20141110
> 

The fix is here:
http://article.gmane.org/gmane.linux.kernel.virtualization/23324/raw

I'm surprised it's not merged yet.

Rusty, could you pick it up please?


> 
> [    0.828494] ------------[ cut here ]------------
> [    0.829039] kernel BUG at
> /home/agrover/git/kernel/include/linux/virtio_config.h:125!
> [    0.831266] invalid opcode: 0000 [#1] SMP DEBUG_PAGEALLOC
> [    0.831266] Modules linked in:
> [    0.831266] CPU: 1 PID: 30 Comm: kworker/1:1 Not tainted 3.18.0-rc4 #120
> [    0.831266] Hardware name: Bochs Bochs, BIOS Bochs 01/01/2011
> [    0.831266] Workqueue: events control_work_handler
> [    0.831266] task: ffff88003cd98000 ti: ffff88003cd94000 task.ti:
> ffff88003cd94000
> [    0.831266] RIP: 0010:[<ffffffff81445004>]  [<ffffffff81445004>]
> add_port+0x264/0x410
> [    0.831266] RSP: 0000:ffff88003cd97c78  EFLAGS: 00010202
> [    0.831266] RAX: 0000000000000007 RBX: ffff88003c58c400 RCX:
> 0000000000000001
> [    0.831266] RDX: 000000000000c132 RSI: ffffffff81a955e9 RDI:
> 000000000001c132
> [    0.831266] RBP: ffff88003cd97cc8 R08: 0000000000000000 R09:
> 0000000000000000
> [    0.831266] R10: 0000000000000001 R11: 0000000000000000 R12:
> ffff88003c58be00
> [    0.831266] R13: 0000000000000001 R14: ffff8800395ca800 R15:
> ffff88003c58c420
> [    0.831266] FS:  0000000000000000(0000) GS:ffff88003fa00000(0000)
> knlGS:0000000000000000
> [    0.831266] CS:  0010 DS: 0000 ES: 0000 CR0: 000000008005003b
> [    0.831266] CR2: 0000000000000000 CR3: 0000000001c11000 CR4:
> 00000000000006e0
> [    0.831266] DR0: 0000000000000000 DR1: 0000000000000000 DR2:
> 0000000000000000
> [    0.831266] DR3: 0000000000000000 DR6: 00000000fffe0ff0 DR7:
> 0000000000000400
> [    0.831266] Stack:
> [    0.831266]  ffff880000000001 0000000000000292 0000000000000000
> 0000000000000001
> [    0.831266]  ffff88003cd97cc8 ffff88003dfa8a20 ffff88003c58beb8
> ffff88003c58be10
> [    0.831266]  ffff8800395a2000 0000000000000000 ffff88003cd97d38
> ffffffff8144531a
> [    0.831266] Call Trace:
> [    0.831266]  [<ffffffff8144531a>] control_work_handler+0x16a/0x3c0
> [    0.831266]  [<ffffffff8108b0c8>] ? process_one_work+0x208/0x500
> [    0.831266]  [<ffffffff8108b16c>] process_one_work+0x2ac/0x500
> [    0.831266]  [<ffffffff8108b0c8>] ? process_one_work+0x208/0x500
> [    0.831266]  [<ffffffff8108b68e>] worker_thread+0x2ce/0x4e0
> [    0.831266]  [<ffffffff8108b3c0>] ? process_one_work+0x500/0x500
> [    0.831266]  [<ffffffff81090b28>] kthread+0xf8/0x100
> [    0.831266]  [<ffffffff810bad7d>] ? trace_hardirqs_on+0xd/0x10
> [    0.831266]  [<ffffffff81090a30>] ? kthread_stop+0x140/0x140
> [    0.831266]  [<ffffffff816ea92c>] ret_from_fork+0x7c/0xb0
> [    0.831266]  [<ffffffff81090a30>] ? kthread_stop+0x140/0x140
> [    0.831266] Code: c7 c2 48 31 01 83 48 c7 c6 e9 55 a9 81 e8 55 b4 c6 ff
> 4d 8b b4 24 58 01 00 00 49 8b 86 e8 04 00 00 4c 89 f7 ff 50 10 a8 04 74 0c
> <0f> 0b 66 2e 0f 1f 84 00 00 00 00 00 49 8b 96 e8 04 00 00 83 c8
> [    0.831266] RIP  [<ffffffff81445004>] add_port+0x264/0x410
> [    0.831266]  RSP <ffff88003cd97c78>
> [    0.878202] ---[ end trace f98fbb172cc7bbf4 ]---
> 
> Thanks -- Andy

^ permalink raw reply	[flat|nested] 43+ messages in thread

end of thread, other threads:[~2014-11-11  6:15 UTC | newest]

Thread overview: 43+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2014-10-13  7:48 [PATCH v4 00/25] virtio: fix spec compliance issues Michael S. Tsirkin
2014-10-13  7:48 ` [PATCH v4 01/25] virtio_pci: fix virtio spec compliance on restore Michael S. Tsirkin
2014-10-13  7:48 ` [PATCH v4 02/25] virtio: unify config_changed handling Michael S. Tsirkin
2014-10-13  7:48 ` [PATCH v4 03/25] virtio-pci: move freeze/restore to virtio core Michael S. Tsirkin
2014-10-15  7:05   ` Paul Bolle
2014-10-13  7:50 ` [PATCH v4 04/25] virtio: defer config changed notifications Michael S. Tsirkin
2014-10-14  0:31   ` Rusty Russell
2014-10-14  8:59     ` Michael S. Tsirkin
2014-10-13  7:50 ` [PATCH v4 05/25] virtio_blk: drop config_enable Michael S. Tsirkin
2014-10-13  7:50 ` [PATCH v4 06/25] virtio-blk: drop config_mutex Michael S. Tsirkin
2014-10-13  7:50 ` [PATCH v4 07/25] virtio_net: drop config_enable Michael S. Tsirkin
2014-10-13  7:50 ` [PATCH v4 08/25] virtio-net: drop config_mutex Michael S. Tsirkin
2014-10-13  7:50 ` [PATCH v4 09/25] virtio_net: minor cleanup Michael S. Tsirkin
2014-10-13  7:50 ` [PATCH v4 10/25] virtio: add API to enable VQs early Michael S. Tsirkin
2014-11-11  0:45   ` Andy Grover
2014-11-11  6:15     ` Michael S. Tsirkin
2014-10-13  7:50 ` [PATCH v4 11/25] virtio_net: " Michael S. Tsirkin
2014-10-13  7:50 ` [PATCH v4 12/25] virtio_blk: " Michael S. Tsirkin
2014-10-13  7:50 ` [PATCH v4 13/25] virtio_console: " Michael S. Tsirkin
2014-10-20 12:07   ` Thomas Graf
2014-10-20 12:42     ` Cornelia Huck
2014-10-20 13:10       ` Thomas Graf
2014-10-20 13:35       ` Michael S. Tsirkin
2014-10-20 13:58         ` [PATCH] virtio_console: move early VQ enablement Cornelia Huck
2014-10-20 14:05           ` Michael S. Tsirkin
2014-10-20 17:09             ` Josh Boyer
2014-11-11  2:24               ` Dave Airlie
2014-10-20 14:04         ` [PATCH v4 13/25] virtio_console: enable VQs early Michael S. Tsirkin
2014-10-20 13:10     ` Michael S. Tsirkin
2014-10-20 13:12       ` Thomas Graf
2014-10-20 13:14       ` Michael S. Tsirkin
2014-10-13  7:50 ` [PATCH v4 14/25] 9p/trans_virtio: " Michael S. Tsirkin
2014-10-13  7:50 ` [PATCH v4 15/25] virtio_net: fix use after free on allocation failure Michael S. Tsirkin
2014-10-13  7:51 ` [PATCH v4 16/25] virtio_scsi: move kick event out from virtscsi_init Michael S. Tsirkin
2014-10-13  7:51 ` [PATCH v4 17/25] virtio_blk: enable VQs early on restore Michael S. Tsirkin
2014-10-13  7:51 ` [PATCH v4 18/25] virtio_scsi: " Michael S. Tsirkin
2014-10-13  7:51 ` [PATCH v4 19/25] virtio_console: " Michael S. Tsirkin
2014-10-13  7:51 ` [PATCH v4 20/25] virtio_net: " Michael S. Tsirkin
2014-10-13  7:51 ` [PATCH v4 21/25] virito_scsi: use freezable WQ for events Michael S. Tsirkin
2014-10-13  7:51 ` [PATCH v4 22/25] virtio_scsi: fix race on device removal Michael S. Tsirkin
2014-10-13  7:51 ` [PATCH v4 23/25] virtio_balloon: enable VQs early on restore Michael S. Tsirkin
2014-10-13  7:51 ` [PATCH v4 24/25] virtio_scsi: drop scan callback Michael S. Tsirkin
2014-10-13  7:51 ` [PATCH v4 25/25] virtio-rng: refactor probe error handling Michael S. Tsirkin

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).