diff options
author | Bartlomiej Zolnierkiewicz <bzolnier@gmail.com> | 2010-01-18 02:17:37 -0500 |
---|---|---|
committer | David S. Miller <davem@davemloft.net> | 2010-01-19 04:24:56 -0500 |
commit | 3c8cc8df5a67a539cd185026e6b6f49b576869ba (patch) | |
tree | a2c042b8768ee08d5f99cd711698a237c6ccdebb /drivers/ide/alim15x3.c | |
parent | 2b7d03a5cdace237525643d48918e68fe24681ed (diff) |
alim15x3: fix PIO timings calculations
Just use the standard ide_timing_compute() helper to calculate
PIO timings. This fixes many issues with the open-coded version
like potential recovery timings underclocking or not accounting
for the enhanced cycle time specified by the device.
Based on libata pata_ali host driver.
Signed-off-by: Bartlomiej Zolnierkiewicz <bzolnier@gmail.com>
Signed-off-by: David S. Miller <davem@davemloft.net>
Diffstat (limited to 'drivers/ide/alim15x3.c')
-rw-r--r-- | drivers/ide/alim15x3.c | 34 |
1 files changed, 15 insertions, 19 deletions
diff --git a/drivers/ide/alim15x3.c b/drivers/ide/alim15x3.c index 0abc43f3101e..99c355e87850 100644 --- a/drivers/ide/alim15x3.c +++ b/drivers/ide/alim15x3.c | |||
@@ -8,7 +8,7 @@ | |||
8 | * Copyright (C) 2002 Alan Cox | 8 | * Copyright (C) 2002 Alan Cox |
9 | * ALi (now ULi M5228) support by Clear Zhang <Clear.Zhang@ali.com.tw> | 9 | * ALi (now ULi M5228) support by Clear Zhang <Clear.Zhang@ali.com.tw> |
10 | * Copyright (C) 2007 MontaVista Software, Inc. <source@mvista.com> | 10 | * Copyright (C) 2007 MontaVista Software, Inc. <source@mvista.com> |
11 | * Copyright (C) 2007 Bartlomiej Zolnierkiewicz <bzolnier@gmail.com> | 11 | * Copyright (C) 2007-2010 Bartlomiej Zolnierkiewicz |
12 | * | 12 | * |
13 | * (U)DMA capable version of ali 1533/1543(C), 1535(D) | 13 | * (U)DMA capable version of ali 1533/1543(C), 1535(D) |
14 | * | 14 | * |
@@ -60,28 +60,22 @@ static void ali_set_pio_mode(ide_drive_t *drive, const u8 pio) | |||
60 | { | 60 | { |
61 | ide_hwif_t *hwif = drive->hwif; | 61 | ide_hwif_t *hwif = drive->hwif; |
62 | struct pci_dev *dev = to_pci_dev(hwif->dev); | 62 | struct pci_dev *dev = to_pci_dev(hwif->dev); |
63 | struct ide_timing *t = ide_timing_find_mode(XFER_PIO_0 + pio); | ||
64 | int s_time = t->setup, a_time = t->active, c_time = t->cycle; | ||
65 | u8 s_clc, a_clc, r_clc; | ||
66 | unsigned long flags; | 63 | unsigned long flags; |
67 | int bus_speed = ide_pci_clk ? ide_pci_clk : 33; | 64 | int bus_speed = ide_pci_clk ? ide_pci_clk : 33; |
65 | unsigned long T = 1000000 / bus_speed; /* PCI clock based */ | ||
68 | int port = hwif->channel ? 0x5c : 0x58; | 66 | int port = hwif->channel ? 0x5c : 0x58; |
69 | int portFIFO = hwif->channel ? 0x55 : 0x54; | 67 | int portFIFO = hwif->channel ? 0x55 : 0x54; |
70 | u8 cd_dma_fifo = 0, unit = drive->dn & 1; | 68 | u8 cd_dma_fifo = 0, unit = drive->dn & 1; |
69 | struct ide_timing t; | ||
71 | 70 | ||
72 | if ((s_clc = (s_time * bus_speed + 999) / 1000) >= 8) | 71 | ide_timing_compute(drive, XFER_PIO_0 + pio, &t, T, 1); |
73 | s_clc = 0; | 72 | |
74 | if ((a_clc = (a_time * bus_speed + 999) / 1000) >= 8) | 73 | t.setup = clamp_val(t.setup, 1, 8) & 7; |
75 | a_clc = 0; | 74 | t.active = clamp_val(t.active, 1, 8) & 7; |
75 | t.recover = clamp_val(t.recover, 1, 16) & 15; | ||
76 | 76 | ||
77 | if (!(r_clc = (c_time * bus_speed + 999) / 1000 - a_clc - s_clc)) { | ||
78 | r_clc = 1; | ||
79 | } else { | ||
80 | if (r_clc >= 16) | ||
81 | r_clc = 0; | ||
82 | } | ||
83 | local_irq_save(flags); | 77 | local_irq_save(flags); |
84 | 78 | ||
85 | /* | 79 | /* |
86 | * PIO mode => ATA FIFO on, ATAPI FIFO off | 80 | * PIO mode => ATA FIFO on, ATAPI FIFO off |
87 | */ | 81 | */ |
@@ -99,9 +93,11 @@ static void ali_set_pio_mode(ide_drive_t *drive, const u8 pio) | |||
99 | pci_write_config_byte(dev, portFIFO, cd_dma_fifo & 0xF0); | 93 | pci_write_config_byte(dev, portFIFO, cd_dma_fifo & 0xF0); |
100 | } | 94 | } |
101 | } | 95 | } |
102 | 96 | ||
103 | pci_write_config_byte(dev, port, s_clc); | 97 | pci_write_config_byte(dev, port, t.setup); |
104 | pci_write_config_byte(dev, port + unit + 2, (a_clc << 4) | r_clc); | 98 | pci_write_config_byte(dev, port + unit + 2, |
99 | (t.active << 4) | t.recover); | ||
100 | |||
105 | local_irq_restore(flags); | 101 | local_irq_restore(flags); |
106 | } | 102 | } |
107 | 103 | ||
@@ -584,6 +580,6 @@ static void __exit ali15x3_ide_exit(void) | |||
584 | module_init(ali15x3_ide_init); | 580 | module_init(ali15x3_ide_init); |
585 | module_exit(ali15x3_ide_exit); | 581 | module_exit(ali15x3_ide_exit); |
586 | 582 | ||
587 | MODULE_AUTHOR("Michael Aubry, Andrzej Krzysztofowicz, CJ, Andre Hedrick, Alan Cox"); | 583 | MODULE_AUTHOR("Michael Aubry, Andrzej Krzysztofowicz, CJ, Andre Hedrick, Alan Cox, Bartlomiej Zolnierkiewicz"); |
588 | MODULE_DESCRIPTION("PCI driver module for ALi 15x3 IDE"); | 584 | MODULE_DESCRIPTION("PCI driver module for ALi 15x3 IDE"); |
589 | MODULE_LICENSE("GPL"); | 585 | MODULE_LICENSE("GPL"); |