Patch "block: Fix a blk_exit_rl() regression" has been added to the 4.11-stable tree
Subsystems (2)
This is a note to let you know that I've just added the patch titled
block: Fix a blk_exit_rl() regression
to the 4.11-stable tree which can be found at:
http://www.kernel.org/git/?p=linux/kernel/git/stable/stable-queue.git;a=summary
The filename of the patch is:
block-fix-a-blk_exit_rl-regression.patch
and it can be found in the queue-4.11 subdirectory.
If you, or anyone else, feels it should not be added to the stable tree, please let <[email protected]> know about it.
Quoted 1 line
From
dc9edc44de6cd7cc8cc7f5b36c1adb221eda3207Mon Sep 17 00:00:00 2001
From: Bart Van Assche <[email protected]>
Date: Wed, 14 Jun 2017 13:27:50 -0600
Subject: block: Fix a blk_exit_rl() regression
From: Bart Van Assche <[email protected]>
commit dc9edc44de6cd7cc8cc7f5b36c1adb221eda3207 upstream.
Avoid that the following complaint is reported:
BUG: sleeping function called from invalid context at kernel/workqueue.c:2790
in_atomic(): 1, irqs_disabled(): 0, pid: 41, name: rcuop/3
1 lock held by rcuop/3/41:
#0: (rcu_callback){......}, at: [<ffffffff8111f9a2>] rcu_nocb_kthread+0x282/0x500
Call Trace:
dump_stack+0x86/0xcf
___might_sleep+0x174/0x260
__might_sleep+0x4a/0x80
flush_work+0x7e/0x2e0
__cancel_work_timer+0x143/0x1c0
cancel_work_sync+0x10/0x20
blk_throtl_exit+0x25/0x60
blkcg_exit_queue+0x35/0x40
blk_release_queue+0x42/0x130
kobject_put+0xa9/0x190This happens since we invoke callbacks that need to block from the queue release handler. Fix this by pushing the final release to a workqueue.
Updated changelog
--- block/blk-sysfs.c | 34 ++++++++++++++++++++++------------ include/linux/blkdev.h | 2 ++ 2 files changed, 24 insertions(+), 12 deletions(-)
block/blk-sysfs.c +22 -12
@@ -791,24 +791,25 @@ static void blk_free_queue_rcu(struct rc }/** -* blk_release_queue: - release a &struct request_queue when it is no longer needed -* @kobj: the kobj belonging to the request queue to be released +* __blk_release_queue - release a request queue when it is no longer needed +* @work: pointer to the release_work member of the request queue to be released * * Description: -* blk_release_queue is the pair to blk_init_queue() or -* blk_queue_make_request(). It should be called when a request queue is -* being released; typically when a block device is being de-registered. -* Currently, its primary task it to free all the &struct request -* structures that were allocated to the queue and the queue itself. +* blk_release_queue is the counterpart of blk_init_queue(). It should be +* called when a request queue is being released; typically when a block +* device is being de-registered. Its primary task it to free the queue +* itself. * -* Note: +* Notes: * The low level driver must have finished any outstanding requests first * via blk_cleanup_queue(). -**/ -static void blk_release_queue (struct kobject *kobj) +* +* Although blk_release_queue() may be called with preemption disabled, +* __blk_release_queue() may sleep. +*/ +static void __blk_release_queue (struct work_struct *work) { -struct request_queue *q = - container_of(kobj, struct request_queue, kobj); +struct request_queue *q =container_of (work,typeof (*q), release_work);wbt_exit (q);bdi_put (q->backing_dev_info);
@@ -844,6 +845,15 @@ static void blk_release_queue(struct kobcall_rcu (&q->rcu_head, blk_free_queue_rcu); } +static void blk_release_queue (struct kobject *kobj) +{ +struct request_queue *q = + container_of(kobj, struct request_queue, kobj); + +INIT_WORK (&q->release_work, __blk_release_queue); +schedule_work (&q->release_work); +} +static const struct sysfs_ops queue_sysfs_ops = { .show = queue_attr_show, .store = queue_attr_store,
include/linux/blkdev.h +2 -0
@@ -580,6 +580,8 @@ struct request_queue {size_t cmd_size;void *rq_alloc_data; + +struct work_struct release_work; };#define QUEUE_FLAG_QUEUED 1/* uses generic tag queueing */
Patches currently in stable-queue which might be from [email protected] are
queue-4.11/block-fix-a-blk_exit_rl-regression.patch