From: Greg Kroah-Hartman Date: Fri, 29 Mar 2024 13:18:45 +0000 (+0100) Subject: 6.1-stable patches X-Git-Tag: v6.7.12~141 X-Git-Url: http://git.ipfire.org/?a=commitdiff_plain;h=81454d9a504f80d4e4e57f81fdb4634110079f26;p=thirdparty%2Fkernel%2Fstable-queue.git 6.1-stable patches added patches: blk-mq-release-scheduler-resource-when-request-completes.patch --- diff --git a/queue-6.1/blk-mq-release-scheduler-resource-when-request-completes.patch b/queue-6.1/blk-mq-release-scheduler-resource-when-request-completes.patch new file mode 100644 index 00000000000..b97152c0e52 --- /dev/null +++ b/queue-6.1/blk-mq-release-scheduler-resource-when-request-completes.patch @@ -0,0 +1,111 @@ +From e5c0ca13659e9d18f53368d651ed7e6e433ec1cf Mon Sep 17 00:00:00 2001 +From: Chengming Zhou +Date: Sun, 13 Aug 2023 23:23:25 +0800 +Subject: blk-mq: release scheduler resource when request completes + +From: Chengming Zhou + +commit e5c0ca13659e9d18f53368d651ed7e6e433ec1cf upstream. + +Chuck reported [1] an IO hang problem on NFS exports that reside on SATA +devices and bisected to commit 615939a2ae73 ("blk-mq: defer to the normal +submission path for post-flush requests"). + +We analysed the IO hang problem, found there are two postflush requests +waiting for each other. + +The first postflush request completed the REQ_FSEQ_DATA sequence, so go to +the REQ_FSEQ_POSTFLUSH sequence and added in the flush pending list, but +failed to blk_kick_flush() because of the second postflush request which +is inflight waiting in scheduler queue. + +The second postflush waiting in scheduler queue can't be dispatched because +the first postflush hasn't released scheduler resource even though it has +completed by itself. + +Fix it by releasing scheduler resource when the first postflush request +completed, so the second postflush can be dispatched and completed, then +make blk_kick_flush() succeed. + +While at it, remove the check for e->ops.finish_request, as all +schedulers set that. Reaffirm this requirement by adding a WARN_ON_ONCE() +at scheduler registration time, just like we do for insert_requests and +dispatch_request. + +[1] https://lore.kernel.org/all/7A57C7AE-A51A-4254-888B-FE15CA21F9E9@oracle.com/ + +Link: https://lore.kernel.org/linux-block/20230819031206.2744005-1-chengming.zhou@linux.dev/ +Reported-by: kernel test robot +Closes: https://lore.kernel.org/oe-lkp/202308172100.8ce4b853-oliver.sang@intel.com +Fixes: 615939a2ae73 ("blk-mq: defer to the normal submission path for post-flush requests") +Reported-by: Chuck Lever +Signed-off-by: Chengming Zhou +Tested-by: Chuck Lever +Link: https://lore.kernel.org/r/20230813152325.3017343-1-chengming.zhou@linux.dev +[axboe: folded in incremental fix and added tags] +Signed-off-by: Jens Axboe +[bvanassche: changed RQF_USE_SCHED into RQF_ELVPRIV; restored the +finish_request pointer check before calling finish_request and removed +the new warning from the elevator code. This patch fixes an I/O hang +when submitting a REQ_FUA request to a request queue for a zoned block +device for which FUA has been disabled (QUEUE_FLAG_FUA is not set).] +Signed-off-by: Bart Van Assche +Signed-off-by: Greg Kroah-Hartman +--- + block/blk-mq.c | 24 +++++++++++++++++++++--- + 1 file changed, 21 insertions(+), 3 deletions(-) + +--- a/block/blk-mq.c ++++ b/block/blk-mq.c +@@ -675,6 +675,22 @@ out_queue_exit: + } + EXPORT_SYMBOL_GPL(blk_mq_alloc_request_hctx); + ++static void blk_mq_finish_request(struct request *rq) ++{ ++ struct request_queue *q = rq->q; ++ ++ if ((rq->rq_flags & RQF_ELVPRIV) && ++ q->elevator->type->ops.finish_request) { ++ q->elevator->type->ops.finish_request(rq); ++ /* ++ * For postflush request that may need to be ++ * completed twice, we should clear this flag ++ * to avoid double finish_request() on the rq. ++ */ ++ rq->rq_flags &= ~RQF_ELVPRIV; ++ } ++} ++ + static void __blk_mq_free_request(struct request *rq) + { + struct request_queue *q = rq->q; +@@ -701,9 +717,7 @@ void blk_mq_free_request(struct request + { + struct request_queue *q = rq->q; + +- if ((rq->rq_flags & RQF_ELVPRIV) && +- q->elevator->type->ops.finish_request) +- q->elevator->type->ops.finish_request(rq); ++ blk_mq_finish_request(rq); + + if (unlikely(laptop_mode && !blk_rq_is_passthrough(rq))) + laptop_io_completion(q->disk->bdi); +@@ -1025,6 +1039,8 @@ inline void __blk_mq_end_request(struct + if (blk_mq_need_time_stamp(rq)) + __blk_mq_end_request_acct(rq, ktime_get_ns()); + ++ blk_mq_finish_request(rq); ++ + if (rq->end_io) { + rq_qos_done(rq->q, rq); + if (rq->end_io(rq, error) == RQ_END_IO_FREE) +@@ -1079,6 +1095,8 @@ void blk_mq_end_request_batch(struct io_ + if (iob->need_ts) + __blk_mq_end_request_acct(rq, now); + ++ blk_mq_finish_request(rq); ++ + rq_qos_done(rq->q, rq); + + /* diff --git a/queue-6.1/series b/queue-6.1/series index d5295d74a3e..41849b9bd4f 100644 --- a/queue-6.1/series +++ b/queue-6.1/series @@ -197,3 +197,4 @@ efi-fix-panic-in-kdump-kernel.patch pwm-img-fix-pwm-clock-lookup.patch tty-serial-imx-fix-broken-rs485.patch block-fix-page-refcounts-for-unaligned-buffers-in-__bio_release_pages.patch +blk-mq-release-scheduler-resource-when-request-completes.patch