aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorMikulas Patocka <mpatocka@redhat.com>2009-12-10 18:52:08 -0500
committerAlasdair G Kergon <agk@redhat.com>2009-12-10 18:52:08 -0500
commit7e201b35132a1f02c931a0a06760766c846bb49b (patch)
tree02ab2bcf4609763ab9780db2a87b9f37aa77186f
parent102c6ddb1d081a6a1fede38c43a42c9811313ec7 (diff)
dm snapshot: abstract minimum_chunk_size fn
The origin needs to find minimum chunksize of all snapshots. This logic is moved to a separate function because it will be used at another place in the snapshot merge patches. Signed-off-by: Mikulas Patocka <mpatocka@redhat.com> Reviewed-by: Mike Snitzer <snitzer@redhat.com> Reviewed-by: Jonathan Brassow <jbrassow@redhat.com> Signed-off-by: Alasdair G Kergon <agk@redhat.com>
-rw-r--r--drivers/md/dm-snap.c34
1 files changed, 22 insertions, 12 deletions
diff --git a/drivers/md/dm-snap.c b/drivers/md/dm-snap.c
index 8a4a9c838afd..48978ab42ae5 100644
--- a/drivers/md/dm-snap.c
+++ b/drivers/md/dm-snap.c
@@ -523,6 +523,25 @@ static int dm_add_exception(void *context, chunk_t old, chunk_t new)
523 return 0; 523 return 0;
524} 524}
525 525
526#define min_not_zero(l, r) (((l) == 0) ? (r) : (((r) == 0) ? (l) : min(l, r)))
527
528/*
529 * Return a minimum chunk size of all snapshots that have the specified origin.
530 * Return zero if the origin has no snapshots.
531 */
532static sector_t __minimum_chunk_size(struct origin *o)
533{
534 struct dm_snapshot *snap;
535 unsigned chunk_size = 0;
536
537 if (o)
538 list_for_each_entry(snap, &o->snapshots, list)
539 chunk_size = min_not_zero(chunk_size,
540 snap->store->chunk_size);
541
542 return chunk_size;
543}
544
526/* 545/*
527 * Hard coded magic. 546 * Hard coded magic.
528 */ 547 */
@@ -1395,8 +1414,6 @@ static int origin_map(struct dm_target *ti, struct bio *bio,
1395 return (bio_rw(bio) == WRITE) ? do_origin(dev, bio) : DM_MAPIO_REMAPPED; 1414 return (bio_rw(bio) == WRITE) ? do_origin(dev, bio) : DM_MAPIO_REMAPPED;
1396} 1415}
1397 1416
1398#define min_not_zero(l, r) (l == 0) ? r : ((r == 0) ? l : min(l, r))
1399
1400/* 1417/*
1401 * Set the target "split_io" field to the minimum of all the snapshots' 1418 * Set the target "split_io" field to the minimum of all the snapshots'
1402 * chunk sizes. 1419 * chunk sizes.
@@ -1404,19 +1421,12 @@ static int origin_map(struct dm_target *ti, struct bio *bio,
1404static void origin_resume(struct dm_target *ti) 1421static void origin_resume(struct dm_target *ti)
1405{ 1422{
1406 struct dm_dev *dev = ti->private; 1423 struct dm_dev *dev = ti->private;
1407 struct dm_snapshot *snap;
1408 struct origin *o;
1409 unsigned chunk_size = 0;
1410 1424
1411 down_read(&_origins_lock); 1425 down_read(&_origins_lock);
1412 o = __lookup_origin(dev->bdev);
1413 if (o)
1414 list_for_each_entry (snap, &o->snapshots, list)
1415 chunk_size = min_not_zero(chunk_size,
1416 snap->store->chunk_size);
1417 up_read(&_origins_lock);
1418 1426
1419 ti->split_io = chunk_size; 1427 ti->split_io = __minimum_chunk_size(__lookup_origin(dev->bdev));
1428
1429 up_read(&_origins_lock);
1420} 1430}
1421 1431
1422static int origin_status(struct dm_target *ti, status_type_t type, char *result, 1432static int origin_status(struct dm_target *ti, status_type_t type, char *result,