]> git.proxmox.com Git - mirror_ubuntu-jammy-kernel.git/commitdiff
Revert "Revert "block, bfq: honor already-setup queue merges""
authorPaolo Valente <paolo.valente@linaro.org>
Thu, 25 Nov 2021 18:15:10 +0000 (19:15 +0100)
committerStefan Bader <stefan.bader@canonical.com>
Fri, 20 May 2022 12:39:44 +0000 (14:39 +0200)
BugLink: https://bugs.launchpad.net/bugs/1969110
[ Upstream commit 15729ff8143f8135b03988a100a19e66d7cb7ecd ]

A crash [1] happened to be triggered in conjunction with commit
2d52c58b9c9b ("block, bfq: honor already-setup queue merges"). The
latter was then reverted by commit ebc69e897e17 ("Revert "block, bfq:
honor already-setup queue merges""). Yet, the reverted commit was not
the one introducing the bug. In fact, it actually triggered a UAF
introduced by a different commit, and now fixed by commit d29bd41428cf
("block, bfq: reset last_bfqq_created on group change").

So, there is no point in keeping commit 2d52c58b9c9b ("block, bfq:
honor already-setup queue merges") out. This commit restores it.

[1] https://bugzilla.kernel.org/show_bug.cgi?id=214503

Reported-by: Holger Hoffstätte <holger@applied-asynchrony.com>
Signed-off-by: Paolo Valente <paolo.valente@linaro.org>
Link: https://lore.kernel.org/r/20211125181510.15004-1-paolo.valente@linaro.org
Signed-off-by: Jens Axboe <axboe@kernel.dk>
Signed-off-by: Sasha Levin <sashal@kernel.org>
(cherry picked from commit 65d8a737452e88f251fe5d925371de6d606df613)
Signed-off-by: Paolo Pisati <paolo.pisati@canonical.com>
block/bfq-iosched.c

index 9843085cc2c35a5e62b2dd486cd50288c75c24d3..63d2d66dece5666bcaf2b74c21be7fd200f4cba7 100644 (file)
@@ -2662,6 +2662,15 @@ bfq_setup_merge(struct bfq_queue *bfqq, struct bfq_queue *new_bfqq)
         * are likely to increase the throughput.
         */
        bfqq->new_bfqq = new_bfqq;
+       /*
+        * The above assignment schedules the following redirections:
+        * each time some I/O for bfqq arrives, the process that
+        * generated that I/O is disassociated from bfqq and
+        * associated with new_bfqq. Here we increases new_bfqq->ref
+        * in advance, adding the number of processes that are
+        * expected to be associated with new_bfqq as they happen to
+        * issue I/O.
+        */
        new_bfqq->ref += process_refs;
        return new_bfqq;
 }
@@ -2724,6 +2733,10 @@ bfq_setup_cooperator(struct bfq_data *bfqd, struct bfq_queue *bfqq,
 {
        struct bfq_queue *in_service_bfqq, *new_bfqq;
 
+       /* if a merge has already been setup, then proceed with that first */
+       if (bfqq->new_bfqq)
+               return bfqq->new_bfqq;
+
        /*
         * Check delayed stable merge for rotational or non-queueing
         * devs. For this branch to be executed, bfqq must not be
@@ -2825,9 +2838,6 @@ bfq_setup_cooperator(struct bfq_data *bfqd, struct bfq_queue *bfqq,
        if (bfq_too_late_for_merging(bfqq))
                return NULL;
 
-       if (bfqq->new_bfqq)
-               return bfqq->new_bfqq;
-
        if (!io_struct || unlikely(bfqq == &bfqd->oom_bfqq))
                return NULL;