diff options
| author | Nitzan Carmi <nitzanc@mellanox.com> | 2018-01-17 06:01:14 -0500 |
|---|---|---|
| committer | Sagi Grimberg <sagi@grimberg.me> | 2018-02-14 08:44:22 -0500 |
| commit | 8000d1fdb07e365e6565c2415aefdfed15413794 (patch) | |
| tree | bb5c280bb677d06e0558f558359dacd8360679cd | |
| parent | 7756f72ccd4359c6df61fc431cd3b5b0a8639837 (diff) | |
nvme-rdma: fix sysfs invoked reset_ctrl error flow
When reset_controller that is invoked by sysfs fails,
it enters an error flow which practically removes the
nvme ctrl entirely (similar to delete_ctrl flow). It
causes the system to hang, since a sysfs attribute cannot
be unregistered by one of its own methods.
This can be fixed by calling delete_ctrl as a work rather
than sequential code. In addition, it should give the ctrl
a chance to recover using reconnection mechanism (consistant
with FC reset_ctrl error flow). Also, while we're here, return
suitable errno in case the reset ended with non live ctrl.
Signed-off-by: Nitzan Carmi <nitzanc@mellanox.com>
Reviewed-by: Max Gurtovoy <maxg@mellanox.com>
Signed-off-by: Sagi Grimberg <sagi@grimberg.me>
| -rw-r--r-- | drivers/nvme/host/core.c | 6 | ||||
| -rw-r--r-- | drivers/nvme/host/rdma.c | 7 |
2 files changed, 7 insertions, 6 deletions
diff --git a/drivers/nvme/host/core.c b/drivers/nvme/host/core.c index 52b3626fb64e..0fe7ea35c221 100644 --- a/drivers/nvme/host/core.c +++ b/drivers/nvme/host/core.c | |||
| @@ -120,8 +120,12 @@ int nvme_reset_ctrl_sync(struct nvme_ctrl *ctrl) | |||
| 120 | int ret; | 120 | int ret; |
| 121 | 121 | ||
| 122 | ret = nvme_reset_ctrl(ctrl); | 122 | ret = nvme_reset_ctrl(ctrl); |
| 123 | if (!ret) | 123 | if (!ret) { |
| 124 | flush_work(&ctrl->reset_work); | 124 | flush_work(&ctrl->reset_work); |
| 125 | if (ctrl->state != NVME_CTRL_LIVE) | ||
| 126 | ret = -ENETRESET; | ||
| 127 | } | ||
| 128 | |||
| 125 | return ret; | 129 | return ret; |
| 126 | } | 130 | } |
| 127 | EXPORT_SYMBOL_GPL(nvme_reset_ctrl_sync); | 131 | EXPORT_SYMBOL_GPL(nvme_reset_ctrl_sync); |
diff --git a/drivers/nvme/host/rdma.c b/drivers/nvme/host/rdma.c index 5e2cc4f0d207..3a51ed50eff2 100644 --- a/drivers/nvme/host/rdma.c +++ b/drivers/nvme/host/rdma.c | |||
| @@ -1784,11 +1784,8 @@ static void nvme_rdma_reset_ctrl_work(struct work_struct *work) | |||
| 1784 | return; | 1784 | return; |
| 1785 | 1785 | ||
| 1786 | out_fail: | 1786 | out_fail: |
| 1787 | dev_warn(ctrl->ctrl.device, "Removing after reset failure\n"); | 1787 | ++ctrl->ctrl.nr_reconnects; |
| 1788 | nvme_remove_namespaces(&ctrl->ctrl); | 1788 | nvme_rdma_reconnect_or_remove(ctrl); |
| 1789 | nvme_rdma_shutdown_ctrl(ctrl, true); | ||
| 1790 | nvme_uninit_ctrl(&ctrl->ctrl); | ||
| 1791 | nvme_put_ctrl(&ctrl->ctrl); | ||
| 1792 | } | 1789 | } |
| 1793 | 1790 | ||
| 1794 | static const struct nvme_ctrl_ops nvme_rdma_ctrl_ops = { | 1791 | static const struct nvme_ctrl_ops nvme_rdma_ctrl_ops = { |
