diff options
author | Hannes Reinecke <hare@suse.de> | 2006-01-24 04:44:38 -0500 |
---|---|---|
committer | James Bottomley <jejb@mulgrave.(none)> | 2006-01-31 15:39:48 -0500 |
commit | 3fb086126462c2de06dddaec58981d8827be100d (patch) | |
tree | eaa3e79ef84f8a68246e0ba68a1d048b03e9acd4 | |
parent | 53467e636b7beb350c307cc88323aae4676577f2 (diff) |
[SCSI] aic79xx: SLOWCRC fix
This patch introduces the SLOWCRC handling for certain buggy chipsets.
Signed-off-by: James Bottomley <James.Bottomley@SteelEye.com>
-rw-r--r-- | drivers/scsi/aic7xxx/aic79xx.h | 3 | ||||
-rw-r--r-- | drivers/scsi/aic7xxx/aic79xx_core.c | 21 | ||||
-rw-r--r-- | drivers/scsi/aic7xxx/aic79xx_osm.c | 17 | ||||
-rw-r--r-- | drivers/scsi/aic7xxx/aic79xx_pci.c | 11 |
4 files changed, 49 insertions, 3 deletions
diff --git a/drivers/scsi/aic7xxx/aic79xx.h b/drivers/scsi/aic7xxx/aic79xx.h index 2cfdbef447db..1d11f7e77564 100644 --- a/drivers/scsi/aic7xxx/aic79xx.h +++ b/drivers/scsi/aic7xxx/aic79xx.h | |||
@@ -37,7 +37,7 @@ | |||
37 | * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE | 37 | * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE |
38 | * POSSIBILITY OF SUCH DAMAGES. | 38 | * POSSIBILITY OF SUCH DAMAGES. |
39 | * | 39 | * |
40 | * $Id: //depot/aic7xxx/aic7xxx/aic79xx.h#108 $ | 40 | * $Id: //depot/aic7xxx/aic7xxx/aic79xx.h#109 $ |
41 | * | 41 | * |
42 | * $FreeBSD$ | 42 | * $FreeBSD$ |
43 | */ | 43 | */ |
@@ -222,6 +222,7 @@ typedef enum { | |||
222 | typedef enum { | 222 | typedef enum { |
223 | AHD_FENONE = 0x00000, | 223 | AHD_FENONE = 0x00000, |
224 | AHD_WIDE = 0x00001,/* Wide Channel */ | 224 | AHD_WIDE = 0x00001,/* Wide Channel */ |
225 | AHD_AIC79XXB_SLOWCRC = 0x00002,/* SLOWCRC bit should be set */ | ||
225 | AHD_MULTI_FUNC = 0x00100,/* Multi-Function/Channel Device */ | 226 | AHD_MULTI_FUNC = 0x00100,/* Multi-Function/Channel Device */ |
226 | AHD_TARGETMODE = 0x01000,/* Has tested target mode support */ | 227 | AHD_TARGETMODE = 0x01000,/* Has tested target mode support */ |
227 | AHD_MULTIROLE = 0x02000,/* Space for two roles at a time */ | 228 | AHD_MULTIROLE = 0x02000,/* Space for two roles at a time */ |
diff --git a/drivers/scsi/aic7xxx/aic79xx_core.c b/drivers/scsi/aic7xxx/aic79xx_core.c index dfd4cc93c05c..6114b3e72caa 100644 --- a/drivers/scsi/aic7xxx/aic79xx_core.c +++ b/drivers/scsi/aic7xxx/aic79xx_core.c | |||
@@ -3332,6 +3332,15 @@ ahd_update_neg_table(struct ahd_softc *ahd, struct ahd_devinfo *devinfo, | |||
3332 | con_opts |= WIDEXFER; | 3332 | con_opts |= WIDEXFER; |
3333 | 3333 | ||
3334 | /* | 3334 | /* |
3335 | * Slow down our CRC interval to be | ||
3336 | * compatible with packetized U320 devices | ||
3337 | * that can't handle a CRC at full speed | ||
3338 | */ | ||
3339 | if (ahd->features & AHD_AIC79XXB_SLOWCRC) { | ||
3340 | con_opts |= ENSLOWCRC; | ||
3341 | } | ||
3342 | |||
3343 | /* | ||
3335 | * During packetized transfers, the target will | 3344 | * During packetized transfers, the target will |
3336 | * give us the oportunity to send command packets | 3345 | * give us the oportunity to send command packets |
3337 | * without us asserting attention. | 3346 | * without us asserting attention. |
@@ -6740,6 +6749,18 @@ ahd_chip_init(struct ahd_softc *ahd) | |||
6740 | 6749 | ||
6741 | ahd_loadseq(ahd); | 6750 | ahd_loadseq(ahd); |
6742 | ahd_set_modes(ahd, AHD_MODE_SCSI, AHD_MODE_SCSI); | 6751 | ahd_set_modes(ahd, AHD_MODE_SCSI, AHD_MODE_SCSI); |
6752 | |||
6753 | if (ahd->features & AHD_AIC79XXB_SLOWCRC) { | ||
6754 | u_int negodat3 = ahd_inb(ahd, NEGCONOPTS); | ||
6755 | |||
6756 | negodat3 |= ENSLOWCRC; | ||
6757 | ahd_outb(ahd, NEGCONOPTS, negodat3); | ||
6758 | negodat3 = ahd_inb(ahd, NEGCONOPTS); | ||
6759 | if (!(negodat3 & ENSLOWCRC)) | ||
6760 | printf("aic79xx: failed to set the SLOWCRC bit\n"); | ||
6761 | else | ||
6762 | printf("aic79xx: SLOWCRC bit set\n"); | ||
6763 | } | ||
6743 | } | 6764 | } |
6744 | 6765 | ||
6745 | /* | 6766 | /* |
diff --git a/drivers/scsi/aic7xxx/aic79xx_osm.c b/drivers/scsi/aic7xxx/aic79xx_osm.c index 2567e29960bd..815c06312c88 100644 --- a/drivers/scsi/aic7xxx/aic79xx_osm.c +++ b/drivers/scsi/aic7xxx/aic79xx_osm.c | |||
@@ -314,6 +314,21 @@ static uint32_t aic79xx_seltime; | |||
314 | */ | 314 | */ |
315 | uint32_t aic79xx_periodic_otag; | 315 | uint32_t aic79xx_periodic_otag; |
316 | 316 | ||
317 | /* Some storage boxes are using an LSI chip which has a bug making it | ||
318 | * impossible to use aic79xx Rev B chip in 320 speeds. The following | ||
319 | * storage boxes have been reported to be buggy: | ||
320 | * EonStor 3U 16-Bay: U16U-G3A3 | ||
321 | * EonStor 2U 12-Bay: U12U-G3A3 | ||
322 | * SentinelRAID: 2500F R5 / R6 | ||
323 | * SentinelRAID: 2500F R1 | ||
324 | * SentinelRAID: 2500F/1500F | ||
325 | * SentinelRAID: 150F | ||
326 | * | ||
327 | * To get around this LSI bug, you can set your board to 160 mode | ||
328 | * or you can enable the SLOWCRC bit. | ||
329 | */ | ||
330 | uint32_t aic79xx_slowcrc; | ||
331 | |||
317 | /* | 332 | /* |
318 | * Module information and settable options. | 333 | * Module information and settable options. |
319 | */ | 334 | */ |
@@ -343,6 +358,7 @@ MODULE_PARM_DESC(aic79xx, | |||
343 | " amplitude:<int> Set the signal amplitude (0-7).\n" | 358 | " amplitude:<int> Set the signal amplitude (0-7).\n" |
344 | " seltime:<int> Selection Timeout:\n" | 359 | " seltime:<int> Selection Timeout:\n" |
345 | " (0/256ms,1/128ms,2/64ms,3/32ms)\n" | 360 | " (0/256ms,1/128ms,2/64ms,3/32ms)\n" |
361 | " slowcrc Turn on the SLOWCRC bit (Rev B only)\n" | ||
346 | "\n" | 362 | "\n" |
347 | " Sample /etc/modprobe.conf line:\n" | 363 | " Sample /etc/modprobe.conf line:\n" |
348 | " Enable verbose logging\n" | 364 | " Enable verbose logging\n" |
@@ -1003,6 +1019,7 @@ aic79xx_setup(char *s) | |||
1003 | { "slewrate", NULL }, | 1019 | { "slewrate", NULL }, |
1004 | { "precomp", NULL }, | 1020 | { "precomp", NULL }, |
1005 | { "amplitude", NULL }, | 1021 | { "amplitude", NULL }, |
1022 | { "slowcrc", &aic79xx_slowcrc }, | ||
1006 | }; | 1023 | }; |
1007 | 1024 | ||
1008 | end = strchr(s, '\0'); | 1025 | end = strchr(s, '\0'); |
diff --git a/drivers/scsi/aic7xxx/aic79xx_pci.c b/drivers/scsi/aic7xxx/aic79xx_pci.c index 196a6344b037..757242e522c2 100644 --- a/drivers/scsi/aic7xxx/aic79xx_pci.c +++ b/drivers/scsi/aic7xxx/aic79xx_pci.c | |||
@@ -38,7 +38,7 @@ | |||
38 | * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE | 38 | * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE |
39 | * POSSIBILITY OF SUCH DAMAGES. | 39 | * POSSIBILITY OF SUCH DAMAGES. |
40 | * | 40 | * |
41 | * $Id: //depot/aic7xxx/aic7xxx/aic79xx_pci.c#89 $ | 41 | * $Id: //depot/aic7xxx/aic7xxx/aic79xx_pci.c#92 $ |
42 | */ | 42 | */ |
43 | 43 | ||
44 | #ifdef __linux__ | 44 | #ifdef __linux__ |
@@ -950,12 +950,19 @@ ahd_aic790X_setup(struct ahd_softc *ahd) | |||
950 | if ((ahd->flags & AHD_HP_BOARD) == 0) | 950 | if ((ahd->flags & AHD_HP_BOARD) == 0) |
951 | AHD_SET_SLEWRATE(ahd, AHD_SLEWRATE_DEF_REVA); | 951 | AHD_SET_SLEWRATE(ahd, AHD_SLEWRATE_DEF_REVA); |
952 | } else { | 952 | } else { |
953 | /* This is revision B and newer. */ | ||
954 | extern uint32_t aic79xx_slowcrc; | ||
953 | u_int devconfig1; | 955 | u_int devconfig1; |
954 | 956 | ||
955 | ahd->features |= AHD_RTI|AHD_NEW_IOCELL_OPTS | 957 | ahd->features |= AHD_RTI|AHD_NEW_IOCELL_OPTS |
956 | | AHD_NEW_DFCNTRL_OPTS|AHD_FAST_CDB_DELIVERY; | 958 | | AHD_NEW_DFCNTRL_OPTS|AHD_FAST_CDB_DELIVERY |
959 | | AHD_BUSFREEREV_BUG; | ||
957 | ahd->bugs |= AHD_LQOOVERRUN_BUG|AHD_EARLY_REQ_BUG; | 960 | ahd->bugs |= AHD_LQOOVERRUN_BUG|AHD_EARLY_REQ_BUG; |
958 | 961 | ||
962 | /* If the user requested the the SLOWCRC bit to be set. */ | ||
963 | if (aic79xx_slowcrc) | ||
964 | ahd->features |= AHD_AIC79XXB_SLOWCRC; | ||
965 | |||
959 | /* | 966 | /* |
960 | * Some issues have been resolved in the 7901B. | 967 | * Some issues have been resolved in the 7901B. |
961 | */ | 968 | */ |