aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/md/dm.c
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/md/dm.c')
-rw-r--r--drivers/md/dm.c31
1 files changed, 24 insertions, 7 deletions
diff --git a/drivers/md/dm.c b/drivers/md/dm.c
index 07cbbb8eb3e0..88c0fd657825 100644
--- a/drivers/md/dm.c
+++ b/drivers/md/dm.c
@@ -672,13 +672,19 @@ static struct bio *clone_bio(struct bio *bio, sector_t sector,
672 return clone; 672 return clone;
673} 673}
674 674
675static void __clone_and_map(struct clone_info *ci) 675static int __clone_and_map(struct clone_info *ci)
676{ 676{
677 struct bio *clone, *bio = ci->bio; 677 struct bio *clone, *bio = ci->bio;
678 struct dm_target *ti = dm_table_find_target(ci->map, ci->sector); 678 struct dm_target *ti;
679 sector_t len = 0, max = max_io_len(ci->md, ci->sector, ti); 679 sector_t len = 0, max;
680 struct dm_target_io *tio; 680 struct dm_target_io *tio;
681 681
682 ti = dm_table_find_target(ci->map, ci->sector);
683 if (!dm_target_is_valid(ti))
684 return -EIO;
685
686 max = max_io_len(ci->md, ci->sector, ti);
687
682 /* 688 /*
683 * Allocate a target io object. 689 * Allocate a target io object.
684 */ 690 */
@@ -736,6 +742,9 @@ static void __clone_and_map(struct clone_info *ci)
736 do { 742 do {
737 if (offset) { 743 if (offset) {
738 ti = dm_table_find_target(ci->map, ci->sector); 744 ti = dm_table_find_target(ci->map, ci->sector);
745 if (!dm_target_is_valid(ti))
746 return -EIO;
747
739 max = max_io_len(ci->md, ci->sector, ti); 748 max = max_io_len(ci->md, ci->sector, ti);
740 749
741 tio = alloc_tio(ci->md); 750 tio = alloc_tio(ci->md);
@@ -759,6 +768,8 @@ static void __clone_and_map(struct clone_info *ci)
759 768
760 ci->idx++; 769 ci->idx++;
761 } 770 }
771
772 return 0;
762} 773}
763 774
764/* 775/*
@@ -767,6 +778,7 @@ static void __clone_and_map(struct clone_info *ci)
767static int __split_bio(struct mapped_device *md, struct bio *bio) 778static int __split_bio(struct mapped_device *md, struct bio *bio)
768{ 779{
769 struct clone_info ci; 780 struct clone_info ci;
781 int error = 0;
770 782
771 ci.map = dm_get_table(md); 783 ci.map = dm_get_table(md);
772 if (unlikely(!ci.map)) 784 if (unlikely(!ci.map))
@@ -784,11 +796,11 @@ static int __split_bio(struct mapped_device *md, struct bio *bio)
784 ci.idx = bio->bi_idx; 796 ci.idx = bio->bi_idx;
785 797
786 start_io_acct(ci.io); 798 start_io_acct(ci.io);
787 while (ci.sector_count) 799 while (ci.sector_count && !error)
788 __clone_and_map(&ci); 800 error = __clone_and_map(&ci);
789 801
790 /* drop the extra reference count */ 802 /* drop the extra reference count */
791 dec_pending(ci.io, 0); 803 dec_pending(ci.io, error);
792 dm_table_put(ci.map); 804 dm_table_put(ci.map);
793 805
794 return 0; 806 return 0;
@@ -1502,7 +1514,7 @@ int dm_resume(struct mapped_device *md)
1502 1514
1503 dm_table_unplug_all(map); 1515 dm_table_unplug_all(map);
1504 1516
1505 kobject_uevent(&md->disk->kobj, KOBJ_CHANGE); 1517 dm_kobject_uevent(md);
1506 1518
1507 r = 0; 1519 r = 0;
1508 1520
@@ -1516,6 +1528,11 @@ out:
1516/*----------------------------------------------------------------- 1528/*-----------------------------------------------------------------
1517 * Event notification. 1529 * Event notification.
1518 *---------------------------------------------------------------*/ 1530 *---------------------------------------------------------------*/
1531void dm_kobject_uevent(struct mapped_device *md)
1532{
1533 kobject_uevent(&md->disk->kobj, KOBJ_CHANGE);
1534}
1535
1519uint32_t dm_next_uevent_seq(struct mapped_device *md) 1536uint32_t dm_next_uevent_seq(struct mapped_device *md)
1520{ 1537{
1521 return atomic_add_return(1, &md->uevent_seq); 1538 return atomic_add_return(1, &md->uevent_seq);