diff options
author | Linus Torvalds <torvalds@linux-foundation.org> | 2009-10-29 12:16:01 -0400 |
---|---|---|
committer | Linus Torvalds <torvalds@linux-foundation.org> | 2009-10-29 12:16:01 -0400 |
commit | 61aa1620be20ddad75dde7882509bfe00148b8aa (patch) | |
tree | 0ce3d4b71d06c460f8c24347ebd8630a52000ed5 /drivers/s390 | |
parent | d4f452f8259086028aa17d495deb735e056188f4 (diff) | |
parent | 9e820afd0c4f3c8e8894aa91f5671fd7d11a787b (diff) |
Merge git://git.kernel.org/pub/scm/linux/kernel/git/jejb/scsi-rc-fixes-2.6
* git://git.kernel.org/pub/scm/linux/kernel/git/jejb/scsi-rc-fixes-2.6:
[SCSI] zfcp: Flush SCSI registration work when adding unit
[SCSI] zfcp: Fix timer initialization for ct and els requests
[SCSI] zfcp: Warn about storage devices with broken PLOGI data
[SCSI] zfcp: Handle WWPN mismatch in PLOGI payload
[SCSI] zfcp: fix kfree handling in zfcp_init_device_setup
[SCSI] fix memory leak in initialization
Diffstat (limited to 'drivers/s390')
-rw-r--r-- | drivers/s390/scsi/zfcp_aux.c | 11 | ||||
-rw-r--r-- | drivers/s390/scsi/zfcp_erp.c | 22 | ||||
-rw-r--r-- | drivers/s390/scsi/zfcp_ext.h | 1 | ||||
-rw-r--r-- | drivers/s390/scsi/zfcp_fc.c | 11 | ||||
-rw-r--r-- | drivers/s390/scsi/zfcp_fsf.c | 13 | ||||
-rw-r--r-- | drivers/s390/scsi/zfcp_sysfs.c | 1 |
6 files changed, 39 insertions, 20 deletions
diff --git a/drivers/s390/scsi/zfcp_aux.c b/drivers/s390/scsi/zfcp_aux.c index 0f79f3af4f54..2889e5f2dfd3 100644 --- a/drivers/s390/scsi/zfcp_aux.c +++ b/drivers/s390/scsi/zfcp_aux.c | |||
@@ -128,12 +128,13 @@ out_ccwdev: | |||
128 | static void __init zfcp_init_device_setup(char *devstr) | 128 | static void __init zfcp_init_device_setup(char *devstr) |
129 | { | 129 | { |
130 | char *token; | 130 | char *token; |
131 | char *str; | 131 | char *str, *str_saved; |
132 | char busid[ZFCP_BUS_ID_SIZE]; | 132 | char busid[ZFCP_BUS_ID_SIZE]; |
133 | u64 wwpn, lun; | 133 | u64 wwpn, lun; |
134 | 134 | ||
135 | /* duplicate devstr and keep the original for sysfs presentation*/ | 135 | /* duplicate devstr and keep the original for sysfs presentation*/ |
136 | str = kmalloc(strlen(devstr) + 1, GFP_KERNEL); | 136 | str_saved = kmalloc(strlen(devstr) + 1, GFP_KERNEL); |
137 | str = str_saved; | ||
137 | if (!str) | 138 | if (!str) |
138 | return; | 139 | return; |
139 | 140 | ||
@@ -152,12 +153,12 @@ static void __init zfcp_init_device_setup(char *devstr) | |||
152 | if (!token || strict_strtoull(token, 0, (unsigned long long *) &lun)) | 153 | if (!token || strict_strtoull(token, 0, (unsigned long long *) &lun)) |
153 | goto err_out; | 154 | goto err_out; |
154 | 155 | ||
155 | kfree(str); | 156 | kfree(str_saved); |
156 | zfcp_init_device_configure(busid, wwpn, lun); | 157 | zfcp_init_device_configure(busid, wwpn, lun); |
157 | return; | 158 | return; |
158 | 159 | ||
159 | err_out: | 160 | err_out: |
160 | kfree(str); | 161 | kfree(str_saved); |
161 | pr_err("%s is not a valid SCSI device\n", devstr); | 162 | pr_err("%s is not a valid SCSI device\n", devstr); |
162 | } | 163 | } |
163 | 164 | ||
diff --git a/drivers/s390/scsi/zfcp_erp.c b/drivers/s390/scsi/zfcp_erp.c index 73d366ba31e5..f73e2180f333 100644 --- a/drivers/s390/scsi/zfcp_erp.c +++ b/drivers/s390/scsi/zfcp_erp.c | |||
@@ -858,10 +858,7 @@ static int zfcp_erp_port_strategy_open_common(struct zfcp_erp_action *act) | |||
858 | if (fc_host_port_type(adapter->scsi_host) == FC_PORTTYPE_PTP) | 858 | if (fc_host_port_type(adapter->scsi_host) == FC_PORTTYPE_PTP) |
859 | return zfcp_erp_open_ptp_port(act); | 859 | return zfcp_erp_open_ptp_port(act); |
860 | if (!port->d_id) { | 860 | if (!port->d_id) { |
861 | zfcp_port_get(port); | 861 | zfcp_fc_trigger_did_lookup(port); |
862 | if (!queue_work(adapter->work_queue, | ||
863 | &port->gid_pn_work)) | ||
864 | zfcp_port_put(port); | ||
865 | return ZFCP_ERP_EXIT; | 862 | return ZFCP_ERP_EXIT; |
866 | } | 863 | } |
867 | return zfcp_erp_port_strategy_open_port(act); | 864 | return zfcp_erp_port_strategy_open_port(act); |
@@ -869,12 +866,11 @@ static int zfcp_erp_port_strategy_open_common(struct zfcp_erp_action *act) | |||
869 | case ZFCP_ERP_STEP_PORT_OPENING: | 866 | case ZFCP_ERP_STEP_PORT_OPENING: |
870 | /* D_ID might have changed during open */ | 867 | /* D_ID might have changed during open */ |
871 | if (p_status & ZFCP_STATUS_COMMON_OPEN) { | 868 | if (p_status & ZFCP_STATUS_COMMON_OPEN) { |
872 | if (port->d_id) | 869 | if (!port->d_id) { |
873 | return ZFCP_ERP_SUCCEEDED; | 870 | zfcp_fc_trigger_did_lookup(port); |
874 | else { | 871 | return ZFCP_ERP_EXIT; |
875 | act->step = ZFCP_ERP_STEP_PORT_CLOSING; | ||
876 | return ZFCP_ERP_CONTINUES; | ||
877 | } | 872 | } |
873 | return ZFCP_ERP_SUCCEEDED; | ||
878 | } | 874 | } |
879 | if (port->d_id && !(p_status & ZFCP_STATUS_COMMON_NOESC)) { | 875 | if (port->d_id && !(p_status & ZFCP_STATUS_COMMON_NOESC)) { |
880 | port->d_id = 0; | 876 | port->d_id = 0; |
@@ -889,19 +885,21 @@ static int zfcp_erp_port_strategy_open_common(struct zfcp_erp_action *act) | |||
889 | static int zfcp_erp_port_strategy(struct zfcp_erp_action *erp_action) | 885 | static int zfcp_erp_port_strategy(struct zfcp_erp_action *erp_action) |
890 | { | 886 | { |
891 | struct zfcp_port *port = erp_action->port; | 887 | struct zfcp_port *port = erp_action->port; |
888 | int p_status = atomic_read(&port->status); | ||
892 | 889 | ||
893 | if (atomic_read(&port->status) & ZFCP_STATUS_COMMON_NOESC) | 890 | if ((p_status & ZFCP_STATUS_COMMON_NOESC) && |
891 | !(p_status & ZFCP_STATUS_COMMON_OPEN)) | ||
894 | goto close_init_done; | 892 | goto close_init_done; |
895 | 893 | ||
896 | switch (erp_action->step) { | 894 | switch (erp_action->step) { |
897 | case ZFCP_ERP_STEP_UNINITIALIZED: | 895 | case ZFCP_ERP_STEP_UNINITIALIZED: |
898 | zfcp_erp_port_strategy_clearstati(port); | 896 | zfcp_erp_port_strategy_clearstati(port); |
899 | if (atomic_read(&port->status) & ZFCP_STATUS_COMMON_OPEN) | 897 | if (p_status & ZFCP_STATUS_COMMON_OPEN) |
900 | return zfcp_erp_port_strategy_close(erp_action); | 898 | return zfcp_erp_port_strategy_close(erp_action); |
901 | break; | 899 | break; |
902 | 900 | ||
903 | case ZFCP_ERP_STEP_PORT_CLOSING: | 901 | case ZFCP_ERP_STEP_PORT_CLOSING: |
904 | if (atomic_read(&port->status) & ZFCP_STATUS_COMMON_OPEN) | 902 | if (p_status & ZFCP_STATUS_COMMON_OPEN) |
905 | return ZFCP_ERP_FAILED; | 903 | return ZFCP_ERP_FAILED; |
906 | break; | 904 | break; |
907 | } | 905 | } |
diff --git a/drivers/s390/scsi/zfcp_ext.h b/drivers/s390/scsi/zfcp_ext.h index 629edec70405..b3f28deb4505 100644 --- a/drivers/s390/scsi/zfcp_ext.h +++ b/drivers/s390/scsi/zfcp_ext.h | |||
@@ -96,6 +96,7 @@ extern int zfcp_fc_scan_ports(struct zfcp_adapter *); | |||
96 | extern void _zfcp_fc_scan_ports_later(struct work_struct *); | 96 | extern void _zfcp_fc_scan_ports_later(struct work_struct *); |
97 | extern void zfcp_fc_incoming_els(struct zfcp_fsf_req *); | 97 | extern void zfcp_fc_incoming_els(struct zfcp_fsf_req *); |
98 | extern void zfcp_fc_port_did_lookup(struct work_struct *); | 98 | extern void zfcp_fc_port_did_lookup(struct work_struct *); |
99 | extern void zfcp_fc_trigger_did_lookup(struct zfcp_port *); | ||
99 | extern void zfcp_fc_plogi_evaluate(struct zfcp_port *, struct fsf_plogi *); | 100 | extern void zfcp_fc_plogi_evaluate(struct zfcp_port *, struct fsf_plogi *); |
100 | extern void zfcp_fc_test_link(struct zfcp_port *); | 101 | extern void zfcp_fc_test_link(struct zfcp_port *); |
101 | extern void zfcp_fc_link_test_work(struct work_struct *); | 102 | extern void zfcp_fc_link_test_work(struct work_struct *); |
diff --git a/drivers/s390/scsi/zfcp_fc.c b/drivers/s390/scsi/zfcp_fc.c index 722f22de8753..df23bcead23d 100644 --- a/drivers/s390/scsi/zfcp_fc.c +++ b/drivers/s390/scsi/zfcp_fc.c | |||
@@ -361,6 +361,17 @@ out: | |||
361 | } | 361 | } |
362 | 362 | ||
363 | /** | 363 | /** |
364 | * zfcp_fc_trigger_did_lookup - trigger the d_id lookup using a GID_PN request | ||
365 | * @port: The zfcp_port to lookup the d_id for. | ||
366 | */ | ||
367 | void zfcp_fc_trigger_did_lookup(struct zfcp_port *port) | ||
368 | { | ||
369 | zfcp_port_get(port); | ||
370 | if (!queue_work(port->adapter->work_queue, &port->gid_pn_work)) | ||
371 | zfcp_port_put(port); | ||
372 | } | ||
373 | |||
374 | /** | ||
364 | * zfcp_fc_plogi_evaluate - evaluate PLOGI playload | 375 | * zfcp_fc_plogi_evaluate - evaluate PLOGI playload |
365 | * @port: zfcp_port structure | 376 | * @port: zfcp_port structure |
366 | * @plogi: plogi payload | 377 | * @plogi: plogi payload |
diff --git a/drivers/s390/scsi/zfcp_fsf.c b/drivers/s390/scsi/zfcp_fsf.c index 38a7e4a6b639..4e41baa0c141 100644 --- a/drivers/s390/scsi/zfcp_fsf.c +++ b/drivers/s390/scsi/zfcp_fsf.c | |||
@@ -1079,7 +1079,7 @@ static int zfcp_fsf_setup_ct_els(struct zfcp_fsf_req *req, | |||
1079 | /* common settings for ct/gs and els requests */ | 1079 | /* common settings for ct/gs and els requests */ |
1080 | req->qtcb->bottom.support.service_class = FSF_CLASS_3; | 1080 | req->qtcb->bottom.support.service_class = FSF_CLASS_3; |
1081 | req->qtcb->bottom.support.timeout = 2 * R_A_TOV; | 1081 | req->qtcb->bottom.support.timeout = 2 * R_A_TOV; |
1082 | zfcp_fsf_start_timer(req, 2 * R_A_TOV + 10); | 1082 | zfcp_fsf_start_timer(req, (2 * R_A_TOV + 10) * HZ); |
1083 | 1083 | ||
1084 | return 0; | 1084 | return 0; |
1085 | } | 1085 | } |
@@ -1475,9 +1475,16 @@ static void zfcp_fsf_open_port_handler(struct zfcp_fsf_req *req) | |||
1475 | plogi = (struct fsf_plogi *) req->qtcb->bottom.support.els; | 1475 | plogi = (struct fsf_plogi *) req->qtcb->bottom.support.els; |
1476 | if (req->qtcb->bottom.support.els1_length >= | 1476 | if (req->qtcb->bottom.support.els1_length >= |
1477 | FSF_PLOGI_MIN_LEN) { | 1477 | FSF_PLOGI_MIN_LEN) { |
1478 | if (plogi->serv_param.wwpn != port->wwpn) | 1478 | if (plogi->serv_param.wwpn != port->wwpn) { |
1479 | port->d_id = 0; | 1479 | port->d_id = 0; |
1480 | else { | 1480 | dev_warn(&port->adapter->ccw_device->dev, |
1481 | "A port opened with WWPN 0x%016Lx " | ||
1482 | "returned data that identifies it as " | ||
1483 | "WWPN 0x%016Lx\n", | ||
1484 | (unsigned long long) port->wwpn, | ||
1485 | (unsigned long long) | ||
1486 | plogi->serv_param.wwpn); | ||
1487 | } else { | ||
1481 | port->wwnn = plogi->serv_param.wwnn; | 1488 | port->wwnn = plogi->serv_param.wwnn; |
1482 | zfcp_fc_plogi_evaluate(port, plogi); | 1489 | zfcp_fc_plogi_evaluate(port, plogi); |
1483 | } | 1490 | } |
diff --git a/drivers/s390/scsi/zfcp_sysfs.c b/drivers/s390/scsi/zfcp_sysfs.c index 079a8cf518a3..d31000886ca8 100644 --- a/drivers/s390/scsi/zfcp_sysfs.c +++ b/drivers/s390/scsi/zfcp_sysfs.c | |||
@@ -224,6 +224,7 @@ static ssize_t zfcp_sysfs_unit_add_store(struct device *dev, | |||
224 | 224 | ||
225 | zfcp_erp_unit_reopen(unit, 0, "syuas_1", NULL); | 225 | zfcp_erp_unit_reopen(unit, 0, "syuas_1", NULL); |
226 | zfcp_erp_wait(unit->port->adapter); | 226 | zfcp_erp_wait(unit->port->adapter); |
227 | flush_work(&unit->scsi_work); | ||
227 | zfcp_unit_put(unit); | 228 | zfcp_unit_put(unit); |
228 | out: | 229 | out: |
229 | mutex_unlock(&zfcp_data.config_mutex); | 230 | mutex_unlock(&zfcp_data.config_mutex); |