linux-raid.vger.kernel.org archive mirror
 help / color / mirror / Atom feed
From: NeilBrown <neilb@suse.de>
To: linux-raid@vger.kernel.org
Subject: [md PATCH 09/10] md/raid10: split out interpretation of layout to separate function.
Date: Tue, 03 Apr 2012 15:53:02 +1000	[thread overview]
Message-ID: <20120403055302.19495.47473.stgit@notabene.brown> (raw)
In-Reply-To: <20120403054656.19495.36380.stgit@notabene.brown>

We will soon be interpreting the layout (and chunksize etc) from
multiple places to support reshape.  So split it out into separate
function.

Signed-off-by: NeilBrown <neilb@suse.de>
---

 drivers/md/raid10.c |   74 ++++++++++++++++++++++++++++++++++++---------------
 1 file changed, 52 insertions(+), 22 deletions(-)

diff --git a/drivers/md/raid10.c b/drivers/md/raid10.c
index 0a6746f..1f84b8e 100644
--- a/drivers/md/raid10.c
+++ b/drivers/md/raid10.c
@@ -3223,28 +3223,65 @@ raid10_size(struct mddev *mddev, sector_t sectors, int raid_disks)
 	return size << conf->geo.chunk_shift;
 }
 
+enum geo_type {geo_new, geo_old, geo_start};
+static int setup_geo(struct geom *geo, struct mddev *mddev, enum geo_type new)
+{
+	int nc, fc, fo;
+	int layout, chunk, disks;
+	switch (new) {
+	case geo_old:
+		layout = mddev->layout;
+		chunk = mddev->chunk_sectors;
+		disks = mddev->raid_disks - mddev->delta_disks;
+		break;
+	case geo_new:
+		layout = mddev->new_layout;
+		chunk = mddev->new_chunk_sectors;
+		disks = mddev->raid_disks;
+		break;
+	default: /* avoid 'may be unused' warnings */
+	case geo_start: /* new when starting reshape - raid_disks not
+			 * updated yet. */
+		layout = mddev->new_layout;
+		chunk = mddev->new_chunk_sectors;
+		disks = mddev->raid_disks + mddev->delta_disks;
+		break;
+	}
+	if (layout >> 17)
+		return -1;
+	if (chunk < (PAGE_SIZE >> 9) ||
+	    !is_power_of_2(chunk))
+		return -2;
+	nc = layout & 255;
+	fc = (layout >> 8) & 255;
+	fo = layout & (1<<16);
+	geo->raid_disks = disks;
+	geo->near_copies = nc;
+	geo->far_copies = fc;
+	geo->far_offset = fo;
+	geo->chunk_mask = chunk - 1;
+	geo->chunk_shift = ffz(~chunk);
+	return nc*fc;
+}
 
 static struct r10conf *setup_conf(struct mddev *mddev)
 {
 	struct r10conf *conf = NULL;
-	int nc, fc, fo;
 	sector_t stride, size;
 	int err = -EINVAL;
+	struct geom geo;
+	int copies;
+
+	copies = setup_geo(&geo, mddev, geo_new);
 
-	if (mddev->new_chunk_sectors < (PAGE_SIZE >> 9) ||
-	    !is_power_of_2(mddev->new_chunk_sectors)) {
+	if (copies == -2) {
 		printk(KERN_ERR "md/raid10:%s: chunk size must be "
 		       "at least PAGE_SIZE(%ld) and be a power of 2.\n",
 		       mdname(mddev), PAGE_SIZE);
 		goto out;
 	}
 
-	nc = mddev->new_layout & 255;
-	fc = (mddev->new_layout >> 8) & 255;
-	fo = mddev->new_layout & (1<<16);
-
-	if ((nc*fc) <2 || (nc*fc) > mddev->raid_disks ||
-	    (mddev->new_layout >> 17)) {
+	if (copies < 2 || copies > mddev->raid_disks) {
 		printk(KERN_ERR "md/raid10:%s: unsupported raid10 layout: 0x%8x\n",
 		       mdname(mddev), mddev->new_layout);
 		goto out;
@@ -3264,24 +3301,17 @@ static struct r10conf *setup_conf(struct mddev *mddev)
 	if (!conf->tmppage)
 		goto out;
 
-
-	conf->geo.raid_disks = mddev->raid_disks;
-	conf->geo.near_copies = nc;
-	conf->geo.far_copies = fc;
-	conf->copies = nc*fc;
-	conf->geo.far_offset = fo;
-	conf->geo.chunk_mask = mddev->new_chunk_sectors - 1;
-	conf->geo.chunk_shift = ffz(~mddev->new_chunk_sectors);
-
+	conf->geo = geo;
+	conf->copies = copies;
 	conf->r10bio_pool = mempool_create(NR_RAID10_BIOS, r10bio_pool_alloc,
 					   r10bio_pool_free, conf);
 	if (!conf->r10bio_pool)
 		goto out;
 
 	size = mddev->dev_sectors >> conf->geo.chunk_shift;
-	sector_div(size, fc);
+	sector_div(size, geo.far_copies);
 	size = size * conf->geo.raid_disks;
-	sector_div(size, nc);
+	sector_div(size, geo.near_copies);
 	/* 'size' is now the number of chunks in the array */
 	/* calculate "used chunks per device" in 'stride' */
 	stride = size * conf->copies;
@@ -3294,10 +3324,10 @@ static struct r10conf *setup_conf(struct mddev *mddev)
 
 	conf->dev_sectors = stride << conf->geo.chunk_shift;
 
-	if (fo)
+	if (geo.far_offset)
 		stride = 1;
 	else
-		sector_div(stride, fc);
+		sector_div(stride, geo.far_copies);
 	conf->geo.stride = stride << conf->geo.chunk_shift;
 	conf->prev = conf->geo;
 	conf->reshape_progress = MaxSector;



  parent reply	other threads:[~2012-04-03  5:53 UTC|newest]

Thread overview: 17+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2012-04-03  5:53 [md PATCH 00/10] md patches for 3.5: RAID10 reshape NeilBrown
2012-04-03  5:53 ` [md PATCH 02/10] md: add possibility to change data-offset for devices NeilBrown
2012-04-03  5:53 ` [md PATCH 03/10] md/raid5: Use correct data_offset for all IO NeilBrown
2012-04-03  5:53 ` [md PATCH 01/10] md: allow a reshape operation to be reversed NeilBrown
2012-10-01  9:11   ` Roman Mamedov
2012-10-01 10:15   ` Roman Mamedov
2012-10-02  2:41     ` NeilBrown
2012-04-03  5:53 ` [md PATCH 04/10] md/raid5: allow for change in data_offset while managing a reshape NeilBrown
2012-04-03  5:53 ` [md PATCH 05/10] md/raid10: collect some geometry fields into a dedicated structure NeilBrown
2012-04-03  5:53 ` [md PATCH 06/10] md: teach sync_page_io about new_data_offset NeilBrown
2012-04-03  5:53 ` [md PATCH 10/10] md/raid10: add reshape support NeilBrown
2012-04-03  5:53 ` [md PATCH 07/10] md: use resync_max_sectors for reshape as well as resync NeilBrown
2012-04-03  5:53 ` [md PATCH 08/10] md/raid10: Introduce 'prev' geometry to support reshape NeilBrown
2012-04-03  5:53 ` NeilBrown [this message]
2014-03-01  5:08 ` [md PATCH 00/10] md patches for 3.5: RAID10 reshape Phillip Susi
2014-03-01  7:03   ` NeilBrown
2014-03-01 19:33     ` Phillip Susi

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=20120403055302.19495.47473.stgit@notabene.brown \
    --to=neilb@suse.de \
    --cc=linux-raid@vger.kernel.org \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).