aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--drivers/infiniband/hw/nes/nes_cm.c26
-rw-r--r--drivers/infiniband/hw/nes/nes_verbs.h7
2 files changed, 16 insertions, 17 deletions
diff --git a/drivers/infiniband/hw/nes/nes_cm.c b/drivers/infiniband/hw/nes/nes_cm.c
index fe08eb57c99f..d89bdee0cf55 100644
--- a/drivers/infiniband/hw/nes/nes_cm.c
+++ b/drivers/infiniband/hw/nes/nes_cm.c
@@ -2450,20 +2450,16 @@ static int nes_cm_init_tsa_conn(struct nes_qp *nesqp, struct nes_cm_node *cm_nod
2450 */ 2450 */
2451int nes_cm_disconn(struct nes_qp *nesqp) 2451int nes_cm_disconn(struct nes_qp *nesqp)
2452{ 2452{
2453 unsigned long flags; 2453 struct disconn_work *work;
2454 2454
2455 spin_lock_irqsave(&nesqp->lock, flags); 2455 work = kzalloc(sizeof *work, GFP_ATOMIC);
2456 if (nesqp->disconn_pending == 0) { 2456 if (!work)
2457 nesqp->disconn_pending++; 2457 return -ENOMEM; /* Timer will clean up */
2458 spin_unlock_irqrestore(&nesqp->lock, flags);
2459 nes_add_ref(&nesqp->ibqp);
2460 /* init our disconnect work element, to */
2461 INIT_WORK(&nesqp->disconn_work, nes_disconnect_worker);
2462
2463 queue_work(g_cm_core->disconn_wq, &nesqp->disconn_work);
2464 } else
2465 spin_unlock_irqrestore(&nesqp->lock, flags);
2466 2458
2459 nes_add_ref(&nesqp->ibqp);
2460 work->nesqp = nesqp;
2461 INIT_WORK(&work->work, nes_disconnect_worker);
2462 queue_work(g_cm_core->disconn_wq, &work->work);
2467 return 0; 2463 return 0;
2468} 2464}
2469 2465
@@ -2473,8 +2469,10 @@ int nes_cm_disconn(struct nes_qp *nesqp)
2473 */ 2469 */
2474static void nes_disconnect_worker(struct work_struct *work) 2470static void nes_disconnect_worker(struct work_struct *work)
2475{ 2471{
2476 struct nes_qp *nesqp = container_of(work, struct nes_qp, disconn_work); 2472 struct disconn_work *dwork = container_of(work, struct disconn_work, work);
2473 struct nes_qp *nesqp = dwork->nesqp;
2477 2474
2475 kfree(dwork);
2478 nes_debug(NES_DBG_CM, "processing AEQE id 0x%04X for QP%u.\n", 2476 nes_debug(NES_DBG_CM, "processing AEQE id 0x%04X for QP%u.\n",
2479 nesqp->last_aeq, nesqp->hwqp.qp_id); 2477 nesqp->last_aeq, nesqp->hwqp.qp_id);
2480 nes_cm_disconn_true(nesqp); 2478 nes_cm_disconn_true(nesqp);
@@ -2557,7 +2555,6 @@ static int nes_cm_disconn_true(struct nes_qp *nesqp)
2557 spin_lock_irqsave(&nesqp->lock, flags); 2555 spin_lock_irqsave(&nesqp->lock, flags);
2558 } 2556 }
2559 2557
2560 nesqp->disconn_pending = 0;
2561 /* There might have been another AE while the lock was released */ 2558 /* There might have been another AE while the lock was released */
2562 original_hw_tcp_state = nesqp->hw_tcp_state; 2559 original_hw_tcp_state = nesqp->hw_tcp_state;
2563 original_ibqp_state = nesqp->ibqp_state; 2560 original_ibqp_state = nesqp->ibqp_state;
@@ -2610,7 +2607,6 @@ static int nes_cm_disconn_true(struct nes_qp *nesqp)
2610 } 2607 }
2611 } 2608 }
2612 } else { 2609 } else {
2613 nesqp->disconn_pending = 0;
2614 spin_unlock_irqrestore(&nesqp->lock, flags); 2610 spin_unlock_irqrestore(&nesqp->lock, flags);
2615 } 2611 }
2616 2612
diff --git a/drivers/infiniband/hw/nes/nes_verbs.h b/drivers/infiniband/hw/nes/nes_verbs.h
index 41c07f29f7c9..7df34fea2888 100644
--- a/drivers/infiniband/hw/nes/nes_verbs.h
+++ b/drivers/infiniband/hw/nes/nes_verbs.h
@@ -119,6 +119,11 @@ struct nes_wq {
119 spinlock_t lock; 119 spinlock_t lock;
120}; 120};
121 121
122struct disconn_work {
123 struct work_struct work;
124 struct nes_qp *nesqp;
125};
126
122struct iw_cm_id; 127struct iw_cm_id;
123struct ietf_mpa_frame; 128struct ietf_mpa_frame;
124 129
@@ -127,7 +132,6 @@ struct nes_qp {
127 void *allocated_buffer; 132 void *allocated_buffer;
128 struct iw_cm_id *cm_id; 133 struct iw_cm_id *cm_id;
129 struct workqueue_struct *wq; 134 struct workqueue_struct *wq;
130 struct work_struct disconn_work;
131 struct nes_cq *nesscq; 135 struct nes_cq *nesscq;
132 struct nes_cq *nesrcq; 136 struct nes_cq *nesrcq;
133 struct nes_pd *nespd; 137 struct nes_pd *nespd;
@@ -165,7 +169,6 @@ struct nes_qp {
165 u8 hw_iwarp_state; 169 u8 hw_iwarp_state;
166 u8 flush_issued; 170 u8 flush_issued;
167 u8 hw_tcp_state; 171 u8 hw_tcp_state;
168 u8 disconn_pending;
169 u8 destroyed; 172 u8 destroyed;
170}; 173};
171#endif /* NES_VERBS_H */ 174#endif /* NES_VERBS_H */