From patchwork Thu May 7 14:11:39 2009 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: "Michael S. Tsirkin" X-Patchwork-Id: 22345 Received: from vger.kernel.org (vger.kernel.org [209.132.176.167]) by demeter.kernel.org (8.14.2/8.14.2) with ESMTP id n47EEkXM015396 for ; Thu, 7 May 2009 14:14:46 GMT Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1757035AbZEGONv (ORCPT ); Thu, 7 May 2009 10:13:51 -0400 Received: (majordomo@vger.kernel.org) by vger.kernel.org id S1755980AbZEGONu (ORCPT ); Thu, 7 May 2009 10:13:50 -0400 Received: from mx2.redhat.com ([66.187.237.31]:43229 "EHLO mx2.redhat.com" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1759242AbZEGONt (ORCPT ); Thu, 7 May 2009 10:13:49 -0400 Received: from int-mx2.corp.redhat.com (int-mx2.corp.redhat.com [172.16.27.26]) by mx2.redhat.com (8.13.8/8.13.8) with ESMTP id n47ECgfM028986; Thu, 7 May 2009 10:12:42 -0400 Received: from ns3.rdu.redhat.com (ns3.rdu.redhat.com [10.11.255.199]) by int-mx2.corp.redhat.com (8.13.1/8.13.1) with ESMTP id n47ECeFg000790; Thu, 7 May 2009 10:12:41 -0400 Received: from redhat.com (dhcp-0-223.tlv.redhat.com [10.35.0.223]) by ns3.rdu.redhat.com (8.13.8/8.13.8) with ESMTP id n47ECc8h001167; Thu, 7 May 2009 10:12:39 -0400 Date: Thu, 7 May 2009 17:11:39 +0300 From: "Michael S. Tsirkin" To: Christian Borntraeger Cc: Rusty Russell , virtualization@lists.linux-foundation.org, Anthony Liguori , kvm@vger.kernel.org, avi@redhat.com Subject: [PATCH 2/3] virtio_pci: split up vp_interrupt Message-ID: <20090507141139.GA1542@redhat.com> References: MIME-Version: 1.0 Content-Disposition: inline In-Reply-To: User-Agent: Mutt/1.5.18 (2008-05-17) X-Scanned-By: MIMEDefang 2.58 on 172.16.27.26 Sender: kvm-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: kvm@vger.kernel.org This reorganizes virtio-pci code in vp_interrupt slightly, so that it's easier to add per-vq MSI support on top. Signed-off-by: Michael S. Tsirkin --- drivers/virtio/virtio_pci.c | 45 +++++++++++++++++++++++++++++++++--------- 1 files changed, 35 insertions(+), 10 deletions(-) diff --git a/drivers/virtio/virtio_pci.c b/drivers/virtio/virtio_pci.c index 3671c42..f7b79a2 100644 --- a/drivers/virtio/virtio_pci.c +++ b/drivers/virtio/virtio_pci.c @@ -164,6 +164,37 @@ static void vp_notify(struct virtqueue *vq) iowrite16(info->queue_index, vp_dev->ioaddr + VIRTIO_PCI_QUEUE_NOTIFY); } +/* Handle a configuration change: Tell driver if it wants to know. */ +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); + return IRQ_HANDLED; +} + +/* Notify all virtqueues on an interrupt. */ +static irqreturn_t vp_vring_interrupt(int irq, void *opaque) +{ + struct virtio_pci_device *vp_dev = opaque; + struct virtio_pci_vq_info *info; + irqreturn_t ret = IRQ_NONE; + unsigned long flags; + + spin_lock_irqsave(&vp_dev->lock, flags); + list_for_each_entry(info, &vp_dev->virtqueues, node) { + if (vring_interrupt(irq, info->vq) == IRQ_HANDLED) + ret = IRQ_HANDLED; + } + spin_unlock_irqrestore(&vp_dev->lock, flags); + + return ret; +} + /* A small wrapper to also acknowledge the interrupt when it's handled. * I really need an EIO hook for the vring so I can ack the interrupt once we * know that we'll be handling the IRQ but before we invoke the callback since @@ -173,9 +204,6 @@ static void vp_notify(struct virtqueue *vq) static irqreturn_t vp_interrupt(int irq, void *opaque) { struct virtio_pci_device *vp_dev = opaque; - struct virtio_pci_vq_info *info; - irqreturn_t ret = IRQ_NONE; - unsigned long flags; u8 isr; /* reading the ISR has the effect of also clearing it so it's very @@ -187,14 +215,11 @@ static irqreturn_t vp_interrupt(int irq, void *opaque) return IRQ_NONE; /* Configuration change? Tell driver if it wants to know. */ - if (isr & VIRTIO_PCI_ISR_CONFIG) { - struct virtio_driver *drv; - drv = container_of(vp_dev->vdev.dev.driver, - struct virtio_driver, driver); + if (isr & VIRTIO_PCI_ISR_CONFIG) + vp_config_changed(irq, opaque); - if (drv && drv->config_changed) - drv->config_changed(&vp_dev->vdev); - } + return vp_vring_interrupt(irq, opaque); +} spin_lock_irqsave(&vp_dev->lock, flags); list_for_each_entry(info, &vp_dev->virtqueues, node) {