diff options
-rw-r--r-- | drivers/scsi/fcoe/fcoe_ctlr.c | 2 | ||||
-rw-r--r-- | drivers/scsi/libfc/fc_disc.c | 12 | ||||
-rw-r--r-- | drivers/scsi/lpfc/lpfc_attr.c | 26 | ||||
-rw-r--r-- | drivers/scsi/lpfc/lpfc_bsg.c | 21 | ||||
-rw-r--r-- | drivers/scsi/lpfc/lpfc_ct.c | 22 | ||||
-rw-r--r-- | drivers/scsi/lpfc/lpfc_els.c | 10 | ||||
-rw-r--r-- | drivers/scsi/lpfc/lpfc_init.c | 25 | ||||
-rw-r--r-- | drivers/scsi/lpfc/lpfc_nportdisc.c | 8 | ||||
-rw-r--r-- | drivers/scsi/lpfc/lpfc_nvmet.c | 2 | ||||
-rw-r--r-- | drivers/scsi/lpfc/lpfc_sli.c | 11 | ||||
-rw-r--r-- | drivers/scsi/lpfc/lpfc_version.h | 2 | ||||
-rw-r--r-- | drivers/scsi/scsi_transport_sas.c | 2 | ||||
-rw-r--r-- | drivers/scsi/sd.c | 10 | ||||
-rw-r--r-- | drivers/scsi/sd.h | 11 | ||||
-rw-r--r-- | drivers/scsi/sd_zbc.c | 93 | ||||
-rw-r--r-- | drivers/target/iscsi/iscsi_target_transport.c | 4 | ||||
-rw-r--r-- | include/target/iscsi/iscsi_transport.h | 2 |
17 files changed, 165 insertions, 98 deletions
diff --git a/drivers/scsi/fcoe/fcoe_ctlr.c b/drivers/scsi/fcoe/fcoe_ctlr.c index 85c7959961cc..1409c7687853 100644 --- a/drivers/scsi/fcoe/fcoe_ctlr.c +++ b/drivers/scsi/fcoe/fcoe_ctlr.c @@ -256,9 +256,9 @@ static void fcoe_sysfs_fcf_del(struct fcoe_fcf *new) WARN_ON(!fcf_dev); new->fcf_dev = NULL; fcoe_fcf_device_delete(fcf_dev); - kfree(new); mutex_unlock(&cdev->lock); } + kfree(new); } /** diff --git a/drivers/scsi/libfc/fc_disc.c b/drivers/scsi/libfc/fc_disc.c index 19721db23283..d8cbc9c0e766 100644 --- a/drivers/scsi/libfc/fc_disc.c +++ b/drivers/scsi/libfc/fc_disc.c @@ -581,8 +581,12 @@ static void fc_disc_gpn_id_resp(struct fc_seq *sp, struct fc_frame *fp, if (PTR_ERR(fp) == -FC_EX_CLOSED) goto out; - if (IS_ERR(fp)) - goto redisc; + if (IS_ERR(fp)) { + mutex_lock(&disc->disc_mutex); + fc_disc_restart(disc); + mutex_unlock(&disc->disc_mutex); + goto out; + } cp = fc_frame_payload_get(fp, sizeof(*cp)); if (!cp) @@ -609,7 +613,7 @@ static void fc_disc_gpn_id_resp(struct fc_seq *sp, struct fc_frame *fp, new_rdata->disc_id = disc->disc_id; fc_rport_login(new_rdata); } - goto out; + goto free_fp; } rdata->disc_id = disc->disc_id; mutex_unlock(&rdata->rp_mutex); @@ -626,6 +630,8 @@ redisc: fc_disc_restart(disc); mutex_unlock(&disc->disc_mutex); } +free_fp: + fc_frame_free(fp); out: kref_put(&rdata->kref, fc_rport_destroy); if (!IS_ERR(fp)) diff --git a/drivers/scsi/lpfc/lpfc_attr.c b/drivers/scsi/lpfc/lpfc_attr.c index a62c60ca6477..ece6c250ebaf 100644 --- a/drivers/scsi/lpfc/lpfc_attr.c +++ b/drivers/scsi/lpfc/lpfc_attr.c @@ -6679,9 +6679,15 @@ lpfc_get_host_speed(struct Scsi_Host *shost) } } else if (lpfc_is_link_up(phba) && (phba->hba_flag & HBA_FCOE_MODE)) { switch (phba->fc_linkspeed) { + case LPFC_ASYNC_LINK_SPEED_1GBPS: + fc_host_speed(shost) = FC_PORTSPEED_1GBIT; + break; case LPFC_ASYNC_LINK_SPEED_10GBPS: fc_host_speed(shost) = FC_PORTSPEED_10GBIT; break; + case LPFC_ASYNC_LINK_SPEED_20GBPS: + fc_host_speed(shost) = FC_PORTSPEED_20GBIT; + break; case LPFC_ASYNC_LINK_SPEED_25GBPS: fc_host_speed(shost) = FC_PORTSPEED_25GBIT; break; @@ -7406,12 +7412,26 @@ lpfc_get_cfgparam(struct lpfc_hba *phba) void lpfc_nvme_mod_param_dep(struct lpfc_hba *phba) { - if (phba->cfg_hdw_queue > phba->sli4_hba.num_present_cpu) + int logit = 0; + + if (phba->cfg_hdw_queue > phba->sli4_hba.num_present_cpu) { phba->cfg_hdw_queue = phba->sli4_hba.num_present_cpu; - if (phba->cfg_irq_chann > phba->sli4_hba.num_present_cpu) + logit = 1; + } + if (phba->cfg_irq_chann > phba->sli4_hba.num_present_cpu) { phba->cfg_irq_chann = phba->sli4_hba.num_present_cpu; - if (phba->cfg_irq_chann > phba->cfg_hdw_queue) + logit = 1; + } + if (phba->cfg_irq_chann > phba->cfg_hdw_queue) { phba->cfg_irq_chann = phba->cfg_hdw_queue; + logit = 1; + } + if (logit) + lpfc_printf_log(phba, KERN_ERR, LOG_SLI, + "2006 Reducing Queues - CPU limitation: " + "IRQ %d HDWQ %d\n", + phba->cfg_irq_chann, + phba->cfg_hdw_queue); if (phba->cfg_enable_fc4_type & LPFC_ENABLE_NVME && phba->nvmet_support) { diff --git a/drivers/scsi/lpfc/lpfc_bsg.c b/drivers/scsi/lpfc/lpfc_bsg.c index 1d88fedaf3f0..6f9d648a9b9c 100644 --- a/drivers/scsi/lpfc/lpfc_bsg.c +++ b/drivers/scsi/lpfc/lpfc_bsg.c @@ -2494,13 +2494,12 @@ lpfc_sli4_bsg_link_diag_test(struct bsg_job *job) diag_status_reply = (struct diag_status *) bsg_reply->reply_data.vendor_reply.vendor_rsp; - if (job->reply_len < - sizeof(struct fc_bsg_request) + sizeof(struct diag_status)) { + if (job->reply_len < sizeof(*bsg_reply) + sizeof(*diag_status_reply)) { lpfc_printf_log(phba, KERN_WARNING, LOG_LIBDFC, "3012 Received Run link diag test reply " "below minimum size (%d): reply_len:%d\n", - (int)(sizeof(struct fc_bsg_request) + - sizeof(struct diag_status)), + (int)(sizeof(*bsg_reply) + + sizeof(*diag_status_reply)), job->reply_len); rc = -EINVAL; goto job_error; @@ -3418,8 +3417,7 @@ lpfc_bsg_get_dfc_rev(struct bsg_job *job) event_reply = (struct get_mgmt_rev_reply *) bsg_reply->reply_data.vendor_reply.vendor_rsp; - if (job->reply_len < - sizeof(struct fc_bsg_request) + sizeof(struct get_mgmt_rev_reply)) { + if (job->reply_len < sizeof(*bsg_reply) + sizeof(*event_reply)) { lpfc_printf_log(phba, KERN_WARNING, LOG_LIBDFC, "2741 Received GET_DFC_REV reply below " "minimum size\n"); @@ -5202,8 +5200,8 @@ lpfc_menlo_cmd(struct bsg_job *job) goto no_dd_data; } - if (job->reply_len < - sizeof(struct fc_bsg_request) + sizeof(struct menlo_response)) { + if (job->reply_len < sizeof(*bsg_reply) + + sizeof(struct menlo_response)) { lpfc_printf_log(phba, KERN_WARNING, LOG_LIBDFC, "2785 Received MENLO_CMD reply below " "minimum size\n"); @@ -5359,9 +5357,7 @@ lpfc_forced_link_speed(struct bsg_job *job) forced_reply = (struct forced_link_speed_support_reply *) bsg_reply->reply_data.vendor_reply.vendor_rsp; - if (job->reply_len < - sizeof(struct fc_bsg_request) + - sizeof(struct forced_link_speed_support_reply)) { + if (job->reply_len < sizeof(*bsg_reply) + sizeof(*forced_reply)) { lpfc_printf_log(phba, KERN_WARNING, LOG_LIBDFC, "0049 Received FORCED_LINK_SPEED reply below " "minimum size\n"); @@ -5715,8 +5711,7 @@ lpfc_get_trunk_info(struct bsg_job *job) event_reply = (struct lpfc_trunk_info *) bsg_reply->reply_data.vendor_reply.vendor_rsp; - if (job->reply_len < - sizeof(struct fc_bsg_request) + sizeof(struct lpfc_trunk_info)) { + if (job->reply_len < sizeof(*bsg_reply) + sizeof(*event_reply)) { lpfc_printf_log(phba, KERN_WARNING, LOG_LIBDFC, "2728 Received GET TRUNK _INFO reply below " "minimum size\n"); diff --git a/drivers/scsi/lpfc/lpfc_ct.c b/drivers/scsi/lpfc/lpfc_ct.c index dd9f2bf54edd..ef2015fad2d5 100644 --- a/drivers/scsi/lpfc/lpfc_ct.c +++ b/drivers/scsi/lpfc/lpfc_ct.c @@ -713,7 +713,8 @@ lpfc_cmpl_ct_cmd_gid_ft(struct lpfc_hba *phba, struct lpfc_iocbq *cmdiocb, /* This is a GID_FT completing so the gidft_inp counter was * incremented before the GID_FT was issued to the wire. */ - vport->gidft_inp--; + if (vport->gidft_inp) + vport->gidft_inp--; /* * Skip processing the NS response @@ -741,11 +742,14 @@ lpfc_cmpl_ct_cmd_gid_ft(struct lpfc_hba *phba, struct lpfc_iocbq *cmdiocb, goto out; /* CT command is being retried */ - vport->gidft_inp--; rc = lpfc_ns_cmd(vport, SLI_CTNS_GID_FT, vport->fc_ns_retry, type); if (rc == 0) goto out; + else { /* Unable to send NS cmd */ + if (vport->gidft_inp) + vport->gidft_inp--; + } } if (vport->fc_flag & FC_RSCN_MODE) lpfc_els_flush_rscn(vport); @@ -825,7 +829,8 @@ lpfc_cmpl_ct_cmd_gid_ft(struct lpfc_hba *phba, struct lpfc_iocbq *cmdiocb, (uint32_t) CTrsp->ReasonCode, (uint32_t) CTrsp->Explanation); } - vport->gidft_inp--; + if (vport->gidft_inp) + vport->gidft_inp--; } lpfc_printf_vlog(vport, KERN_INFO, LOG_DISCOVERY, @@ -918,7 +923,8 @@ lpfc_cmpl_ct_cmd_gid_pt(struct lpfc_hba *phba, struct lpfc_iocbq *cmdiocb, /* This is a GID_PT completing so the gidft_inp counter was * incremented before the GID_PT was issued to the wire. */ - vport->gidft_inp--; + if (vport->gidft_inp) + vport->gidft_inp--; /* * Skip processing the NS response @@ -942,11 +948,14 @@ lpfc_cmpl_ct_cmd_gid_pt(struct lpfc_hba *phba, struct lpfc_iocbq *cmdiocb, vport->fc_ns_retry++; /* CT command is being retried */ - vport->gidft_inp--; rc = lpfc_ns_cmd(vport, SLI_CTNS_GID_PT, vport->fc_ns_retry, GID_PT_N_PORT); if (rc == 0) goto out; + else { /* Unable to send NS cmd */ + if (vport->gidft_inp) + vport->gidft_inp--; + } } if (vport->fc_flag & FC_RSCN_MODE) lpfc_els_flush_rscn(vport); @@ -1027,7 +1036,8 @@ lpfc_cmpl_ct_cmd_gid_pt(struct lpfc_hba *phba, struct lpfc_iocbq *cmdiocb, (uint32_t)CTrsp->ReasonCode, (uint32_t)CTrsp->Explanation); } - vport->gidft_inp--; + if (vport->gidft_inp) + vport->gidft_inp--; } lpfc_printf_vlog(vport, KERN_INFO, LOG_DISCOVERY, diff --git a/drivers/scsi/lpfc/lpfc_els.c b/drivers/scsi/lpfc/lpfc_els.c index 85d4e4000c25..48dc63f22cca 100644 --- a/drivers/scsi/lpfc/lpfc_els.c +++ b/drivers/scsi/lpfc/lpfc_els.c @@ -3937,10 +3937,14 @@ lpfc_els_retry(struct lpfc_hba *phba, struct lpfc_iocbq *cmdiocb, case LSRJT_UNABLE_TPC: /* The driver has a VALID PLOGI but the rport has * rejected the PRLI - can't do it now. Delay - * for 1 second and try again - don't care about - * the explanation. + * for 1 second and try again. + * + * However, if explanation is REQ_UNSUPPORTED there's + * no point to retry PRLI. */ - if (cmd == ELS_CMD_PRLI || cmd == ELS_CMD_NVMEPRLI) { + if ((cmd == ELS_CMD_PRLI || cmd == ELS_CMD_NVMEPRLI) && + stat.un.b.lsRjtRsnCodeExp != + LSEXP_REQ_UNSUPPORTED) { delay = 1000; maxretry = lpfc_max_els_tries + 1; retry = 1; diff --git a/drivers/scsi/lpfc/lpfc_init.c b/drivers/scsi/lpfc/lpfc_init.c index c4a7e82d3ff2..c69725999315 100644 --- a/drivers/scsi/lpfc/lpfc_init.c +++ b/drivers/scsi/lpfc/lpfc_init.c @@ -4577,6 +4577,13 @@ static void lpfc_host_supported_speeds_set(struct Scsi_Host *shost) struct lpfc_hba *phba = vport->phba; fc_host_supported_speeds(shost) = 0; + /* + * Avoid reporting supported link speed for FCoE as it can't be + * controlled via FCoE. + */ + if (phba->hba_flag & HBA_FCOE_MODE) + return; + if (phba->lmt & LMT_128Gb) fc_host_supported_speeds(shost) |= FC_PORTSPEED_128GBIT; if (phba->lmt & LMT_64Gb) @@ -4910,6 +4917,9 @@ lpfc_sli4_port_speed_parse(struct lpfc_hba *phba, uint32_t evt_code, case LPFC_ASYNC_LINK_SPEED_40GBPS: port_speed = 40000; break; + case LPFC_ASYNC_LINK_SPEED_100GBPS: + port_speed = 100000; + break; default: port_speed = 0; } @@ -8589,7 +8599,7 @@ lpfc_sli4_read_config(struct lpfc_hba *phba) "VPI(B:%d M:%d) " "VFI(B:%d M:%d) " "RPI(B:%d M:%d) " - "FCFI:%d EQ:%d CQ:%d WQ:%d RQ:%d\n", + "FCFI:%d EQ:%d CQ:%d WQ:%d RQ:%d lmt:x%x\n", phba->sli4_hba.extents_in_use, phba->sli4_hba.max_cfg_param.xri_base, phba->sli4_hba.max_cfg_param.max_xri, @@ -8603,7 +8613,8 @@ lpfc_sli4_read_config(struct lpfc_hba *phba) phba->sli4_hba.max_cfg_param.max_eq, phba->sli4_hba.max_cfg_param.max_cq, phba->sli4_hba.max_cfg_param.max_wq, - phba->sli4_hba.max_cfg_param.max_rq); + phba->sli4_hba.max_cfg_param.max_rq, + phba->lmt); /* * Calculate queue resources based on how @@ -8626,7 +8637,8 @@ lpfc_sli4_read_config(struct lpfc_hba *phba) if ((phba->cfg_irq_chann > qmin) || (phba->cfg_hdw_queue > qmin)) { lpfc_printf_log(phba, KERN_ERR, LOG_TRACE_EVENT, - "2005 Reducing Queues: " + "2005 Reducing Queues - " + "FW resource limitation: " "WQ %d CQ %d EQ %d: min %d: " "IRQ %d HDWQ %d\n", phba->sli4_hba.max_cfg_param.max_wq, @@ -14100,17 +14112,18 @@ lpfc_init(void) printk(KERN_ERR "Could not register lpfcmgmt device, " "misc_register returned with status %d", error); + error = -ENOMEM; lpfc_transport_functions.vport_create = lpfc_vport_create; lpfc_transport_functions.vport_delete = lpfc_vport_delete; lpfc_transport_template = fc_attach_transport(&lpfc_transport_functions); if (lpfc_transport_template == NULL) - return -ENOMEM; + goto unregister; lpfc_vport_transport_template = fc_attach_transport(&lpfc_vport_transport_functions); if (lpfc_vport_transport_template == NULL) { fc_release_transport(lpfc_transport_template); - return -ENOMEM; + goto unregister; } lpfc_nvme_cmd_template(); lpfc_nvmet_cmd_template(); @@ -14136,6 +14149,8 @@ unwind: cpuhp_failure: fc_release_transport(lpfc_transport_template); fc_release_transport(lpfc_vport_transport_template); +unregister: + misc_deregister(&lpfc_mgmt_dev); return error; } diff --git a/drivers/scsi/lpfc/lpfc_nportdisc.c b/drivers/scsi/lpfc/lpfc_nportdisc.c index e4c710fe0245..cad53d19cb25 100644 --- a/drivers/scsi/lpfc/lpfc_nportdisc.c +++ b/drivers/scsi/lpfc/lpfc_nportdisc.c @@ -1745,7 +1745,13 @@ lpfc_cmpl_adisc_adisc_issue(struct lpfc_vport *vport, } } - if (ndlp->nlp_type & NLP_FCP_TARGET) { + if (ndlp->nlp_type & NLP_FCP_TARGET) + ndlp->nlp_fc4_type |= NLP_FC4_FCP; + + if (ndlp->nlp_type & NLP_NVME_TARGET) + ndlp->nlp_fc4_type |= NLP_FC4_NVME; + + if (ndlp->nlp_type & (NLP_FCP_TARGET | NLP_NVME_TARGET)) { ndlp->nlp_prev_state = NLP_STE_ADISC_ISSUE; lpfc_nlp_set_state(vport, ndlp, NLP_STE_MAPPED_NODE); } else { diff --git a/drivers/scsi/lpfc/lpfc_nvmet.c b/drivers/scsi/lpfc/lpfc_nvmet.c index a4430aeeb04a..d4ade7cdb93a 100644 --- a/drivers/scsi/lpfc/lpfc_nvmet.c +++ b/drivers/scsi/lpfc/lpfc_nvmet.c @@ -2110,7 +2110,7 @@ lpfc_nvmet_destroy_targetport(struct lpfc_hba *phba) } tgtp->tport_unreg_cmp = &tport_unreg_cmp; nvmet_fc_unregister_targetport(phba->targetport); - if (!wait_for_completion_timeout(tgtp->tport_unreg_cmp, + if (!wait_for_completion_timeout(&tport_unreg_cmp, msecs_to_jiffies(LPFC_NVMET_WAIT_TMO))) lpfc_printf_log(phba, KERN_ERR, LOG_TRACE_EVENT, "6179 Unreg targetport x%px timeout " diff --git a/drivers/scsi/lpfc/lpfc_sli.c b/drivers/scsi/lpfc/lpfc_sli.c index 8582b51b0613..4cd7ded656b7 100644 --- a/drivers/scsi/lpfc/lpfc_sli.c +++ b/drivers/scsi/lpfc/lpfc_sli.c @@ -13650,7 +13650,11 @@ lpfc_sli4_sp_handle_rcqe(struct lpfc_hba *phba, struct lpfc_rcqe *rcqe) fc_hdr->fh_r_ctl == FC_RCTL_DD_UNSOL_DATA) { spin_unlock_irqrestore(&phba->hbalock, iflags); /* Handle MDS Loopback frames */ - lpfc_sli4_handle_mds_loopback(phba->pport, dma_buf); + if (!(phba->pport->load_flag & FC_UNLOADING)) + lpfc_sli4_handle_mds_loopback(phba->pport, + dma_buf); + else + lpfc_in_buf_free(phba, &dma_buf->dbuf); break; } @@ -18363,7 +18367,10 @@ lpfc_sli4_handle_received_buffer(struct lpfc_hba *phba, fc_hdr->fh_r_ctl == FC_RCTL_DD_UNSOL_DATA) { vport = phba->pport; /* Handle MDS Loopback frames */ - lpfc_sli4_handle_mds_loopback(vport, dmabuf); + if (!(phba->pport->load_flag & FC_UNLOADING)) + lpfc_sli4_handle_mds_loopback(vport, dmabuf); + else + lpfc_in_buf_free(phba, &dmabuf->dbuf); return; } diff --git a/drivers/scsi/lpfc/lpfc_version.h b/drivers/scsi/lpfc/lpfc_version.h index 1987c6666279..20adec4387f0 100644 --- a/drivers/scsi/lpfc/lpfc_version.h +++ b/drivers/scsi/lpfc/lpfc_version.h @@ -20,7 +20,7 @@ * included with this package. * *******************************************************************/ -#define LPFC_DRIVER_VERSION "12.8.0.2" +#define LPFC_DRIVER_VERSION "12.8.0.3" #define LPFC_DRIVER_NAME "lpfc" /* Used for SLI 2/3 */ diff --git a/drivers/scsi/scsi_transport_sas.c b/drivers/scsi/scsi_transport_sas.c index e443dee43bcf..c9abed8429c9 100644 --- a/drivers/scsi/scsi_transport_sas.c +++ b/drivers/scsi/scsi_transport_sas.c @@ -1526,7 +1526,7 @@ int sas_rphy_add(struct sas_rphy *rphy) list_add_tail(&rphy->list, &sas_host->rphy_list); if (identify->device_type == SAS_END_DEVICE && (identify->target_port_protocols & - (SAS_PROTOCOL_SSP|SAS_PROTOCOL_STP|SAS_PROTOCOL_SATA))) + (SAS_PROTOCOL_SSP | SAS_PROTOCOL_STP | SAS_PROTOCOL_SATA))) rphy->scsi_target_id = sas_host->next_target_id++; else if (identify->device_type == SAS_END_DEVICE) rphy->scsi_target_id = -1; diff --git a/drivers/scsi/sd.c b/drivers/scsi/sd.c index acde0ca35769..95018e650f2d 100644 --- a/drivers/scsi/sd.c +++ b/drivers/scsi/sd.c @@ -2578,8 +2578,6 @@ sd_print_capacity(struct scsi_disk *sdkp, sd_printk(KERN_NOTICE, sdkp, "%u-byte physical blocks\n", sdkp->physical_block_size); - - sd_zbc_print_zones(sdkp); } /* called with buffer of length 512 */ @@ -3220,6 +3218,14 @@ static int sd_revalidate_disk(struct gendisk *disk) sd_config_write_same(sdkp); kfree(buffer); + /* + * For a zoned drive, revalidating the zones can be done only once + * the gendisk capacity is set. So if this fails, set back the gendisk + * capacity to 0. + */ + if (sd_zbc_revalidate_zones(sdkp)) + set_capacity_revalidate_and_notify(disk, 0, false); + out: return 0; } diff --git a/drivers/scsi/sd.h b/drivers/scsi/sd.h index 27c0f4e9b1d4..4933e7daf17d 100644 --- a/drivers/scsi/sd.h +++ b/drivers/scsi/sd.h @@ -75,7 +75,9 @@ struct scsi_disk { struct opal_dev *opal_dev; #ifdef CONFIG_BLK_DEV_ZONED u32 nr_zones; + u32 rev_nr_zones; u32 zone_blocks; + u32 rev_zone_blocks; u32 zones_optimal_open; u32 zones_optimal_nonseq; u32 zones_max_open; @@ -215,8 +217,8 @@ static inline int sd_is_zoned(struct scsi_disk *sdkp) int sd_zbc_init_disk(struct scsi_disk *sdkp); void sd_zbc_release_disk(struct scsi_disk *sdkp); -extern int sd_zbc_read_zones(struct scsi_disk *sdkp, unsigned char *buffer); -extern void sd_zbc_print_zones(struct scsi_disk *sdkp); +int sd_zbc_read_zones(struct scsi_disk *sdkp, unsigned char *buffer); +int sd_zbc_revalidate_zones(struct scsi_disk *sdkp); blk_status_t sd_zbc_setup_zone_mgmt_cmnd(struct scsi_cmnd *cmd, unsigned char op, bool all); unsigned int sd_zbc_complete(struct scsi_cmnd *cmd, unsigned int good_bytes, @@ -242,7 +244,10 @@ static inline int sd_zbc_read_zones(struct scsi_disk *sdkp, return 0; } -static inline void sd_zbc_print_zones(struct scsi_disk *sdkp) {} +static inline int sd_zbc_revalidate_zones(struct scsi_disk *sdkp) +{ + return 0; +} static inline blk_status_t sd_zbc_setup_zone_mgmt_cmnd(struct scsi_cmnd *cmd, unsigned char op, diff --git a/drivers/scsi/sd_zbc.c b/drivers/scsi/sd_zbc.c index 4717e79bff55..0e94ff056bff 100644 --- a/drivers/scsi/sd_zbc.c +++ b/drivers/scsi/sd_zbc.c @@ -634,6 +634,23 @@ static int sd_zbc_check_capacity(struct scsi_disk *sdkp, unsigned char *buf, return 0; } +static void sd_zbc_print_zones(struct scsi_disk *sdkp) +{ + if (!sd_is_zoned(sdkp) || !sdkp->capacity) + return; + + if (sdkp->capacity & (sdkp->zone_blocks - 1)) + sd_printk(KERN_NOTICE, sdkp, + "%u zones of %u logical blocks + 1 runt zone\n", + sdkp->nr_zones - 1, + sdkp->zone_blocks); + else + sd_printk(KERN_NOTICE, sdkp, + "%u zones of %u logical blocks\n", + sdkp->nr_zones, + sdkp->zone_blocks); +} + static void sd_zbc_revalidate_zones_cb(struct gendisk *disk) { struct scsi_disk *sdkp = scsi_disk(disk); @@ -641,36 +658,31 @@ static void sd_zbc_revalidate_zones_cb(struct gendisk *disk) swap(sdkp->zones_wp_offset, sdkp->rev_wp_offset); } -static int sd_zbc_revalidate_zones(struct scsi_disk *sdkp, - u32 zone_blocks, - unsigned int nr_zones) +int sd_zbc_revalidate_zones(struct scsi_disk *sdkp) { struct gendisk *disk = sdkp->disk; + struct request_queue *q = disk->queue; + u32 zone_blocks = sdkp->rev_zone_blocks; + unsigned int nr_zones = sdkp->rev_nr_zones; + u32 max_append; int ret = 0; + if (!sd_is_zoned(sdkp)) + return 0; + /* * Make sure revalidate zones are serialized to ensure exclusive * updates of the scsi disk data. */ mutex_lock(&sdkp->rev_mutex); - /* - * Revalidate the disk zones to update the device request queue zone - * bitmaps and the zone write pointer offset array. Do this only once - * the device capacity is set on the second revalidate execution for - * disk scan or if something changed when executing a normal revalidate. - */ - if (sdkp->first_scan) { - sdkp->zone_blocks = zone_blocks; - sdkp->nr_zones = nr_zones; - goto unlock; - } - if (sdkp->zone_blocks == zone_blocks && sdkp->nr_zones == nr_zones && disk->queue->nr_zones == nr_zones) goto unlock; + sdkp->zone_blocks = zone_blocks; + sdkp->nr_zones = nr_zones; sdkp->rev_wp_offset = kvcalloc(nr_zones, sizeof(u32), GFP_NOIO); if (!sdkp->rev_wp_offset) { ret = -ENOMEM; @@ -682,6 +694,21 @@ static int sd_zbc_revalidate_zones(struct scsi_disk *sdkp, kvfree(sdkp->rev_wp_offset); sdkp->rev_wp_offset = NULL; + if (ret) { + sdkp->zone_blocks = 0; + sdkp->nr_zones = 0; + sdkp->capacity = 0; + goto unlock; + } + + max_append = min_t(u32, logical_to_sectors(sdkp->device, zone_blocks), + q->limits.max_segments << (PAGE_SHIFT - 9)); + max_append = min_t(u32, max_append, queue_max_hw_sectors(q)); + + blk_queue_max_zone_append_sectors(q, max_append); + + sd_zbc_print_zones(sdkp); + unlock: mutex_unlock(&sdkp->rev_mutex); @@ -694,7 +721,6 @@ int sd_zbc_read_zones(struct scsi_disk *sdkp, unsigned char *buf) struct request_queue *q = disk->queue; unsigned int nr_zones; u32 zone_blocks = 0; - u32 max_append; int ret; if (!sd_is_zoned(sdkp)) @@ -728,22 +754,8 @@ int sd_zbc_read_zones(struct scsi_disk *sdkp, unsigned char *buf) sdkp->device->use_16_for_rw = 1; sdkp->device->use_10_for_rw = 0; - ret = sd_zbc_revalidate_zones(sdkp, zone_blocks, nr_zones); - if (ret) - goto err; - - /* - * On the first scan 'chunk_sectors' isn't setup yet, so calling - * blk_queue_max_zone_append_sectors() will result in a WARN(). Defer - * this setting to the second scan. - */ - if (sdkp->first_scan) - return 0; - - max_append = min_t(u32, logical_to_sectors(sdkp->device, zone_blocks), - q->limits.max_segments << (PAGE_SHIFT - 9)); - - blk_queue_max_zone_append_sectors(q, max_append); + sdkp->rev_nr_zones = nr_zones; + sdkp->rev_zone_blocks = zone_blocks; return 0; @@ -753,23 +765,6 @@ err: return ret; } -void sd_zbc_print_zones(struct scsi_disk *sdkp) -{ - if (!sd_is_zoned(sdkp) || !sdkp->capacity) - return; - - if (sdkp->capacity & (sdkp->zone_blocks - 1)) - sd_printk(KERN_NOTICE, sdkp, - "%u zones of %u logical blocks + 1 runt zone\n", - sdkp->nr_zones - 1, - sdkp->zone_blocks); - else - sd_printk(KERN_NOTICE, sdkp, - "%u zones of %u logical blocks\n", - sdkp->nr_zones, - sdkp->zone_blocks); -} - int sd_zbc_init_disk(struct scsi_disk *sdkp) { if (!sd_is_zoned(sdkp)) diff --git a/drivers/target/iscsi/iscsi_target_transport.c b/drivers/target/iscsi/iscsi_target_transport.c index 036940518bfe..27c85f260459 100644 --- a/drivers/target/iscsi/iscsi_target_transport.c +++ b/drivers/target/iscsi/iscsi_target_transport.c @@ -31,7 +31,7 @@ void iscsit_put_transport(struct iscsit_transport *t) module_put(t->owner); } -int iscsit_register_transport(struct iscsit_transport *t) +void iscsit_register_transport(struct iscsit_transport *t) { INIT_LIST_HEAD(&t->t_node); @@ -40,8 +40,6 @@ int iscsit_register_transport(struct iscsit_transport *t) mutex_unlock(&transport_mutex); pr_debug("Registered iSCSI transport: %s\n", t->name); - - return 0; } EXPORT_SYMBOL(iscsit_register_transport); diff --git a/include/target/iscsi/iscsi_transport.h b/include/target/iscsi/iscsi_transport.h index 75bee29fd7dd..b8feba7ffebc 100644 --- a/include/target/iscsi/iscsi_transport.h +++ b/include/target/iscsi/iscsi_transport.h @@ -43,7 +43,7 @@ static inline void *iscsit_priv_cmd(struct iscsi_cmd *cmd) * From iscsi_target_transport.c */ -extern int iscsit_register_transport(struct iscsit_transport *); +extern void iscsit_register_transport(struct iscsit_transport *); extern void iscsit_unregister_transport(struct iscsit_transport *); extern struct iscsit_transport *iscsit_get_transport(int); extern void iscsit_put_transport(struct iscsit_transport *); |