]> git.ipfire.org Git - thirdparty/kernel/linux.git/commitdiff
blk-mq-sched: unify elevators checking for async requests
authorYu Kuai <yukuai@fnnas.com>
Tue, 3 Feb 2026 08:19:43 +0000 (16:19 +0800)
committerJens Axboe <axboe@kernel.dk>
Tue, 3 Feb 2026 14:45:36 +0000 (07:45 -0700)
bfq and mq-deadline consider sync writes as async requests and only
reserve tags for sync reads by async_depth, however, kyber doesn't
consider sync writes as async requests for now.

Consider the case there are lots of dirty pages, and user use fsync to
flush dirty pages. In this case sched_tags can be exhausted by sync writes
and sync reads can stuck waiting for tag. Hence let kyber follow what
mq-deadline and bfq did, and unify async requests checking for all
elevators.

Signed-off-by: Yu Kuai <yukuai@fnnas.com>
Reviewed-by: Nilay Shroff <nilay@linux.ibm.com>
Reviewed-by: Hannes Reinecke <hare@suse.de>
Signed-off-by: Jens Axboe <axboe@kernel.dk>
block/bfq-iosched.c
block/blk-mq-sched.h
block/kyber-iosched.c
block/mq-deadline.c

index 3ebdec40e7589efe7697eb6447b7f92a86d3fdcf..44746f4c0b895e744a63da93f3e67892252196f8 100644 (file)
@@ -697,7 +697,7 @@ static void bfq_limit_depth(blk_opf_t opf, struct blk_mq_alloc_data *data)
        unsigned int limit, act_idx;
 
        /* Sync reads have full depth available */
-       if (op_is_sync(opf) && !op_is_write(opf))
+       if (blk_mq_is_sync_read(opf))
                limit = data->q->nr_requests;
        else
                limit = bfqd->async_depths[!!bfqd->wr_busy_queues][op_is_sync(opf)];
index 02c40a72e9598c7ff6be2b175eba0cc4587a378c..5678e15bd33c4bc4abdb39dfa782a4ea15fd6467 100644 (file)
@@ -137,4 +137,9 @@ static inline void blk_mq_set_min_shallow_depth(struct request_queue *q,
                                                depth);
 }
 
+static inline bool blk_mq_is_sync_read(blk_opf_t opf)
+{
+       return op_is_sync(opf) && !op_is_write(opf);
+}
+
 #endif
index c1b36ffd19ceb43f1bf2a362b7de3725eb94f0fd..2b3f5b8959af03d5436d004a090e902e9ff2159e 100644 (file)
@@ -556,7 +556,7 @@ static void kyber_limit_depth(blk_opf_t opf, struct blk_mq_alloc_data *data)
         * We use the scheduler tags as per-hardware queue queueing tokens.
         * Async requests can be limited at this stage.
         */
-       if (!op_is_sync(opf)) {
+       if (!blk_mq_is_sync_read(opf)) {
                struct kyber_queue_data *kqd = data->q->elevator->elevator_data;
 
                data->shallow_depth = kqd->async_depth;
index 3e3719093aec72051b1c0178aad8f470b7ca609b..29d00221fbea6a3433994475352d4739b1a247d7 100644 (file)
@@ -495,7 +495,7 @@ static void dd_limit_depth(blk_opf_t opf, struct blk_mq_alloc_data *data)
        struct deadline_data *dd = data->q->elevator->elevator_data;
 
        /* Do not throttle synchronous reads. */
-       if (op_is_sync(opf) && !op_is_write(opf))
+       if (blk_mq_is_sync_read(opf))
                return;
 
        /*