The following patch fixes a kernel oops when doing
blk_unplug_work() (oopses in generic_unplug_device()) for md.
The oops and the original report are here:
http://MARC.10East.com/?l=linux-kernel&m=104706400705154&w=2
The problem is that the md driver provides its own unplug
function (among other things) and blk_unplug_work() assumes
that the generic one would work, but it doesn't and BOOM,
it oopses and dies.
--
Luben
--- linux-2.5.64bk6/drivers/block/ll_rw_blk.c.orig 2003-03-11 16:23:55.000000000 -0500
+++ linux-2.5.64bk6/drivers/block/ll_rw_blk.c 2003-03-11 18:38:40.000000000 -0500
@@ -29,6 +29,7 @@
static void blk_unplug_work(void *data);
static void blk_unplug_timeout(unsigned long data);
+static int __make_request(request_queue_t *, struct bio *);
/*
* For the allocated request tables
@@ -1040,7 +1041,13 @@
static void blk_unplug_work(void *data)
{
- generic_unplug_device(data);
+ request_queue_t *q = data;
+
+ if (q->make_request_fn && q->make_request_fn != __make_request
+ && q->unplug_fn)
+ q->unplug_fn(data);
+ else
+ generic_unplug_device(data);
}
static void blk_unplug_timeout(unsigned long data)
@@ -1246,8 +1253,6 @@
return 1;
}
-static int __make_request(request_queue_t *, struct bio *);
-
/**
* blk_init_queue - prepare a request queue for use with a block device
* @q: The &request_queue_t to be initialised
Luben Tuikov <[email protected]> wrote:
>
> The following patch fixes a kernel oops when doing
> blk_unplug_work() (oopses in generic_unplug_device()) for md.
>
> The oops and the original report are here:
> http://MARC.10East.com/?l=linux-kernel&m=104706400705154&w=2
>
Yup, is a bug. I received the below fix from Neil today which looks
simpler.
diff -puN drivers/block/ll_rw_blk.c~auto-unplugging-fix drivers/block/ll_rw_blk.c
--- 25/drivers/block/ll_rw_blk.c~auto-unplugging-fix Tue Mar 11 15:04:00 2003
+++ 25-akpm/drivers/block/ll_rw_blk.c Tue Mar 11 15:04:00 2003
@@ -1004,7 +1004,8 @@ void generic_unplug_device(void *data)
static void blk_unplug_work(void *data)
{
- generic_unplug_device(data);
+ request_queue_t *q = data;
+ q->unplug_fn(q);
}
static void blk_unplug_timeout(unsigned long data)
_
On Tue, Mar 11 2003, Andrew Morton wrote:
> Luben Tuikov <[email protected]> wrote:
> >
> > The following patch fixes a kernel oops when doing
> > blk_unplug_work() (oopses in generic_unplug_device()) for md.
> >
> > The oops and the original report are here:
> > http://MARC.10East.com/?l=linux-kernel&m=104706400705154&w=2
> >
>
> Yup, is a bug. I received the below fix from Neil today which looks
> simpler.
>
> diff -puN drivers/block/ll_rw_blk.c~auto-unplugging-fix drivers/block/ll_rw_blk.c
> --- 25/drivers/block/ll_rw_blk.c~auto-unplugging-fix Tue Mar 11 15:04:00 2003
> +++ 25-akpm/drivers/block/ll_rw_blk.c Tue Mar 11 15:04:00 2003
> @@ -1004,7 +1004,8 @@ void generic_unplug_device(void *data)
>
> static void blk_unplug_work(void *data)
> {
> - generic_unplug_device(data);
> + request_queue_t *q = data;
> + q->unplug_fn(q);
> }
this is the correct fix
--
Jens Axboe