pata_sis: fix MWDMA for <= UDMA66 chipsets and UDMA for UDMA33 chipsets

* Fix MWDMA timings setup in sis_old_set_dmamode() and sis_66_set_dmamode().

  The old timings were overclocked (even worse behavior than sis5513 IDE driver
  which depends on BIOS to program correct timings), the new timings are taken
  from the datasheet (they match timings from ATA spec).

* Fix UDMA timings setup in sis_old_set_dmamode().

  Misplaced pci_write_config_word() call resulted in UDMA timings never
  being set.

* Fix comments for sis_133_early_set_dmamode() and sis_133_set_dmamode():
  - only the former function handles early SiS 961 bridges
  - both functions lack MWDMA timings setup

* Fix typos in sis_100_set_piomode() and sis_133_set_piomode() comments.

* Bump driver version.

Cc: Alan Cox <alan@lxorguk.ukuu.org.uk>
Signed-off-by: Bartlomiej Zolnierkiewicz <bzolnier@gmail.com>
Signed-off-by: Jeff Garzik <jeff@garzik.org>
This commit is contained in:
Bartlomiej Zolnierkiewicz 2007-07-31 22:02:41 +02:00 committed by Jeff Garzik
parent 5d6aca8def
commit 4761c06cb3
1 changed files with 9 additions and 11 deletions

View File

@ -2,6 +2,7 @@
* pata_sis.c - SiS ATA driver * pata_sis.c - SiS ATA driver
* *
* (C) 2005 Red Hat <alan@redhat.com> * (C) 2005 Red Hat <alan@redhat.com>
* (C) 2007 Bartlomiej Zolnierkiewicz
* *
* Based upon linux/drivers/ide/pci/sis5513.c * Based upon linux/drivers/ide/pci/sis5513.c
* Copyright (C) 1999-2000 Andre Hedrick <andre@linux-ide.org> * Copyright (C) 1999-2000 Andre Hedrick <andre@linux-ide.org>
@ -35,7 +36,7 @@
#include "sis.h" #include "sis.h"
#define DRV_NAME "pata_sis" #define DRV_NAME "pata_sis"
#define DRV_VERSION "0.5.1" #define DRV_VERSION "0.5.2"
struct sis_chipset { struct sis_chipset {
u16 device; /* PCI host ID */ u16 device; /* PCI host ID */
@ -237,7 +238,7 @@ static void sis_old_set_piomode (struct ata_port *ap, struct ata_device *adev)
} }
/** /**
* sis_100_set_pioode - Initialize host controller PATA PIO timings * sis_100_set_piomode - Initialize host controller PATA PIO timings
* @ap: Port whose timings we are configuring * @ap: Port whose timings we are configuring
* @adev: Device we are configuring for. * @adev: Device we are configuring for.
* *
@ -262,7 +263,7 @@ static void sis_100_set_piomode (struct ata_port *ap, struct ata_device *adev)
} }
/** /**
* sis_133_set_pioode - Initialize host controller PATA PIO timings * sis_133_set_piomode - Initialize host controller PATA PIO timings
* @ap: Port whose timings we are configuring * @ap: Port whose timings we are configuring
* @adev: Device we are configuring for. * @adev: Device we are configuring for.
* *
@ -334,7 +335,7 @@ static void sis_old_set_dmamode (struct ata_port *ap, struct ata_device *adev)
int drive_pci = sis_old_port_base(adev); int drive_pci = sis_old_port_base(adev);
u16 timing; u16 timing;
const u16 mwdma_bits[] = { 0x707, 0x202, 0x202 }; const u16 mwdma_bits[] = { 0x008, 0x302, 0x301 };
const u16 udma_bits[] = { 0xE000, 0xC000, 0xA000 }; const u16 udma_bits[] = { 0xE000, 0xC000, 0xA000 };
pci_read_config_word(pdev, drive_pci, &timing); pci_read_config_word(pdev, drive_pci, &timing);
@ -342,15 +343,15 @@ static void sis_old_set_dmamode (struct ata_port *ap, struct ata_device *adev)
if (adev->dma_mode < XFER_UDMA_0) { if (adev->dma_mode < XFER_UDMA_0) {
/* bits 3-0 hold recovery timing bits 8-10 active timing and /* bits 3-0 hold recovery timing bits 8-10 active timing and
the higer bits are dependant on the device */ the higer bits are dependant on the device */
timing &= ~ 0x870F; timing &= ~0x870F;
timing |= mwdma_bits[speed]; timing |= mwdma_bits[speed];
pci_write_config_word(pdev, drive_pci, timing);
} else { } else {
/* Bit 15 is UDMA on/off, bit 13-14 are cycle time */ /* Bit 15 is UDMA on/off, bit 13-14 are cycle time */
speed = adev->dma_mode - XFER_UDMA_0; speed = adev->dma_mode - XFER_UDMA_0;
timing &= ~0x6000; timing &= ~0x6000;
timing |= udma_bits[speed]; timing |= udma_bits[speed];
} }
pci_write_config_word(pdev, drive_pci, timing);
} }
/** /**
@ -373,7 +374,7 @@ static void sis_66_set_dmamode (struct ata_port *ap, struct ata_device *adev)
int drive_pci = sis_old_port_base(adev); int drive_pci = sis_old_port_base(adev);
u16 timing; u16 timing;
const u16 mwdma_bits[] = { 0x707, 0x202, 0x202 }; const u16 mwdma_bits[] = { 0x008, 0x302, 0x301 };
const u16 udma_bits[] = { 0xF000, 0xD000, 0xB000, 0xA000, 0x9000}; const u16 udma_bits[] = { 0xF000, 0xD000, 0xB000, 0xA000, 0x9000};
pci_read_config_word(pdev, drive_pci, &timing); pci_read_config_word(pdev, drive_pci, &timing);
@ -432,8 +433,7 @@ static void sis_100_set_dmamode (struct ata_port *ap, struct ata_device *adev)
* @adev: Device to program * @adev: Device to program
* *
* Set UDMA/MWDMA mode for device, in host controller PCI config space. * Set UDMA/MWDMA mode for device, in host controller PCI config space.
* Handles early SiS 961 bridges. Supports MWDMA as well unlike * Handles early SiS 961 bridges.
* the old ide/pci driver.
* *
* LOCKING: * LOCKING:
* None (inherited from caller). * None (inherited from caller).
@ -467,8 +467,6 @@ static void sis_133_early_set_dmamode (struct ata_port *ap, struct ata_device *a
* @adev: Device to program * @adev: Device to program
* *
* Set UDMA/MWDMA mode for device, in host controller PCI config space. * Set UDMA/MWDMA mode for device, in host controller PCI config space.
* Handles early SiS 961 bridges. Supports MWDMA as well unlike
* the old ide/pci driver.
* *
* LOCKING: * LOCKING:
* None (inherited from caller). * None (inherited from caller).