1 /* SPDX-License-Identifier: BSD-3-Clause 2 * Copyright(c) 2010-2014 Intel Corporation. 3 * Copyright(c) 2014 6WIND S.A. 4 */ 5 6 #include <stdio.h> 7 #include <stdlib.h> 8 #include <string.h> 9 #include <sys/queue.h> 10 11 #include <rte_bus.h> 12 #include <rte_class.h> 13 #include <rte_dev.h> 14 #include <rte_devargs.h> 15 #include <rte_errno.h> 16 #include <rte_log.h> 17 #include <rte_spinlock.h> 18 #include <rte_string_fns.h> 19 20 #include "eal_private.h" 21 #include "hotplug_mp.h" 22 23 /** 24 * The device event callback description. 25 * 26 * It contains callback address to be registered by user application, 27 * the pointer to the parameters for callback, and the device name. 28 */ 29 struct dev_event_callback { 30 TAILQ_ENTRY(dev_event_callback) next; /**< Callbacks list */ 31 rte_dev_event_cb_fn cb_fn; /**< Callback address */ 32 void *cb_arg; /**< Callback parameter */ 33 char *dev_name; /**< Callback device name, NULL is for all device */ 34 uint32_t active; /**< Callback is executing */ 35 }; 36 37 /** @internal Structure to keep track of registered callbacks */ 38 TAILQ_HEAD(dev_event_cb_list, dev_event_callback); 39 40 /* The device event callback list for all registered callbacks. */ 41 static struct dev_event_cb_list dev_event_cbs; 42 43 /* spinlock for device callbacks */ 44 static rte_spinlock_t dev_event_lock = RTE_SPINLOCK_INITIALIZER; 45 46 struct dev_next_ctx { 47 struct rte_dev_iterator *it; 48 const char *bus_str; 49 const char *cls_str; 50 }; 51 52 #define CTX(it, bus_str, cls_str) \ 53 (&(const struct dev_next_ctx){ \ 54 .it = it, \ 55 .bus_str = bus_str, \ 56 .cls_str = cls_str, \ 57 }) 58 59 #define ITCTX(ptr) \ 60 (((struct dev_next_ctx *)(intptr_t)ptr)->it) 61 62 #define BUSCTX(ptr) \ 63 (((struct dev_next_ctx *)(intptr_t)ptr)->bus_str) 64 65 #define CLSCTX(ptr) \ 66 (((struct dev_next_ctx *)(intptr_t)ptr)->cls_str) 67 68 static int cmp_dev_name(const struct rte_device *dev, const void *_name) 69 { 70 const char *name = _name; 71 72 return strcmp(dev->name, name); 73 } 74 75 int 76 rte_dev_is_probed(const struct rte_device *dev) 77 { 78 /* The field driver should be set only when the probe is successful. */ 79 return dev->driver != NULL; 80 } 81 82 /* helper function to build devargs, caller should free the memory */ 83 static int 84 build_devargs(const char *busname, const char *devname, 85 const char *drvargs, char **devargs) 86 { 87 int length; 88 89 length = snprintf(NULL, 0, "%s:%s,%s", busname, devname, drvargs); 90 if (length < 0) 91 return -EINVAL; 92 93 *devargs = malloc(length + 1); 94 if (*devargs == NULL) 95 return -ENOMEM; 96 97 length = snprintf(*devargs, length + 1, "%s:%s,%s", 98 busname, devname, drvargs); 99 if (length < 0) { 100 free(*devargs); 101 return -EINVAL; 102 } 103 104 return 0; 105 } 106 107 int 108 rte_eal_hotplug_add(const char *busname, const char *devname, 109 const char *drvargs) 110 { 111 112 char *devargs; 113 int ret; 114 115 ret = build_devargs(busname, devname, drvargs, &devargs); 116 if (ret != 0) 117 return ret; 118 119 ret = rte_dev_probe(devargs); 120 free(devargs); 121 122 return ret; 123 } 124 125 /* probe device at local process. */ 126 int 127 local_dev_probe(const char *devargs, struct rte_device **new_dev) 128 { 129 struct rte_device *dev; 130 struct rte_devargs *da; 131 int ret; 132 133 *new_dev = NULL; 134 da = calloc(1, sizeof(*da)); 135 if (da == NULL) 136 return -ENOMEM; 137 138 ret = rte_devargs_parse(da, devargs); 139 if (ret) 140 goto err_devarg; 141 142 if (da->bus->plug == NULL) { 143 RTE_LOG(ERR, EAL, "Function plug not supported by bus (%s)\n", 144 da->bus->name); 145 ret = -ENOTSUP; 146 goto err_devarg; 147 } 148 149 ret = rte_devargs_insert(&da); 150 if (ret) 151 goto err_devarg; 152 153 /* the rte_devargs will be referenced in the matching rte_device */ 154 ret = da->bus->scan(); 155 if (ret) 156 goto err_devarg; 157 158 dev = da->bus->find_device(NULL, cmp_dev_name, da->name); 159 if (dev == NULL) { 160 RTE_LOG(ERR, EAL, "Cannot find device (%s)\n", 161 da->name); 162 ret = -ENODEV; 163 goto err_devarg; 164 } 165 /* Since there is a matching device, it is now its responsibility 166 * to manage the devargs we've just inserted. From this point 167 * those devargs shouldn't be removed manually anymore. 168 */ 169 170 ret = dev->bus->plug(dev); 171 if (ret > 0) 172 ret = -ENOTSUP; 173 174 if (ret && !rte_dev_is_probed(dev)) { /* if hasn't ever succeeded */ 175 RTE_LOG(ERR, EAL, "Driver cannot attach the device (%s)\n", 176 dev->name); 177 return ret; 178 } 179 180 *new_dev = dev; 181 return ret; 182 183 err_devarg: 184 if (rte_devargs_remove(da) != 0) { 185 rte_devargs_reset(da); 186 free(da); 187 } 188 return ret; 189 } 190 191 int 192 rte_dev_probe(const char *devargs) 193 { 194 struct eal_dev_mp_req req; 195 struct rte_device *dev; 196 int ret; 197 198 memset(&req, 0, sizeof(req)); 199 req.t = EAL_DEV_REQ_TYPE_ATTACH; 200 strlcpy(req.devargs, devargs, EAL_DEV_MP_DEV_ARGS_MAX_LEN); 201 202 if (rte_eal_process_type() != RTE_PROC_PRIMARY) { 203 /** 204 * If in secondary process, just send IPC request to 205 * primary process. 206 */ 207 ret = eal_dev_hotplug_request_to_primary(&req); 208 if (ret != 0) { 209 RTE_LOG(ERR, EAL, 210 "Failed to send hotplug request to primary\n"); 211 return -ENOMSG; 212 } 213 if (req.result != 0) 214 RTE_LOG(ERR, EAL, 215 "Failed to hotplug add device\n"); 216 return req.result; 217 } 218 219 /* attach a shared device from primary start from here: */ 220 221 /* primary attach the new device itself. */ 222 ret = local_dev_probe(devargs, &dev); 223 224 if (ret != 0) { 225 RTE_LOG(ERR, EAL, 226 "Failed to attach device on primary process\n"); 227 228 /** 229 * it is possible that secondary process failed to attached a 230 * device that primary process have during initialization, 231 * so for -EEXIST case, we still need to sync with secondary 232 * process. 233 */ 234 if (ret != -EEXIST) 235 return ret; 236 } 237 238 /* primary send attach sync request to secondary. */ 239 ret = eal_dev_hotplug_request_to_secondary(&req); 240 241 /* if any communication error, we need to rollback. */ 242 if (ret != 0) { 243 RTE_LOG(ERR, EAL, 244 "Failed to send hotplug add request to secondary\n"); 245 ret = -ENOMSG; 246 goto rollback; 247 } 248 249 /** 250 * if any secondary failed to attach, we need to consider if rollback 251 * is necessary. 252 */ 253 if (req.result != 0) { 254 RTE_LOG(ERR, EAL, 255 "Failed to attach device on secondary process\n"); 256 ret = req.result; 257 258 /* for -EEXIST, we don't need to rollback. */ 259 if (ret == -EEXIST) 260 return ret; 261 goto rollback; 262 } 263 264 return 0; 265 266 rollback: 267 req.t = EAL_DEV_REQ_TYPE_ATTACH_ROLLBACK; 268 269 /* primary send rollback request to secondary. */ 270 if (eal_dev_hotplug_request_to_secondary(&req) != 0) 271 RTE_LOG(WARNING, EAL, 272 "Failed to rollback device attach on secondary." 273 "Devices in secondary may not sync with primary\n"); 274 275 /* primary rollback itself. */ 276 if (local_dev_remove(dev) != 0) 277 RTE_LOG(WARNING, EAL, 278 "Failed to rollback device attach on primary." 279 "Devices in secondary may not sync with primary\n"); 280 281 return ret; 282 } 283 284 int 285 rte_eal_hotplug_remove(const char *busname, const char *devname) 286 { 287 struct rte_device *dev; 288 struct rte_bus *bus; 289 290 bus = rte_bus_find_by_name(busname); 291 if (bus == NULL) { 292 RTE_LOG(ERR, EAL, "Cannot find bus (%s)\n", busname); 293 return -ENOENT; 294 } 295 296 dev = bus->find_device(NULL, cmp_dev_name, devname); 297 if (dev == NULL) { 298 RTE_LOG(ERR, EAL, "Cannot find plugged device (%s)\n", devname); 299 return -EINVAL; 300 } 301 302 return rte_dev_remove(dev); 303 } 304 305 /* remove device at local process. */ 306 int 307 local_dev_remove(struct rte_device *dev) 308 { 309 int ret; 310 311 if (dev->bus->unplug == NULL) { 312 RTE_LOG(ERR, EAL, "Function unplug not supported by bus (%s)\n", 313 dev->bus->name); 314 return -ENOTSUP; 315 } 316 317 ret = dev->bus->unplug(dev); 318 if (ret) { 319 RTE_LOG(ERR, EAL, "Driver cannot detach the device (%s)\n", 320 dev->name); 321 return (ret < 0) ? ret : -ENOENT; 322 } 323 324 return 0; 325 } 326 327 int 328 rte_dev_remove(struct rte_device *dev) 329 { 330 struct eal_dev_mp_req req; 331 char *devargs; 332 int ret; 333 334 if (!rte_dev_is_probed(dev)) { 335 RTE_LOG(ERR, EAL, "Device is not probed\n"); 336 return -ENOENT; 337 } 338 339 ret = build_devargs(dev->bus->name, dev->name, "", &devargs); 340 if (ret != 0) 341 return ret; 342 343 memset(&req, 0, sizeof(req)); 344 req.t = EAL_DEV_REQ_TYPE_DETACH; 345 strlcpy(req.devargs, devargs, EAL_DEV_MP_DEV_ARGS_MAX_LEN); 346 free(devargs); 347 348 if (rte_eal_process_type() != RTE_PROC_PRIMARY) { 349 /** 350 * If in secondary process, just send IPC request to 351 * primary process. 352 */ 353 ret = eal_dev_hotplug_request_to_primary(&req); 354 if (ret != 0) { 355 RTE_LOG(ERR, EAL, 356 "Failed to send hotplug request to primary\n"); 357 return -ENOMSG; 358 } 359 if (req.result != 0) 360 RTE_LOG(ERR, EAL, 361 "Failed to hotplug remove device\n"); 362 return req.result; 363 } 364 365 /* detach a device from primary start from here: */ 366 367 /* primary send detach sync request to secondary */ 368 ret = eal_dev_hotplug_request_to_secondary(&req); 369 370 /** 371 * if communication error, we need to rollback, because it is possible 372 * part of the secondary processes still detached it successfully. 373 */ 374 if (ret != 0) { 375 RTE_LOG(ERR, EAL, 376 "Failed to send device detach request to secondary\n"); 377 ret = -ENOMSG; 378 goto rollback; 379 } 380 381 /** 382 * if any secondary failed to detach, we need to consider if rollback 383 * is necessary. 384 */ 385 if (req.result != 0) { 386 RTE_LOG(ERR, EAL, 387 "Failed to detach device on secondary process\n"); 388 ret = req.result; 389 /** 390 * if -ENOENT, we don't need to rollback, since devices is 391 * already detached on secondary process. 392 */ 393 if (ret != -ENOENT) 394 goto rollback; 395 } 396 397 /* primary detach the device itself. */ 398 ret = local_dev_remove(dev); 399 400 /* if primary failed, still need to consider if rollback is necessary */ 401 if (ret != 0) { 402 RTE_LOG(ERR, EAL, 403 "Failed to detach device on primary process\n"); 404 /* if -ENOENT, we don't need to rollback */ 405 if (ret == -ENOENT) 406 return ret; 407 goto rollback; 408 } 409 410 return 0; 411 412 rollback: 413 req.t = EAL_DEV_REQ_TYPE_DETACH_ROLLBACK; 414 415 /* primary send rollback request to secondary. */ 416 if (eal_dev_hotplug_request_to_secondary(&req) != 0) 417 RTE_LOG(WARNING, EAL, 418 "Failed to rollback device detach on secondary." 419 "Devices in secondary may not sync with primary\n"); 420 421 return ret; 422 } 423 424 int 425 rte_dev_event_callback_register(const char *device_name, 426 rte_dev_event_cb_fn cb_fn, 427 void *cb_arg) 428 { 429 struct dev_event_callback *event_cb; 430 int ret; 431 432 if (!cb_fn) 433 return -EINVAL; 434 435 rte_spinlock_lock(&dev_event_lock); 436 437 if (TAILQ_EMPTY(&dev_event_cbs)) 438 TAILQ_INIT(&dev_event_cbs); 439 440 TAILQ_FOREACH(event_cb, &dev_event_cbs, next) { 441 if (event_cb->cb_fn == cb_fn && event_cb->cb_arg == cb_arg) { 442 if (device_name == NULL && event_cb->dev_name == NULL) 443 break; 444 if (device_name == NULL || event_cb->dev_name == NULL) 445 continue; 446 if (!strcmp(event_cb->dev_name, device_name)) 447 break; 448 } 449 } 450 451 /* create a new callback. */ 452 if (event_cb == NULL) { 453 event_cb = malloc(sizeof(struct dev_event_callback)); 454 if (event_cb != NULL) { 455 event_cb->cb_fn = cb_fn; 456 event_cb->cb_arg = cb_arg; 457 event_cb->active = 0; 458 if (!device_name) { 459 event_cb->dev_name = NULL; 460 } else { 461 event_cb->dev_name = strdup(device_name); 462 if (event_cb->dev_name == NULL) { 463 ret = -ENOMEM; 464 goto error; 465 } 466 } 467 TAILQ_INSERT_TAIL(&dev_event_cbs, event_cb, next); 468 } else { 469 RTE_LOG(ERR, EAL, 470 "Failed to allocate memory for device " 471 "event callback."); 472 ret = -ENOMEM; 473 goto error; 474 } 475 } else { 476 RTE_LOG(ERR, EAL, 477 "The callback is already exist, no need " 478 "to register again.\n"); 479 event_cb = NULL; 480 ret = -EEXIST; 481 goto error; 482 } 483 484 rte_spinlock_unlock(&dev_event_lock); 485 return 0; 486 error: 487 free(event_cb); 488 rte_spinlock_unlock(&dev_event_lock); 489 return ret; 490 } 491 492 int 493 rte_dev_event_callback_unregister(const char *device_name, 494 rte_dev_event_cb_fn cb_fn, 495 void *cb_arg) 496 { 497 int ret = 0; 498 struct dev_event_callback *event_cb, *next; 499 500 if (!cb_fn) 501 return -EINVAL; 502 503 rte_spinlock_lock(&dev_event_lock); 504 /*walk through the callbacks and remove all that match. */ 505 for (event_cb = TAILQ_FIRST(&dev_event_cbs); event_cb != NULL; 506 event_cb = next) { 507 508 next = TAILQ_NEXT(event_cb, next); 509 510 if (device_name != NULL && event_cb->dev_name != NULL) { 511 if (!strcmp(event_cb->dev_name, device_name)) { 512 if (event_cb->cb_fn != cb_fn || 513 (cb_arg != (void *)-1 && 514 event_cb->cb_arg != cb_arg)) 515 continue; 516 } 517 } else if (device_name != NULL) { 518 continue; 519 } 520 521 /* 522 * if this callback is not executing right now, 523 * then remove it. 524 */ 525 if (event_cb->active == 0) { 526 TAILQ_REMOVE(&dev_event_cbs, event_cb, next); 527 free(event_cb->dev_name); 528 free(event_cb); 529 ret++; 530 } else { 531 ret = -EAGAIN; 532 break; 533 } 534 } 535 536 /* this callback is not be registered */ 537 if (ret == 0) 538 ret = -ENOENT; 539 540 rte_spinlock_unlock(&dev_event_lock); 541 return ret; 542 } 543 544 void 545 rte_dev_event_callback_process(const char *device_name, 546 enum rte_dev_event_type event) 547 { 548 struct dev_event_callback *cb_lst; 549 550 if (device_name == NULL) 551 return; 552 553 rte_spinlock_lock(&dev_event_lock); 554 555 TAILQ_FOREACH(cb_lst, &dev_event_cbs, next) { 556 if (cb_lst->dev_name) { 557 if (strcmp(cb_lst->dev_name, device_name)) 558 continue; 559 } 560 cb_lst->active = 1; 561 rte_spinlock_unlock(&dev_event_lock); 562 cb_lst->cb_fn(device_name, event, 563 cb_lst->cb_arg); 564 rte_spinlock_lock(&dev_event_lock); 565 cb_lst->active = 0; 566 } 567 rte_spinlock_unlock(&dev_event_lock); 568 } 569 570 int 571 rte_dev_iterator_init(struct rte_dev_iterator *it, 572 const char *dev_str) 573 { 574 struct rte_devargs devargs = { .bus = NULL }; 575 struct rte_class *cls = NULL; 576 struct rte_bus *bus = NULL; 577 578 /* Having both bus_str and cls_str NULL is illegal, 579 * marking this iterator as invalid unless 580 * everything goes well. 581 */ 582 it->bus_str = NULL; 583 it->cls_str = NULL; 584 585 /* Setting data field implies no malloc in parsing. */ 586 devargs.data = (void *)(intptr_t)dev_str; 587 if (rte_devargs_layers_parse(&devargs, dev_str)) 588 goto get_out; 589 590 bus = devargs.bus; 591 cls = devargs.cls; 592 /* The string should have at least 593 * one layer specified. 594 */ 595 if (bus == NULL && cls == NULL) { 596 RTE_LOG(DEBUG, EAL, "Either bus or class must be specified.\n"); 597 rte_errno = EINVAL; 598 goto get_out; 599 } 600 if (bus != NULL && bus->dev_iterate == NULL) { 601 RTE_LOG(DEBUG, EAL, "Bus %s not supported\n", bus->name); 602 rte_errno = ENOTSUP; 603 goto get_out; 604 } 605 if (cls != NULL && cls->dev_iterate == NULL) { 606 RTE_LOG(DEBUG, EAL, "Class %s not supported\n", cls->name); 607 rte_errno = ENOTSUP; 608 goto get_out; 609 } 610 it->bus_str = devargs.bus_str; 611 it->cls_str = devargs.cls_str; 612 it->dev_str = dev_str; 613 it->bus = bus; 614 it->cls = cls; 615 it->device = NULL; 616 it->class_device = NULL; 617 get_out: 618 return -rte_errno; 619 } 620 621 static char * 622 dev_str_sane_copy(const char *str) 623 { 624 size_t end; 625 char *copy; 626 627 end = strcspn(str, ",/"); 628 if (str[end] == ',') { 629 copy = strdup(&str[end + 1]); 630 } else { 631 /* '/' or '\0' */ 632 copy = strdup(""); 633 } 634 if (copy == NULL) { 635 rte_errno = ENOMEM; 636 } else { 637 char *slash; 638 639 slash = strchr(copy, '/'); 640 if (slash != NULL) 641 slash[0] = '\0'; 642 } 643 return copy; 644 } 645 646 static int 647 class_next_dev_cmp(const struct rte_class *cls, 648 const void *ctx) 649 { 650 struct rte_dev_iterator *it; 651 const char *cls_str = NULL; 652 void *dev; 653 654 if (cls->dev_iterate == NULL) 655 return 1; 656 it = ITCTX(ctx); 657 cls_str = CLSCTX(ctx); 658 dev = it->class_device; 659 /* it->cls_str != NULL means a class 660 * was specified in the devstr. 661 */ 662 if (it->cls_str != NULL && cls != it->cls) 663 return 1; 664 /* If an error occurred previously, 665 * no need to test further. 666 */ 667 if (rte_errno != 0) 668 return -1; 669 dev = cls->dev_iterate(dev, cls_str, it); 670 it->class_device = dev; 671 return dev == NULL; 672 } 673 674 static int 675 bus_next_dev_cmp(const struct rte_bus *bus, 676 const void *ctx) 677 { 678 struct rte_device *dev = NULL; 679 struct rte_class *cls = NULL; 680 struct rte_dev_iterator *it; 681 const char *bus_str = NULL; 682 683 if (bus->dev_iterate == NULL) 684 return 1; 685 it = ITCTX(ctx); 686 bus_str = BUSCTX(ctx); 687 dev = it->device; 688 /* it->bus_str != NULL means a bus 689 * was specified in the devstr. 690 */ 691 if (it->bus_str != NULL && bus != it->bus) 692 return 1; 693 /* If an error occurred previously, 694 * no need to test further. 695 */ 696 if (rte_errno != 0) 697 return -1; 698 if (it->cls_str == NULL) { 699 dev = bus->dev_iterate(dev, bus_str, it); 700 goto end; 701 } 702 /* cls_str != NULL */ 703 if (dev == NULL) { 704 next_dev_on_bus: 705 dev = bus->dev_iterate(dev, bus_str, it); 706 it->device = dev; 707 } 708 if (dev == NULL) 709 return 1; 710 if (it->cls != NULL) 711 cls = TAILQ_PREV(it->cls, rte_class_list, next); 712 cls = rte_class_find(cls, class_next_dev_cmp, ctx); 713 if (cls != NULL) { 714 it->cls = cls; 715 goto end; 716 } 717 goto next_dev_on_bus; 718 end: 719 it->device = dev; 720 return dev == NULL; 721 } 722 struct rte_device * 723 rte_dev_iterator_next(struct rte_dev_iterator *it) 724 { 725 struct rte_bus *bus = NULL; 726 int old_errno = rte_errno; 727 char *bus_str = NULL; 728 char *cls_str = NULL; 729 730 rte_errno = 0; 731 if (it->bus_str == NULL && it->cls_str == NULL) { 732 /* Invalid iterator. */ 733 rte_errno = EINVAL; 734 return NULL; 735 } 736 if (it->bus != NULL) 737 bus = TAILQ_PREV(it->bus, rte_bus_list, next); 738 if (it->bus_str != NULL) { 739 bus_str = dev_str_sane_copy(it->bus_str); 740 if (bus_str == NULL) 741 goto out; 742 } 743 if (it->cls_str != NULL) { 744 cls_str = dev_str_sane_copy(it->cls_str); 745 if (cls_str == NULL) 746 goto out; 747 } 748 while ((bus = rte_bus_find(bus, bus_next_dev_cmp, 749 CTX(it, bus_str, cls_str)))) { 750 if (it->device != NULL) { 751 it->bus = bus; 752 goto out; 753 } 754 if (it->bus_str != NULL || 755 rte_errno != 0) 756 break; 757 } 758 if (rte_errno == 0) 759 rte_errno = old_errno; 760 out: 761 free(bus_str); 762 free(cls_str); 763 return it->device; 764 } 765 766 int 767 rte_dev_dma_map(struct rte_device *dev, void *addr, uint64_t iova, 768 size_t len) 769 { 770 if (dev->bus->dma_map == NULL || len == 0) { 771 rte_errno = ENOTSUP; 772 return -1; 773 } 774 /* Memory must be registered through rte_extmem_* APIs */ 775 if (rte_mem_virt2memseg_list(addr) == NULL) { 776 rte_errno = EINVAL; 777 return -1; 778 } 779 780 return dev->bus->dma_map(dev, addr, iova, len); 781 } 782 783 int 784 rte_dev_dma_unmap(struct rte_device *dev, void *addr, uint64_t iova, 785 size_t len) 786 { 787 if (dev->bus->dma_unmap == NULL || len == 0) { 788 rte_errno = ENOTSUP; 789 return -1; 790 } 791 /* Memory must be registered through rte_extmem_* APIs */ 792 if (rte_mem_virt2memseg_list(addr) == NULL) { 793 rte_errno = EINVAL; 794 return -1; 795 } 796 797 return dev->bus->dma_unmap(dev, addr, iova, len); 798 } 799