aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/scsi/qla2xxx/qla_attr.c
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/scsi/qla2xxx/qla_attr.c')
-rw-r--r--drivers/scsi/qla2xxx/qla_attr.c147
1 files changed, 131 insertions, 16 deletions
diff --git a/drivers/scsi/qla2xxx/qla_attr.c b/drivers/scsi/qla2xxx/qla_attr.c
index 5ab953029f8..1c28215f8be 100644
--- a/drivers/scsi/qla2xxx/qla_attr.c
+++ b/drivers/scsi/qla2xxx/qla_attr.c
@@ -1,6 +1,6 @@
1/* 1/*
2 * QLogic Fibre Channel HBA Driver 2 * QLogic Fibre Channel HBA Driver
3 * Copyright (c) 2003-2011 QLogic Corporation 3 * Copyright (c) 2003-2012 QLogic Corporation
4 * 4 *
5 * See LICENSE.qla2xxx for copyright and licensing details. 5 * See LICENSE.qla2xxx for copyright and licensing details.
6 */ 6 */
@@ -26,7 +26,7 @@ qla2x00_sysfs_read_fw_dump(struct file *filp, struct kobject *kobj,
26 struct qla_hw_data *ha = vha->hw; 26 struct qla_hw_data *ha = vha->hw;
27 int rval = 0; 27 int rval = 0;
28 28
29 if (ha->fw_dump_reading == 0) 29 if (!(ha->fw_dump_reading || ha->mctp_dump_reading))
30 return 0; 30 return 0;
31 31
32 if (IS_QLA82XX(ha)) { 32 if (IS_QLA82XX(ha)) {
@@ -39,9 +39,14 @@ qla2x00_sysfs_read_fw_dump(struct file *filp, struct kobject *kobj,
39 rval = memory_read_from_buffer(buf, count, 39 rval = memory_read_from_buffer(buf, count,
40 &off, ha->md_dump, ha->md_dump_size); 40 &off, ha->md_dump, ha->md_dump_size);
41 return rval; 41 return rval;
42 } else 42 } else if (ha->mctp_dumped && ha->mctp_dump_reading)
43 return memory_read_from_buffer(buf, count, &off, ha->mctp_dump,
44 MCTP_DUMP_SIZE);
45 else if (ha->fw_dump_reading)
43 return memory_read_from_buffer(buf, count, &off, ha->fw_dump, 46 return memory_read_from_buffer(buf, count, &off, ha->fw_dump,
44 ha->fw_dump_len); 47 ha->fw_dump_len);
48 else
49 return 0;
45} 50}
46 51
47static ssize_t 52static ssize_t
@@ -107,6 +112,22 @@ qla2x00_sysfs_write_fw_dump(struct file *filp, struct kobject *kobj,
107 if (IS_QLA82XX(ha)) 112 if (IS_QLA82XX(ha))
108 set_bit(ISP_ABORT_NEEDED, &vha->dpc_flags); 113 set_bit(ISP_ABORT_NEEDED, &vha->dpc_flags);
109 break; 114 break;
115 case 6:
116 if (!ha->mctp_dump_reading)
117 break;
118 ql_log(ql_log_info, vha, 0x70c1,
119 "MCTP dump cleared on (%ld).\n", vha->host_no);
120 ha->mctp_dump_reading = 0;
121 ha->mctp_dumped = 0;
122 break;
123 case 7:
124 if (ha->mctp_dumped && !ha->mctp_dump_reading) {
125 ha->mctp_dump_reading = 1;
126 ql_log(ql_log_info, vha, 0x70c2,
127 "Raw mctp dump ready for read on (%ld).\n",
128 vha->host_no);
129 }
130 break;
110 } 131 }
111 return count; 132 return count;
112} 133}
@@ -564,6 +585,7 @@ qla2x00_sysfs_write_reset(struct file *filp, struct kobject *kobj,
564 struct qla_hw_data *ha = vha->hw; 585 struct qla_hw_data *ha = vha->hw;
565 struct scsi_qla_host *base_vha = pci_get_drvdata(ha->pdev); 586 struct scsi_qla_host *base_vha = pci_get_drvdata(ha->pdev);
566 int type; 587 int type;
588 uint32_t idc_control;
567 589
568 if (off != 0) 590 if (off != 0)
569 return -EINVAL; 591 return -EINVAL;
@@ -587,22 +609,36 @@ qla2x00_sysfs_write_reset(struct file *filp, struct kobject *kobj,
587 scsi_unblock_requests(vha->host); 609 scsi_unblock_requests(vha->host);
588 break; 610 break;
589 case 0x2025d: 611 case 0x2025d:
590 if (!IS_QLA81XX(ha) || !IS_QLA8031(ha)) 612 if (!IS_QLA81XX(ha) && !IS_QLA83XX(ha))
591 return -EPERM; 613 return -EPERM;
592 614
593 ql_log(ql_log_info, vha, 0x706f, 615 ql_log(ql_log_info, vha, 0x706f,
594 "Issuing MPI reset.\n"); 616 "Issuing MPI reset.\n");
595 617
596 /* Make sure FC side is not in reset */ 618 if (IS_QLA83XX(ha)) {
597 qla2x00_wait_for_hba_online(vha); 619 uint32_t idc_control;
598 620
599 /* Issue MPI reset */ 621 qla83xx_idc_lock(vha, 0);
600 scsi_block_requests(vha->host); 622 __qla83xx_get_idc_control(vha, &idc_control);
601 if (qla81xx_restart_mpi_firmware(vha) != QLA_SUCCESS) 623 idc_control |= QLA83XX_IDC_GRACEFUL_RESET;
602 ql_log(ql_log_warn, vha, 0x7070, 624 __qla83xx_set_idc_control(vha, idc_control);
603 "MPI reset failed.\n"); 625 qla83xx_wr_reg(vha, QLA83XX_IDC_DEV_STATE,
604 scsi_unblock_requests(vha->host); 626 QLA8XXX_DEV_NEED_RESET);
605 break; 627 qla83xx_idc_audit(vha, IDC_AUDIT_TIMESTAMP);
628 qla83xx_idc_unlock(vha, 0);
629 break;
630 } else {
631 /* Make sure FC side is not in reset */
632 qla2x00_wait_for_hba_online(vha);
633
634 /* Issue MPI reset */
635 scsi_block_requests(vha->host);
636 if (qla81xx_restart_mpi_firmware(vha) != QLA_SUCCESS)
637 ql_log(ql_log_warn, vha, 0x7070,
638 "MPI reset failed.\n");
639 scsi_unblock_requests(vha->host);
640 break;
641 }
606 case 0x2025e: 642 case 0x2025e:
607 if (!IS_QLA82XX(ha) || vha != base_vha) { 643 if (!IS_QLA82XX(ha) || vha != base_vha) {
608 ql_log(ql_log_info, vha, 0x7071, 644 ql_log(ql_log_info, vha, 0x7071,
@@ -616,6 +652,29 @@ qla2x00_sysfs_write_reset(struct file *filp, struct kobject *kobj,
616 qla2xxx_wake_dpc(vha); 652 qla2xxx_wake_dpc(vha);
617 qla2x00_wait_for_fcoe_ctx_reset(vha); 653 qla2x00_wait_for_fcoe_ctx_reset(vha);
618 break; 654 break;
655 case 0x2025f:
656 if (!IS_QLA8031(ha))
657 return -EPERM;
658 ql_log(ql_log_info, vha, 0x70bc,
659 "Disabling Reset by IDC control\n");
660 qla83xx_idc_lock(vha, 0);
661 __qla83xx_get_idc_control(vha, &idc_control);
662 idc_control |= QLA83XX_IDC_RESET_DISABLED;
663 __qla83xx_set_idc_control(vha, idc_control);
664 qla83xx_idc_unlock(vha, 0);
665 break;
666 case 0x20260:
667 if (!IS_QLA8031(ha))
668 return -EPERM;
669 ql_log(ql_log_info, vha, 0x70bd,
670 "Enabling Reset by IDC control\n");
671 qla83xx_idc_lock(vha, 0);
672 __qla83xx_get_idc_control(vha, &idc_control);
673 idc_control &= ~QLA83XX_IDC_RESET_DISABLED;
674 __qla83xx_set_idc_control(vha, idc_control);
675 qla83xx_idc_unlock(vha, 0);
676 break;
677
619 } 678 }
620 return count; 679 return count;
621} 680}
@@ -1251,6 +1310,49 @@ qla2x00_fw_state_show(struct device *dev, struct device_attribute *attr,
1251 state[1], state[2], state[3], state[4]); 1310 state[1], state[2], state[3], state[4]);
1252} 1311}
1253 1312
1313static ssize_t
1314qla2x00_diag_requests_show(struct device *dev,
1315 struct device_attribute *attr, char *buf)
1316{
1317 scsi_qla_host_t *vha = shost_priv(class_to_shost(dev));
1318
1319 if (!IS_BIDI_CAPABLE(vha->hw))
1320 return snprintf(buf, PAGE_SIZE, "\n");
1321
1322 return snprintf(buf, PAGE_SIZE, "%llu\n", vha->bidi_stats.io_count);
1323}
1324
1325static ssize_t
1326qla2x00_diag_megabytes_show(struct device *dev,
1327 struct device_attribute *attr, char *buf)
1328{
1329 scsi_qla_host_t *vha = shost_priv(class_to_shost(dev));
1330
1331 if (!IS_BIDI_CAPABLE(vha->hw))
1332 return snprintf(buf, PAGE_SIZE, "\n");
1333
1334 return snprintf(buf, PAGE_SIZE, "%llu\n",
1335 vha->bidi_stats.transfer_bytes >> 20);
1336}
1337
1338static ssize_t
1339qla2x00_fw_dump_size_show(struct device *dev, struct device_attribute *attr,
1340 char *buf)
1341{
1342 scsi_qla_host_t *vha = shost_priv(class_to_shost(dev));
1343 struct qla_hw_data *ha = vha->hw;
1344 uint32_t size;
1345
1346 if (!ha->fw_dumped)
1347 size = 0;
1348 else if (IS_QLA82XX(ha))
1349 size = ha->md_template_size + ha->md_dump_size;
1350 else
1351 size = ha->fw_dump_len;
1352
1353 return snprintf(buf, PAGE_SIZE, "%d\n", size);
1354}
1355
1254static DEVICE_ATTR(driver_version, S_IRUGO, qla2x00_drvr_version_show, NULL); 1356static DEVICE_ATTR(driver_version, S_IRUGO, qla2x00_drvr_version_show, NULL);
1255static DEVICE_ATTR(fw_version, S_IRUGO, qla2x00_fw_version_show, NULL); 1357static DEVICE_ATTR(fw_version, S_IRUGO, qla2x00_fw_version_show, NULL);
1256static DEVICE_ATTR(serial_num, S_IRUGO, qla2x00_serial_num_show, NULL); 1358static DEVICE_ATTR(serial_num, S_IRUGO, qla2x00_serial_num_show, NULL);
@@ -1289,6 +1391,9 @@ static DEVICE_ATTR(vn_port_mac_address, S_IRUGO,
1289static DEVICE_ATTR(fabric_param, S_IRUGO, qla2x00_fabric_param_show, NULL); 1391static DEVICE_ATTR(fabric_param, S_IRUGO, qla2x00_fabric_param_show, NULL);
1290static DEVICE_ATTR(fw_state, S_IRUGO, qla2x00_fw_state_show, NULL); 1392static DEVICE_ATTR(fw_state, S_IRUGO, qla2x00_fw_state_show, NULL);
1291static DEVICE_ATTR(thermal_temp, S_IRUGO, qla2x00_thermal_temp_show, NULL); 1393static DEVICE_ATTR(thermal_temp, S_IRUGO, qla2x00_thermal_temp_show, NULL);
1394static DEVICE_ATTR(diag_requests, S_IRUGO, qla2x00_diag_requests_show, NULL);
1395static DEVICE_ATTR(diag_megabytes, S_IRUGO, qla2x00_diag_megabytes_show, NULL);
1396static DEVICE_ATTR(fw_dump_size, S_IRUGO, qla2x00_fw_dump_size_show, NULL);
1292 1397
1293struct device_attribute *qla2x00_host_attrs[] = { 1398struct device_attribute *qla2x00_host_attrs[] = {
1294 &dev_attr_driver_version, 1399 &dev_attr_driver_version,
@@ -1318,6 +1423,9 @@ struct device_attribute *qla2x00_host_attrs[] = {
1318 &dev_attr_fw_state, 1423 &dev_attr_fw_state,
1319 &dev_attr_optrom_gold_fw_version, 1424 &dev_attr_optrom_gold_fw_version,
1320 &dev_attr_thermal_temp, 1425 &dev_attr_thermal_temp,
1426 &dev_attr_diag_requests,
1427 &dev_attr_diag_megabytes,
1428 &dev_attr_fw_dump_size,
1321 NULL, 1429 NULL,
1322}; 1430};
1323 1431
@@ -1704,7 +1812,7 @@ qla24xx_vport_create(struct fc_vport *fc_vport, bool disable)
1704 1812
1705 if (IS_T10_PI_CAPABLE(ha) && ql2xenabledif) { 1813 if (IS_T10_PI_CAPABLE(ha) && ql2xenabledif) {
1706 if (ha->fw_attributes & BIT_4) { 1814 if (ha->fw_attributes & BIT_4) {
1707 int prot = 0; 1815 int prot = 0, guard;
1708 vha->flags.difdix_supported = 1; 1816 vha->flags.difdix_supported = 1;
1709 ql_dbg(ql_dbg_user, vha, 0x7082, 1817 ql_dbg(ql_dbg_user, vha, 0x7082,
1710 "Registered for DIF/DIX type 1 and 3 protection.\n"); 1818 "Registered for DIF/DIX type 1 and 3 protection.\n");
@@ -1717,7 +1825,14 @@ qla24xx_vport_create(struct fc_vport *fc_vport, bool disable)
1717 | SHOST_DIX_TYPE1_PROTECTION 1825 | SHOST_DIX_TYPE1_PROTECTION
1718 | SHOST_DIX_TYPE2_PROTECTION 1826 | SHOST_DIX_TYPE2_PROTECTION
1719 | SHOST_DIX_TYPE3_PROTECTION); 1827 | SHOST_DIX_TYPE3_PROTECTION);
1720 scsi_host_set_guard(vha->host, SHOST_DIX_GUARD_CRC); 1828
1829 guard = SHOST_DIX_GUARD_CRC;
1830
1831 if (IS_PI_IPGUARD_CAPABLE(ha) &&
1832 (ql2xenabledif > 1 || IS_PI_DIFB_DIX0_CAPABLE(ha)))
1833 guard |= SHOST_DIX_GUARD_IP;
1834
1835 scsi_host_set_guard(vha->host, guard);
1721 } else 1836 } else
1722 vha->flags.difdix_supported = 0; 1837 vha->flags.difdix_supported = 0;
1723 } 1838 }