You can no longer call dm_table_event() from interrupt context. --- diff/drivers/md/dm-table.c 2003-10-29 14:56:19.000000000 +0000 +++ source/drivers/md/dm-table.c 2003-10-30 11:49:59.000000000 +0000 @@ -12,6 +12,7 @@ #include #include #include +#include #include #define MAX_DEPTH 16 @@ -723,22 +724,28 @@ return r; } -static spinlock_t _event_lock = SPIN_LOCK_UNLOCKED; +static DECLARE_MUTEX(_event_lock); void dm_table_event_callback(struct dm_table *t, void (*fn)(void *), void *context) { - spin_lock_irq(&_event_lock); + down(&_event_lock); t->event_fn = fn; t->event_context = context; - spin_unlock_irq(&_event_lock); + up(&_event_lock); } void dm_table_event(struct dm_table *t) { - spin_lock(&_event_lock); + /* + * You can no longer call dm_table_event() from interrupt + * context, use a bottom half instead. + */ + BUG_ON(in_interrupt()); + + down(&_event_lock); if (t->event_fn) t->event_fn(t->event_context); - spin_unlock(&_event_lock); + up(&_event_lock); } sector_t dm_table_get_size(struct dm_table *t)