1 /****************************************************************************** 2 * evtchn.c 3 * 4 * Driver for receiving and demuxing event-channel signals. 5 * 6 * Copyright (c) 2004-2005, K A Fraser 7 * Multi-process extensions Copyright (c) 2004, Steven Smith 8 * FreeBSD port Copyright (c) 2014, Roger Pau Monné 9 * Fetched from git://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git 10 * File: drivers/xen/evtchn.c 11 * Git commit: 0dc0064add422bc0ef5165ebe9ece3052bbd457d 12 * 13 * This program is free software; you can redistribute it and/or 14 * modify it under the terms of the GNU General Public License version 2 15 * as published by the Free Software Foundation; or, when distributed 16 * separately from the Linux kernel or incorporated into other 17 * software packages, subject to the following license: 18 * 19 * Permission is hereby granted, free of charge, to any person obtaining a copy 20 * of this source file (the "Software"), to deal in the Software without 21 * restriction, including without limitation the rights to use, copy, modify, 22 * merge, publish, distribute, sublicense, and/or sell copies of the Software, 23 * and to permit persons to whom the Software is furnished to do so, subject to 24 * the following conditions: 25 * 26 * The above copyright notice and this permission notice shall be included in 27 * all copies or substantial portions of the Software. 28 * 29 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 30 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 31 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 32 * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 33 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING 34 * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS 35 * IN THE SOFTWARE. 36 */ 37 38 #include <sys/cdefs.h> 39 #include <sys/param.h> 40 #include <sys/systm.h> 41 #include <sys/uio.h> 42 #include <sys/bus.h> 43 #include <sys/malloc.h> 44 #include <sys/kernel.h> 45 #include <sys/lock.h> 46 #include <sys/mutex.h> 47 #include <sys/sx.h> 48 #include <sys/selinfo.h> 49 #include <sys/poll.h> 50 #include <sys/conf.h> 51 #include <sys/fcntl.h> 52 #include <sys/ioccom.h> 53 #include <sys/rman.h> 54 #include <sys/tree.h> 55 #include <sys/module.h> 56 #include <sys/filio.h> 57 #include <sys/vnode.h> 58 59 #include <xen/xen-os.h> 60 #include <xen/evtchn.h> 61 #include <xen/xen_intr.h> 62 63 #include <xen/evtchn/evtchnvar.h> 64 65 MALLOC_DEFINE(M_EVTCHN, "evtchn_dev", "Xen event channel user-space device"); 66 67 struct user_evtchn; 68 69 static int evtchn_cmp(struct user_evtchn *u1, struct user_evtchn *u2); 70 71 RB_HEAD(evtchn_tree, user_evtchn); 72 73 struct per_user_data { 74 struct mtx bind_mutex; /* serialize bind/unbind operations */ 75 struct evtchn_tree evtchns; 76 77 /* Notification ring, accessed via /dev/xen/evtchn. */ 78 #define EVTCHN_RING_SIZE (PAGE_SIZE / sizeof(evtchn_port_t)) 79 #define EVTCHN_RING_MASK(_i) ((_i)&(EVTCHN_RING_SIZE-1)) 80 evtchn_port_t *ring; 81 unsigned int ring_cons, ring_prod, ring_overflow; 82 struct sx ring_cons_mutex; /* protect against concurrent readers */ 83 struct mtx ring_prod_mutex; /* product against concurrent interrupts */ 84 struct selinfo ev_rsel; 85 }; 86 87 struct user_evtchn { 88 RB_ENTRY(user_evtchn) node; 89 struct per_user_data *user; 90 evtchn_port_t port; 91 xen_intr_handle_t handle; 92 bool enabled; 93 }; 94 95 RB_GENERATE_STATIC(evtchn_tree, user_evtchn, node, evtchn_cmp); 96 97 static device_t evtchn_dev; 98 99 static d_read_t evtchn_read; 100 static d_write_t evtchn_write; 101 static d_ioctl_t evtchn_ioctl; 102 static d_poll_t evtchn_poll; 103 static d_open_t evtchn_open; 104 105 static void evtchn_release(void *arg); 106 107 static struct cdevsw evtchn_devsw = { 108 .d_version = D_VERSION, 109 .d_open = evtchn_open, 110 .d_read = evtchn_read, 111 .d_write = evtchn_write, 112 .d_ioctl = evtchn_ioctl, 113 .d_poll = evtchn_poll, 114 .d_name = "evtchn", 115 }; 116 117 /*------------------------- Red-black tree helpers ---------------------------*/ 118 static int 119 evtchn_cmp(struct user_evtchn *u1, struct user_evtchn *u2) 120 { 121 122 return (u1->port - u2->port); 123 } 124 125 static struct user_evtchn * 126 find_evtchn(struct per_user_data *u, evtchn_port_t port) 127 { 128 struct user_evtchn tmp = { 129 .port = port, 130 }; 131 132 return (RB_FIND(evtchn_tree, &u->evtchns, &tmp)); 133 } 134 135 /*--------------------------- Interrupt handlers -----------------------------*/ 136 static int 137 evtchn_filter(void *arg) 138 { 139 struct user_evtchn *evtchn; 140 141 evtchn = arg; 142 143 if (!evtchn->enabled && bootverbose) { 144 device_printf(evtchn_dev, 145 "Received upcall for disabled event channel %d\n", 146 evtchn->port); 147 } 148 149 evtchn_mask_port(evtchn->port); 150 evtchn->enabled = false; 151 152 return (FILTER_SCHEDULE_THREAD); 153 } 154 155 static void 156 evtchn_interrupt(void *arg) 157 { 158 struct user_evtchn *evtchn; 159 struct per_user_data *u; 160 161 evtchn = arg; 162 u = evtchn->user; 163 164 /* 165 * Protect against concurrent events using this handler 166 * on different CPUs. 167 */ 168 mtx_lock(&u->ring_prod_mutex); 169 if ((u->ring_prod - u->ring_cons) < EVTCHN_RING_SIZE) { 170 u->ring[EVTCHN_RING_MASK(u->ring_prod)] = evtchn->port; 171 wmb(); /* Ensure ring contents visible */ 172 if (u->ring_cons == u->ring_prod++) { 173 wakeup(u); 174 selwakeup(&u->ev_rsel); 175 } 176 } else 177 u->ring_overflow = 1; 178 mtx_unlock(&u->ring_prod_mutex); 179 } 180 181 /*------------------------- Character device methods -------------------------*/ 182 static int 183 evtchn_open(struct cdev *dev, int flag, int otyp, struct thread *td) 184 { 185 struct per_user_data *u; 186 int error; 187 188 u = malloc(sizeof(*u), M_EVTCHN, M_WAITOK | M_ZERO); 189 u->ring = malloc(PAGE_SIZE, M_EVTCHN, M_WAITOK | M_ZERO); 190 191 /* Initialize locks */ 192 mtx_init(&u->bind_mutex, "evtchn_bind_mutex", NULL, MTX_DEF); 193 sx_init(&u->ring_cons_mutex, "evtchn_ringc_sx"); 194 mtx_init(&u->ring_prod_mutex, "evtchn_ringp_mutex", NULL, MTX_DEF); 195 196 /* Initialize red-black tree. */ 197 RB_INIT(&u->evtchns); 198 199 /* Assign the allocated per_user_data to this open instance. */ 200 error = devfs_set_cdevpriv(u, evtchn_release); 201 if (error != 0) { 202 mtx_destroy(&u->bind_mutex); 203 mtx_destroy(&u->ring_prod_mutex); 204 sx_destroy(&u->ring_cons_mutex); 205 free(u->ring, M_EVTCHN); 206 free(u, M_EVTCHN); 207 } 208 209 return (error); 210 } 211 212 static void 213 evtchn_release(void *arg) 214 { 215 struct per_user_data *u; 216 struct user_evtchn *evtchn, *tmp; 217 218 u = arg; 219 220 seldrain(&u->ev_rsel); 221 222 RB_FOREACH_SAFE(evtchn, evtchn_tree, &u->evtchns, tmp) { 223 xen_intr_unbind(&evtchn->handle); 224 225 RB_REMOVE(evtchn_tree, &u->evtchns, evtchn); 226 free(evtchn, M_EVTCHN); 227 } 228 229 mtx_destroy(&u->bind_mutex); 230 mtx_destroy(&u->ring_prod_mutex); 231 sx_destroy(&u->ring_cons_mutex); 232 free(u->ring, M_EVTCHN); 233 free(u, M_EVTCHN); 234 } 235 236 static int 237 evtchn_read(struct cdev *dev, struct uio *uio, int ioflag) 238 { 239 int error, count; 240 unsigned int c, p, bytes1 = 0, bytes2 = 0; 241 struct per_user_data *u; 242 243 error = devfs_get_cdevpriv((void **)&u); 244 if (error != 0) 245 return (EINVAL); 246 247 /* Whole number of ports. */ 248 count = uio->uio_resid; 249 count &= ~(sizeof(evtchn_port_t)-1); 250 251 if (count == 0) 252 return (0); 253 254 if (count > PAGE_SIZE) 255 count = PAGE_SIZE; 256 257 sx_xlock(&u->ring_cons_mutex); 258 for (;;) { 259 if (u->ring_overflow) { 260 error = EFBIG; 261 goto unlock_out; 262 } 263 264 c = u->ring_cons; 265 p = u->ring_prod; 266 if (c != p) 267 break; 268 269 if (ioflag & IO_NDELAY) { 270 error = EWOULDBLOCK; 271 goto unlock_out; 272 } 273 274 error = sx_sleep(u, &u->ring_cons_mutex, PCATCH, "evtchw", 0); 275 if ((error != 0) && (error != EWOULDBLOCK)) 276 goto unlock_out; 277 } 278 279 /* Byte lengths of two chunks. Chunk split (if any) is at ring wrap. */ 280 if (((c ^ p) & EVTCHN_RING_SIZE) != 0) { 281 bytes1 = (EVTCHN_RING_SIZE - EVTCHN_RING_MASK(c)) * 282 sizeof(evtchn_port_t); 283 bytes2 = EVTCHN_RING_MASK(p) * sizeof(evtchn_port_t); 284 } else { 285 bytes1 = (p - c) * sizeof(evtchn_port_t); 286 bytes2 = 0; 287 } 288 289 /* Truncate chunks according to caller's maximum byte count. */ 290 if (bytes1 > count) { 291 bytes1 = count; 292 bytes2 = 0; 293 } else if ((bytes1 + bytes2) > count) { 294 bytes2 = count - bytes1; 295 } 296 297 error = EFAULT; 298 rmb(); /* Ensure that we see the port before we copy it. */ 299 300 if (uiomove(&u->ring[EVTCHN_RING_MASK(c)], bytes1, uio) || 301 ((bytes2 != 0) && uiomove(&u->ring[0], bytes2, uio))) 302 goto unlock_out; 303 304 u->ring_cons += (bytes1 + bytes2) / sizeof(evtchn_port_t); 305 error = 0; 306 307 unlock_out: 308 sx_xunlock(&u->ring_cons_mutex); 309 return (error); 310 } 311 312 static int 313 evtchn_write(struct cdev *dev, struct uio *uio, int ioflag) 314 { 315 int error, i, count; 316 evtchn_port_t *kbuf; 317 struct per_user_data *u; 318 319 error = devfs_get_cdevpriv((void **)&u); 320 if (error != 0) 321 return (EINVAL); 322 323 kbuf = malloc(PAGE_SIZE, M_EVTCHN, M_WAITOK); 324 325 count = uio->uio_resid; 326 /* Whole number of ports. */ 327 count &= ~(sizeof(evtchn_port_t)-1); 328 329 error = 0; 330 if (count == 0) 331 goto out; 332 333 if (count > PAGE_SIZE) 334 count = PAGE_SIZE; 335 336 error = uiomove(kbuf, count, uio); 337 if (error != 0) 338 goto out; 339 340 mtx_lock(&u->bind_mutex); 341 342 for (i = 0; i < (count/sizeof(evtchn_port_t)); i++) { 343 evtchn_port_t port = kbuf[i]; 344 struct user_evtchn *evtchn; 345 346 evtchn = find_evtchn(u, port); 347 if (evtchn && !evtchn->enabled) { 348 evtchn->enabled = true; 349 evtchn_unmask_port(evtchn->port); 350 } 351 } 352 353 mtx_unlock(&u->bind_mutex); 354 error = 0; 355 356 out: 357 free(kbuf, M_EVTCHN); 358 return (error); 359 } 360 361 static inline int 362 evtchn_bind_user_port(struct per_user_data *u, struct user_evtchn *evtchn) 363 { 364 int error; 365 366 evtchn->port = xen_intr_port(evtchn->handle); 367 evtchn->user = u; 368 evtchn->enabled = true; 369 mtx_lock(&u->bind_mutex); 370 RB_INSERT(evtchn_tree, &u->evtchns, evtchn); 371 mtx_unlock(&u->bind_mutex); 372 error = xen_intr_add_handler(device_get_nameunit(evtchn_dev), 373 evtchn_filter, evtchn_interrupt, evtchn, 374 INTR_TYPE_MISC | INTR_MPSAFE, evtchn->handle); 375 if (error != 0) { 376 xen_intr_unbind(&evtchn->handle); 377 mtx_lock(&u->bind_mutex); 378 RB_REMOVE(evtchn_tree, &u->evtchns, evtchn); 379 mtx_unlock(&u->bind_mutex); 380 free(evtchn, M_EVTCHN); 381 } 382 return (error); 383 } 384 385 static int 386 evtchn_ioctl(struct cdev *dev, unsigned long cmd, caddr_t arg, 387 int mode, struct thread *td __unused) 388 { 389 struct per_user_data *u; 390 int error; 391 392 error = devfs_get_cdevpriv((void **)&u); 393 if (error != 0) 394 return (EINVAL); 395 396 switch (cmd) { 397 case IOCTL_EVTCHN_BIND_VIRQ: { 398 struct ioctl_evtchn_bind_virq *bind; 399 struct user_evtchn *evtchn; 400 401 evtchn = malloc(sizeof(*evtchn), M_EVTCHN, M_WAITOK | M_ZERO); 402 403 bind = (struct ioctl_evtchn_bind_virq *)arg; 404 405 error = xen_intr_bind_virq(evtchn_dev, bind->virq, 0, 406 NULL, NULL, NULL, 0, &evtchn->handle); 407 if (error != 0) { 408 free(evtchn, M_EVTCHN); 409 break; 410 } 411 error = evtchn_bind_user_port(u, evtchn); 412 if (error != 0) 413 break; 414 bind->port = evtchn->port; 415 break; 416 } 417 418 case IOCTL_EVTCHN_BIND_INTERDOMAIN: { 419 struct ioctl_evtchn_bind_interdomain *bind; 420 struct user_evtchn *evtchn; 421 422 evtchn = malloc(sizeof(*evtchn), M_EVTCHN, M_WAITOK | M_ZERO); 423 424 bind = (struct ioctl_evtchn_bind_interdomain *)arg; 425 426 error = xen_intr_bind_remote_port(evtchn_dev, 427 bind->remote_domain, bind->remote_port, NULL, 428 NULL, NULL, 0, &evtchn->handle); 429 if (error != 0) { 430 free(evtchn, M_EVTCHN); 431 break; 432 } 433 error = evtchn_bind_user_port(u, evtchn); 434 if (error != 0) 435 break; 436 bind->port = evtchn->port; 437 break; 438 } 439 440 case IOCTL_EVTCHN_BIND_UNBOUND_PORT: { 441 struct ioctl_evtchn_bind_unbound_port *bind; 442 struct user_evtchn *evtchn; 443 444 evtchn = malloc(sizeof(*evtchn), M_EVTCHN, M_WAITOK | M_ZERO); 445 446 bind = (struct ioctl_evtchn_bind_unbound_port *)arg; 447 448 error = xen_intr_alloc_and_bind_local_port(evtchn_dev, 449 bind->remote_domain, NULL, NULL, NULL, 0, &evtchn->handle); 450 if (error != 0) { 451 free(evtchn, M_EVTCHN); 452 break; 453 } 454 error = evtchn_bind_user_port(u, evtchn); 455 if (error != 0) 456 break; 457 bind->port = evtchn->port; 458 break; 459 } 460 461 case IOCTL_EVTCHN_UNBIND: { 462 struct ioctl_evtchn_unbind *unbind; 463 struct user_evtchn *evtchn; 464 465 unbind = (struct ioctl_evtchn_unbind *)arg; 466 467 mtx_lock(&u->bind_mutex); 468 evtchn = find_evtchn(u, unbind->port); 469 if (evtchn == NULL) { 470 error = ENOTCONN; 471 break; 472 } 473 RB_REMOVE(evtchn_tree, &u->evtchns, evtchn); 474 mtx_unlock(&u->bind_mutex); 475 476 xen_intr_unbind(&evtchn->handle); 477 free(evtchn, M_EVTCHN); 478 error = 0; 479 break; 480 } 481 482 case IOCTL_EVTCHN_NOTIFY: { 483 struct ioctl_evtchn_notify *notify; 484 struct user_evtchn *evtchn; 485 486 notify = (struct ioctl_evtchn_notify *)arg; 487 488 mtx_lock(&u->bind_mutex); 489 evtchn = find_evtchn(u, notify->port); 490 if (evtchn == NULL) { 491 error = ENOTCONN; 492 break; 493 } 494 495 xen_intr_signal(evtchn->handle); 496 mtx_unlock(&u->bind_mutex); 497 error = 0; 498 break; 499 } 500 501 case IOCTL_EVTCHN_RESET: { 502 /* Initialise the ring to empty. Clear errors. */ 503 sx_xlock(&u->ring_cons_mutex); 504 mtx_lock(&u->ring_prod_mutex); 505 u->ring_cons = u->ring_prod = u->ring_overflow = 0; 506 mtx_unlock(&u->ring_prod_mutex); 507 sx_xunlock(&u->ring_cons_mutex); 508 error = 0; 509 break; 510 } 511 512 case FIONBIO: 513 case FIOASYNC: 514 /* Handled in an upper layer */ 515 error = 0; 516 break; 517 518 default: 519 error = ENOTTY; 520 break; 521 } 522 523 return (error); 524 } 525 526 static int 527 evtchn_poll(struct cdev *dev, int events, struct thread *td) 528 { 529 struct per_user_data *u; 530 int error, mask; 531 532 error = devfs_get_cdevpriv((void **)&u); 533 if (error != 0) 534 return (POLLERR); 535 536 /* we can always write */ 537 mask = events & (POLLOUT | POLLWRNORM); 538 539 mtx_lock(&u->ring_prod_mutex); 540 if (events & (POLLIN | POLLRDNORM)) { 541 if (u->ring_cons != u->ring_prod) { 542 mask |= events & (POLLIN | POLLRDNORM); 543 } else { 544 /* Record that someone is waiting */ 545 selrecord(td, &u->ev_rsel); 546 } 547 } 548 mtx_unlock(&u->ring_prod_mutex); 549 550 return (mask); 551 } 552 553 /*------------------ Private Device Attachment Functions --------------------*/ 554 static void 555 evtchn_identify(driver_t *driver, device_t parent) 556 { 557 558 KASSERT((xen_domain()), 559 ("Trying to attach evtchn device on non Xen domain")); 560 561 evtchn_dev = BUS_ADD_CHILD(parent, 0, "evtchn", 0); 562 if (evtchn_dev == NULL) 563 panic("unable to attach evtchn user-space device"); 564 } 565 566 static int 567 evtchn_probe(device_t dev) 568 { 569 570 device_set_desc(dev, "Xen event channel user-space device"); 571 return (BUS_PROBE_NOWILDCARD); 572 } 573 574 static int 575 evtchn_attach(device_t dev) 576 { 577 578 make_dev_credf(MAKEDEV_ETERNAL, &evtchn_devsw, 0, NULL, UID_ROOT, 579 GID_WHEEL, 0600, "xen/evtchn"); 580 return (0); 581 } 582 583 /*-------------------- Private Device Attachment Data -----------------------*/ 584 static device_method_t evtchn_methods[] = { 585 DEVMETHOD(device_identify, evtchn_identify), 586 DEVMETHOD(device_probe, evtchn_probe), 587 DEVMETHOD(device_attach, evtchn_attach), 588 589 DEVMETHOD_END 590 }; 591 592 static driver_t evtchn_driver = { 593 "evtchn", 594 evtchn_methods, 595 0, 596 }; 597 598 DRIVER_MODULE(evtchn, xenpv, evtchn_driver, 0, 0); 599 MODULE_DEPEND(evtchn, xenpv, 1, 1, 1); 600