While running NVMe/oF wire unplug tests, we hit this warning in kernel/workqueue.c:check_flush_dependency(): WARN_ONCE(worker && ((worker->current_pwq->wq->flags & (WQ_MEM_RECLAIM | __WQ_LEGACY)) == WQ_MEM_RECLAIM), "workqueue: WQ_MEM_RECLAIM %s:%pf is flushing !WQ_MEM_RECLAIM %s:%pf", worker->current_pwq->wq->name, worker->current_func, target_wq->name, target_func); Which I think means we're flushing a workq that doesn't have WQ_MEM_RECLAIM set, from workqueue context that does have it set. Looking at rdma_addr_cancel() which is doing the flushing, it flushes the addr_wq which doesn't have MEM_RECLAIM set. Yet rdma_addr_cancel() is being called by the nvme host connection timeout/reconnect workqueue thread that does have WQ_MEM_RECLAIM set. So set WQ_MEM_RECLAIM on the addr_req workqueue. Signed-off-by: Steve Wise <swise@xxxxxxxxxxxxxxxxxxxxx> --- drivers/infiniband/core/addr.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/drivers/infiniband/core/addr.c b/drivers/infiniband/core/addr.c index 0dce94e3c495..1d88ee3ac8c7 100644 --- a/drivers/infiniband/core/addr.c +++ b/drivers/infiniband/core/addr.c @@ -868,7 +868,7 @@ static int netevent_callback(struct notifier_block *self, unsigned long event, int addr_init(void) { - addr_wq = alloc_ordered_workqueue("ib_addr", 0); + addr_wq = alloc_ordered_workqueue("ib_addr", WQ_MEM_RECLAIM); if (!addr_wq) return -ENOMEM; -- 1.8.3.1