summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorJames Bottomley <James.Bottomley@steeleye.com>2007-07-30 09:52:25 -0500
committerJames Bottomley <jejb@mulgrave.localdomain>2007-07-31 10:44:26 -0500
commit142009a3df39ecd4e96601d8bdabbe0c5f6e2f4e (patch)
treef5a546967d2d9932fae7c96b82146cf2020b22df
parent28f85009e0cf6a5232cd285131eac3dfe26d9e3a (diff)
downloadlinux-3.10-142009a3df39ecd4e96601d8bdabbe0c5f6e2f4e.tar.gz
linux-3.10-142009a3df39ecd4e96601d8bdabbe0c5f6e2f4e.tar.bz2
linux-3.10-142009a3df39ecd4e96601d8bdabbe0c5f6e2f4e.zip
[SCSI] aic7xxx: cap maxsync according to correct card limits
Not doing this can cause cards less than u160 capable to send out PPR offers to devices they can't then deliver on ... causing some devices to get a bit confused. Fix by capping the start syncrate at the appropriate level according to the card capabilities. Signed-off-by: James Bottomley <James.Bottomley@SteelEye.com>
-rw-r--r--drivers/scsi/aic7xxx/aic7xxx_core.c22
1 files changed, 21 insertions, 1 deletions
diff --git a/drivers/scsi/aic7xxx/aic7xxx_core.c b/drivers/scsi/aic7xxx/aic7xxx_core.c
index 75733b09f27..f350b5e89e7 100644
--- a/drivers/scsi/aic7xxx/aic7xxx_core.c
+++ b/drivers/scsi/aic7xxx/aic7xxx_core.c
@@ -1701,7 +1701,16 @@ ahc_find_syncrate(struct ahc_softc *ahc, u_int *period,
if ((*ppr_options & MSG_EXT_PPR_DT_REQ) == 0
&& maxsync < AHC_SYNCRATE_ULTRA2)
maxsync = AHC_SYNCRATE_ULTRA2;
-
+
+ /* Now set the maxsync based on the card capabilities
+ * DT is already done above */
+ if ((ahc->features & (AHC_DT | AHC_ULTRA2)) == 0
+ && maxsync < AHC_SYNCRATE_ULTRA)
+ maxsync = AHC_SYNCRATE_ULTRA;
+ if ((ahc->features & (AHC_DT | AHC_ULTRA2 | AHC_ULTRA)) == 0
+ && maxsync < AHC_SYNCRATE_FAST)
+ maxsync = AHC_SYNCRATE_FAST;
+
for (syncrate = &ahc_syncrates[maxsync];
syncrate->rate != NULL;
syncrate++) {
@@ -1765,6 +1774,17 @@ ahc_find_period(struct ahc_softc *ahc, u_int scsirate, u_int maxsync)
else
scsirate &= SXFR;
+ /* now set maxsync based on card capabilities */
+ if ((ahc->features & AHC_DT) == 0 && maxsync < AHC_SYNCRATE_ULTRA2)
+ maxsync = AHC_SYNCRATE_ULTRA2;
+ if ((ahc->features & (AHC_DT | AHC_ULTRA2)) == 0
+ && maxsync < AHC_SYNCRATE_ULTRA)
+ maxsync = AHC_SYNCRATE_ULTRA;
+ if ((ahc->features & (AHC_DT | AHC_ULTRA2 | AHC_ULTRA)) == 0
+ && maxsync < AHC_SYNCRATE_FAST)
+ maxsync = AHC_SYNCRATE_FAST;
+
+
syncrate = &ahc_syncrates[maxsync];
while (syncrate->rate != NULL) {