[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

[Xen-devel] [PATCH v2 2 of 4] xen: introduce PHYSDEVOP_get_free_pirq



Introduce a new physdev_op called PHYSDEVOP_get_free_pirq to allow a
guest to get a free pirq number from Xen; the hypervisor would keep that
pirq free for the guest to use in a mapping.

Signed-off-by: Stefano Stabellini <stefano.stabellini@xxxxxxxxxxxxx>

diff -r c585b1651a6f xen/arch/x86/hvm/hvm.c
--- a/xen/arch/x86/hvm/hvm.c    Thu Nov 18 19:54:04 2010 +0000
+++ b/xen/arch/x86/hvm/hvm.c    Fri Nov 19 12:56:20 2010 +0000
@@ -2448,6 +2448,7 @@ static long hvm_physdev_op(int cmd, XEN_
         case PHYSDEVOP_unmap_pirq:
         case PHYSDEVOP_eoi:
         case PHYSDEVOP_irq_status_query:
+        case PHYSDEVOP_get_free_pirq:
             return do_physdev_op(cmd, arg);
         default:
             return -ENOSYS;
@@ -2550,6 +2551,7 @@ static long hvm_physdev_op_compat32(
         case PHYSDEVOP_unmap_pirq:
         case PHYSDEVOP_eoi:
         case PHYSDEVOP_irq_status_query:
+        case PHYSDEVOP_get_free_pirq:
             return compat_physdev_op(cmd, arg);
         break;
     default:
diff -r c585b1651a6f xen/arch/x86/irq.c
--- a/xen/arch/x86/irq.c        Thu Nov 18 19:54:04 2010 +0000
+++ b/xen/arch/x86/irq.c        Fri Nov 19 12:56:20 2010 +0000
@@ -1505,7 +1505,7 @@ int map_domain_pirq(
     old_irq = domain_pirq_to_irq(d, pirq);
     old_pirq = domain_irq_to_pirq(d, irq);
 
-    if ( (old_irq && (old_irq != irq) ) ||
+    if ( (old_irq > 0 && (old_irq != irq) ) ||
          (old_pirq && (old_pirq != pirq)) )
     {
         dprintk(XENLOG_G_WARNING, "dom%d: pirq %d or irq %d already mapped\n",
diff -r c585b1651a6f xen/arch/x86/physdev.c
--- a/xen/arch/x86/physdev.c    Thu Nov 18 19:54:04 2010 +0000
+++ b/xen/arch/x86/physdev.c    Fri Nov 19 12:56:20 2010 +0000
@@ -125,7 +125,7 @@ static int physdev_map_pirq(struct physd
             }
 
             irq = domain_pirq_to_irq(current->domain, map->index);
-            if ( !irq )
+            if ( irq <= 0 )
             {
                 if ( IS_PRIV(current->domain) )
                     irq = map->index;
@@ -561,6 +561,26 @@ ret_t do_physdev_op(int cmd, XEN_GUEST_H
                               setup_gsi.polarity);
         break; 
     }
+    case PHYSDEVOP_get_free_pirq: {
+        struct physdev_get_free_pirq out;
+        struct domain *d;
+
+        d = rcu_lock_current_domain();
+        
+        ret = -EFAULT;
+        if ( copy_from_guest(&out, arg, 1) != 0 )
+            break;
+
+        spin_lock(&d->event_lock);
+        out.pirq = get_free_pirq(d, out.type, 0);
+        d->arch.pirq_irq[out.pirq] = PIRQ_ALLOCATED;
+        spin_unlock(&d->event_lock);
+
+        ret = copy_to_guest(arg, &out, 1) ? -EFAULT : 0;
+
+        rcu_unlock_domain(d);
+        break;
+    }
     default:
         ret = -ENOSYS;
         break;
diff -r c585b1651a6f xen/arch/x86/x86_64/physdev.c
--- a/xen/arch/x86/x86_64/physdev.c     Thu Nov 18 19:54:04 2010 +0000
+++ b/xen/arch/x86/x86_64/physdev.c     Fri Nov 19 12:56:20 2010 +0000
@@ -42,6 +42,9 @@
 #define physdev_manage_pci         compat_physdev_manage_pci
 #define physdev_manage_pci_t       physdev_manage_pci_compat_t
 
+#define physdev_get_free_pirq      compat_physdev_get_free_pirq
+#define physdev_get_free_pirq_t    physdev_get_free_pirq_compat_t
+
 #define COMPAT
 #undef guest_handle_okay
 #define guest_handle_okay          compat_handle_okay
diff -r c585b1651a6f xen/include/asm-x86/irq.h
--- a/xen/include/asm-x86/irq.h Thu Nov 18 19:54:04 2010 +0000
+++ b/xen/include/asm-x86/irq.h Fri Nov 19 12:56:20 2010 +0000
@@ -150,6 +150,7 @@ void irq_set_affinity(struct irq_desc *,
 
 #define domain_pirq_to_irq(d, pirq) ((d)->arch.pirq_irq[pirq])
 #define domain_irq_to_pirq(d, irq) ((d)->arch.irq_pirq[irq])
+#define PIRQ_ALLOCATED -1
 #define domain_pirq_to_emuirq(d, pirq) ((d)->arch.pirq_emuirq[pirq])
 #define domain_emuirq_to_pirq(d, emuirq) ((d)->arch.emuirq_pirq[emuirq])
 #define IRQ_UNBOUND -1
diff -r c585b1651a6f xen/include/public/physdev.h
--- a/xen/include/public/physdev.h      Thu Nov 18 19:54:04 2010 +0000
+++ b/xen/include/public/physdev.h      Fri Nov 19 12:56:20 2010 +0000
@@ -240,6 +240,21 @@ struct physdev_setup_gsi {
 typedef struct physdev_setup_gsi physdev_setup_gsi_t;
 DEFINE_XEN_GUEST_HANDLE(physdev_setup_gsi_t);
 
+/* leave PHYSDEVOP 22 free */
+
+/* type is MAP_PIRQ_TYPE_GSI or MAP_PIRQ_TYPE_MSI
+ * the hypercall returns a free pirq */
+#define PHYSDEVOP_get_free_pirq    23
+struct physdev_get_free_pirq {
+    /* IN */ 
+    int type;
+    /* OUT */
+    uint32_t pirq;
+};
+
+typedef struct physdev_get_free_pirq physdev_get_free_pirq_t;
+DEFINE_XEN_GUEST_HANDLE(physdev_get_free_pirq_t);
+
 /*
  * Notify that some PIRQ-bound event channels have been unmasked.
  * ** This command is obsolete since interface version 0x00030202 and is **

_______________________________________________
Xen-devel mailing list
Xen-devel@xxxxxxxxxxxxxxxxxxx
http://lists.xensource.com/xen-devel


 


Rackspace

Lists.xenproject.org is hosted with RackSpace, monitoring our
servers 24x7x365 and backed by RackSpace's Fanatical Support®.