Commit 03aaa89f authored by Darren Trapp's avatar Darren Trapp Committed by Martin K. Petersen

scsi: qla2xxx: Add First Burst support for FC-NVMe devices

Add Support for First Burst for FC-NVMe protocol. This feature requires
First Burst support in the firmware.
Signed-off-by: default avatarDarren Trapp <darren.trapp@cavium.com>
Signed-off-by: default avatarHimanshu Madhani <hmadhani@marvell.com>
Signed-off-by: default avatarMartin K. Petersen <martin.petersen@oracle.com>
parent ec322937
...@@ -2367,7 +2367,9 @@ typedef struct fc_port { ...@@ -2367,7 +2367,9 @@ typedef struct fc_port {
#define NVME_PRLI_SP_INITIATOR BIT_5 #define NVME_PRLI_SP_INITIATOR BIT_5
#define NVME_PRLI_SP_TARGET BIT_4 #define NVME_PRLI_SP_TARGET BIT_4
#define NVME_PRLI_SP_DISCOVERY BIT_3 #define NVME_PRLI_SP_DISCOVERY BIT_3
#define NVME_PRLI_SP_FIRST_BURST BIT_0
uint8_t nvme_flag; uint8_t nvme_flag;
uint32_t nvme_first_burst_size;
#define NVME_FLAG_REGISTERED 4 #define NVME_FLAG_REGISTERED 4
#define NVME_FLAG_DELETING 2 #define NVME_FLAG_DELETING 2
#define NVME_FLAG_RESETTING 1 #define NVME_FLAG_RESETTING 1
...@@ -3966,6 +3968,7 @@ struct qla_hw_data { ...@@ -3966,6 +3968,7 @@ struct qla_hw_data {
uint16_t fw_subminor_version; uint16_t fw_subminor_version;
uint16_t fw_attributes; uint16_t fw_attributes;
uint16_t fw_attributes_h; uint16_t fw_attributes_h;
#define FW_ATTR_H_NVME_FBURST BIT_1
#define FW_ATTR_H_NVME BIT_10 #define FW_ATTR_H_NVME BIT_10
#define FW_ATTR_H_NVME_UPDATED BIT_14 #define FW_ATTR_H_NVME_UPDATED BIT_14
...@@ -4260,6 +4263,7 @@ typedef struct scsi_qla_host { ...@@ -4260,6 +4263,7 @@ typedef struct scsi_qla_host {
uint32_t qpairs_req_created:1; uint32_t qpairs_req_created:1;
uint32_t qpairs_rsp_created:1; uint32_t qpairs_rsp_created:1;
uint32_t nvme_enabled:1; uint32_t nvme_enabled:1;
uint32_t nvme_first_burst:1;
} flags; } flags;
atomic_t loop_state; atomic_t loop_state;
......
...@@ -1831,6 +1831,12 @@ qla24xx_handle_prli_done_event(struct scsi_qla_host *vha, struct event_arg *ea) ...@@ -1831,6 +1831,12 @@ qla24xx_handle_prli_done_event(struct scsi_qla_host *vha, struct event_arg *ea)
ea->fcport->chip_reset = vha->hw->base_qpair->chip_reset; ea->fcport->chip_reset = vha->hw->base_qpair->chip_reset;
ea->fcport->logout_on_delete = 1; ea->fcport->logout_on_delete = 1;
ea->fcport->nvme_prli_service_param = ea->iop[0];
if (ea->iop[0] & NVME_PRLI_SP_FIRST_BURST)
ea->fcport->nvme_first_burst_size =
(ea->iop[1] & 0xffff) * 512;
else
ea->fcport->nvme_first_burst_size = 0;
qla24xx_post_gpdb_work(vha, ea->fcport, 0); qla24xx_post_gpdb_work(vha, ea->fcport, 0);
break; break;
default: default:
......
...@@ -2419,8 +2419,11 @@ qla24xx_prli_iocb(srb_t *sp, struct logio_entry_24xx *logio) ...@@ -2419,8 +2419,11 @@ qla24xx_prli_iocb(srb_t *sp, struct logio_entry_24xx *logio)
logio->entry_type = LOGINOUT_PORT_IOCB_TYPE; logio->entry_type = LOGINOUT_PORT_IOCB_TYPE;
logio->control_flags = cpu_to_le16(LCF_COMMAND_PRLI); logio->control_flags = cpu_to_le16(LCF_COMMAND_PRLI);
if (lio->u.logio.flags & SRB_LOGIN_NVME_PRLI) if (lio->u.logio.flags & SRB_LOGIN_NVME_PRLI) {
logio->control_flags |= LCF_NVME_PRLI; logio->control_flags |= LCF_NVME_PRLI;
if (sp->vha->flags.nvme_first_burst)
logio->io_parameter[0] = NVME_PRLI_SP_FIRST_BURST;
}
logio->nport_handle = cpu_to_le16(sp->fcport->loop_id); logio->nport_handle = cpu_to_le16(sp->fcport->loop_id);
logio->port_id[0] = sp->fcport->d_id.b.al_pa; logio->port_id[0] = sp->fcport->d_id.b.al_pa;
......
...@@ -1715,6 +1715,15 @@ qla24xx_logio_entry(scsi_qla_host_t *vha, struct req_que *req, ...@@ -1715,6 +1715,15 @@ qla24xx_logio_entry(scsi_qla_host_t *vha, struct req_que *req,
vha->hw->exch_starvation = 0; vha->hw->exch_starvation = 0;
data[0] = MBS_COMMAND_COMPLETE; data[0] = MBS_COMMAND_COMPLETE;
if (sp->type == SRB_PRLI_CMD) {
lio->u.logio.iop[0] =
le32_to_cpu(logio->io_parameter[0]);
lio->u.logio.iop[1] =
le32_to_cpu(logio->io_parameter[1]);
goto logio_done;
}
if (sp->type != SRB_LOGIN_CMD) if (sp->type != SRB_LOGIN_CMD)
goto logio_done; goto logio_done;
......
...@@ -1112,6 +1112,9 @@ qla2x00_get_fw_version(scsi_qla_host_t *vha) ...@@ -1112,6 +1112,9 @@ qla2x00_get_fw_version(scsi_qla_host_t *vha)
if ((ha->fw_attributes_h & if ((ha->fw_attributes_h &
(FW_ATTR_H_NVME | FW_ATTR_H_NVME_UPDATED)) && (FW_ATTR_H_NVME | FW_ATTR_H_NVME_UPDATED)) &&
ql2xnvmeenable) { ql2xnvmeenable) {
if (ha->fw_attributes_h & FW_ATTR_H_NVME_FBURST)
vha->flags.nvme_first_burst = 1;
vha->flags.nvme_enabled = 1; vha->flags.nvme_enabled = 1;
ql_log(ql_log_info, vha, 0xd302, ql_log(ql_log_info, vha, 0xd302,
"%s: FC-NVMe is Enabled (0x%x)\n", "%s: FC-NVMe is Enabled (0x%x)\n",
...@@ -6267,8 +6270,6 @@ int __qla24xx_parse_gpdb(struct scsi_qla_host *vha, fc_port_t *fcport, ...@@ -6267,8 +6270,6 @@ int __qla24xx_parse_gpdb(struct scsi_qla_host *vha, fc_port_t *fcport,
fcport->d_id.b.rsvd_1 = 0; fcport->d_id.b.rsvd_1 = 0;
if (fcport->fc4f_nvme) { if (fcport->fc4f_nvme) {
fcport->nvme_prli_service_param =
pd->prli_nvme_svc_param_word_3;
fcport->port_type = FCT_NVME; fcport->port_type = FCT_NVME;
} else { } else {
/* If not target must be initiator or unknown type. */ /* If not target must be initiator or unknown type. */
......
...@@ -358,17 +358,24 @@ static inline int qla2x00_start_nvme_mq(srb_t *sp) ...@@ -358,17 +358,24 @@ static inline int qla2x00_start_nvme_mq(srb_t *sp)
/* No data transfer how do we check buffer len == 0?? */ /* No data transfer how do we check buffer len == 0?? */
if (fd->io_dir == NVMEFC_FCP_READ) { if (fd->io_dir == NVMEFC_FCP_READ) {
cmd_pkt->control_flags = cmd_pkt->control_flags = CF_READ_DATA;
cpu_to_le16(CF_READ_DATA | CF_NVME_ENABLE);
vha->qla_stats.input_bytes += fd->payload_length; vha->qla_stats.input_bytes += fd->payload_length;
vha->qla_stats.input_requests++; vha->qla_stats.input_requests++;
} else if (fd->io_dir == NVMEFC_FCP_WRITE) { } else if (fd->io_dir == NVMEFC_FCP_WRITE) {
cmd_pkt->control_flags = cmd_pkt->control_flags = CF_WRITE_DATA;
cpu_to_le16(CF_WRITE_DATA | CF_NVME_ENABLE); if ((vha->flags.nvme_first_burst) &&
(sp->fcport->nvme_prli_service_param &
NVME_PRLI_SP_FIRST_BURST)) {
if ((fd->payload_length <=
sp->fcport->nvme_first_burst_size) ||
(sp->fcport->nvme_first_burst_size == 0))
cmd_pkt->control_flags |=
CF_NVME_FIRST_BURST_ENABLE;
}
vha->qla_stats.output_bytes += fd->payload_length; vha->qla_stats.output_bytes += fd->payload_length;
vha->qla_stats.output_requests++; vha->qla_stats.output_requests++;
} else if (fd->io_dir == 0) { } else if (fd->io_dir == 0) {
cmd_pkt->control_flags = cpu_to_le16(CF_NVME_ENABLE); cmd_pkt->control_flags = 0;
} }
/* Set NPORT-ID */ /* Set NPORT-ID */
......
...@@ -57,7 +57,7 @@ struct cmd_nvme { ...@@ -57,7 +57,7 @@ struct cmd_nvme {
uint64_t rsvd; uint64_t rsvd;
uint16_t control_flags; /* Control Flags */ uint16_t control_flags; /* Control Flags */
#define CF_NVME_ENABLE BIT_9 #define CF_NVME_FIRST_BURST_ENABLE BIT_11
#define CF_DIF_SEG_DESCR_ENABLE BIT_3 #define CF_DIF_SEG_DESCR_ENABLE BIT_3
#define CF_DATA_SEG_DESCR_ENABLE BIT_2 #define CF_DATA_SEG_DESCR_ENABLE BIT_2
#define CF_READ_DATA BIT_1 #define CF_READ_DATA BIT_1
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment