+ dm-snapshot-tidy-pe-ref-counting.patch added to -mm tree

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



The patch titled

     dm snapshot: tidy pe ref counting

has been added to the -mm tree.  Its filename is

     dm-snapshot-tidy-pe-ref-counting.patch

See http://www.zip.com.au/~akpm/linux/patches/stuff/added-to-mm.txt to find
out what to do about this

------------------------------------------------------
Subject: dm snapshot: tidy pe ref counting
From: Alasdair G Kergon <agk@xxxxxxxxxx>

Rename sibling_count to ref_count and introduce get and put functions.

Signed-off-by: Alasdair G Kergon <agk@xxxxxxxxxx>
Signed-off-by: Andrew Morton <akpm@xxxxxxxx>
---

 drivers/md/dm-snap.c |   83 +++++++++++++++++++++++------------------
 1 files changed, 48 insertions(+), 35 deletions(-)

diff -puN drivers/md/dm-snap.c~dm-snapshot-tidy-pe-ref-counting drivers/md/dm-snap.c
--- a/drivers/md/dm-snap.c~dm-snapshot-tidy-pe-ref-counting
+++ a/drivers/md/dm-snap.c
@@ -59,7 +59,7 @@ struct pending_exception {
 
 	/*
 	 * The primary pending_exception is the one that holds
-	 * the sibling_count and the list of origin_bios for a
+	 * the ref_count and the list of origin_bios for a
 	 * group of pending_exceptions.  It is always last to get freed.
 	 * These fields get set up when writing to the origin.
 	 */
@@ -72,7 +72,7 @@ struct pending_exception {
 	 * the sibling concerned and not pe->primary_pe->snap->lock unless
 	 * they are the same.
 	 */
-	atomic_t sibling_count;
+	atomic_t ref_count;
 
 	/* Pointer back to snapshot context */
 	struct dm_snapshot *snap;
@@ -653,10 +653,46 @@ static void __invalidate_snapshot(struct
 	dm_table_event(s->table);
 }
 
+static void get_pending_exception(struct pending_exception *pe)
+{
+	atomic_inc(&pe->ref_count);
+}
+
+static struct bio *put_pending_exception(struct pending_exception *pe)
+{
+	struct pending_exception *primary_pe;
+	struct bio *origin_bios = NULL;
+
+	primary_pe = pe->primary_pe;
+
+	/*
+	 * If this pe is involved in a write to the origin and
+	 * it is the last sibling to complete then release
+	 * the bios for the original write to the origin.
+	 */
+	if (primary_pe &&
+	    atomic_dec_and_test(&primary_pe->ref_count))
+		origin_bios = bio_list_get(&primary_pe->origin_bios);
+
+	/*
+	 * Free the pe if it's not linked to an origin write or if
+	 * it's not itself a primary pe.
+	 */
+	if (!primary_pe || primary_pe != pe)
+		free_pending_exception(pe);
+
+	/*
+	 * Free the primary pe if nothing references it.
+	 */
+	if (primary_pe && !atomic_read(&primary_pe->ref_count))
+		free_pending_exception(primary_pe);
+
+	return origin_bios;
+}
+
 static void pending_complete(struct pending_exception *pe, int success)
 {
 	struct exception *e;
-	struct pending_exception *primary_pe;
 	struct dm_snapshot *s = pe->snap;
 	struct bio *origin_bios = NULL;
 	struct bio *snapshot_bios = NULL;
@@ -695,30 +731,7 @@ static void pending_complete(struct pend
 
  out:
 	snapshot_bios = bio_list_get(&pe->snapshot_bios);
-
-	primary_pe = pe->primary_pe;
-
-	/*
-	 * If this pe is involved in a write to the origin and
-	 * it is the last sibling to complete then release
-	 * the bios for the original write to the origin.
-	 */
-	if (primary_pe &&
-	    atomic_dec_and_test(&primary_pe->sibling_count))
-		origin_bios = bio_list_get(&primary_pe->origin_bios);
-
-	/*
-	 * Free the pe if it's not linked to an origin write or if
-	 * it's not itself a primary pe.
-	 */
-	if (!primary_pe || primary_pe != pe)
-		free_pending_exception(pe);
-
-	/*
-	 * Free the primary pe if nothing references it.
-	 */
-	if (primary_pe && !atomic_read(&primary_pe->sibling_count))
-		free_pending_exception(primary_pe);
+	origin_bios = put_pending_exception(pe);
 
 	up_write(&s->lock);
 
@@ -829,7 +842,7 @@ __find_pending_exception(struct dm_snaps
 	bio_list_init(&pe->origin_bios);
 	bio_list_init(&pe->snapshot_bios);
 	pe->primary_pe = NULL;
-	atomic_set(&pe->sibling_count, 1);
+	atomic_set(&pe->ref_count, 0);
 	pe->snap = s;
 	pe->started = 0;
 
@@ -838,6 +851,7 @@ __find_pending_exception(struct dm_snaps
 		return NULL;
 	}
 
+	get_pending_exception(pe);
 	insert_exception(&s->pending, &pe->e);
 
  out:
@@ -1012,7 +1026,7 @@ static int __origin_write(struct list_he
 		 * is already remapped in this snapshot
 		 * and trigger an exception if not.
 		 *
-		 * sibling_count is initialised to 1 so pending_complete()
+		 * ref_count is initialised to 1 so pending_complete()
 		 * won't destroy the primary_pe while we're inside this loop.
 		 */
 		e = lookup_exception(&snap->complete, chunk);
@@ -1043,8 +1057,8 @@ static int __origin_write(struct list_he
 		}
 
 		if (!pe->primary_pe) {
-			atomic_inc(&primary_pe->sibling_count);
 			pe->primary_pe = primary_pe;
+			get_pending_exception(primary_pe);
 		}
 
 		if (!pe->started) {
@@ -1057,20 +1071,20 @@ static int __origin_write(struct list_he
 	}
 
 	if (!primary_pe)
-		goto out;
+		return r;
 
 	/*
 	 * If this is the first time we're processing this chunk and
-	 * sibling_count is now 1 it means all the pending exceptions
+	 * ref_count is now 1 it means all the pending exceptions
 	 * got completed while we were in the loop above, so it falls to
 	 * us here to remove the primary_pe and submit any origin_bios.
 	 */
 
-	if (first && atomic_dec_and_test(&primary_pe->sibling_count)) {
+	if (first && atomic_dec_and_test(&primary_pe->ref_count)) {
 		flush_bios(bio_list_get(&primary_pe->origin_bios));
 		free_pending_exception(primary_pe);
 		/* If we got here, pe_queue is necessarily empty. */
-		goto out;
+		return r;
 	}
 
 	/*
@@ -1079,7 +1093,6 @@ static int __origin_write(struct list_he
 	list_for_each_entry_safe(pe, next_pe, &pe_queue, list)
 		start_copy(pe);
 
- out:
 	return r;
 }
 
_

Patches currently in -mm which might be from agk@xxxxxxxxxx are

dm-support-ioctls-on-mapped-devices.patch
dm-linear-support-ioctls.patch
dm-mpath-support-ioctls.patch
dm-export-blkdev_driver_ioctl.patch
dm-support-ioctls-on-mapped-devices-fix-with-fake-file.patch
dm-fix-alloc_dev-error-path.patch
dm-snapshot-fix-invalidation-enomem.patch
dm-snapshot-allow-zero-chunk_size.patch
dm-snapshot-fix-metadata-error-handling.patch
dm-snapshot-make-read-and-write-exception-functions-void.patch
dm-snapshot-fix-metadata-writing-when-suspending.patch
dm-snapshot-tidy-snapshot_map.patch
dm-snapshot-tidy-pending_complete.patch
dm-snapshot-add-workqueue.patch
dm-snapshot-tidy-pe-ref-counting.patch
dm-snapshot-fix-freeing-pending-exception.patch
dm-mirror-remove-trailing-space-from-table.patch
dm-mpath-tidy-ctr.patch
dm-mpath-use-kzalloc.patch
dm-add-uevent-change-event-on-resume.patch
dm-add-debug-macro.patch
dm-table-add-target-preresume.patch
dm-crypt-add-key-msg.patch
dm-crypt-restructure-for-workqueue-change.patch
dm-crypt-restructure-write-processing.patch
dm-crypt-move-io-to-workqueue.patch
dm-crypt-use-private-biosets.patch
dm-use-private-biosets.patch
dm-extract-device-limit-setting.patch
dm-table-add-target-flush.patch
md-dm-reduce-stack-usage-with-stacked-block-devices.patch

-
To unsubscribe from this list: send the line "unsubscribe mm-commits" in
the body of a message to majordomo@xxxxxxxxxxxxxxx
More majordomo info at  http://vger.kernel.org/majordomo-info.html

[Index of Archives]     [Kernel Newbies FAQ]     [Kernel Archive]     [IETF Annouce]     [DCCP]     [Netdev]     [Networking]     [Security]     [Bugtraq]     [Photo]     [Yosemite]     [MIPS Linux]     [ARM Linux]     [Linux Security]     [Linux RAID]     [Linux SCSI]

  Powered by Linux