aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorArun Easi <arun.easi@qlogic.com>2012-08-22 14:21:31 -0400
committerJames Bottomley <JBottomley@Parallels.com>2012-09-24 04:10:54 -0400
commit9e522cd8f3dd7d19b644fc9cfc372bebde9f0053 (patch)
treecf4b8e44ce34c2f206bb3d07b3c75f8959f2f471
parentcb860bbd6b4b12cb56640fefceeaffb526eb7ac5 (diff)
[SCSI] qla2xxx: T10 DIF - ISP83xx changes.
Signed-off-by: Arun Easi <arun.easi@qlogic.com> Signed-off-by: Chad Dupuis <chad.dupuis@qlogic.com> Signed-off-by: James Bottomley <JBottomley@Parallels.com>
-rw-r--r--drivers/scsi/qla2xxx/qla_attr.c11
-rw-r--r--drivers/scsi/qla2xxx/qla_dbg.c3
-rw-r--r--drivers/scsi/qla2xxx/qla_def.h13
-rw-r--r--drivers/scsi/qla2xxx/qla_init.c3
-rw-r--r--drivers/scsi/qla2xxx/qla_iocb.c59
-rw-r--r--drivers/scsi/qla2xxx/qla_isr.c13
-rw-r--r--drivers/scsi/qla2xxx/qla_os.c19
7 files changed, 67 insertions, 54 deletions
diff --git a/drivers/scsi/qla2xxx/qla_attr.c b/drivers/scsi/qla2xxx/qla_attr.c
index e2ca6be86244..1c28215f8bed 100644
--- a/drivers/scsi/qla2xxx/qla_attr.c
+++ b/drivers/scsi/qla2xxx/qla_attr.c
@@ -1812,7 +1812,7 @@ qla24xx_vport_create(struct fc_vport *fc_vport, bool disable)
1812 1812
1813 if (IS_T10_PI_CAPABLE(ha) && ql2xenabledif) { 1813 if (IS_T10_PI_CAPABLE(ha) && ql2xenabledif) {
1814 if (ha->fw_attributes & BIT_4) { 1814 if (ha->fw_attributes & BIT_4) {
1815 int prot = 0; 1815 int prot = 0, guard;
1816 vha->flags.difdix_supported = 1; 1816 vha->flags.difdix_supported = 1;
1817 ql_dbg(ql_dbg_user, vha, 0x7082, 1817 ql_dbg(ql_dbg_user, vha, 0x7082,
1818 "Registered for DIF/DIX type 1 and 3 protection.\n"); 1818 "Registered for DIF/DIX type 1 and 3 protection.\n");
@@ -1825,7 +1825,14 @@ qla24xx_vport_create(struct fc_vport *fc_vport, bool disable)
1825 | SHOST_DIX_TYPE1_PROTECTION 1825 | SHOST_DIX_TYPE1_PROTECTION
1826 | SHOST_DIX_TYPE2_PROTECTION 1826 | SHOST_DIX_TYPE2_PROTECTION
1827 | SHOST_DIX_TYPE3_PROTECTION); 1827 | SHOST_DIX_TYPE3_PROTECTION);
1828 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);
1829 } else 1836 } else
1830 vha->flags.difdix_supported = 0; 1837 vha->flags.difdix_supported = 0;
1831 } 1838 }
diff --git a/drivers/scsi/qla2xxx/qla_dbg.c b/drivers/scsi/qla2xxx/qla_dbg.c
index 3e081bd8d34e..44efe3cc79e6 100644
--- a/drivers/scsi/qla2xxx/qla_dbg.c
+++ b/drivers/scsi/qla2xxx/qla_dbg.c
@@ -17,7 +17,8 @@
17 * | | | 0x113a | 17 * | | | 0x113a |
18 * | Device Discovery | 0x2087 | 0x2020-0x2022, | 18 * | Device Discovery | 0x2087 | 0x2020-0x2022, |
19 * | | | 0x2016 | 19 * | | | 0x2016 |
20 * | Queue Command and IO tracing | 0x3030 | 0x3006,0x3008 | 20 * | Queue Command and IO tracing | 0x3030 | 0x3006-0x300b |
21 * | | | 0x3027-0x3028 |
21 * | | | 0x302d-0x302e | 22 * | | | 0x302d-0x302e |
22 * | DPC Thread | 0x401d | 0x4002,0x4013 | 23 * | DPC Thread | 0x401d | 0x4002,0x4013 |
23 * | Async Events | 0x5071 | 0x502b-0x502f | 24 * | Async Events | 0x5071 | 0x502b-0x502f |
diff --git a/drivers/scsi/qla2xxx/qla_def.h b/drivers/scsi/qla2xxx/qla_def.h
index b214fd816135..a9725bf5527b 100644
--- a/drivers/scsi/qla2xxx/qla_def.h
+++ b/drivers/scsi/qla2xxx/qla_def.h
@@ -1468,9 +1468,10 @@ typedef struct {
1468} cont_a64_entry_t; 1468} cont_a64_entry_t;
1469 1469
1470#define PO_MODE_DIF_INSERT 0 1470#define PO_MODE_DIF_INSERT 0
1471#define PO_MODE_DIF_REMOVE BIT_0 1471#define PO_MODE_DIF_REMOVE 1
1472#define PO_MODE_DIF_PASS BIT_1 1472#define PO_MODE_DIF_PASS 2
1473#define PO_MODE_DIF_REPLACE (BIT_0 + BIT_1) 1473#define PO_MODE_DIF_REPLACE 3
1474#define PO_MODE_DIF_TCP_CKSUM 6
1474#define PO_ENABLE_DIF_BUNDLING BIT_8 1475#define PO_ENABLE_DIF_BUNDLING BIT_8
1475#define PO_ENABLE_INCR_GUARD_SEED BIT_3 1476#define PO_ENABLE_INCR_GUARD_SEED BIT_3
1476#define PO_DISABLE_INCR_REF_TAG BIT_5 1477#define PO_DISABLE_INCR_REF_TAG BIT_5
@@ -2781,6 +2782,12 @@ struct qla_hw_data {
2781/* Bit 21 of fw_attributes decides the MCTP capabilities */ 2782/* Bit 21 of fw_attributes decides the MCTP capabilities */
2782#define IS_MCTP_CAPABLE(ha) (IS_QLA2031(ha) && \ 2783#define IS_MCTP_CAPABLE(ha) (IS_QLA2031(ha) && \
2783 ((ha)->fw_attributes_ext[0] & BIT_0)) 2784 ((ha)->fw_attributes_ext[0] & BIT_0))
2785#define IS_PI_UNINIT_CAPABLE(ha) (IS_QLA83XX(ha))
2786#define IS_PI_IPGUARD_CAPABLE(ha) (IS_QLA83XX(ha))
2787#define IS_PI_DIFB_DIX0_CAPABLE(ha) (0)
2788#define IS_PI_SPLIT_DET_CAPABLE_HBA(ha) (IS_QLA83XX(ha))
2789#define IS_PI_SPLIT_DET_CAPABLE(ha) (IS_PI_SPLIT_DET_CAPABLE_HBA(ha) && \
2790 (((ha)->fw_attributes_h << 16 | (ha)->fw_attributes) & BIT_22))
2784 2791
2785 /* HBA serial number */ 2792 /* HBA serial number */
2786 uint8_t serial0; 2793 uint8_t serial0;
diff --git a/drivers/scsi/qla2xxx/qla_init.c b/drivers/scsi/qla2xxx/qla_init.c
index 62081cf4d824..799a58bb9859 100644
--- a/drivers/scsi/qla2xxx/qla_init.c
+++ b/drivers/scsi/qla2xxx/qla_init.c
@@ -5498,6 +5498,9 @@ qla81xx_nvram_config(scsi_qla_host_t *vha)
5498 rval = 1; 5498 rval = 1;
5499 } 5499 }
5500 5500
5501 if (IS_T10_PI_CAPABLE(ha))
5502 nv->frame_payload_size &= ~7;
5503
5501 /* Reset Initialization control block */ 5504 /* Reset Initialization control block */
5502 memset(icb, 0, ha->init_cb_size); 5505 memset(icb, 0, ha->init_cb_size);
5503 5506
diff --git a/drivers/scsi/qla2xxx/qla_iocb.c b/drivers/scsi/qla2xxx/qla_iocb.c
index f58b2b23fb89..03b752632839 100644
--- a/drivers/scsi/qla2xxx/qla_iocb.c
+++ b/drivers/scsi/qla2xxx/qla_iocb.c
@@ -147,13 +147,6 @@ qla24xx_configure_prot_mode(srb_t *sp, uint16_t *fw_prot_opts)
147 struct scsi_cmnd *cmd = GET_CMD_SP(sp); 147 struct scsi_cmnd *cmd = GET_CMD_SP(sp);
148 uint8_t guard = scsi_host_get_guard(cmd->device->host); 148 uint8_t guard = scsi_host_get_guard(cmd->device->host);
149 149
150 /* We only support T10 DIF right now */
151 if (guard != SHOST_DIX_GUARD_CRC) {
152 ql_dbg(ql_dbg_io, sp->fcport->vha, 0x3007,
153 "Unsupported guard: %d for cmd=%p.\n", guard, cmd);
154 return 0;
155 }
156
157 /* We always use DIFF Bundling for best performance */ 150 /* We always use DIFF Bundling for best performance */
158 *fw_prot_opts = 0; 151 *fw_prot_opts = 0;
159 152
@@ -172,10 +165,11 @@ qla24xx_configure_prot_mode(srb_t *sp, uint16_t *fw_prot_opts)
172 *fw_prot_opts |= PO_MODE_DIF_REMOVE; 165 *fw_prot_opts |= PO_MODE_DIF_REMOVE;
173 break; 166 break;
174 case SCSI_PROT_READ_PASS: 167 case SCSI_PROT_READ_PASS:
175 *fw_prot_opts |= PO_MODE_DIF_PASS;
176 break;
177 case SCSI_PROT_WRITE_PASS: 168 case SCSI_PROT_WRITE_PASS:
178 *fw_prot_opts |= PO_MODE_DIF_PASS; 169 if (guard & SHOST_DIX_GUARD_IP)
170 *fw_prot_opts |= PO_MODE_DIF_TCP_CKSUM;
171 else
172 *fw_prot_opts |= PO_MODE_DIF_PASS;
179 break; 173 break;
180 default: /* Normal Request */ 174 default: /* Normal Request */
181 *fw_prot_opts |= PO_MODE_DIF_PASS; 175 *fw_prot_opts |= PO_MODE_DIF_PASS;
@@ -821,7 +815,6 @@ qla24xx_set_t10dif_tags(srb_t *sp, struct fw_dif_context *pkt,
821 unsigned int protcnt) 815 unsigned int protcnt)
822{ 816{
823 struct scsi_cmnd *cmd = GET_CMD_SP(sp); 817 struct scsi_cmnd *cmd = GET_CMD_SP(sp);
824 scsi_qla_host_t *vha = shost_priv(cmd->device->host);
825 818
826 switch (scsi_get_prot_type(cmd)) { 819 switch (scsi_get_prot_type(cmd)) {
827 case SCSI_PROT_DIF_TYPE0: 820 case SCSI_PROT_DIF_TYPE0:
@@ -891,12 +884,6 @@ qla24xx_set_t10dif_tags(srb_t *sp, struct fw_dif_context *pkt,
891 pkt->ref_tag_mask[3] = 0xff; 884 pkt->ref_tag_mask[3] = 0xff;
892 break; 885 break;
893 } 886 }
894
895 ql_dbg(ql_dbg_io, vha, 0x3009,
896 "Setting protection Tags: (BIG) ref tag = 0x%x, app tag = 0x%x, "
897 "prot SG count %d, cmd lba 0x%x, prot_type=%u cmd=%p.\n",
898 pkt->ref_tag, pkt->app_tag, protcnt, (int)scsi_get_lba(cmd),
899 scsi_get_prot_type(cmd), cmd);
900} 887}
901 888
902struct qla2_sgx { 889struct qla2_sgx {
@@ -1068,9 +1055,6 @@ qla24xx_walk_and_build_sglist(struct qla_hw_data *ha, srb_t *sp, uint32_t *dsd,
1068 int i; 1055 int i;
1069 uint16_t used_dsds = tot_dsds; 1056 uint16_t used_dsds = tot_dsds;
1070 struct scsi_cmnd *cmd = GET_CMD_SP(sp); 1057 struct scsi_cmnd *cmd = GET_CMD_SP(sp);
1071 scsi_qla_host_t *vha = shost_priv(cmd->device->host);
1072
1073 uint8_t *cp;
1074 1058
1075 scsi_for_each_sg(cmd, sg, tot_dsds, i) { 1059 scsi_for_each_sg(cmd, sg, tot_dsds, i) {
1076 dma_addr_t sle_dma; 1060 dma_addr_t sle_dma;
@@ -1113,19 +1097,12 @@ qla24xx_walk_and_build_sglist(struct qla_hw_data *ha, srb_t *sp, uint32_t *dsd,
1113 cur_dsd = (uint32_t *)next_dsd; 1097 cur_dsd = (uint32_t *)next_dsd;
1114 } 1098 }
1115 sle_dma = sg_dma_address(sg); 1099 sle_dma = sg_dma_address(sg);
1116 ql_dbg(ql_dbg_io, vha, 0x300a, 1100
1117 "sg entry %d - addr=0x%x 0x%x, " "len=%d for cmd=%p.\n",
1118 i, LSD(sle_dma), MSD(sle_dma), sg_dma_len(sg), cmd);
1119 *cur_dsd++ = cpu_to_le32(LSD(sle_dma)); 1101 *cur_dsd++ = cpu_to_le32(LSD(sle_dma));
1120 *cur_dsd++ = cpu_to_le32(MSD(sle_dma)); 1102 *cur_dsd++ = cpu_to_le32(MSD(sle_dma));
1121 *cur_dsd++ = cpu_to_le32(sg_dma_len(sg)); 1103 *cur_dsd++ = cpu_to_le32(sg_dma_len(sg));
1122 avail_dsds--; 1104 avail_dsds--;
1123 1105
1124 if (scsi_get_prot_op(cmd) == SCSI_PROT_WRITE_PASS) {
1125 cp = page_address(sg_page(sg)) + sg->offset;
1126 ql_dbg(ql_dbg_io, vha, 0x300b,
1127 "User data buffer=%p for cmd=%p.\n", cp, cmd);
1128 }
1129 } 1106 }
1130 /* Null termination */ 1107 /* Null termination */
1131 *cur_dsd++ = 0; 1108 *cur_dsd++ = 0;
@@ -1148,8 +1125,6 @@ qla24xx_walk_and_build_prot_sglist(struct qla_hw_data *ha, srb_t *sp,
1148 struct scsi_cmnd *cmd; 1125 struct scsi_cmnd *cmd;
1149 uint32_t *cur_dsd = dsd; 1126 uint32_t *cur_dsd = dsd;
1150 uint16_t used_dsds = tot_dsds; 1127 uint16_t used_dsds = tot_dsds;
1151 scsi_qla_host_t *vha = pci_get_drvdata(ha->pdev);
1152 uint8_t *cp;
1153 1128
1154 cmd = GET_CMD_SP(sp); 1129 cmd = GET_CMD_SP(sp);
1155 scsi_for_each_prot_sg(cmd, sg, tot_dsds, i) { 1130 scsi_for_each_prot_sg(cmd, sg, tot_dsds, i) {
@@ -1193,23 +1168,11 @@ qla24xx_walk_and_build_prot_sglist(struct qla_hw_data *ha, srb_t *sp,
1193 cur_dsd = (uint32_t *)next_dsd; 1168 cur_dsd = (uint32_t *)next_dsd;
1194 } 1169 }
1195 sle_dma = sg_dma_address(sg); 1170 sle_dma = sg_dma_address(sg);
1196 if (scsi_get_prot_op(cmd) == SCSI_PROT_WRITE_PASS) { 1171
1197 ql_dbg(ql_dbg_io, vha, 0x3027,
1198 "%s(): %p, sg_entry %d - "
1199 "addr=0x%x0x%x, len=%d.\n",
1200 __func__, cur_dsd, i,
1201 LSD(sle_dma), MSD(sle_dma), sg_dma_len(sg));
1202 }
1203 *cur_dsd++ = cpu_to_le32(LSD(sle_dma)); 1172 *cur_dsd++ = cpu_to_le32(LSD(sle_dma));
1204 *cur_dsd++ = cpu_to_le32(MSD(sle_dma)); 1173 *cur_dsd++ = cpu_to_le32(MSD(sle_dma));
1205 *cur_dsd++ = cpu_to_le32(sg_dma_len(sg)); 1174 *cur_dsd++ = cpu_to_le32(sg_dma_len(sg));
1206 1175
1207 if (scsi_get_prot_op(cmd) == SCSI_PROT_WRITE_PASS) {
1208 cp = page_address(sg_page(sg)) + sg->offset;
1209 ql_dbg(ql_dbg_io, vha, 0x3028,
1210 "%s(): Protection Data buffer = %p.\n", __func__,
1211 cp);
1212 }
1213 avail_dsds--; 1176 avail_dsds--;
1214 } 1177 }
1215 /* Null termination */ 1178 /* Null termination */
@@ -1386,6 +1349,16 @@ qla24xx_build_scsi_crc_2_iocbs(srb_t *sp, struct cmd_type_crc_2 *cmd_pkt,
1386 1349
1387 if (!qla2x00_hba_err_chk_enabled(sp)) 1350 if (!qla2x00_hba_err_chk_enabled(sp))
1388 fw_prot_opts |= 0x10; /* Disable Guard tag checking */ 1351 fw_prot_opts |= 0x10; /* Disable Guard tag checking */
1352 /* HBA error checking enabled */
1353 else if (IS_PI_UNINIT_CAPABLE(ha)) {
1354 if ((scsi_get_prot_type(GET_CMD_SP(sp)) == SCSI_PROT_DIF_TYPE1)
1355 || (scsi_get_prot_type(GET_CMD_SP(sp)) ==
1356 SCSI_PROT_DIF_TYPE2))
1357 fw_prot_opts |= BIT_10;
1358 else if (scsi_get_prot_type(GET_CMD_SP(sp)) ==
1359 SCSI_PROT_DIF_TYPE3)
1360 fw_prot_opts |= BIT_11;
1361 }
1389 1362
1390 if (!bundling) { 1363 if (!bundling) {
1391 cur_dsd = (uint32_t *) &crc_ctx_pkt->u.nobundling.data_address; 1364 cur_dsd = (uint32_t *) &crc_ctx_pkt->u.nobundling.data_address;
diff --git a/drivers/scsi/qla2xxx/qla_isr.c b/drivers/scsi/qla2xxx/qla_isr.c
index f01be76ebecf..7614e14def92 100644
--- a/drivers/scsi/qla2xxx/qla_isr.c
+++ b/drivers/scsi/qla2xxx/qla_isr.c
@@ -2163,6 +2163,19 @@ check_scsi_status:
2163 case CS_DIF_ERROR: 2163 case CS_DIF_ERROR:
2164 logit = qla2x00_handle_dif_error(sp, sts24); 2164 logit = qla2x00_handle_dif_error(sp, sts24);
2165 break; 2165 break;
2166
2167 case CS_TRANSPORT:
2168 res = DID_ERROR << 16;
2169
2170 if (!IS_PI_SPLIT_DET_CAPABLE(ha))
2171 break;
2172
2173 if (state_flags & BIT_4)
2174 scmd_printk(KERN_WARNING, cp,
2175 "Unsupported device '%s' found.\n",
2176 cp->device->vendor);
2177 break;
2178
2166 default: 2179 default:
2167 res = DID_ERROR << 16; 2180 res = DID_ERROR << 16;
2168 break; 2181 break;
diff --git a/drivers/scsi/qla2xxx/qla_os.c b/drivers/scsi/qla2xxx/qla_os.c
index 1020db5c33f9..ec7cefcb6722 100644
--- a/drivers/scsi/qla2xxx/qla_os.c
+++ b/drivers/scsi/qla2xxx/qla_os.c
@@ -116,9 +116,8 @@ MODULE_PARM_DESC(ql2xmaxqdepth,
116 "Maximum queue depth to set for each LUN. " 116 "Maximum queue depth to set for each LUN. "
117 "Default is 32."); 117 "Default is 32.");
118 118
119/* Do not change the value of this after module load */ 119int ql2xenabledif = 2;
120int ql2xenabledif = 0; 120module_param(ql2xenabledif, int, S_IRUGO);
121module_param(ql2xenabledif, int, S_IRUGO|S_IWUSR);
122MODULE_PARM_DESC(ql2xenabledif, 121MODULE_PARM_DESC(ql2xenabledif,
123 " Enable T10-CRC-DIF " 122 " Enable T10-CRC-DIF "
124 " Default is 0 - No DIF Support. 1 - Enable it" 123 " Default is 0 - No DIF Support. 1 - Enable it"
@@ -1358,6 +1357,9 @@ qla2xxx_slave_configure(struct scsi_device *sdev)
1358 scsi_qla_host_t *vha = shost_priv(sdev->host); 1357 scsi_qla_host_t *vha = shost_priv(sdev->host);
1359 struct req_que *req = vha->req; 1358 struct req_que *req = vha->req;
1360 1359
1360 if (IS_T10_PI_CAPABLE(vha->hw))
1361 blk_queue_update_dma_alignment(sdev->request_queue, 0x7);
1362
1361 if (sdev->tagged_supported) 1363 if (sdev->tagged_supported)
1362 scsi_activate_tcq(sdev, req->max_q_depth); 1364 scsi_activate_tcq(sdev, req->max_q_depth);
1363 else 1365 else
@@ -2574,7 +2576,7 @@ skip_dpc:
2574 2576
2575 if (IS_T10_PI_CAPABLE(ha) && ql2xenabledif) { 2577 if (IS_T10_PI_CAPABLE(ha) && ql2xenabledif) {
2576 if (ha->fw_attributes & BIT_4) { 2578 if (ha->fw_attributes & BIT_4) {
2577 int prot = 0; 2579 int prot = 0, guard;
2578 base_vha->flags.difdix_supported = 1; 2580 base_vha->flags.difdix_supported = 1;
2579 ql_dbg(ql_dbg_init, base_vha, 0x00f1, 2581 ql_dbg(ql_dbg_init, base_vha, 0x00f1,
2580 "Registering for DIF/DIX type 1 and 3 protection.\n"); 2582 "Registering for DIF/DIX type 1 and 3 protection.\n");
@@ -2587,7 +2589,14 @@ skip_dpc:
2587 | SHOST_DIX_TYPE1_PROTECTION 2589 | SHOST_DIX_TYPE1_PROTECTION
2588 | SHOST_DIX_TYPE2_PROTECTION 2590 | SHOST_DIX_TYPE2_PROTECTION
2589 | SHOST_DIX_TYPE3_PROTECTION); 2591 | SHOST_DIX_TYPE3_PROTECTION);
2590 scsi_host_set_guard(host, SHOST_DIX_GUARD_CRC); 2592
2593 guard = SHOST_DIX_GUARD_CRC;
2594
2595 if (IS_PI_IPGUARD_CAPABLE(ha) &&
2596 (ql2xenabledif > 1 || IS_PI_DIFB_DIX0_CAPABLE(ha)))
2597 guard |= SHOST_DIX_GUARD_IP;
2598
2599 scsi_host_set_guard(host, guard);
2591 } else 2600 } else
2592 base_vha->flags.difdix_supported = 0; 2601 base_vha->flags.difdix_supported = 0;
2593 } 2602 }