Hi James,

On Tue, Jan 17, 2017 at 05:20:45PM -0800, James Smart wrote:
> 
> NVME Initiator: Base modifications
> 
> This is part A of parts A..F.
> 
> Part A is the bulk of the file list changed by the modifications as
> most mods are small-ish. Changes may be for any aspect below.
> 
> *********
> 
> This set of patches (6 parts) adds base modifications for NVME initiator
> support to the lpfc driver.
> 
> The base modifications consist of:
> - Formal split of SLI3 rings from SLI-4 WQs (sometimes referred to as
>   rings as well) as implementation now widely varies between the two.
> - Addition of configuration modes:
>    SCSI initiator only; NVME initiator only; NVME target only; and
>    SCSI and NVME initiator.
>    The configuration mode drives overall adapter configuration,
>    offloads enabled, and resource splits.
>    NVME support is only available on SLI-4 devices and newer fw.
> - Implements the following based on configuration mode:
>   - Exchange resources are split by protocol; Obviously, if only
>      1 mode, then no split occurs. Default is 50/50. module attribute
>      allows tuning.
>   - Each protocol has it's own set of queues, but share interrupt
>     vectors.
>      SCSI:
>        SLI3 devices have few queues and the original style of queue
>          allocation remains.
>        SLI4 devices piggy back on an "io-channel" concept that
>          eventually needs to merge with scsi-mq/blk-mq support (it is
>        underway).  For now, the paradigm continues as it existed
>        prior. io channel allocates N msix and N WQs (N=4 default)
>        and either round robins or uses cpu # modulo N for scheduling.
>        A bunch of module parameters allow the configuration to be
>        tuned.
>      NVME (initiator):
>        Allocates an msix per cpu (or whatever pci_alloc_irq_vectors
>          gets)
>        Allocates a WQ per cpu, and maps the WQs to msix on a WQ #
>          modulo msix vector count basis.
>        Module parameters exist to cap/control the config if desired.
>   - Each protocol has its own buffer and dma pools.
> 
> Unfortunately, it was very difficult to break out the above into
> functional patches. A such, they are presented as a 6-patch set to
> keep email size reasonable. All patches in the set must be applied to
> create a functional unit.
> 
> Signed-off-by: Dick Kennedy <dick.kenn...@broadcom.com>
> Signed-off-by: James Smart <james.sm...@broadcom.com>
> ---

[...]

> @@ -2704,7 +2710,7 @@ static int lpfcdiag_loop_get_xri(struct lpfc_hba *phba, 
> uint16_t rpi,
>   * @phba: Pointer to HBA context object
>   *
>   * This function allocates BSG_MBOX_SIZE (4KB) page size dma buffer and.
> - * returns the pointer to the buffer.
> + * retruns the pointer to the buffer.

This hunk introduces a spelling error.

>   **/
>  static struct lpfc_dmabuf *
>  lpfc_bsg_dma_page_alloc(struct lpfc_hba *phba)
> @@ -2876,7 +2882,7 @@ static int lpfcdiag_loop_post_rxbufs(struct lpfc_hba 
> *phba, uint16_t rxxri,
>                            size_t len)
>  {
>       struct lpfc_sli *psli = &phba->sli;
> -     struct lpfc_sli_ring *pring = &psli->ring[LPFC_ELS_RING];
> +     struct lpfc_sli_ring *pring;
>       struct lpfc_iocbq *cmdiocbq;
>       IOCB_t *cmd = NULL;
>       struct list_head head, *curr, *next;
> @@ -2890,6 +2896,11 @@ static int lpfcdiag_loop_post_rxbufs(struct lpfc_hba 
> *phba, uint16_t rxxri,
>       int iocb_stat;
>       int i = 0;
>  
> +     if (phba->sli_rev == LPFC_SLI_REV4)
> +             pring = phba->sli4_hba.els_wq->pring;
> +     else
> +             pring = &psli->sli3_ring[LPFC_ELS_RING];
> +
>       cmdiocbq = lpfc_sli_get_iocbq(phba);
>       rxbmp = kmalloc(sizeof(struct lpfc_dmabuf), GFP_KERNEL);
>       if (rxbmp != NULL) {
> @@ -5258,7 +5269,7 @@ static int
>  lpfc_forced_link_speed(struct bsg_job *job)
>  {
>       struct Scsi_Host *shost = fc_bsg_to_shost(job);
> -     struct lpfc_vport *vport = shost_priv(shost);
> +     struct lpfc_vport *vport = (struct lpfc_vport *)shost->hostdata;

Please don't. A) it's unnecessary to cast a void* and b) shost_priv() just
returns shost->hostdata (casted to void*). So all's fine.

[...]

> diff --git a/drivers/scsi/lpfc/lpfc_disc.h b/drivers/scsi/lpfc/lpfc_disc.h
> index 361f5b3..1d07a5f 100644
> --- a/drivers/scsi/lpfc/lpfc_disc.h
> +++ b/drivers/scsi/lpfc/lpfc_disc.h
> @@ -133,6 +133,7 @@ struct lpfc_node_rrq {
>  /* Defines for nlp_flag (uint32) */
>  #define NLP_IGNR_REG_CMPL  0x00000001 /* Rcvd rscn before we cmpl reg login 
> */
>  #define NLP_REG_LOGIN_SEND 0x00000002   /* sent reglogin to adapter */
> +#define NLP_SUPPRESS_RSP   0x00000010        /* Remote NPort supports 
> suppress rsp */
>  #define NLP_PLOGI_SND      0x00000020        /* sent PLOGI request for this 
> entry */
>  #define NLP_PRLI_SND       0x00000040        /* sent PRLI request for this 
> entry */
>  #define NLP_ADISC_SND      0x00000080        /* sent ADISC request for this 
> entry */
> diff --git a/drivers/scsi/lpfc/lpfc_els.c b/drivers/scsi/lpfc/lpfc_els.c
> index 27f0cbb..f61e1c2 100644
> --- a/drivers/scsi/lpfc/lpfc_els.c
> +++ b/drivers/scsi/lpfc/lpfc_els.c
> @@ -1323,7 +1323,10 @@ lpfc_els_abort_flogi(struct lpfc_hba *phba)
>                       "0201 Abort outstanding I/O on NPort x%x\n",
>                       Fabric_DID);
>  
> -     pring = &phba->sli.ring[LPFC_ELS_RING];
> +     if (phba->sli_rev != LPFC_SLI_REV4)
> +             pring = &phba->sli.sli3_ring[LPFC_ELS_RING];
> +     else
> +             pring = phba->sli4_hba.els_wq->pring;
>  

You're doing this quite often, can you make a small helper for it?
static inline struct lpfc_sli_ring *lpfc_sli_ring_from_hba(struct lpfc_hba 
*phba)
{
        if (phba->sli_rev != LPFC_SLI_REV4)
                pring = &phba->sli.sli3_ring[LPFC_ELS_RING];
        else
                pring = phba->sli4_hba.els_wq->pring;
}

[...]

> @@ -1751,7 +1757,7 @@ lpfc_sli4_new_fcf_random_select(struct lpfc_hba *phba, 
> uint32_t fcf_cnt)
>       uint32_t rand_num;
>  
>       /* Get 16-bit uniform random number */
> -     rand_num = 0xFFFF & prandom_u32();
> +     rand_num = (0xFFFF & prandom_u32());

Unnecessary introduction of parenthesis.


[...]

> @@ -4452,28 +4471,51 @@ lpfc_no_rpi(struct lpfc_hba *phba, struct 
> lpfc_nodelist *ndlp)
>       psli = &phba->sli;
>       if (ndlp->nlp_flag & NLP_RPI_REGISTERED) {
>               /* Now process each ring */
> -             for (i = 0; i < psli->num_rings; i++) {
> -                     pring = &psli->ring[i];
> -
> -                     spin_lock_irq(&phba->hbalock);
> -                     list_for_each_entry_safe(iocb, next_iocb, &pring->txq,
> -                                              list) {
> -                             /*
> -                              * Check to see if iocb matches the nport we are
> -                              * looking for
> -                              */
> +             if (phba->sli_rev != LPFC_SLI_REV4) {
> +                     for (i = 0; i < psli->num_rings; i++) {
> +                             pring = &psli->sli3_ring[i];
> +                             spin_lock_irq(&phba->hbalock);
> +                             list_for_each_entry_safe(iocb, next_iocb,
> +                                                      &pring->txq, list) {
> +                                     /*
> +                                      * Check to see if iocb matches the
> +                                      * nport we are looking for
> +                                      */
> +                                     if ((lpfc_check_sli_ndlp(phba, pring,
> +                                                              iocb, ndlp))) {
> +                                             /* It matches, so deque and
> +                                              * call compl with an error
> +                                              */
> +                                             list_move_tail(&iocb->list,
> +                                                            &completions);
> +                                     }
> +                             }
> +                             spin_unlock_irq(&phba->hbalock);
> +                     }
> +                     goto out;
> +             }

Can you please factor the for loop into an own function so that we get

                if (phba->sli_rev != LPFC_SLI_REV4)
                        lpfc_handle_sli_rev4();

The level of indentation is just too high. Btw checkpatch.pl tells you about
it with '--type DEEP_INDENTATION'.

> +             spin_lock_irq(&phba->hbalock);
> +             list_for_each_entry(qp, &phba->sli4_hba.lpfc_wq_list, wq_list) {
> +                     pring = qp->pring;
> +                     if (!pring)
> +                             continue;
> +                     spin_lock_irq(&pring->ring_lock);
> +                     list_for_each_entry_safe(iocb, next_iocb,
> +                                              &pring->txq, list) {
>                               if ((lpfc_check_sli_ndlp(phba, pring, iocb,
>                                                        ndlp))) {
> -                                     /* It matches, so deque and call compl
> -                                        with an error */
> +                                     /* It matches, so deque and
> +                                      * call compl with an error
> +                                      */
>                                       list_move_tail(&iocb->list,
>                                                      &completions);
>                               }
>                       }
> -                     spin_unlock_irq(&phba->hbalock);
> +                     spin_unlock_irq(&pring->ring_lock);
>               }

like above, is it possible to do
                spin_lock_irq(...);
                handler();
                spin_unlock_irq();

This makes it way easier to follow.

[...]

> @@ -5207,7 +5248,10 @@ lpfc_free_tx(struct lpfc_hba *phba, struct 
> lpfc_nodelist *ndlp)
>       struct lpfc_sli_ring *pring;
>  
>       psli = &phba->sli;
> -     pring = &psli->ring[LPFC_ELS_RING];
> +     if (phba->sli_rev != LPFC_SLI_REV4)
> +             pring = &phba->sli.sli3_ring[LPFC_ELS_RING];
> +     else
> +             pring = phba->sli4_hba.els_wq->pring;
>  
you really might want to write a coccinelle rule for this pattern... 

[...]

> diff --git a/drivers/scsi/lpfc/lpfc_scsi.c b/drivers/scsi/lpfc/lpfc_scsi.c
> index 19d349f..c60dfc9 100644
> --- a/drivers/scsi/lpfc/lpfc_scsi.c
> +++ b/drivers/scsi/lpfc/lpfc_scsi.c
> @@ -242,6 +242,7 @@ lpfc_update_stats(struct lpfc_hba *phba, struct  
> lpfc_scsi_buf *lpfc_cmd)
>       spin_unlock_irqrestore(shost->host_lock, flags);
>  }
>  
> +

Stray newine.

[...]

> @@ -605,7 +610,7 @@ lpfc_sli4_fcp_xri_aborted(struct lpfc_hba *phba,
>  }
>  
>  /**
> - * lpfc_sli4_post_scsi_sgl_list - Post blocks of scsi buffer sgls from a list
> + * lpfc_sli4_post_scsi_sgl_list - Psot blocks of scsi buffer sgls from a list
                                     ^^^ o.O

[...]

> @@ -3894,7 +3896,7 @@ int lpfc_sli4_scmd_to_wqidx_distr(struct lpfc_hba *phba,
>               }
>       }
>       chann = atomic_add_return(1, &phba->fcp_qidx);
> -     chann = (chann % phba->cfg_fcp_io_channel);
> +     chann = (chann % phba->cfg_fcp_max_hw_queue);

No need for the parenthesis.

[...]

> @@ -4959,11 +4968,11 @@ lpfc_send_taskmgmt(struct lpfc_vport *vport, struct 
> scsi_cmnd *cmnd,
>       int status;
>  
>       rdata = lpfc_rport_data_from_scsi_device(cmnd->device);
> -     if (!rdata || !rdata->pnode || !NLP_CHK_NODE_ACT(rdata->pnode))
> -             return FAILED;

OK, I don't get this hunk. lpfc_rport_data_from_scsi_device() cannot return
NULL anymore?

I at least expected something like:

        rdata = lpfc_rport_data_from_scsi_device(cmnd->device);
        if (!rdata || !rdata->pnode)
                return FAILED;
        
        pnode = rdata->pnode;
        if (!NLP_CHK_NODE_ACT(pnode)
                return FAILED;

>       pnode = rdata->pnode;
> +     if (!pnode || !NLP_CHK_NODE_ACT(pnode))
> +             return FAILED;
>  
> -     lpfc_cmd = lpfc_get_scsi_buf(phba, pnode);
> +     lpfc_cmd = lpfc_get_scsi_buf(phba, rdata->pnode);
>       if (lpfc_cmd == NULL)
>               return FAILED;
>       lpfc_cmd->timeout = phba->cfg_task_mgmt_tmo;


[...]

-- 
Johannes Thumshirn                                          Storage
jthumsh...@suse.de                                +49 911 74053 689
SUSE LINUX GmbH, Maxfeldstr. 5, 90409 Nürnberg
GF: Felix Imendörffer, Jane Smithard, Graham Norton
HRB 21284 (AG Nürnberg)
Key fingerprint = EC38 9CAB C2C4 F25D 8600 D0D0 0393 969D 2D76 0850
--
To unsubscribe from this list: send the line "unsubscribe linux-scsi" in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html

Reply via email to