[SCSI] lpfc 8.2.8 v2 : Add sysfs control of target queue depth handling
Added new sysfs attribute lpfc_max_scsicmpl_time. Attribute, when enabled, will control target queue depth based on I/O completion time. Signed-off-by: James Smart <james.smart@emulex.com> Signed-off-by: James Bottomley <James.Bottomley@HansenPartnership.com>
This commit is contained in:
committed by
James Bottomley
parent
b522d7d42d
commit
977b5a0af6
@@ -628,6 +628,7 @@ lpfc_scsi_cmd_iocb_cmpl(struct lpfc_hba *phba, struct lpfc_iocbq *pIocbIn,
|
||||
|
||||
lpfc_cmd->result = pIocbOut->iocb.un.ulpWord[4];
|
||||
lpfc_cmd->status = pIocbOut->iocb.ulpStatus;
|
||||
atomic_dec(&pnode->cmd_pending);
|
||||
|
||||
if (lpfc_cmd->status) {
|
||||
if (lpfc_cmd->status == IOSTAT_LOCAL_REJECT &&
|
||||
@@ -688,6 +689,29 @@ lpfc_scsi_cmd_iocb_cmpl(struct lpfc_hba *phba, struct lpfc_iocbq *pIocbIn,
|
||||
|
||||
result = cmd->result;
|
||||
sdev = cmd->device;
|
||||
if (vport->cfg_max_scsicmpl_time &&
|
||||
time_after(jiffies, lpfc_cmd->start_time +
|
||||
msecs_to_jiffies(vport->cfg_max_scsicmpl_time))) {
|
||||
spin_lock_irqsave(sdev->host->host_lock, flags);
|
||||
if ((pnode->cmd_qdepth > atomic_read(&pnode->cmd_pending) &&
|
||||
(atomic_read(&pnode->cmd_pending) > LPFC_MIN_TGT_QDEPTH) &&
|
||||
((cmd->cmnd[0] == READ_10) || (cmd->cmnd[0] == WRITE_10))))
|
||||
pnode->cmd_qdepth = atomic_read(&pnode->cmd_pending);
|
||||
|
||||
pnode->last_change_time = jiffies;
|
||||
spin_unlock_irqrestore(sdev->host->host_lock, flags);
|
||||
} else if ((pnode->cmd_qdepth < LPFC_MAX_TGT_QDEPTH) &&
|
||||
time_after(jiffies, pnode->last_change_time +
|
||||
msecs_to_jiffies(LPFC_TGTQ_INTERVAL))) {
|
||||
spin_lock_irqsave(sdev->host->host_lock, flags);
|
||||
pnode->cmd_qdepth += pnode->cmd_qdepth *
|
||||
LPFC_TGTQ_RAMPUP_PCENT / 100;
|
||||
if (pnode->cmd_qdepth > LPFC_MAX_TGT_QDEPTH)
|
||||
pnode->cmd_qdepth = LPFC_MAX_TGT_QDEPTH;
|
||||
pnode->last_change_time = jiffies;
|
||||
spin_unlock_irqrestore(sdev->host->host_lock, flags);
|
||||
}
|
||||
|
||||
lpfc_scsi_unprep_dma_buf(phba, lpfc_cmd);
|
||||
cmd->scsi_done(cmd);
|
||||
|
||||
@@ -1075,6 +1099,8 @@ lpfc_queuecommand(struct scsi_cmnd *cmnd, void (*done) (struct scsi_cmnd *))
|
||||
cmnd->result = ScsiResult(DID_TRANSPORT_DISRUPTED, 0);
|
||||
goto out_fail_command;
|
||||
}
|
||||
if (atomic_read(&ndlp->cmd_pending) >= ndlp->cmd_qdepth)
|
||||
goto out_host_busy;
|
||||
|
||||
lpfc_cmd = lpfc_get_scsi_buf(phba);
|
||||
if (lpfc_cmd == NULL) {
|
||||
@@ -1093,6 +1119,7 @@ lpfc_queuecommand(struct scsi_cmnd *cmnd, void (*done) (struct scsi_cmnd *))
|
||||
lpfc_cmd->pCmd = cmnd;
|
||||
lpfc_cmd->rdata = rdata;
|
||||
lpfc_cmd->timeout = 0;
|
||||
lpfc_cmd->start_time = jiffies;
|
||||
cmnd->host_scribble = (unsigned char *)lpfc_cmd;
|
||||
cmnd->scsi_done = done;
|
||||
|
||||
@@ -1102,6 +1129,7 @@ lpfc_queuecommand(struct scsi_cmnd *cmnd, void (*done) (struct scsi_cmnd *))
|
||||
|
||||
lpfc_scsi_prep_cmnd(vport, lpfc_cmd, ndlp);
|
||||
|
||||
atomic_inc(&ndlp->cmd_pending);
|
||||
err = lpfc_sli_issue_iocb(phba, &phba->sli.ring[psli->fcp_ring],
|
||||
&lpfc_cmd->cur_iocbq, SLI_IOCB_RET_IOCB);
|
||||
if (err)
|
||||
@@ -1116,6 +1144,7 @@ lpfc_queuecommand(struct scsi_cmnd *cmnd, void (*done) (struct scsi_cmnd *))
|
||||
return 0;
|
||||
|
||||
out_host_busy_free_buf:
|
||||
atomic_dec(&ndlp->cmd_pending);
|
||||
lpfc_scsi_unprep_dma_buf(phba, lpfc_cmd);
|
||||
lpfc_release_scsi_buf(phba, lpfc_cmd);
|
||||
out_host_busy:
|
||||
|
Reference in New Issue
Block a user