diff mbox series

[v2,2/7] qla2xxx: Fix response queue handler reading stale packets

Message ID 20220826102559.17474-3-njavali@marvell.com
State New
Headers show
Series qla2xxx driver features | expand

Commit Message

Nilesh Javali Aug. 26, 2022, 10:25 a.m. UTC
From: Arun Easi <aeasi@marvell.com>

On some platforms, the current logic of relying on finding new packet
solely based on signature pattern can lead to driver reading stale
packets. Though this is a bug in those platforms, reduce such exposures by
limiting reading packets until the IN pointer.

Cc: stable@vger.kernel.org
Signed-off-by: Arun Easi <aeasi@marvell.com>
Signed-off-by: Nilesh Javali <njavali@marvell.com>
---
 drivers/scsi/qla2xxx/qla_isr.c | 17 +++++++++++++++--
 1 file changed, 15 insertions(+), 2 deletions(-)

Comments

Himanshu Madhani Aug. 29, 2022, 4:10 p.m. UTC | #1
> On Aug 26, 2022, at 3:25 AM, Nilesh Javali <njavali@marvell.com> wrote:
> 
> From: Arun Easi <aeasi@marvell.com>
> 
> On some platforms, the current logic of relying on finding new packet
> solely based on signature pattern can lead to driver reading stale
> packets. Though this is a bug in those platforms, reduce such exposures by
> limiting reading packets until the IN pointer.
> 
> Cc: stable@vger.kernel.org
> Signed-off-by: Arun Easi <aeasi@marvell.com>
> Signed-off-by: Nilesh Javali <njavali@marvell.com>
> ---
> drivers/scsi/qla2xxx/qla_isr.c | 17 +++++++++++++++--
> 1 file changed, 15 insertions(+), 2 deletions(-)
> 
> diff --git a/drivers/scsi/qla2xxx/qla_isr.c b/drivers/scsi/qla2xxx/qla_isr.c
> index ede76357ccb6..e19fde304e5c 100644
> --- a/drivers/scsi/qla2xxx/qla_isr.c
> +++ b/drivers/scsi/qla2xxx/qla_isr.c
> @@ -3763,7 +3763,8 @@ void qla24xx_process_response_queue(struct scsi_qla_host *vha,
> 	struct qla_hw_data *ha = vha->hw;
> 	struct purex_entry_24xx *purex_entry;
> 	struct purex_item *pure_item;
> -	u16 cur_ring_index;
> +	u16 rsp_in = 0, cur_ring_index;
> +	int is_shadow_hba;
> 
> 	if (!ha->flags.fw_started)
> 		return;
> @@ -3773,7 +3774,18 @@ void qla24xx_process_response_queue(struct scsi_qla_host *vha,
> 		qla_cpu_update(rsp->qpair, smp_processor_id());
> 	}
> 
> -	while (rsp->ring_ptr->signature != RESPONSE_PROCESSED) {
> +#define __update_rsp_in(_is_shadow_hba, _rsp, _rsp_in)			\
> +	do {								\
> +		_rsp_in = _is_shadow_hba ? *(_rsp)->in_ptr :		\
> +				rd_reg_dword_relaxed((_rsp)->rsp_q_in);	\
> +	} while (0)
> +
> +	is_shadow_hba = IS_SHADOW_REG_CAPABLE(ha);
> +
> +	__update_rsp_in(is_shadow_hba, rsp, rsp_in);
> +
> +	while (rsp->ring_index != rsp_in &&
> +		       rsp->ring_ptr->signature != RESPONSE_PROCESSED) {
> 		pkt = (struct sts_entry_24xx *)rsp->ring_ptr;
> 		cur_ring_index = rsp->ring_index;
> 
> @@ -3887,6 +3899,7 @@ void qla24xx_process_response_queue(struct scsi_qla_host *vha,
> 				}
> 				pure_item = qla27xx_copy_fpin_pkt(vha,
> 							  (void **)&pkt, &rsp);
> +				__update_rsp_in(is_shadow_hba, rsp, rsp_in);
> 				if (!pure_item)
> 					break;
> 				qla24xx_queue_purex_item(vha, pure_item,
> -- 
> 2.19.0.rc0
> 

Reviewed-by: Himanshu Madhani <himanshu.madhani@oracle.com>
diff mbox series

Patch

diff --git a/drivers/scsi/qla2xxx/qla_isr.c b/drivers/scsi/qla2xxx/qla_isr.c
index ede76357ccb6..e19fde304e5c 100644
--- a/drivers/scsi/qla2xxx/qla_isr.c
+++ b/drivers/scsi/qla2xxx/qla_isr.c
@@ -3763,7 +3763,8 @@  void qla24xx_process_response_queue(struct scsi_qla_host *vha,
 	struct qla_hw_data *ha = vha->hw;
 	struct purex_entry_24xx *purex_entry;
 	struct purex_item *pure_item;
-	u16 cur_ring_index;
+	u16 rsp_in = 0, cur_ring_index;
+	int is_shadow_hba;
 
 	if (!ha->flags.fw_started)
 		return;
@@ -3773,7 +3774,18 @@  void qla24xx_process_response_queue(struct scsi_qla_host *vha,
 		qla_cpu_update(rsp->qpair, smp_processor_id());
 	}
 
-	while (rsp->ring_ptr->signature != RESPONSE_PROCESSED) {
+#define __update_rsp_in(_is_shadow_hba, _rsp, _rsp_in)			\
+	do {								\
+		_rsp_in = _is_shadow_hba ? *(_rsp)->in_ptr :		\
+				rd_reg_dword_relaxed((_rsp)->rsp_q_in);	\
+	} while (0)
+
+	is_shadow_hba = IS_SHADOW_REG_CAPABLE(ha);
+
+	__update_rsp_in(is_shadow_hba, rsp, rsp_in);
+
+	while (rsp->ring_index != rsp_in &&
+		       rsp->ring_ptr->signature != RESPONSE_PROCESSED) {
 		pkt = (struct sts_entry_24xx *)rsp->ring_ptr;
 		cur_ring_index = rsp->ring_index;
 
@@ -3887,6 +3899,7 @@  void qla24xx_process_response_queue(struct scsi_qla_host *vha,
 				}
 				pure_item = qla27xx_copy_fpin_pkt(vha,
 							  (void **)&pkt, &rsp);
+				__update_rsp_in(is_shadow_hba, rsp, rsp_in);
 				if (!pure_item)
 					break;
 				qla24xx_queue_purex_item(vha, pure_item,