summaryrefslogtreecommitdiffstats
path: root/drivers/ide
diff options
context:
space:
mode:
authorRalf Baechle <ralf@linux-mips.org>2000-06-19 22:45:37 +0000
committerRalf Baechle <ralf@linux-mips.org>2000-06-19 22:45:37 +0000
commit6d403070f28cd44860fdb3a53be5da0275c65cf4 (patch)
tree0d0e7fe7b5fb7568d19e11d7d862b77a866ce081 /drivers/ide
parentecf1bf5f6c2e668d03b0a9fb026db7aa41e292e1 (diff)
Merge with 2.4.0-test1-ac21 + pile of MIPS cleanups to make merging
possible. Chainsawed RM200 kernel to compile again. Jazz machine status unknown.
Diffstat (limited to 'drivers/ide')
-rw-r--r--drivers/ide/Config.in31
-rw-r--r--drivers/ide/Makefile24
-rw-r--r--drivers/ide/aec62xx.c28
-rw-r--r--drivers/ide/alim15x3.c50
-rw-r--r--drivers/ide/amd7409.c74
-rw-r--r--drivers/ide/cmd64x.c85
-rw-r--r--drivers/ide/cs5530.c4
-rw-r--r--drivers/ide/cy82c693.c4
-rw-r--r--drivers/ide/gayle.c24
-rw-r--r--drivers/ide/hd.c2
-rw-r--r--drivers/ide/hpt34x.c10
-rw-r--r--drivers/ide/hpt366.c436
-rw-r--r--drivers/ide/icside.c6
-rw-r--r--drivers/ide/ide-cd.c32
-rw-r--r--drivers/ide/ide-disk.c19
-rw-r--r--drivers/ide/ide-dma.c53
-rw-r--r--drivers/ide/ide-features.c48
-rw-r--r--drivers/ide/ide-geometry.c4
-rw-r--r--drivers/ide/ide-pci.c54
-rw-r--r--drivers/ide/ide-pmac.c6
-rw-r--r--drivers/ide/ide-probe.c6
-rw-r--r--drivers/ide/ide.c76
-rw-r--r--drivers/ide/ns87415.c2
-rw-r--r--drivers/ide/pdc202xx.c159
-rw-r--r--drivers/ide/piix.c35
-rw-r--r--drivers/ide/qd6580.c332
-rw-r--r--drivers/ide/sis5513.c22
-rw-r--r--drivers/ide/trm290.c4
-rw-r--r--drivers/ide/via82cxxx.c48
29 files changed, 1096 insertions, 582 deletions
diff --git a/drivers/ide/Config.in b/drivers/ide/Config.in
index b591b3563..2719f6f80 100644
--- a/drivers/ide/Config.in
+++ b/drivers/ide/Config.in
@@ -1,6 +1,8 @@
#
# IDE ATA ATAPI Block device driver configuration
#
+# Andre Hedrick <andre@linux-ide.org>
+#
mainmenu_option next_comment
comment 'IDE, ATA and ATAPI Block devices'
@@ -21,6 +23,9 @@ if [ "$CONFIG_BLK_DEV_IDE" != "n" ]; then
dep_mbool ' Seagate Vendor Specific' CONFIG_BLK_DEV_IDEDISK_SEAGATE $CONFIG_BLK_DEV_IDEDISK_VENDOR
dep_mbool ' Western Digital Vendor Specific' CONFIG_BLK_DEV_IDEDISK_WD $CONFIG_BLK_DEV_IDEDISK_VENDOR
+ define_bool CONFIG_BLK_DEV_COMMERIAL n
+ dep_mbool ' TiVo Commerial Application Specific' CONFIG_BLK_DEV_TIVO $CONFIG_BLK_DEV_COMMERIAL
+
dep_tristate ' PCMCIA IDE support' CONFIG_BLK_DEV_IDECS $CONFIG_BLK_DEV_IDE $CONFIG_PCMCIA
dep_tristate ' Include IDE/ATAPI CDROM support' CONFIG_BLK_DEV_IDECD $CONFIG_BLK_DEV_IDE
dep_tristate ' Include IDE/ATAPI TAPE support' CONFIG_BLK_DEV_IDETAPE $CONFIG_BLK_DEV_IDE
@@ -44,32 +49,28 @@ if [ "$CONFIG_BLK_DEV_IDE" != "n" ]; then
dep_bool ' ATA Work(s) In Progress (EXPERIMENTAL)' CONFIG_IDEDMA_PCI_WIP $CONFIG_BLK_DEV_IDEDMA_PCI $CONFIG_EXPERIMENTAL
dep_bool ' Good-Bad DMA Model-Firmware (WIP)' CONFIG_IDEDMA_NEW_DRIVE_LISTINGS $CONFIG_IDEDMA_PCI_WIP
dep_bool ' AEC62XX chipset support' CONFIG_BLK_DEV_AEC62XX $CONFIG_BLK_DEV_IDEDMA_PCI
- dep_mbool ' AEC62XX Tuning support (WIP)' CONFIG_AEC62XX_TUNING $CONFIG_BLK_DEV_AEC62XX $CONFIG_IDEDMA_PCI_WIP
+ dep_mbool ' AEC62XX Tuning support' CONFIG_AEC62XX_TUNING $CONFIG_BLK_DEV_AEC62XX
dep_bool ' ALI M15x3 chipset support' CONFIG_BLK_DEV_ALI15X3 $CONFIG_BLK_DEV_IDEDMA_PCI
dep_mbool ' ALI M15x3 WDC support (DANGEROUS)' CONFIG_WDC_ALI15X3 $CONFIG_BLK_DEV_ALI15X3
dep_bool ' AMD Viper support' CONFIG_BLK_DEV_AMD7409 $CONFIG_BLK_DEV_IDEDMA_PCI
dep_mbool ' AMD Viper ATA-66 Override (WIP)' CONFIG_AMD7409_OVERRIDE $CONFIG_BLK_DEV_AMD7409 $CONFIG_IDEDMA_PCI_WIP
dep_bool ' CMD64X chipset support' CONFIG_BLK_DEV_CMD64X $CONFIG_BLK_DEV_IDEDMA_PCI
- dep_mbool ' CMD64X chipset RAID (WIP)' CONFIG_CMD64X_RAID $CONFIG_BLK_DEV_CMD64X $CONFIG_IDEDMA_PCI_WIP
- dep_bool ' CY82C693 chipset support (EXPERIMENTAL)' CONFIG_BLK_DEV_CY82C693 $CONFIG_BLK_DEV_IDEDMA_PCI
+ dep_bool ' CY82C693 chipset support' CONFIG_BLK_DEV_CY82C693 $CONFIG_BLK_DEV_IDEDMA_PCI
dep_bool ' Cyrix CS5530 MediaGX chipset support' CONFIG_BLK_DEV_CS5530 $CONFIG_BLK_DEV_IDEDMA_PCI
dep_bool ' HPT34X chipset support' CONFIG_BLK_DEV_HPT34X $CONFIG_BLK_DEV_IDEDMA_PCI
dep_mbool ' HPT34X AUTODMA support (WIP)' CONFIG_HPT34X_AUTODMA $CONFIG_BLK_DEV_HPT34X $CONFIG_IDEDMA_PCI_WIP
dep_bool ' HPT366 chipset support' CONFIG_BLK_DEV_HPT366 $CONFIG_BLK_DEV_IDEDMA_PCI
- dep_bool ' HPT366 Fast Interrupts (WIP)' CONFIG_HPT366_FIP $CONFIG_BLK_DEV_HPT366 $CONFIG_IDEDMA_PCI_WIP
- dep_mbool ' HPT366 mode Three (WIP)' CONFIG_HPT366_MODE3 $CONFIG_BLK_DEV_HPT366 $CONFIG_IDEDMA_PCI_WIP
if [ "$CONFIG_X86" = "y" -o "$CONFIG_IA64" = "y" ]; then
dep_mbool ' Intel PIIXn chipsets support' CONFIG_BLK_DEV_PIIX $CONFIG_BLK_DEV_IDEDMA_PCI
dep_mbool ' PIIXn Tuning support' CONFIG_PIIX_TUNING $CONFIG_BLK_DEV_PIIX $CONFIG_IDEDMA_PCI_AUTO
fi
dep_bool ' NS87415 chipset support (EXPERIMENTAL)' CONFIG_BLK_DEV_NS87415 $CONFIG_BLK_DEV_IDEDMA_PCI
dep_bool ' OPTi 82C621 chipset enhanced support (EXPERIMENTAL)' CONFIG_BLK_DEV_OPTI621 $CONFIG_EXPERIMENTAL
- dep_bool ' PROMISE PDC20246/PDC20262 support' CONFIG_BLK_DEV_PDC202XX $CONFIG_BLK_DEV_IDEDMA_PCI
+ dep_bool ' PROMISE PDC20246/PDC20262/PDC20267 support' CONFIG_BLK_DEV_PDC202XX $CONFIG_BLK_DEV_IDEDMA_PCI
dep_bool ' Special UDMA Feature' CONFIG_PDC202XX_BURST $CONFIG_BLK_DEV_PDC202XX
- dep_mbool ' Special Mode Feature (WIP)' CONFIG_PDC202XX_MASTER $CONFIG_BLK_DEV_PDC202XX $CONFIG_IDEDMA_PCI_WIP
dep_bool ' SiS5513 chipset support' CONFIG_BLK_DEV_SIS5513 $CONFIG_BLK_DEV_IDEDMA_PCI $CONFIG_X86
dep_bool ' Tekram TRM290 chipset support (EXPERIMENTAL)' CONFIG_BLK_DEV_TRM290 $CONFIG_BLK_DEV_IDEDMA_PCI
- dep_bool ' VIA82CXXX chipset support (EXPERIMENTAL)' CONFIG_BLK_DEV_VIA82CXXX $CONFIG_BLK_DEV_IDEDMA_PCI
+ dep_bool ' VIA82CXXX chipset support' CONFIG_BLK_DEV_VIA82CXXX $CONFIG_BLK_DEV_IDEDMA_PCI
dep_mbool ' VIA82CXXX Tuning support (WIP)' CONFIG_VIA82CXXX_TUNING $CONFIG_BLK_DEV_VIA82CXXX $CONFIG_IDEDMA_PCI_WIP
fi
if [ "$CONFIG_PPC" = "y" -o "$CONFIG_ARM" = "y" ]; then
@@ -81,14 +82,13 @@ if [ "$CONFIG_BLK_DEV_IDE" != "n" ]; then
dep_bool ' PowerMac IDE DMA support' CONFIG_BLK_DEV_IDEDMA_PMAC $CONFIG_BLK_DEV_IDE_PMAC
dep_bool ' Use DMA by default' CONFIG_IDEDMA_PMAC_AUTO $CONFIG_BLK_DEV_IDEDMA_PMAC
define_bool CONFIG_BLK_DEV_IDEDMA $CONFIG_BLK_DEV_IDEDMA_PMAC
- define_bool CONFIG_BLK_DEV_IDEDMA_PCI $CONFIG_BLK_DEV_IDEDMA_PMAC
+ define_bool CONFIG_BLK_DEV_IDEPCI $CONFIG_BLK_DEV_IDEDMA_PMAC
fi
if [ "$CONFIG_ARCH_ACORN" = "y" ]; then
dep_bool ' ICS IDE interface support' CONFIG_BLK_DEV_IDE_ICSIDE $CONFIG_ARCH_ACORN
dep_bool ' ICS DMA support' CONFIG_BLK_DEV_IDEDMA_ICS $CONFIG_BLK_DEV_IDE_ICSIDE
dep_bool ' Use ICS DMA by default' CONFIG_IDEDMA_ICS_AUTO $CONFIG_BLK_DEV_IDEDMA_ICS
define_bool CONFIG_BLK_DEV_IDEDMA $CONFIG_BLK_DEV_IDEDMA_ICS
- define_bool CONFIG_BLK_DEV_IDEDMA_PCI $CONFIG_BLK_DEV_IDEDMA_ICS
dep_bool ' RapIDE interface support' CONFIG_BLK_DEV_IDE_RAPIDE $CONFIG_ARCH_ACORN
fi
if [ "$CONFIG_AMIGA" = "y" ]; then
@@ -132,6 +132,17 @@ else
define_bool CONFIG_IDEDMA_AUTO n
fi
+if [ "$CONFIG_BLK_DEV_IDEDMA_PCI" = "y" -o \
+ "$CONFIG_BLK_DEV_IDEDMA_PMAC" = "y" -o \
+ "$CONFIG_BLK_DEV_IDEDMA_ICS" = "y" ]; then
+ bool ' IGNORE word93 Validation BITS' CONFIG_IDEDMA_IVB
+fi
+
+if [ "$CONFIG_BLK_DEV_TIVO" = "y" ]; then
+ define_bool CONFIG_DMA_NONPCI y
+else
+ define_bool CONFIG_DMA_NONPCI n
+fi
if [ "$CONFIG_IDE_CHIPSETS" = "y" -o \
"$CONFIG_BLK_DEV_AEC62XX" = "y" -o \
"$CONFIG_BLK_DEV_ALI15X3" = "y" -o \
diff --git a/drivers/ide/Makefile b/drivers/ide/Makefile
index 028dbcffe..2ffc5855e 100644
--- a/drivers/ide/Makefile
+++ b/drivers/ide/Makefile
@@ -18,11 +18,11 @@ SUB_DIRS :=
MOD_SUB_DIRS := $(SUB_DIRS)
ALL_SUB_DIRS := $(SUB_DIRS)
-L_TARGET := ide.a
-L_OBJS := ide-geometry.o
+O_TARGET := idedriver.o
+O_OBJS := ide-geometry.o
M_OBJS :=
MOD_LIST_NAME := IDE_MODULES
-LX_OBJS :=
+OX_OBJS :=
MX_OBJS :=
ifeq ($(CONFIG_BLK_DEV_AEC62XX),y)
@@ -78,7 +78,7 @@ IDE_OBJS += q40ide.o
endif
ifeq ($(CONFIG_BLK_DEV_HD),y)
-L_OBJS += hd.o
+O_OBJS += hd.o
endif
ifeq ($(CONFIG_BLK_DEV_HPT34X),y)
@@ -97,7 +97,7 @@ ifeq ($(CONFIG_BLK_DEV_IDE_ICSIDE),y)
IDE_OBJS += icside.o
endif
-ifeq ($(CONFIG_BLK_DEV_IDEDMA_PCI),y)
+ifeq ($(CONFIG_BLK_DEV_IDEDMA),y)
IDE_OBJS += ide-dma.o
endif
@@ -178,8 +178,8 @@ endif
###Collect
ifeq ($(CONFIG_BLK_DEV_IDE),y)
- LX_OBJS += ide.o ide-features.o
- L_OBJS += ide-probe.o $(IDE_OBJS)
+ OX_OBJS += ide.o ide-features.o
+ O_OBJS += ide-probe.o $(IDE_OBJS)
else
ifeq ($(CONFIG_BLK_DEV_IDE),m)
MIX_OBJS += ide.o ide-features.o $(IDE_OBJS)
@@ -190,7 +190,7 @@ endif
############
ifeq ($(CONFIG_BLK_DEV_IDECS),y)
-L_OBJS += ide-cs.o
+O_OBJS += ide-cs.o
else
ifeq ($(CONFIG_BLK_DEV_IDECS),m)
M_OBJS += ide-cs.o
@@ -198,7 +198,7 @@ else
endif
ifeq ($(CONFIG_BLK_DEV_IDEDISK),y)
-L_OBJS += ide-disk.o
+O_OBJS += ide-disk.o
else
ifeq ($(CONFIG_BLK_DEV_IDEDISK),m)
M_OBJS += ide-disk.o
@@ -206,7 +206,7 @@ else
endif
ifeq ($(CONFIG_BLK_DEV_IDECD),y)
-L_OBJS += ide-cd.o
+O_OBJS += ide-cd.o
else
ifeq ($(CONFIG_BLK_DEV_IDECD),m)
M_OBJS += ide-cd.o
@@ -214,7 +214,7 @@ else
endif
ifeq ($(CONFIG_BLK_DEV_IDETAPE),y)
-L_OBJS += ide-tape.o
+O_OBJS += ide-tape.o
else
ifeq ($(CONFIG_BLK_DEV_IDETAPE),m)
M_OBJS += ide-tape.o
@@ -222,7 +222,7 @@ else
endif
ifeq ($(CONFIG_BLK_DEV_IDEFLOPPY),y)
-L_OBJS += ide-floppy.o
+O_OBJS += ide-floppy.o
else
ifeq ($(CONFIG_BLK_DEV_IDEFLOPPY),m)
M_OBJS += ide-floppy.o
diff --git a/drivers/ide/aec62xx.c b/drivers/ide/aec62xx.c
index 75b3153b7..2f3d2fc3a 100644
--- a/drivers/ide/aec62xx.c
+++ b/drivers/ide/aec62xx.c
@@ -1,7 +1,7 @@
/*
- * linux/drivers/ide/aec62xx.c Version 0.08 Mar. 28, 2000
+ * linux/drivers/ide/aec62xx.c Version 0.09 June. 9, 2000
*
- * Copyright (C) 2000 Andre Hedrick (andre@suse.com)
+ * Copyright (C) 1999-2000 Andre Hedrick (andre@linux-ide.org)
* May be copied or modified under the terms of the GNU General Public License
*
*/
@@ -55,7 +55,7 @@ static int aec62xx_get_info (char *buffer, char **addr, off_t offset, int count)
{
char *p = buffer;
- u32 bibma = bmide_dev->resource[4].start;
+ u32 bibma = pci_resource_start(bmide_dev, 4);
u8 c0 = 0, c1 = 0;
u8 art = 0, uart = 0;
@@ -358,7 +358,7 @@ static int config_aec6260_chipset_for_dma (ide_drive_t *drive, byte ultra)
byte unit = (drive->select.b.unit & 0x01);
unsigned long dma_base = hwif->dma_base;
byte speed = -1;
- byte ultra66 = ((id->hw_config & 0x2000) && (hwif->udma_four)) ? 1 : 0;
+ byte ultra66 = eighty_ninty_three(drive);
if (drive->media != ide_disk)
return ((int) ide_dma_off_quietly);
@@ -497,6 +497,23 @@ int aec62xx_dmaproc (ide_dma_action_t func, ide_drive_t *drive)
switch (func) {
case ide_dma_check:
return config_drive_xfer_rate(drive);
+ case ide_dma_lostirq:
+ case ide_dma_timeout:
+ switch(HWIF(drive)->pci_dev->device) {
+ case PCI_DEVICE_ID_ARTOP_ATP860:
+ case PCI_DEVICE_ID_ARTOP_ATP860R:
+// {
+// int i = 0;
+// byte reg49h = 0;
+// pci_read_config_byte(HWIF(drive)->pci_dev, 0x49, &reg49h);
+// for (i=0;i<256;i++)
+// pci_write_config_byte(HWIF(drive)->pci_dev, 0x49, reg49h|0x10);
+// pci_write_config_byte(HWIF(drive)->pci_dev, 0x49, reg49h & ~0x10);
+// }
+// return 0;
+ default:
+ break;
+ }
default:
break;
}
@@ -529,9 +546,6 @@ unsigned int __init ata66_aec62xx (ide_hwif_t *hwif)
byte ata66 = 0;
pci_read_config_byte(hwif->pci_dev, 0x49, &ata66);
-#if 1
- printk("AEC6260: reg49h=0x%02x ATA-%s Cable Port%d\n", ata66, (ata66 & mask) ? "33" : "66", hwif->channel);
-#endif
return ((ata66 & mask) ? 0 : 1);
}
diff --git a/drivers/ide/alim15x3.c b/drivers/ide/alim15x3.c
index 02af0a0f8..41768bb90 100644
--- a/drivers/ide/alim15x3.c
+++ b/drivers/ide/alim15x3.c
@@ -1,17 +1,15 @@
/*
- * linux/drivers/ide/alim15x3.c Version 0.09 Mar. 18, 2000
+ * linux/drivers/ide/alim15x3.c Version 0.10 Jun. 9, 2000
*
* Copyright (C) 1998-2000 Michel Aubry, Maintainer
* Copyright (C) 1998-2000 Andrzej Krzysztofowicz, Maintainer
+ * Copyright (C) 1999-2000 CJ, cjtsai@ali.com.tw, Maintainer
*
- * Copyright (C) 1998-2000 Andre Hedrick (andre@suse.com)
+ * Copyright (C) 1998-2000 Andre Hedrick (andre@linux-ide.org)
* May be copied or modified under the terms of the GNU General Public License
*
* (U)DMA capable version of ali 1533/1543(C), 1535(D)
*
- * version: 1.0 beta2 (Sep. 2, 1999)
- * e-mail your problems to cjtsai@ali.com.tw
- *
**********************************************************************
* 9/7/99 --Parts from the above author are included and need to be
* converted into standard interface, once I finish the thought.
@@ -237,7 +235,6 @@ static int ali_get_info (char *buffer, char **addr, off_t offset, int count)
static byte m5229_revision = 0;
static byte chip_is_1543c_e = 0;
-static byte cable_80_pin[2] = { 0, 0 };
byte ali_proc = 0;
static struct pci_dev *isa_dev;
@@ -346,7 +343,7 @@ static int ali15x3_tune_chipset (ide_drive_t *drive, byte speed)
/*
* enable ultra dma and set timing
*/
- tmpbyte |= ((0x08 | (4-speed)) << (unit << 2));
+ tmpbyte |= ((0x08 | ((4-speed)&0x07)) << (unit << 2));
pci_write_config_byte(dev, m5229_udma, tmpbyte);
if (speed >= XFER_UDMA_3) {
pci_read_config_byte(dev, 0x4b, &tmpbyte);
@@ -370,12 +367,14 @@ static void config_chipset_for_pio (ide_drive_t *drive)
static int config_chipset_for_dma (ide_drive_t *drive, byte ultra33)
{
struct hd_driveid *id = drive->id;
- ide_hwif_t *hwif = HWIF(drive);
byte speed = 0x00;
- byte ultra66 = ((hwif->udma_four) && (id->hw_config & 0x2000)) ? 1 : 0;
+ byte ultra66 = eighty_ninty_three(drive);
+ byte ultra100 = (m5229_revision>=0xc4) ? 1 : 0;
int rval;
- if ((id->dma_ultra & 0x0010) && (ultra66) && (ultra33)) {
+ if ((id->dma_ultra & 0x0020) && (ultra100) && (ultra66) && (ultra33)) {
+ speed = XFER_UDMA_5;
+ } else if ((id->dma_ultra & 0x0010) && (ultra66) && (ultra33)) {
speed = XFER_UDMA_4;
} else if ((id->dma_ultra & 0x0008) && (ultra66) && (ultra33)) {
speed = XFER_UDMA_3;
@@ -454,7 +453,7 @@ static int ali15x3_config_drive_for_dma(ide_drive_t *drive)
}
dma_func = ide_dma_off_quietly;
if ((id->field_valid & 4) && (m5229_revision >= 0xC2)) {
- if (id->dma_ultra & 0x001F) {
+ if (id->dma_ultra & 0x002F) {
/* Force if Capable UltraDMA */
dma_func = config_chipset_for_dma(drive, can_ultra_dma);
if ((id->field_valid & 2) &&
@@ -508,13 +507,13 @@ static int ali15x3_dmaproc (ide_dma_action_t func, ide_drive_t *drive)
unsigned int __init pci_init_ali15x3 (struct pci_dev *dev, const char *name)
{
- unsigned long fixdma_base = dev->resource[4].start;
+ unsigned long fixdma_base = pci_resource_start(dev, 4);
pci_read_config_byte(dev, PCI_REVISION_ID, &m5229_revision);
isa_dev = pci_find_device(PCI_VENDOR_ID_AL, PCI_DEVICE_ID_AL_M1533, NULL);
- if (!fixdma_base || fixdma_base == PCI_BASE_ADDRESS_IO_MASK) {
+ if (!fixdma_base) {
/*
*
*/
@@ -539,11 +538,16 @@ unsigned int __init pci_init_ali15x3 (struct pci_dev *dev, const char *name)
return 0;
}
+/*
+ * This checks if the controller and the cable are capable
+ * of UDMA66 transfers. It doesn't check the drives.
+ * But see note 2 below!
+ */
unsigned int __init ata66_ali15x3 (ide_hwif_t *hwif)
{
struct pci_dev *dev = hwif->pci_dev;
- byte ata66mask = hwif->channel ? 0x02 : 0x01;
unsigned int ata66 = 0;
+ byte cable_80_pin[2] = { 0, 0 };
unsigned long flags;
byte tmpbyte;
@@ -575,7 +579,7 @@ unsigned int __init ata66_ali15x3 (ide_hwif_t *hwif)
* 1543C-B0 (m1533, 0x79, bit 2)
*/
pci_write_config_byte(isa_dev, 0x79, tmpbyte | 0x04);
- } else if (m5229_revision == 0xC3) {
+ } else if (m5229_revision >= 0xC3) {
/*
* 1553/1535 (m1533, 0x79, bit 1)
*/
@@ -596,6 +600,10 @@ unsigned int __init ata66_ali15x3 (ide_hwif_t *hwif)
* has 80-pin (from host view)
*/
if (!(tmpbyte & 0x02)) cable_80_pin[1] = 1;
+ /*
+ * Allow ata66 if cable of current channel has 80 pins
+ */
+ ata66 = (hwif->channel)?cable_80_pin[1]:cable_80_pin[0];
} else {
/*
* revision 0x20 (1543-E, 1543-F)
@@ -625,18 +633,6 @@ unsigned int __init ata66_ali15x3 (ide_hwif_t *hwif)
pci_write_config_byte(dev, 0x53, tmpbyte);
- /*
- * Ultra66 cable detection (from Host View)
- * m5229, 0x4a, bit0: primary, bit1: secondary 80 pin
- *
- * 0x4a, bit0 is 0 => primary channel
- * has 80-pin (from host view)
- *
- * 0x4a, bit1 is 0 => secondary channel
- * has 80-pin (from host view)
- */
- pci_read_config_byte(dev, 0x4a, &tmpbyte);
- ata66 = (!(tmpbyte & ata66mask)) ? 1 : 0;
__restore_flags(flags);
return(ata66);
diff --git a/drivers/ide/amd7409.c b/drivers/ide/amd7409.c
index d54a240d4..ca23d3af4 100644
--- a/drivers/ide/amd7409.c
+++ b/drivers/ide/amd7409.c
@@ -1,7 +1,7 @@
/*
- * linux/drivers/ide/amd7409.c Version 0.04 Mar. 18, 2000
+ * linux/drivers/ide/amd7409.c Version 0.05 June 9, 2000
*
- * Copyright (C) 2000 Andre Hedrick <andre@suse.com>
+ * Copyright (C) 1999-2000 Andre Hedrick <andre@linux-ide.org>
* May be copied or modified under the terms of the GNU General Public License
*
*/
@@ -40,7 +40,7 @@ static struct pci_dev *bmide_dev;
static int amd7409_get_info (char *buffer, char **addr, off_t offset, int count)
{
char *p = buffer;
- u32 bibma = bmide_dev->resource[4].start;
+ u32 bibma = pci_resource_start(bmide_dev, 4);
u8 c0 = 0, c1 = 0;
/*
@@ -71,6 +71,20 @@ byte amd7409_proc = 0;
extern char *ide_xfer_verbose (byte xfer_rate);
+static unsigned int amd7409_swdma_check (struct pci_dev *dev)
+{
+ unsigned int class_rev;
+ pci_read_config_dword(dev, PCI_CLASS_REVISION, &class_rev);
+ class_rev &= 0xff;
+ return ((int) (class_rev >= 7) ? 1 : 0);
+}
+
+static int amd7409_swdma_error(ide_drive_t *drive)
+{
+ printk("%s: single-word DMA not support (revision < C4)\n", drive->name);
+ return 0;
+}
+
/*
* Here is where all the hard work goes to program the chipset.
*
@@ -122,64 +136,68 @@ static int amd7409_tune_chipset (ide_drive_t *drive, byte speed)
case XFER_UDMA_4:
ultra_timing |= 0x45;
dma_pio_timing |= 0x20;
- pio_timing |= (0x03 << drive->dn);
break;
case XFER_UDMA_3:
ultra_timing |= 0x44;
dma_pio_timing |= 0x20;
- pio_timing |= (0x03 << drive->dn);
break;
case XFER_UDMA_2:
ultra_timing |= 0x40;
dma_pio_timing |= 0x20;
- pio_timing |= (0x03 << drive->dn);
break;
case XFER_UDMA_1:
ultra_timing |= 0x41;
dma_pio_timing |= 0x20;
- pio_timing |= (0x03 << drive->dn);
break;
case XFER_UDMA_0:
ultra_timing |= 0x42;
dma_pio_timing |= 0x20;
- pio_timing |= (0x03 << drive->dn);
break;
case XFER_MW_DMA_2:
dma_pio_timing |= 0x20;
- pio_timing |= (0x03 << drive->dn);
break;
case XFER_MW_DMA_1:
dma_pio_timing |= 0x21;
- pio_timing |= (0x03 << drive->dn);
break;
case XFER_MW_DMA_0:
dma_pio_timing |= 0x77;
- pio_timing |= (0x03 << drive->dn);
+ break;
+ case XFER_SW_DMA_2:
+ if (!amd7409_swdma_check(dev))
+ return amd7409_swdma_error(drive);
+ dma_pio_timing |= 0x42;
+ break;
+ case XFER_SW_DMA_1:
+ if (!amd7409_swdma_check(dev))
+ return amd7409_swdma_error(drive);
+ dma_pio_timing |= 0x65;
+ break;
+ case XFER_SW_DMA_0:
+ if (!amd7409_swdma_check(dev))
+ return amd7409_swdma_error(drive);
+ dma_pio_timing |= 0xA8;
break;
#endif /* CONFIG_BLK_DEV_IDEDMA */
case XFER_PIO_4:
dma_pio_timing |= 0x20;
- pio_timing |= (0x03 << drive->dn);
break;
case XFER_PIO_3:
dma_pio_timing |= 0x22;
- pio_timing |= (0x03 << drive->dn);
break;
case XFER_PIO_2:
dma_pio_timing |= 0x42;
- pio_timing |= (0x03 << drive->dn);
break;
case XFER_PIO_1:
dma_pio_timing |= 0x65;
- pio_timing |= (0x03 << drive->dn);
break;
case XFER_PIO_0:
default:
dma_pio_timing |= 0xA8;
- pio_timing |= (0x03 << drive->dn);
break;
}
+ pio_timing |= (0x03 << drive->dn);
+
if (!drive->init_speed)
drive->init_speed = speed;
@@ -268,12 +286,14 @@ static void amd7409_tune_drive (ide_drive_t *drive, byte pio)
static int config_chipset_for_dma (ide_drive_t *drive)
{
struct hd_driveid *id = drive->id;
- byte udma_66 = ((id->hw_config & 0x2000) &&
- (HWIF(drive)->udma_four)) ? 1 : 0;
+ byte udma_66 = eighty_ninty_three(drive);
+ byte udma_100 = 0;
byte speed = 0x00;
int rval;
- if ((id->dma_ultra & 0x0010) && (udma_66)) {
+ if ((id->dma_ultra & 0x0020) && (udma_66)&& (udma_100)) {
+ speed = XFER_UDMA_5;
+ } else if ((id->dma_ultra & 0x0010) && (udma_66)) {
speed = XFER_UDMA_4;
} else if ((id->dma_ultra & 0x0008) && (udma_66)) {
speed = XFER_UDMA_3;
@@ -318,7 +338,7 @@ static int config_drive_xfer_rate (ide_drive_t *drive)
}
dma_func = ide_dma_off_quietly;
if (id->field_valid & 4) {
- if (id->dma_ultra & 0x001F) {
+ if (id->dma_ultra & 0x002F) {
/* Force if Capable UltraDMA */
dma_func = config_chipset_for_dma(drive);
if ((id->field_valid & 2) &&
@@ -327,12 +347,15 @@ static int config_drive_xfer_rate (ide_drive_t *drive)
}
} else if (id->field_valid & 2) {
try_dma_modes:
- if (id->dma_mword & 0x0007) {
+ if ((id->dma_mword & 0x0007) ||
+ ((id->dma_1word & 0x007) &&
+ (amd7409_swdma_check(HWIF(drive)->pci_dev)))) {
/* Force if Capable regular DMA modes */
dma_func = config_chipset_for_dma(drive);
if (dma_func != ide_dma_on)
goto no_dma_set;
}
+
} else if (ide_dmaproc(ide_dma_good_drive, drive)) {
if (id->eide_dma_time > 150) {
goto no_dma_set;
@@ -372,9 +395,14 @@ int amd7409_dmaproc (ide_dma_action_t func, ide_drive_t *drive)
unsigned int __init pci_init_amd7409 (struct pci_dev *dev, const char *name)
{
- unsigned long fixdma_base = dev->resource[4].start;
+ unsigned long fixdma_base = pci_resource_start(dev, 4);
+
+#ifdef CONFIG_BLK_DEV_IDEDMA
+ if (!amd7409_swdma_check(dev))
+ printk("%s: disabling single-word DMA support (revision < C4)\n", name);
+#endif /* CONFIG_BLK_DEV_IDEDMA */
- if (!fixdma_base || fixdma_base == PCI_BASE_ADDRESS_IO_MASK) {
+ if (!fixdma_base) {
/*
*
*/
diff --git a/drivers/ide/cmd64x.c b/drivers/ide/cmd64x.c
index 7e9f0c7ee..6e45bf0e0 100644
--- a/drivers/ide/cmd64x.c
+++ b/drivers/ide/cmd64x.c
@@ -1,6 +1,6 @@
/* $Id: cmd64x.c,v 1.21 2000/01/30 23:23:16
*
- * linux/drivers/ide/cmd64x.c Version 1.21 Mar. 18, 2000
+ * linux/drivers/ide/cmd64x.c Version 1.22 June 9, 2000
*
* cmd64x.c: Enable interrupts at initialization time on Ultra/PCI machines.
* Note, this driver is not used at all on other systems because
@@ -10,7 +10,7 @@
*
* Copyright (C) 1998 Eddie C. Dost (ecd@skynet.be)
* Copyright (C) 1998 David S. Miller (davem@redhat.com)
- * Copyright (C) 1999-2000 Andre Hedrick (andre@suse.com)
+ * Copyright (C) 1999-2000 Andre Hedrick <andre@linux-ide.org>
*/
#include <linux/config.h>
@@ -41,6 +41,8 @@
* CMD64x specific registers definition.
*/
+#define CFR 0x50
+#define CFR_INTR_CH0 0x02
#define CNTRL 0x51
#define CNTRL_DIS_RA0 0x40
#define CNTRL_DIS_RA1 0x80
@@ -52,6 +54,7 @@
#define ARTTIM1 0x55
#define DRWTIM1 0x56
#define ARTTIM23 0x57
+#define ARTTIM23_INTR_CH1 0x04
#define ARTTIM23_DIS_RA2 0x04
#define ARTTIM23_DIS_RA3 0x08
#define ARTTIM2 0x57
@@ -63,6 +66,10 @@
#define BMIDECR0 0x70
#define MRDMODE 0x71
+#define MRDMODE_INTR_CH0 0x04
+#define MRDMODE_INTR_CH1 0x08
+#define MRDMODE_BLK_CH0 0x10
+#define MRDMODE_BLK_CH1 0x20
#define BMIDESR0 0x72
#define UDIDETCR0 0x73
#define DTPR0 0x74
@@ -90,9 +97,13 @@ static int cmd64x_get_info (char *buffer, char **addr, off_t offset, int count)
u8 reg57 = 0, reg58 = 0, reg5b; /* secondary */
u8 reg72 = 0, reg73 = 0; /* primary */
u8 reg7a = 0, reg7b = 0; /* secondary */
+ u8 reg50 = 0, reg71 = 0; /* extra */
u8 hi_byte = 0, lo_byte = 0;
switch(bmide_dev->device) {
+ case PCI_DEVICE_ID_CMD_649:
+ p += sprintf(p, "\n CMD649 Chipset.\n");
+ break;
case PCI_DEVICE_ID_CMD_648:
p += sprintf(p, "\n CMD648 Chipset.\n");
break;
@@ -106,6 +117,7 @@ static int cmd64x_get_info (char *buffer, char **addr, off_t offset, int count)
p += sprintf(p, "\n CMD64? Chipse.\n");
break;
}
+ (void) pci_read_config_byte(bmide_dev, CFR, &reg50);
(void) pci_read_config_byte(bmide_dev, ARTTIM0, &reg53);
(void) pci_read_config_byte(bmide_dev, DRWTIM0, &reg54);
(void) pci_read_config_byte(bmide_dev, ARTTIM1, &reg55);
@@ -113,6 +125,7 @@ static int cmd64x_get_info (char *buffer, char **addr, off_t offset, int count)
(void) pci_read_config_byte(bmide_dev, ARTTIM2, &reg57);
(void) pci_read_config_byte(bmide_dev, DRWTIM2, &reg58);
(void) pci_read_config_byte(bmide_dev, DRWTIM3, &reg5b);
+ (void) pci_read_config_byte(bmide_dev, MRDMODE, &reg71);
(void) pci_read_config_byte(bmide_dev, BMIDESR0, &reg72);
(void) pci_read_config_byte(bmide_dev, UDIDETCR0, &reg73);
(void) pci_read_config_byte(bmide_dev, BMIDESR1, &reg7a);
@@ -128,42 +141,42 @@ static int cmd64x_get_info (char *buffer, char **addr, off_t offset, int count)
(reg72&0x20)?((reg73&0x01)?"UDMA":" DMA"):" PIO",
(reg72&0x20)?( ((reg73&0x30)==0x30)?(((reg73&0x35)==0x35)?"3":"0"):
((reg73&0x20)==0x20)?(((reg73&0x25)==0x25)?"3":"1"):
- ((reg73&0x10)==0x10)?(((reg73&0x15)==0x15)?"4":"2"):"X"):"?",
+ ((reg73&0x10)==0x10)?(((reg73&0x15)==0x15)?"4":"2"):
+ ((reg73&0x00)==0x00)?(((reg73&0x05)==0x05)?"5":"2"):"X"):"?",
(reg72&0x40)?((reg73&0x02)?"UDMA":" DMA"):" PIO",
(reg72&0x40)?( ((reg73&0xC0)==0xC0)?(((reg73&0xC5)==0xC5)?"3":"0"):
((reg73&0x80)==0x80)?(((reg73&0x85)==0x85)?"3":"1"):
- ((reg73&0x40)==0x40)?(((reg73&0x4A)==0x4A)?"4":"2"):"X"):"?",
+ ((reg73&0x40)==0x40)?(((reg73&0x4A)==0x4A)?"4":"2"):
+ ((reg73&0x00)==0x00)?(((reg73&0x0A)==0x0A)?"5":"2"):"X"):"?",
(reg7a&0x20)?((reg7b&0x01)?"UDMA":" DMA"):" PIO",
(reg7a&0x20)?( ((reg7b&0x30)==0x30)?(((reg7b&0x35)==0x35)?"3":"0"):
((reg7b&0x20)==0x20)?(((reg7b&0x25)==0x25)?"3":"1"):
- ((reg7b&0x10)==0x10)?(((reg7b&0x15)==0x15)?"4":"2"):"X"):"?",
+ ((reg7b&0x10)==0x10)?(((reg7b&0x15)==0x15)?"4":"2"):
+ ((reg7b&0x00)==0x00)?(((reg7b&0x05)==0x05)?"5":"2"):"X"):"?",
(reg7a&0x40)?((reg7b&0x02)?"UDMA":" DMA"):" PIO",
(reg7a&0x40)?( ((reg7b&0xC0)==0xC0)?(((reg7b&0xC5)==0xC5)?"3":"0"):
((reg7b&0x80)==0x80)?(((reg7b&0x85)==0x85)?"3":"1"):
- ((reg7b&0x40)==0x40)?(((reg7b&0x4A)==0x4A)?"4":"2"):"X"):"?" );
+ ((reg7b&0x40)==0x40)?(((reg7b&0x4A)==0x4A)?"4":"2"):
+ ((reg7b&0x00)==0x00)?(((reg7b&0x0A)==0x0A)?"5":"2"):"X"):"?" );
p += sprintf(p, "PIO Mode: %s %s %s %s\n",
"?", "?", "?", "?");
- p += sprintf(p, "PIO\n");
-
- SPLIT_BYTE(reg53, hi_byte, lo_byte);
- p += sprintf(p, "ARTTIM0 = 0x%02x, HI = 0x%02x, LOW = 0x%02x\n", reg53, hi_byte, lo_byte);
- SPLIT_BYTE(reg54, hi_byte, lo_byte);
- p += sprintf(p, "DRWTIM0 = 0x%02x, HI = 0x%02x, LOW = 0x%02x\n", reg54, hi_byte, lo_byte);
- SPLIT_BYTE(reg55, hi_byte, lo_byte);
- p += sprintf(p, "ARTTIM1 = 0x%02x, HI = 0x%02x, LOW = 0x%02x\n", reg55, hi_byte, lo_byte);
- SPLIT_BYTE(reg56, hi_byte, lo_byte);
- p += sprintf(p, "DRWTIM1 = 0x%02x, HI = 0x%02x, LOW = 0x%02x\n", reg56, hi_byte, lo_byte);
+ p += sprintf(p, " %s %s\n",
+ (reg50 & CFR_INTR_CH0) ? "interrupting" : "polling ",
+ (reg57 & ARTTIM23_INTR_CH1) ? "interrupting" : "polling");
+ p += sprintf(p, " %s %s\n",
+ (reg71 & MRDMODE_INTR_CH0) ? "pending" : "clear ",
+ (reg71 & MRDMODE_INTR_CH1) ? "pending" : "clear");
+ p += sprintf(p, " %s %s\n",
+ (reg71 & MRDMODE_BLK_CH0) ? "blocked" : "enabled",
+ (reg71 & MRDMODE_BLK_CH1) ? "blocked" : "enabled");
+
+ SPLIT_BYTE(reg50, hi_byte, lo_byte);
+ p += sprintf(p, "CFR = 0x%02x, HI = 0x%02x, LOW = 0x%02x\n", reg50, hi_byte, lo_byte);
SPLIT_BYTE(reg57, hi_byte, lo_byte);
p += sprintf(p, "ARTTIM23 = 0x%02x, HI = 0x%02x, LOW = 0x%02x\n", reg57, hi_byte, lo_byte);
- SPLIT_BYTE(reg58, hi_byte, lo_byte);
- p += sprintf(p, "DRWTIM2 = 0x%02x, HI = 0x%02x, LOW = 0x%02x\n", reg58, hi_byte, lo_byte);
- SPLIT_BYTE(reg5b, hi_byte, lo_byte);
- p += sprintf(p, "DRWTIM3 = 0x%02x, HI = 0x%02x, LOW = 0x%02x\n", reg5b, hi_byte, lo_byte);
- SPLIT_BYTE(reg73, hi_byte, lo_byte);
- p += sprintf(p, "UDIDETCR0 = 0x%02x, HI = 0x%02x, LOW = 0x%02x\n", reg73, hi_byte, lo_byte);
- SPLIT_BYTE(reg7b, hi_byte, lo_byte);
- p += sprintf(p, "UDIDETCR1 = 0x%02x, HI = 0x%02x, LOW = 0x%02x\n", reg7b, hi_byte, lo_byte);
+ SPLIT_BYTE(reg71, hi_byte, lo_byte);
+ p += sprintf(p, "MRDMODE = 0x%02x, HI = 0x%02x, LOW = 0x%02x\n", reg71, hi_byte, lo_byte);
return p-buffer; /* => must be less than 4k! */
}
@@ -349,9 +362,9 @@ static int cmd64x_tune_chipset (ide_drive_t *drive, byte speed)
#ifdef CONFIG_BLK_DEV_IDEDMA
ide_hwif_t *hwif = HWIF(drive);
struct pci_dev *dev = hwif->pci_dev;
- byte unit = (drive->select.b.unit & 0x01);
int err = 0;
+ byte unit = (drive->select.b.unit & 0x01);
u8 pciU = (hwif->channel) ? UDIDETCR1 : UDIDETCR0;
u8 pciD = (hwif->channel) ? BMIDESR1 : BMIDESR0;
u8 regU = 0;
@@ -369,6 +382,7 @@ static int cmd64x_tune_chipset (ide_drive_t *drive, byte speed)
(void) pci_read_config_byte(dev, pciD, &regD);
(void) pci_read_config_byte(dev, pciU, &regU);
switch(speed) {
+ case XFER_UDMA_5: regU |= (unit ? 0x0A : 0x05); break;
case XFER_UDMA_4: regU |= (unit ? 0x4A : 0x15); break;
case XFER_UDMA_3: regU |= (unit ? 0x8A : 0x25); break;
case XFER_UDMA_2: regU |= (unit ? 0x42 : 0x11); break;
@@ -383,7 +397,7 @@ static int cmd64x_tune_chipset (ide_drive_t *drive, byte speed)
#else
int err = 0;
- switch(speed) {
+ switch(speed) {
#endif /* CONFIG_BLK_DEV_IDEDMA */
case XFER_PIO_4: cmd64x_tuneproc(drive, 4); break;
case XFER_PIO_3: cmd64x_tuneproc(drive, 3); break;
@@ -394,6 +408,7 @@ static int cmd64x_tune_chipset (ide_drive_t *drive, byte speed)
default:
return 1;
}
+
#ifdef CONFIG_BLK_DEV_IDEDMA
(void) pci_write_config_byte(dev, pciU, regU);
#endif /* CONFIG_BLK_DEV_IDEDMA */
@@ -420,10 +435,12 @@ static int config_chipset_for_dma (ide_drive_t *drive, unsigned int rev, byte ul
byte speed = 0x00;
byte set_pio = 0x00;
byte udma_33 = ((rev >= 0x05) || (ultra_66)) ? 1 : 0;
- byte udma_66 = ((id->hw_config & 0x2000) && (hwif->udma_four)) ? 1 : 0;
+ byte udma_66 = eighty_ninty_three(drive);
+ byte udma_100 = 0;
int rval;
switch(dev->device) {
+ case PCI_DEVICE_ID_CMD_649: udma_100 = 1; break;
case PCI_DEVICE_ID_CMD_648:
case PCI_DEVICE_ID_CMD_646:
case PCI_DEVICE_ID_CMD_643:
@@ -446,7 +463,9 @@ static int config_chipset_for_dma (ide_drive_t *drive, unsigned int rev, byte ul
* in the 646U2.
* So we only do UltraDMA on revision 0x05 and 0x07 chipsets.
*/
- if ((id->dma_ultra & 0x0010) && (udma_66) && (udma_33)) {
+ if ((id->dma_ultra & 0x0020) && (udma_100) && (udma_66) && (udma_33)) {
+ speed = XFER_UDMA_5;
+ } else if ((id->dma_ultra & 0x0010) && (udma_66) && (udma_33)) {
speed = XFER_UDMA_4;
} else if ((id->dma_ultra & 0x0008) && (udma_66) && (udma_33)) {
speed = XFER_UDMA_3;
@@ -483,7 +502,7 @@ static int config_chipset_for_dma (ide_drive_t *drive, unsigned int rev, byte ul
if (cmd64x_tune_chipset(drive, speed))
return ((int) ide_dma_off);
- rval = (int)( ((id->dma_ultra >> 11) & 3) ? ide_dma_on :
+ rval = (int)( ((id->dma_ultra >> 11) & 7) ? ide_dma_on :
((id->dma_ultra >> 8) & 7) ? ide_dma_on :
((id->dma_mword >> 8) & 7) ? ide_dma_on :
((id->dma_1word >> 8) & 7) ? ide_dma_on :
@@ -500,12 +519,15 @@ static int cmd64x_config_drive_for_dma (ide_drive_t *drive)
unsigned int class_rev = 0;
byte can_ultra_33 = 0;
byte can_ultra_66 = 0;
+ byte can_ultra_100 = 0;
ide_dma_action_t dma_func = ide_dma_on;
pci_read_config_dword(dev, PCI_CLASS_REVISION, &class_rev);
class_rev &= 0xff;
switch(dev->device) {
+ case PCI_DEVICE_ID_CMD_649:
+ can_ultra_100 = 1;
case PCI_DEVICE_ID_CMD_648:
can_ultra_66 = 1;
case PCI_DEVICE_ID_CMD_643:
@@ -514,6 +536,7 @@ static int cmd64x_config_drive_for_dma (ide_drive_t *drive)
case PCI_DEVICE_ID_CMD_646:
can_ultra_33 = (class_rev >= 0x05) ? 1 : 0;
can_ultra_66 = 0;
+ can_ultra_100 = 0;
break;
default:
return hwif->dmaproc(ide_dma_off, drive);
@@ -528,7 +551,7 @@ static int cmd64x_config_drive_for_dma (ide_drive_t *drive)
}
dma_func = ide_dma_off_quietly;
if ((id->field_valid & 4) && (can_ultra_33)) {
- if (id->dma_ultra & 0x001F) {
+ if (id->dma_ultra & 0x002F) {
/* Force if Capable UltraDMA */
dma_func = config_chipset_for_dma(drive, class_rev, can_ultra_66);
if ((id->field_valid & 2) &&
@@ -636,6 +659,7 @@ unsigned int __init pci_init_cmd64x (struct pci_dev *dev, const char *name)
printk("\n");
break;
case PCI_DEVICE_ID_CMD_648:
+ case PCI_DEVICE_ID_CMD_649:
break;
default:
break;
@@ -714,6 +738,7 @@ void __init ide_init_cmd64x (ide_hwif_t *hwif)
#ifdef CONFIG_BLK_DEV_IDEDMA
switch(dev->device) {
+ case PCI_DEVICE_ID_CMD_649:
case PCI_DEVICE_ID_CMD_648:
case PCI_DEVICE_ID_CMD_643:
hwif->dmaproc = &cmd64x_dmaproc;
diff --git a/drivers/ide/cs5530.c b/drivers/ide/cs5530.c
index b160d7716..fb531e813 100644
--- a/drivers/ide/cs5530.c
+++ b/drivers/ide/cs5530.c
@@ -1,7 +1,7 @@
/*
* linux/drivers/ide/cs5530.c Version 0.6 Mar. 18, 2000
*
- * Copyright (C) 2000 Andre Hedrick <andre@suse.com>
+ * Copyright (C) 2000 Andre Hedrick <andre@linux-ide.org>
* Ditto of GNU General Public License.
*
* Copyright (C) 2000 Mark Lord <mlord@pobox.com>
@@ -43,7 +43,7 @@ static struct pci_dev *bmide_dev;
static int cs5530_get_info (char *buffer, char **addr, off_t offset, int count)
{
char *p = buffer;
- u32 bibma = bmide_dev->resource[4].start;
+ u32 bibma = pci_resource_start(bmide_dev, 4);
u8 c0 = 0, c1 = 0;
/*
diff --git a/drivers/ide/cy82c693.c b/drivers/ide/cy82c693.c
index 3ecaa31ec..3e4961cbe 100644
--- a/drivers/ide/cy82c693.c
+++ b/drivers/ide/cy82c693.c
@@ -1,8 +1,8 @@
/*
* linux/drivers/ide/cy82c693.c Version 0.34 Dec. 13, 1999
*
- * Copyright (C) 1998-99 Andreas S. Krebs (akrebs@altavista.net), Maintainer
- * Copyright (C) 1998-99 Andre Hedrick, Integrater
+ * Copyright (C) 1998-2000 Andreas S. Krebs (akrebs@altavista.net), Maintainer
+ * Copyright (C) 1998-2000 Andre Hedrick <andre@linux-ide.org>, Integrater
*
* CYPRESS CY82C693 chipset IDE controller
*
diff --git a/drivers/ide/gayle.c b/drivers/ide/gayle.c
index 748068242..2011b6a26 100644
--- a/drivers/ide/gayle.c
+++ b/drivers/ide/gayle.c
@@ -67,11 +67,13 @@ static int __init gayle_offsets[IDE_NR_PORTS] = {
#define GAYLE_NUM_HWIFS 1
#define GAYLE_NUM_PROBE_HWIFS GAYLE_NUM_HWIFS
#define GAYLE_HAS_CONTROL_REG 1
+#define GAYLE_IDEREG_SIZE 0x2000
#else /* CONFIG_BLK_DEV_IDEDOUBLER */
#define GAYLE_NUM_HWIFS 2
#define GAYLE_NUM_PROBE_HWIFS (ide_doubler ? GAYLE_NUM_HWIFS : \
GAYLE_NUM_HWIFS-1)
#define GAYLE_HAS_CONTROL_REG (!ide_doubler)
+#define GAYLE_IDEREG_SIZE (ide_doubler ? 0x1000 : 0x2000)
int ide_doubler = 0; /* support IDE doublers? */
#endif /* CONFIG_BLK_DEV_IDEDOUBLER */
@@ -121,23 +123,27 @@ void __init gayle_init(void)
ide_ack_intr_t *ack_intr;
hw_regs_t hw;
int index;
+ unsigned long phys_base, res_start, res_n;
if (a4000) {
- base = (ide_ioreg_t)ZTWO_VADDR(GAYLE_BASE_4000);
+ phys_base = GAYLE_BASE_4000;
irqport = (ide_ioreg_t)ZTWO_VADDR(GAYLE_IRQ_4000);
ack_intr = gayle_ack_intr_a4000;
} else {
- base = (ide_ioreg_t)ZTWO_VADDR(GAYLE_BASE_1200);
+ phys_base = GAYLE_BASE_1200;
irqport = (ide_ioreg_t)ZTWO_VADDR(GAYLE_IRQ_1200);
ack_intr = gayle_ack_intr_a1200;
}
+ phys_base += i*GAYLE_NEXT_PORT;
- if (GAYLE_HAS_CONTROL_REG)
- ctrlport = base + GAYLE_CONTROL;
- else
- ctrlport = 0;
+ res_start = ((unsigned long)phys_base) & ~(GAYLE_NEXT_PORT-1);
+ res_n = GAYLE_IDEREG_SIZE;
- base += i*GAYLE_NEXT_PORT;
+ if (!request_mem_region(res_start, res_n, "IDE"))
+ continue;
+
+ base = (ide_ioreg_t)ZTWO_VADDR(phys_base);
+ ctrlport = GAYLE_HAS_CONTROL_REG ? (base + GAYLE_CONTROL) : 0;
ide_setup_ports(&hw, base, gayle_offsets,
ctrlport, irqport, ack_intr, IRQ_AMIGA_PORTS);
@@ -155,7 +161,9 @@ void __init gayle_init(void)
break;
#endif /* CONFIG_BLK_DEV_IDEDOUBLER */
}
- }
+ } else
+ release_mem_region(res_start, res_n);
+
#if 1 /* TESTING */
if (i == 1) {
volatile u_short *addr = (u_short *)base;
diff --git a/drivers/ide/hd.c b/drivers/ide/hd.c
index eb73c2445..6fd109c83 100644
--- a/drivers/ide/hd.c
+++ b/drivers/ide/hd.c
@@ -889,7 +889,7 @@ static int parse_hd_setup (char *line) {
(void) get_options(line, ARRAY_SIZE(ints), ints);
hd_setup(NULL, ints);
- return 0;
+ return 1;
}
__setup("hd=", parse_hd_setup);
diff --git a/drivers/ide/hpt34x.c b/drivers/ide/hpt34x.c
index 911068f78..cbd71e60a 100644
--- a/drivers/ide/hpt34x.c
+++ b/drivers/ide/hpt34x.c
@@ -1,7 +1,7 @@
/*
- * linux/drivers/ide/hpt34x.c Version 0.30 Mar. 18, 2000
+ * linux/drivers/ide/hpt34x.c Version 0.31 June. 9, 2000
*
- * Copyright (C) 1998-2000 Andre Hedrick (andre@suse.com)
+ * Copyright (C) 1998-2000 Andre Hedrick <andre@linux-ide.org>
* May be copied or modified under the terms of the GNU General Public License
*
*
@@ -62,7 +62,7 @@ static struct pci_dev *bmide_dev;
static int hpt34x_get_info (char *buffer, char **addr, off_t offset, int count)
{
char *p = buffer;
- u32 bibma = bmide_dev->resource[4].start;
+ u32 bibma = pci_resource_start(bmide_dev, 4);
u8 c0 = 0, c1 = 0;
/*
@@ -360,7 +360,7 @@ int hpt34x_dmaproc (ide_dma_action_t func, ide_drive_t *drive)
unsigned int __init pci_init_hpt34x (struct pci_dev *dev, const char *name)
{
int i = 0;
- unsigned long hpt34xIoBase = dev->resource[4].start;
+ unsigned long hpt34xIoBase = pci_resource_start(dev, 4);
unsigned short cmd;
unsigned long flags;
@@ -371,7 +371,7 @@ unsigned int __init pci_init_hpt34x (struct pci_dev *dev, const char *name)
pci_read_config_word(dev, PCI_COMMAND, &cmd);
if (cmd & PCI_COMMAND_MEMORY) {
- if (dev->resource[PCI_ROM_RESOURCE].start) {
+ if (pci_resource_start(dev, PCI_ROM_RESOURCE)) {
pci_write_config_byte(dev, PCI_ROM_ADDRESS, dev->resource[PCI_ROM_RESOURCE].start | PCI_ROM_ADDRESS_ENABLE);
printk(KERN_INFO "HPT345: ROM enabled at 0x%08lx\n", dev->resource[PCI_ROM_RESOURCE].start);
}
diff --git a/drivers/ide/hpt366.c b/drivers/ide/hpt366.c
index 28232b576..74d3018c5 100644
--- a/drivers/ide/hpt366.c
+++ b/drivers/ide/hpt366.c
@@ -1,13 +1,16 @@
/*
- * linux/drivers/ide/hpt366.c Version 0.17 Mar. 18, 2000
+ * linux/drivers/ide/hpt366.c Version 0.18 June. 9, 2000
*
- * Copyright (C) 1999-2000 Andre Hedrick <andre@suse.com>
+ * Copyright (C) 1999-2000 Andre Hedrick <andre@linux-ide.org>
* May be copied or modified under the terms of the GNU General Public License
*
* Thanks to HighPoint Technologies for their assistance, and hardware.
* Special Thanks to Jon Burchmore in SanDiego for the deep pockets, his
* donation of an ABit BP6 mainboard, processor, and memory acellerated
* development and support.
+ *
+ * Note that final HPT370 support was done by force extraction of GPL.
+ *
*/
#include <linux/config.h>
@@ -30,13 +33,26 @@
#include "ide_modes.h"
-#undef DISPLAY_HPT366_TIMINGS
+#define DISPLAY_HPT366_TIMINGS
#if defined(DISPLAY_HPT366_TIMINGS) && defined(CONFIG_PROC_FS)
#include <linux/stat.h>
#include <linux/proc_fs.h>
#endif /* defined(DISPLAY_HPT366_TIMINGS) && defined(CONFIG_PROC_FS) */
+extern char *ide_dmafunc_verbose(ide_dma_action_t dmafunc);
+
+const char *quirk_drives[] = {
+ "QUANTUM FIREBALLlct08 08",
+ "QUANTUM FIREBALLP KA6.4",
+ "QUANTUM FIREBALLP LM20.5",
+ NULL
+};
+
+const char *bad_ata100_5[] = {
+ NULL
+};
+
const char *bad_ata66_4[] = {
"WDC AC310200R",
NULL
@@ -60,70 +76,92 @@ const char *bad_ata33[] = {
struct chipset_bus_clock_list_entry {
byte xfer_speed;
- unsigned int chipset_settings;
+ unsigned int chipset_settings_write;
+ unsigned int chipset_settings_read;
};
struct chipset_bus_clock_list_entry forty_base [] = {
- { XFER_UDMA_4 , 0x900fd943 },
- { XFER_UDMA_3 , 0x900ad943 },
- { XFER_UDMA_2 , 0x900bd943 },
- { XFER_UDMA_1 , 0x9008d943 },
- { XFER_UDMA_0 , 0x9008d943 },
-
- { XFER_MW_DMA_2 , 0xa008d943 },
- { XFER_MW_DMA_1 , 0xa010d955 },
- { XFER_MW_DMA_0 , 0xa010d9fc },
-
- { XFER_PIO_4 , 0xc008d963 },
- { XFER_PIO_3 , 0xc010d974 },
- { XFER_PIO_2 , 0xc010d997 },
- { XFER_PIO_1 , 0xc010d9c7 },
- { XFER_PIO_0 , 0xc018d9d9 },
- { 0 , 0x0120d9d9 }
+ { XFER_UDMA_4, 0x900fd943, 0x900fd943 },
+ { XFER_UDMA_3, 0x900ad943, 0x900ad943 },
+ { XFER_UDMA_2, 0x900bd943, 0x900bd943 },
+ { XFER_UDMA_1, 0x9008d943, 0x9008d943 },
+ { XFER_UDMA_0, 0x9008d943, 0x9008d943 },
+
+ { XFER_MW_DMA_2, 0xa008d943, 0xa008d943 },
+ { XFER_MW_DMA_1, 0xa010d955, 0xa010d955 },
+ { XFER_MW_DMA_0, 0xa010d9fc, 0xa010d9fc },
+
+ { XFER_PIO_4, 0xc008d963, 0xc008d963 },
+ { XFER_PIO_3, 0xc010d974, 0xc010d974 },
+ { XFER_PIO_2, 0xc010d997, 0xc010d997 },
+ { XFER_PIO_1, 0xc010d9c7, 0xc010d9c7 },
+ { XFER_PIO_0, 0xc018d9d9, 0xc018d9d9 },
+ { 0, 0x0120d9d9, 0x0120d9d9 }
};
struct chipset_bus_clock_list_entry thirty_three_base [] = {
- { XFER_UDMA_4 , 0x90c9a731 },
- { XFER_UDMA_3 , 0x90cfa731 },
- { XFER_UDMA_2 , 0x90caa731 },
- { XFER_UDMA_1 , 0x90cba731 },
- { XFER_UDMA_0 , 0x90c8a731 },
-
- { XFER_MW_DMA_2 , 0xa0c8a731 },
- { XFER_MW_DMA_1 , 0xa0c8a732 }, /* 0xa0c8a733 */
- { XFER_MW_DMA_0 , 0xa0c8a797 },
-
- { XFER_PIO_4 , 0xc0c8a731 },
- { XFER_PIO_3 , 0xc0c8a742 },
- { XFER_PIO_2 , 0xc0d0a753 },
- { XFER_PIO_1 , 0xc0d0a7a3 }, /* 0xc0d0a793 */
- { XFER_PIO_0 , 0xc0d0a7aa }, /* 0xc0d0a7a7 */
- { 0 , 0x0120a7a7 }
+ { XFER_UDMA_4, 0x90c9a731, 0x90c9a731 },
+ { XFER_UDMA_3, 0x90cfa731, 0x90cfa731 },
+ { XFER_UDMA_2, 0x90caa731, 0x90caa731 },
+ { XFER_UDMA_1, 0x90cba731, 0x90cba731 },
+ { XFER_UDMA_0, 0x90c8a731, 0x90c8a731 },
+
+ { XFER_MW_DMA_2, 0xa0c8a731, 0xa0c8a731 },
+ { XFER_MW_DMA_1, 0xa0c8a732, 0xa0c8a732 }, /* 0xa0c8a733 */
+ { XFER_MW_DMA_0, 0xa0c8a797, 0xa0c8a797 },
+
+ { XFER_PIO_4, 0xc0c8a731, 0xc0c8a731 },
+ { XFER_PIO_3, 0xc0c8a742, 0xc0c8a742 },
+ { XFER_PIO_2, 0xc0d0a753, 0xc0d0a753 },
+ { XFER_PIO_1, 0xc0d0a7a3, 0xc0d0a7a3 }, /* 0xc0d0a793 */
+ { XFER_PIO_0, 0xc0d0a7aa, 0xc0d0a7aa }, /* 0xc0d0a7a7 */
+ { 0, 0x0120a7a7, 0x0120a7a7 }
};
struct chipset_bus_clock_list_entry twenty_five_base [] = {
- { XFER_UDMA_4 , 0x90c98521 },
- { XFER_UDMA_3 , 0x90cf8521 },
- { XFER_UDMA_2 , 0x90cf8521 },
- { XFER_UDMA_1 , 0x90cb8521 },
- { XFER_UDMA_0 , 0x90cb8521 },
-
- { XFER_MW_DMA_2 , 0xa0ca8521 },
- { XFER_MW_DMA_1 , 0xa0ca8532 },
- { XFER_MW_DMA_0 , 0xa0ca8575 },
-
- { XFER_PIO_4 , 0xc0ca8521 },
- { XFER_PIO_3 , 0xc0ca8532 },
- { XFER_PIO_2 , 0xc0ca8542 },
- { XFER_PIO_1 , 0xc0d08572 },
- { XFER_PIO_0 , 0xc0d08585 },
- { 0 , 0x01208585 }
+ { XFER_UDMA_4, 0x90c98521, 0x90c98521 },
+ { XFER_UDMA_3, 0x90cf8521, 0x90cf8521 },
+ { XFER_UDMA_2, 0x90cf8521, 0x90cf8521 },
+ { XFER_UDMA_1, 0x90cb8521, 0x90cb8521 },
+ { XFER_UDMA_0, 0x90cb8521, 0x90cb8521 },
+
+ { XFER_MW_DMA_2, 0xa0ca8521, 0xa0ca8521 },
+ { XFER_MW_DMA_1, 0xa0ca8532, 0xa0ca8532 },
+ { XFER_MW_DMA_0, 0xa0ca8575, 0xa0ca8575 },
+
+ { XFER_PIO_4, 0xc0ca8521, 0xc0ca8521 },
+ { XFER_PIO_3, 0xc0ca8532, 0xc0ca8532 },
+ { XFER_PIO_2, 0xc0ca8542, 0xc0ca8542 },
+ { XFER_PIO_1, 0xc0d08572, 0xc0d08572 },
+ { XFER_PIO_0, 0xc0d08585, 0xc0d08585 },
+ { 0, 0x01208585, 0x01208585 }
+};
+
+struct chipset_bus_clock_list_entry thirty_three_base_hpt370[] = {
+ { XFER_UDMA_5, 0x1A85F442, 0x16454e31 },
+ { XFER_UDMA_4, 0x16454e31, 0x16454e31 },
+ { XFER_UDMA_3, 0x166d4e31, 0x166d4e31 },
+ { XFER_UDMA_2, 0x16494e31, 0x16494e31 },
+ { XFER_UDMA_1, 0x164d4e31, 0x164d4e31 },
+ { XFER_UDMA_0, 0x16514e31, 0x16514e31 },
+
+ { XFER_MW_DMA_2, 0x26514e21, 0x26514e21 },
+ { XFER_MW_DMA_1, 0x26514e33, 0x26514e33 },
+ { XFER_MW_DMA_0, 0x26514e97, 0x26514e97 },
+
+ { XFER_PIO_4, 0x06514e21, 0x06514e21 },
+ { XFER_PIO_3, 0x06514e22, 0x06514e22 },
+ { XFER_PIO_2, 0x06514e33, 0x06514e33 },
+ { XFER_PIO_1, 0x06914e43, 0x06914e43 },
+ { XFER_PIO_0, 0x06914e57, 0x06914e57 },
+ { 0, 0x06514e57, 0x06514e57 }
};
#define HPT366_DEBUG_DRIVE_INFO 0
+#define HPT370_ALLOW_ATA100_5 1
#define HPT366_ALLOW_ATA66_4 1
#define HPT366_ALLOW_ATA66_3 1
@@ -139,7 +177,12 @@ static int hpt366_get_info (char *buffer, char **addr, off_t offset, int count)
char *p = buffer;
u32 bibma = bmide_dev->resource[4].start;
u32 bibma2 = bmide2_dev->resource[4].start;
+ char *chipset_names[] = {"HPT366", "HPT366", "HPT368", "HPT370", "HPT370A"};
u8 c0 = 0, c1 = 0;
+ u32 class_rev;
+
+ pci_read_config_dword(bmide_dev, PCI_CLASS_REVISION, &class_rev);
+ class_rev &= 0xff;
/*
* at that point bibma+0x2 et bibma+0xa are byte registers
@@ -149,7 +192,7 @@ static int hpt366_get_info (char *buffer, char **addr, off_t offset, int count)
if (bmide2_dev)
c1 = inb_p((unsigned short)bibma2 + 0x02);
- p += sprintf(p, "\n HPT366 Chipset.\n");
+ p += sprintf(p, "\n %s Chipset.\n", chipset_names[class_rev]);
p += sprintf(p, "--------------- Primary Channel ---------------- Secondary Channel -------------\n");
p += sprintf(p, " %sabled %sabled\n",
(c0&0x80) ? "dis" : " en",
@@ -173,74 +216,74 @@ extern char *ide_xfer_verbose (byte xfer_rate);
byte hpt363_shared_irq = 0;
byte hpt363_shared_pin = 0;
-static unsigned int pci_rev_check_hpt366 (struct pci_dev *dev)
+static unsigned int pci_rev_check_hpt3xx (struct pci_dev *dev)
{
unsigned int class_rev;
pci_read_config_dword(dev, PCI_CLASS_REVISION, &class_rev);
class_rev &= 0xff;
- return ((int) (class_rev == 0x03) ? 1 : 0);
+ return ((int) (class_rev > 0x02) ? 1 : 0);
}
static int check_in_drive_lists (ide_drive_t *drive, const char **list)
{
struct hd_driveid *id = drive->id;
-#if HPT366_DEBUG_DRIVE_INFO
- printk("check_in_drive_lists(%s, %p)\n", drive->name, list);
-#endif /* HPT366_DEBUG_DRIVE_INFO */
- while (*list) {
- if (!strcmp(*list++,id->model)) {
-#ifdef DEBUG
- printk("%s: Broken ASIC, BackSpeeding (U)DMA for %s\n", drive->name, id->model);
-#endif /* DEBUG */
- return 1;
+ if (quirk_drives == list) {
+ while (*list) {
+ if (strstr(id->model, *list++)) {
+ return 1;
+ }
+ }
+ } else {
+ while (*list) {
+ if (!strcmp(*list++,id->model)) {
+ return 1;
+ }
}
}
return 0;
}
-static unsigned int pci_bus_clock_list (byte speed, struct chipset_bus_clock_list_entry * chipset_table)
+static unsigned int pci_bus_clock_list (byte speed, int direction, struct chipset_bus_clock_list_entry * chipset_table)
{
-#if HPT366_DEBUG_DRIVE_INFO
- printk("pci_bus_clock_list(speed=0x%02x, table=%p)\n", speed, chipset_table);
-#endif /* HPT366_DEBUG_DRIVE_INFO */
for ( ; chipset_table->xfer_speed ; chipset_table++)
if (chipset_table->xfer_speed == speed) {
-#if HPT366_DEBUG_DRIVE_INFO
- printk("pci_bus_clock_list: found match: 0x%08x\n", chipset_table->chipset_settings);
-#endif /* HPT366_DEBUG_DRIVE_INFO */
- return chipset_table->chipset_settings;
+ return (direction) ? chipset_table->chipset_settings_write : chipset_table->chipset_settings_read;
}
-#if HPT366_DEBUG_DRIVE_INFO
- printk("pci_bus_clock_list: using default: 0x%08x\n", 0x01208585);
-#endif /* HPT366_DEBUG_DRIVE_INFO */
- return 0x01208585;
+ return (direction) ? chipset_table->chipset_settings_write : chipset_table->chipset_settings_read;
}
-static int hpt366_tune_chipset (ide_drive_t *drive, byte speed)
+static void hpt366_tune_chipset (ide_drive_t *drive, byte speed, int direction)
{
- int err;
byte regtime = (drive->select.b.unit & 0x01) ? 0x44 : 0x40;
+ byte regfast = (HWIF(drive)->channel) ? 0x55 : 0x51;
+ /*
+ * since the channel is always 0 it does not matter.
+ */
+
unsigned int reg1 = 0;
unsigned int reg2 = 0;
+ byte drive_fast = 0;
-#if HPT366_DEBUG_DRIVE_INFO
- printk("hpt366_tune_chipset(%s, speed=0x%02x)\n", drive->name, speed);
-#endif /* HPT366_DEBUG_DRIVE_INFO */
+ /*
+ * Disable the "fast interrupt" prediction.
+ */
+ pci_read_config_byte(HWIF(drive)->pci_dev, regfast, &drive_fast);
+ if (drive_fast & 0x02)
+ pci_write_config_byte(HWIF(drive)->pci_dev, regfast, drive_fast & ~0x20);
pci_read_config_dword(HWIF(drive)->pci_dev, regtime, &reg1);
/* detect bus speed by looking at control reg timing: */
switch((reg1 >> 8) & 7) {
case 5:
- reg2 = pci_bus_clock_list(speed, forty_base);
+ reg2 = pci_bus_clock_list(speed, direction, forty_base);
break;
case 9:
- reg2 = pci_bus_clock_list(speed, twenty_five_base);
+ reg2 = pci_bus_clock_list(speed, direction, twenty_five_base);
break;
default:
- printk("hpt366: assuming 33Mhz PCI bus\n");
case 7:
- reg2 = pci_bus_clock_list(speed, thirty_three_base);
+ reg2 = pci_bus_clock_list(speed, direction, thirty_three_base);
break;
}
/*
@@ -254,18 +297,56 @@ static int hpt366_tune_chipset (ide_drive_t *drive, byte speed)
reg2 &= ~0x80000000;
pci_write_config_dword(HWIF(drive)->pci_dev, regtime, reg2);
- err = ide_config_drive_speed(drive, speed);
+}
+
+static void hpt370_tune_chipset (ide_drive_t *drive, byte speed, int direction)
+{
+ byte regfast = (HWIF(drive)->channel) ? 0x55 : 0x51;
+ byte reg5bh = (speed != XFER_UDMA_5) ? 0x22 : (direction) ? 0x20 : 0x22;
+ unsigned int list_conf = pci_bus_clock_list(speed, direction, thirty_three_base_hpt370);
+ unsigned int drive_conf = 0;
+ unsigned int conf_mask = (speed >= XFER_MW_DMA_0) ? 0xc0000000 : 0x30070000;
+ byte drive_pci = 0;
+ byte drive_fast = 0;
+
+ switch (drive->dn) {
+ case 0: drive_pci = 0x40; break;
+ case 1: drive_pci = 0x44; break;
+ case 2: drive_pci = 0x48; break;
+ case 3: drive_pci = 0x4c; break;
+ default: return;
+ }
+ /*
+ * Disable the "fast interrupt" prediction.
+ */
+ pci_read_config_byte(HWIF(drive)->pci_dev, regfast, &drive_fast);
+ if (drive_fast & 0x80)
+ pci_write_config_byte(HWIF(drive)->pci_dev, regfast, drive_fast & ~0x80);
+
+ pci_read_config_dword(HWIF(drive)->pci_dev, drive_pci, &drive_conf);
+ pci_write_config_byte(HWIF(drive)->pci_dev, 0x5b, reg5bh);
+
+ list_conf = (list_conf & ~conf_mask) | (drive_conf & conf_mask);
+ /*
+ * Disable on-chip PIO FIFO/buffer (to avoid problems handling I/O errors later)
+ */
+ list_conf &= ~0x80000000;
+
+ pci_write_config_dword(HWIF(drive)->pci_dev, drive_pci, list_conf);
+}
+static int hpt3xx_tune_chipset (ide_drive_t *drive, byte speed)
+{
if (!drive->init_speed)
drive->init_speed = speed;
-#if HPT366_DEBUG_DRIVE_INFO
- printk("%s: speed=0x%02x(%s), drive%d, old=0x%08x, new=0x%08x, err=0x%04x\n",
- drive->name, speed, ide_xfer_verbose(speed),
- drive->dn, reg1, reg2, err);
-#endif /* HPT366_DEBUG_DRIVE_INFO */
+ if (pci_rev_check_hpt3xx(HWIF(drive)->pci_dev)) {
+ hpt370_tune_chipset(drive, speed, 0);
+ } else {
+ hpt366_tune_chipset(drive, speed, 0);
+ }
drive->current_speed = speed;
- return(err);
+ return ((int) ide_config_drive_speed(drive, speed));
}
static void config_chipset_for_pio (ide_drive_t *drive)
@@ -274,9 +355,6 @@ static void config_chipset_for_pio (ide_drive_t *drive)
unsigned short xfer_pio = drive->id->eide_pio_modes;
byte timing, speed, pio;
-#if HPT366_DEBUG_DRIVE_INFO
- printk("%s: config_chipset_for_pio\n", drive->name);
-#endif /* HPT366_DEBUG_DRIVE_INFO */
pio = ide_get_best_pio_mode(drive, 255, 5, NULL);
if (xfer_pio> 4)
@@ -306,13 +384,10 @@ static void config_chipset_for_pio (ide_drive_t *drive)
speed = (!drive->id->tPIO) ? XFER_PIO_0 : XFER_PIO_SLOW;
break;
}
-#if HPT366_DEBUG_DRIVE_INFO
- printk("%s: config_chipset_for_pio: speed=0x%04x\n", drive->name, speed);
-#endif /* HPT366_DEBUG_DRIVE_INFO */
- (void) hpt366_tune_chipset(drive, speed);
+ (void) hpt3xx_tune_chipset(drive, speed);
}
-static void hpt366_tune_drive (ide_drive_t *drive, byte pio)
+static void hpt3xx_tune_drive (ide_drive_t *drive, byte pio)
{
byte speed;
switch(pio) {
@@ -322,7 +397,7 @@ static void hpt366_tune_drive (ide_drive_t *drive, byte pio)
case 1: speed = XFER_PIO_1;break;
default: speed = XFER_PIO_0;break;
}
- (void) hpt366_tune_chipset(drive, speed);
+ (void) hpt3xx_tune_chipset(drive, speed);
}
#ifdef CONFIG_BLK_DEV_IDEDMA
@@ -341,18 +416,24 @@ static int config_chipset_for_dma (ide_drive_t *drive)
{
struct hd_driveid *id = drive->id;
byte speed = 0x00;
- byte reg51h = 0;
+ byte ultra66 = eighty_ninty_three(drive);
int rval;
- if ((id->dma_ultra & 0x0010) &&
- (!check_in_drive_lists(drive, bad_ata66_4)) &&
- (HPT366_ALLOW_ATA66_4) &&
- (HWIF(drive)->udma_four)) {
+ if ((id->dma_ultra & 0x0020) &&
+ (!check_in_drive_lists(drive, bad_ata100_5)) &&
+ (HPT370_ALLOW_ATA100_5) &&
+ (pci_rev_check_hpt3xx(HWIF(drive)->pci_dev)) &&
+ (ultra66)) {
+ speed = XFER_UDMA_5;
+ } else if ((id->dma_ultra & 0x0010) &&
+ (!check_in_drive_lists(drive, bad_ata66_4)) &&
+ (HPT366_ALLOW_ATA66_4) &&
+ (ultra66)) {
speed = XFER_UDMA_4;
} else if ((id->dma_ultra & 0x0008) &&
(!check_in_drive_lists(drive, bad_ata66_3)) &&
(HPT366_ALLOW_ATA66_3) &&
- (HWIF(drive)->udma_four)) {
+ (ultra66)) {
speed = XFER_UDMA_3;
} else if (id->dma_ultra && (!check_in_drive_lists(drive, bad_ata33))) {
if (id->dma_ultra & 0x0004) {
@@ -368,52 +449,56 @@ static int config_chipset_for_dma (ide_drive_t *drive)
speed = XFER_MW_DMA_1;
} else if (id->dma_mword & 0x0001) {
speed = XFER_MW_DMA_0;
- } else if (id->dma_1word & 0x0004) {
- speed = XFER_SW_DMA_2;
- } else if (id->dma_1word & 0x0002) {
- speed = XFER_SW_DMA_1;
- } else if (id->dma_1word & 0x0001) {
- speed = XFER_SW_DMA_0;
- } else {
-#if HPT366_DEBUG_DRIVE_INFO
- printk("%s: config_chipset_for_dma: returning 'ide_dma_off_quietly'\n", drive->name);
-#endif /* HPT366_DEBUG_DRIVE_INFO */
+ } else {
return ((int) ide_dma_off_quietly);
}
- pci_read_config_byte(HWIF(drive)->pci_dev, 0x51, &reg51h);
+ (void) hpt3xx_tune_chipset(drive, speed);
-#ifdef CONFIG_HPT366_FIP
- /*
- * Some drives prefer/allow for the method of handling interrupts.
- */
- if (!(reg51h & 0x80))
- pci_write_config_byte(HWIF(drive)->pci_dev, 0x51, reg51h|0x80);
-#else /* ! CONFIG_HPT366_FIP */
- /*
- * Disable the "fast interrupt" prediction.
- * Instead, always wait for the real interrupt from the drive!
- */
- if (reg51h & 0x80)
- pci_write_config_byte(HWIF(drive)->pci_dev, 0x51, reg51h & ~0x80);
-#endif /* CONFIG_HPT366_FIP */
-#if HPT366_DEBUG_DRIVE_INFO
- printk("%s: config_chipset_for_dma: speed=0x%04x\n", drive->name, speed);
-#endif /* HPT366_DEBUG_DRIVE_INFO */
- (void) hpt366_tune_chipset(drive, speed);
-
- rval = (int)( ((id->dma_ultra >> 11) & 3) ? ide_dma_on :
+ rval = (int)( ((id->dma_ultra >> 11) & 7) ? ide_dma_on :
((id->dma_ultra >> 8) & 7) ? ide_dma_on :
((id->dma_mword >> 8) & 7) ? ide_dma_on :
- ((id->dma_1word >> 8) & 7) ? ide_dma_on :
ide_dma_off_quietly);
-
-#if HPT366_DEBUG_DRIVE_INFO
- printk("%s: config_chipset_for_dma: returning %d (%s)\n", drive->name, rval, rval == ide_dma_on ? "dma_on" : "dma_off");
-#endif /* HPT366_DEBUG_DRIVE_INFO */
return rval;
}
+int hpt3xx_quirkproc (ide_drive_t *drive)
+{
+ return ((int) check_in_drive_lists(drive, quirk_drives));
+}
+
+void hpt3xx_intrproc (ide_drive_t *drive)
+{
+}
+
+void hpt3xx_maskproc (ide_drive_t *drive, int mask)
+{
+ if (drive->quirk_list) {
+ if (pci_rev_check_hpt3xx(HWIF(drive)->pci_dev)) {
+ byte reg5a = 0;
+ pci_read_config_byte(HWIF(drive)->pci_dev, 0x5a, &reg5a);
+ if (((reg5a & 0x10) >> 4) != mask)
+ pci_write_config_byte(HWIF(drive)->pci_dev, 0x5a, mask ? (reg5a | 0x10) : (reg5a & ~0x10));
+ } else {
+ if (mask) {
+ disable_irq(HWIF(drive)->irq);
+ } else {
+ enable_irq(HWIF(drive)->irq);
+ }
+ }
+ } else {
+ if (IDE_CONTROL_REG)
+ OUT_BYTE(mask ? (drive->ctl | 2) : (drive->ctl & ~2), IDE_CONTROL_REG);
+ }
+}
+
+void hpt370_rw_proc (ide_drive_t *drive, ide_dma_action_t func)
+{
+ if ((func != ide_dma_write) || (func != ide_dma_read))
+ return;
+ hpt370_tune_chipset(drive, drive->current_speed, (func == ide_dma_write));
+}
+
static int config_drive_xfer_rate (ide_drive_t *drive)
{
struct hd_driveid *id = drive->id;
@@ -427,7 +512,7 @@ static int config_drive_xfer_rate (ide_drive_t *drive)
}
dma_func = ide_dma_off_quietly;
if (id->field_valid & 4) {
- if (id->dma_ultra & 0x001F) {
+ if (id->dma_ultra & 0x002F) {
/* Force if Capable UltraDMA */
dma_func = config_chipset_for_dma(drive);
if ((id->field_valid & 2) &&
@@ -436,8 +521,7 @@ static int config_drive_xfer_rate (ide_drive_t *drive)
}
} else if (id->field_valid & 2) {
try_dma_modes:
- if ((id->dma_mword & 0x0007) ||
- (id->dma_1word & 0x0007)) {
+ if (id->dma_mword & 0x0007) {
/* Force if Capable regular DMA modes */
dma_func = config_chipset_for_dma(drive);
if (dma_func != ide_dma_on)
@@ -472,24 +556,39 @@ no_dma_set:
*/
int hpt366_dmaproc (ide_dma_action_t func, ide_drive_t *drive)
{
- byte reg50h = 0;
+ byte reg50h = 0, reg52h = 0, reg5ah = 0;
switch (func) {
case ide_dma_check:
return config_drive_xfer_rate(drive);
case ide_dma_lostirq:
-#if 0
- pci_read_config_byte(HWIF(drive)->pci_dev, 0x50, &reg50h);
- pci_write_config_byte(HWIF(drive)->pci_dev, 0x50, reg50h|0x03);
pci_read_config_byte(HWIF(drive)->pci_dev, 0x50, &reg50h);
- /* ide_set_handler(drive, &ide_dma_intr, WAIT_CMD, NULL); */
-#endif
+ pci_read_config_byte(HWIF(drive)->pci_dev, 0x52, &reg52h);
+ pci_read_config_byte(HWIF(drive)->pci_dev, 0x5a, &reg5ah);
+ printk("%s: (%s) reg50h=0x%02x, reg52h=0x%02x, reg5ah=0x%02x\n",
+ drive->name,
+ ide_dmafunc_verbose(func),
+ reg50h, reg52h, reg5ah);
+ if (reg5ah & 0x10)
+ pci_write_config_byte(HWIF(drive)->pci_dev, 0x5a, reg5ah & ~0x10);
+ break;
case ide_dma_timeout:
default:
break;
}
return ide_dmaproc(func, drive); /* use standard DMA stuff */
}
+
+int hpt370_dmaproc (ide_dma_action_t func, ide_drive_t *drive)
+{
+ switch (func) {
+ case ide_dma_check:
+ return config_drive_xfer_rate(drive);
+ default:
+ break;
+ }
+ return ide_dmaproc(func, drive); /* use standard DMA stuff */
+}
#endif /* CONFIG_BLK_DEV_IDEDMA */
unsigned int __init pci_init_hpt366 (struct pci_dev *dev, const char *name)
@@ -519,7 +618,7 @@ unsigned int __init pci_init_hpt366 (struct pci_dev *dev, const char *name)
if (!hpt366_proc) {
hpt366_proc = 1;
bmide_dev = dev;
- if (pci_rev_check_hpt366(dev))
+ if (pci_rev_check_hpt3xx(dev))
bmide2_dev = dev;
hpt366_display_info = &hpt366_get_info;
}
@@ -546,14 +645,24 @@ unsigned int __init ata66_hpt366 (ide_hwif_t *hwif)
void __init ide_init_hpt366 (ide_hwif_t *hwif)
{
- if (pci_rev_check_hpt366(hwif->pci_dev)) return;
-
- hwif->tuneproc = &hpt366_tune_drive;
- hwif->speedproc = &hpt366_tune_chipset;
+ hwif->tuneproc = &hpt3xx_tune_drive;
+ hwif->speedproc = &hpt3xx_tune_chipset;
+ hwif->quirkproc = &hpt3xx_quirkproc;
+ hwif->intrproc = &hpt3xx_intrproc;
+ hwif->maskproc = &hpt3xx_maskproc;
#ifdef CONFIG_BLK_DEV_IDEDMA
if (hwif->dma_base) {
- hwif->dmaproc = &hpt366_dmaproc;
+ if (pci_rev_check_hpt3xx(hwif->pci_dev)) {
+ byte reg5ah = 0;
+ pci_read_config_byte(hwif->pci_dev, 0x5a, &reg5ah);
+ if (reg5ah & 0x10) /* interrupt force enable */
+ pci_write_config_byte(hwif->pci_dev, 0x5a, reg5ah & ~0x10);
+ hwif->dmaproc = &hpt370_dmaproc;
+ hwif->rwproc = &hpt370_rw_proc;
+ } else {
+ hwif->dmaproc = &hpt366_dmaproc;
+ }
hwif->autodma = 1;
} else {
hwif->autodma = 0;
@@ -571,19 +680,16 @@ void ide_dmacapable_hpt366 (ide_hwif_t *hwif, unsigned long dmabase)
{
byte masterdma = 0, slavedma = 0;
byte dma_new = 0, dma_old = inb(dmabase+2);
+ byte primary = hwif->channel ? 0x4b : 0x43;
+ byte secondary = hwif->channel ? 0x4f : 0x47;
unsigned long flags;
- if (pci_rev_check_hpt366(hwif->pci_dev)) {
- ide_setup_dma(hwif, dmabase, 8);
- return;
- }
-
__save_flags(flags); /* local CPU only */
__cli(); /* local CPU only */
dma_new = dma_old;
- pci_read_config_byte(hwif->pci_dev, 0x43, &masterdma);
- pci_read_config_byte(hwif->pci_dev, 0x47, &slavedma);
+ pci_read_config_byte(hwif->pci_dev, primary, &masterdma);
+ pci_read_config_byte(hwif->pci_dev, secondary, &slavedma);
if (masterdma & 0x30) dma_new |= 0x20;
if (slavedma & 0x30) dma_new |= 0x40;
diff --git a/drivers/ide/icside.c b/drivers/ide/icside.c
index dcc50362f..7d5bfaedf 100644
--- a/drivers/ide/icside.c
+++ b/drivers/ide/icside.c
@@ -351,7 +351,7 @@ icside_config_if(ide_drive_t *drive, int xfer_mode)
static int
icside_set_speed(ide_drive_t *drive, byte speed)
{
- return ((int) icside_config_if(drive, (int) speed));
+ return icside_config_if(drive, speed);
}
static int
@@ -508,9 +508,9 @@ icside_setup_dma(ide_hwif_t *hwif, int autodma)
goto failed;
}
- hwif->dmaproc = &icside_dmaproc;
+ hwif->speedproc = icside_set_speed;
+ hwif->dmaproc = icside_dmaproc;
hwif->autodma = autodma;
- hwif->speedproc = &icside_set_speed;
printk(" capable%s\n", autodma ?
", auto-enable" : "");
diff --git a/drivers/ide/ide-cd.c b/drivers/ide/ide-cd.c
index d209c29ff..ab4d3afbb 100644
--- a/drivers/ide/ide-cd.c
+++ b/drivers/ide/ide-cd.c
@@ -426,11 +426,13 @@ void cdrom_analyze_sense_data(ide_drive_t *drive,
while (hi > lo) {
mid = (lo + hi) / 2;
- if (packet_command_texts[mid].packet_command == failed_command->c[0]) {
+ if (packet_command_texts[mid].packet_command ==
+ failed_command->c[0]) {
s = packet_command_texts[mid].text;
break;
}
- else if (packet_command_texts[mid].packet_command > failed_command->c[0])
+ if (packet_command_texts[mid].packet_command >
+ failed_command->c[0])
hi = mid;
else
lo = mid+1;
@@ -1524,7 +1526,7 @@ cdrom_lockdoor(ide_drive_t *drive, int lockflag, struct request_sense *sense)
memset(&pc, 0, sizeof(pc));
pc.sense = sense;
pc.c[0] = GPCMD_PREVENT_ALLOW_MEDIUM_REMOVAL;
- pc.c[4] = lockflag ? 3 : 0;
+ pc.c[4] = lockflag ? 1 : 0;
stat = cdrom_queue_packet_command (drive, &pc);
}
@@ -1624,7 +1626,8 @@ static int cdrom_read_tocentry(ide_drive_t *drive, int trackno, int msf_flag,
/* Try to read the entire TOC for the disk into our internal buffer. */
static int cdrom_read_toc(ide_drive_t *drive, struct request_sense *sense)
{
- int stat, ntracks, i;
+ int minor, stat, ntracks, i;
+ kdev_t dev;
struct cdrom_info *info = drive->driver_data;
struct atapi_toc *toc = info->toc;
struct {
@@ -1663,8 +1666,10 @@ static int cdrom_read_toc(ide_drive_t *drive, struct request_sense *sense)
#endif /* not STANDARD_ATAPI */
ntracks = toc->hdr.last_track - toc->hdr.first_track + 1;
- if (ntracks <= 0) return -EIO;
- if (ntracks > MAX_TRACKS) ntracks = MAX_TRACKS;
+ if (ntracks <= 0)
+ return -EIO;
+ if (ntracks > MAX_TRACKS)
+ ntracks = MAX_TRACKS;
/* Now read the whole schmeer. */
stat = cdrom_read_tocentry(drive, toc->hdr.first_track, 1, 0,
@@ -1755,13 +1760,13 @@ static int cdrom_read_toc(ide_drive_t *drive, struct request_sense *sense)
toc->xa_flag = (ms_tmp.hdr.first_track != ms_tmp.hdr.last_track);
/* Now try to get the total cdrom capacity. */
-#if 0
- stat = cdrom_get_last_written(MKDEV(HWIF(drive)->major, minor),
- (long *)&toc->capacity);
+ minor = (drive->select.b.unit) << PARTN_BITS;
+ dev = MKDEV(HWIF(drive)->major, minor);
+ stat = cdrom_get_last_written(dev, (long *)&toc->capacity);
if (stat)
-#endif
- stat = cdrom_read_capacity(drive, &toc->capacity, sense);
- if (stat) toc->capacity = 0x1fffff;
+ stat = cdrom_read_capacity(drive, &toc->capacity, sense);
+ if (stat)
+ toc->capacity = 0x1fffff;
/* Remember that we've read this stuff. */
CDROM_STATE_FLAGS (drive)->toc_valid = 1;
@@ -2552,7 +2557,8 @@ unsigned long ide_cdrom_capacity (ide_drive_t *drive)
{
unsigned capacity;
- return cdrom_read_capacity(drive, &capacity, NULL) ? 0 : capacity * SECTORS_PER_FRAME;
+ return cdrom_read_capacity(drive, &capacity, NULL)
+ ? 0 : capacity * SECTORS_PER_FRAME;
}
static
diff --git a/drivers/ide/ide-disk.c b/drivers/ide/ide-disk.c
index 4e2952018..ae9f62768 100644
--- a/drivers/ide/ide-disk.c
+++ b/drivers/ide/ide-disk.c
@@ -1,14 +1,13 @@
/*
- * linux/drivers/ide/ide-disk.c Version 1.09 April 23, 1999
+ * linux/drivers/ide/ide-disk.c Version 1.10 June 9, 2000
*
* Copyright (C) 1994-1998 Linus Torvalds & authors (see below)
*/
/*
* Mostly written by Mark Lord <mlord@pobox.com>
- * and Gadi Oxman <gadio@netvision.net.il>
- *
- * See linux/MAINTAINERS for address of current maintainer.
+ * and Gadi Oxman <gadio@netvision.net.il>
+ * and Andre Hedrick <andre@linux-ide.org>
*
* This is the IDE/ATA disk driver, as evolved from hd.c and ide.c.
*
@@ -27,9 +26,10 @@
* the entire disk.
* Version 1.09 added increment of rq->sector in ide_multwrite
* added UDMA 3/4 reporting
+ * Version 1.10 request queue changes, Ultra DMA 100
*/
-#define IDEDISK_VERSION "1.09"
+#define IDEDISK_VERSION "1.10"
#undef REALLY_SLOW_IO /* most systems can safely undef this */
@@ -140,11 +140,8 @@ static ide_startstop_t read_intr (ide_drive_t *drive)
int i;
unsigned int msect, nsect;
struct request *rq;
-#if 0
- if (!OK_STAT(stat=GET_STAT(),DATA_READY,BAD_R_STAT)) {
- return ide_error(drive, "read_intr", stat);
- }
-#else /* new way for dealing with premature shared PCI interrupts */
+
+ /* new way for dealing with premature shared PCI interrupts */
if (!OK_STAT(stat=GET_STAT(),DATA_READY,BAD_R_STAT)) {
if (stat & (ERR_STAT|DRQ_STAT)) {
return ide_error(drive, "read_intr", stat);
@@ -153,7 +150,6 @@ static ide_startstop_t read_intr (ide_drive_t *drive)
ide_set_handler(drive, &read_intr, WAIT_CMD, NULL);
return ide_started;
}
-#endif
msect = drive->mult_count;
read_next:
@@ -688,7 +684,6 @@ static int set_nowerr(ide_drive_t *drive, int arg)
{
if (ide_spin_wait_hwgroup(drive))
return -EBUSY;
-
drive->nowerr = arg;
drive->bad_wstat = arg ? BAD_R_STAT : BAD_W_STAT;
spin_unlock_irq(&io_request_lock);
diff --git a/drivers/ide/ide-dma.c b/drivers/ide/ide-dma.c
index 835fa91e3..e9a34afc1 100644
--- a/drivers/ide/ide-dma.c
+++ b/drivers/ide/ide-dma.c
@@ -1,7 +1,7 @@
/*
- * linux/drivers/ide/ide-dma.c Version 4.09 April 23, 1999
+ * linux/drivers/ide/ide-dma.c Version 4.10 June 9, 2000
*
- * Copyright (c) 1999 Andre Hedrick
+ * Copyright (c) 1999-2000 Andre Hedrick <andre@linux-ide.org>
* May be copied or modified under the terms of the GNU General Public License
*/
@@ -70,12 +70,11 @@
*
* And, yes, Intel Zappa boards really *do* use both PIIX IDE ports.
*
- * ACARD ATP850UF Chipset "Modified SCSI Class" with other names
- * AEC6210 U/UF
- * SIIG's UltraIDE Pro CN-2449
- * TTI HPT343 Chipset "Modified SCSI Class" but reports as an
- * unknown storage device.
- * NEW check_drive_lists(ide_drive_t *drive, int good_bad)
+ * check_drive_lists(ide_drive_t *drive, int good_bad)
+ *
+ * ATA-66/100 and recovery functions, I forgot the rest......
+ * SELECT_READ_WRITE(hwif,drive,func) for active tuning based on IO direction.
+ *
*/
#include <linux/config.h>
@@ -358,10 +357,11 @@ int report_drive_dmaing (ide_drive_t *drive)
{
struct hd_driveid *id = drive->id;
- if ((id->field_valid & 4) && (id->hw_config & 0x2000) &&
- (HWIF(drive)->udma_four) &&
- (id->dma_ultra & (id->dma_ultra >> 11) & 3)) {
- if ((id->dma_ultra >> 12) & 1) {
+ if ((id->field_valid & 4) && (eighty_ninty_three(drive)) &&
+ (id->dma_ultra & (id->dma_ultra >> 11) & 7)) {
+ if ((id->dma_ultra >> 13) & 1) {
+ printk(", UDMA(100)"); /* UDMA BIOS-enabled! */
+ } else if ((id->dma_ultra >> 12) & 1) {
printk(", UDMA(66)"); /* UDMA BIOS-enabled! */
} else {
printk(", UDMA(44)"); /* UDMA BIOS-enabled! */
@@ -393,9 +393,9 @@ static int config_drive_for_dma (ide_drive_t *drive)
if (ide_dmaproc(ide_dma_bad_drive, drive))
return hwif->dmaproc(ide_dma_off, drive);
- /* Enable DMA on any drive that has UltraDMA (mode 3/4) enabled */
- if ((id->field_valid & 4) && (hwif->udma_four) && (id->hw_config & 0x2000))
- if ((id->dma_ultra & (id->dma_ultra >> 11) & 3))
+ /* Enable DMA on any drive that has UltraDMA (mode 3/4/5) enabled */
+ if ((id->field_valid & 4) && (eighty_ninty_three(drive)))
+ if ((id->dma_ultra & (id->dma_ultra >> 11) & 7))
return hwif->dmaproc(ide_dma_on, drive);
/* Enable DMA on any drive that has UltraDMA (mode 0/1/2) enabled */
if (id->field_valid & 4) /* UltraDMA */
@@ -413,6 +413,22 @@ static int config_drive_for_dma (ide_drive_t *drive)
}
/*
+ * 1 dmaing, 2 error, 4 intr
+ */
+static int dma_timer_expiry (ide_drive_t *drive)
+{
+ byte dma_stat = inb(HWIF(drive)->dma_base+2);
+
+#ifdef DEBUG
+ printk("%s: dma_timer_expiry: dma status == 0x%02x\n", drive->name, dma_stat);
+#endif /* DEBUG */
+
+ if (dma_stat & 1) /* DMAing */
+ return WAIT_CMD;
+ return 0;
+}
+
+/*
* ide_dmaproc() initiates/aborts DMA read/write operations on a drive.
*
* The caller is assumed to have selected the drive and programmed the drive's
@@ -451,6 +467,7 @@ int ide_dmaproc (ide_dma_action_t func, ide_drive_t *drive)
case ide_dma_read:
reading = 1 << 3;
case ide_dma_write:
+ SELECT_READ_WRITE(hwif,drive,func);
if (!(count = ide_build_dmatable(drive, func)))
return 1; /* try PIO instead of DMA */
outl(hwif->dmatable_dma, dma_base + 4); /* PRD table */
@@ -459,7 +476,7 @@ int ide_dmaproc (ide_dma_action_t func, ide_drive_t *drive)
drive->waiting_for_dma = 1;
if (drive->media != ide_disk)
return 0;
- ide_set_handler(drive, &ide_dma_intr, WAIT_CMD, NULL); /* issue cmd to drive */
+ ide_set_handler(drive, &ide_dma_intr, WAIT_CMD, dma_timer_expiry); /* issue cmd to drive */
OUT_BYTE(reading ? WIN_READDMA : WIN_WRITEDMA, IDE_COMMAND_REG);
case ide_dma_begin:
/* Note that this is done *after* the cmd has
@@ -570,8 +587,8 @@ unsigned long __init ide_get_or_set_dma_base (ide_hwif_t *hwif, int extra, const
if (hwif->mate && hwif->mate->dma_base) {
dma_base = hwif->mate->dma_base - (hwif->channel ? 0 : 8);
} else {
- dma_base = dev->resource[4].start;
- if (!dma_base || dma_base == PCI_BASE_ADDRESS_IO_MASK) {
+ dma_base = pci_resource_start(dev, 4);
+ if (!dma_base) {
printk("%s: dma_base is invalid (0x%04lx)\n", name, dma_base);
dma_base = 0;
}
diff --git a/drivers/ide/ide-features.c b/drivers/ide/ide-features.c
index cb3790fa6..967b91e55 100644
--- a/drivers/ide/ide-features.c
+++ b/drivers/ide/ide-features.c
@@ -1,14 +1,16 @@
/*
- * linux/drivers/block/ide-features.c Version 0.03 Feb. 10, 2000
+ * linux/drivers/block/ide-features.c Version 0.04 June 9, 2000
*
* Copyright (C) 1999-2000 Linus Torvalds & authors (see below)
*
- * Copyright (C) 1999-2000 Andre Hedrick <andre@suse.com>
+ * Copyright (C) 1999-2000 Andre Hedrick <andre@linux-ide.org>
*
* Extracts if ide.c to address the evolving transfer rate code for
* the SETFEATURES_XFER callouts. Various parts of any given function
* are credited to previous ATA-IDE maintainers.
*
+ * Auto-CRC downgrade for Ultra DMA(ing)
+ *
* May be copied or modified under the terms of the GNU General Public License
*/
@@ -115,6 +117,10 @@ char *ide_dmafunc_verbose (ide_dma_action_t dmafunc)
*/
byte ide_auto_reduce_xfer (ide_drive_t *drive)
{
+ if (!drive->crc_count)
+ return drive->current_speed;
+ drive->crc_count = 0;
+
switch(drive->current_speed) {
case XFER_UDMA_7: return XFER_UDMA_6;
case XFER_UDMA_6: return XFER_UDMA_5;
@@ -164,6 +170,7 @@ int ide_driveid_update (ide_drive_t *drive)
probe_irq_off(probe_irq_on());
irqs = probe_irq_on();
+ SELECT_MASK(HWIF(drive), drive, 1);
if (IDE_CONTROL_REG)
OUT_BYTE(drive->ctl,IDE_CONTROL_REG);
ide_delay_50ms();
@@ -173,17 +180,20 @@ int ide_driveid_update (ide_drive_t *drive)
if (0 < (signed long)(jiffies - timeout)) {
if (irqs)
(void) probe_irq_off(irqs);
+ SELECT_MASK(HWIF(drive), drive, 0);
return 0; /* drive timed-out */
}
ide_delay_50ms(); /* give drive a breather */
} while (IN_BYTE(IDE_ALTSTATUS_REG) & BUSY_STAT);
ide_delay_50ms(); /* wait for IRQ and DRQ_STAT */
if (!OK_STAT(GET_STAT(),DRQ_STAT,BAD_R_STAT)) {
+ SELECT_MASK(HWIF(drive), drive, 0);
printk("%s: CHECK for good STATUS\n", drive->name);
return 0;
}
__save_flags(flags); /* local CPU only */
__cli(); /* local CPU only; some systems need this */
+ SELECT_MASK(HWIF(drive), drive, 0);
id = kmalloc(SECTOR_WORDS*4, GFP_ATOMIC);
ide_input_data(drive, id, SECTOR_WORDS);
(void) GET_STAT(); /* clear drive IRQ */
@@ -214,11 +224,15 @@ int ide_ata66_check (ide_drive_t *drive, byte cmd, byte nsect, byte feature)
(nsect > XFER_UDMA_2) &&
(feature == SETFEATURES_XFER)) {
if (!HWIF(drive)->udma_four) {
- printk("%s: Speed warnings UDMA 3/4 is not functional.\n", HWIF(drive)->name);
+ printk("%s: Speed warnings UDMA 3/4/5 is not functional.\n", HWIF(drive)->name);
return 1;
}
+#ifndef CONFIG_IDEDMA_IVB
+ if ((drive->id->hw_config & 0x6000) == 0) {
+#else /* !CONFIG_IDEDMA_IVB */
if ((drive->id->hw_config & 0x2000) == 0) {
- printk("%s: Speed warnings UDMA 3/4 is not functional.\n", drive->name);
+#endif /* CONFIG_IDEDMA_IVB */
+ printk("%s: Speed warnings UDMA 3/4/5 is not functional.\n", drive->name);
return 1;
}
}
@@ -244,6 +258,18 @@ int set_transfer (ide_drive_t *drive, byte cmd, byte nsect, byte feature)
}
/*
+ * All hosts that use the 80c ribbon mus use!
+ */
+byte eighty_ninty_three (ide_drive_t *drive)
+{
+ return ((byte) ((HWIF(drive)->udma_four) &&
+#ifndef CONFIG_IDEDMA_IVB
+ (drive->id->hw_config & 0x4000) &&
+#endif /* CONFIG_IDEDMA_IVB */
+ (drive->id->hw_config & 0x2000)) ? 1 : 0);
+}
+
+/*
* Similar to ide_wait_stat(), except it never calls ide_error internally.
* This is a kludge to handle the new ide_config_drive_speed() function,
* and should not otherwise be used anywhere. Eventually, the tuneproc's
@@ -260,10 +286,11 @@ int ide_config_drive_speed (ide_drive_t *drive, byte speed)
int i, error = 1;
byte stat;
-#ifdef CONFIG_BLK_DEV_IDEDMA_PCI
+#if defined(CONFIG_BLK_DEV_IDEDMA) && !defined(CONFIG_DMA_NONPCI)
byte unit = (drive->select.b.unit & 0x01);
outb(inb(hwif->dma_base+2) & ~(1<<(5+unit)), hwif->dma_base+2);
-#endif /* CONFIG_BLK_DEV_IDEDMA_PCI */
+#endif /* (CONFIG_BLK_DEV_IDEDMA) && !(CONFIG_DMA_NONPCI) */
+
/*
* Don't use ide_wait_cmd here - it will
* attempt to set_geometry and recalibrate,
@@ -276,6 +303,7 @@ int ide_config_drive_speed (ide_drive_t *drive, byte speed)
disable_irq(hwif->irq); /* disable_irq_nosync ?? */
udelay(1);
SELECT_DRIVE(HWIF(drive), drive);
+ SELECT_MASK(HWIF(drive), drive, 0);
udelay(1);
if (IDE_CONTROL_REG)
OUT_BYTE(drive->ctl | 2, IDE_CONTROL_REG);
@@ -315,6 +343,8 @@ int ide_config_drive_speed (ide_drive_t *drive, byte speed)
}
}
+ SELECT_MASK(HWIF(drive), drive, 0);
+
enable_irq(hwif->irq);
if (error) {
@@ -326,13 +356,13 @@ int ide_config_drive_speed (ide_drive_t *drive, byte speed)
drive->id->dma_mword &= ~0x0F00;
drive->id->dma_1word &= ~0x0F00;
-#ifdef CONFIG_BLK_DEV_IDEDMA_PCI
+#if defined(CONFIG_BLK_DEV_IDEDMA) && !defined(CONFIG_DMA_NONPCI)
if (speed > XFER_PIO_4) {
outb(inb(hwif->dma_base+2)|(1<<(5+unit)), hwif->dma_base+2);
} else {
outb(inb(hwif->dma_base+2) & ~(1<<(5+unit)), hwif->dma_base+2);
}
-#endif /* CONFIG_BLK_DEV_IDEDMA_PCI */
+#endif /* (CONFIG_BLK_DEV_IDEDMA) && !(CONFIG_DMA_NONPCI) */
switch(speed) {
case XFER_UDMA_7: drive->id->dma_ultra |= 0x8080; break;
@@ -358,5 +388,5 @@ EXPORT_SYMBOL(ide_auto_reduce_xfer);
EXPORT_SYMBOL(ide_driveid_update);
EXPORT_SYMBOL(ide_ata66_check);
EXPORT_SYMBOL(set_transfer);
+EXPORT_SYMBOL(eighty_ninty_three);
EXPORT_SYMBOL(ide_config_drive_speed);
-
diff --git a/drivers/ide/ide-geometry.c b/drivers/ide/ide-geometry.c
index a29178597..639d4c6f1 100644
--- a/drivers/ide/ide-geometry.c
+++ b/drivers/ide/ide-geometry.c
@@ -3,7 +3,7 @@
*/
#include <linux/config.h>
-#if defined(CONFIG_IDE) && !defined(CONFIG_BLK_DEV_HD)
+#if defined(CONFIG_IDE) && !defined(CONFIG_BLK_DEV_HD_ONLY)
#include <linux/ide.h>
#include <asm/io.h>
@@ -211,4 +211,4 @@ int ide_xlate_1024 (kdev_t i_rdev, int xparm, int ptheads, const char *msg)
drive->bios_cyl, drive->bios_head, drive->bios_sect);
return ret;
}
-#endif /* (CONFIG_IDE) && !(CONFIG_BLK_DEV_HD) */
+#endif /* (CONFIG_IDE) && !(CONFIG_BLK_DEV_HD_ONLY) */
diff --git a/drivers/ide/ide-pci.c b/drivers/ide/ide-pci.c
index c10ae4b51..8c9354394 100644
--- a/drivers/ide/ide-pci.c
+++ b/drivers/ide/ide-pci.c
@@ -1,5 +1,5 @@
/*
- * linux/drivers/ide/ide-pci.c Version 1.04 July 27, 1999
+ * linux/drivers/ide/ide-pci.c Version 1.05 June 9, 2000
*
* Copyright (c) 1998-2000 Andre Hedrick <andre@linux-ide.org>
*
@@ -33,10 +33,13 @@
#define DEVID_PIIX4E2 ((ide_pci_devid_t){PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_82443MX_1})
#define DEVID_PIIX4U ((ide_pci_devid_t){PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_82801AA_1})
#define DEVID_PIIX4U2 ((ide_pci_devid_t){PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_82372FB_1})
+#define DEVID_PIIX4NX ((ide_pci_devid_t){PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_82451NX})
+#define DEVID_PIIX4U3 ((ide_pci_devid_t){PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_82820FW_5})
#define DEVID_VIA_IDE ((ide_pci_devid_t){PCI_VENDOR_ID_VIA, PCI_DEVICE_ID_VIA_82C561})
#define DEVID_VP_IDE ((ide_pci_devid_t){PCI_VENDOR_ID_VIA, PCI_DEVICE_ID_VIA_82C586_1})
#define DEVID_PDC20246 ((ide_pci_devid_t){PCI_VENDOR_ID_PROMISE, PCI_DEVICE_ID_PROMISE_20246})
#define DEVID_PDC20262 ((ide_pci_devid_t){PCI_VENDOR_ID_PROMISE, PCI_DEVICE_ID_PROMISE_20262})
+#define DEVID_PDC20267 ((ide_pci_devid_t){PCI_VENDOR_ID_PROMISE, PCI_DEVICE_ID_PROMISE_20267})
#define DEVID_RZ1000 ((ide_pci_devid_t){PCI_VENDOR_ID_PCTECH, PCI_DEVICE_ID_PCTECH_RZ1000})
#define DEVID_RZ1001 ((ide_pci_devid_t){PCI_VENDOR_ID_PCTECH, PCI_DEVICE_ID_PCTECH_RZ1001})
#define DEVID_SAMURAI ((ide_pci_devid_t){PCI_VENDOR_ID_PCTECH, PCI_DEVICE_ID_PCTECH_SAMURAI_IDE})
@@ -44,6 +47,7 @@
#define DEVID_CMD643 ((ide_pci_devid_t){PCI_VENDOR_ID_CMD, PCI_DEVICE_ID_CMD_643})
#define DEVID_CMD646 ((ide_pci_devid_t){PCI_VENDOR_ID_CMD, PCI_DEVICE_ID_CMD_646})
#define DEVID_CMD648 ((ide_pci_devid_t){PCI_VENDOR_ID_CMD, PCI_DEVICE_ID_CMD_648})
+#define DEVID_CMD649 ((ide_pci_devid_t){PCI_VENDOR_ID_CMD, PCI_DEVICE_ID_CMD_649})
#define DEVID_SIS5513 ((ide_pci_devid_t){PCI_VENDOR_ID_SI, PCI_DEVICE_ID_SI_5513})
#define DEVID_OPTI621 ((ide_pci_devid_t){PCI_VENDOR_ID_OPTI, PCI_DEVICE_ID_OPTI_82C621})
#define DEVID_OPTI621V ((ide_pci_devid_t){PCI_VENDOR_ID_OPTI, PCI_DEVICE_ID_OPTI_82C558})
@@ -65,6 +69,7 @@
#define DEVID_CY82C693 ((ide_pci_devid_t){PCI_VENDOR_ID_CONTAQ, PCI_DEVICE_ID_CONTAQ_82C693})
#define DEVID_HINT ((ide_pci_devid_t){0x3388, 0x8013})
#define DEVID_CS5530 ((ide_pci_devid_t){PCI_VENDOR_ID_CYRIX, PCI_DEVICE_ID_CYRIX_5530_IDE})
+#define DEVID_AMD7403 ((ide_pci_devid_t){PCI_VENDOR_ID_AMD, PCI_DEVICE_ID_AMD_COBRA_7403})
#define DEVID_AMD7409 ((ide_pci_devid_t){PCI_VENDOR_ID_AMD, PCI_DEVICE_ID_AMD_VIPER_7409})
#define IDE_IGNORE ((void *)-1)
@@ -288,7 +293,7 @@ typedef struct ide_pci_enablebit_s {
typedef struct ide_pci_device_s {
ide_pci_devid_t devid;
- const char *name;
+ char *name;
unsigned int (*init_chipset)(struct pci_dev *dev, const char *name);
unsigned int (*ata66_check)(ide_hwif_t *hwif);
void (*init_hwif)(ide_hwif_t *hwif);
@@ -307,10 +312,13 @@ static ide_pci_device_t ide_pci_chipsets[] __initdata = {
{DEVID_PIIX4E2, "PIIX4", PCI_PIIX, NULL, INIT_PIIX, NULL, {{0x41,0x80,0x80}, {0x43,0x80,0x80}}, ON_BOARD, 0 },
{DEVID_PIIX4U, "PIIX4", PCI_PIIX, ATA66_PIIX, INIT_PIIX, NULL, {{0x41,0x80,0x80}, {0x43,0x80,0x80}}, ON_BOARD, 0 },
{DEVID_PIIX4U2, "PIIX4", PCI_PIIX, ATA66_PIIX, INIT_PIIX, NULL, {{0x41,0x80,0x80}, {0x43,0x80,0x80}}, ON_BOARD, 0 },
+ {DEVID_PIIX4NX, "PIIX4", PCI_PIIX, NULL, INIT_PIIX, NULL, {{0x41,0x80,0x80}, {0x43,0x80,0x80}}, ON_BOARD, 0 },
+ {DEVID_PIIX4U3, "PIIX4", PCI_PIIX, ATA66_PIIX, INIT_PIIX, NULL, {{0x41,0x80,0x80}, {0x43,0x80,0x80}}, ON_BOARD, 0 },
{DEVID_VIA_IDE, "VIA_IDE", NULL, NULL, NULL, NULL, {{0x00,0x00,0x00}, {0x00,0x00,0x00}}, ON_BOARD, 0 },
{DEVID_VP_IDE, "VP_IDE", PCI_VIA82CXXX, ATA66_VIA82CXXX,INIT_VIA82CXXX, DMA_VIA82CXXX, {{0x40,0x02,0x02}, {0x40,0x01,0x01}}, ON_BOARD, 0 },
{DEVID_PDC20246,"PDC20246", PCI_PDC202XX, NULL, INIT_PDC202XX, NULL, {{0x50,0x02,0x02}, {0x50,0x04,0x04}}, OFF_BOARD, 16 },
{DEVID_PDC20262,"PDC20262", PCI_PDC202XX, ATA66_PDC202XX, INIT_PDC202XX, NULL, {{0x50,0x02,0x02}, {0x50,0x04,0x04}}, OFF_BOARD, 48 },
+ {DEVID_PDC20267,"PDC20267", PCI_PDC202XX, ATA66_PDC202XX, INIT_PDC202XX, NULL, {{0x50,0x02,0x02}, {0x50,0x04,0x04}}, OFF_BOARD, 48 },
{DEVID_RZ1000, "RZ1000", NULL, NULL, INIT_RZ1000, NULL, {{0x00,0x00,0x00}, {0x00,0x00,0x00}}, ON_BOARD, 0 },
{DEVID_RZ1001, "RZ1001", NULL, NULL, INIT_RZ1000, NULL, {{0x00,0x00,0x00}, {0x00,0x00,0x00}}, ON_BOARD, 0 },
{DEVID_SAMURAI, "SAMURAI", NULL, NULL, INIT_SAMURAI, NULL, {{0x00,0x00,0x00}, {0x00,0x00,0x00}}, ON_BOARD, 0 },
@@ -320,6 +328,7 @@ static ide_pci_device_t ide_pci_chipsets[] __initdata = {
{DEVID_CMD643, "CMD643", PCI_CMD64X, NULL, INIT_CMD64X, NULL, {{0x00,0x00,0x00}, {0x00,0x00,0x00}}, ON_BOARD, 0 },
{DEVID_CMD646, "CMD646", PCI_CMD64X, NULL, INIT_CMD64X, NULL, {{0x00,0x00,0x00}, {0x51,0x80,0x80}}, ON_BOARD, 0 },
{DEVID_CMD648, "CMD648", PCI_CMD64X, ATA66_CMD64X, INIT_CMD64X, NULL, {{0x00,0x00,0x00}, {0x00,0x00,0x00}}, ON_BOARD, 0 },
+ {DEVID_CMD649, "CMD649", PCI_CMD64X, ATA66_CMD64X, INIT_CMD64X, NULL, {{0x00,0x00,0x00}, {0x00,0x00,0x00}}, ON_BOARD, 0 },
{DEVID_HT6565, "HT6565", NULL, NULL, NULL, NULL, {{0x00,0x00,0x00}, {0x00,0x00,0x00}}, ON_BOARD, 0 },
{DEVID_OPTI621, "OPTI621", NULL, NULL, INIT_OPTI621, NULL, {{0x45,0x80,0x00}, {0x40,0x08,0x00}}, ON_BOARD, 0 },
{DEVID_OPTI621X,"OPTI621X", NULL, NULL, INIT_OPTI621, NULL, {{0x45,0x80,0x00}, {0x40,0x08,0x00}}, ON_BOARD, 0 },
@@ -338,6 +347,7 @@ static ide_pci_device_t ide_pci_chipsets[] __initdata = {
{DEVID_CY82C693,"CY82C693", PCI_CY82C693, NULL, INIT_CY82C693, NULL, {{0x00,0x00,0x00}, {0x00,0x00,0x00}}, ON_BOARD, 0 },
{DEVID_HINT, "HINT_IDE", NULL, NULL, NULL, NULL, {{0x00,0x00,0x00}, {0x00,0x00,0x00}}, ON_BOARD, 0 },
{DEVID_CS5530, "CS5530", PCI_CS5530, NULL, INIT_CS5530, NULL, {{0x00,0x00,0x00}, {0x00,0x00,0x00}}, ON_BOARD, 0 },
+ {DEVID_AMD7403, "AMD7403", NULL, NULL, NULL, NULL, {{0x00,0x00,0x00}, {0x00,0x00,0x00}}, ON_BOARD, 0 },
{DEVID_AMD7409, "AMD7409", PCI_AMD7409, ATA66_AMD7409, INIT_AMD7409, DMA_AMD7409, {{0x40,0x01,0x01}, {0x40,0x02,0x02}}, ON_BOARD, 0 },
{IDE_PCI_DEVID_NULL, "PCI_IDE", NULL, NULL, NULL, NULL, {{0x00,0x00,0x00}, {0x00,0x00,0x00}}, ON_BOARD, 0 }};
@@ -352,6 +362,7 @@ static unsigned int __init ide_special_settings (struct pci_dev *dev, const char
case PCI_DEVICE_ID_TTI_HPT366:
case PCI_DEVICE_ID_PROMISE_20246:
case PCI_DEVICE_ID_PROMISE_20262:
+ case PCI_DEVICE_ID_PROMISE_20267:
case PCI_DEVICE_ID_ARTOP_ATP850UF:
case PCI_DEVICE_ID_ARTOP_ATP860:
case PCI_DEVICE_ID_ARTOP_ATP860R:
@@ -510,6 +521,14 @@ check_if_enabled:
pci_read_config_dword(dev, PCI_CLASS_REVISION, &class_rev);
class_rev &= 0xff;
+
+ if (IDE_PCI_DEVID_EQ(d->devid, DEVID_HPT34X)) {
+ /* see comments in hpt34x.c on why..... */
+ char *chipset_names[] = {"HPT343", "HPT345"};
+ strcpy(d->name, chipset_names[(pcicmd & PCI_COMMAND_MEMORY)]);
+ d->bootable = (pcicmd & PCI_COMMAND_MEMORY) ? OFF_BOARD : NEVER_BOARD;
+ }
+
printk("%s: chipset revision %d\n", d->name, class_rev);
/*
@@ -541,10 +560,7 @@ check_if_enabled:
printk("%s: 100%% native mode on irq %d\n", d->name, pciirq);
#endif
}
- if (IDE_PCI_DEVID_EQ(d->devid, DEVID_HPT34X)) {
- /* see comments in hpt34x.c on why..... */
- d->bootable = (pcicmd & PCI_COMMAND_MEMORY) ? OFF_BOARD : NEVER_BOARD;
- }
+
/*
* Set up the IDE ports
*/
@@ -553,14 +569,14 @@ check_if_enabled:
ide_pci_enablebit_t *e = &(d->enablebits[port]);
if (e->reg && (pci_read_config_byte(dev, e->reg, &tmp) || (tmp & e->mask) != e->val))
continue; /* port not enabled */
- if (IDE_PCI_DEVID_EQ(d->devid, DEVID_HPT366) && (port) && (class_rev != 0x03))
+ if (IDE_PCI_DEVID_EQ(d->devid, DEVID_HPT366) && (port) && (class_rev < 0x03))
return;
if ((dev->class >> 8) != PCI_CLASS_STORAGE_IDE || (dev->class & (port ? 4 : 1)) != 0) {
ctl = dev->resource[(2*port)+1].start;
base = dev->resource[2*port].start;
if (!(ctl & PCI_BASE_ADDRESS_IO_MASK) ||
!(base & PCI_BASE_ADDRESS_IO_MASK)) {
- printk("%s: IO baseregs (BIOS) are reported as MEM, report to <andre@suse.com>.\n", d->name);
+ printk("%s: IO baseregs (BIOS) are reported as MEM, report to <andre@linux-ide.org>.\n", d->name);
#if 0
/* FIXME! This really should check that it really gets the IO/MEM part right! */
continue;
@@ -603,19 +619,21 @@ check_if_enabled:
goto bypass_umc_dma;
}
if (hwif->udma_four) {
- printk("%s: ATA-66 forced bit set (WARNING)!!\n", d->name);
+ printk("%s: ATA-66/100 forced bit set (WARNING)!!\n", d->name);
} else {
hwif->udma_four = (d->ata66_check) ? d->ata66_check(hwif) : 0;
}
#ifdef CONFIG_BLK_DEV_IDEDMA
if (IDE_PCI_DEVID_EQ(d->devid, DEVID_SIS5513) ||
IDE_PCI_DEVID_EQ(d->devid, DEVID_AEC6260) ||
+ IDE_PCI_DEVID_EQ(d->devid, DEVID_PIIX4NX) ||
IDE_PCI_DEVID_EQ(d->devid, DEVID_HPT34X))
autodma = 0;
if (autodma)
hwif->autodma = 1;
if (IDE_PCI_DEVID_EQ(d->devid, DEVID_PDC20246) ||
IDE_PCI_DEVID_EQ(d->devid, DEVID_PDC20262) ||
+ IDE_PCI_DEVID_EQ(d->devid, DEVID_PDC20267) ||
IDE_PCI_DEVID_EQ(d->devid, DEVID_AEC6210) ||
IDE_PCI_DEVID_EQ(d->devid, DEVID_AEC6260) ||
IDE_PCI_DEVID_EQ(d->devid, DEVID_AEC6260R) ||
@@ -625,6 +643,7 @@ check_if_enabled:
IDE_PCI_DEVID_EQ(d->devid, DEVID_CY82C693) ||
IDE_PCI_DEVID_EQ(d->devid, DEVID_CMD646) ||
IDE_PCI_DEVID_EQ(d->devid, DEVID_CMD648) ||
+ IDE_PCI_DEVID_EQ(d->devid, DEVID_CMD649) ||
((dev->class >> 8) == PCI_CLASS_STORAGE_IDE && (dev->class & 0x80))) {
unsigned long dma_base = ide_get_or_set_dma_base(hwif, (!mate && d->extra) ? d->extra : 0, d->name);
if (dma_base && !(pcicmd & PCI_COMMAND_MASTER)) {
@@ -665,6 +684,7 @@ static void __init hpt366_device_order_fixup (struct pci_dev *dev, ide_pci_devic
ide_pci_device_t *d2;
unsigned char pin1 = 0, pin2 = 0;
unsigned int class_rev;
+ char *chipset_names[] = {"HPT366", "HPT366", "HPT368", "HPT370", "HPT370A"};
if (PCI_FUNC(dev->devfn) & 1)
return;
@@ -672,8 +692,13 @@ static void __init hpt366_device_order_fixup (struct pci_dev *dev, ide_pci_devic
pci_read_config_dword(dev, PCI_CLASS_REVISION, &class_rev);
class_rev &= 0xff;
+ strcpy(d->name, chipset_names[class_rev]);
+
switch(class_rev) {
- case 3: return;
+ case 4:
+ case 3: printk("%s: IDE controller on PCI bus %02x dev %02x\n", d->name, dev->bus->number, dev->devfn);
+ ide_setup_pci_device(dev, d);
+ return;
default: break;
}
@@ -700,15 +725,6 @@ static void __init hpt366_device_order_fixup (struct pci_dev *dev, ide_pci_devic
return;
d2 = d;
printk("%s: IDE controller on PCI bus %02x dev %02x\n", d2->name, dev2->bus->number, dev2->devfn);
- if (hpt363_shared_pin && !hpt363_shared_irq) {
- printk("%s: IDE controller run unsupported mode three!!!\n", d2->name);
-#ifndef CONFIG_HPT366_MODE3
- printk("%s: IDE controller report to <andre@suse.com>\n", d->name);
- return;
-#else /* CONFIG_HPT366_MODE3 */
- printk("%s: OVERRIDE IDE controller not advisable this mode!!!\n", d2->name);
-#endif /* CONFIG_HPT366_MODE3 */
- }
ide_setup_pci_device(dev2, d2);
}
diff --git a/drivers/ide/ide-pmac.c b/drivers/ide/ide-pmac.c
index 45bbe77ac..83cea6ba2 100644
--- a/drivers/ide/ide-pmac.c
+++ b/drivers/ide/ide-pmac.c
@@ -813,12 +813,6 @@ pmac_ide_dma_onoff(ide_drive_t *drive, int enable)
return 0;
}
-static int
-pmac_ide_tune_chipset(ide_drive_t *drive, byte speed)
-{
- return 0;
-}
-
int pmac_ide_dmaproc(ide_dma_action_t func, ide_drive_t *drive)
{
ide_hwif_t *hwif = HWIF(drive);
diff --git a/drivers/ide/ide-probe.c b/drivers/ide/ide-probe.c
index ddf6c8dae..dd5f660fe 100644
--- a/drivers/ide/ide-probe.c
+++ b/drivers/ide/ide-probe.c
@@ -1,5 +1,5 @@
/*
- * linux/drivers/ide/ide-probe.c Version 1.05 July 3, 1999
+ * linux/drivers/ide/ide-probe.c Version 1.06 June 9, 2000
*
* Copyright (C) 1994-1998 Linus Torvalds & authors (see below)
*/
@@ -7,6 +7,7 @@
/*
* Mostly written by Mark Lord <mlord@pobox.com>
* and Gadi Oxman <gadio@netvision.net.il>
+ * and Andre Hedrick <andre@linux-ide.org>
*
* See linux/MAINTAINERS for address of current maintainer.
*
@@ -23,6 +24,7 @@
* added ide6/7/8/9
* allowed for secondary flash card to be detectable
* with new flag : drive->ata_flash : 1;
+ * Version 1.06 stream line request queue and prep for cascade project.
*/
#undef REALLY_SLOW_IO /* most systems can safely undef this */
@@ -41,6 +43,7 @@
#include <linux/malloc.h>
#include <linux/delay.h>
#include <linux/ide.h>
+#include <linux/spinlock.h>
#include <asm/byteorder.h>
#include <asm/irq.h>
@@ -167,6 +170,7 @@ static inline void do_identify (ide_drive_t *drive, byte cmd)
}
drive->media = ide_disk;
printk("ATA DISK drive\n");
+ QUIRK_LIST(HWIF(drive),drive);
return;
}
diff --git a/drivers/ide/ide.c b/drivers/ide/ide.c
index a3394807b..932c6f114 100644
--- a/drivers/ide/ide.c
+++ b/drivers/ide/ide.c
@@ -1,5 +1,5 @@
/*
- * linux/drivers/ide/ide.c Version 6.30 Dec 28, 1999
+ * linux/drivers/ide/ide.c Version 6.31 June 9, 2000
*
* Copyright (C) 1994-1998 Linus Torvalds & authors (see below)
*/
@@ -7,6 +7,7 @@
/*
* Mostly written by Mark Lord <mlord@pobox.com>
* and Gadi Oxman <gadio@netvision.net.il>
+ * and Andre Hedrick <andre@linux-ide.org>
*
* See linux/MAINTAINERS for address of current maintainer.
*
@@ -109,6 +110,9 @@
* Version 6.21 Fixing/Fixed SMP spinlock issue with insight from an old
* hat that clarified original low level driver design.
* Version 6.30 Added SMP support; fixed multmode issues. -ml
+ * Version 6.31 Debug Share INTR's and request queue streaming
+ * Native ATA-100 support
+ * Prep for Cascades Project
*
* Some additional driver compile-time options are in ./include/linux/ide.h
*
@@ -117,8 +121,8 @@
*
*/
-#define REVISION "Revision: 6.30"
-#define VERSION "Id: ide.c 6.30 1999/12/28"
+#define REVISION "Revision: 6.31"
+#define VERSION "Id: ide.c 6.31 2000/06/09"
#undef REALLY_SLOW_IO /* most systems can safely undef this */
@@ -482,7 +486,8 @@ static inline int drive_is_ready (ide_drive_t *drive)
#if 0
udelay(1); /* need to guarantee 400ns since last command was issued */
#endif
- if (GET_STAT() & BUSY_STAT) /* Note: this may clear a pending IRQ!! */
+// if (GET_STAT() & BUSY_STAT) /* Note: this may clear a pending IRQ!! */
+ if (IN_BYTE(IDE_ALTSTATUS_REG) & BUSY_STAT)
return 0; /* drive busy: definitely not interrupting */
return 1; /* drive ready: *might* be interrupting */
}
@@ -651,6 +656,19 @@ static ide_startstop_t reset_pollfunc (ide_drive_t *drive)
return ide_stopped;
}
+static void check_dma_crc (ide_drive_t *drive)
+{
+ if (drive->crc_count) {
+ (void) HWIF(drive)->dmaproc(ide_dma_off_quietly, drive);
+ if ((HWIF(drive)->speedproc) != NULL)
+ HWIF(drive)->speedproc(drive, ide_auto_reduce_xfer(drive));
+ if (drive->current_speed >= XFER_SW_DMA_0)
+ (void) HWIF(drive)->dmaproc(ide_dma_on, drive);
+ } else {
+ (void) HWIF(drive)->dmaproc(ide_dma_off, drive);
+ }
+}
+
static void pre_reset (ide_drive_t *drive)
{
if (drive->driver != NULL)
@@ -658,12 +676,15 @@ static void pre_reset (ide_drive_t *drive)
if (!drive->keep_settings) {
if (drive->using_dma) {
- (void) HWIF(drive)->dmaproc(ide_dma_off, drive);
+ check_dma_crc(drive);
} else {
drive->unmask = 0;
drive->io_32bit = 0;
}
+ return;
}
+ if (drive->using_dma)
+ check_dma_crc(drive);
}
/*
@@ -902,9 +923,9 @@ ide_startstop_t ide_error (ide_drive_t *drive, const char *msg, byte stat)
if (err == ABRT_ERR) {
if (drive->select.b.lba && IN_BYTE(IDE_COMMAND_REG) == WIN_SPECIFY)
return ide_stopped; /* some newer drives don't support WIN_SPECIFY */
- } else if ((err & (ABRT_ERR | ICRC_ERR)) == (ABRT_ERR | ICRC_ERR))
- ; /* UDMA crc error -- just retry the operation */
- else if (err & (BBD_ERR | ECC_ERR)) /* retries won't help these */
+ } else if ((err & (ABRT_ERR | ICRC_ERR)) == (ABRT_ERR | ICRC_ERR)) {
+ drive->crc_count++; /* UDMA crc error -- just retry the operation */
+ } else if (err & (BBD_ERR | ECC_ERR)) /* retries won't help these */
rq->errors = ERROR_MAX;
else if (err & TRK0_ERR) /* help it find track zero */
rq->errors |= ERROR_RECAL;
@@ -941,6 +962,7 @@ void ide_cmd (ide_drive_t *drive, byte cmd, byte nsect, ide_handler_t *handler)
ide_set_handler (drive, handler, WAIT_CMD, NULL);
if (IDE_CONTROL_REG)
OUT_BYTE(drive->ctl,IDE_CONTROL_REG); /* clear nIEN */
+ SELECT_MASK(HWIF(drive),drive,0);
OUT_BYTE(nsect,IDE_NSECTOR_REG);
OUT_BYTE(cmd,IDE_COMMAND_REG);
}
@@ -1298,7 +1320,7 @@ static void ide_do_request(ide_hwgroup_t *hwgroup, int masked_irq)
hwif = HWIF(drive);
if (hwgroup->hwif->sharing_irq && hwif != hwgroup->hwif && hwif->io_ports[IDE_CONTROL_OFFSET]) {
/* set nIEN for previous hwif */
- OUT_BYTE(hwgroup->drive->ctl|2, hwgroup->hwif->io_ports[IDE_CONTROL_OFFSET]);
+ SELECT_INTERRUPT(hwif, drive);
}
hwgroup->hwif = hwif;
hwgroup->drive = drive;
@@ -1316,13 +1338,13 @@ static void ide_do_request(ide_hwgroup_t *hwgroup, int masked_irq)
* happens anyway when any interrupt comes in, IDE or otherwise
* -- the kernel masks the IRQ while it is being handled.
*/
- if (hwif->irq != masked_irq)
+ if (masked_irq && hwif->irq != masked_irq)
disable_irq_nosync(hwif->irq);
spin_unlock(&io_request_lock);
ide__sti(); /* allow other IRQs while we start this request */
startstop = start_request(drive);
spin_lock_irq(&io_request_lock);
- if (hwif->irq != masked_irq)
+ if (masked_irq && hwif->irq != masked_irq)
enable_irq(hwif->irq);
if (startstop == ide_stopped)
hwgroup->busy = 0;
@@ -1404,7 +1426,11 @@ void ide_timer_expiry (unsigned long data)
*/
spin_unlock(&io_request_lock);
hwif = HWIF(drive);
+#if DISABLE_IRQ_NOSYNC
+ disable_irq_nosync(hwif->irq);
+#else
disable_irq(hwif->irq); /* disable_irq_nosync ?? */
+#endif /* DISABLE_IRQ_NOSYNC */
__cli(); /* local CPU only, as if we were handling an interrupt */
if (hwgroup->poll_timeout != 0) {
startstop = handler(drive);
@@ -2008,12 +2034,12 @@ void ide_unregister (unsigned int index)
else
hwgroup->hwif = HWIF(hwgroup->drive);
-#ifdef CONFIG_BLK_DEV_IDEDMA_PCI
+#if defined(CONFIG_BLK_DEV_IDEDMA) && !defined(CONFIG_DMA_NONPCI)
if (hwif->dma_base) {
(void) ide_release_dma(hwif);
hwif->dma_base = 0;
}
-#endif /* CONFIG_BLK_DEV_IDEDMA_PCI */
+#endif /* (CONFIG_BLK_DEV_IDEDMA) && !(CONFIG_DMA_NONPCI) */
/*
* Remove us from the kernel's knowledge
@@ -2048,6 +2074,10 @@ void ide_unregister (unsigned int index)
hwif->speedproc = old_hwif.speedproc;
hwif->selectproc = old_hwif.selectproc;
hwif->resetproc = old_hwif.resetproc;
+ hwif->intrproc = old_hwif.intrproc;
+ hwif->maskproc = old_hwif.maskproc;
+ hwif->quirkproc = old_hwif.quirkproc;
+ hwif->rwproc = old_hwif.rwproc;
hwif->dmaproc = old_hwif.dmaproc;
hwif->dma_base = old_hwif.dma_base;
hwif->dma_extra = old_hwif.dma_extra;
@@ -2275,17 +2305,18 @@ int ide_spin_wait_hwgroup (ide_drive_t *drive)
unsigned long timeout = jiffies + (3 * HZ);
spin_lock_irq(&io_request_lock);
+
while (hwgroup->busy) {
- unsigned long flags;
+ unsigned long lflags;
spin_unlock_irq(&io_request_lock);
- __save_flags(flags); /* local CPU only */
+ __save_flags(lflags); /* local CPU only */
__sti(); /* local CPU only; needed for jiffies */
if (0 < (signed long)(jiffies - timeout)) {
- __restore_flags(flags);
+ __restore_flags(lflags); /* local CPU only */
printk("%s: channel busy\n", drive->name);
return -EBUSY;
}
- __restore_flags(flags); /* local CPU only */
+ __restore_flags(lflags); /* local CPU only */
spin_lock_irq(&io_request_lock);
}
return 0;
@@ -2422,13 +2453,13 @@ int ide_wait_cmd_task (ide_drive_t *drive, byte *buf)
*/
void ide_delay_50ms (void)
{
-#if 0
+#ifndef CONFIG_BLK_DEV_IDECS
unsigned long timeout = jiffies + ((HZ + 19)/20) + 1;
while (0 < (signed long)(timeout - jiffies));
#else
__set_current_state(TASK_UNINTERRUPTIBLE);
schedule_timeout(HZ/20);
-#endif
+#endif /* CONFIG_BLK_DEV_IDECS */
}
int system_bus_clock (void)
@@ -2576,7 +2607,6 @@ static int ide_ioctl (struct inode *inode, struct file *file,
err = -EFAULT;
return err;
}
-
case HDIO_SCAN_HWIF:
{
int args[3];
@@ -3266,6 +3296,7 @@ void __init ide_init_builtin_drivers (void)
if (ide_hwifs[0].io_ports[IDE_DATA_OFFSET]) {
ide_get_lock(&ide_lock, NULL, NULL); /* for atari only */
disable_irq(ide_hwifs[0].irq); /* disable_irq_nosync ?? */
+// disable_irq_nosync(ide_hwifs[0].irq);
}
#endif /* __mc68000__ || CONFIG_APUS */
@@ -3619,10 +3650,10 @@ void cleanup_module (void)
for (index = 0; index < MAX_HWIFS; ++index) {
ide_unregister(index);
-#ifdef CONFIG_BLK_DEV_IDEDMA_PCI
+#if defined(CONFIG_BLK_DEV_IDEDMA) && !defined(CONFIG_DMA_NONPCI)
if (ide_hwifs[index].dma_base)
(void) ide_release_dma(&ide_hwifs[index]);
-#endif /* CONFIG_BLK_DEV_IDEDMA_PCI */
+#endif /* (CONFIG_BLK_DEV_IDEDMA) && !(CONFIG_DMA_NONPCI) */
}
#ifdef CONFIG_PROC_FS
@@ -3636,6 +3667,7 @@ void cleanup_module (void)
static int parse_ide_setup (char *line)
{
parse_options(line);
+ /* We MUST return 0 as otherwise no subsequent __setup option works... */
return 0;
}
__setup("", parse_ide_setup);
diff --git a/drivers/ide/ns87415.c b/drivers/ide/ns87415.c
index 70f185108..1837f01e0 100644
--- a/drivers/ide/ns87415.c
+++ b/drivers/ide/ns87415.c
@@ -3,7 +3,7 @@
*
* Copyright (C) 1997-1998 Mark Lord <mlord@pobox.com>
* Copyright (C) 1998 Eddie C. Dost <ecd@skynet.be>
- * Copyright (C) 1999-2000 Andre Hedrick <andre@suse.com>
+ * Copyright (C) 1999-2000 Andre Hedrick <andre@linux-ide.org>
*
* Inspired by an earlier effort from David S. Miller <davem@redhat.com>
*/
diff --git a/drivers/ide/pdc202xx.c b/drivers/ide/pdc202xx.c
index f16d33921..66a123841 100644
--- a/drivers/ide/pdc202xx.c
+++ b/drivers/ide/pdc202xx.c
@@ -1,7 +1,7 @@
/*
* linux/drivers/ide/pdc202xx.c Version 0.30 Mar. 18, 2000
*
- * Copyright (C) 1998-2000 Andre Hedrick (andre@suse.com)
+ * Copyright (C) 1998-2000 Andre Hedrick <andre@linux-ide.org>
* May be copied or modified under the terms of the GNU General Public License
*
* Promise Ultra33 cards with BIOS v1.20 through 1.28 will need this
@@ -12,6 +12,8 @@
* Promise Ultra66 cards with BIOS v1.11 this
* compiled into the kernel if you have more than one card installed.
*
+ * Promise Ultra100 cards.
+ *
* The latest chipset code will support the following ::
* Three Ultra33 controllers and 12 drives.
* 8 are UDMA supported and 4 are limited to DMA mode 2 multi-word.
@@ -51,6 +53,10 @@
#define DISPLAY_PDC202XX_TIMINGS
+#ifndef SPLIT_BYTE
+#define SPLIT_BYTE(B,H,L) ((H)=(B>>4), (L)=(B-((B>>4)<<4)))
+#endif
+
#if defined(DISPLAY_PDC202XX_TIMINGS) && defined(CONFIG_PROC_FS)
#include <linux/stat.h>
#include <linux/proc_fs.h>
@@ -99,10 +105,25 @@ static int pdc202xx_get_info (char *buffer, char **addr, off_t offset, int count
{
char *p = buffer;
- u32 bibma = bmide_dev->resource[4].start;
+ u32 bibma = pci_resource_start(bmide_dev, 4);
u32 reg60h = 0, reg64h = 0, reg68h = 0, reg6ch = 0;
u16 reg50h = 0, pmask = (1<<10), smask = (1<<11);
- u8 c0 = 0, c1 = 0;
+ u8 hi = 0, lo = 0;
+
+ /*
+ * at that point bibma+0x2 et bibma+0xa are byte registers
+ * to investigate:
+ */
+ u8 c0 = inb_p((unsigned short)bibma + 0x02);
+ u8 c1 = inb_p((unsigned short)bibma + 0x0a);
+
+ u8 sc11 = inb_p((unsigned short)bibma + 0x11);
+ u8 sc1a = inb_p((unsigned short)bibma + 0x1a);
+ u8 sc1b = inb_p((unsigned short)bibma + 0x1b);
+ u8 sc1c = inb_p((unsigned short)bibma + 0x1c);
+ u8 sc1d = inb_p((unsigned short)bibma + 0x1d);
+ u8 sc1e = inb_p((unsigned short)bibma + 0x1e);
+ u8 sc1f = inb_p((unsigned short)bibma + 0x1f);
pci_read_config_word(bmide_dev, 0x50, &reg50h);
pci_read_config_dword(bmide_dev, 0x60, &reg60h);
@@ -110,14 +131,10 @@ static int pdc202xx_get_info (char *buffer, char **addr, off_t offset, int count
pci_read_config_dword(bmide_dev, 0x68, &reg68h);
pci_read_config_dword(bmide_dev, 0x6c, &reg6ch);
- /*
- * at that point bibma+0x2 et bibma+0xa are byte registers
- * to investigate:
- */
- c0 = inb_p((unsigned short)bibma + 0x02);
- c1 = inb_p((unsigned short)bibma + 0x0a);
-
- switch(bmide_dev->device) {
+ switch(bmide_dev->device) {
+ case PCI_DEVICE_ID_PROMISE_20267:
+ p += sprintf(p, "\n PDC20267 Chipset.\n");
+ break;
case PCI_DEVICE_ID_PROMISE_20262:
p += sprintf(p, "\n PDC20262 Chipset.\n");
break;
@@ -130,9 +147,40 @@ static int pdc202xx_get_info (char *buffer, char **addr, off_t offset, int count
break;
}
+ p += sprintf(p, "------------------------------- General Status ---------------------------------\n");
+ p += sprintf(p, "Burst Mode : %sabled\n", (sc1f & 0x01) ? "en" : "dis");
+ p += sprintf(p, "Host Mode : %s\n", (sc1f & 0x08) ? "Tri-Stated" : "Normal");
+ p += sprintf(p, "Bus Clocking : %s\n",
+ ((sc1f & 0xC0) == 0xC0) ? "100 External" :
+ ((sc1f & 0x80) == 0x80) ? "66 External" :
+ ((sc1f & 0x40) == 0x40) ? "33 External" : "33 PCI Internal");
+ p += sprintf(p, "IO pad select : %s mA\n",
+ ((sc1c & 0x03) == 0x03) ? "10" :
+ ((sc1c & 0x02) == 0x02) ? "8" :
+ ((sc1c & 0x01) == 0x01) ? "6" :
+ ((sc1c & 0x00) == 0x00) ? "4" : "??");
+ SPLIT_BYTE(sc1e, hi, lo);
+ p += sprintf(p, "Status Polling Period : %d\n", hi);
+ p += sprintf(p, "Interrupt Check Status Polling Delay : %d\n", lo);
p += sprintf(p, "--------------- Primary Channel ---------------- Secondary Channel -------------\n");
- p += sprintf(p, " %sabled %sabled\n",
- (c0&0x80)?"dis":" en",(c1&0x80)?"dis":" en");
+ p += sprintf(p, " %s %s\n",
+ (c0&0x80)?"disabled":"enabled ",
+ (c1&0x80)?"disabled":"enabled ");
+ p += sprintf(p, "66 Clocking %s %s\n",
+ (sc11&0x02)?"enabled ":"disabled",
+ (sc11&0x08)?"enabled ":"disabled");
+ p += sprintf(p, " Mode %s Mode %s\n",
+ (sc1a & 0x01) ? "MASTER" : "PCI ",
+ (sc1b & 0x01) ? "MASTER" : "PCI ");
+ p += sprintf(p, " %s %s\n",
+ (sc1d & 0x08) ? "Error " :
+ (sc1d & 0x04) ? "Interrupting" :
+ (sc1d & 0x02) ? "FIFO Full " :
+ (sc1d & 0x01) ? "FIFO Empty " : "????????????",
+ (sc1d & 0x80) ? "Error " :
+ (sc1d & 0x40) ? "Interrupting" :
+ (sc1d & 0x20) ? "FIFO Full " :
+ (sc1d & 0x10) ? "FIFO Empty " : "????????????");
p += sprintf(p, "--------------- drive0 --------- drive1 -------- drive0 ---------- drive1 ------\n");
p += sprintf(p, "DMA enabled: %s %s %s %s\n",
(c0&0x20)?"yes":"no ",(c0&0x40)?"yes":"no ",(c1&0x20)?"yes":"no ",(c1&0x40)?"yes":"no ");
@@ -141,9 +189,13 @@ static int pdc202xx_get_info (char *buffer, char **addr, off_t offset, int count
pdc202xx_ultra_verbose(reg64h, (reg50h & pmask)),
pdc202xx_ultra_verbose(reg68h, (reg50h & smask)),
pdc202xx_ultra_verbose(reg6ch, (reg50h & smask)));
- p += sprintf(p, " PIO Mode: %s %s %s %s\n",
+ p += sprintf(p, "PIO Mode: %s %s %s %s\n",
pdc202xx_pio_verbose(reg60h),pdc202xx_pio_verbose(reg64h),
pdc202xx_pio_verbose(reg68h),pdc202xx_pio_verbose(reg6ch));
+#if 0
+ p += sprintf(p, "--------------- Can ATAPI DMA ---------------\n");
+#endif
+
return p-buffer; /* => must be less than 4k! */
}
#endif /* defined(DISPLAY_PDC202XX_TIMINGS) && defined(CONFIG_PROC_FS) */
@@ -324,6 +376,7 @@ static int pdc202xx_tune_chipset (ide_drive_t *drive, byte speed)
switch(speed) {
#ifdef CONFIG_BLK_DEV_IDEDMA
+ case XFER_UDMA_5:
case XFER_UDMA_4: TB = 0x20; TC = 0x01; break; /* speed 8 == UDMA mode 4 */
case XFER_UDMA_3: TB = 0x40; TC = 0x02; break; /* speed 7 == UDMA mode 3 */
case XFER_UDMA_2: TB = 0x20; TC = 0x01; break; /* speed 6 == UDMA mode 2 */
@@ -408,7 +461,7 @@ static int config_chipset_for_dma (ide_drive_t *drive, byte ultra)
struct hd_driveid *id = drive->id;
ide_hwif_t *hwif = HWIF(drive);
struct pci_dev *dev = hwif->pci_dev;
- unsigned long high_16 = dev->resource[4].start & PCI_BASE_ADDRESS_IO_MASK;
+ unsigned long high_16 = pci_resource_start(dev, 4);
unsigned long dma_base = hwif->dma_base;
byte unit = (drive->select.b.unit & 0x01);
@@ -418,8 +471,9 @@ static int config_chipset_for_dma (ide_drive_t *drive, byte ultra)
byte AP;
unsigned short EP;
byte CLKSPD = IN_BYTE(high_16 + 0x11);
- byte udma_66 = ((id->hw_config & 0x2000) && (hwif->udma_four)) ? 1 : 0;
byte udma_33 = ultra ? (inb(high_16 + 0x001f) & 1) : 0;
+ byte udma_66 = ((eighty_ninty_three(drive)) && udma_33) ? 1 : 0;
+ byte udma_100 = ((dev->device == PCI_DEVICE_ID_PROMISE_20267) && udma_66) ? 1 : 0;
/*
* Set the control register to use the 66Mhz system
@@ -436,11 +490,15 @@ static int config_chipset_for_dma (ide_drive_t *drive, byte ultra)
byte mask = hwif->channel ? 0x08 : 0x02;
unsigned short c_mask = hwif->channel ? (1<<11) : (1<<10);
- byte ultra_66 = ((id->dma_ultra & 0x0010) || (id->dma_ultra & 0x0008)) ? 1 : 0;
+ byte ultra_66 = ((id->dma_ultra & 0x0010) ||
+ (id->dma_ultra & 0x0008)) ? 1 : 0;
+ byte ultra_100 = ((id->dma_ultra & 0x0020) ||
+ (id->dma_ultra & 0x0010) ||
+ (id->dma_ultra & 0x0008)) ? 1 : 0;
pci_read_config_word(dev, 0x50, &EP);
- if ((ultra_66) && (EP & c_mask)) {
+ if (((ultra_66) || (ultra_100)) && (EP & c_mask)) {
#ifdef DEBUG
printk("ULTRA66: %s channel of Ultra 66 requires an 80-pin cable for Ultra66 operation.\n", hwif->channel ? "Secondary", "Primary");
printk(" Switching to Ultra33 mode.\n");
@@ -449,13 +507,14 @@ static int config_chipset_for_dma (ide_drive_t *drive, byte ultra)
/* Secondary : zero out fourth bit */
OUT_BYTE(CLKSPD & ~mask, (high_16 + 0x11));
} else {
- if (ultra_66) {
+ if ((ultra_66) || (ultra_100)) {
/*
* check to make sure drive on same channel
* is u66 capable
*/
if (hwif->drives[!(drive->dn%2)].id) {
- if ((hwif->drives[!(drive->dn%2)].id->dma_ultra & 0x0010) ||
+ if ((hwif->drives[!(drive->dn%2)].id->dma_ultra & 0x0020) ||
+ (hwif->drives[!(drive->dn%2)].id->dma_ultra & 0x0010) ||
(hwif->drives[!(drive->dn%2)].id->dma_ultra & 0x0008)) {
OUT_BYTE(CLKSPD | mask, (high_16 + 0x11));
} else {
@@ -517,17 +576,18 @@ chipset_is_set:
if (drive->media == ide_disk) /* PREFETCH_EN */
pci_write_config_byte(dev, (drive_pci), AP|PREFETCH_EN);
- if ((id->dma_ultra & 0x0010) && (udma_66) && (udma_33)) speed = XFER_UDMA_4;
- else if ((id->dma_ultra & 0x0008) && (udma_66) && (udma_33)) speed = XFER_UDMA_3;
- else if ((id->dma_ultra & 0x0004) && (udma_33)) speed = XFER_UDMA_2;
- else if ((id->dma_ultra & 0x0002) && (udma_33)) speed = XFER_UDMA_1;
- else if ((id->dma_ultra & 0x0001) && (udma_33)) speed = XFER_UDMA_0;
- else if (id->dma_mword & 0x0004) speed = XFER_MW_DMA_2;
- else if (id->dma_mword & 0x0002) speed = XFER_MW_DMA_1;
- else if (id->dma_mword & 0x0001) speed = XFER_MW_DMA_0;
- else if (id->dma_1word & 0x0004) speed = XFER_SW_DMA_2;
- else if (id->dma_1word & 0x0002) speed = XFER_SW_DMA_1;
- else if (id->dma_1word & 0x0001) speed = XFER_SW_DMA_0;
+ if ((id->dma_ultra & 0x0020) && (udma_100)) speed = XFER_UDMA_5;
+ else if ((id->dma_ultra & 0x0010) && (udma_66)) speed = XFER_UDMA_4;
+ else if ((id->dma_ultra & 0x0008) && (udma_66)) speed = XFER_UDMA_3;
+ else if ((id->dma_ultra & 0x0004) && (udma_33)) speed = XFER_UDMA_2;
+ else if ((id->dma_ultra & 0x0002) && (udma_33)) speed = XFER_UDMA_1;
+ else if ((id->dma_ultra & 0x0001) && (udma_33)) speed = XFER_UDMA_0;
+ else if (id->dma_mword & 0x0004) speed = XFER_MW_DMA_2;
+ else if (id->dma_mword & 0x0002) speed = XFER_MW_DMA_1;
+ else if (id->dma_mword & 0x0001) speed = XFER_MW_DMA_0;
+ else if (id->dma_1word & 0x0004) speed = XFER_SW_DMA_2;
+ else if (id->dma_1word & 0x0002) speed = XFER_SW_DMA_1;
+ else if (id->dma_1word & 0x0001) speed = XFER_SW_DMA_0;
else {
/* restore original pci-config space */
pci_write_config_dword(dev, drive_pci, drive_conf);
@@ -537,7 +597,7 @@ chipset_is_set:
outb(inb(dma_base+2) & ~(1<<(5+unit)), dma_base+2);
(void) pdc202xx_tune_chipset(drive, speed);
- return ((int) ((id->dma_ultra >> 11) & 3) ? ide_dma_on :
+ return ((int) ((id->dma_ultra >> 11) & 7) ? ide_dma_on :
((id->dma_ultra >> 8) & 7) ? ide_dma_on :
((id->dma_mword >> 8) & 7) ? ide_dma_on :
((id->dma_1word >> 8) & 7) ? ide_dma_on :
@@ -558,7 +618,7 @@ static int config_drive_xfer_rate (ide_drive_t *drive)
}
dma_func = ide_dma_off_quietly;
if (id->field_valid & 4) {
- if (id->dma_ultra & 0x001F) {
+ if (id->dma_ultra & 0x002F) {
/* Force if Capable UltraDMA */
dma_func = config_chipset_for_dma(drive, 1);
if ((id->field_valid & 2) &&
@@ -603,6 +663,10 @@ int pdc202xx_dmaproc (ide_dma_action_t func, ide_drive_t *drive)
switch (func) {
case ide_dma_check:
return config_drive_xfer_rate(drive);
+ case ide_dma_lostirq:
+ case ide_dma_timeout:
+ if (HWIF(drive)->resetproc != NULL)
+ HWIF(drive)->resetproc(drive);
default:
break;
}
@@ -610,14 +674,29 @@ int pdc202xx_dmaproc (ide_dma_action_t func, ide_drive_t *drive)
}
#endif /* CONFIG_BLK_DEV_IDEDMA */
+void pdc202xx_reset (ide_drive_t *drive)
+{
+ unsigned long high_16 = pci_resource_start(HWIF(drive)->pci_dev, 4);
+ byte udma_speed_flag = inb(high_16 + 0x001f);
+ int i = 0;
+
+ OUT_BYTE(udma_speed_flag | 0x10, high_16 + 0x001f);
+ ide_delay_50ms();
+ ide_delay_50ms();
+ OUT_BYTE(udma_speed_flag & ~0x10, high_16 + 0x001f);
+ for (i = 0; i < 40; i++)
+ ide_delay_50ms();
+}
+
unsigned int __init pci_init_pdc202xx (struct pci_dev *dev, const char *name)
{
- unsigned long high_16 = dev->resource[4].start & PCI_BASE_ADDRESS_IO_MASK;
+ unsigned long high_16 = pci_resource_start(dev, 4);
byte udma_speed_flag = inb(high_16 + 0x001f);
byte primary_mode = inb(high_16 + 0x001a);
byte secondary_mode = inb(high_16 + 0x001b);
- if (dev->device == PCI_DEVICE_ID_PROMISE_20262) {
+ if ((dev->device == PCI_DEVICE_ID_PROMISE_20262) ||
+ (dev->device == PCI_DEVICE_ID_PROMISE_20267)) {
int i = 0;
/*
* software reset - this is required because the bios
@@ -646,7 +725,7 @@ unsigned int __init pci_init_pdc202xx (struct pci_dev *dev, const char *name)
byte irq = 0, irq2 = 0;
pci_read_config_byte(dev, PCI_INTERRUPT_LINE, &irq);
pci_read_config_byte(dev, (PCI_INTERRUPT_LINE)|0x80, &irq2); /* 0xbc */
- if (irq != irq2) {
+ if ((irq != irq2) && (dev->device != PCI_DEVICE_ID_PROMISE_20267)) {
pci_write_config_byte(dev, (PCI_INTERRUPT_LINE)|0x80, irq); /* 0xbc */
printk("%s: pci-config space interrupt mirror fixed.\n", name);
}
@@ -705,8 +784,12 @@ unsigned int __init ata66_pdc202xx (ide_hwif_t *hwif)
void __init ide_init_pdc202xx (ide_hwif_t *hwif)
{
- hwif->tuneproc = &pdc202xx_tune_drive;
- hwif->speedproc = &pdc202xx_tune_chipset;
+ hwif->tuneproc = &pdc202xx_tune_drive;
+ hwif->speedproc = &pdc202xx_tune_chipset;
+
+ if ((hwif->pci_dev->device == PCI_DEVICE_ID_PROMISE_20262) ||
+ (hwif->pci_dev->device == PCI_DEVICE_ID_PROMISE_20267))
+ hwif->resetproc = &pdc202xx_reset;
#ifdef CONFIG_BLK_DEV_IDEDMA
if (hwif->dma_base) {
diff --git a/drivers/ide/piix.c b/drivers/ide/piix.c
index 56c185236..0dbb8d883 100644
--- a/drivers/ide/piix.c
+++ b/drivers/ide/piix.c
@@ -1,8 +1,8 @@
/*
- * linux/drivers/ide/piix.c Version 0.31 Mar. 18, 2000
+ * linux/drivers/ide/piix.c Version 0.32 June 9, 2000
*
* Copyright (C) 1998-1999 Andrzej Krzysztofowicz, Author and Maintainer
- * Copyright (C) 1998-2000 Andre Hedrick (andre@suse.com)
+ * Copyright (C) 1998-2000 Andre Hedrick <andre@linux-ide.org>
* May be copied or modified under the terms of the GNU General Public License
*
* PIO mode setting function for Intel chipsets.
@@ -83,7 +83,7 @@ static struct pci_dev *bmide_dev;
static int piix_get_info (char *buffer, char **addr, off_t offset, int count)
{
char *p = buffer;
- u32 bibma = bmide_dev->resource[4].start;
+ u32 bibma = pci_resource_start(bmide_dev, 4);
u16 reg40 = 0, psitre = 0, reg42 = 0, ssitre = 0;
u8 c0 = 0, c1 = 0;
u8 reg44 = 0, reg48 = 0, reg4a = 0, reg4b = 0, reg54 = 0, reg55 = 0;
@@ -108,10 +108,14 @@ static int piix_get_info (char *buffer, char **addr, off_t offset, int count)
c1 = inb_p((unsigned short)bibma + 0x0a);
switch(bmide_dev->device) {
+ case PCI_DEVICE_ID_INTEL_82820FW_5:
+ p += sprintf(p, "\n Intel PIIX4 Ultra 100 Chipset.\n");
+ break;
case PCI_DEVICE_ID_INTEL_82372FB_1:
case PCI_DEVICE_ID_INTEL_82801AA_1:
p += sprintf(p, "\n Intel PIIX4 Ultra 66 Chipset.\n");
break;
+ case PCI_DEVICE_ID_INTEL_82451NX:
case PCI_DEVICE_ID_INTEL_82801AB_1:
case PCI_DEVICE_ID_INTEL_82443MX_1:
case PCI_DEVICE_ID_INTEL_82371AB:
@@ -142,21 +146,25 @@ static int piix_get_info (char *buffer, char **addr, off_t offset, int count)
(reg48&0x04) ? "yes" : "no ",
(reg48&0x08) ? "yes" : "no " );
p += sprintf(p, "UDMA enabled: %s %s %s %s\n",
+ ((reg54&0x11) && (reg55&0x10) && (reg4a&0x01)) ? "5" :
((reg54&0x11) && (reg4a&0x02)) ? "4" :
((reg54&0x11) && (reg4a&0x01)) ? "3" :
(reg4a&0x02) ? "2" :
(reg4a&0x01) ? "1" :
(reg4a&0x00) ? "0" : "X",
+ ((reg54&0x22) && (reg55&0x20) && (reg4a&0x10)) ? "5" :
((reg54&0x22) && (reg4a&0x20)) ? "4" :
((reg54&0x22) && (reg4a&0x10)) ? "3" :
(reg4a&0x20) ? "2" :
(reg4a&0x10) ? "1" :
(reg4a&0x00) ? "0" : "X",
+ ((reg54&0x44) && (reg55&0x40) && (reg4b&0x03)) ? "5" :
((reg54&0x44) && (reg4b&0x02)) ? "4" :
((reg54&0x44) && (reg4b&0x01)) ? "3" :
(reg4b&0x02) ? "2" :
(reg4b&0x01) ? "1" :
(reg4b&0x00) ? "0" : "X",
+ ((reg54&0x88) && (reg55&0x80) && (reg4b&0x30)) ? "5" :
((reg54&0x88) && (reg4b&0x20)) ? "4" :
((reg54&0x88) && (reg4b&0x10)) ? "3" :
(reg4b&0x20) ? "2" :
@@ -188,6 +196,7 @@ extern char *ide_xfer_verbose (byte xfer_rate);
*/
static byte piix_dma_2_pio (byte xfer_rate) {
switch(xfer_rate) {
+ case XFER_UDMA_5:
case XFER_UDMA_4:
case XFER_UDMA_3:
case XFER_UDMA_2:
@@ -286,6 +295,7 @@ static int piix_tune_chipset (ide_drive_t *drive, byte speed)
switch(speed) {
case XFER_UDMA_4:
case XFER_UDMA_2: u_speed = 2 << (drive->dn * 4); break;
+ case XFER_UDMA_5:
case XFER_UDMA_3:
case XFER_UDMA_1: u_speed = 1 << (drive->dn * 4); break;
case XFER_UDMA_0: u_speed = 0 << (drive->dn * 4); break;
@@ -298,7 +308,11 @@ static int piix_tune_chipset (ide_drive_t *drive, byte speed)
if (speed >= XFER_UDMA_0) {
if (!(reg48 & u_flag))
pci_write_config_word(dev, 0x48, reg48|u_flag);
- pci_write_config_byte(dev, 0x55, (byte) reg55 & ~w_flag);
+ if (speed == XFER_UDMA_5) {
+ pci_write_config_byte(dev, 0x55, (byte) reg55|w_flag);
+ } else {
+ pci_write_config_byte(dev, 0x55, (byte) reg55 & ~w_flag);
+ }
if (!(reg4a & u_speed)) {
pci_write_config_word(dev, 0x4a, reg4a & ~a_speed);
pci_write_config_word(dev, 0x4a, reg4a|u_speed);
@@ -341,15 +355,20 @@ static int piix_config_drive_for_dma (ide_drive_t *drive)
struct pci_dev *dev = hwif->pci_dev;
byte speed;
- byte udma_66 = ((id->hw_config & 0x2000) && (hwif->udma_four)) ? 1 : 0;
- int ultra66 = ((dev->device == PCI_DEVICE_ID_INTEL_82801AA_1) ||
+ byte udma_66 = eighty_ninty_three(drive);
+ int ultra100 = ((dev->device == PCI_DEVICE_ID_INTEL_82820FW_5)) ? 1 : 0;
+ int ultra66 = ((ultra100) ||
+ (dev->device == PCI_DEVICE_ID_INTEL_82801AA_1) ||
(dev->device == PCI_DEVICE_ID_INTEL_82372FB_1)) ? 1 : 0;
int ultra = ((ultra66) ||
(dev->device == PCI_DEVICE_ID_INTEL_82371AB) ||
(dev->device == PCI_DEVICE_ID_INTEL_82443MX_1) ||
+ (dev->device == PCI_DEVICE_ID_INTEL_82451NX) ||
(dev->device == PCI_DEVICE_ID_INTEL_82801AB_1)) ? 1 : 0;
- if ((id->dma_ultra & 0x0010) && (ultra)) {
+ if ((id->dma_ultra & 0x0020) && (udma_66) && (ultra100)) {
+ speed = XFER_UDMA_5;
+ } else if ((id->dma_ultra & 0x0010) && (ultra)) {
speed = ((udma_66) && (ultra66)) ? XFER_UDMA_4 : XFER_UDMA_2;
} else if ((id->dma_ultra & 0x0008) && (ultra)) {
speed = ((udma_66) && (ultra66)) ? XFER_UDMA_3 : XFER_UDMA_1;
@@ -371,7 +390,7 @@ static int piix_config_drive_for_dma (ide_drive_t *drive)
(void) piix_tune_chipset(drive, speed);
- return ((int) ((id->dma_ultra >> 11) & 3) ? ide_dma_on :
+ return ((int) ((id->dma_ultra >> 11) & 7) ? ide_dma_on :
((id->dma_ultra >> 8) & 7) ? ide_dma_on :
((id->dma_mword >> 8) & 7) ? ide_dma_on :
((id->dma_1word >> 8) & 7) ? ide_dma_on :
diff --git a/drivers/ide/qd6580.c b/drivers/ide/qd6580.c
index 4c00de504..5787b73f2 100644
--- a/drivers/ide/qd6580.c
+++ b/drivers/ide/qd6580.c
@@ -1,16 +1,19 @@
/*
- * linux/drivers/ide/qd6580.c Version 0.03 May 13, 2000
+ * linux/drivers/ide/qd6580.c Version 0.04 June 4, 2000
*
* Copyright (C) 1996-2000 Linus Torvalds & author (see below)
*/
/*
* Version 0.03 Cleaned auto-tune, added probe
- *
+ * Version 0.04 Added second channel tuning
+ *
* QDI QD6580 EIDE controller fast support
- *
+ *
* To activate controller support use kernel parameter "ide0=qd6580"
* To enable tuning use kernel parameter "ide0=autotune"
+ * To enable tuning second channel (not really tested),
+ * use parameter "ide1=autotune"
*/
/*
@@ -36,146 +39,254 @@
#include "ide_modes.h"
/*
- * I/O ports are 0xb0 0xb1 0xb2 and 0xb3
- * or 0x30 0x31 0x32 and 0x33
+ * I/O ports are 0xb0-0xb3
+ * or 0x30-0x33
* -- this is a dual IDE interface with I/O chips
*
* More research on qd6580 being done by willmore@cig.mot.com (David)
+ * More Information given by Petr Sourcek (petr@ryston.cz)
+ * http://www.ryston.cz/petr/vlb
*/
-/*
+/*
* 0xb0: Timer1
*
- *
- * 0xb1: Status
*
- * && 0xf0 is either 0b1010000 or 0b01010000, or else it isn't a qd6580
- * bit 3 & 2: unknown (useless ?) I have 0 & 1, respectively
- * bit 1: 1 if qd6580 baseport is 0xb0
- * 0 if qd6580 baseport is 0x30
- * bit 0: 1 if ide baseport is 0x1f0
- * 0 if ide baseport is 0x170
+ * 0xb1: Config
+ *
+ * bit 0: ide baseport: 1 = 0x1f0 ; 0 = 0x170
* (? Strange: the Dos driver uses it, and then forces baseport to 0x1f0 ?)
- *
- *
+ * bit 1: qd baseport: 1 = 0xb0 ; 0 = 0x30
+ * bit 2: ID3: bus speed: 1 = <=33MHz ; 0 = >33MHz
+ * bit 3: 1 for qd6580
+ * upper nibble is either 1010 or 0101, or else it isn't a qd6580
+ *
+ *
* 0xb2: Timer2
*
- *
+ *
* 0xb3: Control
*
- * bits 0-3 are always set 1
- * bit 6 : if 1, must be set 1
- * bit 1 : if 1, bit 7 must be set 1
- * bit 0 : if 1, drives are independant, we can have two different timers for
- * the two drives.
- * if 0, we have to take the slowest drive into account,
- * but we may tune the second hwif ?
+ * bits 0-3 must always be set 1
+ * bit 4 must be set 1, but is set 0 by dos driver while measuring vlb clock
+ * bit 0 : 1 = Only primary port enabled : channel 0 for hda, channel 1 for hdb
+ * 0 = Primary and Secondary ports enabled : channel 0 for hda & hdb
+ * channel 1 for hdc & hdd
+ * bit 1 : 1 = only disks on primary port
+ * 0 = disks & ATAPI devices on primary port
+ * bit 2-4 : always 0
+ * bit 5 : status, but of what ?
+ * bit 6 : always set 1 by dos driver
+ * bit 7 : set 1 for non-ATAPI devices (read-ahead and post-write buffer ?)
*/
+/* truncates a in [b,c] */
+#define IDE_IN(a,b,c) ( ((a)<(b)) ? (b) : ( (a)>(c) ? (c) : (a)) )
+
typedef struct ide_hd_timings_s {
int active_time; /* Active pulse (ns) minimum */
int recovery_time; /* Recovery pulse (ns) minimum */
} ide_hd_timings_t;
static int basePort; /* base port address (0x30 or 0xb0) */
-static byte status; /* status register of qd6580 */
+static byte config; /* config register of qd6580 */
static byte control; /* control register of qd6580 */
-/* truncates a in [b,c] */
-#define IDE_IN(a,b,c) ( ((a)<(b)) ? (b) : ( (a)>(c) ? (c) : (a)) )
-
static int bus_clock; /* Vesa local bus clock (ns) */
static int tuned=0; /* to remember whether we've already been tuned */
+static int snd_tuned=0; /* to remember whether we've already been tuned */
+static int nb_disks_prim=0; /* number of disk drives on primary port */
+
+/*
+ * write_reg
+ *
+ * writes the specified byte on the specified register
+ */
+
+static void write_reg ( byte content, byte reg )
+{
+ unsigned long flags;
+
+ save_flags(flags); /* all CPUs */
+ cli(); /* all CPUs */
+ outb_p(content,reg);
+ inb(0x3f6);
+ restore_flags(flags); /* all CPUs */
+}
/*
* tune_drive
*
- * Finds timings for the specified drive, returns it in struc t
+ * Finds timings for the specified drive, returns it in struct t
*/
-static void tune_drive ( ide_drive_t *drive, byte pio, ide_hd_timings_t *t)
+static void tune_drive ( ide_drive_t *drive, byte pio, ide_hd_timings_t *t )
{
ide_pio_data_t d;
- t->active_time = 0xaf;
- t->recovery_time = 0x19f; /* worst cases values from the dos driver */
+ t->active_time = 175;
+ t->recovery_time = 415; /* worst cases values from the dos driver */
- if (drive->present == 0) { /* not present : free to give any timing */
- t->active_time = 0x0;
- t->recovery_time = 0x0;
+ if (!drive->present) { /* not present : free to give any timing */
+ t->active_time = 0;
+ t->recovery_time = 0;
return;
}
-
- pio = ide_get_best_pio_mode(drive, pio, 4, &d);
-
- if (pio) {
-
- switch (pio) {
- case 0: break;
- case 3: t->active_time = 0x56;
- t->recovery_time = d.cycle_time-0x66;
- break;
- case 4: t->active_time = 0x46;
- t->recovery_time = d.cycle_time-0x3d;
- break;
- default: if (d.cycle_time >= 0xb4) {
- t->active_time = 0x6e;
- t->recovery_time = d.cycle_time - 0x78;
- } else {
- t->active_time = ide_pio_timings[pio].active_time;
- t->recovery_time = d.cycle_time
- -t->active_time
- -ide_pio_timings[pio].setup_time;
- }
- }
- }
+
+ pio = ide_get_best_pio_mode(drive, pio, 255, &d);
+ pio = IDE_MIN(pio,4);
+
+ switch (pio) {
+ case 0: break;
+ case 3:
+ if (d.cycle_time >= 110) {
+ t->active_time = 86;
+ t->recovery_time = d.cycle_time-102;
+ } else {
+ printk("%s: Strange recovery time !\n",drive->name);
+ return;
+ }
+ break;
+ case 4:
+ if (d.cycle_time >= 69) {
+ t->active_time = 70;
+ t->recovery_time = d.cycle_time-61;
+ } else {
+ printk("%s: Strange recovery time !\n",drive->name);
+ return;
+ }
+ break;
+ default:
+ if (d.cycle_time >= 180) {
+ t->active_time = 110;
+ t->recovery_time = d.cycle_time - 120;
+ } else {
+ t->active_time = ide_pio_timings[pio].active_time;
+ t->recovery_time = d.cycle_time
+ -t->active_time;
+ }
+ }
printk("%s: PIO mode%d, tim1=%dns tim2=%dns\n", drive->name, pio, t->active_time, t->recovery_time);
+
+ if (drive->media == ide_disk)
+ nb_disks_prim++;
+ else {
+/* need to disable read-ahead FIFO and post-write buffer for ATAPI drives*/
+ write_reg(0x5f,basePort+0x03);
+ printk("%s: Warning: please try to connect this drive to secondary IDE port\nto improve data transfer rate on primary IDE port.\n",drive->name);
+ }
}
-/*
+/*
+ * tune_snd_drive
+ *
+ * Finds timings for the specified drive, using second channel rules
+ */
+
+static void tune_snd_drive ( ide_drive_t *drive, byte pio, ide_hd_timings_t *t )
+{
+ ide_pio_data_t d;
+
+ t->active_time = 175;
+ t->recovery_time = 415;
+
+ if (!drive->present) { /* not present : free to give any timing */
+ t->active_time = 0;
+ t->recovery_time = 0;
+ return;
+ }
+
+ pio = ide_get_best_pio_mode(drive, pio, 255, &d);
+
+ if ((pio) && (d.cycle_time >= 180)) {
+ t->active_time = 115;
+ t->recovery_time = d.cycle_time - 115;
+ }
+ printk("%s: PIO mode%d, tim1=%dns tim2=%dns\n", drive->name, pio, t->active_time, t->recovery_time);
+
+ if ((drive->media == ide_disk) && (nb_disks_prim<2)) {
+/* a disk drive on secondary port while there's room on primary, which is the
+ * only one that has read-ahead fifo and post-write buffer ? What a waste !*/
+ printk("%s: Warning: please try to connect this drive to primary IDE port\nto improve data transfer rate.\n",drive->name);
+ }
+}
+
+/*
+ * compute_timing
+ *
+ * computes the timing value where
+ * lower nibble is active time, in count of VLB clocks, 17-(from 2 to 17)
+ * upper nibble is recovery time, in count of VLB clocks, 15-(from 2 to 15)
+ */
+
+static byte compute_timing ( char name[6], ide_hd_timings_t *t )
+{
+ byte active_cycle;
+ byte recovery_cycle;
+ byte parameter;
+
+ active_cycle = 17-IDE_IN(t->active_time / bus_clock + 1, 2, 17);
+ recovery_cycle = 15-IDE_IN(t->recovery_time / bus_clock + 1, 2, 15);
+
+ parameter = active_cycle | (recovery_cycle<<4);
+
+ printk("%s: tim1=%dns tim2=%dns => %#x\n", name, t[0].active_time, t[0].recovery_time, parameter);
+ return(parameter);
+}
+
+/*
* tune_ide
*
- * Tunes the whole ide, ie tunes each drives, and takes the worst timings
- * to tune qd6580
+ * Tunes the whole hwif, ie tunes each drives, and in case we have to share,
+ * takes the worse timings to tune qd6580
*/
static void tune_ide ( ide_hwif_t *hwif, byte pio )
{
unsigned long flags;
ide_hd_timings_t t[2]={{0,0},{0,0}};
-
- byte active_cycle;
- byte recovery_cycle;
- byte parameter;
int bus_speed = ide_system_bus_speed ();
-
+
bus_clock = 1000 / bus_speed;
-
+
save_flags(flags); /* all CPUs */
cli(); /* all CPUs */
outb( (bus_clock<30) ? 0x0 : 0x0a, basePort + 0x02);
outb( 0x40 | ((control & 0x02) ? 0x9f:0x1f), basePort+0x03);
- restore_flags(flags);
+ restore_flags(flags);
tune_drive (&hwif->drives[0], pio, &t[0]);
tune_drive (&hwif->drives[1], pio, &t[1]);
+ if (control & 0x01) { /* only primary port enabled, can tune separately */
+ write_reg(compute_timing (hwif->drives[0].name, &t[0]),basePort);
+ write_reg(compute_timing (hwif->drives[1].name, &t[1]),basePort+0x02);
+ } else { /* both ports enabled, we have to share */
+
+ t[0].active_time = IDE_MAX(t[0].active_time, t[1].active_time);
+ t[0].recovery_time = IDE_MAX(t[0].recovery_time,t[1].recovery_time);
+ write_reg(compute_timing (hwif->name, &t[0]),basePort);
+ }
+}
+
+/*
+ * tune_snd_ide
+ *
+ * Tunes the whole secondary hwif, ie tunes each drives, and takes the worse
+ * timings to tune qd6580
+ */
+
+static void tune_snd_ide ( ide_hwif_t *hwif, byte pio )
+{
+ ide_hd_timings_t t[2]={{0,0},{0,0}};
+
+ tune_snd_drive (&hwif->drives[0], pio, &t[0]);
+ tune_snd_drive (&hwif->drives[1], pio, &t[1]);
+
t[0].active_time = IDE_MAX(t[0].active_time, t[1].active_time);
t[0].recovery_time = IDE_MAX(t[0].recovery_time,t[1].recovery_time);
-
- active_cycle = 17-IDE_IN(t[0].active_time / bus_clock + 1, 2, 17);
- recovery_cycle = 15-IDE_IN(t[0].recovery_time / bus_clock + 1, 2, 15);
-
- parameter=active_cycle | (recovery_cycle<<4);
-
- printk("%s: tim1=%dns tim2=%dns => %#x\n", hwif->name, t[0].active_time, t[0].recovery_time, parameter);
-
- save_flags(flags); /* all CPUs */
- cli(); /* all CPUs */
- outb_p(parameter,0xb0);
- inb(0x3f6);
- restore_flags(flags); /* all CPUs */
-
+
+ write_reg(compute_timing (hwif->name, &t[0]),basePort+0x02);
}
/*
@@ -193,6 +304,20 @@ static void tune_qd6580 (ide_drive_t *drive, byte pio)
}
/*
+ * tune_snd_qd6580
+ *
+ * tunes the second hwif if not tuned
+ */
+
+static void tune_snd_qd6580 (ide_drive_t *drive, byte pio)
+{
+ if (! snd_tuned) {
+ tune_snd_ide(HWIF(drive), pio);
+ snd_tuned = 1;
+ }
+}
+
+/*
* testreg
*
* tests if the given port is a register
@@ -203,7 +328,7 @@ static int __init testreg(int port)
byte savereg;
byte readreg;
unsigned long flags;
-
+
save_flags(flags); /* all CPUs */
cli(); /* all CPUs */
savereg = inb(port);
@@ -214,14 +339,15 @@ static int __init testreg(int port)
if (savereg == 0x15) {
printk("Outch ! the probe for qd6580 isn't reliable !\n");
- printk("Please contact samuel.thibault@fnac.net to tell about your hardware\n");
- printk("Assuming qd6580 is present");
+ printk("Please contact maintainers to tell about your hardware\n");
+ printk("Assuming qd6580 is not present.\n");
+ return 0;
}
return (readreg == 0x15);
}
-/*
+/*
* trybase:
*
* tries to find a qd6580 at the given base and save it if found
@@ -233,20 +359,20 @@ static int __init trybase (int base)
save_flags(flags); /* all CPUs */
cli(); /* all CPUs */
- status = inb(base+0x01);
+ config = inb(base+0x01);
control = inb(base+0x03);
restore_flags(flags); /* all CPUs */
- if (((status & 0xf0) != 0x50) && ((status & 0xf0) != 0xa0)) return(0);
- if (! ( ((status & 0x02) == 0x0) == (base == 0x30) ) ) return (0);
+ if (((config & 0xf0) != 0x50) && ((config & 0xf0) != 0xa0)) return(0);
+ if (! ( ((config & 0x02) == 0x0) == (base == 0x30) ) ) return (0);
/* Seems to be OK, let's use it */
-
+
basePort = base;
return(testreg(base));
}
-/*
+/*
* probe:
*
* probes qd6580 at 0xb0 (the default) or 0x30
@@ -257,6 +383,11 @@ static int __init probe (void)
return (trybase(0xb0) ? 1 : trybase(0x30));
}
+/*
+ * init_qd6580:
+ *
+ * called at the very beginning of initialization ; should just probe and link
+ */
void __init init_qd6580 (void)
{
@@ -264,13 +395,16 @@ void __init init_qd6580 (void)
printk("qd6580: not found\n");
return;
}
-
- printk("qd6580: base=%#x, status=%#x, control=%#x\n", basePort, status, control);
-
+
+ printk("qd6580: base=%#x, config=%#x, control=%#x\n", basePort, config, control);
+
ide_hwifs[0].chipset = ide_qd6580;
- ide_hwifs[1].chipset = ide_qd6580;
ide_hwifs[0].tuneproc = &tune_qd6580;
- ide_hwifs[0].mate = &ide_hwifs[1];
- ide_hwifs[1].mate = &ide_hwifs[0];
- ide_hwifs[1].channel = 1;
+ if (!(control & 0x01)) {
+ ide_hwifs[1].chipset = ide_qd6580;
+ ide_hwifs[1].tuneproc = &tune_snd_qd6580;
+ ide_hwifs[0].mate = &ide_hwifs[1];
+ ide_hwifs[1].mate = &ide_hwifs[0];
+ ide_hwifs[1].channel = 1;
+ }
}
diff --git a/drivers/ide/sis5513.c b/drivers/ide/sis5513.c
index be56a7f24..4f0a33086 100644
--- a/drivers/ide/sis5513.c
+++ b/drivers/ide/sis5513.c
@@ -1,7 +1,7 @@
/*
- * linux/drivers/ide/sis5513.c Version 0.10 Mar. 18, 2000
+ * linux/drivers/ide/sis5513.c Version 0.11 June 9, 2000
*
- * Copyright (C) 1999-2000 Andre Hedrick (andre@suse.com)
+ * Copyright (C) 1999-2000 Andre Hedrick <andre@linux-ide.org>
* May be copied or modified under the terms of the GNU General Public License
*
* Thanks to SIS Taiwan for direct support and hardware.
@@ -111,12 +111,12 @@ static int sis_get_info(char *, char **, off_t, int);
extern int (*sis_display_info)(char *, char **, off_t, int); /* ide-proc.c */
static struct pci_dev *bmide_dev;
-static char *cable_type[] __initdata = {
+static char *cable_type[] = {
"80 pins",
"40 pins"
};
-static char *recovery_time [] __initdata ={
+static char *recovery_time [] ={
"12 PCICLK", "1 PCICLK",
"2 PCICLK", "3 PCICLK",
"4 PCICLK", "5 PCICLCK",
@@ -127,14 +127,14 @@ static char *recovery_time [] __initdata ={
"15 PCICLK", "15 PCICLK"
};
-static char * cycle_time [] __initdata = {
+static char * cycle_time [] = {
"Undefined", "2 CLCK",
"3 CLK", "4 CLK",
"5 CLK", "6 CLK",
"7 CLK", "8 CLK"
};
-static char * active_time [] __initdata = {
+static char * active_time [] = {
"8 PCICLK", "1 PCICLCK",
"2 PCICLK", "2 PCICLK",
"4 PCICLK", "5 PCICLK",
@@ -185,7 +185,7 @@ static int sis_get_info (char *buffer, char **addr, off_t offset, int count)
p += sprintf(p, " UDMA Cycle Time %s \t UDMA Cycle Time %s\n",
cycle_time[(reg & 0x70) >> 4], cycle_time[(reg1 & 0x70) >> 4]);
p += sprintf(p, " Data Active Time %s \t Data Active Time %s\n",
- active_time[(reg & 0x07)], active_time[(reg &0x07)] );
+ active_time[(reg & 0x07)], active_time[(reg1 &0x07)] );
rc = pci_read_config_byte(bmide_dev, 0x40, &reg);
rc = pci_read_config_byte(bmide_dev, 0x44, &reg1);
@@ -209,7 +209,7 @@ static int sis_get_info (char *buffer, char **addr, off_t offset, int count)
p += sprintf(p, " UDMA Cycle Time %s \t UDMA Cycle Time %s\n",
cycle_time[(reg & 0x70) >> 4], cycle_time[(reg1 & 0x70) >> 4]);
p += sprintf(p, " Data Active Time %s \t Data Active Time %s\n",
- active_time[(reg & 0x07)], active_time[(reg &0x07)] );
+ active_time[(reg & 0x07)], active_time[(reg1 &0x07)] );
rc = pci_read_config_byte(bmide_dev, 0x42, &reg);
rc = pci_read_config_byte(bmide_dev, 0x46, &reg1);
@@ -335,7 +335,7 @@ static void sis5513_tune_drive (ide_drive_t *drive, byte pio)
#ifdef CONFIG_BLK_DEV_IDEDMA
/*
- * ((id->hw_config & 0x2000) && (HWIF(drive)->udma_four))
+ * ((id->hw_config & 0x4000|0x2000) && (HWIF(drive)->udma_four))
*/
static int config_chipset_for_dma (ide_drive_t *drive, byte ultra)
{
@@ -349,7 +349,7 @@ static int config_chipset_for_dma (ide_drive_t *drive, byte ultra)
unsigned long dma_base = hwif->dma_base;
byte unit = (drive->select.b.unit & 0x01);
byte speed = 0x00, unmask = 0xE0, four_two = 0x00;
- byte udma_66 = ((id->hw_config & 0x2000) && (hwif->udma_four)) ? 1 : 0;
+ byte udma_66 = eighty_ninty_three(drive);
if (host_dev) {
switch(host_dev->device) {
@@ -536,7 +536,7 @@ unsigned int __init pci_init_sis5513 (struct pci_dev *dev, const char *name)
pci_read_config_byte(dev, 0x52, &reg52h);
if (!(reg52h & 0x04)) {
- /* set IDE controller to operate in Compabitility mode obly */
+ /* set IDE controller to operate in Compabitility mode only */
pci_write_config_byte(dev, 0x52, reg52h|0x04);
}
#if defined(DISPLAY_SIS_TIMINGS) && defined(CONFIG_PROC_FS)
diff --git a/drivers/ide/trm290.c b/drivers/ide/trm290.c
index e7ee2e977..c1aa3fb4e 100644
--- a/drivers/ide/trm290.c
+++ b/drivers/ide/trm290.c
@@ -224,10 +224,10 @@ void __init ide_init_trm290 (ide_hwif_t *hwif)
struct pci_dev *dev = hwif->pci_dev;
hwif->chipset = ide_trm290;
- cfgbase = dev->resource[4].start;
+ cfgbase = pci_resource_start(dev, 4);
if ((dev->class & 5) && cfgbase)
{
- hwif->config_data = cfgbase & PCI_BASE_ADDRESS_IO_MASK;
+ hwif->config_data = cfgbase;
printk("TRM290: chip config base at 0x%04lx\n", hwif->config_data);
} else {
hwif->config_data = 0x3df0;
diff --git a/drivers/ide/via82cxxx.c b/drivers/ide/via82cxxx.c
index 6c201599f..3ab298596 100644
--- a/drivers/ide/via82cxxx.c
+++ b/drivers/ide/via82cxxx.c
@@ -1,10 +1,10 @@
/*
- * linux/drivers/ide/via82cxxx.c Version 0.09 Apr. 02, 2000
+ * linux/drivers/ide/via82cxxx.c Version 0.10 June 9, 2000
*
* Copyright (C) 1998-99 Michel Aubry, Maintainer
* Copyright (C) 1999 Jeff Garzik, MVP4 Support
* (jgarzik@mandrakesoft.com)
- * Copyright (C) 1998-2000 Andre Hedrick (andre@suse.com)
+ * Copyright (C) 1998-2000 Andre Hedrick <andre@linux-ide.org>
* May be copied or modified under the terms of the GNU General Public License
*
* The VIA MVP-4 is reported OK with UDMA.
@@ -101,19 +101,19 @@ static struct pci_dev *isa_dev = NULL;
struct chipset_bus_clock_list_entry {
byte xfer_speed;
- byte chipset_settings_25;
byte ultra_settings_25;
- byte chipset_settings_33;
+ byte chipset_settings_25;
byte ultra_settings_33;
- byte chipset_settings_37;
+ byte chipset_settings_33;
byte ultra_settings_37;
- byte chipset_settings_41;
+ byte chipset_settings_37;
byte ultra_settings_41;
+ byte chipset_settings_41;
};
static struct chipset_bus_clock_list_entry * via82cxxx_table = NULL;
-struct chipset_bus_clock_list_entry via82cxxx_type_one [] = {
+static struct chipset_bus_clock_list_entry via82cxxx_type_one [] = {
/* speed */ /* 25 */ /* 33 */ /* 37.5 */ /* 41.5 */
#ifdef CONFIG_BLK_DEV_IDEDMA
{ XFER_UDMA_4, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 },
@@ -134,7 +134,7 @@ struct chipset_bus_clock_list_entry via82cxxx_type_one [] = {
{ 0, 0x03, 0xA8, 0x03, 0xA8, 0x03, 0xA9, 0x00, 0x00 }
};
-struct chipset_bus_clock_list_entry via82cxxx_type_two [] = {
+static struct chipset_bus_clock_list_entry via82cxxx_type_two [] = {
/* speed */ /* 25 */ /* 33 */ /* 37.5 */ /* 41.5 */
#ifdef CONFIG_BLK_DEV_IDEDMA
{ XFER_UDMA_4, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 },
@@ -155,7 +155,7 @@ struct chipset_bus_clock_list_entry via82cxxx_type_two [] = {
{ 0, 0x03, 0xA8, 0x03, 0xA8, 0x03, 0xDB, 0x03, 0xFE }
};
-struct chipset_bus_clock_list_entry via82cxxx_type_three [] = {
+static struct chipset_bus_clock_list_entry via82cxxx_type_three [] = {
/* speed */ /* 25 */ /* 33 */ /* 37.5 */ /* 41.5 */
#ifdef CONFIG_BLK_DEV_IDEDMA
{ XFER_UDMA_4, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 },
@@ -176,7 +176,7 @@ struct chipset_bus_clock_list_entry via82cxxx_type_three [] = {
{ 0, 0x03, 0xA8, 0x03, 0xA8, 0x03, 0xDB, 0x03, 0xFE }
};
-struct chipset_bus_clock_list_entry via82cxxx_type_four [] = {
+static struct chipset_bus_clock_list_entry via82cxxx_type_four [] = {
/* speed */ /* 25 */ /* 33 */ /* 37.5 */ /* 41.5 */
#ifdef CONFIG_BLK_DEV_IDEDMA
{ XFER_UDMA_4, 0x00, 0x00, 0xE0, 0x20, 0xE1, 0x31, 0x00, 0x00 },
@@ -243,20 +243,20 @@ static const struct {
#define arraysize(x) (sizeof(x)/sizeof(*(x)))
-#undef DISPLAY_VIA_TIMINGS
+#define DISPLAY_VIA_TIMINGS
#if defined(DISPLAY_VIA_TIMINGS) && defined(CONFIG_PROC_FS)
#include <linux/stat.h>
#include <linux/proc_fs.h>
-static char *FIFO_str[] __initdata = {
+static char *FIFO_str[] = {
" 1 ",
"3/4",
"1/2",
"1/4"
};
-static char *control3_str[] __initdata = {
+static char *control3_str[] = {
"No limitation",
"64",
"128",
@@ -760,11 +760,15 @@ static int config_chipset_for_dma (ide_drive_t *drive)
{
struct hd_driveid *id = drive->id;
byte speed = 0x00;
+ byte ultra66 = eighty_ninty_three(drive);
+ byte ultra100 = 0;
int rval;
- if ((id->dma_ultra & 0x0010) && (HWIF(drive)->udma_four)) {
+ if ((id->dma_ultra & 0x0020) && (ultra66) && (ultra100)) {
+ speed = XFER_UDMA_5;
+ } else if ((id->dma_ultra & 0x0010) && (ultra66)) {
speed = XFER_UDMA_4;
- } else if ((id->dma_ultra & 0x0008) && (HWIF(drive)->udma_four)) {
+ } else if ((id->dma_ultra & 0x0008) && (ultra66)) {
speed = XFER_UDMA_3;
} else if (id->dma_ultra & 0x0004) {
speed = XFER_UDMA_2;
@@ -778,12 +782,6 @@ static int config_chipset_for_dma (ide_drive_t *drive)
speed = XFER_MW_DMA_1;
} else if (id->dma_mword & 0x0001) {
speed = XFER_MW_DMA_0;
- } else if (id->dma_1word & 0x0004) {
- speed = XFER_SW_DMA_2;
- } else if (id->dma_1word & 0x0002) {
- speed = XFER_SW_DMA_1;
- } else if (id->dma_1word & 0x0001) {
- speed = XFER_SW_DMA_0;
} else {
return ((int) ide_dma_off_quietly);
}
@@ -793,7 +791,6 @@ static int config_chipset_for_dma (ide_drive_t *drive)
rval = (int)( ((id->dma_ultra >> 11) & 3) ? ide_dma_on :
((id->dma_ultra >> 8) & 7) ? ide_dma_on :
((id->dma_mword >> 8) & 7) ? ide_dma_on :
- ((id->dma_1word >> 8) & 7) ? ide_dma_on :
ide_dma_off_quietly);
return rval;
}
@@ -811,7 +808,7 @@ static int config_drive_xfer_rate (ide_drive_t *drive)
}
dma_func = ide_dma_off_quietly;
if (id->field_valid & 4) {
- if (id->dma_ultra & 0x001F) {
+ if (id->dma_ultra & 0x002F) {
/* Force if Capable UltraDMA */
dma_func = config_chipset_for_dma(drive);
if ((id->field_valid & 2) &&
@@ -820,8 +817,7 @@ static int config_drive_xfer_rate (ide_drive_t *drive)
}
} else if (id->field_valid & 2) {
try_dma_modes:
- if ((id->dma_mword & 0x0007) ||
- (id->dma_1word & 0x0007)) {
+ if (id->dma_mword & 0x0007) {
/* Force if Capable regular DMA modes */
dma_func = config_chipset_for_dma(drive);
if (dma_func != ide_dma_on)
@@ -870,7 +866,7 @@ unsigned int __init pci_init_via82cxxx (struct pci_dev *dev, const char *name)
byte revision = 0;
for (i = 0; i < arraysize (ApolloHostChipInfo) && !host_dev; i++) {
- host = pci_find_device (PCI_VENDOR_ID_VIA,
+ host = pci_find_device (ApolloHostChipInfo[i].vendor_id,
ApolloHostChipInfo[i].host_id,
NULL);
if (!host)