dm table: fix queue_limit checking device iterator

The logic to check for valid device areas is inverted relative to proper
use with iterate_devices.

The iterate_devices method calls its callback for every underlying
device in the target.  If any callback returns non-zero, iterate_devices
exits immediately.  But the callback device_area_is_valid() returns 0 on
error and 1 on success.  The overall effect without is that an error is
issued only if every device is invalid.

This patch renames device_area_is_valid to device_area_is_invalid and
inverts the logic so that one invalid device is sufficient to raise
an error.

Signed-off-by: Mikulas Patocka <mpatocka@redhat.com>
Signed-off-by: Mike Snitzer <snitzer@redhat.com>
Signed-off-by: Alasdair G Kergon <agk@redhat.com>
This commit is contained in:
Mikulas Patocka 2009-09-04 20:40:22 +01:00 committed by Alasdair G Kergon
parent 8811f46c1f
commit f6a1ed1086

View File

@ -343,10 +343,10 @@ static void close_dev(struct dm_dev_internal *d, struct mapped_device *md)
} }
/* /*
* If possible, this checks an area of a destination device is valid. * If possible, this checks an area of a destination device is invalid.
*/ */
static int device_area_is_valid(struct dm_target *ti, struct dm_dev *dev, static int device_area_is_invalid(struct dm_target *ti, struct dm_dev *dev,
sector_t start, sector_t len, void *data) sector_t start, sector_t len, void *data)
{ {
struct queue_limits *limits = data; struct queue_limits *limits = data;
struct block_device *bdev = dev->bdev; struct block_device *bdev = dev->bdev;
@ -357,16 +357,16 @@ static int device_area_is_valid(struct dm_target *ti, struct dm_dev *dev,
char b[BDEVNAME_SIZE]; char b[BDEVNAME_SIZE];
if (!dev_size) if (!dev_size)
return 1; return 0;
if ((start >= dev_size) || (start + len > dev_size)) { if ((start >= dev_size) || (start + len > dev_size)) {
DMWARN("%s: %s too small for target", DMWARN("%s: %s too small for target",
dm_device_name(ti->table->md), bdevname(bdev, b)); dm_device_name(ti->table->md), bdevname(bdev, b));
return 0; return 1;
} }
if (logical_block_size_sectors <= 1) if (logical_block_size_sectors <= 1)
return 1; return 0;
if (start & (logical_block_size_sectors - 1)) { if (start & (logical_block_size_sectors - 1)) {
DMWARN("%s: start=%llu not aligned to h/w " DMWARN("%s: start=%llu not aligned to h/w "
@ -374,7 +374,7 @@ static int device_area_is_valid(struct dm_target *ti, struct dm_dev *dev,
dm_device_name(ti->table->md), dm_device_name(ti->table->md),
(unsigned long long)start, (unsigned long long)start,
limits->logical_block_size, bdevname(bdev, b)); limits->logical_block_size, bdevname(bdev, b));
return 0; return 1;
} }
if (len & (logical_block_size_sectors - 1)) { if (len & (logical_block_size_sectors - 1)) {
@ -383,10 +383,10 @@ static int device_area_is_valid(struct dm_target *ti, struct dm_dev *dev,
dm_device_name(ti->table->md), dm_device_name(ti->table->md),
(unsigned long long)len, (unsigned long long)len,
limits->logical_block_size, bdevname(bdev, b)); limits->logical_block_size, bdevname(bdev, b));
return 0; return 1;
} }
return 1; return 0;
} }
/* /*
@ -1000,8 +1000,8 @@ int dm_calculate_queue_limits(struct dm_table *table,
* Check each device area is consistent with the target's * Check each device area is consistent with the target's
* overall queue limits. * overall queue limits.
*/ */
if (!ti->type->iterate_devices(ti, device_area_is_valid, if (ti->type->iterate_devices(ti, device_area_is_invalid,
&ti_limits)) &ti_limits))
return -EINVAL; return -EINVAL;
combine_limits: combine_limits: