[PATCH] dm: log: rename complete_resync_work
authorJonathan E Brassow <jbrassow@redhat.com>
Fri, 8 Dec 2006 10:41:11 +0000 (02:41 -0800)
committerLinus Torvalds <torvalds@woody.osdl.org>
Fri, 8 Dec 2006 16:29:09 +0000 (08:29 -0800)
The complete_resync_work function only provides the ability to change an
out-of-sync region to in-sync.  This patch enhances the function to allow us
to change the status from in-sync to out-of-sync as well, something that is
needed when a mirror write to one of the devices or an initial resync on a
given region fails.

Signed-off-by: Jonathan E Brassow <jbrassow@redhat.com>
Signed-off-by: Alasdair G Kergon <agk@redhat.com>
Cc: dm-devel@redhat.com
Signed-off-by: Andrew Morton <akpm@osdl.org>
Signed-off-by: Linus Torvalds <torvalds@osdl.org>
drivers/md/dm-log.c
drivers/md/dm-log.h
drivers/md/dm-raid1.c

index 64b764bd02cc3e1ff15d9aa26df40f536d34f22b..ce5c5d6fc1077362c03d49b0f048d2cce0a33913 100644 (file)
@@ -549,16 +549,19 @@ static int core_get_resync_work(struct dirty_log *log, region_t *region)
        return 1;
 }
 
-static void core_complete_resync_work(struct dirty_log *log, region_t region,
-                                     int success)
+static void core_set_region_sync(struct dirty_log *log, region_t region,
+                                int in_sync)
 {
        struct log_c *lc = (struct log_c *) log->context;
 
        log_clear_bit(lc, lc->recovering_bits, region);
-       if (success) {
+       if (in_sync) {
                log_set_bit(lc, lc->sync_bits, region);
                 lc->sync_count++;
-        }
+        } else if (log_test_bit(lc->sync_bits, region)) {
+               lc->sync_count--;
+               log_clear_bit(lc, lc->sync_bits, region);
+       }
 }
 
 static region_t core_get_sync_count(struct dirty_log *log)
@@ -625,7 +628,7 @@ static struct dirty_log_type _core_type = {
        .mark_region = core_mark_region,
        .clear_region = core_clear_region,
        .get_resync_work = core_get_resync_work,
-       .complete_resync_work = core_complete_resync_work,
+       .set_region_sync = core_set_region_sync,
        .get_sync_count = core_get_sync_count,
        .status = core_status,
 };
@@ -644,7 +647,7 @@ static struct dirty_log_type _disk_type = {
        .mark_region = core_mark_region,
        .clear_region = core_clear_region,
        .get_resync_work = core_get_resync_work,
-       .complete_resync_work = core_complete_resync_work,
+       .set_region_sync = core_set_region_sync,
        .get_sync_count = core_get_sync_count,
        .status = disk_status,
 };
index 5ae5309ebf2808dea579d2cb0b9e0d7fa8beda48..86a301c8daf15d5962afe2ca8ed6eee39e58d24e 100644 (file)
@@ -90,12 +90,12 @@ struct dirty_log_type {
        int (*get_resync_work)(struct dirty_log *log, region_t *region);
 
        /*
-        * This notifies the log that the resync of an area has
-        * been completed.  The log should then mark this region
-        * as CLEAN.
+        * This notifies the log that the resync status of a region
+        * has changed.  It also clears the region from the recovering
+        * list (if present).
         */
-       void (*complete_resync_work)(struct dirty_log *log,
-                                    region_t region, int success);
+       void (*set_region_sync)(struct dirty_log *log,
+                               region_t region, int in_sync);
 
         /*
         * Returns the number of regions that are in sync.
index 3b3f4c9c3f0917f90ad706588ec87dc45498c70c..23a642619bedfbbe76137f2d1e8d174782622f4e 100644 (file)
@@ -344,6 +344,17 @@ static void dispatch_bios(struct mirror_set *ms, struct bio_list *bio_list)
        }
 }
 
+static void complete_resync_work(struct region *reg, int success)
+{
+       struct region_hash *rh = reg->rh;
+
+       rh->log->type->set_region_sync(rh->log, reg->key, success);
+       dispatch_bios(rh->ms, &reg->delayed_bios);
+       if (atomic_dec_and_test(&rh->recovery_in_flight))
+               wake_up_all(&_kmirrord_recovery_stopped);
+       up(&rh->recovery_count);
+}
+
 static void rh_update_states(struct region_hash *rh)
 {
        struct region *reg, *next;
@@ -383,11 +394,7 @@ static void rh_update_states(struct region_hash *rh)
         */
        list_for_each_entry_safe (reg, next, &recovered, list) {
                rh->log->type->clear_region(rh->log, reg->key);
-               rh->log->type->complete_resync_work(rh->log, reg->key, 1);
-               dispatch_bios(rh->ms, &reg->delayed_bios);
-               if (atomic_dec_and_test(&rh->recovery_in_flight))
-                       wake_up_all(&_kmirrord_recovery_stopped);
-               up(&rh->recovery_count);
+               complete_resync_work(reg, 1);
                mempool_free(reg, rh->region_pool);
        }