From patchwork Fri Nov 15 20:01:07 2019 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Stewart Hildebrand X-Patchwork-Id: 11247071 Return-Path: Received: from mail.kernel.org (pdx-korg-mail-1.web.codeaurora.org [172.30.200.123]) by pdx-korg-patchwork-2.web.codeaurora.org (Postfix) with ESMTP id C7D886C1 for ; Fri, 15 Nov 2019 20:02:53 +0000 (UTC) Received: from lists.xenproject.org (lists.xenproject.org [192.237.175.120]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by mail.kernel.org (Postfix) with ESMTPS id ADE2220733 for ; Fri, 15 Nov 2019 20:02:53 +0000 (UTC) DMARC-Filter: OpenDMARC Filter v1.3.2 mail.kernel.org ADE2220733 Authentication-Results: mail.kernel.org; dmarc=none (p=none dis=none) header.from=dornerworks.com Authentication-Results: mail.kernel.org; spf=none smtp.mailfrom=xen-devel-bounces@lists.xenproject.org Received: from localhost ([127.0.0.1] helo=lists.xenproject.org) by lists.xenproject.org with esmtp (Exim 4.89) (envelope-from ) id 1iVhmk-0005Zu-1O; Fri, 15 Nov 2019 20:01:38 +0000 Received: from us1-rack-iad1.inumbo.com ([172.99.69.81]) by lists.xenproject.org with esmtp (Exim 4.89) (envelope-from ) id 1iVhmj-0005Zg-CW for xen-devel@lists.xenproject.org; Fri, 15 Nov 2019 20:01:37 +0000 X-Inumbo-ID: b3d339d2-07e2-11ea-adbe-bc764e2007e4 Received: from webmail.dornerworks.com (unknown [12.207.209.150]) by us1-rack-iad1.inumbo.com (Halon) with ESMTP id b3d339d2-07e2-11ea-adbe-bc764e2007e4; Fri, 15 Nov 2019 20:01:25 +0000 (UTC) From: Stewart Hildebrand To: Date: Fri, 15 Nov 2019 15:01:07 -0500 Message-ID: <20191115200115.44890-4-stewart.hildebrand@dornerworks.com> X-Mailer: git-send-email 2.24.0 In-Reply-To: <20191115200115.44890-1-stewart.hildebrand@dornerworks.com> References: <20191115200115.44890-1-stewart.hildebrand@dornerworks.com> MIME-Version: 1.0 X-Originating-IP: [172.27.14.58] X-ClientProxiedBy: Mcbain.dw.local (172.27.1.45) To Mcbain.dw.local (172.27.1.45) X-spam-status: No, score=-2.9 required=3.5 tests=ALL_TRUSTED, BAYES_00, MAILSHELL_SCORE_10_69 X-Spam-Flag: NO Subject: [Xen-devel] [XEN PATCH v3 03/11] xen: arm: Refactor route_irq_to_guest X-BeenThere: xen-devel@lists.xenproject.org X-Mailman-Version: 2.1.23 Precedence: list List-Id: Xen developer discussion List-Unsubscribe: , List-Post: List-Help: List-Subscribe: , Cc: Volodymyr Babchuk , Stefano Stabellini , Julien Grall , Ian Campbell Errors-To: xen-devel-bounces@lists.xenproject.org Sender: "Xen-devel" From: Ian Campbell Split out the bit which allocates the struct irqaction and calls __setup_irq into a new function (setup_guest_irq). I'm going to want to call this a second time in a subsequent patch. Note that the action is now allocated and initialised with the desc lock held (since it is taken by the caller). I don't think this is an issue (and avoiding this would make things more complex) Signed-off-by: Ian Campbell Signed-off-by: Stewart Hildebrand --- v2: New patch (maybe, it's been a while...) v3: Rebase + trivial fixups --- Note: I have not given much thought regarding Julien's comment in [1] [1] https://lists.xenproject.org/archives/html/xen-devel/2015-11/msg01041.html --- xen/arch/arm/irq.c | 108 +++++++++++++++++++++++++++------------------ 1 file changed, 64 insertions(+), 44 deletions(-) diff --git a/xen/arch/arm/irq.c b/xen/arch/arm/irq.c index 3877657a52..9cc0a54867 100644 --- a/xen/arch/arm/irq.c +++ b/xen/arch/arm/irq.c @@ -407,61 +407,25 @@ bool irq_type_set_by_domain(const struct domain *d) return (d == hardware_domain); } -/* - * Route an IRQ to a specific guest. - * For now only SPIs are assignable to the guest. - */ -int route_irq_to_guest(struct domain *d, unsigned int virq, - unsigned int irq, const char * devname) +static int setup_guest_irq(struct irq_desc *desc, unsigned int virq, + unsigned int irqflags, + struct irq_guest *info, const char *devname) { + const unsigned irq = desc->irq; struct irqaction *action; - struct irq_guest *info; - struct irq_desc *desc; - unsigned long flags; - int retval = 0; - - if ( virq >= vgic_num_irqs(d) ) - { - printk(XENLOG_G_ERR - "the vIRQ number %u is too high for domain %u (max = %u)\n", - irq, d->domain_id, vgic_num_irqs(d)); - return -EINVAL; - } - - /* Only routing to virtual SPIs is supported */ - if ( virq < NR_LOCAL_IRQS ) - { - printk(XENLOG_G_ERR "IRQ can only be routed to an SPI\n"); - return -EINVAL; - } + int retval; + struct domain *d = info->d; - if ( !is_assignable_irq(irq) ) - { - printk(XENLOG_G_ERR "the IRQ%u is not routable\n", irq); - return -EINVAL; - } - desc = irq_to_desc(irq); + ASSERT(spin_is_locked(&desc->lock)); action = xmalloc(struct irqaction); if ( !action ) return -ENOMEM; - info = xmalloc(struct irq_guest); - if ( !info ) - { - xfree(action); - return -ENOMEM; - } - - info->d = d; - info->virq = virq; - action->dev_id = info; action->name = devname; action->free_on_release = 1; - spin_lock_irqsave(&desc->lock, flags); - if ( !irq_type_set_by_domain(d) && desc->arch.type == IRQ_TYPE_INVALID ) { printk(XENLOG_G_ERR "IRQ %u has not been configured\n", irq); @@ -496,6 +460,8 @@ int route_irq_to_guest(struct domain *d, unsigned int virq, d->domain_id, irq, irq_get_guest_info(desc)->virq); retval = -EBUSY; } + else + retval = 0; } else { @@ -509,6 +475,61 @@ int route_irq_to_guest(struct domain *d, unsigned int virq, if ( retval ) goto out; + return 0; + +out: + xfree(action); + return retval; +} + +/* + * Route an IRQ to a specific guest. + * For now only SPIs are assignable to the guest. + */ +int route_irq_to_guest(struct domain *d, unsigned int virq, + unsigned int irq, const char * devname) +{ + struct irq_guest *info; + struct irq_desc *desc; + unsigned long flags; + int retval; + + if ( virq >= vgic_num_irqs(d) ) + { + printk(XENLOG_G_ERR + "the vIRQ number %u is too high for domain %u (max = %u)\n", + irq, d->domain_id, vgic_num_irqs(d)); + return -EINVAL; + } + + /* Only routing to virtual SPIs is supported */ + if ( virq < NR_LOCAL_IRQS ) + { + printk(XENLOG_G_ERR "IRQ can only be routed to an SPI\n"); + return -EINVAL; + } + + if ( !is_assignable_irq(irq) ) + { + printk(XENLOG_G_ERR "the IRQ%u is not routable\n", irq); + return -EINVAL; + } + + desc = irq_to_desc(irq); + + info = xmalloc(struct irq_guest); + if ( !info ) + return -ENOMEM; + + info->d = d; + info->virq = virq; + + spin_lock_irqsave(&desc->lock, flags); + + retval = setup_guest_irq(desc, virq, flags, info, devname); + if ( retval ) + goto out; + retval = gic_route_irq_to_guest(d, virq, desc, GIC_PRI_IRQ); spin_unlock_irqrestore(&desc->lock, flags); @@ -523,7 +544,6 @@ int route_irq_to_guest(struct domain *d, unsigned int virq, out: spin_unlock_irqrestore(&desc->lock, flags); - xfree(action); free_info: xfree(info);