aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorBart Van Assche <bart.vanassche@sandisk.com>2016-02-11 14:06:14 -0500
committerDoug Ledford <dledford@redhat.com>2016-02-29 17:12:35 -0500
commitf108f0f66a1f01ab077a88b1da2e2f092acd4b14 (patch)
tree246da5ad24f30e238d882b635dddc42e09d0c260
parent88936259c6a42c98e23181c9e1bba4b0bddb966a (diff)
IB/srpt: Fix srpt_close_session()
Avoid that srpt_close_session() waits if it doesn't have to wait. Additionally, increase the time during which srpt_close_session() waits until closing a session has finished. This makes it easier to detect session shutdown bugs. Signed-off-by: Bart Van Assche <bart.vanassche@sandisk.com> Reviewed-by: Christoph Hellwig <hch@lst.de> Reviewed-by: Sagi Grimberg <sagig@mellanox.com> Cc: Alex Estrin <alex.estrin@intel.com> Signed-off-by: Doug Ledford <dledford@redhat.com>
-rw-r--r--drivers/infiniband/ulp/srpt/ib_srpt.c31
1 files changed, 16 insertions, 15 deletions
diff --git a/drivers/infiniband/ulp/srpt/ib_srpt.c b/drivers/infiniband/ulp/srpt/ib_srpt.c
index bffca47ade4e..d6446068e884 100644
--- a/drivers/infiniband/ulp/srpt/ib_srpt.c
+++ b/drivers/infiniband/ulp/srpt/ib_srpt.c
@@ -1986,8 +1986,8 @@ static void srpt_release_channel_work(struct work_struct *w)
1986 struct se_session *se_sess; 1986 struct se_session *se_sess;
1987 1987
1988 ch = container_of(w, struct srpt_rdma_ch, release_work); 1988 ch = container_of(w, struct srpt_rdma_ch, release_work);
1989 pr_debug("ch = %p; ch->sess = %p; release_done = %p\n", ch, ch->sess, 1989 pr_debug("%s: %s-%d; release_done = %p\n", __func__, ch->sess_name,
1990 ch->release_done); 1990 ch->qp->qp_num, ch->release_done);
1991 1991
1992 sdev = ch->sport->sdev; 1992 sdev = ch->sport->sdev;
1993 BUG_ON(!sdev); 1993 BUG_ON(!sdev);
@@ -2011,11 +2011,10 @@ static void srpt_release_channel_work(struct work_struct *w)
2011 ch->rsp_size, DMA_TO_DEVICE); 2011 ch->rsp_size, DMA_TO_DEVICE);
2012 2012
2013 spin_lock_irq(&sdev->spinlock); 2013 spin_lock_irq(&sdev->spinlock);
2014 list_del(&ch->list); 2014 list_del_init(&ch->list);
2015 spin_unlock_irq(&sdev->spinlock);
2016
2017 if (ch->release_done) 2015 if (ch->release_done)
2018 complete(ch->release_done); 2016 complete(ch->release_done);
2017 spin_unlock_irq(&sdev->spinlock);
2019 2018
2020 wake_up(&sdev->ch_releaseQ); 2019 wake_up(&sdev->ch_releaseQ);
2021 2020
@@ -3025,24 +3024,26 @@ static void srpt_release_cmd(struct se_cmd *se_cmd)
3025static void srpt_close_session(struct se_session *se_sess) 3024static void srpt_close_session(struct se_session *se_sess)
3026{ 3025{
3027 DECLARE_COMPLETION_ONSTACK(release_done); 3026 DECLARE_COMPLETION_ONSTACK(release_done);
3028 struct srpt_rdma_ch *ch; 3027 struct srpt_rdma_ch *ch = se_sess->fabric_sess_ptr;
3029 struct srpt_device *sdev; 3028 struct srpt_device *sdev = ch->sport->sdev;
3030 unsigned long res; 3029 bool wait;
3031
3032 ch = se_sess->fabric_sess_ptr;
3033 WARN_ON(ch->sess != se_sess);
3034 3030
3035 pr_debug("ch %p state %d\n", ch, ch->state); 3031 pr_debug("ch %s-%d state %d\n", ch->sess_name, ch->qp->qp_num,
3032 ch->state);
3036 3033
3037 sdev = ch->sport->sdev;
3038 spin_lock_irq(&sdev->spinlock); 3034 spin_lock_irq(&sdev->spinlock);
3039 BUG_ON(ch->release_done); 3035 BUG_ON(ch->release_done);
3040 ch->release_done = &release_done; 3036 ch->release_done = &release_done;
3037 wait = !list_empty(&ch->list);
3041 __srpt_close_ch(ch); 3038 __srpt_close_ch(ch);
3042 spin_unlock_irq(&sdev->spinlock); 3039 spin_unlock_irq(&sdev->spinlock);
3043 3040
3044 res = wait_for_completion_timeout(&release_done, 60 * HZ); 3041 if (!wait)
3045 WARN_ON(res == 0); 3042 return;
3043
3044 while (wait_for_completion_timeout(&release_done, 180 * HZ) == 0)
3045 pr_info("%s(%s-%d state %d): still waiting ...\n", __func__,
3046 ch->sess_name, ch->qp->qp_num, ch->state);
3046} 3047}
3047 3048
3048/** 3049/**