diff options
author | Jeff Garzik <jgarzik@pobox.com> | 2005-09-14 08:19:08 -0400 |
---|---|---|
committer | Jeff Garzik <jgarzik@pobox.com> | 2005-09-14 08:19:08 -0400 |
commit | 905ec87e93bc9e01b15c60035cd6a50c636cbaef (patch) | |
tree | 46fd7618d6511611ffc19eb0dd4d7bc6b90a41c2 /drivers/md/dm-raid1.c | |
parent | 1d6ae775d7a948c9575658eb41184fd2e506c0df (diff) | |
parent | 2f4ba45a75d6383b4a1201169a808ffea416ffa0 (diff) | |
download | blackbird-op-linux-905ec87e93bc9e01b15c60035cd6a50c636cbaef.tar.gz blackbird-op-linux-905ec87e93bc9e01b15c60035cd6a50c636cbaef.zip |
Merge /spare/repo/linux-2.6/
Diffstat (limited to 'drivers/md/dm-raid1.c')
-rw-r--r-- | drivers/md/dm-raid1.c | 12 |
1 files changed, 9 insertions, 3 deletions
diff --git a/drivers/md/dm-raid1.c b/drivers/md/dm-raid1.c index b08df8b9b2ca..863282513753 100644 --- a/drivers/md/dm-raid1.c +++ b/drivers/md/dm-raid1.c @@ -375,16 +375,18 @@ static void rh_inc(struct region_hash *rh, region_t region) read_lock(&rh->hash_lock); reg = __rh_find(rh, region); + + atomic_inc(®->pending); + + spin_lock_irq(&rh->region_lock); if (reg->state == RH_CLEAN) { rh->log->type->mark_region(rh->log, reg->key); - spin_lock_irq(&rh->region_lock); reg->state = RH_DIRTY; list_del_init(®->list); /* take off the clean list */ - spin_unlock_irq(&rh->region_lock); } + spin_unlock_irq(&rh->region_lock); - atomic_inc(®->pending); read_unlock(&rh->hash_lock); } @@ -408,6 +410,10 @@ static void rh_dec(struct region_hash *rh, region_t region) if (atomic_dec_and_test(®->pending)) { spin_lock_irqsave(&rh->region_lock, flags); + if (atomic_read(®->pending)) { /* check race */ + spin_unlock_irqrestore(&rh->region_lock, flags); + return; + } if (reg->state == RH_RECOVERING) { list_add_tail(®->list, &rh->quiesced_regions); } else { |