mirror of
https://github.com/torvalds/linux.git
synced 2026-11-07 06:17:02 +01:00
blk-mq: free the bitmaps of tags in the SRCU callback
Commitad0d05dbddkeeps struct blk_mq_tags and the requests until the iterators under tags_srcu are gone, but the two bitmaps they walk are still freed right away. When the number of hardware queues shrinks, blk_mq_tagset_busy_iter() may be about to walk tags that __blk_mq_update_nr_hw_queues() frees. sbitmap_free() clears the map pointer, so that's a NULL dereference or a use-after-free, depending on the timing. Free the bitmaps with the rest in the callback. Fixes:ad0d05dbdd("blk-mq: Defer freeing of tags page_list to SRCU callback") Signed-off-by: Josef Bacik <josef@toxicpanda.com> Reviewed-by: Hannes Reinecke <hare@kernel.org> Link: https://patch.msgid.link/20261028164415.1262013-44-axboe@kernel.dk Signed-off-by: Jens Axboe <axboe@kernel.dk>
This commit is contained in:
parent
6c55f94317
commit
10b249e9b0
|
|
@ -611,17 +611,17 @@ static void blk_mq_free_tags_callback(struct rcu_head *head)
|
|||
kmemleak_free(page_address(page));
|
||||
__free_pages(page, page->private);
|
||||
}
|
||||
/* An iterator may walk the bitmaps for as long as it may see the tags */
|
||||
sbitmap_queue_free(&tags->bitmap_tags);
|
||||
sbitmap_queue_free(&tags->breserved_tags);
|
||||
kfree(tags);
|
||||
}
|
||||
|
||||
void blk_mq_free_tags(struct blk_mq_tags *tags)
|
||||
{
|
||||
sbitmap_queue_free(&tags->bitmap_tags);
|
||||
sbitmap_queue_free(&tags->breserved_tags);
|
||||
|
||||
/* if tags pages is not allocated yet, free tags directly */
|
||||
if (list_empty(&tags->page_list)) {
|
||||
kfree(tags);
|
||||
blk_mq_free_tags_callback(&tags->rcu_head);
|
||||
return;
|
||||
}
|
||||
|
||||
|
|
|
|||
Loading…
Reference in New Issue
Block a user