Updates to BIOS IDE timings code
Hi Alan,
Attached is a patch that addresses some of the issues we discussed previously. The patch does the following:
# Moves BIOS timings IDE detection into chipset drivers (by providing a
library function).
# Provide the above library function that sets default values for tune
parameters. It also handles the special case where user has requested to use BIOS IDE timings. Caller is assumed to support DMA on/off probe using the dma_status register unless a dma_check funtion is provided (note, the tekram driver is somewhat different from all the others, and haven't been updated yet).
# Makes BIOS IDE timings work for both IDE0 and IDE1 at the same time.
What hasn't been addresses yet, but that I'm working on is proper simplex detection when 'biostimings' are used. However, to me it seems like the simplex code is in the middle of being updated, right? On some chipsets we make just dma_base isn't set on both interfaces if device claims to be simplex. On others we force dma on both channels if simplex mode, why?
Tested with via82cxxx, serverworks and piix. 'biostimings' is only supported on PCI chips.
More generic IDE cleanups are needed here and there, so thats probaly next.
Cheers,
Torben
include/linux/ide.h +1 -0
@@ -1723,6 +1723,7 @@extern void export_ide_init_queue (ide_drive_t *);extern u8 export_probe_for_drive (ide_drive_t *);extern int probe_hwif_init (ide_hwif_t *); +extern int ide_setup_tune (ide_hwif_t *,int (dma_check )(ide_hwif_t *,int ));static inline void *ide_get_hwifdata (ide_hwif_t * hwif) {
drivers/ide/ide-dma.c +93 -11
115 lines not on this page · raw message
drivers/ide/ide.c +6 -8
@@ -1849,9 +1849,9 @@*/ const char *ide_words[] = {"noprobe" ,"serialize" ,"autotune" ,"noautotune" , -"reset" ,"dma" ,"ata66" ,"minus8" ,"minus9" ,"minus10" , +"reset" ,"dma" ,"ata66" ,"biostimings" ,"minus9" ,"minus10" ,"four" ,"qd65xx" ,"ht6560b" ,"cmd640_vlb" ,"dtc2278" , -"umc8672" ,"ali14xx" ,"dc4030" ,"biostimings" ,NULL }; +"umc8672" ,"ali14xx" ,"dc4030" ,NULL }; hw = s[3 ] -'0' ; hwif = &ide_hwifs[hw]; i =match_parm (&s[4 ], ide_words, vals,3 );
@@ -1870,10 +1870,6 @@ }switch (i) { -case -19 :/* "biostimings" */ - hwif->drives[0 ].autotune =IDE_TUNE_BIOS ; - hwif->drives[1 ].autotune =IDE_TUNE_BIOS ; - goto done;#ifdef CONFIG_BLK_DEV_PDC4030 case -18 :/* "dc4030" */ {
@@ -1944,8 +1940,10 @@#endif /* CONFIG_BLK_DEV_4DRIVES */ case -10 :/* minus10 */ case -9 :/* minus9 */ -case -8 :/* minus8 */ - goto bad_option; +case -8 :/* "biostimings" */ + hwif->drives[0 ].autotune =IDE_TUNE_BIOS ; + hwif->drives[1 ].autotune =IDE_TUNE_BIOS ; + goto done;case -7 :/* ata66 */ #ifdef CONFIG_BLK_DEV_IDEPCI hwif->udma_four =1 ;
drivers/ide/pci/aec62xx.c +3 -6
@@ -442,12 +442,9 @@if (hwif->mate) hwif->mate->serialized = hwif->serialized; - -if (!hwif->dma_base) { - hwif->drives[0 ].autotune =1 ; - hwif->drives[1 ].autotune =1 ; + +if (ide_setup_tune (hwif,NULL ))return ; - } hwif->ultra_mask =0x7f ; hwif->mwdma_mask =0x07 ;
@@ -480,7 +477,7 @@if (!(hwif->udma_four)) hwif->udma_four = (ata66&(hwif->channel?0x02 :0x01 ))?0 :1 ; } - +ide_setup_dma (hwif, dmabase,8 ); }
drivers/ide/pci/alim15x3.c +2 -5
@@ -740,12 +740,9 @@/* Don't use LBA48 on ALi devices before rev 0xC5 */ hwif->addressing = (m5229_revision <=0xC4 ) ?1 :0 ; - -if (!hwif->dma_base) { - hwif->drives[0 ].autotune =1 ; - hwif->drives[1 ].autotune =1 ; + +if (ide_setup_tune (hwif,NULL ))return ; - }if (m5229_revision >0x20 ) hwif->ultra_mask =0x3f ;
drivers/ide/pci/amd74xx.c +1 -4
@@ -349,11 +349,8 @@ hwif->tuneproc = &amd74xx_tune_drive; hwif->speedproc = &amd74xx_tune_chipset; -if (!hwif->dma_base) { - hwif->drives[0 ].autotune =1 ; - hwif->drives[1 ].autotune =1 ; +if (ide_setup_tune (hwif,NULL ))return ; - } hwif->atapi_dma =1 ; hwif->ultra_mask =0x3f ;
drivers/ide/pci/cmd640.c +2 -1
@@ -846,7 +846,8 @@for (index =0 ; index < (2 + (second_port_cmd640 <<1 )); index++) {ide_drive_t *drive = cmd_drives[index];#ifdef CONFIG_BLK_DEV_CMD640_ENHANCED -if (drive->autotune || ((index >1 ) && second_port_toggled)) { +if (drive->autotune ==IDE_TUNE_AUTO || + ((index >1 ) && second_port_toggled)) {/* * Reset timing to the slowest speed and turn off prefetch. * This way, the drive identify code has a better chance.
drivers/ide/pci/cmd64x.c +1 -4
@@ -703,11 +703,8 @@ hwif->tuneproc = &cmd64x_tuneproc; hwif->speedproc = &cmd64x_tune_chipset; -if (!hwif->dma_base) { - hwif->drives[0 ].autotune =1 ; - hwif->drives[1 ].autotune =1 ; +if (ide_setup_tune (hwif,NULL ))return ; - } hwif->atapi_dma =1 ;
drivers/ide/pci/cs5530.c +7 -4
@@ -377,17 +377,20 @@if (CS5530_BAD_PIO (d0_timings)) {/* PIO timings not initialized? */ hwif->OUTL (cs5530_pio_timings[(d0_timings>>31 )&1 ][0 ], basereg+0 ); -if (!hwif->drives[0 ].autotune) - hwif->drives[0 ].autotune =1 ; +if (hwif->drives[0 ].autotune ==IDE_TUNE_DEFAULT ) + hwif->drives[0 ].autotune =IDE_TUNE_AUTO ;/* needs autotuning later */ }if (CS5530_BAD_PIO (hwif->INL (basereg+8 ))) {/* PIO timings not initialized? */ hwif->OUTL (cs5530_pio_timings[(d0_timings>>31 )&1 ][0 ], basereg+8 ); -if (!hwif->drives[1 ].autotune) - hwif->drives[1 ].autotune =1 ; +if (hwif->drives[1 ].autotune ==IDE_TUNE_DEFAULT ) + hwif->drives[1 ].autotune =IDE_TUNE_AUTO ;/* needs autotuning later */ } + +if (ide_setup_tune (hwif,NULL )) +return ; hwif->atapi_dma =1 ; hwif->ultra_mask =0x07 ;
drivers/ide/pci/cy82c693.c +2 -5
@@ -393,12 +393,9 @@ hwif->chipset = ide_cy82c693; hwif->tuneproc = &cy82c693_tune_drive; - -if (!hwif->dma_base) { - hwif->drives[0 ].autotune =1 ; - hwif->drives[1 ].autotune =1 ; + +if (ide_setup_tune (hwif,NULL ))return ; - } hwif->atapi_dma =1 ; hwif->mwdma_mask =0x04 ;
drivers/ide/pci/generic.c +2 -2
@@ -41,8 +41,8 @@default :break ; } - -if (!(hwif->dma_base)) + +if (ide_setup_tune (hwif,NULL ))return ; hwif->atapi_dma =1 ;
drivers/ide/pci/hpt34x.c +3 -2
@@ -293,8 +293,9 @@ hwif->tuneproc = &hpt34x_tune_drive; hwif->speedproc = &hpt34x_tune_chipset; hwif->no_dsc =1 ; - hwif->drives[0 ].autotune =1 ; - hwif->drives[1 ].autotune =1 ; + +if (ide_setup_tune (hwif,NULL )) +return ;pci_read_config_word (hwif->pci_dev,PCI_COMMAND , &pcicmd);
drivers/ide/pci/hpt366.c +1 -4
@@ -1015,11 +1015,8 @@ hwif->busproc = &hpt3xx_tristate; } -if (!hwif->dma_base) { - hwif->drives[0 ].autotune =1 ; - hwif->drives[1 ].autotune =1 ; +if (ide_setup_tune (hwif,NULL ))return ; - } hwif->ultra_mask =0x7f ; hwif->mwdma_mask =0x07 ;
drivers/ide/pci/it8172.c +2 -5
@@ -266,12 +266,9 @@ide_init_hwif_ports (&hwif->hw, cmdBase, ctrlBase |2 ,NULL );memcpy (hwif->io_ports, hwif->hw.io_ports,sizeof (hwif->io_ports)); hwif->noprobe =0 ; - -if (!hwif->dma_base) { - hwif->drives[0 ].autotune =1 ; - hwif->drives[1 ].autotune =1 ; + + if (ide_setup_tune(hwif, NULL)return ; - } hwif->atapi_dma =1 ; hwif->ultra_mask =0x07 ;
drivers/ide/pci/ns87415.c +1 -1
@@ -204,7 +204,7 @@else if (!hwif->irq && hwif->mate && hwif->mate->irq) hwif->irq = hwif->mate->irq;/* share IRQ with mate */ -if (!hwif->dma_base) +if (ide_setup_tune (hwif,NULL ))return ; hwif->OUTB (0x60 , hwif->dma_status);
drivers/ide/pci/nvidia.c +1 -4
@@ -301,11 +301,8 @@ hwif->speedproc = &nforce_tune_chipset; hwif->autodma =0 ; -if (!hwif->dma_base) { - hwif->drives[0 ].autotune =1 ; - hwif->drives[1 ].autotune =1 ; +if (ide_setup_tune (hwif,NULL ))return ; - } hwif->atapi_dma =1 ; hwif->ultra_mask =0x3f ;
drivers/ide/pci/opti621.c +2 -2
@@ -335,8 +335,8 @@ hwif->drives[0 ].drive_data =PIO_DONT_KNOW ; hwif->drives[1 ].drive_data =PIO_DONT_KNOW ; hwif->tuneproc = &opti621_tune_drive; - -if (!(hwif->dma_base)) + +if (ide_setup_tune (hwif,NULL ))return ; hwif->atapi_dma =1 ;
drivers/ide/pci/pdc202xx_new.c +2 -4
@@ -537,11 +537,9 @@ hwif->quirkproc = &pdcnew_quirkproc; hwif->speedproc = &pdcnew_new_tune_chipset; hwif->resetproc = &pdcnew_new_reset; - -if (!hwif->dma_base) { - hwif->drives[0 ].autotune = hwif->drives[1 ].autotune =1 ; + +if (ide_setup_tune (hwif,NULL ))return ; - } hwif->ultra_mask =0x7f ; hwif->mwdma_mask =0x07 ;
drivers/ide/pci/pdc202xx_old.c +2 -4
@@ -759,11 +759,9 @@ } hwif->speedproc = &pdc202xx_tune_chipset; - -if (!hwif->dma_base) { - hwif->drives[0 ].autotune = hwif->drives[1 ].autotune =1 ; + +if (ide_setup_tune (hwif,NULL ))return ; - } hwif->ultra_mask =0x3f ; hwif->mwdma_mask =0x07 ;
drivers/ide/pci/piix.c +2 -4
@@ -581,10 +581,8 @@ hwif->autodma =0 ; hwif->tuneproc = &piix_tune_drive; hwif->speedproc = &piix_tune_chipset; - hwif->drives[0 ].autotune =1 ; - hwif->drives[1 ].autotune =1 ; - -if (!hwif->dma_base) + +if (ide_setup_tune (hwif,NULL ))return ; hwif->atapi_dma =1 ;
drivers/ide/pci/sc1200.c +11 -8
@@ -526,14 +526,17 @@if (hwif->mate) hwif->serialized = hwif->mate->serialized =1 ; hwif->autodma =0 ; -if (hwif->dma_base) { - hwif->ide_dma_check = &sc1200_config_dma; - hwif->ide_dma_end = &sc1200_ide_dma_end; -if (!noautodma) - hwif->autodma =1 ; - hwif->tuneproc = &sc1200_tuneproc; - } - hwif->atapi_dma =1 ; + hwif->tuneproc = &sc1200_tuneproc; + +if (ide_setup_tune (hwif,NULL )) +return ; + + hwif->ide_dma_check = &sc1200_config_dma; + hwif->ide_dma_end = &sc1200_ide_dma_end; +if (!noautodma) + hwif->autodma =1 ; + + hwif->atapi_dma =1 ; hwif->ultra_mask =0x07 ; hwif->mwdma_mask =0x07 ;
drivers/ide/pci/serverworks.c +4 -7
@@ -704,12 +704,9 @@#endif /* CAN_SW_DMA */ hwif->autodma =0 ; - -if (!hwif->dma_base) { - hwif->drives[0 ].autotune =1 ; - hwif->drives[1 ].autotune =1 ; + +if (ide_setup_tune (hwif,NULL ))return ; - } hwif->ide_dma_check = &svwks_config_drive_xfer_rate;if (hwif->pci_dev->device ==PCI_DEVICE_ID_SERVERWORKS_OSB4IDE )
@@ -722,8 +719,8 @@ dma_stat = hwif->INB (hwif->dma_status); hwif->drives[0 ].autodma = (dma_stat &0x20 ); hwif->drives[1 ].autodma = (dma_stat &0x40 ); - hwif->drives[0 ].autotune = (!(dma_stat &0x20 )); - hwif->drives[1 ].autotune = (!(dma_stat &0x40 )); +// hwif->drives[0].autotune = (!(dma_stat & 0x20)); +// hwif->drives[1].autotune = (!(dma_stat & 0x40)); // hwif->drives[0].autodma = hwif->autodma; // hwif->drives[1].autodma = hwif->autodma; }
drivers/ide/pci/siimage.c +1 -4
@@ -794,11 +794,8 @@ hwif->reset_poll = &siimage_reset_poll; hwif->pre_reset = &siimage_pre_reset; -if (!hwif->dma_base) { - hwif->drives[0 ].autotune =1 ; - hwif->drives[1 ].autotune =1 ; +if (ide_setup_tune (hwif,NULL ))return ; - } hwif->ultra_mask =0x7f ; hwif->mwdma_mask =0x07 ;
drivers/ide/pci/sis5513.c +2 -5
@@ -982,12 +982,9 @@ hwif->tuneproc = &sis5513_tune_drive; hwif->speedproc = &sis5513_tune_chipset; - -if (!(hwif->dma_base)) { - hwif->drives[0 ].autotune =1 ; - hwif->drives[1 ].autotune =1 ; + +if (ide_setup_tune (hwif,NULL ))return ; - } hwif->atapi_dma =1 ; hwif->ultra_mask =0x7f ;
drivers/ide/pci/sl82c105.c +4 -4
@@ -238,8 +238,8 @@ dma_state = hwif->INB (dma_base +2 ); rev =sl82c105_bridge_revision (hwif->pci_dev);if (rev <=5 ) { - hwif->drives[0 ].autotune =1 ; - hwif->drives[1 ].autotune =1 ; + hwif->drives[0 ].autotune =IDE_TUNE_AUTO ; + hwif->drives[1 ].autotune =IDE_TUNE_AUTO ;printk (" %s: Winbond 553 bridge revision %d, BM-DMA disabled\n" , hwif->name, rev); dma_state &= ~0x60 ;
@@ -260,8 +260,8 @@static void __init init_hwif_sl82c105 (ide_hwif_t *hwif) { hwif->tuneproc = tune_sl82c105; - -if (!hwif->dma_base) + +if (ide_setup_tune (hwif,NULL ))return ; hwif->atapi_dma =1 ;
drivers/ide/pci/slc90e66.c +2 -5
@@ -333,12 +333,9 @@ hwif->tuneproc = &slc90e66_tune_drive;pci_read_config_byte (hwif->pci_dev,0x47 , ®47); - -if (!hwif->dma_base) { - hwif->drives[0 ].autotune =1 ; - hwif->drives[1 ].autotune =1 ; + +if (ide_setup_tune (hwif,NULL ))return ; - } hwif->atapi_dma =1 ; hwif->ultra_mask =0x1f ;
drivers/ide/pci/via82cxxx.c +2 -3
@@ -592,11 +592,10 @@for (i =0 ; i <2 ; i++) { hwif->drives[i].io_32bit =1 ; hwif->drives[i].unmask = (via_config->flags &VIA_NO_UNMASK ) ?0 :1 ; - hwif->drives[i].autotune =1 ; hwif->drives[i].dn = hwif->channel *2 + i; } - -if (!hwif->dma_base) + +if (ide_setup_tune (hwif,NULL ))return ; hwif->atapi_dma =1 ;
drivers/ide/setup-pci.c +0 -15
@@ -587,7 +587,6 @@int at_least_one_hwif_enabled =0 ;ide_hwif_t *hwif, *mate =NULL ;static int secondpdc =0 ; -int drive0_tune, drive1_tune;u8 tmp; index->all =0xf0f0 ;
@@ -649,26 +648,12 @@ide_hwif_setup_dma (dev, d, hwif); bypass_legacy_dma: - drive0_tune = hwif->drives[0 ].autotune; - drive1_tune = hwif->drives[1 ].autotune; -if (d->init_hwif)/* Call chipset-specific routine * for each enabled hwif */ d->init_hwif (hwif); -/* -* This is in the wrong place. The driver may -* do set up based on the autotune value and this -* will then trash it. Torben please move it and -* propogate the fixes into the drivers -*/ -if (drive0_tune ==IDE_TUNE_BIOS )/* biostimings */ - hwif->drives[0 ].autotune =IDE_TUNE_BIOS ; -if (drive1_tune ==IDE_TUNE_BIOS ) - hwif->drives[1 ].autotune =IDE_TUNE_BIOS ; - mate = hwif; at_least_one_hwif_enabled =1 ; }
Quoted 5 lines · Torben Mathiasen
What hasn't been addresses yet, but that I'm working on is proper simplex detection when 'biostimings' are used. However, to me it seems like the simplex code is in the middle of being updated, right? On some chipsets we make just
dma_baseisn't set on both interfaces if device claims to be simplex. On others we force dma on both channels if simplex mode, why?
See the documentation for the chips concerned, that ought to make it more obvious. I dont think any of the examples I have docs for are non-NDA'd 8(
Alan