Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux
1
fork

Configure Feed

Select the types of activity you want to include in your feed.

Merge tag 'for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/rdma/rdma

Pull rdma fixes from Doug Ledford:

- Various driver bug fixes in mlx5, mlx4, bnxt_re and qedr, ranging
from bugs under load to bad error case handling

- There in one largish patch fixing the locking in bnxt_re to avoid a
machine hard lock situation

- A few core bugs on error paths

- A patch to reduce stack usage in the new CQ API

- One mlx5 regression introduced in this merge window

- There were new syzkaller scripts written for the RDMA subsystem and
we are fixing issues found by the bot

- One of the commits (aa0de36a40f4 “RDMA/mlx5: Fix integer overflow
while resizing CQ”) is missing part of the commit log message and one
of the SOB lines. The original patch was from Leon Romanovsky, and a
cut-n-paste separator in the commit message confused patchworks which
then put the end of message separator in the wrong place in the
downloaded patch, and I didn’t notice in time. The patch made it into
the official branch, and the only way to fix it in-place was to
rebase. Given the pain that a rebase causes, and the fact that the
patch has relevant tags for stable and syzkaller, a revert of the
munged patch and a reapplication of the original patch with the log
message intact was done.

* tag 'for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/rdma/rdma: (25 commits)
RDMA/mlx5: Fix integer overflow while resizing CQ
Revert "RDMA/mlx5: Fix integer overflow while resizing CQ"
RDMA/ucma: Check that user doesn't overflow QP state
RDMA/mlx5: Fix integer overflow while resizing CQ
RDMA/ucma: Limit possible option size
IB/core: Fix possible crash to access NULL netdev
RDMA/bnxt_re: Avoid Hard lockup during error CQE processing
RDMA/core: Reduce poll batch for direct cq polling
IB/mlx5: Fix an error code in __mlx5_ib_modify_qp()
IB/mlx5: When not in dual port RoCE mode, use provided port as native
IB/mlx4: Include GID type when deleting GIDs from HW table under RoCE
IB/mlx4: Fix corruption of RoCEv2 IPv4 GIDs
RDMA/qedr: Fix iWARP write and send with immediate
RDMA/qedr: Fix kernel panic when running fio over NFSoRDMA
RDMA/qedr: Fix iWARP connect with port mapper
RDMA/qedr: Fix ipv6 destination address resolution
IB/core : Add null pointer check in addr_resolve
RDMA/bnxt_re: Fix the ib_reg failure cleanup
RDMA/bnxt_re: Fix incorrect DB offset calculation
RDMA/bnxt_re: Unconditionly fence non wire memory operations
...

+192 -156
+5 -10
drivers/infiniband/core/addr.c
··· 550 550 dst_release(dst); 551 551 } 552 552 553 - if (ndev->flags & IFF_LOOPBACK) { 554 - ret = rdma_translate_ip(dst_in, addr); 555 - /* 556 - * Put the loopback device and get the translated 557 - * device instead. 558 - */ 553 + if (ndev) { 554 + if (ndev->flags & IFF_LOOPBACK) 555 + ret = rdma_translate_ip(dst_in, addr); 556 + else 557 + addr->bound_dev_if = ndev->ifindex; 559 558 dev_put(ndev); 560 - ndev = dev_get_by_index(addr->net, addr->bound_dev_if); 561 - } else { 562 - addr->bound_dev_if = ndev->ifindex; 563 559 } 564 - dev_put(ndev); 565 560 566 561 return ret; 567 562 }
+11 -10
drivers/infiniband/core/cq.c
··· 17 17 18 18 /* # of WCs to poll for with a single call to ib_poll_cq */ 19 19 #define IB_POLL_BATCH 16 20 + #define IB_POLL_BATCH_DIRECT 8 20 21 21 22 /* # of WCs to iterate over before yielding */ 22 23 #define IB_POLL_BUDGET_IRQ 256 ··· 26 25 #define IB_POLL_FLAGS \ 27 26 (IB_CQ_NEXT_COMP | IB_CQ_REPORT_MISSED_EVENTS) 28 27 29 - static int __ib_process_cq(struct ib_cq *cq, int budget, struct ib_wc *poll_wc) 28 + static int __ib_process_cq(struct ib_cq *cq, int budget, struct ib_wc *wcs, 29 + int batch) 30 30 { 31 31 int i, n, completed = 0; 32 - struct ib_wc *wcs = poll_wc ? : cq->wc; 33 32 34 33 /* 35 34 * budget might be (-1) if the caller does not 36 35 * want to bound this call, thus we need unsigned 37 36 * minimum here. 38 37 */ 39 - while ((n = ib_poll_cq(cq, min_t(u32, IB_POLL_BATCH, 40 - budget - completed), wcs)) > 0) { 38 + while ((n = ib_poll_cq(cq, min_t(u32, batch, 39 + budget - completed), wcs)) > 0) { 41 40 for (i = 0; i < n; i++) { 42 41 struct ib_wc *wc = &wcs[i]; 43 42 ··· 49 48 50 49 completed += n; 51 50 52 - if (n != IB_POLL_BATCH || 53 - (budget != -1 && completed >= budget)) 51 + if (n != batch || (budget != -1 && completed >= budget)) 54 52 break; 55 53 } 56 54 ··· 72 72 */ 73 73 int ib_process_cq_direct(struct ib_cq *cq, int budget) 74 74 { 75 - struct ib_wc wcs[IB_POLL_BATCH]; 75 + struct ib_wc wcs[IB_POLL_BATCH_DIRECT]; 76 76 77 - return __ib_process_cq(cq, budget, wcs); 77 + return __ib_process_cq(cq, budget, wcs, IB_POLL_BATCH_DIRECT); 78 78 } 79 79 EXPORT_SYMBOL(ib_process_cq_direct); 80 80 ··· 88 88 struct ib_cq *cq = container_of(iop, struct ib_cq, iop); 89 89 int completed; 90 90 91 - completed = __ib_process_cq(cq, budget, NULL); 91 + completed = __ib_process_cq(cq, budget, cq->wc, IB_POLL_BATCH); 92 92 if (completed < budget) { 93 93 irq_poll_complete(&cq->iop); 94 94 if (ib_req_notify_cq(cq, IB_POLL_FLAGS) > 0) ··· 108 108 struct ib_cq *cq = container_of(work, struct ib_cq, work); 109 109 int completed; 110 110 111 - completed = __ib_process_cq(cq, IB_POLL_BUDGET_WORKQUEUE, NULL); 111 + completed = __ib_process_cq(cq, IB_POLL_BUDGET_WORKQUEUE, cq->wc, 112 + IB_POLL_BATCH); 112 113 if (completed >= IB_POLL_BUDGET_WORKQUEUE || 113 114 ib_req_notify_cq(cq, IB_POLL_FLAGS) > 0) 114 115 queue_work(ib_comp_wq, &cq->work);
+4 -2
drivers/infiniband/core/device.c
··· 536 536 ret = device->query_device(device, &device->attrs, &uhw); 537 537 if (ret) { 538 538 pr_warn("Couldn't query the device attributes\n"); 539 - goto cache_cleanup; 539 + goto cg_cleanup; 540 540 } 541 541 542 542 ret = ib_device_register_sysfs(device, port_callback); 543 543 if (ret) { 544 544 pr_warn("Couldn't register device %s with driver model\n", 545 545 device->name); 546 - goto cache_cleanup; 546 + goto cg_cleanup; 547 547 } 548 548 549 549 device->reg_state = IB_DEV_REGISTERED; ··· 559 559 mutex_unlock(&device_mutex); 560 560 return 0; 561 561 562 + cg_cleanup: 563 + ib_device_unregister_rdmacg(device); 562 564 cache_cleanup: 563 565 ib_cache_cleanup_one(device); 564 566 ib_cache_release_one(device);
+3 -4
drivers/infiniband/core/sa_query.c
··· 1291 1291 1292 1292 resolved_dev = dev_get_by_index(dev_addr.net, 1293 1293 dev_addr.bound_dev_if); 1294 - if (resolved_dev->flags & IFF_LOOPBACK) { 1295 - dev_put(resolved_dev); 1296 - resolved_dev = idev; 1297 - dev_hold(resolved_dev); 1294 + if (!resolved_dev) { 1295 + dev_put(idev); 1296 + return -ENODEV; 1298 1297 } 1299 1298 ndev = ib_get_ndev_from_path(rec); 1300 1299 rcu_read_lock();
+6
drivers/infiniband/core/ucma.c
··· 1149 1149 if (copy_from_user(&cmd, inbuf, sizeof(cmd))) 1150 1150 return -EFAULT; 1151 1151 1152 + if (cmd.qp_state > IB_QPS_ERR) 1153 + return -EINVAL; 1154 + 1152 1155 ctx = ucma_get_ctx(file, cmd.id); 1153 1156 if (IS_ERR(ctx)) 1154 1157 return PTR_ERR(ctx); ··· 1296 1293 ctx = ucma_get_ctx(file, cmd.id); 1297 1294 if (IS_ERR(ctx)) 1298 1295 return PTR_ERR(ctx); 1296 + 1297 + if (unlikely(cmd.optval > KMALLOC_MAX_SIZE)) 1298 + return -EINVAL; 1299 1299 1300 1300 optval = memdup_user((void __user *) (unsigned long) cmd.optval, 1301 1301 cmd.optlen);
+19 -7
drivers/infiniband/hw/bnxt_re/ib_verbs.c
··· 785 785 return 0; 786 786 } 787 787 788 - static unsigned long bnxt_re_lock_cqs(struct bnxt_re_qp *qp) 788 + unsigned long bnxt_re_lock_cqs(struct bnxt_re_qp *qp) 789 789 __acquires(&qp->scq->cq_lock) __acquires(&qp->rcq->cq_lock) 790 790 { 791 791 unsigned long flags; ··· 799 799 return flags; 800 800 } 801 801 802 - static void bnxt_re_unlock_cqs(struct bnxt_re_qp *qp, 803 - unsigned long flags) 802 + void bnxt_re_unlock_cqs(struct bnxt_re_qp *qp, 803 + unsigned long flags) 804 804 __releases(&qp->scq->cq_lock) __releases(&qp->rcq->cq_lock) 805 805 { 806 806 if (qp->rcq != qp->scq) ··· 1606 1606 int status; 1607 1607 union ib_gid sgid; 1608 1608 struct ib_gid_attr sgid_attr; 1609 + unsigned int flags; 1609 1610 u8 nw_type; 1610 1611 1611 1612 qp->qplib_qp.modify_flags = 0; ··· 1635 1634 dev_dbg(rdev_to_dev(rdev), 1636 1635 "Move QP = %p to flush list\n", 1637 1636 qp); 1637 + flags = bnxt_re_lock_cqs(qp); 1638 1638 bnxt_qplib_add_flush_qp(&qp->qplib_qp); 1639 + bnxt_re_unlock_cqs(qp, flags); 1639 1640 } 1640 1641 if (!qp->sumem && 1641 1642 qp->qplib_qp.state == CMDQ_MODIFY_QP_NEW_STATE_RESET) { 1642 1643 dev_dbg(rdev_to_dev(rdev), 1643 1644 "Move QP = %p out of flush list\n", 1644 1645 qp); 1646 + flags = bnxt_re_lock_cqs(qp); 1645 1647 bnxt_qplib_clean_qp(&qp->qplib_qp); 1648 + bnxt_re_unlock_cqs(qp, flags); 1646 1649 } 1647 1650 } 1648 1651 if (qp_attr_mask & IB_QP_EN_SQD_ASYNC_NOTIFY) { ··· 2232 2227 wqe->type = BNXT_QPLIB_SWQE_TYPE_LOCAL_INV; 2233 2228 wqe->local_inv.inv_l_key = wr->ex.invalidate_rkey; 2234 2229 2230 + /* Need unconditional fence for local invalidate 2231 + * opcode to work as expected. 2232 + */ 2233 + wqe->flags |= BNXT_QPLIB_SWQE_FLAGS_UC_FENCE; 2234 + 2235 2235 if (wr->send_flags & IB_SEND_SIGNALED) 2236 2236 wqe->flags |= BNXT_QPLIB_SWQE_FLAGS_SIGNAL_COMP; 2237 - if (wr->send_flags & IB_SEND_FENCE) 2238 - wqe->flags |= BNXT_QPLIB_SWQE_FLAGS_UC_FENCE; 2239 2237 if (wr->send_flags & IB_SEND_SOLICITED) 2240 2238 wqe->flags |= BNXT_QPLIB_SWQE_FLAGS_SOLICIT_EVENT; 2241 2239 ··· 2259 2251 wqe->frmr.levels = qplib_frpl->hwq.level + 1; 2260 2252 wqe->type = BNXT_QPLIB_SWQE_TYPE_REG_MR; 2261 2253 2262 - if (wr->wr.send_flags & IB_SEND_FENCE) 2263 - wqe->flags |= BNXT_QPLIB_SWQE_FLAGS_UC_FENCE; 2254 + /* Need unconditional fence for reg_mr 2255 + * opcode to function as expected. 2256 + */ 2257 + 2258 + wqe->flags |= BNXT_QPLIB_SWQE_FLAGS_UC_FENCE; 2259 + 2264 2260 if (wr->wr.send_flags & IB_SEND_SIGNALED) 2265 2261 wqe->flags |= BNXT_QPLIB_SWQE_FLAGS_SIGNAL_COMP; 2266 2262
+3
drivers/infiniband/hw/bnxt_re/ib_verbs.h
··· 222 222 struct ib_udata *udata); 223 223 int bnxt_re_dealloc_ucontext(struct ib_ucontext *context); 224 224 int bnxt_re_mmap(struct ib_ucontext *context, struct vm_area_struct *vma); 225 + 226 + unsigned long bnxt_re_lock_cqs(struct bnxt_re_qp *qp); 227 + void bnxt_re_unlock_cqs(struct bnxt_re_qp *qp, unsigned long flags); 225 228 #endif /* __BNXT_RE_IB_VERBS_H__ */
+11 -1
drivers/infiniband/hw/bnxt_re/main.c
··· 730 730 struct bnxt_re_qp *qp) 731 731 { 732 732 struct ib_event event; 733 + unsigned int flags; 734 + 735 + if (qp->qplib_qp.state == CMDQ_MODIFY_QP_NEW_STATE_ERR) { 736 + flags = bnxt_re_lock_cqs(qp); 737 + bnxt_qplib_add_flush_qp(&qp->qplib_qp); 738 + bnxt_re_unlock_cqs(qp, flags); 739 + } 733 740 734 741 memset(&event, 0, sizeof(event)); 735 742 if (qp->qplib_qp.srq) { ··· 1423 1416 switch (re_work->event) { 1424 1417 case NETDEV_REGISTER: 1425 1418 rc = bnxt_re_ib_reg(rdev); 1426 - if (rc) 1419 + if (rc) { 1427 1420 dev_err(rdev_to_dev(rdev), 1428 1421 "Failed to register with IB: %#x", rc); 1422 + bnxt_re_remove_one(rdev); 1423 + bnxt_re_dev_unreg(rdev); 1424 + } 1429 1425 break; 1430 1426 case NETDEV_UP: 1431 1427 bnxt_re_dispatch_event(&rdev->ibdev, NULL, 1,
+24 -85
drivers/infiniband/hw/bnxt_re/qplib_fp.c
··· 88 88 } 89 89 } 90 90 91 - void bnxt_qplib_acquire_cq_locks(struct bnxt_qplib_qp *qp, 92 - unsigned long *flags) 93 - __acquires(&qp->scq->hwq.lock) __acquires(&qp->rcq->hwq.lock) 91 + static void bnxt_qplib_acquire_cq_flush_locks(struct bnxt_qplib_qp *qp, 92 + unsigned long *flags) 93 + __acquires(&qp->scq->flush_lock) __acquires(&qp->rcq->flush_lock) 94 94 { 95 - spin_lock_irqsave(&qp->scq->hwq.lock, *flags); 95 + spin_lock_irqsave(&qp->scq->flush_lock, *flags); 96 96 if (qp->scq == qp->rcq) 97 - __acquire(&qp->rcq->hwq.lock); 97 + __acquire(&qp->rcq->flush_lock); 98 98 else 99 - spin_lock(&qp->rcq->hwq.lock); 99 + spin_lock(&qp->rcq->flush_lock); 100 100 } 101 101 102 - void bnxt_qplib_release_cq_locks(struct bnxt_qplib_qp *qp, 103 - unsigned long *flags) 104 - __releases(&qp->scq->hwq.lock) __releases(&qp->rcq->hwq.lock) 102 + static void bnxt_qplib_release_cq_flush_locks(struct bnxt_qplib_qp *qp, 103 + unsigned long *flags) 104 + __releases(&qp->scq->flush_lock) __releases(&qp->rcq->flush_lock) 105 105 { 106 106 if (qp->scq == qp->rcq) 107 - __release(&qp->rcq->hwq.lock); 107 + __release(&qp->rcq->flush_lock); 108 108 else 109 - spin_unlock(&qp->rcq->hwq.lock); 110 - spin_unlock_irqrestore(&qp->scq->hwq.lock, *flags); 111 - } 112 - 113 - static struct bnxt_qplib_cq *bnxt_qplib_find_buddy_cq(struct bnxt_qplib_qp *qp, 114 - struct bnxt_qplib_cq *cq) 115 - { 116 - struct bnxt_qplib_cq *buddy_cq = NULL; 117 - 118 - if (qp->scq == qp->rcq) 119 - buddy_cq = NULL; 120 - else if (qp->scq == cq) 121 - buddy_cq = qp->rcq; 122 - else 123 - buddy_cq = qp->scq; 124 - return buddy_cq; 125 - } 126 - 127 - static void bnxt_qplib_lock_buddy_cq(struct bnxt_qplib_qp *qp, 128 - struct bnxt_qplib_cq *cq) 129 - __acquires(&buddy_cq->hwq.lock) 130 - { 131 - struct bnxt_qplib_cq *buddy_cq = NULL; 132 - 133 - buddy_cq = bnxt_qplib_find_buddy_cq(qp, cq); 134 - if (!buddy_cq) 135 - __acquire(&cq->hwq.lock); 136 - else 137 - spin_lock(&buddy_cq->hwq.lock); 138 - } 139 - 140 - static void bnxt_qplib_unlock_buddy_cq(struct bnxt_qplib_qp *qp, 141 - struct bnxt_qplib_cq *cq) 142 - __releases(&buddy_cq->hwq.lock) 143 - { 144 - struct bnxt_qplib_cq *buddy_cq = NULL; 145 - 146 - buddy_cq = bnxt_qplib_find_buddy_cq(qp, cq); 147 - if (!buddy_cq) 148 - __release(&cq->hwq.lock); 149 - else 150 - spin_unlock(&buddy_cq->hwq.lock); 109 + spin_unlock(&qp->rcq->flush_lock); 110 + spin_unlock_irqrestore(&qp->scq->flush_lock, *flags); 151 111 } 152 112 153 113 void bnxt_qplib_add_flush_qp(struct bnxt_qplib_qp *qp) 154 114 { 155 115 unsigned long flags; 156 116 157 - bnxt_qplib_acquire_cq_locks(qp, &flags); 117 + bnxt_qplib_acquire_cq_flush_locks(qp, &flags); 158 118 __bnxt_qplib_add_flush_qp(qp); 159 - bnxt_qplib_release_cq_locks(qp, &flags); 119 + bnxt_qplib_release_cq_flush_locks(qp, &flags); 160 120 } 161 121 162 122 static void __bnxt_qplib_del_flush_qp(struct bnxt_qplib_qp *qp) ··· 137 177 { 138 178 unsigned long flags; 139 179 140 - bnxt_qplib_acquire_cq_locks(qp, &flags); 180 + bnxt_qplib_acquire_cq_flush_locks(qp, &flags); 141 181 __clean_cq(qp->scq, (u64)(unsigned long)qp); 142 182 qp->sq.hwq.prod = 0; 143 183 qp->sq.hwq.cons = 0; ··· 146 186 qp->rq.hwq.cons = 0; 147 187 148 188 __bnxt_qplib_del_flush_qp(qp); 149 - bnxt_qplib_release_cq_locks(qp, &flags); 189 + bnxt_qplib_release_cq_flush_locks(qp, &flags); 150 190 } 151 191 152 192 static void bnxt_qpn_cqn_sched_task(struct work_struct *work) ··· 2067 2107 /* Must block new posting of SQ and RQ */ 2068 2108 qp->state = CMDQ_MODIFY_QP_NEW_STATE_ERR; 2069 2109 bnxt_qplib_cancel_phantom_processing(qp); 2070 - 2071 - /* Add qp to flush list of the CQ */ 2072 - __bnxt_qplib_add_flush_qp(qp); 2073 2110 } 2074 2111 2075 2112 /* Note: SQE is valid from sw_sq_cons up to cqe_sq_cons (exclusive) ··· 2242 2285 sw_sq_cons, cqe->wr_id, cqe->status); 2243 2286 cqe++; 2244 2287 (*budget)--; 2245 - bnxt_qplib_lock_buddy_cq(qp, cq); 2246 2288 bnxt_qplib_mark_qp_error(qp); 2247 - bnxt_qplib_unlock_buddy_cq(qp, cq); 2289 + /* Add qp to flush list of the CQ */ 2290 + bnxt_qplib_add_flush_qp(qp); 2248 2291 } else { 2249 2292 if (swq->flags & SQ_SEND_FLAGS_SIGNAL_COMP) { 2250 2293 /* Before we complete, do WA 9060 */ ··· 2360 2403 if (hwcqe->status != CQ_RES_RC_STATUS_OK) { 2361 2404 qp->state = CMDQ_MODIFY_QP_NEW_STATE_ERR; 2362 2405 /* Add qp to flush list of the CQ */ 2363 - bnxt_qplib_lock_buddy_cq(qp, cq); 2364 - __bnxt_qplib_add_flush_qp(qp); 2365 - bnxt_qplib_unlock_buddy_cq(qp, cq); 2406 + bnxt_qplib_add_flush_qp(qp); 2366 2407 } 2367 2408 } 2368 2409 ··· 2444 2489 if (hwcqe->status != CQ_RES_RC_STATUS_OK) { 2445 2490 qp->state = CMDQ_MODIFY_QP_NEW_STATE_ERR; 2446 2491 /* Add qp to flush list of the CQ */ 2447 - bnxt_qplib_lock_buddy_cq(qp, cq); 2448 - __bnxt_qplib_add_flush_qp(qp); 2449 - bnxt_qplib_unlock_buddy_cq(qp, cq); 2492 + bnxt_qplib_add_flush_qp(qp); 2450 2493 } 2451 2494 } 2452 2495 done: ··· 2454 2501 bool bnxt_qplib_is_cq_empty(struct bnxt_qplib_cq *cq) 2455 2502 { 2456 2503 struct cq_base *hw_cqe, **hw_cqe_ptr; 2457 - unsigned long flags; 2458 2504 u32 sw_cons, raw_cons; 2459 2505 bool rc = true; 2460 2506 2461 - spin_lock_irqsave(&cq->hwq.lock, flags); 2462 2507 raw_cons = cq->hwq.cons; 2463 2508 sw_cons = HWQ_CMP(raw_cons, &cq->hwq); 2464 2509 hw_cqe_ptr = (struct cq_base **)cq->hwq.pbl_ptr; ··· 2464 2513 2465 2514 /* Check for Valid bit. If the CQE is valid, return false */ 2466 2515 rc = !CQE_CMP_VALID(hw_cqe, raw_cons, cq->hwq.max_elements); 2467 - spin_unlock_irqrestore(&cq->hwq.lock, flags); 2468 2516 return rc; 2469 2517 } 2470 2518 ··· 2552 2602 if (hwcqe->status != CQ_RES_RC_STATUS_OK) { 2553 2603 qp->state = CMDQ_MODIFY_QP_NEW_STATE_ERR; 2554 2604 /* Add qp to flush list of the CQ */ 2555 - bnxt_qplib_lock_buddy_cq(qp, cq); 2556 - __bnxt_qplib_add_flush_qp(qp); 2557 - bnxt_qplib_unlock_buddy_cq(qp, cq); 2605 + bnxt_qplib_add_flush_qp(qp); 2558 2606 } 2559 2607 } 2560 2608 ··· 2667 2719 */ 2668 2720 2669 2721 /* Add qp to flush list of the CQ */ 2670 - bnxt_qplib_lock_buddy_cq(qp, cq); 2671 - __bnxt_qplib_add_flush_qp(qp); 2672 - bnxt_qplib_unlock_buddy_cq(qp, cq); 2722 + bnxt_qplib_add_flush_qp(qp); 2673 2723 done: 2674 2724 return rc; 2675 2725 } ··· 2696 2750 u32 budget = num_cqes; 2697 2751 unsigned long flags; 2698 2752 2699 - spin_lock_irqsave(&cq->hwq.lock, flags); 2753 + spin_lock_irqsave(&cq->flush_lock, flags); 2700 2754 list_for_each_entry(qp, &cq->sqf_head, sq_flush) { 2701 2755 dev_dbg(&cq->hwq.pdev->dev, 2702 2756 "QPLIB: FP: Flushing SQ QP= %p", ··· 2710 2764 qp); 2711 2765 __flush_rq(&qp->rq, qp, &cqe, &budget); 2712 2766 } 2713 - spin_unlock_irqrestore(&cq->hwq.lock, flags); 2767 + spin_unlock_irqrestore(&cq->flush_lock, flags); 2714 2768 2715 2769 return num_cqes - budget; 2716 2770 } ··· 2719 2773 int num_cqes, struct bnxt_qplib_qp **lib_qp) 2720 2774 { 2721 2775 struct cq_base *hw_cqe, **hw_cqe_ptr; 2722 - unsigned long flags; 2723 2776 u32 sw_cons, raw_cons; 2724 2777 int budget, rc = 0; 2725 2778 2726 - spin_lock_irqsave(&cq->hwq.lock, flags); 2727 2779 raw_cons = cq->hwq.cons; 2728 2780 budget = num_cqes; 2729 2781 ··· 2797 2853 bnxt_qplib_arm_cq(cq, DBR_DBR_TYPE_CQ); 2798 2854 } 2799 2855 exit: 2800 - spin_unlock_irqrestore(&cq->hwq.lock, flags); 2801 2856 return num_cqes - budget; 2802 2857 } 2803 2858 2804 2859 void bnxt_qplib_req_notify_cq(struct bnxt_qplib_cq *cq, u32 arm_type) 2805 2860 { 2806 - unsigned long flags; 2807 - 2808 - spin_lock_irqsave(&cq->hwq.lock, flags); 2809 2861 if (arm_type) 2810 2862 bnxt_qplib_arm_cq(cq, arm_type); 2811 2863 /* Using cq->arm_state variable to track whether to issue cq handler */ 2812 2864 atomic_set(&cq->arm_state, 1); 2813 - spin_unlock_irqrestore(&cq->hwq.lock, flags); 2814 2865 } 2815 2866 2816 2867 void bnxt_qplib_flush_cqn_wq(struct bnxt_qplib_qp *qp)
+12
drivers/infiniband/hw/bnxt_re/qplib_fp.h
··· 389 389 struct list_head sqf_head, rqf_head; 390 390 atomic_t arm_state; 391 391 spinlock_t compl_lock; /* synch CQ handlers */ 392 + /* Locking Notes: 393 + * QP can move to error state from modify_qp, async error event or error 394 + * CQE as part of poll_cq. When QP is moved to error state, it gets added 395 + * to two flush lists, one each for SQ and RQ. 396 + * Each flush list is protected by qplib_cq->flush_lock. Both scq and rcq 397 + * flush_locks should be acquired when QP is moved to error. The control path 398 + * operations(modify_qp and async error events) are synchronized with poll_cq 399 + * using upper level CQ locks (bnxt_re_cq->cq_lock) of both SCQ and RCQ. 400 + * The qplib_cq->flush_lock is required to synchronize two instances of poll_cq 401 + * of the same QP while manipulating the flush list. 402 + */ 403 + spinlock_t flush_lock; /* QP flush management */ 392 404 }; 393 405 394 406 #define BNXT_QPLIB_MAX_IRRQE_ENTRY_SIZE sizeof(struct xrrq_irrq)
+6 -3
drivers/infiniband/hw/bnxt_re/qplib_rcfw.c
··· 305 305 err_event->res_err_state_reason); 306 306 if (!qp) 307 307 break; 308 - bnxt_qplib_acquire_cq_locks(qp, &flags); 309 308 bnxt_qplib_mark_qp_error(qp); 310 - bnxt_qplib_release_cq_locks(qp, &flags); 309 + rcfw->aeq_handler(rcfw, qp_event, qp); 311 310 break; 312 311 default: 313 312 /* Command Response */ ··· 459 460 int rc; 460 461 461 462 RCFW_CMD_PREP(req, INITIALIZE_FW, cmd_flags); 462 - 463 + /* Supply (log-base-2-of-host-page-size - base-page-shift) 464 + * to bono to adjust the doorbell page sizes. 465 + */ 466 + req.log2_dbr_pg_size = cpu_to_le16(PAGE_SHIFT - 467 + RCFW_DBR_BASE_PAGE_SHIFT); 463 468 /* 464 469 * VFs need not setup the HW context area, PF 465 470 * shall setup this area for VF. Skipping the
+1
drivers/infiniband/hw/bnxt_re/qplib_rcfw.h
··· 49 49 #define RCFW_COMM_SIZE 0x104 50 50 51 51 #define RCFW_DBR_PCI_BAR_REGION 2 52 + #define RCFW_DBR_BASE_PAGE_SHIFT 12 52 53 53 54 #define RCFW_CMD_PREP(req, CMD, cmd_flags) \ 54 55 do { \
+2 -1
drivers/infiniband/hw/bnxt_re/qplib_sp.c
··· 139 139 attr->max_pkey = le32_to_cpu(sb->max_pkeys); 140 140 141 141 attr->max_inline_data = le32_to_cpu(sb->max_inline_data); 142 - attr->l2_db_size = (sb->l2_db_space_size + 1) * PAGE_SIZE; 142 + attr->l2_db_size = (sb->l2_db_space_size + 1) * 143 + (0x01 << RCFW_DBR_BASE_PAGE_SHIFT); 143 144 attr->max_sgid = le32_to_cpu(sb->max_gid); 144 145 145 146 bnxt_qplib_query_version(rcfw, attr->fw_ver);
+24 -1
drivers/infiniband/hw/bnxt_re/roce_hsi.h
··· 1761 1761 #define CMDQ_INITIALIZE_FW_TIM_PG_SIZE_PG_2M (0x3UL << 4) 1762 1762 #define CMDQ_INITIALIZE_FW_TIM_PG_SIZE_PG_8M (0x4UL << 4) 1763 1763 #define CMDQ_INITIALIZE_FW_TIM_PG_SIZE_PG_1G (0x5UL << 4) 1764 - __le16 reserved16; 1764 + /* This value is (log-base-2-of-DBR-page-size - 12). 1765 + * 0 for 4KB. HW supported values are enumerated below. 1766 + */ 1767 + __le16 log2_dbr_pg_size; 1768 + #define CMDQ_INITIALIZE_FW_LOG2_DBR_PG_SIZE_MASK 0xfUL 1769 + #define CMDQ_INITIALIZE_FW_LOG2_DBR_PG_SIZE_SFT 0 1770 + #define CMDQ_INITIALIZE_FW_LOG2_DBR_PG_SIZE_PG_4K 0x0UL 1771 + #define CMDQ_INITIALIZE_FW_LOG2_DBR_PG_SIZE_PG_8K 0x1UL 1772 + #define CMDQ_INITIALIZE_FW_LOG2_DBR_PG_SIZE_PG_16K 0x2UL 1773 + #define CMDQ_INITIALIZE_FW_LOG2_DBR_PG_SIZE_PG_32K 0x3UL 1774 + #define CMDQ_INITIALIZE_FW_LOG2_DBR_PG_SIZE_PG_64K 0x4UL 1775 + #define CMDQ_INITIALIZE_FW_LOG2_DBR_PG_SIZE_PG_128K 0x5UL 1776 + #define CMDQ_INITIALIZE_FW_LOG2_DBR_PG_SIZE_PG_256K 0x6UL 1777 + #define CMDQ_INITIALIZE_FW_LOG2_DBR_PG_SIZE_PG_512K 0x7UL 1778 + #define CMDQ_INITIALIZE_FW_LOG2_DBR_PG_SIZE_PG_1M 0x8UL 1779 + #define CMDQ_INITIALIZE_FW_LOG2_DBR_PG_SIZE_PG_2M 0x9UL 1780 + #define CMDQ_INITIALIZE_FW_LOG2_DBR_PG_SIZE_PG_4M 0xaUL 1781 + #define CMDQ_INITIALIZE_FW_LOG2_DBR_PG_SIZE_PG_8M 0xbUL 1782 + #define CMDQ_INITIALIZE_FW_LOG2_DBR_PG_SIZE_PG_16M 0xcUL 1783 + #define CMDQ_INITIALIZE_FW_LOG2_DBR_PG_SIZE_PG_32M 0xdUL 1784 + #define CMDQ_INITIALIZE_FW_LOG2_DBR_PG_SIZE_PG_64M 0xeUL 1785 + #define CMDQ_INITIALIZE_FW_LOG2_DBR_PG_SIZE_PG_128M 0xfUL 1786 + #define CMDQ_INITIALIZE_FW_LOG2_DBR_PG_SIZE_LAST \ 1787 + CMDQ_INITIALIZE_FW_LOG2_DBR_PG_SIZE_PG_128M 1765 1788 __le64 qpc_page_dir; 1766 1789 __le64 mrw_page_dir; 1767 1790 __le64 srq_page_dir;
+3 -1
drivers/infiniband/hw/mlx4/cq.c
··· 601 601 wc->dlid_path_bits = 0; 602 602 603 603 if (is_eth) { 604 + wc->slid = 0; 604 605 wc->vlan_id = be16_to_cpu(hdr->tun.sl_vid); 605 606 memcpy(&(wc->smac[0]), (char *)&hdr->tun.mac_31_0, 4); 606 607 memcpy(&(wc->smac[4]), (char *)&hdr->tun.slid_mac_47_32, 2); ··· 852 851 } 853 852 } 854 853 855 - wc->slid = be16_to_cpu(cqe->rlid); 856 854 g_mlpath_rqpn = be32_to_cpu(cqe->g_mlpath_rqpn); 857 855 wc->src_qp = g_mlpath_rqpn & 0xffffff; 858 856 wc->dlid_path_bits = (g_mlpath_rqpn >> 24) & 0x7f; ··· 860 860 wc->wc_flags |= mlx4_ib_ipoib_csum_ok(cqe->status, 861 861 cqe->checksum) ? IB_WC_IP_CSUM_OK : 0; 862 862 if (is_eth) { 863 + wc->slid = 0; 863 864 wc->sl = be16_to_cpu(cqe->sl_vid) >> 13; 864 865 if (be32_to_cpu(cqe->vlan_my_qpn) & 865 866 MLX4_CQE_CVLAN_PRESENT_MASK) { ··· 872 871 memcpy(wc->smac, cqe->smac, ETH_ALEN); 873 872 wc->wc_flags |= (IB_WC_WITH_VLAN | IB_WC_WITH_SMAC); 874 873 } else { 874 + wc->slid = be16_to_cpu(cqe->rlid); 875 875 wc->sl = be16_to_cpu(cqe->sl_vid) >> 12; 876 876 wc->vlan_id = 0xffff; 877 877 }
+7 -4
drivers/infiniband/hw/mlx4/main.c
··· 219 219 gid_tbl[i].version = 2; 220 220 if (!ipv6_addr_v4mapped((struct in6_addr *)&gids[i].gid)) 221 221 gid_tbl[i].type = 1; 222 - else 223 - memset(&gid_tbl[i].gid, 0, 12); 224 222 } 225 223 } 226 224 ··· 364 366 if (!gids) { 365 367 ret = -ENOMEM; 366 368 } else { 367 - for (i = 0; i < MLX4_MAX_PORT_GIDS; i++) 368 - memcpy(&gids[i].gid, &port_gid_table->gids[i].gid, sizeof(union ib_gid)); 369 + for (i = 0; i < MLX4_MAX_PORT_GIDS; i++) { 370 + memcpy(&gids[i].gid, 371 + &port_gid_table->gids[i].gid, 372 + sizeof(union ib_gid)); 373 + gids[i].gid_type = 374 + port_gid_table->gids[i].gid_type; 375 + } 369 376 } 370 377 } 371 378 spin_unlock_bh(&iboe->lock);
+8 -2
drivers/infiniband/hw/mlx5/cq.c
··· 226 226 wc->ex.invalidate_rkey = be32_to_cpu(cqe->imm_inval_pkey); 227 227 break; 228 228 } 229 - wc->slid = be16_to_cpu(cqe->slid); 230 229 wc->src_qp = be32_to_cpu(cqe->flags_rqpn) & 0xffffff; 231 230 wc->dlid_path_bits = cqe->ml_path; 232 231 g = (be32_to_cpu(cqe->flags_rqpn) >> 28) & 3; ··· 240 241 } 241 242 242 243 if (ll != IB_LINK_LAYER_ETHERNET) { 244 + wc->slid = be16_to_cpu(cqe->slid); 243 245 wc->sl = (be32_to_cpu(cqe->flags_rqpn) >> 24) & 0xf; 244 246 return; 245 247 } 246 248 249 + wc->slid = 0; 247 250 vlan_present = cqe->l4_l3_hdr_type & 0x1; 248 251 roce_packet_type = (be32_to_cpu(cqe->flags_rqpn) >> 24) & 0x3; 249 252 if (vlan_present) { ··· 1178 1177 if (ucmd.reserved0 || ucmd.reserved1) 1179 1178 return -EINVAL; 1180 1179 1181 - umem = ib_umem_get(context, ucmd.buf_addr, entries * ucmd.cqe_size, 1180 + /* check multiplication overflow */ 1181 + if (ucmd.cqe_size && SIZE_MAX / ucmd.cqe_size <= entries - 1) 1182 + return -EINVAL; 1183 + 1184 + umem = ib_umem_get(context, ucmd.buf_addr, 1185 + (size_t)ucmd.cqe_size * entries, 1182 1186 IB_ACCESS_LOCAL_WRITE, 1); 1183 1187 if (IS_ERR(umem)) { 1184 1188 err = PTR_ERR(umem);
+9 -12
drivers/infiniband/hw/mlx5/main.c
··· 245 245 struct mlx5_ib_multiport_info *mpi; 246 246 struct mlx5_ib_port *port; 247 247 248 + if (!mlx5_core_mp_enabled(ibdev->mdev) || 249 + ll != IB_LINK_LAYER_ETHERNET) { 250 + if (native_port_num) 251 + *native_port_num = ib_port_num; 252 + return ibdev->mdev; 253 + } 254 + 248 255 if (native_port_num) 249 256 *native_port_num = 1; 250 - 251 - if (!mlx5_core_mp_enabled(ibdev->mdev) || ll != IB_LINK_LAYER_ETHERNET) 252 - return ibdev->mdev; 253 257 254 258 port = &ibdev->port[ib_port_num - 1]; 255 259 if (!port) ··· 3267 3263 struct mlx5_ib_dev *ibdev; 3268 3264 struct ib_event ibev; 3269 3265 bool fatal = false; 3270 - u8 port = 0; 3266 + u8 port = (u8)work->param; 3271 3267 3272 3268 if (mlx5_core_is_mp_slave(work->dev)) { 3273 3269 ibdev = mlx5_ib_get_ibdev_from_mpi(work->context); ··· 3287 3283 case MLX5_DEV_EVENT_PORT_UP: 3288 3284 case MLX5_DEV_EVENT_PORT_DOWN: 3289 3285 case MLX5_DEV_EVENT_PORT_INITIALIZED: 3290 - port = (u8)work->param; 3291 - 3292 3286 /* In RoCE, port up/down events are handled in 3293 3287 * mlx5_netdev_event(). 3294 3288 */ ··· 3300 3298 3301 3299 case MLX5_DEV_EVENT_LID_CHANGE: 3302 3300 ibev.event = IB_EVENT_LID_CHANGE; 3303 - port = (u8)work->param; 3304 3301 break; 3305 3302 3306 3303 case MLX5_DEV_EVENT_PKEY_CHANGE: 3307 3304 ibev.event = IB_EVENT_PKEY_CHANGE; 3308 - port = (u8)work->param; 3309 - 3310 3305 schedule_work(&ibdev->devr.ports[port - 1].pkey_change_work); 3311 3306 break; 3312 3307 3313 3308 case MLX5_DEV_EVENT_GUID_CHANGE: 3314 3309 ibev.event = IB_EVENT_GID_CHANGE; 3315 - port = (u8)work->param; 3316 3310 break; 3317 3311 3318 3312 case MLX5_DEV_EVENT_CLIENT_REREG: 3319 3313 ibev.event = IB_EVENT_CLIENT_REREGISTER; 3320 - port = (u8)work->param; 3321 3314 break; 3322 3315 case MLX5_DEV_EVENT_DELAY_DROP_TIMEOUT: 3323 3316 schedule_work(&ibdev->delay_drop.delay_drop_work); ··· 3324 3327 ibev.device = &ibdev->ib_dev; 3325 3328 ibev.element.port_num = port; 3326 3329 3327 - if (port < 1 || port > ibdev->num_ports) { 3330 + if (!rdma_is_port_valid(&ibdev->ib_dev, port)) { 3328 3331 mlx5_ib_warn(ibdev, "warning: event on port %d\n", port); 3329 3332 goto out; 3330 3333 }
+1 -1
drivers/infiniband/hw/mlx5/mr.c
··· 1816 1816 1817 1817 mr->ibmr.iova = sg_dma_address(sg) + sg_offset; 1818 1818 mr->ibmr.length = 0; 1819 - mr->ndescs = sg_nents; 1820 1819 1821 1820 for_each_sg(sgl, sg, sg_nents, i) { 1822 1821 if (unlikely(i >= mr->max_descs)) ··· 1827 1828 1828 1829 sg_offset = 0; 1829 1830 } 1831 + mr->ndescs = i; 1830 1832 1831 1833 if (sg_offset_p) 1832 1834 *sg_offset_p = sg_offset;
+9 -2
drivers/infiniband/hw/mlx5/qp.c
··· 1584 1584 u32 uidx = MLX5_IB_DEFAULT_UIDX; 1585 1585 struct mlx5_ib_create_qp ucmd; 1586 1586 struct mlx5_ib_qp_base *base; 1587 + int mlx5_st; 1587 1588 void *qpc; 1588 1589 u32 *in; 1589 1590 int err; ··· 1592 1591 mutex_init(&qp->mutex); 1593 1592 spin_lock_init(&qp->sq.lock); 1594 1593 spin_lock_init(&qp->rq.lock); 1594 + 1595 + mlx5_st = to_mlx5_st(init_attr->qp_type); 1596 + if (mlx5_st < 0) 1597 + return -EINVAL; 1595 1598 1596 1599 if (init_attr->rwq_ind_tbl) { 1597 1600 if (!udata) ··· 1758 1753 1759 1754 qpc = MLX5_ADDR_OF(create_qp_in, in, qpc); 1760 1755 1761 - MLX5_SET(qpc, qpc, st, to_mlx5_st(init_attr->qp_type)); 1756 + MLX5_SET(qpc, qpc, st, mlx5_st); 1762 1757 MLX5_SET(qpc, qpc, pm_state, MLX5_QP_PM_MIGRATED); 1763 1758 1764 1759 if (init_attr->qp_type != MLX5_IB_QPT_REG_UMR) ··· 3100 3095 goto out; 3101 3096 3102 3097 if (mlx5_cur >= MLX5_QP_NUM_STATE || mlx5_new >= MLX5_QP_NUM_STATE || 3103 - !optab[mlx5_cur][mlx5_new]) 3098 + !optab[mlx5_cur][mlx5_new]) { 3099 + err = -EINVAL; 3104 3100 goto out; 3101 + } 3105 3102 3106 3103 op = optab[mlx5_cur][mlx5_new]; 3107 3104 optpar = ib_mask_to_mlx5_opt(attr_mask);
+11 -8
drivers/infiniband/hw/qedr/qedr_iw_cm.c
··· 458 458 } 459 459 return -EINVAL; 460 460 } 461 - neigh = dst_neigh_lookup(dst, &dst_in); 462 - 461 + neigh = dst_neigh_lookup(dst, &fl6.daddr); 463 462 if (neigh) { 464 463 rcu_read_lock(); 465 464 if (neigh->nud_state & NUD_VALID) { ··· 493 494 494 495 qp = idr_find(&dev->qpidr, conn_param->qpn); 495 496 496 - laddr = (struct sockaddr_in *)&cm_id->local_addr; 497 - raddr = (struct sockaddr_in *)&cm_id->remote_addr; 498 - laddr6 = (struct sockaddr_in6 *)&cm_id->local_addr; 499 - raddr6 = (struct sockaddr_in6 *)&cm_id->remote_addr; 497 + laddr = (struct sockaddr_in *)&cm_id->m_local_addr; 498 + raddr = (struct sockaddr_in *)&cm_id->m_remote_addr; 499 + laddr6 = (struct sockaddr_in6 *)&cm_id->m_local_addr; 500 + raddr6 = (struct sockaddr_in6 *)&cm_id->m_remote_addr; 501 + 502 + DP_DEBUG(dev, QEDR_MSG_IWARP, "MAPPED %d %d\n", 503 + ntohs(((struct sockaddr_in *)&cm_id->remote_addr)->sin_port), 504 + ntohs(raddr->sin_port)); 500 505 501 506 DP_DEBUG(dev, QEDR_MSG_IWARP, 502 507 "Connect source address: %pISpc, remote address: %pISpc\n", ··· 602 599 int rc; 603 600 int i; 604 601 605 - laddr = (struct sockaddr_in *)&cm_id->local_addr; 606 - laddr6 = (struct sockaddr_in6 *)&cm_id->local_addr; 602 + laddr = (struct sockaddr_in *)&cm_id->m_local_addr; 603 + laddr6 = (struct sockaddr_in6 *)&cm_id->m_local_addr; 607 604 608 605 DP_DEBUG(dev, QEDR_MSG_IWARP, 609 606 "Create Listener address: %pISpc\n", &cm_id->local_addr);
+12 -1
drivers/infiniband/hw/qedr/verbs.c
··· 3034 3034 3035 3035 switch (wr->opcode) { 3036 3036 case IB_WR_SEND_WITH_IMM: 3037 + if (unlikely(rdma_protocol_iwarp(&dev->ibdev, 1))) { 3038 + rc = -EINVAL; 3039 + *bad_wr = wr; 3040 + break; 3041 + } 3037 3042 wqe->req_type = RDMA_SQ_REQ_TYPE_SEND_WITH_IMM; 3038 3043 swqe = (struct rdma_sq_send_wqe_1st *)wqe; 3039 3044 swqe->wqe_size = 2; ··· 3080 3075 break; 3081 3076 3082 3077 case IB_WR_RDMA_WRITE_WITH_IMM: 3078 + if (unlikely(rdma_protocol_iwarp(&dev->ibdev, 1))) { 3079 + rc = -EINVAL; 3080 + *bad_wr = wr; 3081 + break; 3082 + } 3083 3083 wqe->req_type = RDMA_SQ_REQ_TYPE_RDMA_WR_WITH_IMM; 3084 3084 rwqe = (struct rdma_sq_rdma_wqe_1st *)wqe; 3085 3085 ··· 3734 3724 { 3735 3725 struct qedr_dev *dev = get_qedr_dev(ibcq->device); 3736 3726 struct qedr_cq *cq = get_qedr_cq(ibcq); 3737 - union rdma_cqe *cqe = cq->latest_cqe; 3727 + union rdma_cqe *cqe; 3738 3728 u32 old_cons, new_cons; 3739 3729 unsigned long flags; 3740 3730 int update = 0; ··· 3751 3741 return qedr_gsi_poll_cq(ibcq, num_entries, wc); 3752 3742 3753 3743 spin_lock_irqsave(&cq->cq_lock, flags); 3744 + cqe = cq->latest_cqe; 3754 3745 old_cons = qed_chain_get_cons_idx_u32(&cq->pbl); 3755 3746 while (num_entries && is_valid_cqe(cq, cqe)) { 3756 3747 struct qedr_qp *qp;
+1 -1
drivers/net/ethernet/mellanox/mlx5/core/health.c
··· 124 124 trigger_cmd_completions(dev); 125 125 } 126 126 127 - mlx5_core_event(dev, MLX5_DEV_EVENT_SYS_ERROR, 0); 127 + mlx5_core_event(dev, MLX5_DEV_EVENT_SYS_ERROR, 1); 128 128 mlx5_core_err(dev, "end\n"); 129 129 130 130 unlock: