[SCSI] lpfc 8.3.33: Misc changes to optimize critical path

Signed-off-by: James Smart <james.smart@emulex.com>
Signed-off-by: James Bottomley <JBottomley@Parallels.com>
This commit is contained in:
James Smart 2012-08-03 12:35:44 -04:00 committed by James Bottomley
parent 7e56aa25e3
commit 027140eab7
2 changed files with 29 additions and 14 deletions

View file

@ -3919,6 +3919,8 @@ lpfc_scsi_prep_cmnd(struct lpfc_vport *vport, struct lpfc_scsi_buf *lpfc_cmd,
struct lpfc_iocbq *piocbq = &(lpfc_cmd->cur_iocbq);
int datadir = scsi_cmnd->sc_data_direction;
char tag[2];
uint8_t *ptr;
bool sli4;
if (!pnode || !NLP_CHK_NODE_ACT(pnode))
return;
@ -3930,8 +3932,13 @@ lpfc_scsi_prep_cmnd(struct lpfc_vport *vport, struct lpfc_scsi_buf *lpfc_cmd,
int_to_scsilun(lpfc_cmd->pCmd->device->lun,
&lpfc_cmd->fcp_cmnd->fcp_lun);
memset(&fcp_cmnd->fcpCdb[0], 0, LPFC_FCP_CDB_LEN);
memcpy(&fcp_cmnd->fcpCdb[0], scsi_cmnd->cmnd, scsi_cmnd->cmd_len);
ptr = &fcp_cmnd->fcpCdb[0];
memcpy(ptr, scsi_cmnd->cmnd, scsi_cmnd->cmd_len);
if (scsi_cmnd->cmd_len < LPFC_FCP_CDB_LEN) {
ptr += scsi_cmnd->cmd_len;
memset(ptr, 0, (LPFC_FCP_CDB_LEN - scsi_cmnd->cmd_len));
}
if (scsi_populate_tag_msg(scsi_cmnd, tag)) {
switch (tag[0]) {
case HEAD_OF_QUEUE_TAG:
@ -3947,6 +3954,8 @@ lpfc_scsi_prep_cmnd(struct lpfc_vport *vport, struct lpfc_scsi_buf *lpfc_cmd,
} else
fcp_cmnd->fcpCntl1 = 0;
sli4 = (phba->sli_rev == LPFC_SLI_REV4);
/*
* There are three possibilities here - use scatter-gather segment, use
* the single mapping, or neither. Start the lpfc command prep by
@ -3956,11 +3965,12 @@ lpfc_scsi_prep_cmnd(struct lpfc_vport *vport, struct lpfc_scsi_buf *lpfc_cmd,
if (scsi_sg_count(scsi_cmnd)) {
if (datadir == DMA_TO_DEVICE) {
iocb_cmd->ulpCommand = CMD_FCP_IWRITE64_CR;
if (phba->sli_rev < LPFC_SLI_REV4) {
if (sli4)
iocb_cmd->ulpPU = PARM_READ_CHECK;
else {
iocb_cmd->un.fcpi.fcpi_parm = 0;
iocb_cmd->ulpPU = 0;
} else
iocb_cmd->ulpPU = PARM_READ_CHECK;
}
fcp_cmnd->fcpCntl3 = WRITE_DATA;
phba->fc4OutputRequests++;
} else {
@ -3984,7 +3994,7 @@ lpfc_scsi_prep_cmnd(struct lpfc_vport *vport, struct lpfc_scsi_buf *lpfc_cmd,
* of the scsi_cmnd request_buffer
*/
piocbq->iocb.ulpContext = pnode->nlp_rpi;
if (phba->sli_rev == LPFC_SLI_REV4)
if (sli4)
piocbq->iocb.ulpContext =
phba->sli4_hba.rpi_ids[pnode->nlp_rpi];
if (pnode->nlp_fcp_info & NLP_FCP_2_DEVICE)

View file

@ -94,6 +94,7 @@ lpfc_sli4_wq_put(struct lpfc_queue *q, union lpfc_wqe *wqe)
union lpfc_wqe *temp_wqe;
struct lpfc_register doorbell;
uint32_t host_index;
uint32_t idx;
/* sanity check on queue memory */
if (unlikely(!q))
@ -101,7 +102,8 @@ lpfc_sli4_wq_put(struct lpfc_queue *q, union lpfc_wqe *wqe)
temp_wqe = q->qe[q->host_index].wqe;
/* If the host has not yet processed the next entry then we are done */
if (((q->host_index + 1) % q->entry_count) == q->hba_index) {
idx = ((q->host_index + 1) % q->entry_count);
if (idx == q->hba_index) {
q->WQ_overflow++;
return -ENOMEM;
}
@ -115,7 +117,8 @@ lpfc_sli4_wq_put(struct lpfc_queue *q, union lpfc_wqe *wqe)
/* Update the host index before invoking device */
host_index = q->host_index;
q->host_index = ((q->host_index + 1) % q->entry_count);
q->host_index = idx;
/* Ring Doorbell */
doorbell.word0 = 0;
@ -123,7 +126,6 @@ lpfc_sli4_wq_put(struct lpfc_queue *q, union lpfc_wqe *wqe)
bf_set(lpfc_wq_doorbell_index, &doorbell, host_index);
bf_set(lpfc_wq_doorbell_id, &doorbell, q->queue_id);
writel(doorbell.word0, q->phba->sli4_hba.WQDBregaddr);
readl(q->phba->sli4_hba.WQDBregaddr); /* Flush */
return 0;
}
@ -197,7 +199,6 @@ lpfc_sli4_mq_put(struct lpfc_queue *q, struct lpfc_mqe *mqe)
bf_set(lpfc_mq_doorbell_num_posted, &doorbell, 1);
bf_set(lpfc_mq_doorbell_id, &doorbell, q->queue_id);
writel(doorbell.word0, q->phba->sli4_hba.MQDBregaddr);
readl(q->phba->sli4_hba.MQDBregaddr); /* Flush */
return 0;
}
@ -237,6 +238,7 @@ static struct lpfc_eqe *
lpfc_sli4_eq_get(struct lpfc_queue *q)
{
struct lpfc_eqe *eqe;
uint32_t idx;
/* sanity check on queue memory */
if (unlikely(!q))
@ -247,10 +249,11 @@ lpfc_sli4_eq_get(struct lpfc_queue *q)
if (!bf_get_le32(lpfc_eqe_valid, eqe))
return NULL;
/* If the host has not yet processed the next entry then we are done */
if (((q->hba_index + 1) % q->entry_count) == q->host_index)
idx = ((q->hba_index + 1) % q->entry_count);
if (idx == q->host_index)
return NULL;
q->hba_index = ((q->hba_index + 1) % q->entry_count);
q->hba_index = idx;
return eqe;
}
@ -321,6 +324,7 @@ static struct lpfc_cqe *
lpfc_sli4_cq_get(struct lpfc_queue *q)
{
struct lpfc_cqe *cqe;
uint32_t idx;
/* sanity check on queue memory */
if (unlikely(!q))
@ -330,11 +334,12 @@ lpfc_sli4_cq_get(struct lpfc_queue *q)
if (!bf_get_le32(lpfc_cqe_valid, q->qe[q->hba_index].cqe))
return NULL;
/* If the host has not yet processed the next entry then we are done */
if (((q->hba_index + 1) % q->entry_count) == q->host_index)
idx = ((q->hba_index + 1) % q->entry_count);
if (idx == q->host_index)
return NULL;
cqe = q->qe[q->hba_index].cqe;
q->hba_index = ((q->hba_index + 1) % q->entry_count);
q->hba_index = idx;
return cqe;
}