diff options
Diffstat (limited to 'drivers/scsi/lpfc/lpfc_sli.c')
-rw-r--r-- | drivers/scsi/lpfc/lpfc_sli.c | 42 |
1 files changed, 37 insertions, 5 deletions
diff --git a/drivers/scsi/lpfc/lpfc_sli.c b/drivers/scsi/lpfc/lpfc_sli.c index 582f5ea4e84e..a4128e19338a 100644 --- a/drivers/scsi/lpfc/lpfc_sli.c +++ b/drivers/scsi/lpfc/lpfc_sli.c | |||
@@ -117,6 +117,10 @@ lpfc_sli_iocb_cmd_type(uint8_t iocb_cmnd) | |||
117 | case CMD_FCP_IREAD_CX: | 117 | case CMD_FCP_IREAD_CX: |
118 | case CMD_FCP_ICMND_CR: | 118 | case CMD_FCP_ICMND_CR: |
119 | case CMD_FCP_ICMND_CX: | 119 | case CMD_FCP_ICMND_CX: |
120 | case CMD_FCP_TSEND_CX: | ||
121 | case CMD_FCP_TRSP_CX: | ||
122 | case CMD_FCP_TRECEIVE_CX: | ||
123 | case CMD_FCP_AUTO_TRSP_CX: | ||
120 | case CMD_ADAPTER_MSG: | 124 | case CMD_ADAPTER_MSG: |
121 | case CMD_ADAPTER_DUMP: | 125 | case CMD_ADAPTER_DUMP: |
122 | case CMD_XMIT_SEQUENCE64_CR: | 126 | case CMD_XMIT_SEQUENCE64_CR: |
@@ -131,6 +135,9 @@ lpfc_sli_iocb_cmd_type(uint8_t iocb_cmnd) | |||
131 | case CMD_FCP_IREAD64_CX: | 135 | case CMD_FCP_IREAD64_CX: |
132 | case CMD_FCP_ICMND64_CR: | 136 | case CMD_FCP_ICMND64_CR: |
133 | case CMD_FCP_ICMND64_CX: | 137 | case CMD_FCP_ICMND64_CX: |
138 | case CMD_FCP_TSEND64_CX: | ||
139 | case CMD_FCP_TRSP64_CX: | ||
140 | case CMD_FCP_TRECEIVE64_CX: | ||
134 | case CMD_GEN_REQUEST64_CR: | 141 | case CMD_GEN_REQUEST64_CR: |
135 | case CMD_GEN_REQUEST64_CX: | 142 | case CMD_GEN_REQUEST64_CX: |
136 | case CMD_XMIT_ELS_RSP64_CX: | 143 | case CMD_XMIT_ELS_RSP64_CX: |
@@ -1098,6 +1105,7 @@ lpfc_sli_handle_fast_ring_event(struct lpfc_hba * phba, | |||
1098 | lpfc_sli_pcimem_bcopy((uint32_t *) entry, | 1105 | lpfc_sli_pcimem_bcopy((uint32_t *) entry, |
1099 | (uint32_t *) &rspiocbq.iocb, | 1106 | (uint32_t *) &rspiocbq.iocb, |
1100 | sizeof (IOCB_t)); | 1107 | sizeof (IOCB_t)); |
1108 | INIT_LIST_HEAD(&(rspiocbq.list)); | ||
1101 | irsp = &rspiocbq.iocb; | 1109 | irsp = &rspiocbq.iocb; |
1102 | 1110 | ||
1103 | type = lpfc_sli_iocb_cmd_type(irsp->ulpCommand & CMD_IOCB_MASK); | 1111 | type = lpfc_sli_iocb_cmd_type(irsp->ulpCommand & CMD_IOCB_MASK); |
@@ -1149,6 +1157,11 @@ lpfc_sli_handle_fast_ring_event(struct lpfc_hba * phba, | |||
1149 | } | 1157 | } |
1150 | } | 1158 | } |
1151 | break; | 1159 | break; |
1160 | case LPFC_UNSOL_IOCB: | ||
1161 | spin_unlock_irqrestore(phba->host->host_lock, iflag); | ||
1162 | lpfc_sli_process_unsol_iocb(phba, pring, &rspiocbq); | ||
1163 | spin_lock_irqsave(phba->host->host_lock, iflag); | ||
1164 | break; | ||
1152 | default: | 1165 | default: |
1153 | if (irsp->ulpCommand == CMD_ADAPTER_MSG) { | 1166 | if (irsp->ulpCommand == CMD_ADAPTER_MSG) { |
1154 | char adaptermsg[LPFC_MAX_ADPTMSG]; | 1167 | char adaptermsg[LPFC_MAX_ADPTMSG]; |
@@ -2472,13 +2485,17 @@ lpfc_extra_ring_setup( struct lpfc_hba *phba) | |||
2472 | psli = &phba->sli; | 2485 | psli = &phba->sli; |
2473 | 2486 | ||
2474 | /* Adjust cmd/rsp ring iocb entries more evenly */ | 2487 | /* Adjust cmd/rsp ring iocb entries more evenly */ |
2488 | |||
2489 | /* Take some away from the FCP ring */ | ||
2475 | pring = &psli->ring[psli->fcp_ring]; | 2490 | pring = &psli->ring[psli->fcp_ring]; |
2476 | pring->numCiocb -= SLI2_IOCB_CMD_R1XTRA_ENTRIES; | 2491 | pring->numCiocb -= SLI2_IOCB_CMD_R1XTRA_ENTRIES; |
2477 | pring->numRiocb -= SLI2_IOCB_RSP_R1XTRA_ENTRIES; | 2492 | pring->numRiocb -= SLI2_IOCB_RSP_R1XTRA_ENTRIES; |
2478 | pring->numCiocb -= SLI2_IOCB_CMD_R3XTRA_ENTRIES; | 2493 | pring->numCiocb -= SLI2_IOCB_CMD_R3XTRA_ENTRIES; |
2479 | pring->numRiocb -= SLI2_IOCB_RSP_R3XTRA_ENTRIES; | 2494 | pring->numRiocb -= SLI2_IOCB_RSP_R3XTRA_ENTRIES; |
2480 | 2495 | ||
2481 | pring = &psli->ring[1]; | 2496 | /* and give them to the extra ring */ |
2497 | pring = &psli->ring[psli->extra_ring]; | ||
2498 | |||
2482 | pring->numCiocb += SLI2_IOCB_CMD_R1XTRA_ENTRIES; | 2499 | pring->numCiocb += SLI2_IOCB_CMD_R1XTRA_ENTRIES; |
2483 | pring->numRiocb += SLI2_IOCB_RSP_R1XTRA_ENTRIES; | 2500 | pring->numRiocb += SLI2_IOCB_RSP_R1XTRA_ENTRIES; |
2484 | pring->numCiocb += SLI2_IOCB_CMD_R3XTRA_ENTRIES; | 2501 | pring->numCiocb += SLI2_IOCB_CMD_R3XTRA_ENTRIES; |
@@ -2488,8 +2505,8 @@ lpfc_extra_ring_setup( struct lpfc_hba *phba) | |||
2488 | pring->iotag_max = 4096; | 2505 | pring->iotag_max = 4096; |
2489 | pring->num_mask = 1; | 2506 | pring->num_mask = 1; |
2490 | pring->prt[0].profile = 0; /* Mask 0 */ | 2507 | pring->prt[0].profile = 0; /* Mask 0 */ |
2491 | pring->prt[0].rctl = FC_UNSOL_DATA; | 2508 | pring->prt[0].rctl = phba->cfg_multi_ring_rctl; |
2492 | pring->prt[0].type = 5; | 2509 | pring->prt[0].type = phba->cfg_multi_ring_type; |
2493 | pring->prt[0].lpfc_sli_rcv_unsol_event = NULL; | 2510 | pring->prt[0].lpfc_sli_rcv_unsol_event = NULL; |
2494 | return 0; | 2511 | return 0; |
2495 | } | 2512 | } |
@@ -2505,7 +2522,7 @@ lpfc_sli_setup(struct lpfc_hba *phba) | |||
2505 | psli->sli_flag = 0; | 2522 | psli->sli_flag = 0; |
2506 | psli->fcp_ring = LPFC_FCP_RING; | 2523 | psli->fcp_ring = LPFC_FCP_RING; |
2507 | psli->next_ring = LPFC_FCP_NEXT_RING; | 2524 | psli->next_ring = LPFC_FCP_NEXT_RING; |
2508 | psli->ip_ring = LPFC_IP_RING; | 2525 | psli->extra_ring = LPFC_EXTRA_RING; |
2509 | 2526 | ||
2510 | psli->iocbq_lookup = NULL; | 2527 | psli->iocbq_lookup = NULL; |
2511 | psli->iocbq_lookup_len = 0; | 2528 | psli->iocbq_lookup_len = 0; |
@@ -2528,7 +2545,7 @@ lpfc_sli_setup(struct lpfc_hba *phba) | |||
2528 | pring->fast_iotag = pring->iotag_max; | 2545 | pring->fast_iotag = pring->iotag_max; |
2529 | pring->num_mask = 0; | 2546 | pring->num_mask = 0; |
2530 | break; | 2547 | break; |
2531 | case LPFC_IP_RING: /* ring 1 - IP */ | 2548 | case LPFC_EXTRA_RING: /* ring 1 - EXTRA */ |
2532 | /* numCiocb and numRiocb are used in config_port */ | 2549 | /* numCiocb and numRiocb are used in config_port */ |
2533 | pring->numCiocb = SLI2_IOCB_CMD_R1_ENTRIES; | 2550 | pring->numCiocb = SLI2_IOCB_CMD_R1_ENTRIES; |
2534 | pring->numRiocb = SLI2_IOCB_RSP_R1_ENTRIES; | 2551 | pring->numRiocb = SLI2_IOCB_RSP_R1_ENTRIES; |
@@ -3238,6 +3255,21 @@ lpfc_intr_handler(int irq, void *dev_id) | |||
3238 | lpfc_sli_handle_fast_ring_event(phba, | 3255 | lpfc_sli_handle_fast_ring_event(phba, |
3239 | &phba->sli.ring[LPFC_FCP_RING], | 3256 | &phba->sli.ring[LPFC_FCP_RING], |
3240 | status); | 3257 | status); |
3258 | |||
3259 | if (phba->cfg_multi_ring_support == 2) { | ||
3260 | /* | ||
3261 | * Process all events on extra ring. Take the optimized path | ||
3262 | * for extra ring IO. Any other IO is slow path and is handled | ||
3263 | * by the worker thread. | ||
3264 | */ | ||
3265 | status = (ha_copy & (HA_RXMASK << (4*LPFC_EXTRA_RING))); | ||
3266 | status >>= (4*LPFC_EXTRA_RING); | ||
3267 | if (status & HA_RXATT) { | ||
3268 | lpfc_sli_handle_fast_ring_event(phba, | ||
3269 | &phba->sli.ring[LPFC_EXTRA_RING], | ||
3270 | status); | ||
3271 | } | ||
3272 | } | ||
3241 | return IRQ_HANDLED; | 3273 | return IRQ_HANDLED; |
3242 | 3274 | ||
3243 | } /* lpfc_intr_handler */ | 3275 | } /* lpfc_intr_handler */ |