On Thu, 2017-03-30 at 05:10 +0200, Mike Galbraith wrote: > WRT spin, you should need do nothing more than boot with threadirqs, > that's 100% repeatable here in absolutely virgin source.
No idea why virtqueue_get_buf() in __send_control_msg() fails forever with threadirqs, but marking that vq as being busted (it clearly is) results in one gripe, and a vbox that seemingly cares not one whit that something went missing. CONFIG_DEBUG_SHIRQ OTOH notices, mutters something that sounds like "idiot" when I hibernate the thing ;-) diff --git a/drivers/char/virtio_console.c b/drivers/char/virtio_console.c index e9b7e0b3cabe..831406dae1cb 100644 --- a/drivers/char/virtio_console.c +++ b/drivers/char/virtio_console.c @@ -567,6 +567,7 @@ static ssize_t __send_control_msg(struct ports_device *portdev, u32 port_id, struct scatterlist sg[1]; struct virtqueue *vq; unsigned int len; + unsigned long deadline = jiffies+1; if (!use_multiport(portdev)) return 0; @@ -583,9 +584,13 @@ static ssize_t __send_control_msg(struct ports_device *portdev, u32 port_id, if (virtqueue_add_outbuf(vq, sg, 1, &portdev->cpkt, GFP_ATOMIC) == 0) { virtqueue_kick(vq); - while (!virtqueue_get_buf(vq, &len) - && !virtqueue_is_broken(vq)) + while (!virtqueue_get_buf(vq, &len) && !virtqueue_is_broken(vq)) { cpu_relax(); + if (time_after(jiffies, deadline)) { + trace_printk("Aw crap, I'm stuck.. breaking device\n"); + virtio_break_device(portdev->vdev); + } + } } spin_unlock(&portdev->c_ovq_lock);