diff options
author | Linus Torvalds <torvalds@linux-foundation.org> | 2013-11-28 09:51:39 -0800 |
---|---|---|
committer | Linus Torvalds <torvalds@linux-foundation.org> | 2013-11-28 09:51:39 -0800 |
commit | 962ba26326ba02ca5c67f18c6979c3adfd7c2097 (patch) | |
tree | b460ef885521484d20554fd8270515625154f62c | |
parent | 3bad8bb5cd3048a67df43ac6b1e2f191f19d9ff0 (diff) | |
parent | 6d183de4077191d1201283a9035ce57a9b05254d (diff) |
Merge tag 'md/3.13-fixes' of git://neil.brown.name/md
Pull md fixes from Neil Brown:
"Three bug fixes for md in 3.13-rc
All recent regressions, one in 3.12 so marked for -stable"
* tag 'md/3.13-fixes' of git://neil.brown.name/md:
md/raid5: fix newly-broken locking in get_active_stripe.
md: test mddev->flags more safely in md_check_recovery.
md/raid5: fix new memory-reference bug in alloc_thread_groups.
-rw-r--r-- | drivers/md/md.c | 2 | ||||
-rw-r--r-- | drivers/md/raid5.c | 13 |
2 files changed, 6 insertions, 9 deletions
diff --git a/drivers/md/md.c b/drivers/md/md.c index b6b7a2866c9e..e60cebf3f519 100644 --- a/drivers/md/md.c +++ b/drivers/md/md.c @@ -7777,7 +7777,7 @@ void md_check_recovery(struct mddev *mddev) if (mddev->ro && !test_bit(MD_RECOVERY_NEEDED, &mddev->recovery)) return; if ( ! ( - (mddev->flags & ~ (1<<MD_CHANGE_PENDING)) || + (mddev->flags & MD_UPDATE_SB_FLAGS & ~ (1<<MD_CHANGE_PENDING)) || test_bit(MD_RECOVERY_NEEDED, &mddev->recovery) || test_bit(MD_RECOVERY_DONE, &mddev->recovery) || (mddev->external == 0 && mddev->safemode == 1) || diff --git a/drivers/md/raid5.c b/drivers/md/raid5.c index 47da0af6322b..cc055da02e2a 100644 --- a/drivers/md/raid5.c +++ b/drivers/md/raid5.c @@ -678,26 +678,23 @@ get_active_stripe(struct r5conf *conf, sector_t sector, } else init_stripe(sh, sector, previous); } else { + spin_lock(&conf->device_lock); if (atomic_read(&sh->count)) { BUG_ON(!list_empty(&sh->lru) && !test_bit(STRIPE_EXPANDING, &sh->state) && !test_bit(STRIPE_ON_UNPLUG_LIST, &sh->state) - && !test_bit(STRIPE_ON_RELEASE_LIST, &sh->state)); + ); } else { - spin_lock(&conf->device_lock); if (!test_bit(STRIPE_HANDLE, &sh->state)) atomic_inc(&conf->active_stripes); - if (list_empty(&sh->lru) && - !test_bit(STRIPE_ON_RELEASE_LIST, &sh->state) && - !test_bit(STRIPE_EXPANDING, &sh->state)) - BUG(); + BUG_ON(list_empty(&sh->lru)); list_del_init(&sh->lru); if (sh->group) { sh->group->stripes_cnt--; sh->group = NULL; } - spin_unlock(&conf->device_lock); } + spin_unlock(&conf->device_lock); } } while (sh == NULL); @@ -5471,7 +5468,7 @@ static int alloc_thread_groups(struct r5conf *conf, int cnt, for (i = 0; i < *group_cnt; i++) { struct r5worker_group *group; - group = worker_groups[i]; + group = &(*worker_groups)[i]; INIT_LIST_HEAD(&group->handle_list); group->conf = conf; group->workers = workers + i * cnt; |