diff mbox series

[v2,2/7] scsi: NCR5380: Always re-enable reselection interrupt

Message ID 61f0c0f6aaf8fa96bf3dade5475615b2cfbc8846.1560043151.git.fthain@telegraphics.com.au (mailing list archive)
State Mainlined
Commit 57f31326518e98ee4cabf9a04efe00ed57c54147
Headers show
Series NCR5380 drivers: fixes and other improvements | expand

Commit Message

Finn Thain June 9, 2019, 1:19 a.m. UTC
The reselection interrupt gets disabled during selection and must be
re-enabled when hostdata->connected becomes NULL. If it isn't re-enabled
a disconnected command may time-out or the target may wedge the bus while
trying to reselect the host. This can happen after a command is aborted.

Fix this by enabling the reselection interrupt in NCR5380_main() after
calls to NCR5380_select() and NCR5380_information_transfer() return.

Cc: Michael Schmitz <schmitzmic@gmail.com>
Cc: stable@vger.kernel.org # v4.9+
Fixes: 8b00c3d5d40d ("ncr5380: Implement new eh_abort_handler")
Tested-by: Stan Johnson <userm57@yahoo.com>
Signed-off-by: Finn Thain <fthain@telegraphics.com.au>
---
 drivers/scsi/NCR5380.c | 12 ++----------
 1 file changed, 2 insertions(+), 10 deletions(-)

Comments

Michael Schmitz June 11, 2019, 5:07 a.m. UTC | #1
Hi Finn,

IIRC I'd tested that change as well - didn't change broken target 
behaviour but no regressions in other respects. Add my tested-by if needed.

Cheers,

	Michael


Am 09.06.2019 um 13:19 schrieb Finn Thain:
> The reselection interrupt gets disabled during selection and must be
> re-enabled when hostdata->connected becomes NULL. If it isn't re-enabled
> a disconnected command may time-out or the target may wedge the bus while
> trying to reselect the host. This can happen after a command is aborted.
>
> Fix this by enabling the reselection interrupt in NCR5380_main() after
> calls to NCR5380_select() and NCR5380_information_transfer() return.
>
> Cc: Michael Schmitz <schmitzmic@gmail.com>
> Cc: stable@vger.kernel.org # v4.9+
> Fixes: 8b00c3d5d40d ("ncr5380: Implement new eh_abort_handler")
> Tested-by: Stan Johnson <userm57@yahoo.com>
> Signed-off-by: Finn Thain <fthain@telegraphics.com.au>
> ---
>  drivers/scsi/NCR5380.c | 12 ++----------
>  1 file changed, 2 insertions(+), 10 deletions(-)
>
> diff --git a/drivers/scsi/NCR5380.c b/drivers/scsi/NCR5380.c
> index fe0535affc14..08e3ea8159b3 100644
> --- a/drivers/scsi/NCR5380.c
> +++ b/drivers/scsi/NCR5380.c
> @@ -709,6 +709,8 @@ static void NCR5380_main(struct work_struct *work)
>  			NCR5380_information_transfer(instance);
>  			done = 0;
>  		}
> +		if (!hostdata->connected)
> +			NCR5380_write(SELECT_ENABLE_REG, hostdata->id_mask);
>  		spin_unlock_irq(&hostdata->lock);
>  		if (!done)
>  			cond_resched();
> @@ -1110,8 +1112,6 @@ static bool NCR5380_select(struct Scsi_Host *instance, struct scsi_cmnd *cmd)
>  		spin_lock_irq(&hostdata->lock);
>  		NCR5380_write(INITIATOR_COMMAND_REG, ICR_BASE);
>  		NCR5380_reselect(instance);
> -		if (!hostdata->connected)
> -			NCR5380_write(SELECT_ENABLE_REG, hostdata->id_mask);
>  		shost_printk(KERN_ERR, instance, "reselection after won arbitration?\n");
>  		goto out;
>  	}
> @@ -1119,7 +1119,6 @@ static bool NCR5380_select(struct Scsi_Host *instance, struct scsi_cmnd *cmd)
>  	if (err < 0) {
>  		spin_lock_irq(&hostdata->lock);
>  		NCR5380_write(INITIATOR_COMMAND_REG, ICR_BASE);
> -		NCR5380_write(SELECT_ENABLE_REG, hostdata->id_mask);
>
>  		/* Can't touch cmd if it has been reclaimed by the scsi ML */
>  		if (!hostdata->selecting)
> @@ -1157,7 +1156,6 @@ static bool NCR5380_select(struct Scsi_Host *instance, struct scsi_cmnd *cmd)
>  	if (err < 0) {
>  		shost_printk(KERN_ERR, instance, "select: REQ timeout\n");
>  		NCR5380_write(INITIATOR_COMMAND_REG, ICR_BASE);
> -		NCR5380_write(SELECT_ENABLE_REG, hostdata->id_mask);
>  		goto out;
>  	}
>  	if (!hostdata->selecting) {
> @@ -1826,9 +1824,6 @@ static void NCR5380_information_transfer(struct Scsi_Host *instance)
>  					 */
>  					NCR5380_write(TARGET_COMMAND_REG, 0);
>
> -					/* Enable reselect interrupts */
> -					NCR5380_write(SELECT_ENABLE_REG, hostdata->id_mask);
> -
>  					maybe_release_dma_irq(instance);
>  					return;
>  				case MESSAGE_REJECT:
> @@ -1860,8 +1855,6 @@ static void NCR5380_information_transfer(struct Scsi_Host *instance)
>  					 */
>  					NCR5380_write(TARGET_COMMAND_REG, 0);
>
> -					/* Enable reselect interrupts */
> -					NCR5380_write(SELECT_ENABLE_REG, hostdata->id_mask);
>  #ifdef SUN3_SCSI_VME
>  					dregs->csr |= CSR_DMA_ENABLE;
>  #endif
> @@ -1964,7 +1957,6 @@ static void NCR5380_information_transfer(struct Scsi_Host *instance)
>  					cmd->result = DID_ERROR << 16;
>  					complete_cmd(instance, cmd);
>  					maybe_release_dma_irq(instance);
> -					NCR5380_write(SELECT_ENABLE_REG, hostdata->id_mask);
>  					return;
>  				}
>  				msgout = NOP;
>
Finn Thain June 11, 2019, 9:33 a.m. UTC | #2
On Tue, 11 Jun 2019, Michael Schmitz wrote:

> Hi Finn,
> 
> IIRC I'd tested that change as well - didn't change broken target 
> behaviour but no regressions in other respects. Add my tested-by if 
> needed.
> 

Unfortunately I can't confirm that this is the same patch as the one you 
tested as I no longer have that commit. But Stan did test a wide variety 
of targets and I'm confident that the reselection code path was covered.
Michael Schmitz June 11, 2019, 11:46 p.m. UTC | #3
Hi Finn,

On 11/06/19 9:33 PM, Finn Thain wrote:
> On Tue, 11 Jun 2019, Michael Schmitz wrote:
>
>> Hi Finn,
>>
>> IIRC I'd tested that change as well - didn't change broken target
>> behaviour but no regressions in other respects. Add my tested-by if
>> needed.
>>
> Unfortunately I can't confirm that this is the same patch as the one you
> tested as I no longer have that commit. But Stan did test a wide variety
> of targets and I'm confident that the reselection code path was covered.
>
No matter - patch applied cleanly to what I'm running on my Falcon, and 
works just fine for now (stresstest will take a few hours to complete). 
And that'll thoroughly exercise the reselection code path, from what 
we've seen before.

Cheers,

     Michael
Martin K. Petersen June 19, 2019, 12:47 a.m. UTC | #4
Michael,

> No matter - patch applied cleanly to what I'm running on my Falcon,
> and works just fine for now (stresstest will take a few hours to
> complete). And that'll thoroughly exercise the reselection code path,
> from what we've seen before.

How did it go?
Michael Schmitz June 19, 2019, 1:47 a.m. UTC | #5
Martin,

On 19/06/19 12:47 PM, Martin K. Petersen wrote:
> Michael,
>
>> No matter - patch applied cleanly to what I'm running on my Falcon,
>> and works just fine for now (stresstest will take a few hours to
>> complete). And that'll thoroughly exercise the reselection code path,
>> from what we've seen before.
> How did it go?


Just fine - repeated with different settings for can_queue and 
cmd_per_lun, with not a single hitch. No regression at all.

Cheers,

     Michael



>
diff mbox series

Patch

diff --git a/drivers/scsi/NCR5380.c b/drivers/scsi/NCR5380.c
index fe0535affc14..08e3ea8159b3 100644
--- a/drivers/scsi/NCR5380.c
+++ b/drivers/scsi/NCR5380.c
@@ -709,6 +709,8 @@  static void NCR5380_main(struct work_struct *work)
 			NCR5380_information_transfer(instance);
 			done = 0;
 		}
+		if (!hostdata->connected)
+			NCR5380_write(SELECT_ENABLE_REG, hostdata->id_mask);
 		spin_unlock_irq(&hostdata->lock);
 		if (!done)
 			cond_resched();
@@ -1110,8 +1112,6 @@  static bool NCR5380_select(struct Scsi_Host *instance, struct scsi_cmnd *cmd)
 		spin_lock_irq(&hostdata->lock);
 		NCR5380_write(INITIATOR_COMMAND_REG, ICR_BASE);
 		NCR5380_reselect(instance);
-		if (!hostdata->connected)
-			NCR5380_write(SELECT_ENABLE_REG, hostdata->id_mask);
 		shost_printk(KERN_ERR, instance, "reselection after won arbitration?\n");
 		goto out;
 	}
@@ -1119,7 +1119,6 @@  static bool NCR5380_select(struct Scsi_Host *instance, struct scsi_cmnd *cmd)
 	if (err < 0) {
 		spin_lock_irq(&hostdata->lock);
 		NCR5380_write(INITIATOR_COMMAND_REG, ICR_BASE);
-		NCR5380_write(SELECT_ENABLE_REG, hostdata->id_mask);
 
 		/* Can't touch cmd if it has been reclaimed by the scsi ML */
 		if (!hostdata->selecting)
@@ -1157,7 +1156,6 @@  static bool NCR5380_select(struct Scsi_Host *instance, struct scsi_cmnd *cmd)
 	if (err < 0) {
 		shost_printk(KERN_ERR, instance, "select: REQ timeout\n");
 		NCR5380_write(INITIATOR_COMMAND_REG, ICR_BASE);
-		NCR5380_write(SELECT_ENABLE_REG, hostdata->id_mask);
 		goto out;
 	}
 	if (!hostdata->selecting) {
@@ -1826,9 +1824,6 @@  static void NCR5380_information_transfer(struct Scsi_Host *instance)
 					 */
 					NCR5380_write(TARGET_COMMAND_REG, 0);
 
-					/* Enable reselect interrupts */
-					NCR5380_write(SELECT_ENABLE_REG, hostdata->id_mask);
-
 					maybe_release_dma_irq(instance);
 					return;
 				case MESSAGE_REJECT:
@@ -1860,8 +1855,6 @@  static void NCR5380_information_transfer(struct Scsi_Host *instance)
 					 */
 					NCR5380_write(TARGET_COMMAND_REG, 0);
 
-					/* Enable reselect interrupts */
-					NCR5380_write(SELECT_ENABLE_REG, hostdata->id_mask);
 #ifdef SUN3_SCSI_VME
 					dregs->csr |= CSR_DMA_ENABLE;
 #endif
@@ -1964,7 +1957,6 @@  static void NCR5380_information_transfer(struct Scsi_Host *instance)
 					cmd->result = DID_ERROR << 16;
 					complete_cmd(instance, cmd);
 					maybe_release_dma_irq(instance);
-					NCR5380_write(SELECT_ENABLE_REG, hostdata->id_mask);
 					return;
 				}
 				msgout = NOP;