History

IB/mlx5: Reset flow support for IB kernel ULPs

The driver exposes interfaces that directly relate to HW state. Upon fatal error, consumers of these interfaces (ULPs) that rely on completion of all their posted work-request could hang, thereby introducing dependencies in shutdown order. To prevent this from happening, we manage the relevant resources (CQs, QPs) that are used by the device. Upon a fatal error, we now generate simulated completions for outstanding WQEs that were not completed at the time the HW was reset. It includes invoking the completion event handler for all involved CQs so that the ULPs will poll those CQs. When polled we return simulated CQEs with IB_WC_WR_FLUSH_ERR return code enabling ULPs to clean up their resources and not wait forever for completions upon receiving remove_one. The above change requires an extra check in the data path to make sure that when device is in error state, the simulated CQEs will be returned and no further WQEs will be posted.

Maor Gottlieb committed 10 years ago

Commit 89ea94a1 parent 7c2344c7 files · +250 −21Browse files

Unified · Split

7 files
  1. drivers/infiniband/hw/mlx5/cq.c +86 −1
  2. drivers/infiniband/hw/mlx5/main.c +62 −0
  3. drivers/infiniband/hw/mlx5/mlx5_ib.h +8 −0
  4. drivers/infiniband/hw/mlx5/mr.c +4 −0
  5. drivers/infiniband/hw/mlx5/qp.c +79 −19
  6. drivers/infiniband/hw/mlx5/srq.c +9 −1
  7. include/linux/mlx5/cq.h +2 −0
drivers/infiniband/hw/mlx5/cq.c+86−1
@@ -424,6 +424,83 @@ static void get_sig_err_item(struct mlx5_sig_err_cqe *cqe, · 423 unmodified lines
424424 item->key = be32_to_cpu(cqe->mkey);
425425 }
426426
427+static void sw_send_comp(struct mlx5_ib_qp *qp, int num_entries,
428+ struct ib_wc *wc, int *npolled)
429+{
430+ struct mlx5_ib_wq *wq;
431+ unsigned int cur;
432+ unsigned int idx;
433+ int np;
434+ int i;
435+
436+ wq = &qp->sq;
437+ cur = wq->head - wq->tail;
438+ np = *npolled;
439+
440+ if (cur == 0)
441+ return;
442+
443+ for (i = 0; i < cur && np < num_entries; i++) {
444+ idx = wq->last_poll & (wq->wqe_cnt - 1);
445+ wc->wr_id = wq->wrid[idx];
446+ wc->status = IB_WC_WR_FLUSH_ERR;
447+ wc->vendor_err = MLX5_CQE_SYNDROME_WR_FLUSH_ERR;
448+ wq->tail++;
449+ np++;
450+ wc->qp = &qp->ibqp;
451+ wc++;
452+ wq->last_poll = wq->w_list[idx].next;
453+ }
454+ *npolled = np;
455+}
456+
457+static void sw_recv_comp(struct mlx5_ib_qp *qp, int num_entries,
458+ struct ib_wc *wc, int *npolled)
459+{
460+ struct mlx5_ib_wq *wq;
461+ unsigned int cur;
462+ int np;
463+ int i;
464+
465+ wq = &qp->rq;
466+ cur = wq->head - wq->tail;
467+ np = *npolled;
468+
469+ if (cur == 0)
470+ return;
471+
472+ for (i = 0; i < cur && np < num_entries; i++) {
473+ wc->wr_id = wq->wrid[wq->tail & (wq->wqe_cnt - 1)];
474+ wc->status = IB_WC_WR_FLUSH_ERR;
475+ wc->vendor_err = MLX5_CQE_SYNDROME_WR_FLUSH_ERR;
476+ wq->tail++;
477+ np++;
478+ wc->qp = &qp->ibqp;
479+ wc++;
480+ }
481+ *npolled = np;
482+}
483+
484+static void mlx5_ib_poll_sw_comp(struct mlx5_ib_cq *cq, int num_entries,
485+ struct ib_wc *wc, int *npolled)
486+{
487+ struct mlx5_ib_qp *qp;
488+
489+ *npolled = 0;
490+ /* Find uncompleted WQEs belonging to that cq and retrun mmics ones */
491+ list_for_each_entry(qp, &cq->list_send_qp, cq_send_list) {
492+ sw_send_comp(qp, num_entries, wc + *npolled, npolled);
493+ if (*npolled >= num_entries)
494+ return;
495+ }
496+
497+ list_for_each_entry(qp, &cq->list_recv_qp, cq_recv_list) {
498+ sw_recv_comp(qp, num_entries, wc + *npolled, npolled);
499+ if (*npolled >= num_entries)
500+ return;
501+ }
502+}
503+
427504 static int mlx5_poll_one(struct mlx5_ib_cq *cq,
428505 struct mlx5_ib_qp **cur_qp,
429506 struct ib_wc *wc)
@@ -594,12 +671,18 @@ int mlx5_ib_poll_cq(struct ib_cq *ibcq, int num_entries, struct ib_wc *wc) · 164 unmodified lines
594671 {
595672 struct mlx5_ib_cq *cq = to_mcq(ibcq);
596673 struct mlx5_ib_qp *cur_qp = NULL;
674+ struct mlx5_ib_dev *dev = to_mdev(cq->ibcq.device);
675+ struct mlx5_core_dev *mdev = dev->mdev;
597676 unsigned long flags;
598677 int soft_polled = 0;
599678 int npolled;
600679 int err = 0;
601680
602681 spin_lock_irqsave(&cq->lock, flags);
682+ if (mdev->state == MLX5_DEVICE_STATE_INTERNAL_ERROR) {
683+ mlx5_ib_poll_sw_comp(cq, num_entries, wc, &npolled);
684+ goto out;
685+ }
603686
604687 if (unlikely(!list_empty(&cq->wc_list)))
605688 soft_polled = poll_soft_wc(cq, num_entries, wc);
@@ -612,7 +695,7 @@ int mlx5_ib_poll_cq(struct ib_cq *ibcq, int num_entries, struct ib_wc *wc) · 6 unmodified lines
612695
613696 if (npolled)
614697 mlx5_cq_set_ci(&cq->mcq);
615−
698+out:
616699 spin_unlock_irqrestore(&cq->lock, flags);
617700
618701 if (err == 0 || err == -EAGAIN)
@@ -843,6 +926,8 @@ struct ib_cq *mlx5_ib_create_cq(struct ib_device *ibdev, · 224 unmodified lines
843926 cq->resize_buf = NULL;
844927 cq->resize_umem = NULL;
845928 cq->create_flags = attr->flags;
929+ INIT_LIST_HEAD(&cq->list_send_qp);
930+ INIT_LIST_HEAD(&cq->list_recv_qp);
846931
847932 if (context) {
848933 err = create_cq_user(dev, udata, context, cq, entries,
drivers/infiniband/hw/mlx5/main.c+62−0
@@ -1980,6 +1980,65 @@ static void pkey_change_handler(struct work_struct *work) · 1979 unmodified lines
19801980 mutex_unlock(&ports->devr->mutex);
19811981 }
19821982
1983+static void mlx5_ib_handle_internal_error(struct mlx5_ib_dev *ibdev)
1984+{
1985+ struct mlx5_ib_qp *mqp;
1986+ struct mlx5_ib_cq *send_mcq, *recv_mcq;
1987+ struct mlx5_core_cq *mcq;
1988+ struct list_head cq_armed_list;
1989+ unsigned long flags_qp;
1990+ unsigned long flags_cq;
1991+ unsigned long flags;
1992+
1993+ INIT_LIST_HEAD(&cq_armed_list);
1994+
1995+ /* Go over qp list reside on that ibdev, sync with create/destroy qp.*/
1996+ spin_lock_irqsave(&ibdev->reset_flow_resource_lock, flags);
1997+ list_for_each_entry(mqp, &ibdev->qp_list, qps_list) {
1998+ spin_lock_irqsave(&mqp->sq.lock, flags_qp);
1999+ if (mqp->sq.tail != mqp->sq.head) {
2000+ send_mcq = to_mcq(mqp->ibqp.send_cq);
2001+ spin_lock_irqsave(&send_mcq->lock, flags_cq);
2002+ if (send_mcq->mcq.comp &&
2003+ mqp->ibqp.send_cq->comp_handler) {
2004+ if (!send_mcq->mcq.reset_notify_added) {
2005+ send_mcq->mcq.reset_notify_added = 1;
2006+ list_add_tail(&send_mcq->mcq.reset_notify,
2007+ &cq_armed_list);
2008+ }
2009+ }
2010+ spin_unlock_irqrestore(&send_mcq->lock, flags_cq);
2011+ }
2012+ spin_unlock_irqrestore(&mqp->sq.lock, flags_qp);
2013+ spin_lock_irqsave(&mqp->rq.lock, flags_qp);
2014+ /* no handling is needed for SRQ */
2015+ if (!mqp->ibqp.srq) {
2016+ if (mqp->rq.tail != mqp->rq.head) {
2017+ recv_mcq = to_mcq(mqp->ibqp.recv_cq);
2018+ spin_lock_irqsave(&recv_mcq->lock, flags_cq);
2019+ if (recv_mcq->mcq.comp &&
2020+ mqp->ibqp.recv_cq->comp_handler) {
2021+ if (!recv_mcq->mcq.reset_notify_added) {
2022+ recv_mcq->mcq.reset_notify_added = 1;
2023+ list_add_tail(&recv_mcq->mcq.reset_notify,
2024+ &cq_armed_list);
2025+ }
2026+ }
2027+ spin_unlock_irqrestore(&recv_mcq->lock,
2028+ flags_cq);
2029+ }
2030+ }
2031+ spin_unlock_irqrestore(&mqp->rq.lock, flags_qp);
2032+ }
2033+ /*At that point all inflight post send were put to be executed as of we
2034+ * lock/unlock above locks Now need to arm all involved CQs.
2035+ */
2036+ list_for_each_entry(mcq, &cq_armed_list, reset_notify) {
2037+ mcq->comp(mcq);
2038+ }
2039+ spin_unlock_irqrestore(&ibdev->reset_flow_resource_lock, flags);
2040+}
2041+
19832042 static void mlx5_ib_event(struct mlx5_core_dev *dev, void *context,
19842043 enum mlx5_dev_event event, unsigned long param)
19852044 {
@@ -1992,6 +2051,7 @@ static void mlx5_ib_event(struct mlx5_core_dev *dev, void *context, · 6 unmodified lines
19922051 case MLX5_DEV_EVENT_SYS_ERROR:
19932052 ibdev->ib_active = false;
19942053 ibev.event = IB_EVENT_DEVICE_FATAL;
2054+ mlx5_ib_handle_internal_error(ibdev);
19952055 break;
19962056
19972057 case MLX5_DEV_EVENT_PORT_UP:
@@ -2595,6 +2655,8 @@ static void *mlx5_ib_add(struct mlx5_core_dev *mdev) · 597 unmodified lines
25952655
25962656 mutex_init(&dev->flow_db.lock);
25972657 mutex_init(&dev->cap_mask_mutex);
2658+ INIT_LIST_HEAD(&dev->qp_list);
2659+ spin_lock_init(&dev->reset_flow_resource_lock);
25982660
25992661 if (ll == IB_LINK_LAYER_ETHERNET) {
26002662 err = mlx5_enable_roce(dev);
drivers/infiniband/hw/mlx5/mlx5_ib.h+8−0
@@ -380,6 +380,9 @@ struct mlx5_ib_qp { · 379 unmodified lines
380380 spinlock_t disable_page_faults_lock;
381381 struct mlx5_ib_pfault pagefaults[MLX5_IB_PAGEFAULT_CONTEXTS];
382382 #endif
383+ struct list_head qps_list;
384+ struct list_head cq_recv_list;
385+ struct list_head cq_send_list;
383386 };
384387
385388 struct mlx5_ib_cq_buf {
@@ -441,6 +444,8 @@ struct mlx5_ib_cq { · 55 unmodified lines
441444 struct mlx5_ib_cq_buf *resize_buf;
442445 struct ib_umem *resize_umem;
443446 int cqe_size;
447+ struct list_head list_send_qp;
448+ struct list_head list_recv_qp;
444449 u32 create_flags;
445450 struct list_head wc_list;
446451 enum ib_cq_notify_flags notify_flags;
@@ -621,6 +626,9 @@ struct mlx5_ib_dev { · 174 unmodified lines
621626 struct srcu_struct mr_srcu;
622627 #endif
623628 struct mlx5_ib_flow_db flow_db;
629+ /* protect resources needed as part of reset flow */
630+ spinlock_t reset_flow_resource_lock;
631+ struct list_head qp_list;
624632 };
625633
626634 static inline struct mlx5_ib_cq *to_mibcq(struct mlx5_core_cq *mcq)
drivers/infiniband/hw/mlx5/mr.c+4−0
@@ -1193,12 +1193,16 @@ error: · 1192 unmodified lines
11931193
11941194 static int unreg_umr(struct mlx5_ib_dev *dev, struct mlx5_ib_mr *mr)
11951195 {
1196+ struct mlx5_core_dev *mdev = dev->mdev;
11961197 struct umr_common *umrc = &dev->umrc;
11971198 struct mlx5_ib_umr_context umr_context;
11981199 struct mlx5_umr_wr umrwr = {};
11991200 struct ib_send_wr *bad;
12001201 int err;
12011202
1203+ if (mdev->state == MLX5_DEVICE_STATE_INTERNAL_ERROR)
1204+ return 0;
1205+
12021206 mlx5_ib_init_umr_context(&umr_context);
12031207
12041208 umrwr.wr.wr_cqe = &umr_context.cqe;
drivers/infiniband/hw/mlx5/qp.c+79−19
@@ -77,6 +77,10 @@ struct mlx5_wqe_eth_pad { · 76 unmodified lines
7777 u8 rsvd0[16];
7878 };
7979
80+static void get_cqs(enum ib_qp_type qp_type,
81+ struct ib_cq *ib_send_cq, struct ib_cq *ib_recv_cq,
82+ struct mlx5_ib_cq **send_cq, struct mlx5_ib_cq **recv_cq);
83+
8084 static int is_qp0(enum ib_qp_type qp_type)
8185 {
8286 return qp_type == IB_QPT_SMI;
@@ -609,6 +613,11 @@ static int to_mlx5_st(enum ib_qp_type type) · 526 unmodified lines
609613 }
610614 }
611615
616+static void mlx5_ib_lock_cqs(struct mlx5_ib_cq *send_cq,
617+ struct mlx5_ib_cq *recv_cq);
618+static void mlx5_ib_unlock_cqs(struct mlx5_ib_cq *send_cq,
619+ struct mlx5_ib_cq *recv_cq);
620+
612621 static int uuarn_to_uar_index(struct mlx5_uuar_info *uuari, int uuarn)
613622 {
614623 return uuari->uars[uuarn / MLX5_BF_REGS_PER_PAGE].index;
@@ -1457,6 +1466,9 @@ static int create_qp_common(struct mlx5_ib_dev *dev, struct ib_pd *pd, · 842 unmodified lines
14571466 struct mlx5_ib_create_qp_resp resp;
14581467 struct mlx5_create_qp_mbox_in *in;
14591468 struct mlx5_ib_create_qp ucmd;
1469+ struct mlx5_ib_cq *send_cq;
1470+ struct mlx5_ib_cq *recv_cq;
1471+ unsigned long flags;
14601472 int inlen = sizeof(*in);
14611473 int err;
14621474 u32 uidx = MLX5_IB_DEFAULT_UIDX;
@@ -1714,6 +1726,23 @@ static int create_qp_common(struct mlx5_ib_dev *dev, struct ib_pd *pd, · 251 unmodified lines
17141726 base->container_mibqp = qp;
17151727 base->mqp.event = mlx5_ib_qp_event;
17161728
1729+ get_cqs(init_attr->qp_type, init_attr->send_cq, init_attr->recv_cq,
1730+ &send_cq, &recv_cq);
1731+ spin_lock_irqsave(&dev->reset_flow_resource_lock, flags);
1732+ mlx5_ib_lock_cqs(send_cq, recv_cq);
1733+ /* Maintain device to QPs access, needed for further handling via reset
1734+ * flow
1735+ */
1736+ list_add_tail(&qp->qps_list, &dev->qp_list);
1737+ /* Maintain CQ to QPs access, needed for further handling via reset flow
1738+ */
1739+ if (send_cq)
1740+ list_add_tail(&qp->cq_send_list, &send_cq->list_send_qp);
1741+ if (recv_cq)
1742+ list_add_tail(&qp->cq_recv_list, &recv_cq->list_recv_qp);
1743+ mlx5_ib_unlock_cqs(send_cq, recv_cq);
1744+ spin_unlock_irqrestore(&dev->reset_flow_resource_lock, flags);
1745+
17171746 return 0;
17181747
17191748 err_create:
@@ -1732,23 +1761,23 @@ static void mlx5_ib_lock_cqs(struct mlx5_ib_cq *send_cq, struct mlx5_ib_cq *recv · 12 unmodified lines
17321761 if (send_cq) {
17331762 if (recv_cq) {
17341763 if (send_cq->mcq.cqn < recv_cq->mcq.cqn) {
1735− spin_lock_irq(&send_cq->lock);
1764+ spin_lock(&send_cq->lock);
17361765 spin_lock_nested(&recv_cq->lock,
17371766 SINGLE_DEPTH_NESTING);
17381767 } else if (send_cq->mcq.cqn == recv_cq->mcq.cqn) {
1739− spin_lock_irq(&send_cq->lock);
1768+ spin_lock(&send_cq->lock);
17401769 __acquire(&recv_cq->lock);
17411770 } else {
1742− spin_lock_irq(&recv_cq->lock);
1771+ spin_lock(&recv_cq->lock);
17431772 spin_lock_nested(&send_cq->lock,
17441773 SINGLE_DEPTH_NESTING);
17451774 }
17461775 } else {
1747− spin_lock_irq(&send_cq->lock);
1776+ spin_lock(&send_cq->lock);
17481777 __acquire(&recv_cq->lock);
17491778 }
17501779 } else if (recv_cq) {
1751− spin_lock_irq(&recv_cq->lock);
1780+ spin_lock(&recv_cq->lock);
17521781 __acquire(&send_cq->lock);
17531782 } else {
17541783 __acquire(&send_cq->lock);
@@ -1763,21 +1792,21 @@ static void mlx5_ib_unlock_cqs(struct mlx5_ib_cq *send_cq, struct mlx5_ib_cq *re · 8 unmodified lines
17631792 if (recv_cq) {
17641793 if (send_cq->mcq.cqn < recv_cq->mcq.cqn) {
17651794 spin_unlock(&recv_cq->lock);
1766− spin_unlock_irq(&send_cq->lock);
1795+ spin_unlock(&send_cq->lock);
17671796 } else if (send_cq->mcq.cqn == recv_cq->mcq.cqn) {
17681797 __release(&recv_cq->lock);
1769− spin_unlock_irq(&send_cq->lock);
1798+ spin_unlock(&send_cq->lock);
17701799 } else {
17711800 spin_unlock(&send_cq->lock);
1772− spin_unlock_irq(&recv_cq->lock);
1801+ spin_unlock(&recv_cq->lock);
17731802 }
17741803 } else {
17751804 __release(&recv_cq->lock);
1776− spin_unlock_irq(&send_cq->lock);
1805+ spin_unlock(&send_cq->lock);
17771806 }
17781807 } else if (recv_cq) {
17791808 __release(&send_cq->lock);
1780− spin_unlock_irq(&recv_cq->lock);
1809+ spin_unlock(&recv_cq->lock);
17811810 } else {
17821811 __release(&recv_cq->lock);
17831812 __release(&send_cq->lock);
@@ -1789,17 +1818,18 @@ static struct mlx5_ib_pd *get_pd(struct mlx5_ib_qp *qp) · 5 unmodified lines
17891818 return to_mpd(qp->ibqp.pd);
17901819 }
17911820
1792−static void get_cqs(struct mlx5_ib_qp *qp,
1821+static void get_cqs(enum ib_qp_type qp_type,
1822+ struct ib_cq *ib_send_cq, struct ib_cq *ib_recv_cq,
17931823 struct mlx5_ib_cq **send_cq, struct mlx5_ib_cq **recv_cq)
17941824 {
1795− switch (qp->ibqp.qp_type) {
1825+ switch (qp_type) {
17961826 case IB_QPT_XRC_TGT:
17971827 *send_cq = NULL;
17981828 *recv_cq = NULL;
17991829 break;
18001830 case MLX5_IB_QPT_REG_UMR:
18011831 case IB_QPT_XRC_INI:
1802− *send_cq = to_mcq(qp->ibqp.send_cq);
1832+ *send_cq = ib_send_cq ? to_mcq(ib_send_cq) : NULL;
18031833 *recv_cq = NULL;
18041834 break;
18051835
@@ -1811,8 +1841,8 @@ static void get_cqs(struct mlx5_ib_qp *qp, · 5 unmodified lines
18111841 case IB_QPT_RAW_IPV6:
18121842 case IB_QPT_RAW_ETHERTYPE:
18131843 case IB_QPT_RAW_PACKET:
1814− *send_cq = to_mcq(qp->ibqp.send_cq);
1815− *recv_cq = to_mcq(qp->ibqp.recv_cq);
1844+ *send_cq = ib_send_cq ? to_mcq(ib_send_cq) : NULL;
1845+ *recv_cq = ib_recv_cq ? to_mcq(ib_recv_cq) : NULL;
18161846 break;
18171847
18181848 case IB_QPT_MAX:
@@ -1831,6 +1861,7 @@ static void destroy_qp_common(struct mlx5_ib_dev *dev, struct mlx5_ib_qp *qp) · 12 unmodified lines
18311861 struct mlx5_ib_cq *send_cq, *recv_cq;
18321862 struct mlx5_ib_qp_base *base = &qp->trans_qp.base;
18331863 struct mlx5_modify_qp_mbox_in *in;
1864+ unsigned long flags;
18341865 int err;
18351866
18361867 if (qp->ibqp.rwq_ind_tbl) {
@@ -1861,17 +1892,28 @@ static void destroy_qp_common(struct mlx5_ib_dev *dev, struct mlx5_ib_qp *qp) · 24 unmodified lines
18611892 base->mqp.qpn);
18621893 }
18631894
1864− get_cqs(qp, &send_cq, &recv_cq);
1895+ get_cqs(qp->ibqp.qp_type, qp->ibqp.send_cq, qp->ibqp.recv_cq,
1896+ &send_cq, &recv_cq);
1897+
1898+ spin_lock_irqsave(&dev->reset_flow_resource_lock, flags);
1899+ mlx5_ib_lock_cqs(send_cq, recv_cq);
1900+ /* del from lists under both locks above to protect reset flow paths */
1901+ list_del(&qp->qps_list);
1902+ if (send_cq)
1903+ list_del(&qp->cq_send_list);
1904+
1905+ if (recv_cq)
1906+ list_del(&qp->cq_recv_list);
18651907
18661908 if (qp->create_type == MLX5_QP_KERNEL) {
1867− mlx5_ib_lock_cqs(send_cq, recv_cq);
18681909 __mlx5_ib_cq_clean(recv_cq, base->mqp.qpn,
18691910 qp->ibqp.srq ? to_msrq(qp->ibqp.srq) : NULL);
18701911 if (send_cq != recv_cq)
18711912 __mlx5_ib_cq_clean(send_cq, base->mqp.qpn,
18721913 NULL);
1873− mlx5_ib_unlock_cqs(send_cq, recv_cq);
18741914 }
1915+ mlx5_ib_unlock_cqs(send_cq, recv_cq);
1916+ spin_unlock_irqrestore(&dev->reset_flow_resource_lock, flags);
18751917
18761918 if (qp->ibqp.qp_type == IB_QPT_RAW_PACKET) {
18771919 destroy_raw_packet_qp(dev, qp);
@@ -2559,7 +2601,8 @@ static int __mlx5_ib_modify_qp(struct ib_qp *ibqp, · 681 unmodified lines
25592601 }
25602602
25612603 pd = get_pd(qp);
2562− get_cqs(qp, &send_cq, &recv_cq);
2604+ get_cqs(qp->ibqp.qp_type, qp->ibqp.send_cq, qp->ibqp.recv_cq,
2605+ &send_cq, &recv_cq);
25632606
25642607 context->flags_pd = cpu_to_be32(pd ? pd->pdn : to_mpd(dev->devr.p0)->pdn);
25652608 context->cqn_send = send_cq ? cpu_to_be32(send_cq->mcq.cqn) : 0;
@@ -3658,6 +3701,7 @@ int mlx5_ib_post_send(struct ib_qp *ibqp, struct ib_send_wr *wr, · 1092 unmodified lines
36583701 {
36593702 struct mlx5_wqe_ctrl_seg *ctrl = NULL; /* compiler warning */
36603703 struct mlx5_ib_dev *dev = to_mdev(ibqp->device);
3704+ struct mlx5_core_dev *mdev = dev->mdev;
36613705 struct mlx5_ib_qp *qp;
36623706 struct mlx5_ib_mr *mr;
36633707 struct mlx5_wqe_data_seg *dpseg;
@@ -3685,6 +3729,13 @@ int mlx5_ib_post_send(struct ib_qp *ibqp, struct ib_send_wr *wr, · 21 unmodified lines
36853729
36863730 spin_lock_irqsave(&qp->sq.lock, flags);
36873731
3732+ if (mdev->state == MLX5_DEVICE_STATE_INTERNAL_ERROR) {
3733+ err = -EIO;
3734+ *bad_wr = wr;
3735+ nreq = 0;
3736+ goto out;
3737+ }
3738+
36883739 for (nreq = 0; wr; nreq++, wr = wr->next) {
36893740 if (unlikely(wr->opcode >= ARRAY_SIZE(mlx5_ib_opcode))) {
36903741 mlx5_ib_warn(dev, "\n");
@@ -3986,6 +4037,8 @@ int mlx5_ib_post_recv(struct ib_qp *ibqp, struct ib_recv_wr *wr, · 295 unmodified lines
39864037 struct mlx5_ib_qp *qp = to_mqp(ibqp);
39874038 struct mlx5_wqe_data_seg *scat;
39884039 struct mlx5_rwqe_sig *sig;
4040+ struct mlx5_ib_dev *dev = to_mdev(ibqp->device);
4041+ struct mlx5_core_dev *mdev = dev->mdev;
39894042 unsigned long flags;
39904043 int err = 0;
39914044 int nreq;
@@ -3997,6 +4050,13 @@ int mlx5_ib_post_recv(struct ib_qp *ibqp, struct ib_recv_wr *wr, · 5 unmodified lines
39974050
39984051 spin_lock_irqsave(&qp->rq.lock, flags);
39994052
4053+ if (mdev->state == MLX5_DEVICE_STATE_INTERNAL_ERROR) {
4054+ err = -EIO;
4055+ *bad_wr = wr;
4056+ nreq = 0;
4057+ goto out;
4058+ }
4059+
40004060 ind = qp->rq.head & (qp->rq.wqe_cnt - 1);
40014061
40024062 for (nreq = 0; wr; nreq++, wr = wr->next) {
drivers/infiniband/hw/mlx5/srq.c+9−1
@@ -458,6 +458,8 @@ int mlx5_ib_post_srq_recv(struct ib_srq *ibsrq, struct ib_recv_wr *wr, · 457 unmodified lines
458458 struct mlx5_ib_srq *srq = to_msrq(ibsrq);
459459 struct mlx5_wqe_srq_next_seg *next;
460460 struct mlx5_wqe_data_seg *scat;
461+ struct mlx5_ib_dev *dev = to_mdev(ibsrq->device);
462+ struct mlx5_core_dev *mdev = dev->mdev;
461463 unsigned long flags;
462464 int err = 0;
463465 int nreq;
@@ -465,6 +467,12 @@ int mlx5_ib_post_srq_recv(struct ib_srq *ibsrq, struct ib_recv_wr *wr, · 1 unmodified line
465467
466468 spin_lock_irqsave(&srq->lock, flags);
467469
470+ if (mdev->state == MLX5_DEVICE_STATE_INTERNAL_ERROR) {
471+ err = -EIO;
472+ *bad_wr = wr;
473+ goto out;
474+ }
475+
468476 for (nreq = 0; wr; nreq++, wr = wr->next) {
469477 if (unlikely(wr->num_sge > srq->msrq.max_gs)) {
470478 err = -EINVAL;
@@ -507,7 +515,7 @@ int mlx5_ib_post_srq_recv(struct ib_srq *ibsrq, struct ib_recv_wr *wr, · 36 unmodified lines
507515
508516 *srq->db.db = cpu_to_be32(srq->wqe_ctr);
509517 }
510−
518+out:
511519 spin_unlock_irqrestore(&srq->lock, flags);
512520
513521 return err;
include/linux/mlx5/cq.h+2−0
@@ -58,6 +58,8 @@ struct mlx5_core_cq { · 57 unmodified lines
5858 void (*comp)(struct mlx5_core_cq *);
5959 void *priv;
6060 } tasklet_ctx;
61+ int reset_notify_added;
62+ struct list_head reset_notify;
6163 };
6264
6365

Keyboard shortcuts

General

Show keyboard shortcuts
?
Focus the current search
/

Issues and pull requests

Open filters
f

Issues, pull requests and Inbox

Select next item
j↓
Select previous item
k↑
Open selected item
Enter
Dismiss filters or clear selection
Esc

Repository code

Go to file
t