diff options
author | Mike Snitzer <snitzer@redhat.com> | 2009-06-22 05:12:33 -0400 |
---|---|---|
committer | Alasdair G Kergon <agk@redhat.com> | 2009-06-22 05:12:33 -0400 |
commit | af4874e03ed82f050d5872d8c39ce64bf16b5c38 (patch) | |
tree | 38aa5dee43b4bb7a369995d4f38dee992cb051e0 | |
parent | 1197764e403d97231eb6da2b1e16f511a7fd3101 (diff) |
dm target:s introduce iterate devices fn
Add .iterate_devices to 'struct target_type' to allow a function to be
called for all devices in a DM target. Implemented it for all targets
except those in dm-snap.c (origin and snapshot).
(The raid1 version number jumps to 1.12 because we originally reserved
1.1 to 1.11 for 'block_on_error' but ended up using 'handle_errors'
instead.)
Signed-off-by: Mike Snitzer <snitzer@redhat.com>
Signed-off-by: Alasdair G Kergon <agk@redhat.com>
Cc: martin.petersen@oracle.com
-rw-r--r-- | drivers/md/dm-crypt.c | 11 | ||||
-rw-r--r-- | drivers/md/dm-delay.c | 20 | ||||
-rw-r--r-- | drivers/md/dm-linear.c | 11 | ||||
-rw-r--r-- | drivers/md/dm-mpath.c | 23 | ||||
-rw-r--r-- | drivers/md/dm-raid1.c | 17 | ||||
-rw-r--r-- | drivers/md/dm-stripe.c | 18 | ||||
-rw-r--r-- | include/linux/device-mapper.h | 11 |
7 files changed, 105 insertions, 6 deletions
diff --git a/drivers/md/dm-crypt.c b/drivers/md/dm-crypt.c index 04db6c4004a8..9933eb861c71 100644 --- a/drivers/md/dm-crypt.c +++ b/drivers/md/dm-crypt.c | |||
@@ -1313,9 +1313,17 @@ static int crypt_merge(struct dm_target *ti, struct bvec_merge_data *bvm, | |||
1313 | return min(max_size, q->merge_bvec_fn(q, bvm, biovec)); | 1313 | return min(max_size, q->merge_bvec_fn(q, bvm, biovec)); |
1314 | } | 1314 | } |
1315 | 1315 | ||
1316 | static int crypt_iterate_devices(struct dm_target *ti, | ||
1317 | iterate_devices_callout_fn fn, void *data) | ||
1318 | { | ||
1319 | struct crypt_config *cc = ti->private; | ||
1320 | |||
1321 | return fn(ti, cc->dev, cc->start, data); | ||
1322 | } | ||
1323 | |||
1316 | static struct target_type crypt_target = { | 1324 | static struct target_type crypt_target = { |
1317 | .name = "crypt", | 1325 | .name = "crypt", |
1318 | .version= {1, 6, 0}, | 1326 | .version = {1, 7, 0}, |
1319 | .module = THIS_MODULE, | 1327 | .module = THIS_MODULE, |
1320 | .ctr = crypt_ctr, | 1328 | .ctr = crypt_ctr, |
1321 | .dtr = crypt_dtr, | 1329 | .dtr = crypt_dtr, |
@@ -1326,6 +1334,7 @@ static struct target_type crypt_target = { | |||
1326 | .resume = crypt_resume, | 1334 | .resume = crypt_resume, |
1327 | .message = crypt_message, | 1335 | .message = crypt_message, |
1328 | .merge = crypt_merge, | 1336 | .merge = crypt_merge, |
1337 | .iterate_devices = crypt_iterate_devices, | ||
1329 | }; | 1338 | }; |
1330 | 1339 | ||
1331 | static int __init dm_crypt_init(void) | 1340 | static int __init dm_crypt_init(void) |
diff --git a/drivers/md/dm-delay.c b/drivers/md/dm-delay.c index 8ad8a9044bbf..4e5b843cd4d7 100644 --- a/drivers/md/dm-delay.c +++ b/drivers/md/dm-delay.c | |||
@@ -318,9 +318,26 @@ static int delay_status(struct dm_target *ti, status_type_t type, | |||
318 | return 0; | 318 | return 0; |
319 | } | 319 | } |
320 | 320 | ||
321 | static int delay_iterate_devices(struct dm_target *ti, | ||
322 | iterate_devices_callout_fn fn, void *data) | ||
323 | { | ||
324 | struct delay_c *dc = ti->private; | ||
325 | int ret = 0; | ||
326 | |||
327 | ret = fn(ti, dc->dev_read, dc->start_read, data); | ||
328 | if (ret) | ||
329 | goto out; | ||
330 | |||
331 | if (dc->dev_write) | ||
332 | ret = fn(ti, dc->dev_write, dc->start_write, data); | ||
333 | |||
334 | out: | ||
335 | return ret; | ||
336 | } | ||
337 | |||
321 | static struct target_type delay_target = { | 338 | static struct target_type delay_target = { |
322 | .name = "delay", | 339 | .name = "delay", |
323 | .version = {1, 0, 2}, | 340 | .version = {1, 1, 0}, |
324 | .module = THIS_MODULE, | 341 | .module = THIS_MODULE, |
325 | .ctr = delay_ctr, | 342 | .ctr = delay_ctr, |
326 | .dtr = delay_dtr, | 343 | .dtr = delay_dtr, |
@@ -328,6 +345,7 @@ static struct target_type delay_target = { | |||
328 | .presuspend = delay_presuspend, | 345 | .presuspend = delay_presuspend, |
329 | .resume = delay_resume, | 346 | .resume = delay_resume, |
330 | .status = delay_status, | 347 | .status = delay_status, |
348 | .iterate_devices = delay_iterate_devices, | ||
331 | }; | 349 | }; |
332 | 350 | ||
333 | static int __init dm_delay_init(void) | 351 | static int __init dm_delay_init(void) |
diff --git a/drivers/md/dm-linear.c b/drivers/md/dm-linear.c index ecbb17421da4..9184b6deb868 100644 --- a/drivers/md/dm-linear.c +++ b/drivers/md/dm-linear.c | |||
@@ -134,9 +134,17 @@ static int linear_merge(struct dm_target *ti, struct bvec_merge_data *bvm, | |||
134 | return min(max_size, q->merge_bvec_fn(q, bvm, biovec)); | 134 | return min(max_size, q->merge_bvec_fn(q, bvm, biovec)); |
135 | } | 135 | } |
136 | 136 | ||
137 | static int linear_iterate_devices(struct dm_target *ti, | ||
138 | iterate_devices_callout_fn fn, void *data) | ||
139 | { | ||
140 | struct linear_c *lc = ti->private; | ||
141 | |||
142 | return fn(ti, lc->dev, lc->start, data); | ||
143 | } | ||
144 | |||
137 | static struct target_type linear_target = { | 145 | static struct target_type linear_target = { |
138 | .name = "linear", | 146 | .name = "linear", |
139 | .version= {1, 0, 3}, | 147 | .version = {1, 1, 0}, |
140 | .module = THIS_MODULE, | 148 | .module = THIS_MODULE, |
141 | .ctr = linear_ctr, | 149 | .ctr = linear_ctr, |
142 | .dtr = linear_dtr, | 150 | .dtr = linear_dtr, |
@@ -144,6 +152,7 @@ static struct target_type linear_target = { | |||
144 | .status = linear_status, | 152 | .status = linear_status, |
145 | .ioctl = linear_ioctl, | 153 | .ioctl = linear_ioctl, |
146 | .merge = linear_merge, | 154 | .merge = linear_merge, |
155 | .iterate_devices = linear_iterate_devices, | ||
147 | }; | 156 | }; |
148 | 157 | ||
149 | int __init dm_linear_init(void) | 158 | int __init dm_linear_init(void) |
diff --git a/drivers/md/dm-mpath.c b/drivers/md/dm-mpath.c index 890c0e8ed13e..f8aeaaa54afe 100644 --- a/drivers/md/dm-mpath.c +++ b/drivers/md/dm-mpath.c | |||
@@ -1450,12 +1450,32 @@ static int multipath_ioctl(struct dm_target *ti, unsigned int cmd, | |||
1450 | return r ? : __blkdev_driver_ioctl(bdev, mode, cmd, arg); | 1450 | return r ? : __blkdev_driver_ioctl(bdev, mode, cmd, arg); |
1451 | } | 1451 | } |
1452 | 1452 | ||
1453 | static int multipath_iterate_devices(struct dm_target *ti, | ||
1454 | iterate_devices_callout_fn fn, void *data) | ||
1455 | { | ||
1456 | struct multipath *m = ti->private; | ||
1457 | struct priority_group *pg; | ||
1458 | struct pgpath *p; | ||
1459 | int ret = 0; | ||
1460 | |||
1461 | list_for_each_entry(pg, &m->priority_groups, list) { | ||
1462 | list_for_each_entry(p, &pg->pgpaths, list) { | ||
1463 | ret = fn(ti, p->path.dev, ti->begin, data); | ||
1464 | if (ret) | ||
1465 | goto out; | ||
1466 | } | ||
1467 | } | ||
1468 | |||
1469 | out: | ||
1470 | return ret; | ||
1471 | } | ||
1472 | |||
1453 | /*----------------------------------------------------------------- | 1473 | /*----------------------------------------------------------------- |
1454 | * Module setup | 1474 | * Module setup |
1455 | *---------------------------------------------------------------*/ | 1475 | *---------------------------------------------------------------*/ |
1456 | static struct target_type multipath_target = { | 1476 | static struct target_type multipath_target = { |
1457 | .name = "multipath", | 1477 | .name = "multipath", |
1458 | .version = {1, 0, 5}, | 1478 | .version = {1, 1, 0}, |
1459 | .module = THIS_MODULE, | 1479 | .module = THIS_MODULE, |
1460 | .ctr = multipath_ctr, | 1480 | .ctr = multipath_ctr, |
1461 | .dtr = multipath_dtr, | 1481 | .dtr = multipath_dtr, |
@@ -1466,6 +1486,7 @@ static struct target_type multipath_target = { | |||
1466 | .status = multipath_status, | 1486 | .status = multipath_status, |
1467 | .message = multipath_message, | 1487 | .message = multipath_message, |
1468 | .ioctl = multipath_ioctl, | 1488 | .ioctl = multipath_ioctl, |
1489 | .iterate_devices = multipath_iterate_devices, | ||
1469 | }; | 1490 | }; |
1470 | 1491 | ||
1471 | static int __init dm_multipath_init(void) | 1492 | static int __init dm_multipath_init(void) |
diff --git a/drivers/md/dm-raid1.c b/drivers/md/dm-raid1.c index 076fbb4e967a..ce8868c768cc 100644 --- a/drivers/md/dm-raid1.c +++ b/drivers/md/dm-raid1.c | |||
@@ -1283,9 +1283,23 @@ static int mirror_status(struct dm_target *ti, status_type_t type, | |||
1283 | return 0; | 1283 | return 0; |
1284 | } | 1284 | } |
1285 | 1285 | ||
1286 | static int mirror_iterate_devices(struct dm_target *ti, | ||
1287 | iterate_devices_callout_fn fn, void *data) | ||
1288 | { | ||
1289 | struct mirror_set *ms = ti->private; | ||
1290 | int ret = 0; | ||
1291 | unsigned i; | ||
1292 | |||
1293 | for (i = 0; !ret && i < ms->nr_mirrors; i++) | ||
1294 | ret = fn(ti, ms->mirror[i].dev, | ||
1295 | ms->mirror[i].offset, data); | ||
1296 | |||
1297 | return ret; | ||
1298 | } | ||
1299 | |||
1286 | static struct target_type mirror_target = { | 1300 | static struct target_type mirror_target = { |
1287 | .name = "mirror", | 1301 | .name = "mirror", |
1288 | .version = {1, 0, 20}, | 1302 | .version = {1, 12, 0}, |
1289 | .module = THIS_MODULE, | 1303 | .module = THIS_MODULE, |
1290 | .ctr = mirror_ctr, | 1304 | .ctr = mirror_ctr, |
1291 | .dtr = mirror_dtr, | 1305 | .dtr = mirror_dtr, |
@@ -1295,6 +1309,7 @@ static struct target_type mirror_target = { | |||
1295 | .postsuspend = mirror_postsuspend, | 1309 | .postsuspend = mirror_postsuspend, |
1296 | .resume = mirror_resume, | 1310 | .resume = mirror_resume, |
1297 | .status = mirror_status, | 1311 | .status = mirror_status, |
1312 | .iterate_devices = mirror_iterate_devices, | ||
1298 | }; | 1313 | }; |
1299 | 1314 | ||
1300 | static int __init dm_mirror_init(void) | 1315 | static int __init dm_mirror_init(void) |
diff --git a/drivers/md/dm-stripe.c b/drivers/md/dm-stripe.c index c64fe827a5f1..b240e85ae39a 100644 --- a/drivers/md/dm-stripe.c +++ b/drivers/md/dm-stripe.c | |||
@@ -313,15 +313,31 @@ static int stripe_end_io(struct dm_target *ti, struct bio *bio, | |||
313 | return error; | 313 | return error; |
314 | } | 314 | } |
315 | 315 | ||
316 | static int stripe_iterate_devices(struct dm_target *ti, | ||
317 | iterate_devices_callout_fn fn, void *data) | ||
318 | { | ||
319 | struct stripe_c *sc = ti->private; | ||
320 | int ret = 0; | ||
321 | unsigned i = 0; | ||
322 | |||
323 | do | ||
324 | ret = fn(ti, sc->stripe[i].dev, | ||
325 | sc->stripe[i].physical_start, data); | ||
326 | while (!ret && ++i < sc->stripes); | ||
327 | |||
328 | return ret; | ||
329 | } | ||
330 | |||
316 | static struct target_type stripe_target = { | 331 | static struct target_type stripe_target = { |
317 | .name = "striped", | 332 | .name = "striped", |
318 | .version = {1, 1, 0}, | 333 | .version = {1, 2, 0}, |
319 | .module = THIS_MODULE, | 334 | .module = THIS_MODULE, |
320 | .ctr = stripe_ctr, | 335 | .ctr = stripe_ctr, |
321 | .dtr = stripe_dtr, | 336 | .dtr = stripe_dtr, |
322 | .map = stripe_map, | 337 | .map = stripe_map, |
323 | .end_io = stripe_end_io, | 338 | .end_io = stripe_end_io, |
324 | .status = stripe_status, | 339 | .status = stripe_status, |
340 | .iterate_devices = stripe_iterate_devices, | ||
325 | }; | 341 | }; |
326 | 342 | ||
327 | int __init dm_stripe_init(void) | 343 | int __init dm_stripe_init(void) |
diff --git a/include/linux/device-mapper.h b/include/linux/device-mapper.h index 236880c1dc3f..deac3b4e5e18 100644 --- a/include/linux/device-mapper.h +++ b/include/linux/device-mapper.h | |||
@@ -11,6 +11,7 @@ | |||
11 | #include <linux/bio.h> | 11 | #include <linux/bio.h> |
12 | #include <linux/blkdev.h> | 12 | #include <linux/blkdev.h> |
13 | 13 | ||
14 | struct dm_dev; | ||
14 | struct dm_target; | 15 | struct dm_target; |
15 | struct dm_table; | 16 | struct dm_table; |
16 | struct mapped_device; | 17 | struct mapped_device; |
@@ -81,6 +82,15 @@ typedef int (*dm_ioctl_fn) (struct dm_target *ti, unsigned int cmd, | |||
81 | typedef int (*dm_merge_fn) (struct dm_target *ti, struct bvec_merge_data *bvm, | 82 | typedef int (*dm_merge_fn) (struct dm_target *ti, struct bvec_merge_data *bvm, |
82 | struct bio_vec *biovec, int max_size); | 83 | struct bio_vec *biovec, int max_size); |
83 | 84 | ||
85 | typedef int (*iterate_devices_callout_fn) (struct dm_target *ti, | ||
86 | struct dm_dev *dev, | ||
87 | sector_t physical_start, | ||
88 | void *data); | ||
89 | |||
90 | typedef int (*dm_iterate_devices_fn) (struct dm_target *ti, | ||
91 | iterate_devices_callout_fn fn, | ||
92 | void *data); | ||
93 | |||
84 | /* | 94 | /* |
85 | * Returns: | 95 | * Returns: |
86 | * 0: The target can handle the next I/O immediately. | 96 | * 0: The target can handle the next I/O immediately. |
@@ -139,6 +149,7 @@ struct target_type { | |||
139 | dm_ioctl_fn ioctl; | 149 | dm_ioctl_fn ioctl; |
140 | dm_merge_fn merge; | 150 | dm_merge_fn merge; |
141 | dm_busy_fn busy; | 151 | dm_busy_fn busy; |
152 | dm_iterate_devices_fn iterate_devices; | ||
142 | 153 | ||
143 | /* For internal device-mapper use. */ | 154 | /* For internal device-mapper use. */ |
144 | struct list_head list; | 155 | struct list_head list; |