diff options
Diffstat (limited to 'drivers/infiniband/hw')
-rw-r--r-- | drivers/infiniband/hw/cxgb4/device.c | 111 | ||||
-rw-r--r-- | drivers/infiniband/hw/cxgb4/iw_cxgb4.h | 6 | ||||
-rw-r--r-- | drivers/infiniband/hw/cxgb4/provider.c | 2 |
3 files changed, 66 insertions, 53 deletions
diff --git a/drivers/infiniband/hw/cxgb4/device.c b/drivers/infiniband/hw/cxgb4/device.c index 8e70953c4f4..40a13cc633a 100644 --- a/drivers/infiniband/hw/cxgb4/device.c +++ b/drivers/infiniband/hw/cxgb4/device.c | |||
@@ -44,7 +44,7 @@ MODULE_DESCRIPTION("Chelsio T4 RDMA Driver"); | |||
44 | MODULE_LICENSE("Dual BSD/GPL"); | 44 | MODULE_LICENSE("Dual BSD/GPL"); |
45 | MODULE_VERSION(DRV_VERSION); | 45 | MODULE_VERSION(DRV_VERSION); |
46 | 46 | ||
47 | static LIST_HEAD(dev_list); | 47 | static LIST_HEAD(uld_ctx_list); |
48 | static DEFINE_MUTEX(dev_mutex); | 48 | static DEFINE_MUTEX(dev_mutex); |
49 | 49 | ||
50 | static struct dentry *c4iw_debugfs_root; | 50 | static struct dentry *c4iw_debugfs_root; |
@@ -370,18 +370,23 @@ static void c4iw_rdev_close(struct c4iw_rdev *rdev) | |||
370 | c4iw_destroy_resource(&rdev->resource); | 370 | c4iw_destroy_resource(&rdev->resource); |
371 | } | 371 | } |
372 | 372 | ||
373 | static void c4iw_remove(struct c4iw_dev *dev) | 373 | struct uld_ctx { |
374 | struct list_head entry; | ||
375 | struct cxgb4_lld_info lldi; | ||
376 | struct c4iw_dev *dev; | ||
377 | }; | ||
378 | |||
379 | static void c4iw_remove(struct uld_ctx *ctx) | ||
374 | { | 380 | { |
375 | PDBG("%s c4iw_dev %p\n", __func__, dev); | 381 | PDBG("%s c4iw_dev %p\n", __func__, ctx->dev); |
376 | list_del(&dev->entry); | 382 | c4iw_unregister_device(ctx->dev); |
377 | if (dev->registered) | 383 | c4iw_rdev_close(&ctx->dev->rdev); |
378 | c4iw_unregister_device(dev); | 384 | idr_destroy(&ctx->dev->cqidr); |
379 | c4iw_rdev_close(&dev->rdev); | 385 | idr_destroy(&ctx->dev->qpidr); |
380 | idr_destroy(&dev->cqidr); | 386 | idr_destroy(&ctx->dev->mmidr); |
381 | idr_destroy(&dev->qpidr); | 387 | iounmap(ctx->dev->rdev.oc_mw_kva); |
382 | idr_destroy(&dev->mmidr); | 388 | ib_dealloc_device(&ctx->dev->ibdev); |
383 | iounmap(dev->rdev.oc_mw_kva); | 389 | ctx->dev = NULL; |
384 | ib_dealloc_device(&dev->ibdev); | ||
385 | } | 390 | } |
386 | 391 | ||
387 | static struct c4iw_dev *c4iw_alloc(const struct cxgb4_lld_info *infop) | 392 | static struct c4iw_dev *c4iw_alloc(const struct cxgb4_lld_info *infop) |
@@ -402,13 +407,11 @@ static struct c4iw_dev *c4iw_alloc(const struct cxgb4_lld_info *infop) | |||
402 | devp->rdev.oc_mw_kva = ioremap_wc(devp->rdev.oc_mw_pa, | 407 | devp->rdev.oc_mw_kva = ioremap_wc(devp->rdev.oc_mw_pa, |
403 | devp->rdev.lldi.vr->ocq.size); | 408 | devp->rdev.lldi.vr->ocq.size); |
404 | 409 | ||
405 | printk(KERN_INFO MOD "ocq memory: " | 410 | PDBG(KERN_INFO MOD "ocq memory: " |
406 | "hw_start 0x%x size %u mw_pa 0x%lx mw_kva %p\n", | 411 | "hw_start 0x%x size %u mw_pa 0x%lx mw_kva %p\n", |
407 | devp->rdev.lldi.vr->ocq.start, devp->rdev.lldi.vr->ocq.size, | 412 | devp->rdev.lldi.vr->ocq.start, devp->rdev.lldi.vr->ocq.size, |
408 | devp->rdev.oc_mw_pa, devp->rdev.oc_mw_kva); | 413 | devp->rdev.oc_mw_pa, devp->rdev.oc_mw_kva); |
409 | 414 | ||
410 | mutex_lock(&dev_mutex); | ||
411 | |||
412 | ret = c4iw_rdev_open(&devp->rdev); | 415 | ret = c4iw_rdev_open(&devp->rdev); |
413 | if (ret) { | 416 | if (ret) { |
414 | mutex_unlock(&dev_mutex); | 417 | mutex_unlock(&dev_mutex); |
@@ -421,8 +424,6 @@ static struct c4iw_dev *c4iw_alloc(const struct cxgb4_lld_info *infop) | |||
421 | idr_init(&devp->qpidr); | 424 | idr_init(&devp->qpidr); |
422 | idr_init(&devp->mmidr); | 425 | idr_init(&devp->mmidr); |
423 | spin_lock_init(&devp->lock); | 426 | spin_lock_init(&devp->lock); |
424 | list_add_tail(&devp->entry, &dev_list); | ||
425 | mutex_unlock(&dev_mutex); | ||
426 | 427 | ||
427 | if (c4iw_debugfs_root) { | 428 | if (c4iw_debugfs_root) { |
428 | devp->debugfs_root = debugfs_create_dir( | 429 | devp->debugfs_root = debugfs_create_dir( |
@@ -435,7 +436,7 @@ static struct c4iw_dev *c4iw_alloc(const struct cxgb4_lld_info *infop) | |||
435 | 436 | ||
436 | static void *c4iw_uld_add(const struct cxgb4_lld_info *infop) | 437 | static void *c4iw_uld_add(const struct cxgb4_lld_info *infop) |
437 | { | 438 | { |
438 | struct c4iw_dev *dev; | 439 | struct uld_ctx *ctx; |
439 | static int vers_printed; | 440 | static int vers_printed; |
440 | int i; | 441 | int i; |
441 | 442 | ||
@@ -443,25 +444,33 @@ static void *c4iw_uld_add(const struct cxgb4_lld_info *infop) | |||
443 | printk(KERN_INFO MOD "Chelsio T4 RDMA Driver - version %s\n", | 444 | printk(KERN_INFO MOD "Chelsio T4 RDMA Driver - version %s\n", |
444 | DRV_VERSION); | 445 | DRV_VERSION); |
445 | 446 | ||
446 | dev = c4iw_alloc(infop); | 447 | ctx = kzalloc(sizeof *ctx, GFP_KERNEL); |
447 | if (IS_ERR(dev)) | 448 | if (!ctx) { |
449 | ctx = ERR_PTR(-ENOMEM); | ||
448 | goto out; | 450 | goto out; |
451 | } | ||
452 | ctx->lldi = *infop; | ||
449 | 453 | ||
450 | PDBG("%s found device %s nchan %u nrxq %u ntxq %u nports %u\n", | 454 | PDBG("%s found device %s nchan %u nrxq %u ntxq %u nports %u\n", |
451 | __func__, pci_name(dev->rdev.lldi.pdev), | 455 | __func__, pci_name(ctx->lldi.pdev), |
452 | dev->rdev.lldi.nchan, dev->rdev.lldi.nrxq, | 456 | ctx->lldi.nchan, ctx->lldi.nrxq, |
453 | dev->rdev.lldi.ntxq, dev->rdev.lldi.nports); | 457 | ctx->lldi.ntxq, ctx->lldi.nports); |
458 | |||
459 | mutex_lock(&dev_mutex); | ||
460 | list_add_tail(&ctx->entry, &uld_ctx_list); | ||
461 | mutex_unlock(&dev_mutex); | ||
454 | 462 | ||
455 | for (i = 0; i < dev->rdev.lldi.nrxq; i++) | 463 | for (i = 0; i < ctx->lldi.nrxq; i++) |
456 | PDBG("rxqid[%u] %u\n", i, dev->rdev.lldi.rxq_ids[i]); | 464 | PDBG("rxqid[%u] %u\n", i, ctx->lldi.rxq_ids[i]); |
457 | out: | 465 | out: |
458 | return dev; | 466 | return ctx; |
459 | } | 467 | } |
460 | 468 | ||
461 | static int c4iw_uld_rx_handler(void *handle, const __be64 *rsp, | 469 | static int c4iw_uld_rx_handler(void *handle, const __be64 *rsp, |
462 | const struct pkt_gl *gl) | 470 | const struct pkt_gl *gl) |
463 | { | 471 | { |
464 | struct c4iw_dev *dev = handle; | 472 | struct uld_ctx *ctx = handle; |
473 | struct c4iw_dev *dev = ctx->dev; | ||
465 | struct sk_buff *skb; | 474 | struct sk_buff *skb; |
466 | const struct cpl_act_establish *rpl; | 475 | const struct cpl_act_establish *rpl; |
467 | unsigned int opcode; | 476 | unsigned int opcode; |
@@ -503,47 +512,49 @@ nomem: | |||
503 | 512 | ||
504 | static int c4iw_uld_state_change(void *handle, enum cxgb4_state new_state) | 513 | static int c4iw_uld_state_change(void *handle, enum cxgb4_state new_state) |
505 | { | 514 | { |
506 | struct c4iw_dev *dev = handle; | 515 | struct uld_ctx *ctx = handle; |
507 | 516 | ||
508 | PDBG("%s new_state %u\n", __func__, new_state); | 517 | PDBG("%s new_state %u\n", __func__, new_state); |
509 | switch (new_state) { | 518 | switch (new_state) { |
510 | case CXGB4_STATE_UP: | 519 | case CXGB4_STATE_UP: |
511 | printk(KERN_INFO MOD "%s: Up\n", pci_name(dev->rdev.lldi.pdev)); | 520 | printk(KERN_INFO MOD "%s: Up\n", pci_name(ctx->lldi.pdev)); |
512 | if (!dev->registered) { | 521 | if (!ctx->dev) { |
513 | int ret; | 522 | int ret = 0; |
514 | ret = c4iw_register_device(dev); | 523 | |
515 | if (ret) | 524 | ctx->dev = c4iw_alloc(&ctx->lldi); |
525 | if (!IS_ERR(ctx->dev)) | ||
526 | ret = c4iw_register_device(ctx->dev); | ||
527 | if (IS_ERR(ctx->dev) || ret) | ||
516 | printk(KERN_ERR MOD | 528 | printk(KERN_ERR MOD |
517 | "%s: RDMA registration failed: %d\n", | 529 | "%s: RDMA registration failed: %d\n", |
518 | pci_name(dev->rdev.lldi.pdev), ret); | 530 | pci_name(ctx->lldi.pdev), ret); |
519 | } | 531 | } |
520 | break; | 532 | break; |
521 | case CXGB4_STATE_DOWN: | 533 | case CXGB4_STATE_DOWN: |
522 | printk(KERN_INFO MOD "%s: Down\n", | 534 | printk(KERN_INFO MOD "%s: Down\n", |
523 | pci_name(dev->rdev.lldi.pdev)); | 535 | pci_name(ctx->lldi.pdev)); |
524 | if (dev->registered) | 536 | if (ctx->dev) |
525 | c4iw_unregister_device(dev); | 537 | c4iw_remove(ctx); |
526 | break; | 538 | break; |
527 | case CXGB4_STATE_START_RECOVERY: | 539 | case CXGB4_STATE_START_RECOVERY: |
528 | printk(KERN_INFO MOD "%s: Fatal Error\n", | 540 | printk(KERN_INFO MOD "%s: Fatal Error\n", |
529 | pci_name(dev->rdev.lldi.pdev)); | 541 | pci_name(ctx->lldi.pdev)); |
530 | dev->rdev.flags |= T4_FATAL_ERROR; | 542 | if (ctx->dev) { |
531 | if (dev->registered) { | ||
532 | struct ib_event event; | 543 | struct ib_event event; |
533 | 544 | ||
545 | ctx->dev->rdev.flags |= T4_FATAL_ERROR; | ||
534 | memset(&event, 0, sizeof event); | 546 | memset(&event, 0, sizeof event); |
535 | event.event = IB_EVENT_DEVICE_FATAL; | 547 | event.event = IB_EVENT_DEVICE_FATAL; |
536 | event.device = &dev->ibdev; | 548 | event.device = &ctx->dev->ibdev; |
537 | ib_dispatch_event(&event); | 549 | ib_dispatch_event(&event); |
538 | c4iw_unregister_device(dev); | 550 | c4iw_remove(ctx); |
539 | } | 551 | } |
540 | break; | 552 | break; |
541 | case CXGB4_STATE_DETACH: | 553 | case CXGB4_STATE_DETACH: |
542 | printk(KERN_INFO MOD "%s: Detach\n", | 554 | printk(KERN_INFO MOD "%s: Detach\n", |
543 | pci_name(dev->rdev.lldi.pdev)); | 555 | pci_name(ctx->lldi.pdev)); |
544 | mutex_lock(&dev_mutex); | 556 | if (ctx->dev) |
545 | c4iw_remove(dev); | 557 | c4iw_remove(ctx); |
546 | mutex_unlock(&dev_mutex); | ||
547 | break; | 558 | break; |
548 | } | 559 | } |
549 | return 0; | 560 | return 0; |
@@ -576,11 +587,13 @@ static int __init c4iw_init_module(void) | |||
576 | 587 | ||
577 | static void __exit c4iw_exit_module(void) | 588 | static void __exit c4iw_exit_module(void) |
578 | { | 589 | { |
579 | struct c4iw_dev *dev, *tmp; | 590 | struct uld_ctx *ctx, *tmp; |
580 | 591 | ||
581 | mutex_lock(&dev_mutex); | 592 | mutex_lock(&dev_mutex); |
582 | list_for_each_entry_safe(dev, tmp, &dev_list, entry) { | 593 | list_for_each_entry_safe(ctx, tmp, &uld_ctx_list, entry) { |
583 | c4iw_remove(dev); | 594 | if (ctx->dev) |
595 | c4iw_remove(ctx); | ||
596 | kfree(ctx); | ||
584 | } | 597 | } |
585 | mutex_unlock(&dev_mutex); | 598 | mutex_unlock(&dev_mutex); |
586 | cxgb4_unregister_uld(CXGB4_ULD_RDMA); | 599 | cxgb4_unregister_uld(CXGB4_ULD_RDMA); |
diff --git a/drivers/infiniband/hw/cxgb4/iw_cxgb4.h b/drivers/infiniband/hw/cxgb4/iw_cxgb4.h index 3dcfe82b124..35d2a5dd9bb 100644 --- a/drivers/infiniband/hw/cxgb4/iw_cxgb4.h +++ b/drivers/infiniband/hw/cxgb4/iw_cxgb4.h | |||
@@ -170,6 +170,10 @@ static inline int c4iw_wait_for_reply(struct c4iw_rdev *rdev, | |||
170 | printk(KERN_ERR MOD "%s - Device %s not responding - " | 170 | printk(KERN_ERR MOD "%s - Device %s not responding - " |
171 | "tid %u qpid %u\n", func, | 171 | "tid %u qpid %u\n", func, |
172 | pci_name(rdev->lldi.pdev), hwtid, qpid); | 172 | pci_name(rdev->lldi.pdev), hwtid, qpid); |
173 | if (c4iw_fatal_error(rdev)) { | ||
174 | wr_waitp->ret = -EIO; | ||
175 | break; | ||
176 | } | ||
173 | to = to << 2; | 177 | to = to << 2; |
174 | } | 178 | } |
175 | } while (!ret); | 179 | } while (!ret); |
@@ -187,9 +191,7 @@ struct c4iw_dev { | |||
187 | struct idr qpidr; | 191 | struct idr qpidr; |
188 | struct idr mmidr; | 192 | struct idr mmidr; |
189 | spinlock_t lock; | 193 | spinlock_t lock; |
190 | struct list_head entry; | ||
191 | struct dentry *debugfs_root; | 194 | struct dentry *debugfs_root; |
192 | u8 registered; | ||
193 | }; | 195 | }; |
194 | 196 | ||
195 | static inline struct c4iw_dev *to_c4iw_dev(struct ib_device *ibdev) | 197 | static inline struct c4iw_dev *to_c4iw_dev(struct ib_device *ibdev) |
diff --git a/drivers/infiniband/hw/cxgb4/provider.c b/drivers/infiniband/hw/cxgb4/provider.c index f66dd8bf512..5b9e4220ca0 100644 --- a/drivers/infiniband/hw/cxgb4/provider.c +++ b/drivers/infiniband/hw/cxgb4/provider.c | |||
@@ -516,7 +516,6 @@ int c4iw_register_device(struct c4iw_dev *dev) | |||
516 | if (ret) | 516 | if (ret) |
517 | goto bail2; | 517 | goto bail2; |
518 | } | 518 | } |
519 | dev->registered = 1; | ||
520 | return 0; | 519 | return 0; |
521 | bail2: | 520 | bail2: |
522 | ib_unregister_device(&dev->ibdev); | 521 | ib_unregister_device(&dev->ibdev); |
@@ -535,6 +534,5 @@ void c4iw_unregister_device(struct c4iw_dev *dev) | |||
535 | c4iw_class_attributes[i]); | 534 | c4iw_class_attributes[i]); |
536 | ib_unregister_device(&dev->ibdev); | 535 | ib_unregister_device(&dev->ibdev); |
537 | kfree(dev->ibdev.iwcm); | 536 | kfree(dev->ibdev.iwcm); |
538 | dev->registered = 0; | ||
539 | return; | 537 | return; |
540 | } | 538 | } |