2 * linux/drivers/block/sis5513.c Version 0.07 Sept. 3, 1999
4 * Copyright (C) 1999 Andre Hedrick (andre@suse.com)
5 * May be copied or modified under the terms of the GNU General Public License
7 * Thanks to SIS Taiwan for direct support and hardware.
8 * Tested and designed on the SiS620/5513 chipset.
11 #include <linux/types.h>
12 #include <linux/kernel.h>
13 #include <linux/delay.h>
14 #include <linux/timer.h>
16 #include <linux/ioport.h>
17 #include <linux/blkdev.h>
18 #include <linux/hdreg.h>
20 #include <linux/interrupt.h>
21 #include <linux/pci.h>
22 #include <linux/init.h>
23 #include <linux/ide.h>
28 #include "ide_modes.h"
30 #define SIS5513_DEBUG_DRIVE_INFO 0
32 #define DISPLAY_SIS_TIMINGS
34 static struct pci_dev
*host_dev
;
37 static struct _pio_mode_mapping
{
41 } pio_mode_mapping
[] = {
49 static struct _dma_mode_mapping
{
53 } dma_mode_mapping
[] = {
59 static struct _udma_mode_mapping
{
62 } udma_mode_mapping
[] = {
71 static __inline__
char * find_udma_mode (byte cycle_time
)
75 for (n
= 0; n
<= 4; n
++)
76 if (udma_mode_mapping
[n
].cycle_time
<= cycle_time
)
77 return udma_mode_mapping
[n
].udma_mode
;
78 return udma_mode_mapping
[4].udma_mode
;
82 #if defined(DISPLAY_SIS_TIMINGS) && defined(CONFIG_PROC_FS)
83 #include <linux/stat.h>
84 #include <linux/proc_fs.h>
86 static int sis_get_info(char *, char **, off_t
, int, int);
87 extern int (*sis_display_info
)(char *, char **, off_t
, int, int); /* ide-proc.c */
88 struct pci_dev
*bmide_dev
;
90 static char *cable_type
[] = {
95 static char *recovery_time
[] ={
96 "12 PCICLK", "1 PCICLK",
97 "2 PCICLK", "3 PCICLK",
98 "4 PCICLK", "5 PCICLCK",
99 "6 PCICLK", "7 PCICLCK",
100 "8 PCICLK", "9 PCICLCK",
101 "10 PCICLK", "11 PCICLK",
102 "13 PCICLK", "14 PCICLK",
103 "15 PCICLK", "15 PCICLK"
106 static char *cycle_time
[] = {
107 "Undefined", "2 CLCK",
113 static char *active_time
[] = {
114 "8 PCICLK", "1 PCICLCK",
115 "2 PCICLK", "2 PCICLK",
116 "4 PCICLK", "5 PCICLK",
117 "6 PCICLK", "12 PCICLK"
120 static int sis_get_info (char *buffer
, char **addr
, off_t offset
, int count
, int dummy
)
130 p
+= sprintf(p
, "--------------- Primary Channel ---------------- Secondary Channel -------------\n");
131 rc
= pci_read_config_byte(bmide_dev
, 0x4a, ®
);
132 p
+= sprintf(p
, "Channel Status: %s \t \t \t \t %s \n",
133 (reg
& 0x02) ? "On" : "Off",
134 (reg
& 0x04) ? "On" : "Off");
136 rc
= pci_read_config_byte(bmide_dev
, 0x09, ®
);
137 p
+= sprintf(p
, "Operation Mode: %s \t \t \t %s \n",
138 (reg
& 0x01) ? "Native" : "Compatible",
139 (reg
& 0x04) ? "Native" : "Compatible");
141 rc
= pci_read_config_byte(bmide_dev
, 0x48, ®
);
142 p
+= sprintf(p
, "Cable Type: %s \t \t \t %s\n",
143 (reg
& 0x10) ? cable_type
[1] : cable_type
[0],
144 (reg
& 0x20) ? cable_type
[1] : cable_type
[0]);
146 rc
= pci_read_config_word(bmide_dev
, 0x4c, ®2
);
147 rc
= pci_read_config_word(bmide_dev
, 0x4e, ®3
);
148 p
+= sprintf(p
, "Prefetch Count: %d \t \t \t \t %d\n",
151 rc
= pci_read_config_byte(bmide_dev
, 0x4b, ®
);
152 p
+= sprintf(p
, "Drvie 0: Postwrite %s \t \t Postwrite %s\n",
153 (reg
& 0x10) ? "Enabled" : "Disabled",
154 (reg
& 0x40) ? "Enabled" : "Disabled");
155 p
+= sprintf(p
, " Prefetch %s \t \t Prefetch %s\n",
156 (reg
& 0x01) ? "Enabled" : "Disabled",
157 (reg
& 0x04) ? "Enabled" : "Disabled");
159 rc
= pci_read_config_byte(bmide_dev
, 0x41, ®
);
160 rc
= pci_read_config_byte(bmide_dev
, 0x45, ®1
);
161 p
+= sprintf(p
, " UDMA %s \t \t \t UDMA %s\n",
162 (reg
& 0x80) ? "Enabled" : "Disabled",
163 (reg1
& 0x80) ? "Enabled" : "Disabled");
164 p
+= sprintf(p
, " UDMA Cycle Time %s \t UDMA Cycle Time %s\n",
165 cycle_time
[(reg
& 0x70) >> 4], cycle_time
[(reg1
& 0x70) >> 4]);
166 p
+= sprintf(p
, " Data Active Time %s \t Data Active Time %s\n",
167 active_time
[(reg
& 0x07)], active_time
[(reg
&0x07)] );
169 rc
= pci_read_config_byte(bmide_dev
, 0x40, ®
);
170 rc
= pci_read_config_byte(bmide_dev
, 0x44, ®1
);
171 p
+= sprintf(p
, " Data Recovery Time %s \t Data Recovery Time %s\n",
172 recovery_time
[(reg
& 0x0f)], recovery_time
[(reg1
& 0x0f)]);
175 rc
= pci_read_config_byte(bmide_dev
, 0x4b, ®
);
176 p
+= sprintf(p
, "Drvie 1: Postwrite %s \t \t Postwrite %s\n",
177 (reg
& 0x20) ? "Enabled" : "Disabled",
178 (reg
& 0x80) ? "Enabled" : "Disabled");
179 p
+= sprintf(p
, " Prefetch %s \t \t Prefetch %s\n",
180 (reg
& 0x02) ? "Enabled" : "Disabled",
181 (reg
& 0x08) ? "Enabled" : "Disabled");
183 rc
= pci_read_config_byte(bmide_dev
, 0x43, ®
);
184 rc
= pci_read_config_byte(bmide_dev
, 0x47, ®1
);
185 p
+= sprintf(p
, " UDMA %s \t \t \t UDMA %s\n",
186 (reg
& 0x80) ? "Enabled" : "Disabled",
187 (reg1
& 0x80) ? "Enabled" : "Disabled");
188 p
+= sprintf(p
, " UDMA Cycle Time %s \t UDMA Cycle Time %s\n",
189 cycle_time
[(reg
& 0x70) >> 4], cycle_time
[(reg1
& 0x70) >> 4]);
190 p
+= sprintf(p
, " Data Active Time %s \t Data Active Time %s\n",
191 active_time
[(reg
& 0x07)], active_time
[(reg
&0x07)] );
193 rc
= pci_read_config_byte(bmide_dev
, 0x42, ®
);
194 rc
= pci_read_config_byte(bmide_dev
, 0x46, ®1
);
195 p
+= sprintf(p
, " Data Recovery Time %s \t Data Recovery Time %s\n",
196 recovery_time
[(reg
& 0x0f)], recovery_time
[(reg1
& 0x0f)]);
199 #endif /* defined(DISPLAY_SIS_TIMINGS) && defined(CONFIG_PROC_FS) */
202 extern char *ide_xfer_verbose (byte xfer_rate
);
205 * ((id->word93 & 0x2000) && (HWIF(drive)->udma_four))
207 static int config_chipset_for_dma (ide_drive_t
*drive
, byte ultra
)
209 struct hd_driveid
*id
= drive
->id
;
210 ide_hwif_t
*hwif
= HWIF(drive
);
211 struct pci_dev
*dev
= hwif
->pci_dev
;
213 byte drive_pci
, test1
, test2
, mask
;
218 byte four_two
= 0x00;
219 int drive_number
= ((hwif
->channel
? 2 : 0) + (drive
->select
.b
.unit
& 0x01));
220 byte udma_66
= ((id
->word93
& 0x2000) && (hwif
->udma_four
)) ? 1 : 0;
223 switch(host_dev
->device
) {
224 case PCI_DEVICE_ID_SI_530
:
225 case PCI_DEVICE_ID_SI_620
:
233 switch(drive_number
) {
234 case 0: drive_pci
= 0x40;break;
235 case 1: drive_pci
= 0x42;break;
236 case 2: drive_pci
= 0x44;break;
237 case 3: drive_pci
= 0x46;break;
238 default: return ide_dma_off
;
241 pci_read_config_byte(dev
, drive_pci
, &test1
);
242 pci_read_config_byte(dev
, drive_pci
|0x01, &test2
);
244 if ((!ultra
) && (test2
& 0x80)) {
245 pci_write_config_byte(dev
, drive_pci
|0x01, test2
& ~0x80);
246 pci_read_config_byte(dev
, drive_pci
|0x01, &test2
);
249 if ((id
->dma_ultra
& 0x0010) && (ultra
) && (udma_66
) && (four_two
)) {
250 if (!(test2
& 0x90)) {
251 pci_write_config_byte(dev
, drive_pci
|0x01, test2
& ~unmask
);
252 pci_write_config_byte(dev
, drive_pci
|0x01, test2
|0x90);
255 } else if ((id
->dma_ultra
& 0x0008) && (ultra
) && (udma_66
) && (four_two
)) {
256 if (!(test2
& 0xA0)) {
257 pci_write_config_byte(dev
, drive_pci
|0x01, test2
& ~unmask
);
258 pci_write_config_byte(dev
, drive_pci
|0x01, test2
|0xA0);
261 } else if ((id
->dma_ultra
& 0x0004) && (ultra
)) {
262 mask
= (four_two
) ? 0xB0 : 0xA0;
263 if (!(test2
& mask
)) {
264 pci_write_config_byte(dev
, drive_pci
|0x01, test2
& ~unmask
);
265 pci_write_config_byte(dev
, drive_pci
|0x01, test2
|mask
);
268 } else if ((id
->dma_ultra
& 0x0002) && (ultra
)) {
269 mask
= (four_two
) ? 0xD0 : 0xC0;
270 if (!(test2
& mask
)) {
271 pci_write_config_byte(dev
, drive_pci
|0x01, test2
& ~unmask
);
272 pci_write_config_byte(dev
, drive_pci
|0x01, test2
|mask
);
275 } else if ((id
->dma_ultra
& 0x0001) && (ultra
)) {
276 if (!(test2
& unmask
)) {
277 pci_write_config_byte(dev
, drive_pci
|0x01, test2
& ~unmask
);
278 pci_write_config_byte(dev
, drive_pci
|0x01, test2
|unmask
);
281 } else if (id
->dma_mword
& 0x0004) {
282 speed
= XFER_MW_DMA_2
;
283 } else if (id
->dma_mword
& 0x0002) {
284 speed
= XFER_MW_DMA_1
;
285 } else if (id
->dma_mword
& 0x0001) {
286 speed
= XFER_MW_DMA_0
;
287 } else if (id
->dma_1word
& 0x0004) {
288 speed
= XFER_SW_DMA_2
;
289 } else if (id
->dma_1word
& 0x0002) {
290 speed
= XFER_SW_DMA_1
;
291 } else if (id
->dma_1word
& 0x0001) {
292 speed
= XFER_SW_DMA_0
;
294 return ((int) ide_dma_off_quietly
);
297 err
= ide_config_drive_speed(drive
, speed
);
299 #if SIS5513_DEBUG_DRIVE_INFO
300 printk("%s: %s drive%d\n", drive
->name
, ide_xfer_verbose(speed
), drive_number
);
301 #endif /* SIS5513_DEBUG_DRIVE_INFO */
303 return ((int) ((id
->dma_ultra
>> 11) & 3) ? ide_dma_on
:
304 ((id
->dma_ultra
>> 8) & 7) ? ide_dma_on
:
305 ((id
->dma_mword
>> 8) & 7) ? ide_dma_on
:
306 ((id
->dma_1word
>> 8) & 7) ? ide_dma_on
:
307 ide_dma_off_quietly
);
310 static void config_drive_art_rwp (ide_drive_t
*drive
)
312 ide_hwif_t
*hwif
= HWIF(drive
);
313 struct pci_dev
*dev
= hwif
->pci_dev
;
315 byte timing
, pio
, drive_pci
, test1
, test2
;
317 unsigned short eide_pio_timing
[6] = {600, 390, 240, 180, 120, 90};
318 unsigned short xfer_pio
= drive
->id
->eide_pio_modes
;
319 int drive_number
= ((hwif
->channel
? 2 : 0) + (drive
->select
.b
.unit
& 0x01));
321 if (drive
->media
== ide_disk
) {
322 struct pci_dev
*dev
= hwif
->pci_dev
;
324 byte rw_prefetch
= (0x11 << drive_number
);
326 pci_read_config_byte(dev
, 0x4b, ®4bh
);
327 if ((reg4bh
& rw_prefetch
) != rw_prefetch
)
328 pci_write_config_byte(dev
, 0x4b, reg4bh
|rw_prefetch
);
331 pio
= ide_get_best_pio_mode(drive
, 255, 5, NULL
);
336 if (drive
->id
->eide_pio_iordy
> 0) {
339 drive
->id
->eide_pio_iordy
>eide_pio_timing
[xfer_pio
];
342 xfer_pio
= (drive
->id
->eide_pio_modes
& 4) ? 0x05 :
343 (drive
->id
->eide_pio_modes
& 2) ? 0x04 :
344 (drive
->id
->eide_pio_modes
& 1) ? 0x03 : xfer_pio
;
347 timing
= (xfer_pio
>= pio
) ? xfer_pio
: pio
;
350 * Mode 0 Mode 1 Mode 2 Mode 3 Mode 4
351 * Active time 8T (240ns) 6T (180ns) 4T (120ns) 3T (90ns) 3T (90ns)
352 * 0x41 2:0 bits 000 110 100 011 011
353 * Recovery time 12T (360ns) 7T (210ns) 4T (120ns) 3T (90ns) 1T (30ns)
354 * 0x40 3:0 bits 0000 0111 0100 0011 0001
355 * Cycle time 20T (600ns) 13T (390ns) 8T (240ns) 6T (180ns) 4T (120ns)
358 switch(drive_number
) {
359 case 0: drive_pci
= 0x40;break;
360 case 1: drive_pci
= 0x42;break;
361 case 2: drive_pci
= 0x44;break;
362 case 3: drive_pci
= 0x46;break;
366 pci_read_config_byte(dev
, drive_pci
, &test1
);
367 pci_read_config_byte(dev
, drive_pci
|0x01, &test2
);
370 * Do a blanket clear of active and recovery timings.
377 case 4: test1
|= 0x01;test2
|= 0x03;break;
378 case 3: test1
|= 0x03;test2
|= 0x03;break;
379 case 2: test1
|= 0x04;test2
|= 0x04;break;
380 case 1: test1
|= 0x07;test2
|= 0x06;break;
384 pci_write_config_byte(dev
, drive_pci
, test1
);
385 pci_write_config_byte(dev
, drive_pci
|0x01, test2
);
388 static int config_drive_xfer_rate (ide_drive_t
*drive
)
390 struct hd_driveid
*id
= drive
->id
;
391 ide_dma_action_t dma_func
= ide_dma_off_quietly
;
393 if (id
&& (id
->capability
& 1) && HWIF(drive
)->autodma
) {
394 /* Consult the list of known "bad" drives */
395 if (ide_dmaproc(ide_dma_bad_drive
, drive
)) {
396 return HWIF(drive
)->dmaproc(ide_dma_off
, drive
);
399 if (id
->field_valid
& 4) {
400 if (id
->dma_ultra
& 0x001F) {
401 /* Force if Capable UltraDMA */
402 dma_func
= config_chipset_for_dma(drive
, 1);
403 if ((id
->field_valid
& 2) &&
404 (dma_func
!= ide_dma_on
))
407 } else if (id
->field_valid
& 2) {
409 if ((id
->dma_mword
& 0x0007) ||
410 (id
->dma_1word
& 0x0007)) {
411 /* Force if Capable regular DMA modes */
412 dma_func
= config_chipset_for_dma(drive
, 0);
414 } else if ((ide_dmaproc(ide_dma_good_drive
, drive
)) &&
415 (id
->eide_dma_time
> 150)) {
416 /* Consult the list of known "good" drives */
417 dma_func
= config_chipset_for_dma(drive
, 0);
420 return HWIF(drive
)->dmaproc(dma_func
, drive
);
424 * sis5513_dmaproc() initiates/aborts (U)DMA read/write operations on a drive.
426 int sis5513_dmaproc (ide_dma_action_t func
, ide_drive_t
*drive
)
430 config_drive_art_rwp(drive
);
431 return config_drive_xfer_rate(drive
);
435 return ide_dmaproc(func
, drive
); /* use standard DMA stuff */
438 unsigned int __init
pci_init_sis5513 (struct pci_dev
*dev
, const char *name
)
440 struct pci_dev
*host
;
443 pci_read_config_byte(dev
, PCI_LATENCY_TIMER
, &latency
);
445 for (host
= pci_devices
; host
; host
=host
->next
) {
446 if (host
->vendor
== PCI_VENDOR_ID_SI
&&
447 host
->device
== PCI_DEVICE_ID_SI_620
) {
449 pci_write_config_byte(dev
, PCI_LATENCY_TIMER
, 0x10);
452 } else if (host
->vendor
== PCI_VENDOR_ID_SI
&&
453 host
->device
== PCI_DEVICE_ID_SI_530
) {
456 } else if (host
->vendor
== PCI_VENDOR_ID_SI
&&
457 host
->device
== PCI_DEVICE_ID_SI_5600
) {
460 } else if (host
->vendor
== PCI_VENDOR_ID_SI
&&
461 host
->device
== PCI_DEVICE_ID_SI_5597
) {
470 pci_read_config_byte(dev
, 0x52, ®52h
);
471 if (!(reg52h
& 0x04))
472 /* set IDE controller to operate in Compabitility mode obly */
473 pci_write_config_byte(dev
, 0x52, reg52h
|0x04);
474 #if defined(DISPLAY_SIS_TIMINGS) && defined(CONFIG_PROC_FS)
477 sis_display_info
= &sis_get_info
;
478 #endif /* defined(DISPLAY_SIS_TIMINGS) && defined(CONFIG_PROC_FS) */
483 unsigned int __init
ata66_sis5513 (ide_hwif_t
*hwif
)
485 byte reg48h
= 0, ata66
= 0;
486 byte mask
= hwif
->channel
? 0x20 : 0x10;
487 pci_read_config_byte(hwif
->pci_dev
, 0x48, ®48h
);
490 switch(host_dev
->device
) {
491 case PCI_DEVICE_ID_SI_530
:
492 case PCI_DEVICE_ID_SI_620
:
493 ata66
= (reg48h
& mask
) ? 0 : 1;
501 void __init
ide_init_sis5513 (ide_hwif_t
*hwif
)
504 hwif
->irq
= hwif
->channel
? 15 : 14;
506 if (!(hwif
->dma_base
))
510 switch(host_dev
->device
) {
511 case PCI_DEVICE_ID_SI_530
:
512 case PCI_DEVICE_ID_SI_620
:
513 case PCI_DEVICE_ID_SI_5600
:
514 case PCI_DEVICE_ID_SI_5597
:
516 hwif
->dmaproc
= &sis5513_dmaproc
;