1 /****************************************************************************** 2 * xen_intr.h 3 * 4 * APIs for managing Xen event channel, virtual IRQ, and physical IRQ 5 * notifications. 6 * 7 * Copyright (c) 2004, K A Fraser 8 * Copyright (c) 2012, Spectra Logic Corporation 9 * 10 * This file may be distributed separately from the Linux kernel, or 11 * incorporated into other software packages, subject to the following license: 12 * 13 * Permission is hereby granted, free of charge, to any person obtaining a copy 14 * of this source file (the "Software"), to deal in the Software without 15 * restriction, including without limitation the rights to use, copy, modify, 16 * merge, publish, distribute, sublicense, and/or sell copies of the Software, 17 * and to permit persons to whom the Software is furnished to do so, subject to 18 * the following conditions: 19 * 20 * The above copyright notice and this permission notice shall be included in 21 * all copies or substantial portions of the Software. 22 * 23 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 24 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 25 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 26 * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 27 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING 28 * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS 29 * IN THE SOFTWARE. 30 */ 31 #ifndef _XEN_INTR_H_ 32 #define _XEN_INTR_H_ 33 34 #include <contrib/xen/event_channel.h> 35 36 /** Registered Xen interrupt callback handle. */ 37 typedef void * xen_intr_handle_t; 38 39 /* 40 * Main handler for Xen event channel interrupts 41 */ 42 extern driver_filter_t xen_intr_handle_upcall; 43 44 /** 45 * Associate an already allocated local event channel port an interrupt 46 * handler. 47 * 48 * \param dev The device making this bind request. 49 * \param local_port The event channel to bind. 50 * \param filter An interrupt filter handler. Specify NULL 51 * to always dispatch to the ithread handler. 52 * \param handler An interrupt ithread handler. Optional (can 53 * specify NULL) if all necessary event actions 54 * are performed by filter. 55 * \param arg Argument to present to both filter and handler. 56 * \param irqflags Interrupt handler flags. See sys/bus.h. 57 * \param handlep Pointer to an opaque handle used to manage this 58 * registration. 59 * 60 * \returns 0 on success, otherwise an errno. 61 */ 62 int xen_intr_bind_local_port(device_t dev, evtchn_port_t local_port, 63 driver_filter_t filter, driver_intr_t handler, void *arg, 64 enum intr_type irqflags, xen_intr_handle_t *handlep); 65 66 /** 67 * Allocate a local event channel port, accessible by the specified 68 * remote/foreign domain and, if successful, associate the port with 69 * the specified interrupt handler. 70 * 71 * \param dev The device making this bind request. 72 * \param remote_domain Remote domain grant permission to signal the 73 * newly allocated local port. 74 * \param filter An interrupt filter handler. Specify NULL 75 * to always dispatch to the ithread handler. 76 * \param handler An interrupt ithread handler. Optional (can 77 * specify NULL) if all necessary event actions 78 * are performed by filter. 79 * \param arg Argument to present to both filter and handler. 80 * \param irqflags Interrupt handler flags. See sys/bus.h. 81 * \param handlep Pointer to an opaque handle used to manage this 82 * registration. 83 * 84 * \returns 0 on success, otherwise an errno. 85 */ 86 int xen_intr_alloc_and_bind_local_port(device_t dev, 87 u_int remote_domain, driver_filter_t filter, driver_intr_t handler, 88 void *arg, enum intr_type irqflags, xen_intr_handle_t *handlep); 89 90 /** 91 * Associate the specified interrupt handler with the remote event 92 * channel port specified by remote_domain and remote_port. 93 * 94 * \param dev The device making this bind request. 95 * \param remote_domain The domain peer for this event channel connection. 96 * \param remote_port Remote domain's local port number for this event 97 * channel port. 98 * \param filter An interrupt filter handler. Specify NULL 99 * to always dispatch to the ithread handler. 100 * \param handler An interrupt ithread handler. Optional (can 101 * specify NULL) if all necessary event actions 102 * are performed by filter. 103 * \param arg Argument to present to both filter and handler. 104 * \param irqflags Interrupt handler flags. See sys/bus.h. 105 * \param handlep Pointer to an opaque handle used to manage this 106 * registration. 107 * 108 * \returns 0 on success, otherwise an errno. 109 */ 110 int xen_intr_bind_remote_port(device_t dev, u_int remote_domain, 111 evtchn_port_t remote_port, driver_filter_t filter, 112 driver_intr_t handler, void *arg, enum intr_type irqflags, 113 xen_intr_handle_t *handlep); 114 115 /** 116 * Associate the specified interrupt handler with the specified Xen 117 * virtual interrupt source. 118 * 119 * \param dev The device making this bind request. 120 * \param virq The Xen virtual IRQ number for the Xen interrupt 121 * source being hooked. 122 * \param cpu The cpu on which interrupt events should be delivered. 123 * \param filter An interrupt filter handler. Specify NULL 124 * to always dispatch to the ithread handler. 125 * \param handler An interrupt ithread handler. Optional (can 126 * specify NULL) if all necessary event actions 127 * are performed by filter. 128 * \param arg Argument to present to both filter and handler. 129 * \param irqflags Interrupt handler flags. See sys/bus.h. 130 * \param handlep Pointer to an opaque handle used to manage this 131 * registration. 132 * 133 * \returns 0 on success, otherwise an errno. 134 */ 135 int xen_intr_bind_virq(device_t dev, u_int virq, u_int cpu, 136 driver_filter_t filter, driver_intr_t handler, 137 void *arg, enum intr_type irqflags, xen_intr_handle_t *handlep); 138 139 /** 140 * Allocate a local event channel port for servicing interprocessor 141 * interupts and, if successful, associate the port with the specified 142 * interrupt handler. 143 * 144 * \param cpu The cpu receiving the IPI. 145 * \param filter The interrupt filter servicing this IPI. 146 * \param irqflags Interrupt handler flags. See sys/bus.h. 147 * \param handlep Pointer to an opaque handle used to manage this 148 * registration. 149 * 150 * \returns 0 on success, otherwise an errno. 151 */ 152 int xen_intr_alloc_and_bind_ipi(u_int cpu, 153 driver_filter_t filter, enum intr_type irqflags, 154 xen_intr_handle_t *handlep); 155 156 /** 157 * Unbind an interrupt handler from its interrupt source. 158 * 159 * \param handlep A pointer to the opaque handle that was initialized 160 * at the time the interrupt source was bound. 161 * 162 * \returns 0 on success, otherwise an errno. 163 * 164 * \note The event channel, if any, that was allocated at bind time is 165 * closed upon successful return of this method. 166 * 167 * \note It is always safe to call xen_intr_unbind() on a handle that 168 * has been initilized to NULL. 169 */ 170 void xen_intr_unbind(xen_intr_handle_t *handle); 171 172 /** 173 * Add a description to an interrupt handler. 174 * 175 * \param handle The opaque handle that was initialized at the time 176 * the interrupt source was bound. 177 * 178 * \param fmt The sprintf compatible format string for the description, 179 * followed by optional sprintf arguments. 180 * 181 * \returns 0 on success, otherwise an errno. 182 */ 183 int 184 xen_intr_describe(xen_intr_handle_t port_handle, const char *fmt, ...) 185 __attribute__((format(printf, 2, 3))); 186 187 /** 188 * Signal the remote peer of an interrupt source associated with an 189 * event channel port. 190 * 191 * \param handle The opaque handle that was initialized at the time 192 * the interrupt source was bound. 193 * 194 * \note For xen interrupt sources other than event channel ports, 195 * this method takes no action. 196 */ 197 void xen_intr_signal(xen_intr_handle_t handle); 198 199 /** 200 * Get the local event channel port number associated with this interrupt 201 * source. 202 * 203 * \param handle The opaque handle that was initialized at the time 204 * the interrupt source was bound. 205 * 206 * \returns 0 if the handle is invalid, otherwise positive port number. 207 */ 208 evtchn_port_t xen_intr_port(xen_intr_handle_t handle); 209 210 /** 211 * Bind an event channel port with a handler 212 * 213 * \param dev The device making this bind request. 214 * \param filter An interrupt filter handler. Specify NULL 215 * to always dispatch to the ithread handler. 216 * \param handler An interrupt ithread handler. Optional (can 217 * specify NULL) if all necessary event actions 218 * are performed by filter. 219 * \param arg Argument to present to both filter and handler. 220 * \param irqflags Interrupt handler flags. See sys/bus.h. 221 * \param handle Opaque handle used to manage this registration. 222 * 223 * \returns 0 on success, otherwise an errno. 224 */ 225 int xen_intr_add_handler(const char *name, driver_filter_t filter, 226 driver_intr_t handler, void *arg, enum intr_type flags, 227 xen_intr_handle_t handle); 228 229 /** 230 * Get a reference to an event channel port 231 * 232 * \param port Event channel port to which we get a reference. 233 * \param handlep Pointer to an opaque handle used to manage this 234 * registration. 235 * 236 * \returns 0 on success, otherwise an errno. 237 */ 238 int xen_intr_get_evtchn_from_port(evtchn_port_t port, 239 xen_intr_handle_t *handlep); 240 241 #endif /* _XEN_INTR_H_ */ 242