diff options
Diffstat (limited to 'drivers/md/dm-mpath.c')
-rw-r--r-- | drivers/md/dm-mpath.c | 14 |
1 files changed, 8 insertions, 6 deletions
diff --git a/drivers/md/dm-mpath.c b/drivers/md/dm-mpath.c index d94ba6f72ff5..419362c2d8ac 100644 --- a/drivers/md/dm-mpath.c +++ b/drivers/md/dm-mpath.c | |||
@@ -806,19 +806,19 @@ static int parse_path_selector(struct dm_arg_set *as, struct priority_group *pg, | |||
806 | } | 806 | } |
807 | 807 | ||
808 | static int setup_scsi_dh(struct block_device *bdev, struct multipath *m, | 808 | static int setup_scsi_dh(struct block_device *bdev, struct multipath *m, |
809 | const char *attached_handler_name, char **error) | 809 | const char **attached_handler_name, char **error) |
810 | { | 810 | { |
811 | struct request_queue *q = bdev_get_queue(bdev); | 811 | struct request_queue *q = bdev_get_queue(bdev); |
812 | int r; | 812 | int r; |
813 | 813 | ||
814 | if (test_bit(MPATHF_RETAIN_ATTACHED_HW_HANDLER, &m->flags)) { | 814 | if (test_bit(MPATHF_RETAIN_ATTACHED_HW_HANDLER, &m->flags)) { |
815 | retain: | 815 | retain: |
816 | if (attached_handler_name) { | 816 | if (*attached_handler_name) { |
817 | /* | 817 | /* |
818 | * Clear any hw_handler_params associated with a | 818 | * Clear any hw_handler_params associated with a |
819 | * handler that isn't already attached. | 819 | * handler that isn't already attached. |
820 | */ | 820 | */ |
821 | if (m->hw_handler_name && strcmp(attached_handler_name, m->hw_handler_name)) { | 821 | if (m->hw_handler_name && strcmp(*attached_handler_name, m->hw_handler_name)) { |
822 | kfree(m->hw_handler_params); | 822 | kfree(m->hw_handler_params); |
823 | m->hw_handler_params = NULL; | 823 | m->hw_handler_params = NULL; |
824 | } | 824 | } |
@@ -830,7 +830,8 @@ retain: | |||
830 | * handler instead of the original table passed in. | 830 | * handler instead of the original table passed in. |
831 | */ | 831 | */ |
832 | kfree(m->hw_handler_name); | 832 | kfree(m->hw_handler_name); |
833 | m->hw_handler_name = attached_handler_name; | 833 | m->hw_handler_name = *attached_handler_name; |
834 | *attached_handler_name = NULL; | ||
834 | } | 835 | } |
835 | } | 836 | } |
836 | 837 | ||
@@ -867,7 +868,7 @@ static struct pgpath *parse_path(struct dm_arg_set *as, struct path_selector *ps | |||
867 | struct pgpath *p; | 868 | struct pgpath *p; |
868 | struct multipath *m = ti->private; | 869 | struct multipath *m = ti->private; |
869 | struct request_queue *q; | 870 | struct request_queue *q; |
870 | const char *attached_handler_name; | 871 | const char *attached_handler_name = NULL; |
871 | 872 | ||
872 | /* we need at least a path arg */ | 873 | /* we need at least a path arg */ |
873 | if (as->argc < 1) { | 874 | if (as->argc < 1) { |
@@ -890,7 +891,7 @@ static struct pgpath *parse_path(struct dm_arg_set *as, struct path_selector *ps | |||
890 | attached_handler_name = scsi_dh_attached_handler_name(q, GFP_KERNEL); | 891 | attached_handler_name = scsi_dh_attached_handler_name(q, GFP_KERNEL); |
891 | if (attached_handler_name || m->hw_handler_name) { | 892 | if (attached_handler_name || m->hw_handler_name) { |
892 | INIT_DELAYED_WORK(&p->activate_path, activate_path_work); | 893 | INIT_DELAYED_WORK(&p->activate_path, activate_path_work); |
893 | r = setup_scsi_dh(p->path.dev->bdev, m, attached_handler_name, &ti->error); | 894 | r = setup_scsi_dh(p->path.dev->bdev, m, &attached_handler_name, &ti->error); |
894 | if (r) { | 895 | if (r) { |
895 | dm_put_device(ti, p->path.dev); | 896 | dm_put_device(ti, p->path.dev); |
896 | goto bad; | 897 | goto bad; |
@@ -905,6 +906,7 @@ static struct pgpath *parse_path(struct dm_arg_set *as, struct path_selector *ps | |||
905 | 906 | ||
906 | return p; | 907 | return p; |
907 | bad: | 908 | bad: |
909 | kfree(attached_handler_name); | ||
908 | free_pgpath(p); | 910 | free_pgpath(p); |
909 | return ERR_PTR(r); | 911 | return ERR_PTR(r); |
910 | } | 912 | } |