1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
|
/*
* linux/drivers/block/via82c586.c Version 0.01 Aug 16, 1998
*
* Copyright (C) 1998 Michel Aubry
* Copyright (C) 1998 Andre Hedrick
*
* The VIA MVP-3 is reported OK with UDMA.
*
* VIA chips also have a single FIFO, with the same 64 bytes deep buffer (16 levels
* of 4 bytes each).
* However, VIA chips can have the buffer split either 8:8 levels, 16:0 levels or
* 0:16 levels between both channels. One could think of using this feature, as even
* if no level of FIFO is given to a given channel, one can always reach ATAPI drives
* through it, or, if one channel is unused, configuration defaults to an even split
* FIFO levels.
*/
#include <linux/types.h>
#include <linux/kernel.h>
#include <linux/timer.h>
#include <linux/mm.h>
#include <linux/ioport.h>
#include <linux/interrupt.h>
#include <linux/blkdev.h>
#include <linux/hdreg.h>
#include <linux/pci.h>
#include <linux/delay.h>
#include <asm/io.h>
#include "ide.h"
/*
* Set VIA Chipset Timings for (U)DMA modes enabled.
*
* VIA Apollo chipset has complete support for
* setting up the timing parameters.
*/
static void set_via_timings (ide_hwif_t *hwif)
{
struct pci_dev *dev = hwif->pci_dev;
byte post = hwif->channel ? 0xc0 : 0x30;
byte flush = hwif->channel ? 0xa0 : 0x50;
byte via_config = 0;
int rc = 0, errors = 0;
printk("%s: VIA Bus-Master ", hwif->name);
if (!hwif->dma_base) {
printk(" ERROR, NO DMA_BASE\n");
return;
}
/* setting IDE read prefetch buffer and IDE post write buffer.
* (This feature allows prefetched reads and post writes).
*/
if ((rc = pci_read_config_byte(dev, 0x41, &via_config))) {
errors++;
goto via_error;
}
if ((rc = pci_write_config_byte(dev, 0x41, via_config | post))) {
errors++;
goto via_error;
}
/* setting Channel read and End-of-sector FIFO flush.
* (This feature ensures that FIFO flush is enabled:
* - for read DMA when interrupt asserts the given channel.
* - at the end of each sector for the given channel.)
*/
if ((rc = pci_read_config_byte(dev, 0x46, &via_config))) {
errors++;
goto via_error;
}
if ((rc = pci_write_config_byte(dev, 0x46, via_config | flush))) {
errors++;
goto via_error;
}
via_error:
printk("(U)DMA Timing Config %s\n", errors ? "ERROR" : "Success");
}
void ide_init_via82c586 (ide_hwif_t *hwif)
{
set_via_timings(hwif);
}
|