Skip to content

Commit cc3200e

Browse files
Ming Leiaxboe
authored andcommitted
blk-mq: insert flush request to the front of dispatch queue
commit 01e99ae ("blk-mq: insert passthrough request into hctx->dispatch directly") may change to add flush request to the tail of dispatch by applying the 'add_head' parameter of blk_mq_sched_insert_request. Turns out this way causes performance regression on NCQ controller because flush is non-NCQ command, which can't be queued when there is any in-flight NCQ command. When adding flush rq to the front of hctx->dispatch, it is easier to introduce extra time to flush rq's latency compared with adding to the tail of dispatch queue because of S_SCHED_RESTART, then chance of flush merge is increased, and less flush requests may be issued to controller. So always insert flush request to the front of dispatch queue just like before applying commit 01e99ae ("blk-mq: insert passthrough request into hctx->dispatch directly"). Cc: Damien Le Moal <[email protected]> Cc: Shinichiro Kawasaki <[email protected]> Reported-by: Shinichiro Kawasaki <[email protected]> Fixes: 01e99ae ("blk-mq: insert passthrough request into hctx->dispatch directly") Signed-off-by: Ming Lei <[email protected]> Signed-off-by: Jens Axboe <[email protected]>
1 parent 5e6bdd3 commit cc3200e

File tree

1 file changed

+22
-0
lines changed

1 file changed

+22
-0
lines changed

block/blk-mq-sched.c

Lines changed: 22 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -398,6 +398,28 @@ void blk_mq_sched_insert_request(struct request *rq, bool at_head,
398398
WARN_ON(e && (rq->tag != -1));
399399

400400
if (blk_mq_sched_bypass_insert(hctx, !!e, rq)) {
401+
/*
402+
* Firstly normal IO request is inserted to scheduler queue or
403+
* sw queue, meantime we add flush request to dispatch queue(
404+
* hctx->dispatch) directly and there is at most one in-flight
405+
* flush request for each hw queue, so it doesn't matter to add
406+
* flush request to tail or front of the dispatch queue.
407+
*
408+
* Secondly in case of NCQ, flush request belongs to non-NCQ
409+
* command, and queueing it will fail when there is any
410+
* in-flight normal IO request(NCQ command). When adding flush
411+
* rq to the front of hctx->dispatch, it is easier to introduce
412+
* extra time to flush rq's latency because of S_SCHED_RESTART
413+
* compared with adding to the tail of dispatch queue, then
414+
* chance of flush merge is increased, and less flush requests
415+
* will be issued to controller. It is observed that ~10% time
416+
* is saved in blktests block/004 on disk attached to AHCI/NCQ
417+
* drive when adding flush rq to the front of hctx->dispatch.
418+
*
419+
* Simply queue flush rq to the front of hctx->dispatch so that
420+
* intensive flush workloads can benefit in case of NCQ HW.
421+
*/
422+
at_head = (rq->rq_flags & RQF_FLUSH_SEQ) ? true : at_head;
401423
blk_mq_request_bypass_insert(rq, at_head, false);
402424
goto run;
403425
}

0 commit comments

Comments
 (0)