diff options
author | Ming Lei <ming.lei@canonical.com> | 2015-01-20 04:00:56 +0100 |
---|---|---|
committer | Jens Axboe <axboe@fb.com> | 2015-01-20 17:28:33 +0100 |
commit | 76d697d10769048e5721510100bf3a9413a56385 (patch) | |
tree | e7d78afb91e9f7ff47f7e1e558f762908c50f49e /block/blk-mq.c | |
parent | NVMe: cq_vector should be signed (diff) | |
download | linux-76d697d10769048e5721510100bf3a9413a56385.tar.xz linux-76d697d10769048e5721510100bf3a9413a56385.zip |
blk-mq: fix hctx/ctx kobject use-after-free
The kobject memory shouldn't have been freed before the kobject
is released because driver core can access it freely before its
release.
This patch frees hctx in its release callback. For ctx, they
share one single per-cpu variable which is associated with
the request queue, so free ctx in q->mq_kobj's release handler.
Signed-off-by: Sasha Levin <sasha.levin@oracle.com>
(fix ctx kobjects)
Signed-off-by: Ming Lei <ming.lei@canonical.com>
Signed-off-by: Jens Axboe <axboe@fb.com>
Diffstat (limited to 'block/blk-mq.c')
-rw-r--r-- | block/blk-mq.c | 6 |
1 files changed, 1 insertions, 5 deletions
diff --git a/block/blk-mq.c b/block/blk-mq.c index 2f95747c287e..9ee3b87c4498 100644 --- a/block/blk-mq.c +++ b/block/blk-mq.c @@ -1641,10 +1641,8 @@ static void blk_mq_free_hw_queues(struct request_queue *q, struct blk_mq_hw_ctx *hctx; unsigned int i; - queue_for_each_hw_ctx(q, hctx, i) { + queue_for_each_hw_ctx(q, hctx, i) free_cpumask_var(hctx->cpumask); - kfree(hctx); - } } static int blk_mq_init_hctx(struct request_queue *q, @@ -2002,11 +2000,9 @@ void blk_mq_free_queue(struct request_queue *q) percpu_ref_exit(&q->mq_usage_counter); - free_percpu(q->queue_ctx); kfree(q->queue_hw_ctx); kfree(q->mq_map); - q->queue_ctx = NULL; q->queue_hw_ctx = NULL; q->mq_map = NULL; |