diff options
| author | Linus Torvalds <torvalds@woody.linux-foundation.org> | 2007-05-15 21:47:21 -0400 |
|---|---|---|
| committer | Linus Torvalds <torvalds@woody.linux-foundation.org> | 2007-05-15 21:47:21 -0400 |
| commit | e089d43fb1ab8e39168c9f61d30aef5b8724d085 (patch) | |
| tree | d027ec95c300076a83804b99c4014920844c34e1 | |
| parent | 0e402c6ec4f32a9192a30c4a5b5ba6867c0be7bc (diff) | |
| parent | e0ff9cd12a26259f8dd676124a188037e7e90b38 (diff) | |
Merge master.kernel.org:/pub/scm/linux/kernel/git/bart/ide-2.6
* master.kernel.org:/pub/scm/linux/kernel/git/bart/ide-2.6:
Use menuconfig objects: IDE
sl82c105: Switch to ref counting API
ide: remove ide_use_dma()
ide: add missing validity checks for identify words 62 and 63
ide: remove ide_dma_enable()
sl82c105: add speedproc() method and MWDMA0/1 support
cs5530/sc1200: add ->speedproc support
cs5530/sc1200: DMA support cleanup
ide: use ide_tune_dma() part #2
cs5530/sc1200: add ->udma_filter methods
ide: always disable DMA before tuning it
pdc202xx_new: use ide_tune_dma()
alim15x3: use ide_tune_dma()
sis5513: PIO mode setup fixes
serverworks: PIO mode setup fixes
pdc202xx_old: rewrite mode programming code (v2)
| -rw-r--r-- | drivers/ide/Kconfig | 15 | ||||
| -rw-r--r-- | drivers/ide/cris/ide-cris.c | 14 | ||||
| -rw-r--r-- | drivers/ide/ide-dma.c | 53 | ||||
| -rw-r--r-- | drivers/ide/ide-io.c | 1 | ||||
| -rw-r--r-- | drivers/ide/ide-lib.c | 12 | ||||
| -rw-r--r-- | drivers/ide/ide.c | 1 | ||||
| -rw-r--r-- | drivers/ide/pci/alim15x3.c | 69 | ||||
| -rw-r--r-- | drivers/ide/pci/cmd64x.c | 15 | ||||
| -rw-r--r-- | drivers/ide/pci/cs5530.c | 160 | ||||
| -rw-r--r-- | drivers/ide/pci/it821x.c | 21 | ||||
| -rw-r--r-- | drivers/ide/pci/pdc202xx_new.c | 29 | ||||
| -rw-r--r-- | drivers/ide/pci/pdc202xx_old.c | 184 | ||||
| -rw-r--r-- | drivers/ide/pci/sc1200.c | 161 | ||||
| -rw-r--r-- | drivers/ide/pci/scc_pata.c | 22 | ||||
| -rw-r--r-- | drivers/ide/pci/serverworks.c | 77 | ||||
| -rw-r--r-- | drivers/ide/pci/siimage.c | 24 | ||||
| -rw-r--r-- | drivers/ide/pci/sis5513.c | 85 | ||||
| -rw-r--r-- | drivers/ide/pci/sl82c105.c | 76 | ||||
| -rw-r--r-- | include/linux/ide.h | 3 |
19 files changed, 340 insertions, 682 deletions
diff --git a/drivers/ide/Kconfig b/drivers/ide/Kconfig index 9040809d2c25..b1a9b81c211f 100644 --- a/drivers/ide/Kconfig +++ b/drivers/ide/Kconfig | |||
| @@ -4,13 +4,10 @@ | |||
| 4 | # Andre Hedrick <andre@linux-ide.org> | 4 | # Andre Hedrick <andre@linux-ide.org> |
| 5 | # | 5 | # |
| 6 | 6 | ||
| 7 | if BLOCK | 7 | menuconfig IDE |
| 8 | |||
| 9 | menu "ATA/ATAPI/MFM/RLL support" | ||
| 10 | depends on HAS_IOMEM | ||
| 11 | |||
| 12 | config IDE | ||
| 13 | tristate "ATA/ATAPI/MFM/RLL support" | 8 | tristate "ATA/ATAPI/MFM/RLL support" |
| 9 | depends on BLOCK | ||
| 10 | depends on HAS_IOMEM | ||
| 14 | ---help--- | 11 | ---help--- |
| 15 | If you say Y here, your kernel will be able to manage low cost mass | 12 | If you say Y here, your kernel will be able to manage low cost mass |
| 16 | storage units such as ATA/(E)IDE and ATAPI units. The most common | 13 | storage units such as ATA/(E)IDE and ATAPI units. The most common |
| @@ -1099,8 +1096,4 @@ config BLK_DEV_HD_ONLY | |||
| 1099 | config BLK_DEV_HD | 1096 | config BLK_DEV_HD |
| 1100 | def_bool BLK_DEV_HD_IDE || BLK_DEV_HD_ONLY | 1097 | def_bool BLK_DEV_HD_IDE || BLK_DEV_HD_ONLY |
| 1101 | 1098 | ||
| 1102 | endif | 1099 | endif # IDE |
| 1103 | |||
| 1104 | endmenu | ||
| 1105 | |||
| 1106 | endif | ||
diff --git a/drivers/ide/cris/ide-cris.c b/drivers/ide/cris/ide-cris.c index c04cb25a01ff..ca0341c05e55 100644 --- a/drivers/ide/cris/ide-cris.c +++ b/drivers/ide/cris/ide-cris.c | |||
| @@ -1002,18 +1002,6 @@ static int cris_ide_build_dmatable (ide_drive_t *drive) | |||
| 1002 | return 1; /* let the PIO routines handle this weirdness */ | 1002 | return 1; /* let the PIO routines handle this weirdness */ |
| 1003 | } | 1003 | } |
| 1004 | 1004 | ||
| 1005 | static int cris_config_drive_for_dma (ide_drive_t *drive) | ||
| 1006 | { | ||
| 1007 | u8 speed = ide_max_dma_mode(drive); | ||
| 1008 | |||
| 1009 | if (!speed) | ||
| 1010 | return 0; | ||
| 1011 | |||
| 1012 | speed_cris_ide(drive, speed); | ||
| 1013 | |||
| 1014 | return ide_dma_enable(drive); | ||
| 1015 | } | ||
| 1016 | |||
| 1017 | /* | 1005 | /* |
| 1018 | * cris_dma_intr() is the handler for disk read/write DMA interrupts | 1006 | * cris_dma_intr() is the handler for disk read/write DMA interrupts |
| 1019 | */ | 1007 | */ |
| @@ -1043,7 +1031,7 @@ static ide_startstop_t cris_dma_intr (ide_drive_t *drive) | |||
| 1043 | 1031 | ||
| 1044 | static int cris_dma_check(ide_drive_t *drive) | 1032 | static int cris_dma_check(ide_drive_t *drive) |
| 1045 | { | 1033 | { |
| 1046 | if (ide_use_dma(drive) && cris_config_drive_for_dma(drive)) | 1034 | if (ide_tune_dma(drive)) |
| 1047 | return 0; | 1035 | return 0; |
| 1048 | 1036 | ||
| 1049 | return -1; | 1037 | return -1; |
diff --git a/drivers/ide/ide-dma.c b/drivers/ide/ide-dma.c index 5fe85191d49c..b77b7d138c49 100644 --- a/drivers/ide/ide-dma.c +++ b/drivers/ide/ide-dma.c | |||
| @@ -670,41 +670,6 @@ int __ide_dma_good_drive (ide_drive_t *drive) | |||
| 670 | 670 | ||
| 671 | EXPORT_SYMBOL(__ide_dma_good_drive); | 671 | EXPORT_SYMBOL(__ide_dma_good_drive); |
| 672 | 672 | ||
| 673 | int ide_use_dma(ide_drive_t *drive) | ||
| 674 | { | ||
| 675 | struct hd_driveid *id = drive->id; | ||
| 676 | ide_hwif_t *hwif = drive->hwif; | ||
| 677 | |||
| 678 | if ((id->capability & 1) == 0 || drive->autodma == 0) | ||
| 679 | return 0; | ||
| 680 | |||
| 681 | /* consult the list of known "bad" drives */ | ||
| 682 | if (__ide_dma_bad_drive(drive)) | ||
| 683 | return 0; | ||
| 684 | |||
| 685 | /* capable of UltraDMA modes */ | ||
| 686 | if (id->field_valid & 4) { | ||
| 687 | if (hwif->ultra_mask & id->dma_ultra) | ||
| 688 | return 1; | ||
| 689 | } | ||
| 690 | |||
| 691 | /* capable of regular DMA modes */ | ||
| 692 | if (id->field_valid & 2) { | ||
| 693 | if (hwif->mwdma_mask & id->dma_mword) | ||
| 694 | return 1; | ||
| 695 | if (hwif->swdma_mask & id->dma_1word) | ||
| 696 | return 1; | ||
| 697 | } | ||
| 698 | |||
| 699 | /* consult the list of known "good" drives */ | ||
| 700 | if (__ide_dma_good_drive(drive) && id->eide_dma_time < 150) | ||
| 701 | return 1; | ||
| 702 | |||
| 703 | return 0; | ||
| 704 | } | ||
| 705 | |||
| 706 | EXPORT_SYMBOL_GPL(ide_use_dma); | ||
| 707 | |||
| 708 | static const u8 xfer_mode_bases[] = { | 673 | static const u8 xfer_mode_bases[] = { |
| 709 | XFER_UDMA_0, | 674 | XFER_UDMA_0, |
| 710 | XFER_MW_DMA_0, | 675 | XFER_MW_DMA_0, |
| @@ -731,10 +696,12 @@ static unsigned int ide_get_mode_mask(ide_drive_t *drive, u8 base) | |||
| 731 | mask &= 0x07; | 696 | mask &= 0x07; |
| 732 | break; | 697 | break; |
| 733 | case XFER_MW_DMA_0: | 698 | case XFER_MW_DMA_0: |
| 734 | mask = id->dma_mword & hwif->mwdma_mask; | 699 | if (id->field_valid & 2) |
| 700 | mask = id->dma_mword & hwif->mwdma_mask; | ||
| 735 | break; | 701 | break; |
| 736 | case XFER_SW_DMA_0: | 702 | case XFER_SW_DMA_0: |
| 737 | mask = id->dma_1word & hwif->swdma_mask; | 703 | if (id->field_valid & 2) |
| 704 | mask = id->dma_1word & hwif->swdma_mask; | ||
| 738 | break; | 705 | break; |
| 739 | default: | 706 | default: |
| 740 | BUG(); | 707 | BUG(); |
| @@ -783,8 +750,11 @@ int ide_tune_dma(ide_drive_t *drive) | |||
| 783 | { | 750 | { |
| 784 | u8 speed; | 751 | u8 speed; |
| 785 | 752 | ||
| 786 | /* TODO: use only ide_max_dma_mode() */ | 753 | if ((drive->id->capability & 1) == 0 || drive->autodma == 0) |
| 787 | if (!ide_use_dma(drive)) | 754 | return 0; |
| 755 | |||
| 756 | /* consult the list of known "bad" drives */ | ||
| 757 | if (__ide_dma_bad_drive(drive)) | ||
| 788 | return 0; | 758 | return 0; |
| 789 | 759 | ||
| 790 | speed = ide_max_dma_mode(drive); | 760 | speed = ide_max_dma_mode(drive); |
| @@ -792,9 +762,10 @@ int ide_tune_dma(ide_drive_t *drive) | |||
| 792 | if (!speed) | 762 | if (!speed) |
| 793 | return 0; | 763 | return 0; |
| 794 | 764 | ||
| 795 | drive->hwif->speedproc(drive, speed); | 765 | if (drive->hwif->speedproc(drive, speed)) |
| 766 | return 0; | ||
| 796 | 767 | ||
| 797 | return ide_dma_enable(drive); | 768 | return 1; |
| 798 | } | 769 | } |
| 799 | 770 | ||
| 800 | EXPORT_SYMBOL_GPL(ide_tune_dma); | 771 | EXPORT_SYMBOL_GPL(ide_tune_dma); |
diff --git a/drivers/ide/ide-io.c b/drivers/ide/ide-io.c index 8e568143d90d..bfe8f1b712ba 100644 --- a/drivers/ide/ide-io.c +++ b/drivers/ide/ide-io.c | |||
| @@ -223,6 +223,7 @@ static ide_startstop_t ide_start_power_step(ide_drive_t *drive, struct request * | |||
| 223 | break; | 223 | break; |
| 224 | if (drive->hwif->ide_dma_check == NULL) | 224 | if (drive->hwif->ide_dma_check == NULL) |
| 225 | break; | 225 | break; |
| 226 | drive->hwif->dma_off_quietly(drive); | ||
| 226 | ide_set_dma(drive); | 227 | ide_set_dma(drive); |
| 227 | break; | 228 | break; |
| 228 | } | 229 | } |
diff --git a/drivers/ide/ide-lib.c b/drivers/ide/ide-lib.c index 3be3c69383f2..074bb32a4a40 100644 --- a/drivers/ide/ide-lib.c +++ b/drivers/ide/ide-lib.c | |||
| @@ -111,18 +111,6 @@ u8 ide_rate_filter(ide_drive_t *drive, u8 speed) | |||
| 111 | 111 | ||
| 112 | EXPORT_SYMBOL(ide_rate_filter); | 112 | EXPORT_SYMBOL(ide_rate_filter); |
| 113 | 113 | ||
| 114 | int ide_dma_enable (ide_drive_t *drive) | ||
| 115 | { | ||
| 116 | ide_hwif_t *hwif = HWIF(drive); | ||
| 117 | struct hd_driveid *id = drive->id; | ||
| 118 | |||
| 119 | return ((int) ((((id->dma_ultra >> 8) & hwif->ultra_mask) || | ||
| 120 | ((id->dma_mword >> 8) & hwif->mwdma_mask) || | ||
| 121 | ((id->dma_1word >> 8) & hwif->swdma_mask)) ? 1 : 0)); | ||
| 122 | } | ||
| 123 | |||
| 124 | EXPORT_SYMBOL(ide_dma_enable); | ||
| 125 | |||
| 126 | int ide_use_fast_pio(ide_drive_t *drive) | 114 | int ide_use_fast_pio(ide_drive_t *drive) |
| 127 | { | 115 | { |
| 128 | struct hd_driveid *id = drive->id; | 116 | struct hd_driveid *id = drive->id; |
diff --git a/drivers/ide/ide.c b/drivers/ide/ide.c index f2b547ff7722..6002713a20a1 100644 --- a/drivers/ide/ide.c +++ b/drivers/ide/ide.c | |||
| @@ -910,6 +910,7 @@ int set_using_dma(ide_drive_t *drive, int arg) | |||
| 910 | err = 0; | 910 | err = 0; |
| 911 | 911 | ||
| 912 | if (arg) { | 912 | if (arg) { |
| 913 | hwif->dma_off_quietly(drive); | ||
| 913 | if (ide_set_dma(drive) || hwif->ide_dma_on(drive)) | 914 | if (ide_set_dma(drive) || hwif->ide_dma_on(drive)) |
| 914 | err = -EIO; | 915 | err = -EIO; |
| 915 | } else | 916 | } else |
diff --git a/drivers/ide/pci/alim15x3.c b/drivers/ide/pci/alim15x3.c index 428efdae0c7b..27525ec2e19a 100644 --- a/drivers/ide/pci/alim15x3.c +++ b/drivers/ide/pci/alim15x3.c | |||
| @@ -455,28 +455,6 @@ static int ali15x3_tune_chipset (ide_drive_t *drive, u8 xferspeed) | |||
| 455 | return (ide_config_drive_speed(drive, speed)); | 455 | return (ide_config_drive_speed(drive, speed)); |
| 456 | } | 456 | } |
| 457 | 457 | ||
| 458 | |||
| 459 | /** | ||
| 460 | * config_chipset_for_dma - set up DMA mode | ||
| 461 | * @drive: drive to configure for | ||
| 462 | * | ||
| 463 | * Place a drive into DMA mode and tune the chipset for | ||
| 464 | * the selected speed. | ||
| 465 | * | ||
| 466 | * Returns true if DMA mode can be used | ||
| 467 | */ | ||
| 468 | |||
| 469 | static int config_chipset_for_dma (ide_drive_t *drive) | ||
| 470 | { | ||
| 471 | u8 speed = ide_max_dma_mode(drive); | ||
| 472 | |||
| 473 | if (!(speed)) | ||
| 474 | return 0; | ||
| 475 | |||
| 476 | (void) ali15x3_tune_chipset(drive, speed); | ||
| 477 | return ide_dma_enable(drive); | ||
| 478 | } | ||
| 479 | |||
| 480 | /** | 458 | /** |
| 481 | * ali15x3_config_drive_for_dma - configure for DMA | 459 | * ali15x3_config_drive_for_dma - configure for DMA |
| 482 | * @drive: drive to configure | 460 | * @drive: drive to configure |
| @@ -487,48 +465,14 @@ static int config_chipset_for_dma (ide_drive_t *drive) | |||
| 487 | 465 | ||
| 488 | static int ali15x3_config_drive_for_dma(ide_drive_t *drive) | 466 | static int ali15x3_config_drive_for_dma(ide_drive_t *drive) |
| 489 | { | 467 | { |
| 490 | ide_hwif_t *hwif = HWIF(drive); | ||
| 491 | struct hd_driveid *id = drive->id; | ||
| 492 | |||
| 493 | if ((m5229_revision<=0x20) && (drive->media!=ide_disk)) | ||
| 494 | goto ata_pio; | ||
| 495 | |||
| 496 | drive->init_speed = 0; | 468 | drive->init_speed = 0; |
| 497 | 469 | ||
| 498 | if ((id != NULL) && ((id->capability & 1) != 0) && drive->autodma) { | 470 | if (ide_tune_dma(drive)) |
| 499 | /* Consult the list of known "bad" drives */ | 471 | return 0; |
| 500 | if (__ide_dma_bad_drive(drive)) | ||
| 501 | goto ata_pio; | ||
| 502 | if ((id->field_valid & 4) && (m5229_revision >= 0xC2)) { | ||
| 503 | if (id->dma_ultra & hwif->ultra_mask) { | ||
| 504 | /* Force if Capable UltraDMA */ | ||
| 505 | int dma = config_chipset_for_dma(drive); | ||
| 506 | if ((id->field_valid & 2) && !dma) | ||
| 507 | goto try_dma_modes; | ||
| 508 | } | ||
| 509 | } else if (id->field_valid & 2) { | ||
| 510 | try_dma_modes: | ||
| 511 | if ((id->dma_mword & hwif->mwdma_mask) || | ||
| 512 | (id->dma_1word & hwif->swdma_mask)) { | ||
| 513 | /* Force if Capable regular DMA modes */ | ||
| 514 | if (!config_chipset_for_dma(drive)) | ||
| 515 | goto ata_pio; | ||
| 516 | } | ||
| 517 | } else if (__ide_dma_good_drive(drive) && | ||
| 518 | (id->eide_dma_time < 150)) { | ||
| 519 | /* Consult the list of known "good" drives */ | ||
| 520 | if (!config_chipset_for_dma(drive)) | ||
| 521 | goto ata_pio; | ||
| 522 | } else { | ||
| 523 | goto ata_pio; | ||
| 524 | } | ||
| 525 | } else { | ||
| 526 | ata_pio: | ||
| 527 | hwif->tuneproc(drive, 255); | ||
| 528 | return -1; | ||
| 529 | } | ||
| 530 | 472 | ||
| 531 | return 0; | 473 | ali15x3_tune_drive(drive, 255); |
| 474 | |||
| 475 | return -1; | ||
| 532 | } | 476 | } |
| 533 | 477 | ||
| 534 | /** | 478 | /** |
| @@ -739,7 +683,8 @@ static void __devinit init_hwif_common_ali15x3 (ide_hwif_t *hwif) | |||
| 739 | return; | 683 | return; |
| 740 | } | 684 | } |
| 741 | 685 | ||
| 742 | hwif->atapi_dma = 1; | 686 | if (m5229_revision > 0x20) |
| 687 | hwif->atapi_dma = 1; | ||
| 743 | 688 | ||
| 744 | if (m5229_revision <= 0x20) | 689 | if (m5229_revision <= 0x20) |
| 745 | hwif->ultra_mask = 0x00; /* no udma */ | 690 | hwif->ultra_mask = 0x00; /* no udma */ |
diff --git a/drivers/ide/pci/cmd64x.c b/drivers/ide/pci/cmd64x.c index 61ea96b5555c..7c57dc696f52 100644 --- a/drivers/ide/pci/cmd64x.c +++ b/drivers/ide/pci/cmd64x.c | |||
| @@ -352,22 +352,9 @@ static int cmd64x_tune_chipset (ide_drive_t *drive, u8 speed) | |||
| 352 | return ide_config_drive_speed(drive, speed); | 352 | return ide_config_drive_speed(drive, speed); |
| 353 | } | 353 | } |
| 354 | 354 | ||
| 355 | static int config_chipset_for_dma (ide_drive_t *drive) | ||
| 356 | { | ||
| 357 | u8 speed = ide_max_dma_mode(drive); | ||
| 358 | |||
| 359 | if (!speed) | ||
| 360 | return 0; | ||
| 361 | |||
| 362 | if (cmd64x_tune_chipset(drive, speed)) | ||
| 363 | return 0; | ||
| 364 | |||
| 365 | return ide_dma_enable(drive); | ||
| 366 | } | ||
| 367 | |||
| 368 | static int cmd64x_config_drive_for_dma (ide_drive_t *drive) | 355 | static int cmd64x_config_drive_for_dma (ide_drive_t *drive) |
| 369 | { | 356 | { |
| 370 | if (ide_use_dma(drive) && config_chipset_for_dma(drive)) | 357 | if (ide_tune_dma(drive)) |
| 371 | return 0; | 358 | return 0; |
| 372 | 359 | ||
| 373 | if (ide_use_fast_pio(drive)) | 360 | if (ide_use_fast_pio(drive)) |
diff --git a/drivers/ide/pci/cs5530.c b/drivers/ide/pci/cs5530.c index b2d7c132ef4b..1eec1f308d16 100644 --- a/drivers/ide/pci/cs5530.c +++ b/drivers/ide/pci/cs5530.c | |||
| @@ -1,10 +1,10 @@ | |||
| 1 | /* | 1 | /* |
| 2 | * linux/drivers/ide/pci/cs5530.c Version 0.7 Sept 10, 2002 | 2 | * linux/drivers/ide/pci/cs5530.c Version 0.73 Mar 10 2007 |
| 3 | * | 3 | * |
| 4 | * Copyright (C) 2000 Andre Hedrick <andre@linux-ide.org> | 4 | * Copyright (C) 2000 Andre Hedrick <andre@linux-ide.org> |
| 5 | * Ditto of GNU General Public License. | ||
| 6 | * | ||
| 7 | * Copyright (C) 2000 Mark Lord <mlord@pobox.com> | 5 | * Copyright (C) 2000 Mark Lord <mlord@pobox.com> |
| 6 | * Copyright (C) 2007 Bartlomiej Zolnierkiewicz | ||
| 7 | * | ||
| 8 | * May be copied or modified under the terms of the GNU General Public License | 8 | * May be copied or modified under the terms of the GNU General Public License |
| 9 | * | 9 | * |
| 10 | * Development of this chipset driver was funded | 10 | * Development of this chipset driver was funded |
| @@ -62,6 +62,14 @@ static unsigned int cs5530_pio_timings[2][5] = { | |||
| 62 | #define CS5530_BAD_PIO(timings) (((timings)&~0x80000000)==0x0000e132) | 62 | #define CS5530_BAD_PIO(timings) (((timings)&~0x80000000)==0x0000e132) |
| 63 | #define CS5530_BASEREG(hwif) (((hwif)->dma_base & ~0xf) + ((hwif)->channel ? 0x30 : 0x20)) | 63 | #define CS5530_BASEREG(hwif) (((hwif)->dma_base & ~0xf) + ((hwif)->channel ? 0x30 : 0x20)) |
| 64 | 64 | ||
| 65 | static void cs5530_tunepio(ide_drive_t *drive, u8 pio) | ||
| 66 | { | ||
| 67 | unsigned long basereg = CS5530_BASEREG(drive->hwif); | ||
| 68 | unsigned int format = (inl(basereg + 4) >> 31) & 1; | ||
| 69 | |||
| 70 | outl(cs5530_pio_timings[format][pio], basereg + ((drive->dn & 1)<<3)); | ||
| 71 | } | ||
| 72 | |||
| 65 | /** | 73 | /** |
| 66 | * cs5530_tuneproc - select/set PIO modes | 74 | * cs5530_tuneproc - select/set PIO modes |
| 67 | * | 75 | * |
| @@ -74,98 +82,78 @@ static unsigned int cs5530_pio_timings[2][5] = { | |||
| 74 | 82 | ||
| 75 | static void cs5530_tuneproc (ide_drive_t *drive, u8 pio) /* pio=255 means "autotune" */ | 83 | static void cs5530_tuneproc (ide_drive_t *drive, u8 pio) /* pio=255 means "autotune" */ |
| 76 | { | 84 | { |
| 77 | ide_hwif_t *hwif = HWIF(drive); | ||
| 78 | unsigned int format; | ||
| 79 | unsigned long basereg = CS5530_BASEREG(hwif); | ||
| 80 | static u8 modes[5] = { XFER_PIO_0, XFER_PIO_1, XFER_PIO_2, XFER_PIO_3, XFER_PIO_4}; | ||
| 81 | |||
| 82 | pio = ide_get_best_pio_mode(drive, pio, 4, NULL); | 85 | pio = ide_get_best_pio_mode(drive, pio, 4, NULL); |
| 83 | if (!cs5530_set_xfer_mode(drive, modes[pio])) { | 86 | |
| 84 | format = (inl(basereg + 4) >> 31) & 1; | 87 | if (cs5530_set_xfer_mode(drive, XFER_PIO_0 + pio) == 0) |
| 85 | outl(cs5530_pio_timings[format][pio], | 88 | cs5530_tunepio(drive, pio); |
| 86 | basereg+(drive->select.b.unit<<3)); | 89 | } |
| 90 | |||
| 91 | /** | ||
| 92 | * cs5530_udma_filter - UDMA filter | ||
| 93 | * @drive: drive | ||
| 94 | * | ||
| 95 | * cs5530_udma_filter() does UDMA mask filtering for the given drive | ||
| 96 | * taking into the consideration capabilities of the mate device. | ||
| 97 | * | ||
| 98 | * The CS5530 specifies that two drives sharing a cable cannot mix | ||
| 99 | * UDMA/MDMA. It has to be one or the other, for the pair, though | ||
| 100 | * different timings can still be chosen for each drive. We could | ||
| 101 | * set the appropriate timing bits on the fly, but that might be | ||
| 102 | * a bit confusing. So, for now we statically handle this requirement | ||
| 103 | * by looking at our mate drive to see what it is capable of, before | ||
| 104 | * choosing a mode for our own drive. | ||
| 105 | * | ||
| 106 | * Note: This relies on the fact we never fail from UDMA to MWDMA2 | ||
| 107 | * but instead drop to PIO. | ||
| 108 | */ | ||
| 109 | |||
| 110 | static u8 cs5530_udma_filter(ide_drive_t *drive) | ||
| 111 | { | ||
| 112 | ide_hwif_t *hwif = drive->hwif; | ||
| 113 | ide_drive_t *mate = &hwif->drives[(drive->dn & 1) ^ 1]; | ||
| 114 | struct hd_driveid *mateid = mate->id; | ||
| 115 | u8 mask = hwif->ultra_mask; | ||
| 116 | |||
| 117 | if (mate->present == 0) | ||
| 118 | goto out; | ||
| 119 | |||
| 120 | if ((mateid->capability & 1) && __ide_dma_bad_drive(mate) == 0) { | ||
| 121 | if ((mateid->field_valid & 4) && (mateid->dma_ultra & 7)) | ||
| 122 | goto out; | ||
| 123 | if ((mateid->field_valid & 2) && (mateid->dma_mword & 7)) | ||
| 124 | mask = 0; | ||
| 87 | } | 125 | } |
| 126 | out: | ||
| 127 | return mask; | ||
| 88 | } | 128 | } |
| 89 | 129 | ||
| 90 | /** | 130 | /** |
| 91 | * cs5530_config_dma - select/set DMA and UDMA modes | 131 | * cs5530_config_dma - set DMA/UDMA mode |
| 92 | * @drive: drive to tune | 132 | * @drive: drive to tune |
| 93 | * | 133 | * |
| 94 | * cs5530_config_dma() handles selection/setting of DMA/UDMA modes | 134 | * cs5530_config_dma() handles setting of DMA/UDMA mode |
| 95 | * for both the chipset and drive. The CS5530 has limitations about | 135 | * for both the chipset and drive. |
| 96 | * mixing DMA/UDMA on the same cable. | ||
| 97 | */ | 136 | */ |
| 98 | 137 | ||
| 99 | static int cs5530_config_dma (ide_drive_t *drive) | 138 | static int cs5530_config_dma(ide_drive_t *drive) |
| 100 | { | 139 | { |
| 101 | int udma_ok = 1, mode = 0; | 140 | if (ide_tune_dma(drive)) |
| 102 | ide_hwif_t *hwif = HWIF(drive); | 141 | return 0; |
| 103 | int unit = drive->select.b.unit; | ||
| 104 | ide_drive_t *mate = &hwif->drives[unit^1]; | ||
| 105 | struct hd_driveid *id = drive->id; | ||
| 106 | unsigned int reg, timings = 0; | ||
| 107 | unsigned long basereg; | ||
| 108 | 142 | ||
| 109 | /* | 143 | return 1; |
| 110 | * Default to DMA-off in case we run into trouble here. | 144 | } |
| 111 | */ | ||
| 112 | hwif->dma_off_quietly(drive); | ||
| 113 | 145 | ||
| 114 | /* | 146 | static int cs5530_tune_chipset(ide_drive_t *drive, u8 mode) |
| 115 | * The CS5530 specifies that two drives sharing a cable cannot | 147 | { |
| 116 | * mix UDMA/MDMA. It has to be one or the other, for the pair, | 148 | unsigned long basereg; |
| 117 | * though different timings can still be chosen for each drive. | 149 | unsigned int reg, timings = 0; |
| 118 | * We could set the appropriate timing bits on the fly, | ||
| 119 | * but that might be a bit confusing. So, for now we statically | ||
| 120 | * handle this requirement by looking at our mate drive to see | ||
| 121 | * what it is capable of, before choosing a mode for our own drive. | ||
| 122 | * | ||
| 123 | * Note: This relies on the fact we never fail from UDMA to MWDMA_2 | ||
| 124 | * but instead drop to PIO | ||
| 125 | */ | ||
| 126 | if (mate->present) { | ||
| 127 | struct hd_driveid *mateid = mate->id; | ||
| 128 | if (mateid && (mateid->capability & 1) && | ||
| 129 | !__ide_dma_bad_drive(mate)) { | ||
| 130 | if ((mateid->field_valid & 4) && | ||
| 131 | (mateid->dma_ultra & 7)) | ||
| 132 | udma_ok = 1; | ||
| 133 | else if ((mateid->field_valid & 2) && | ||
| 134 | (mateid->dma_mword & 7)) | ||
| 135 | udma_ok = 0; | ||
| 136 | else | ||
| 137 | udma_ok = 1; | ||
| 138 | } | ||
| 139 | } | ||
| 140 | 150 | ||
| 141 | /* | 151 | mode = ide_rate_filter(drive, mode); |
| 142 | * Now see what the current drive is capable of, | ||
| 143 | * selecting UDMA only if the mate said it was ok. | ||
| 144 | */ | ||
| 145 | if (id && (id->capability & 1) && drive->autodma && | ||
| 146 | !__ide_dma_bad_drive(drive)) { | ||
| 147 | if (udma_ok && (id->field_valid & 4) && (id->dma_ultra & 7)) { | ||
| 148 | if (id->dma_ultra & 4) | ||
| 149 | mode = XFER_UDMA_2; | ||
| 150 | else if (id->dma_ultra & 2) | ||
| 151 | mode = XFER_UDMA_1; | ||
| 152 | else if (id->dma_ultra & 1) | ||
| 153 | mode = XFER_UDMA_0; | ||
| 154 | } | ||
| 155 | if (!mode && (id->field_valid & 2) && (id->dma_mword & 7)) { | ||
| 156 | if (id->dma_mword & 4) | ||
| 157 | mode = XFER_MW_DMA_2; | ||
| 158 | else if (id->dma_mword & 2) | ||
| 159 | mode = XFER_MW_DMA_1; | ||
| 160 | else if (id->dma_mword & 1) | ||
| 161 | mode = XFER_MW_DMA_0; | ||
| 162 | } | ||
| 163 | } | ||
| 164 | 152 | ||
| 165 | /* | 153 | /* |
| 166 | * Tell the drive to switch to the new mode; abort on failure. | 154 | * Tell the drive to switch to the new mode; abort on failure. |
| 167 | */ | 155 | */ |
| 168 | if (!mode || cs5530_set_xfer_mode(drive, mode)) | 156 | if (cs5530_set_xfer_mode(drive, mode)) |
| 169 | return 1; /* failure */ | 157 | return 1; /* failure */ |
| 170 | 158 | ||
| 171 | /* | 159 | /* |
| @@ -178,14 +166,21 @@ static int cs5530_config_dma (ide_drive_t *drive) | |||
| 178 | case XFER_MW_DMA_0: timings = 0x00077771; break; | 166 | case XFER_MW_DMA_0: timings = 0x00077771; break; |
| 179 | case XFER_MW_DMA_1: timings = 0x00012121; break; | 167 | case XFER_MW_DMA_1: timings = 0x00012121; break; |
| 180 | case XFER_MW_DMA_2: timings = 0x00002020; break; | 168 | case XFER_MW_DMA_2: timings = 0x00002020; break; |
| 169 | case XFER_PIO_4: | ||
| 170 | case XFER_PIO_3: | ||
| 171 | case XFER_PIO_2: | ||
| 172 | case XFER_PIO_1: | ||
| 173 | case XFER_PIO_0: | ||
| 174 | cs5530_tunepio(drive, mode - XFER_PIO_0); | ||
| 175 | return 0; | ||
| 181 | default: | 176 | default: |
| 182 | BUG(); | 177 | BUG(); |
| 183 | break; | 178 | break; |
| 184 | } | 179 | } |
| 185 | basereg = CS5530_BASEREG(hwif); | 180 | basereg = CS5530_BASEREG(drive->hwif); |
| 186 | reg = inl(basereg + 4); /* get drive0 config register */ | 181 | reg = inl(basereg + 4); /* get drive0 config register */ |
| 187 | timings |= reg & 0x80000000; /* preserve PIO format bit */ | 182 | timings |= reg & 0x80000000; /* preserve PIO format bit */ |
| 188 | if (unit == 0) { /* are we configuring drive0? */ | 183 | if ((drive-> dn & 1) == 0) { /* are we configuring drive0? */ |
| 189 | outl(timings, basereg + 4); /* write drive0 config register */ | 184 | outl(timings, basereg + 4); /* write drive0 config register */ |
| 190 | } else { | 185 | } else { |
| 191 | if (timings & 0x00100000) | 186 | if (timings & 0x00100000) |
| @@ -311,6 +306,8 @@ static void __devinit init_hwif_cs5530 (ide_hwif_t *hwif) | |||
| 311 | hwif->serialized = hwif->mate->serialized = 1; | 306 | hwif->serialized = hwif->mate->serialized = 1; |
| 312 | 307 | ||
| 313 | hwif->tuneproc = &cs5530_tuneproc; | 308 | hwif->tuneproc = &cs5530_tuneproc; |
| 309 | hwif->speedproc = &cs5530_tune_chipset; | ||
| 310 | |||
| 314 | basereg = CS5530_BASEREG(hwif); | 311 | basereg = CS5530_BASEREG(hwif); |
| 315 | d0_timings = inl(basereg + 0); | 312 | d0_timings = inl(basereg + 0); |
| 316 | if (CS5530_BAD_PIO(d0_timings)) { | 313 | if (CS5530_BAD_PIO(d0_timings)) { |
| @@ -332,6 +329,7 @@ static void __devinit init_hwif_cs5530 (ide_hwif_t *hwif) | |||
| 332 | hwif->ultra_mask = 0x07; | 329 | hwif->ultra_mask = 0x07; |
| 333 | hwif->mwdma_mask = 0x07; | 330 | hwif->mwdma_mask = 0x07; |
| 334 | 331 | ||
| 332 | hwif->udma_filter = cs5530_udma_filter; | ||
| 335 | hwif->ide_dma_check = &cs5530_config_dma; | 333 | hwif->ide_dma_check = &cs5530_config_dma; |
| 336 | if (!noautodma) | 334 | if (!noautodma) |
| 337 | hwif->autodma = 1; | 335 | hwif->autodma = 1; |
diff --git a/drivers/ide/pci/it821x.c b/drivers/ide/pci/it821x.c index 442f658c6ae7..5faaff87d580 100644 --- a/drivers/ide/pci/it821x.c +++ b/drivers/ide/pci/it821x.c | |||
| @@ -464,25 +464,6 @@ static int it821x_tune_chipset (ide_drive_t *drive, byte xferspeed) | |||
| 464 | } | 464 | } |
| 465 | 465 | ||
| 466 | /** | 466 | /** |
| 467 | * config_chipset_for_dma - configure for DMA | ||
| 468 | * @drive: drive to configure | ||
| 469 | * | ||
| 470 | * Called by the IDE layer when it wants the timings set up. | ||
| 471 | */ | ||
| 472 | |||
| 473 | static int config_chipset_for_dma (ide_drive_t *drive) | ||
| 474 | { | ||
| 475 | u8 speed = ide_max_dma_mode(drive); | ||
| 476 | |||
| 477 | if (speed == 0) | ||
| 478 | return 0; | ||
| 479 | |||
| 480 | it821x_tune_chipset(drive, speed); | ||
| 481 | |||
| 482 | return ide_dma_enable(drive); | ||
| 483 | } | ||
| 484 | |||
| 485 | /** | ||
| 486 | * it821x_configure_drive_for_dma - set up for DMA transfers | 467 | * it821x_configure_drive_for_dma - set up for DMA transfers |
| 487 | * @drive: drive we are going to set up | 468 | * @drive: drive we are going to set up |
| 488 | * | 469 | * |
| @@ -494,7 +475,7 @@ static int config_chipset_for_dma (ide_drive_t *drive) | |||
| 494 | 475 | ||
| 495 | static int it821x_config_drive_for_dma (ide_drive_t *drive) | 476 | static int it821x_config_drive_for_dma (ide_drive_t *drive) |
| 496 | { | 477 | { |
| 497 | if (ide_use_dma(drive) && config_chipset_for_dma(drive)) | 478 | if (ide_tune_dma(drive)) |
| 498 | return 0; | 479 | return 0; |
| 499 | 480 | ||
| 500 | it821x_tuneproc(drive, 255); | 481 | it821x_tuneproc(drive, 255); |
diff --git a/drivers/ide/pci/pdc202xx_new.c b/drivers/ide/pci/pdc202xx_new.c index 65b1e124edf7..cc0bfdcf1f19 100644 --- a/drivers/ide/pci/pdc202xx_new.c +++ b/drivers/ide/pci/pdc202xx_new.c | |||
| @@ -228,38 +228,11 @@ static u8 pdcnew_cable_detect(ide_hwif_t *hwif) | |||
| 228 | return get_indexed_reg(hwif, 0x0b) & 0x04; | 228 | return get_indexed_reg(hwif, 0x0b) & 0x04; |
| 229 | } | 229 | } |
| 230 | 230 | ||
| 231 | static int config_chipset_for_dma(ide_drive_t *drive) | ||
| 232 | { | ||
| 233 | struct hd_driveid *id = drive->id; | ||
| 234 | ide_hwif_t *hwif = HWIF(drive); | ||
| 235 | u8 speed; | ||
| 236 | |||
| 237 | if (id->capability & 4) { | ||
| 238 | /* | ||
| 239 | * Set IORDY_EN & PREFETCH_EN (this seems to have | ||
| 240 | * NO real effect since this register is reloaded | ||
| 241 | * by hardware when the transfer mode is selected) | ||
| 242 | */ | ||
| 243 | u8 tmp, adj = (drive->dn & 1) ? 0x08 : 0x00; | ||
| 244 | |||
| 245 | tmp = get_indexed_reg(hwif, 0x13 + adj); | ||
| 246 | set_indexed_reg(hwif, 0x13 + adj, tmp | 0x03); | ||
| 247 | } | ||
| 248 | |||
| 249 | speed = ide_max_dma_mode(drive); | ||
| 250 | |||
| 251 | if (!speed) | ||
| 252 | return 0; | ||
| 253 | |||
| 254 | (void) hwif->speedproc(drive, speed); | ||
| 255 | return ide_dma_enable(drive); | ||
| 256 | } | ||
| 257 | |||
| 258 | static int pdcnew_config_drive_xfer_rate(ide_drive_t *drive) | 231 | static int pdcnew_config_drive_xfer_rate(ide_drive_t *drive) |
| 259 | { | 232 | { |
| 260 | drive->init_speed = 0; | 233 | drive->init_speed = 0; |
| 261 | 234 | ||
| 262 | if (ide_use_dma(drive) && config_chipset_for_dma(drive)) | 235 | if (ide_tune_dma(drive)) |
| 263 | return 0; | 236 | return 0; |
| 264 | 237 | ||
| 265 | if (ide_use_fast_pio(drive)) | 238 | if (ide_use_fast_pio(drive)) |
diff --git a/drivers/ide/pci/pdc202xx_old.c b/drivers/ide/pci/pdc202xx_old.c index 7146fe3f6ba7..23844687deea 100644 --- a/drivers/ide/pci/pdc202xx_old.c +++ b/drivers/ide/pci/pdc202xx_old.c | |||
| @@ -1,8 +1,9 @@ | |||
| 1 | /* | 1 | /* |
| 2 | * linux/drivers/ide/pci/pdc202xx_old.c Version 0.36 Sept 11, 2002 | 2 | * linux/drivers/ide/pci/pdc202xx_old.c Version 0.50 Mar 3, 2007 |
| 3 | * | 3 | * |
| 4 | * Copyright (C) 1998-2002 Andre Hedrick <andre@linux-ide.org> | 4 | * Copyright (C) 1998-2002 Andre Hedrick <andre@linux-ide.org> |
| 5 | * Copyright (C) 2006-2007 MontaVista Software, Inc. | 5 | * Copyright (C) 2006-2007 MontaVista Software, Inc. |
| 6 | * Copyright (C) 2007 Bartlomiej Zolnierkiewicz | ||
| 6 | * | 7 | * |
| 7 | * Promise Ultra33 cards with BIOS v1.20 through 1.28 will need this | 8 | * Promise Ultra33 cards with BIOS v1.20 through 1.28 will need this |
| 8 | * compiled into the kernel if you have more than one card installed. | 9 | * compiled into the kernel if you have more than one card installed. |
| @@ -60,45 +61,7 @@ static const char *pdc_quirk_drives[] = { | |||
| 60 | NULL | 61 | NULL |
| 61 | }; | 62 | }; |
| 62 | 63 | ||
| 63 | /* A Register */ | 64 | static void pdc_old_disable_66MHz_clock(ide_hwif_t *); |
| 64 | #define SYNC_ERRDY_EN 0xC0 | ||
| 65 | |||
| 66 | #define SYNC_IN 0x80 /* control bit, different for master vs. slave drives */ | ||
| 67 | #define ERRDY_EN 0x40 /* control bit, different for master vs. slave drives */ | ||
| 68 | #define IORDY_EN 0x20 /* PIO: IOREADY */ | ||
| 69 | #define PREFETCH_EN 0x10 /* PIO: PREFETCH */ | ||
| 70 | |||
| 71 | #define PA3 0x08 /* PIO"A" timing */ | ||
| 72 | #define PA2 0x04 /* PIO"A" timing */ | ||
| 73 | #define PA1 0x02 /* PIO"A" timing */ | ||
| 74 | #define PA0 0x01 /* PIO"A" timing */ | ||
| 75 | |||
| 76 | /* B Register */ | ||
| 77 | |||
| 78 | #define MB2 0x80 /* DMA"B" timing */ | ||
| 79 | #define MB1 0x40 /* DMA"B" timing */ | ||
| 80 | #define MB0 0x20 /* DMA"B" timing */ | ||
| 81 | |||
| 82 | #define PB4 0x10 /* PIO_FORCE 1:0 */ | ||
| 83 | |||
| 84 | #define PB3 0x08 /* PIO"B" timing */ /* PIO flow Control mode */ | ||
| 85 | #define PB2 0x04 /* PIO"B" timing */ /* PIO 4 */ | ||
| 86 | #define PB1 0x02 /* PIO"B" timing */ /* PIO 3 half */ | ||
| 87 | #define PB0 0x01 /* PIO"B" timing */ /* PIO 3 other half */ | ||
| 88 | |||
| 89 | /* C Register */ | ||
| 90 | #define IORDYp_NO_SPEED 0x4F | ||
| 91 | #define SPEED_DIS 0x0F | ||
| 92 | |||
| 93 | #define DMARQp 0x80 | ||
| 94 | #define IORDYp 0x40 | ||
| 95 | #define DMAR_EN 0x20 | ||
| 96 | #define DMAW_EN 0x10 | ||
| 97 | |||
| 98 | #define MC3 0x08 /* DMA"C" timing */ | ||
| 99 | #define MC2 0x04 /* DMA"C" timing */ | ||
| 100 | #define MC1 0x02 /* DMA"C" timing */ | ||
| 101 | #define MC0 0x01 /* DMA"C" timing */ | ||
| 102 | 65 | ||
| 103 | static int pdc202xx_tune_chipset (ide_drive_t *drive, u8 xferspeed) | 66 | static int pdc202xx_tune_chipset (ide_drive_t *drive, u8 xferspeed) |
| 104 | { | 67 | { |
| @@ -107,52 +70,25 @@ static int pdc202xx_tune_chipset (ide_drive_t *drive, u8 xferspeed) | |||
| 107 | u8 drive_pci = 0x60 + (drive->dn << 2); | 70 | u8 drive_pci = 0x60 + (drive->dn << 2); |
| 108 | u8 speed = ide_rate_filter(drive, xferspeed); | 71 | u8 speed = ide_rate_filter(drive, xferspeed); |
| 109 | 72 | ||
| 110 | u32 drive_conf; | 73 | u8 AP = 0, BP = 0, CP = 0; |
| 111 | u8 AP, BP, CP, DP; | ||
| 112 | u8 TA = 0, TB = 0, TC = 0; | 74 | u8 TA = 0, TB = 0, TC = 0; |
| 113 | 75 | ||
| 114 | if (drive->media != ide_disk && | 76 | #if PDC202XX_DEBUG_DRIVE_INFO |
| 115 | drive->media != ide_cdrom && speed < XFER_SW_DMA_0) | 77 | u32 drive_conf = 0; |
| 116 | return -1; | ||
| 117 | |||
| 118 | pci_read_config_dword(dev, drive_pci, &drive_conf); | 78 | pci_read_config_dword(dev, drive_pci, &drive_conf); |
| 119 | pci_read_config_byte(dev, (drive_pci), &AP); | 79 | #endif |
| 120 | pci_read_config_byte(dev, (drive_pci)|0x01, &BP); | ||
| 121 | pci_read_config_byte(dev, (drive_pci)|0x02, &CP); | ||
| 122 | pci_read_config_byte(dev, (drive_pci)|0x03, &DP); | ||
| 123 | 80 | ||
| 124 | if (speed < XFER_SW_DMA_0) { | 81 | /* |
| 125 | if ((AP & 0x0F) || (BP & 0x07)) { | 82 | * TODO: do this once per channel |
| 126 | /* clear PIO modes of lower 8421 bits of A Register */ | 83 | */ |
| 127 | pci_write_config_byte(dev, (drive_pci), AP &~0x0F); | 84 | if (dev->device != PCI_DEVICE_ID_PROMISE_20246) |
| 128 | pci_read_config_byte(dev, (drive_pci), &AP); | 85 | pdc_old_disable_66MHz_clock(hwif); |
| 129 | |||
| 130 | /* clear PIO modes of lower 421 bits of B Register */ | ||
| 131 | pci_write_config_byte(dev, (drive_pci)|0x01, BP &~0x07); | ||
| 132 | pci_read_config_byte(dev, (drive_pci)|0x01, &BP); | ||
| 133 | |||
| 134 | pci_read_config_byte(dev, (drive_pci), &AP); | ||
| 135 | pci_read_config_byte(dev, (drive_pci)|0x01, &BP); | ||
| 136 | } | ||
| 137 | } else { | ||
| 138 | if ((BP & 0xF0) && (CP & 0x0F)) { | ||
| 139 | /* clear DMA modes of upper 842 bits of B Register */ | ||
| 140 | /* clear PIO forced mode upper 1 bit of B Register */ | ||
| 141 | pci_write_config_byte(dev, (drive_pci)|0x01, BP &~0xF0); | ||
| 142 | pci_read_config_byte(dev, (drive_pci)|0x01, &BP); | ||
| 143 | |||
| 144 | /* clear DMA modes of lower 8421 bits of C Register */ | ||
| 145 | pci_write_config_byte(dev, (drive_pci)|0x02, CP &~0x0F); | ||
| 146 | pci_read_config_byte(dev, (drive_pci)|0x02, &CP); | ||
| 147 | } | ||
| 148 | } | ||
| 149 | 86 | ||
| 150 | pci_read_config_byte(dev, (drive_pci), &AP); | 87 | pci_read_config_byte(dev, drive_pci, &AP); |
| 151 | pci_read_config_byte(dev, (drive_pci)|0x01, &BP); | 88 | pci_read_config_byte(dev, drive_pci + 1, &BP); |
| 152 | pci_read_config_byte(dev, (drive_pci)|0x02, &CP); | 89 | pci_read_config_byte(dev, drive_pci + 2, &CP); |
| 153 | 90 | ||
| 154 | switch(speed) { | 91 | switch(speed) { |
| 155 | case XFER_UDMA_6: speed = XFER_UDMA_5; | ||
| 156 | case XFER_UDMA_5: | 92 | case XFER_UDMA_5: |
| 157 | case XFER_UDMA_4: TB = 0x20; TC = 0x01; break; | 93 | case XFER_UDMA_4: TB = 0x20; TC = 0x01; break; |
| 158 | case XFER_UDMA_2: TB = 0x20; TC = 0x01; break; | 94 | case XFER_UDMA_2: TB = 0x20; TC = 0x01; break; |
| @@ -161,7 +97,7 @@ static int pdc202xx_tune_chipset (ide_drive_t *drive, u8 xferspeed) | |||
| 161 | case XFER_UDMA_0: | 97 | case XFER_UDMA_0: |
| 162 | case XFER_MW_DMA_2: TB = 0x60; TC = 0x03; break; | 98 | case XFER_MW_DMA_2: TB = 0x60; TC = 0x03; break; |
| 163 | case XFER_MW_DMA_1: TB = 0x60; TC = 0x04; break; | 99 | case XFER_MW_DMA_1: TB = 0x60; TC = 0x04; break; |
| 164 | case XFER_MW_DMA_0: | 100 | case XFER_MW_DMA_0: TB = 0xE0; TC = 0x0F; break; |
| 165 | case XFER_SW_DMA_2: TB = 0x60; TC = 0x05; break; | 101 | case XFER_SW_DMA_2: TB = 0x60; TC = 0x05; break; |
| 166 | case XFER_SW_DMA_1: TB = 0x80; TC = 0x06; break; | 102 | case XFER_SW_DMA_1: TB = 0x80; TC = 0x06; break; |
| 167 | case XFER_SW_DMA_0: TB = 0xC0; TC = 0x0B; break; | 103 | case XFER_SW_DMA_0: TB = 0xC0; TC = 0x0B; break; |
| @@ -174,25 +110,39 @@ static int pdc202xx_tune_chipset (ide_drive_t *drive, u8 xferspeed) | |||
| 174 | } | 110 | } |
| 175 | 111 | ||
| 176 | if (speed < XFER_SW_DMA_0) { | 112 | if (speed < XFER_SW_DMA_0) { |
| 177 | pci_write_config_byte(dev, (drive_pci), AP|TA); | 113 | /* |
| 178 | pci_write_config_byte(dev, (drive_pci)|0x01, BP|TB); | 114 | * preserve SYNC_INT / ERDDY_EN bits while clearing |
| 115 | * Prefetch_EN / IORDY_EN / PA[3:0] bits of register A | ||
| 116 | */ | ||
| 117 | AP &= ~0x3f; | ||
| 118 | if (drive->id->capability & 4) | ||
| 119 | AP |= 0x20; /* set IORDY_EN bit */ | ||
| 120 | if (drive->media == ide_disk) | ||
| 121 | AP |= 0x10; /* set Prefetch_EN bit */ | ||
| 122 | /* clear PB[4:0] bits of register B */ | ||
| 123 | BP &= ~0x1f; | ||
| 124 | pci_write_config_byte(dev, drive_pci, AP | TA); | ||
| 125 | pci_write_config_byte(dev, drive_pci + 1, BP | TB); | ||
| 179 | } else { | 126 | } else { |
| 180 | pci_write_config_byte(dev, (drive_pci)|0x01, BP|TB); | 127 | /* clear MB[2:0] bits of register B */ |
| 181 | pci_write_config_byte(dev, (drive_pci)|0x02, CP|TC); | 128 | BP &= ~0xe0; |
| 129 | /* clear MC[3:0] bits of register C */ | ||
| 130 | CP &= ~0x0f; | ||
| 131 | pci_write_config_byte(dev, drive_pci + 1, BP | TB); | ||
| 132 | pci_write_config_byte(dev, drive_pci + 2, CP | TC); | ||
| 182 | } | 133 | } |
| 183 | 134 | ||
| 184 | #if PDC202XX_DEBUG_DRIVE_INFO | 135 | #if PDC202XX_DEBUG_DRIVE_INFO |
| 185 | printk(KERN_DEBUG "%s: %s drive%d 0x%08x ", | 136 | printk(KERN_DEBUG "%s: %s drive%d 0x%08x ", |
| 186 | drive->name, ide_xfer_verbose(speed), | 137 | drive->name, ide_xfer_verbose(speed), |
| 187 | drive->dn, drive_conf); | 138 | drive->dn, drive_conf); |
| 188 | pci_read_config_dword(dev, drive_pci, &drive_conf); | 139 | pci_read_config_dword(dev, drive_pci, &drive_conf); |
| 189 | printk("0x%08x\n", drive_conf); | 140 | printk("0x%08x\n", drive_conf); |
| 190 | #endif /* PDC202XX_DEBUG_DRIVE_INFO */ | 141 | #endif |
| 191 | 142 | ||
| 192 | return (ide_config_drive_speed(drive, speed)); | 143 | return ide_config_drive_speed(drive, speed); |
| 193 | } | 144 | } |
| 194 | 145 | ||
| 195 | |||
| 196 | static void pdc202xx_tune_drive(ide_drive_t *drive, u8 pio) | 146 | static void pdc202xx_tune_drive(ide_drive_t *drive, u8 pio) |
| 197 | { | 147 | { |
| 198 | pio = ide_get_best_pio_mode(drive, pio, 4, NULL); | 148 | pio = ide_get_best_pio_mode(drive, pio, 4, NULL); |
| @@ -210,6 +160,8 @@ static u8 pdc202xx_old_cable_detect (ide_hwif_t *hwif) | |||
| 210 | * Set the control register to use the 66MHz system | 160 | * Set the control register to use the 66MHz system |
| 211 | * clock for UDMA 3/4/5 mode operation when necessary. | 161 | * clock for UDMA 3/4/5 mode operation when necessary. |
| 212 | * | 162 | * |
| 163 | * FIXME: this register is shared by both channels, some locking is needed | ||
| 164 | * | ||
| 213 | * It may also be possible to leave the 66MHz clock on | 165 | * It may also be possible to leave the 66MHz clock on |
| 214 | * and readjust the timing parameters. | 166 | * and readjust the timing parameters. |
| 215 | */ | 167 | */ |
| @@ -229,65 +181,11 @@ static void pdc_old_disable_66MHz_clock(ide_hwif_t *hwif) | |||
| 229 | outb(clock & ~(hwif->channel ? 0x08 : 0x02), clock_reg); | 181 | outb(clock & ~(hwif->channel ? 0x08 : 0x02), clock_reg); |
| 230 | } | 182 | } |
| 231 | 183 | ||
| 232 | static int config_chipset_for_dma (ide_drive_t *drive) | ||
| 233 | { | ||
| 234 | struct hd_driveid *id = drive->id; | ||
| 235 | ide_hwif_t *hwif = HWIF(drive); | ||
| 236 | struct pci_dev *dev = hwif->pci_dev; | ||
| 237 | u32 drive_conf = 0; | ||
| 238 | u8 drive_pci = 0x60 + (drive->dn << 2); | ||
| 239 | u8 test1 = 0, test2 = 0, speed = -1; | ||
| 240 | u8 AP = 0; | ||
| 241 | |||
| 242 | if (dev->device != PCI_DEVICE_ID_PROMISE_20246) | ||
| 243 | pdc_old_disable_66MHz_clock(drive->hwif); | ||
| 244 | |||
| 245 | drive_pci = 0x60 + (drive->dn << 2); | ||
| 246 | pci_read_config_dword(dev, drive_pci, &drive_conf); | ||
| 247 | if ((drive_conf != 0x004ff304) && (drive_conf != 0x004ff3c4)) | ||
| 248 | goto chipset_is_set; | ||
| 249 | |||
| 250 | pci_read_config_byte(dev, drive_pci, &test1); | ||
| 251 | if (!(test1 & SYNC_ERRDY_EN)) { | ||
| 252 | if (drive->select.b.unit & 0x01) { | ||
| 253 | pci_read_config_byte(dev, drive_pci - 4, &test2); | ||
| 254 | if ((test2 & SYNC_ERRDY_EN) && | ||
| 255 | !(test1 & SYNC_ERRDY_EN)) { | ||
| 256 | pci_write_config_byte(dev, drive_pci, | ||
| 257 | test1|SYNC_ERRDY_EN); | ||
| 258 | } | ||
| 259 | } else { | ||
| 260 | pci_write_config_byte(dev, drive_pci, | ||
| 261 | test1|SYNC_ERRDY_EN); | ||
| 262 | } | ||
| 263 | } | ||
| 264 | |||
| 265 | chipset_is_set: | ||
| 266 | |||
| 267 | pci_read_config_byte(dev, (drive_pci), &AP); | ||
| 268 | if (id->capability & 4) /* IORDY_EN */ | ||
| 269 | pci_write_config_byte(dev, (drive_pci), AP|IORDY_EN); | ||
| 270 | pci_read_config_byte(dev, (drive_pci), &AP); | ||
| 271 | if (drive->media == ide_disk) /* PREFETCH_EN */ | ||
| 272 | pci_write_config_byte(dev, (drive_pci), AP|PREFETCH_EN); | ||
| 273 | |||
| 274 | speed = ide_max_dma_mode(drive); | ||
| 275 | |||
| 276 | if (!(speed)) { | ||
| 277 | /* restore original pci-config space */ | ||
| 278 | pci_write_config_dword(dev, drive_pci, drive_conf); | ||
| 279 | return 0; | ||
| 280 | } | ||
| 281 | |||
| 282 | (void) hwif->speedproc(drive, speed); | ||
| 283 | return ide_dma_enable(drive); | ||
| 284 | } | ||
| 285 | |||
| 286 | static int pdc202xx_config_drive_xfer_rate (ide_drive_t *drive) | 184 | static int pdc202xx_config_drive_xfer_rate (ide_drive_t *drive) |
| 287 | { | 185 | { |
| 288 | drive->init_speed = 0; | 186 | drive->init_speed = 0; |
| 289 | 187 | ||
| 290 | if (ide_use_dma(drive) && config_chipset_for_dma(drive)) | 188 | if (ide_tune_dma(drive)) |
| 291 | return 0; | 189 | return 0; |
| 292 | 190 | ||
| 293 | if (ide_use_fast_pio(drive)) | 191 | if (ide_use_fast_pio(drive)) |
diff --git a/drivers/ide/pci/sc1200.c b/drivers/ide/pci/sc1200.c index b5ae0c50e216..523363c93794 100644 --- a/drivers/ide/pci/sc1200.c +++ b/drivers/ide/pci/sc1200.c | |||
| @@ -1,7 +1,9 @@ | |||
| 1 | /* | 1 | /* |
| 2 | * linux/drivers/ide/pci/sc1200.c Version 0.91 28-Jan-2003 | 2 | * linux/drivers/ide/pci/sc1200.c Version 0.94 Mar 10 2007 |
| 3 | * | 3 | * |
| 4 | * Copyright (C) 2000-2002 Mark Lord <mlord@pobox.com> | 4 | * Copyright (C) 2000-2002 Mark Lord <mlord@pobox.com> |
| 5 | * Copyright (C) 2007 Bartlomiej Zolnierkiewicz | ||
| 6 | * | ||
| 5 | * May be copied or modified under the terms of the GNU General Public License | 7 | * May be copied or modified under the terms of the GNU General Public License |
| 6 | * | 8 | * |
| 7 | * Development of this chipset driver was funded | 9 | * Development of this chipset driver was funded |
| @@ -93,64 +95,50 @@ static const unsigned int sc1200_pio_timings[4][5] = | |||
| 93 | */ | 95 | */ |
| 94 | //#define SC1200_BAD_PIO(timings) (((timings)&~0x80000000)==0x00009172) | 96 | //#define SC1200_BAD_PIO(timings) (((timings)&~0x80000000)==0x00009172) |
| 95 | 97 | ||
| 96 | static int sc1200_autoselect_dma_mode (ide_drive_t *drive) | 98 | static void sc1200_tunepio(ide_drive_t *drive, u8 pio) |
| 97 | { | 99 | { |
| 98 | int udma_ok = 1, mode = 0; | 100 | ide_hwif_t *hwif = drive->hwif; |
| 99 | ide_hwif_t *hwif = HWIF(drive); | 101 | struct pci_dev *pdev = hwif->pci_dev; |
| 100 | int unit = drive->select.b.unit; | 102 | unsigned int basereg = hwif->channel ? 0x50 : 0x40, format = 0; |
| 101 | ide_drive_t *mate = &hwif->drives[unit^1]; | 103 | |
| 102 | struct hd_driveid *id = drive->id; | 104 | pci_read_config_dword(pdev, basereg + 4, &format); |
| 103 | 105 | format = (format >> 31) & 1; | |
| 104 | /* | 106 | if (format) |
| 105 | * The SC1200 specifies that two drives sharing a cable cannot | 107 | format += sc1200_get_pci_clock(); |
| 106 | * mix UDMA/MDMA. It has to be one or the other, for the pair, | 108 | pci_write_config_dword(pdev, basereg + ((drive->dn & 1) << 3), |
| 107 | * though different timings can still be chosen for each drive. | 109 | sc1200_pio_timings[format][pio]); |
| 108 | * We could set the appropriate timing bits on the fly, | ||
| 109 | * but that might be a bit confusing. So, for now we statically | ||
| 110 | * handle this requirement by looking at our mate drive to see | ||
| 111 | * what it is capable of, before choosing a mode for our own drive. | ||
| 112 | */ | ||
| 113 | if (mate->present) { | ||
| 114 | struct hd_driveid *mateid = mate->id; | ||
| 115 | if (mateid && (mateid->capability & 1) && !__ide_dma_bad_drive(mate)) { | ||
| 116 | if ((mateid->field_valid & 4) && (mateid->dma_ultra & 7)) | ||
| 117 | udma_ok = 1; | ||
| 118 | else if ((mateid->field_valid & 2) && (mateid->dma_mword & 7)) | ||
| 119 | udma_ok = 0; | ||
| 120 | else | ||
| 121 | udma_ok = 1; | ||
| 122 | } | ||
| 123 | } | ||
| 124 | /* | ||
| 125 | * Now see what the current drive is capable of, | ||
| 126 | * selecting UDMA only if the mate said it was ok. | ||
| 127 | */ | ||
| 128 | if (id && (id->capability & 1) && hwif->autodma && !__ide_dma_bad_drive(drive)) { | ||
| 129 | if (udma_ok && (id->field_valid & 4) && (id->dma_ultra & 7)) { | ||
| 130 | if (id->dma_ultra & 4) | ||
| 131 | mode = XFER_UDMA_2; | ||
| 132 | else if (id->dma_ultra & 2) | ||
| 133 | mode = XFER_UDMA_1; | ||
| 134 | else if (id->dma_ultra & 1) | ||
| 135 | mode = XFER_UDMA_0; | ||
| 136 | } | ||
| 137 | if (!mode && (id->field_valid & 2) && (id->dma_mword & 7)) { | ||
| 138 | if (id->dma_mword & 4) | ||
| 139 | mode = XFER_MW_DMA_2; | ||
| 140 | else if (id->dma_mword & 2) | ||
| 141 | mode = XFER_MW_DMA_1; | ||
| 142 | else if (id->dma_mword & 1) | ||
| 143 | mode = XFER_MW_DMA_0; | ||
| 144 | } | ||
| 145 | } | ||
| 146 | return mode; | ||
| 147 | } | 110 | } |
| 148 | 111 | ||
| 149 | /* | 112 | /* |
| 150 | * sc1200_config_dma2() handles selection/setting of DMA/UDMA modes | 113 | * The SC1200 specifies that two drives sharing a cable cannot mix |
| 151 | * for both the chipset and drive. | 114 | * UDMA/MDMA. It has to be one or the other, for the pair, though |
| 115 | * different timings can still be chosen for each drive. We could | ||
| 116 | * set the appropriate timing bits on the fly, but that might be | ||
| 117 | * a bit confusing. So, for now we statically handle this requirement | ||
| 118 | * by looking at our mate drive to see what it is capable of, before | ||
| 119 | * choosing a mode for our own drive. | ||
| 152 | */ | 120 | */ |
| 153 | static int sc1200_config_dma2 (ide_drive_t *drive, int mode) | 121 | static u8 sc1200_udma_filter(ide_drive_t *drive) |
| 122 | { | ||
| 123 | ide_hwif_t *hwif = drive->hwif; | ||
| 124 | ide_drive_t *mate = &hwif->drives[(drive->dn & 1) ^ 1]; | ||
| 125 | struct hd_driveid *mateid = mate->id; | ||
| 126 | u8 mask = hwif->ultra_mask; | ||
| 127 | |||
| 128 | if (mate->present == 0) | ||
| 129 | goto out; | ||
| 130 | |||
| 131 | if ((mateid->capability & 1) && __ide_dma_bad_drive(mate) == 0) { | ||
| 132 | if ((mateid->field_valid & 4) && (mateid->dma_ultra & 7)) | ||
| 133 | goto out; | ||
| 134 | if ((mateid->field_valid & 2) && (mateid->dma_mword & 7)) | ||
| 135 | mask = 0; | ||
| 136 | } | ||
| 137 | out: | ||
| 138 | return mask; | ||
| 139 | } | ||
| 140 | |||
| 141 | static int sc1200_tune_chipset(ide_drive_t *drive, u8 mode) | ||
| 154 | { | 142 | { |
| 155 | ide_hwif_t *hwif = HWIF(drive); | 143 | ide_hwif_t *hwif = HWIF(drive); |
| 156 | int unit = drive->select.b.unit; | 144 | int unit = drive->select.b.unit; |
| @@ -158,20 +146,26 @@ static int sc1200_config_dma2 (ide_drive_t *drive, int mode) | |||
| 158 | unsigned short pci_clock; | 146 | unsigned short pci_clock; |
| 159 | unsigned int basereg = hwif->channel ? 0x50 : 0x40; | 147 | unsigned int basereg = hwif->channel ? 0x50 : 0x40; |
| 160 | 148 | ||
| 161 | /* | 149 | mode = ide_rate_filter(drive, mode); |
| 162 | * Default to DMA-off in case we run into trouble here. | ||
| 163 | */ | ||
| 164 | hwif->dma_off_quietly(drive); /* turn off DMA while we fiddle */ | ||
| 165 | outb(inb(hwif->dma_base+2)&~(unit?0x40:0x20), hwif->dma_base+2); /* clear DMA_capable bit */ | ||
| 166 | 150 | ||
| 167 | /* | 151 | /* |
| 168 | * Tell the drive to switch to the new mode; abort on failure. | 152 | * Tell the drive to switch to the new mode; abort on failure. |
| 169 | */ | 153 | */ |
| 170 | if (!mode || sc1200_set_xfer_mode(drive, mode)) { | 154 | if (sc1200_set_xfer_mode(drive, mode)) { |
| 171 | printk("SC1200: set xfer mode failure\n"); | 155 | printk("SC1200: set xfer mode failure\n"); |
| 172 | return 1; /* failure */ | 156 | return 1; /* failure */ |
| 173 | } | 157 | } |
| 174 | 158 | ||
| 159 | switch (mode) { | ||
| 160 | case XFER_PIO_4: | ||
| 161 | case XFER_PIO_3: | ||
| 162 | case XFER_PIO_2: | ||
| 163 | case XFER_PIO_1: | ||
| 164 | case XFER_PIO_0: | ||
| 165 | sc1200_tunepio(drive, mode - XFER_PIO_0); | ||
| 166 | return 0; | ||
| 167 | } | ||
| 168 | |||
| 175 | pci_clock = sc1200_get_pci_clock(); | 169 | pci_clock = sc1200_get_pci_clock(); |
| 176 | 170 | ||
| 177 | /* | 171 | /* |
| @@ -224,11 +218,9 @@ static int sc1200_config_dma2 (ide_drive_t *drive, int mode) | |||
| 224 | case PCI_CLK_66: timings = 0x00015151; break; | 218 | case PCI_CLK_66: timings = 0x00015151; break; |
| 225 | } | 219 | } |
| 226 | break; | 220 | break; |
| 227 | } | 221 | default: |
| 228 | 222 | BUG(); | |
| 229 | if (timings == 0) { | 223 | break; |
| 230 | printk("%s: sc1200_config_dma: huh? mode=%02x clk=%x \n", drive->name, mode, pci_clock); | ||
| 231 | return 1; /* failure */ | ||
| 232 | } | 224 | } |
| 233 | 225 | ||
| 234 | if (unit == 0) { /* are we configuring drive0? */ | 226 | if (unit == 0) { /* are we configuring drive0? */ |
| @@ -239,8 +231,6 @@ static int sc1200_config_dma2 (ide_drive_t *drive, int mode) | |||
| 239 | pci_write_config_dword(hwif->pci_dev, basereg+12, timings); | 231 | pci_write_config_dword(hwif->pci_dev, basereg+12, timings); |
| 240 | } | 232 | } |
| 241 | 233 | ||
| 242 | outb(inb(hwif->dma_base+2)|(unit?0x40:0x20), hwif->dma_base+2); /* set DMA_capable bit */ | ||
| 243 | |||
| 244 | return 0; /* success */ | 234 | return 0; /* success */ |
| 245 | } | 235 | } |
| 246 | 236 | ||
| @@ -250,7 +240,10 @@ static int sc1200_config_dma2 (ide_drive_t *drive, int mode) | |||
| 250 | */ | 240 | */ |
| 251 | static int sc1200_config_dma (ide_drive_t *drive) | 241 | static int sc1200_config_dma (ide_drive_t *drive) |
| 252 | { | 242 | { |
| 253 | return sc1200_config_dma2(drive, sc1200_autoselect_dma_mode(drive)); | 243 | if (ide_tune_dma(drive)) |
| 244 | return 0; | ||
| 245 | |||
| 246 | return 1; | ||
| 254 | } | 247 | } |
| 255 | 248 | ||
| 256 | 249 | ||
| @@ -290,10 +283,11 @@ static int sc1200_ide_dma_end (ide_drive_t *drive) | |||
| 290 | static void sc1200_tuneproc (ide_drive_t *drive, byte pio) /* mode=255 means "autotune" */ | 283 | static void sc1200_tuneproc (ide_drive_t *drive, byte pio) /* mode=255 means "autotune" */ |
| 291 | { | 284 | { |
| 292 | ide_hwif_t *hwif = HWIF(drive); | 285 | ide_hwif_t *hwif = HWIF(drive); |
| 293 | unsigned int format; | ||
| 294 | static byte modes[5] = {XFER_PIO_0, XFER_PIO_1, XFER_PIO_2, XFER_PIO_3, XFER_PIO_4}; | ||
| 295 | int mode = -1; | 286 | int mode = -1; |
| 296 | 287 | ||
| 288 | /* | ||
| 289 | * bad abuse of ->tuneproc interface | ||
| 290 | */ | ||
| 297 | switch (pio) { | 291 | switch (pio) { |
| 298 | case 200: mode = XFER_UDMA_0; break; | 292 | case 200: mode = XFER_UDMA_0; break; |
| 299 | case 201: mode = XFER_UDMA_1; break; | 293 | case 201: mode = XFER_UDMA_1; break; |
| @@ -304,20 +298,17 @@ static void sc1200_tuneproc (ide_drive_t *drive, byte pio) /* mode=255 means "au | |||
| 304 | } | 298 | } |
| 305 | if (mode != -1) { | 299 | if (mode != -1) { |
| 306 | printk("SC1200: %s: changing (U)DMA mode\n", drive->name); | 300 | printk("SC1200: %s: changing (U)DMA mode\n", drive->name); |
| 307 | (void)sc1200_config_dma2(drive, mode); | 301 | hwif->dma_off_quietly(drive); |
| 302 | if (sc1200_tune_chipset(drive, mode) == 0) | ||
| 303 | hwif->dma_host_on(drive); | ||
| 308 | return; | 304 | return; |
| 309 | } | 305 | } |
| 310 | 306 | ||
| 311 | pio = ide_get_best_pio_mode(drive, pio, 4, NULL); | 307 | pio = ide_get_best_pio_mode(drive, pio, 4, NULL); |
| 312 | printk("SC1200: %s: setting PIO mode%d\n", drive->name, pio); | 308 | printk("SC1200: %s: setting PIO mode%d\n", drive->name, pio); |
| 313 | if (!sc1200_set_xfer_mode(drive, modes[pio])) { | 309 | |
| 314 | unsigned int basereg = hwif->channel ? 0x50 : 0x40; | 310 | if (sc1200_set_xfer_mode(drive, XFER_PIO_0 + pio) == 0) |
| 315 | pci_read_config_dword (hwif->pci_dev, basereg+4, &format); | 311 | sc1200_tunepio(drive, pio); |
| 316 | format = (format >> 31) & 1; | ||
| 317 | if (format) | ||
| 318 | format += sc1200_get_pci_clock(); | ||
| 319 | pci_write_config_dword(hwif->pci_dev, basereg + (drive->select.b.unit << 3), sc1200_pio_timings[format][pio]); | ||
| 320 | } | ||
| 321 | } | 312 | } |
| 322 | 313 | ||
| 323 | #ifdef CONFIG_PM | 314 | #ifdef CONFIG_PM |
| @@ -438,12 +429,12 @@ static int sc1200_resume (struct pci_dev *dev) | |||
| 438 | for (d = 0; d < MAX_DRIVES; ++d) { | 429 | for (d = 0; d < MAX_DRIVES; ++d) { |
| 439 | ide_drive_t *drive = &(hwif->drives[d]); | 430 | ide_drive_t *drive = &(hwif->drives[d]); |
| 440 | if (drive->present && !__ide_dma_bad_drive(drive)) { | 431 | if (drive->present && !__ide_dma_bad_drive(drive)) { |
| 441 | int was_using_dma = drive->using_dma; | 432 | int enable_dma = drive->using_dma; |
| 442 | hwif->dma_off_quietly(drive); | 433 | hwif->dma_off_quietly(drive); |
| 443 | sc1200_config_dma(drive); | 434 | if (sc1200_config_dma(drive)) |
| 444 | if (!was_using_dma && drive->using_dma) { | 435 | enable_dma = 0; |
| 445 | hwif->dma_off_quietly(drive); | 436 | if (enable_dma) |
| 446 | } | 437 | hwif->dma_host_on(drive); |
| 447 | } | 438 | } |
| 448 | } | 439 | } |
| 449 | } | 440 | } |
| @@ -461,11 +452,13 @@ static void __devinit init_hwif_sc1200 (ide_hwif_t *hwif) | |||
| 461 | hwif->serialized = hwif->mate->serialized = 1; | 452 | hwif->serialized = hwif->mate->serialized = 1; |
| 462 | hwif->autodma = 0; | 453 | hwif->autodma = 0; |
| 463 | if (hwif->dma_base) { | 454 | if (hwif->dma_base) { |
| 455 | hwif->udma_filter = sc1200_udma_filter; | ||
| 464 | hwif->ide_dma_check = &sc1200_config_dma; | 456 | hwif->ide_dma_check = &sc1200_config_dma; |
| 465 | hwif->ide_dma_end = &sc1200_ide_dma_end; | 457 | hwif->ide_dma_end = &sc1200_ide_dma_end; |
| 466 | if (!noautodma) | 458 | if (!noautodma) |
| 467 | hwif->autodma = 1; | 459 | hwif->autodma = 1; |
| 468 | hwif->tuneproc = &sc1200_tuneproc; | 460 | hwif->tuneproc = &sc1200_tuneproc; |
| 461 | hwif->speedproc = &sc1200_tune_chipset; | ||
| 469 | } | 462 | } |
| 470 | hwif->atapi_dma = 1; | 463 | hwif->atapi_dma = 1; |
| 471 | hwif->ultra_mask = 0x07; | 464 | hwif->ultra_mask = 0x07; |
diff --git a/drivers/ide/pci/scc_pata.c b/drivers/ide/pci/scc_pata.c index cbf936325355..55bc0a32e34f 100644 --- a/drivers/ide/pci/scc_pata.c +++ b/drivers/ide/pci/scc_pata.c | |||
| @@ -322,26 +322,6 @@ static int scc_tune_chipset(ide_drive_t *drive, byte xferspeed) | |||
| 322 | } | 322 | } |
| 323 | 323 | ||
| 324 | /** | 324 | /** |
| 325 | * scc_config_chipset_for_dma - configure for DMA | ||
| 326 | * @drive: drive to configure | ||
| 327 | * | ||
| 328 | * Called by scc_config_drive_for_dma(). | ||
| 329 | */ | ||
| 330 | |||
| 331 | static int scc_config_chipset_for_dma(ide_drive_t *drive) | ||
| 332 | { | ||
| 333 | u8 speed = ide_max_dma_mode(drive); | ||
| 334 | |||
| 335 | if (!speed) | ||
| 336 | return 0; | ||
| 337 | |||
| 338 | if (scc_tune_chipset(drive, speed)) | ||
| 339 | return 0; | ||
| 340 | |||
| 341 | return ide_dma_enable(drive); | ||
| 342 | } | ||
| 343 | |||
| 344 | /** | ||
| 345 | * scc_configure_drive_for_dma - set up for DMA transfers | 325 | * scc_configure_drive_for_dma - set up for DMA transfers |
| 346 | * @drive: drive we are going to set up | 326 | * @drive: drive we are going to set up |
| 347 | * | 327 | * |
| @@ -354,7 +334,7 @@ static int scc_config_chipset_for_dma(ide_drive_t *drive) | |||
| 354 | 334 | ||
| 355 | static int scc_config_drive_for_dma(ide_drive_t *drive) | 335 | static int scc_config_drive_for_dma(ide_drive_t *drive) |
| 356 | { | 336 | { |
| 357 | if (ide_use_dma(drive) && scc_config_chipset_for_dma(drive)) | 337 | if (ide_tune_dma(drive)) |
| 358 | return 0; | 338 | return 0; |
| 359 | 339 | ||
| 360 | if (ide_use_fast_pio(drive)) | 340 | if (ide_use_fast_pio(drive)) |
diff --git a/drivers/ide/pci/serverworks.c b/drivers/ide/pci/serverworks.c index 2fa6d92d16cc..6234f806c6b5 100644 --- a/drivers/ide/pci/serverworks.c +++ b/drivers/ide/pci/serverworks.c | |||
| @@ -1,9 +1,10 @@ | |||
| 1 | /* | 1 | /* |
| 2 | * linux/drivers/ide/pci/serverworks.c Version 0.8 25 Ebr 2003 | 2 | * linux/drivers/ide/pci/serverworks.c Version 0.9 Mar 4 2007 |
| 3 | * | 3 | * |
| 4 | * Copyright (C) 1998-2000 Michel Aubry | 4 | * Copyright (C) 1998-2000 Michel Aubry |
| 5 | * Copyright (C) 1998-2000 Andrzej Krzysztofowicz | 5 | * Copyright (C) 1998-2000 Andrzej Krzysztofowicz |
| 6 | * Copyright (C) 1998-2000 Andre Hedrick <andre@linux-ide.org> | 6 | * Copyright (C) 1998-2000 Andre Hedrick <andre@linux-ide.org> |
| 7 | * Copyright (C) 2007 Bartlomiej Zolnierkiewicz | ||
| 7 | * Portions copyright (c) 2001 Sun Microsystems | 8 | * Portions copyright (c) 2001 Sun Microsystems |
| 8 | * | 9 | * |
| 9 | * | 10 | * |
| @@ -136,19 +137,14 @@ static int svwks_tune_chipset (ide_drive_t *drive, u8 xferspeed) | |||
| 136 | 137 | ||
| 137 | ide_hwif_t *hwif = HWIF(drive); | 138 | ide_hwif_t *hwif = HWIF(drive); |
| 138 | struct pci_dev *dev = hwif->pci_dev; | 139 | struct pci_dev *dev = hwif->pci_dev; |
| 139 | u8 speed; | 140 | u8 speed = ide_rate_filter(drive, xferspeed); |
| 140 | u8 pio = ide_get_best_pio_mode(drive, 255, 5, NULL); | 141 | u8 pio = ide_get_best_pio_mode(drive, 255, 4, NULL); |
| 141 | u8 unit = (drive->select.b.unit & 0x01); | 142 | u8 unit = (drive->select.b.unit & 0x01); |
| 142 | u8 csb5 = svwks_csb_check(dev); | 143 | u8 csb5 = svwks_csb_check(dev); |
| 143 | u8 ultra_enable = 0, ultra_timing = 0; | 144 | u8 ultra_enable = 0, ultra_timing = 0; |
| 144 | u8 dma_timing = 0, pio_timing = 0; | 145 | u8 dma_timing = 0, pio_timing = 0; |
| 145 | u16 csb5_pio = 0; | 146 | u16 csb5_pio = 0; |
| 146 | 147 | ||
| 147 | if (xferspeed == 255) /* PIO auto-tuning */ | ||
| 148 | speed = XFER_PIO_0 + pio; | ||
| 149 | else | ||
| 150 | speed = ide_rate_filter(drive, xferspeed); | ||
| 151 | |||
| 152 | /* If we are about to put a disk into UDMA mode we screwed up. | 148 | /* If we are about to put a disk into UDMA mode we screwed up. |
| 153 | Our code assumes we never _ever_ do this on an OSB4 */ | 149 | Our code assumes we never _ever_ do this on an OSB4 */ |
| 154 | 150 | ||
| @@ -231,6 +227,9 @@ oem_setup_failed: | |||
| 231 | case XFER_MW_DMA_2: | 227 | case XFER_MW_DMA_2: |
| 232 | case XFER_MW_DMA_1: | 228 | case XFER_MW_DMA_1: |
| 233 | case XFER_MW_DMA_0: | 229 | case XFER_MW_DMA_0: |
| 230 | /* | ||
| 231 | * TODO: always setup PIO mode so this won't be needed | ||
| 232 | */ | ||
| 234 | pio_timing |= pio_modes[pio]; | 233 | pio_timing |= pio_modes[pio]; |
| 235 | csb5_pio |= (pio << (4*drive->dn)); | 234 | csb5_pio |= (pio << (4*drive->dn)); |
| 236 | dma_timing |= dma_modes[speed - XFER_MW_DMA_0]; | 235 | dma_timing |= dma_modes[speed - XFER_MW_DMA_0]; |
| @@ -242,6 +241,9 @@ oem_setup_failed: | |||
| 242 | case XFER_UDMA_2: | 241 | case XFER_UDMA_2: |
| 243 | case XFER_UDMA_1: | 242 | case XFER_UDMA_1: |
| 244 | case XFER_UDMA_0: | 243 | case XFER_UDMA_0: |
| 244 | /* | ||
| 245 | * TODO: always setup PIO mode so this won't be needed | ||
| 246 | */ | ||
| 245 | pio_timing |= pio_modes[pio]; | 247 | pio_timing |= pio_modes[pio]; |
| 246 | csb5_pio |= (pio << (4*drive->dn)); | 248 | csb5_pio |= (pio << (4*drive->dn)); |
| 247 | dma_timing |= dma_modes[2]; | 249 | dma_timing |= dma_modes[2]; |
| @@ -262,72 +264,21 @@ oem_setup_failed: | |||
| 262 | return (ide_config_drive_speed(drive, speed)); | 264 | return (ide_config_drive_speed(drive, speed)); |
| 263 | } | 265 | } |
| 264 | 266 | ||
| 265 | static void config_chipset_for_pio (ide_drive_t *drive) | ||
| 266 | { | ||
| 267 | u16 eide_pio_timing[6] = {960, 480, 240, 180, 120, 90}; | ||
| 268 | u16 xfer_pio = drive->id->eide_pio_modes; | ||
| 269 | u8 timing, speed, pio; | ||
| 270 | |||
| 271 | pio = ide_get_best_pio_mode(drive, 255, 5, NULL); | ||
| 272 | |||
| 273 | if (xfer_pio > 4) | ||
| 274 | xfer_pio = 0; | ||
| 275 | |||
| 276 | if (drive->id->eide_pio_iordy > 0) | ||
| 277 | for (xfer_pio = 5; | ||
| 278 | xfer_pio>0 && | ||
| 279 | drive->id->eide_pio_iordy>eide_pio_timing[xfer_pio]; | ||
| 280 | xfer_pio--); | ||
| 281 | else | ||
| 282 | xfer_pio = (drive->id->eide_pio_modes & 4) ? 0x05 : | ||
| 283 | (drive->id->eide_pio_modes & 2) ? 0x04 : | ||
| 284 | (drive->id->eide_pio_modes & 1) ? 0x03 : | ||
| 285 | (drive->id->tPIO & 2) ? 0x02 : | ||
| 286 | (drive->id->tPIO & 1) ? 0x01 : xfer_pio; | ||
| 287 | |||
| 288 | timing = (xfer_pio >= pio) ? xfer_pio : pio; | ||
| 289 | |||
| 290 | switch(timing) { | ||
| 291 | case 4: speed = XFER_PIO_4;break; | ||
| 292 | case 3: speed = XFER_PIO_3;break; | ||
| 293 | case 2: speed = XFER_PIO_2;break; | ||
| 294 | case 1: speed = XFER_PIO_1;break; | ||
| 295 | default: | ||
| 296 | speed = (!drive->id->tPIO) ? XFER_PIO_0 : XFER_PIO_SLOW; | ||
| 297 | break; | ||
| 298 | } | ||
| 299 | (void) svwks_tune_chipset(drive, speed); | ||
| 300 | drive->current_speed = speed; | ||
| 301 | } | ||
| 302 | |||
| 303 | static void svwks_tune_drive (ide_drive_t *drive, u8 pio) | 267 | static void svwks_tune_drive (ide_drive_t *drive, u8 pio) |
| 304 | { | 268 | { |
| 305 | if(pio == 255) | 269 | pio = ide_get_best_pio_mode(drive, pio, 4, NULL); |
| 306 | (void) svwks_tune_chipset(drive, 255); | 270 | (void)svwks_tune_chipset(drive, XFER_PIO_0 + pio); |
| 307 | else | ||
| 308 | (void) svwks_tune_chipset(drive, (XFER_PIO_0 + pio)); | ||
| 309 | } | ||
| 310 | |||
| 311 | static int config_chipset_for_dma (ide_drive_t *drive) | ||
| 312 | { | ||
| 313 | u8 speed = ide_max_dma_mode(drive); | ||
| 314 | |||
| 315 | if (!(speed)) | ||
| 316 | speed = XFER_PIO_0 + ide_get_best_pio_mode(drive, 255, 5, NULL); | ||
| 317 | |||
| 318 | (void) svwks_tune_chipset(drive, speed); | ||
| 319 | return ide_dma_enable(drive); | ||
| 320 | } | 271 | } |
| 321 | 272 | ||
| 322 | static int svwks_config_drive_xfer_rate (ide_drive_t *drive) | 273 | static int svwks_config_drive_xfer_rate (ide_drive_t *drive) |
| 323 | { | 274 | { |
| 324 | drive->init_speed = 0; | 275 | drive->init_speed = 0; |
| 325 | 276 | ||
| 326 | if (ide_use_dma(drive) && config_chipset_for_dma(drive)) | 277 | if (ide_tune_dma(drive)) |
| 327 | return 0; | 278 | return 0; |
| 328 | 279 | ||
| 329 | if (ide_use_fast_pio(drive)) | 280 | if (ide_use_fast_pio(drive)) |
| 330 | config_chipset_for_pio(drive); | 281 | svwks_tune_drive(drive, 255); |
| 331 | 282 | ||
| 332 | return -1; | 283 | return -1; |
| 333 | } | 284 | } |
diff --git a/drivers/ide/pci/siimage.c b/drivers/ide/pci/siimage.c index d09e74c2996e..1a4444e7226a 100644 --- a/drivers/ide/pci/siimage.c +++ b/drivers/ide/pci/siimage.c | |||
| @@ -375,28 +375,6 @@ static int siimage_tune_chipset (ide_drive_t *drive, byte xferspeed) | |||
| 375 | } | 375 | } |
| 376 | 376 | ||
| 377 | /** | 377 | /** |
| 378 | * config_chipset_for_dma - configure for DMA | ||
| 379 | * @drive: drive to configure | ||
| 380 | * | ||
| 381 | * Called by the IDE layer when it wants the timings set up. | ||
| 382 | * For the CMD680 we also need to set up the PIO timings and | ||
| 383 | * enable DMA. | ||
| 384 | */ | ||
| 385 | |||
| 386 | static int config_chipset_for_dma (ide_drive_t *drive) | ||
| 387 | { | ||
| 388 | u8 speed = ide_max_dma_mode(drive); | ||
| 389 | |||
| 390 | if (!speed) | ||
| 391 | return 0; | ||
| 392 | |||
| 393 | if (siimage_tune_chipset(drive, speed)) | ||
| 394 | return 0; | ||
| 395 | |||
| 396 | return ide_dma_enable(drive); | ||
| 397 | } | ||
| 398 | |||
| 399 | /** | ||
| 400 | * siimage_configure_drive_for_dma - set up for DMA transfers | 378 | * siimage_configure_drive_for_dma - set up for DMA transfers |
| 401 | * @drive: drive we are going to set up | 379 | * @drive: drive we are going to set up |
| 402 | * | 380 | * |
| @@ -408,7 +386,7 @@ static int config_chipset_for_dma (ide_drive_t *drive) | |||
| 408 | 386 | ||
| 409 | static int siimage_config_drive_for_dma (ide_drive_t *drive) | 387 | static int siimage_config_drive_for_dma (ide_drive_t *drive) |
| 410 | { | 388 | { |
| 411 | if (ide_use_dma(drive) && config_chipset_for_dma(drive)) | 389 | if (ide_tune_dma(drive)) |
| 412 | return 0; | 390 | return 0; |
| 413 | 391 | ||
| 414 | if (ide_use_fast_pio(drive)) | 392 | if (ide_use_fast_pio(drive)) |
diff --git a/drivers/ide/pci/sis5513.c b/drivers/ide/pci/sis5513.c index 2bde1b92784a..bb6cc4aedd63 100644 --- a/drivers/ide/pci/sis5513.c +++ b/drivers/ide/pci/sis5513.c | |||
| @@ -1,9 +1,11 @@ | |||
| 1 | /* | 1 | /* |
| 2 | * linux/drivers/ide/pci/sis5513.c Version 0.16ac+vp Jun 18, 2003 | 2 | * linux/drivers/ide/pci/sis5513.c Version 0.20 Mar 4, 2007 |
| 3 | * | 3 | * |
| 4 | * Copyright (C) 1999-2000 Andre Hedrick <andre@linux-ide.org> | 4 | * Copyright (C) 1999-2000 Andre Hedrick <andre@linux-ide.org> |
| 5 | * Copyright (C) 2002 Lionel Bouton <Lionel.Bouton@inet6.fr>, Maintainer | 5 | * Copyright (C) 2002 Lionel Bouton <Lionel.Bouton@inet6.fr>, Maintainer |
| 6 | * Copyright (C) 2003 Vojtech Pavlik <vojtech@suse.cz> | 6 | * Copyright (C) 2003 Vojtech Pavlik <vojtech@suse.cz> |
| 7 | * Copyright (C) 2007 Bartlomiej Zolnierkiewicz | ||
| 8 | * | ||
| 7 | * May be copied or modified under the terms of the GNU General Public License | 9 | * May be copied or modified under the terms of the GNU General Public License |
| 8 | * | 10 | * |
| 9 | * | 11 | * |
| @@ -448,36 +450,15 @@ static void config_drive_art_rwp (ide_drive_t *drive) | |||
| 448 | pci_write_config_byte(dev, 0x4b, reg4bh|rw_prefetch); | 450 | pci_write_config_byte(dev, 0x4b, reg4bh|rw_prefetch); |
| 449 | } | 451 | } |
| 450 | 452 | ||
| 451 | |||
| 452 | /* Set per-drive active and recovery time */ | 453 | /* Set per-drive active and recovery time */ |
| 453 | static void config_art_rwp_pio (ide_drive_t *drive, u8 pio) | 454 | static void config_art_rwp_pio (ide_drive_t *drive, u8 pio) |
| 454 | { | 455 | { |
| 455 | ide_hwif_t *hwif = HWIF(drive); | 456 | ide_hwif_t *hwif = HWIF(drive); |
| 456 | struct pci_dev *dev = hwif->pci_dev; | 457 | struct pci_dev *dev = hwif->pci_dev; |
| 457 | 458 | ||
| 458 | u8 timing, drive_pci, test1, test2; | 459 | u8 drive_pci, test1, test2; |
| 459 | |||
| 460 | u16 eide_pio_timing[6] = {600, 390, 240, 180, 120, 90}; | ||
| 461 | u16 xfer_pio = drive->id->eide_pio_modes; | ||
| 462 | 460 | ||
| 463 | config_drive_art_rwp(drive); | 461 | config_drive_art_rwp(drive); |
| 464 | pio = ide_get_best_pio_mode(drive, 255, pio, NULL); | ||
| 465 | |||
| 466 | if (xfer_pio> 4) | ||
| 467 | xfer_pio = 0; | ||
| 468 | |||
| 469 | if (drive->id->eide_pio_iordy > 0) { | ||
| 470 | for (xfer_pio = 5; | ||
| 471 | (xfer_pio > 0) && | ||
| 472 | (drive->id->eide_pio_iordy > eide_pio_timing[xfer_pio]); | ||
| 473 | xfer_pio--); | ||
| 474 | } else { | ||
| 475 | xfer_pio = (drive->id->eide_pio_modes & 4) ? 0x05 : | ||
| 476 | (drive->id->eide_pio_modes & 2) ? 0x04 : | ||
| 477 | (drive->id->eide_pio_modes & 1) ? 0x03 : xfer_pio; | ||
| 478 | } | ||
| 479 | |||
| 480 | timing = (xfer_pio >= pio) ? xfer_pio : pio; | ||
| 481 | 462 | ||
| 482 | /* In pre ATA_133 case, drives sit at 0x40 + 4*drive->dn */ | 463 | /* In pre ATA_133 case, drives sit at 0x40 + 4*drive->dn */ |
| 483 | drive_pci = 0x40; | 464 | drive_pci = 0x40; |
| @@ -500,17 +481,18 @@ static void config_art_rwp_pio (ide_drive_t *drive, u8 pio) | |||
| 500 | test1 &= ~0x0F; | 481 | test1 &= ~0x0F; |
| 501 | test2 &= ~0x07; | 482 | test2 &= ~0x07; |
| 502 | 483 | ||
| 503 | switch(timing) { | 484 | switch(pio) { |
| 504 | case 4: test1 |= 0x01; test2 |= 0x03; break; | 485 | case 4: test1 |= 0x01; test2 |= 0x03; break; |
| 505 | case 3: test1 |= 0x03; test2 |= 0x03; break; | 486 | case 3: test1 |= 0x03; test2 |= 0x03; break; |
| 506 | case 2: test1 |= 0x04; test2 |= 0x04; break; | 487 | case 2: test1 |= 0x04; test2 |= 0x04; break; |
| 507 | case 1: test1 |= 0x07; test2 |= 0x06; break; | 488 | case 1: test1 |= 0x07; test2 |= 0x06; break; |
| 489 | case 0: /* PIO0: register setting == X000 */ | ||
| 508 | default: break; | 490 | default: break; |
| 509 | } | 491 | } |
| 510 | pci_write_config_byte(dev, drive_pci, test1); | 492 | pci_write_config_byte(dev, drive_pci, test1); |
| 511 | pci_write_config_byte(dev, drive_pci+1, test2); | 493 | pci_write_config_byte(dev, drive_pci+1, test2); |
| 512 | } else if (chipset_family < ATA_133) { | 494 | } else if (chipset_family < ATA_133) { |
| 513 | switch(timing) { /* active recovery | 495 | switch(pio) { /* active recovery |
| 514 | v v */ | 496 | v v */ |
| 515 | case 4: test1 = 0x30|0x01; break; | 497 | case 4: test1 = 0x30|0x01; break; |
| 516 | case 3: test1 = 0x30|0x03; break; | 498 | case 3: test1 = 0x30|0x03; break; |
| @@ -525,24 +507,28 @@ static void config_art_rwp_pio (ide_drive_t *drive, u8 pio) | |||
| 525 | pci_read_config_dword(dev, drive_pci, &test3); | 507 | pci_read_config_dword(dev, drive_pci, &test3); |
| 526 | test3 &= 0xc0c00fff; | 508 | test3 &= 0xc0c00fff; |
| 527 | if (test3 & 0x08) { | 509 | if (test3 & 0x08) { |
| 528 | test3 |= (unsigned long)ini_time_value[ATA_133][timing] << 12; | 510 | test3 |= ini_time_value[ATA_133][pio] << 12; |
| 529 | test3 |= (unsigned long)act_time_value[ATA_133][timing] << 16; | 511 | test3 |= act_time_value[ATA_133][pio] << 16; |
| 530 | test3 |= (unsigned long)rco_time_value[ATA_133][timing] << 24; | 512 | test3 |= rco_time_value[ATA_133][pio] << 24; |
| 531 | } else { | 513 | } else { |
| 532 | test3 |= (unsigned long)ini_time_value[ATA_100][timing] << 12; | 514 | test3 |= ini_time_value[ATA_100][pio] << 12; |
| 533 | test3 |= (unsigned long)act_time_value[ATA_100][timing] << 16; | 515 | test3 |= act_time_value[ATA_100][pio] << 16; |
| 534 | test3 |= (unsigned long)rco_time_value[ATA_100][timing] << 24; | 516 | test3 |= rco_time_value[ATA_100][pio] << 24; |
| 535 | } | 517 | } |
| 536 | pci_write_config_dword(dev, drive_pci, test3); | 518 | pci_write_config_dword(dev, drive_pci, test3); |
| 537 | } | 519 | } |
| 538 | } | 520 | } |
| 539 | 521 | ||
| 540 | static int config_chipset_for_pio (ide_drive_t *drive, u8 pio) | 522 | static int sis5513_tune_drive(ide_drive_t *drive, u8 pio) |
| 541 | { | 523 | { |
| 542 | if (pio == 255) | 524 | pio = ide_get_best_pio_mode(drive, pio, 4, NULL); |
| 543 | pio = ide_find_best_mode(drive, XFER_PIO | XFER_EPIO) - XFER_PIO_0; | ||
| 544 | config_art_rwp_pio(drive, pio); | 525 | config_art_rwp_pio(drive, pio); |
| 545 | return ide_config_drive_speed(drive, XFER_PIO_0 + min_t(u8, pio, 4)); | 526 | return ide_config_drive_speed(drive, XFER_PIO_0 + pio); |
| 527 | } | ||
| 528 | |||
| 529 | static void sis5513_tuneproc(ide_drive_t *drive, u8 pio) | ||
| 530 | { | ||
| 531 | (void)sis5513_tune_drive(drive, pio); | ||
| 546 | } | 532 | } |
| 547 | 533 | ||
| 548 | static int sis5513_tune_chipset (ide_drive_t *drive, u8 xferspeed) | 534 | static int sis5513_tune_chipset (ide_drive_t *drive, u8 xferspeed) |
| @@ -622,25 +608,26 @@ static int sis5513_tune_chipset (ide_drive_t *drive, u8 xferspeed) | |||
| 622 | case XFER_SW_DMA_1: | 608 | case XFER_SW_DMA_1: |
| 623 | case XFER_SW_DMA_0: | 609 | case XFER_SW_DMA_0: |
| 624 | break; | 610 | break; |
| 625 | case XFER_PIO_4: return((int) config_chipset_for_pio(drive, 4)); | 611 | case XFER_PIO_4: |
| 626 | case XFER_PIO_3: return((int) config_chipset_for_pio(drive, 3)); | 612 | case XFER_PIO_3: |
| 627 | case XFER_PIO_2: return((int) config_chipset_for_pio(drive, 2)); | 613 | case XFER_PIO_2: |
| 628 | case XFER_PIO_1: return((int) config_chipset_for_pio(drive, 1)); | 614 | case XFER_PIO_1: |
| 629 | case XFER_PIO_0: | 615 | case XFER_PIO_0: |
| 630 | default: return((int) config_chipset_for_pio(drive, 0)); | 616 | return sis5513_tune_drive(drive, speed - XFER_PIO_0); |
| 617 | default: | ||
| 618 | BUG(); | ||
| 619 | break; | ||
| 631 | } | 620 | } |
| 632 | 621 | ||
| 633 | return ((int) ide_config_drive_speed(drive, speed)); | 622 | return ide_config_drive_speed(drive, speed); |
| 634 | } | ||
| 635 | |||
| 636 | static void sis5513_tune_drive (ide_drive_t *drive, u8 pio) | ||
| 637 | { | ||
| 638 | (void) config_chipset_for_pio(drive, pio); | ||
| 639 | } | 623 | } |
| 640 | 624 | ||
| 641 | static int sis5513_config_xfer_rate(ide_drive_t *drive) | 625 | static int sis5513_config_xfer_rate(ide_drive_t *drive) |
| 642 | { | 626 | { |
| 643 | config_art_rwp_pio(drive, 5); | 627 | /* |
| 628 | * TODO: always set PIO mode and remove this | ||
| 629 | */ | ||
| 630 | sis5513_tuneproc(drive, 255); | ||
| 644 | 631 | ||
| 645 | drive->init_speed = 0; | 632 | drive->init_speed = 0; |
| 646 | 633 | ||
| @@ -648,7 +635,7 @@ static int sis5513_config_xfer_rate(ide_drive_t *drive) | |||
| 648 | return 0; | 635 | return 0; |
| 649 | 636 | ||
| 650 | if (ide_use_fast_pio(drive)) | 637 | if (ide_use_fast_pio(drive)) |
| 651 | sis5513_tune_drive(drive, 5); | 638 | sis5513_tuneproc(drive, 255); |
| 652 | 639 | ||
| 653 | return -1; | 640 | return -1; |
| 654 | } | 641 | } |
| @@ -836,7 +823,7 @@ static void __devinit init_hwif_sis5513 (ide_hwif_t *hwif) | |||
| 836 | if (!hwif->irq) | 823 | if (!hwif->irq) |
| 837 | hwif->irq = hwif->channel ? 15 : 14; | 824 | hwif->irq = hwif->channel ? 15 : 14; |
| 838 | 825 | ||
| 839 | hwif->tuneproc = &sis5513_tune_drive; | 826 | hwif->tuneproc = &sis5513_tuneproc; |
| 840 | hwif->speedproc = &sis5513_tune_chipset; | 827 | hwif->speedproc = &sis5513_tune_chipset; |
| 841 | 828 | ||
| 842 | if (!(hwif->dma_base)) { | 829 | if (!(hwif->dma_base)) { |
diff --git a/drivers/ide/pci/sl82c105.c b/drivers/ide/pci/sl82c105.c index fe3b4b91f854..7c383d9cc472 100644 --- a/drivers/ide/pci/sl82c105.c +++ b/drivers/ide/pci/sl82c105.c | |||
| @@ -82,7 +82,14 @@ static u8 sl82c105_tune_pio(ide_drive_t *drive, u8 pio) | |||
| 82 | 82 | ||
| 83 | pio = ide_get_best_pio_mode(drive, pio, 5, &p); | 83 | pio = ide_get_best_pio_mode(drive, pio, 5, &p); |
| 84 | 84 | ||
| 85 | drive->drive_data = drv_ctrl = get_pio_timings(&p); | 85 | drv_ctrl = get_pio_timings(&p); |
| 86 | |||
| 87 | /* | ||
| 88 | * Store the PIO timings so that we can restore them | ||
| 89 | * in case DMA will be turned off... | ||
| 90 | */ | ||
| 91 | drive->drive_data &= 0xffff0000; | ||
| 92 | drive->drive_data |= drv_ctrl; | ||
| 86 | 93 | ||
| 87 | if (!drive->using_dma) { | 94 | if (!drive->using_dma) { |
| 88 | /* | 95 | /* |
| @@ -100,17 +107,55 @@ static u8 sl82c105_tune_pio(ide_drive_t *drive, u8 pio) | |||
| 100 | } | 107 | } |
| 101 | 108 | ||
| 102 | /* | 109 | /* |
| 103 | * Configure the drive for DMA. | 110 | * Configure the drive and chipset for a new transfer speed. |
| 104 | * We'll program the chipset only when DMA is actually turned on. | ||
| 105 | */ | 111 | */ |
| 106 | static int config_for_dma(ide_drive_t *drive) | 112 | static int sl82c105_tune_chipset(ide_drive_t *drive, u8 speed) |
| 107 | { | 113 | { |
| 108 | DBG(("config_for_dma(drive:%s)\n", drive->name)); | 114 | static u16 mwdma_timings[] = {0x0707, 0x0201, 0x0200}; |
| 115 | u16 drv_ctrl; | ||
| 109 | 116 | ||
| 110 | if (ide_config_drive_speed(drive, XFER_MW_DMA_2) != 0) | 117 | DBG(("sl82c105_tune_chipset(drive:%s, speed:%s)\n", |
| 111 | return 0; | 118 | drive->name, ide_xfer_verbose(speed))); |
| 112 | 119 | ||
| 113 | return ide_dma_enable(drive); | 120 | speed = ide_rate_filter(drive, speed); |
| 121 | |||
| 122 | switch (speed) { | ||
| 123 | case XFER_MW_DMA_2: | ||
| 124 | case XFER_MW_DMA_1: | ||
| 125 | case XFER_MW_DMA_0: | ||
| 126 | drv_ctrl = mwdma_timings[speed - XFER_MW_DMA_0]; | ||
| 127 | |||
| 128 | /* | ||
| 129 | * Store the DMA timings so that we can actually program | ||
| 130 | * them when DMA will be turned on... | ||
| 131 | */ | ||
| 132 | drive->drive_data &= 0x0000ffff; | ||
| 133 | drive->drive_data |= (unsigned long)drv_ctrl << 16; | ||
| 134 | |||
| 135 | /* | ||
| 136 | * If we are already using DMA, we just reprogram | ||
| 137 | * the drive control register. | ||
| 138 | */ | ||
| 139 | if (drive->using_dma) { | ||
| 140 | struct pci_dev *dev = HWIF(drive)->pci_dev; | ||
| 141 | int reg = 0x44 + drive->dn * 4; | ||
| 142 | |||
| 143 | pci_write_config_word(dev, reg, drv_ctrl); | ||
| 144 | } | ||
| 145 | break; | ||
| 146 | case XFER_PIO_5: | ||
| 147 | case XFER_PIO_4: | ||
| 148 | case XFER_PIO_3: | ||
| 149 | case XFER_PIO_2: | ||
| 150 | case XFER_PIO_1: | ||
| 151 | case XFER_PIO_0: | ||
| 152 | (void) sl82c105_tune_pio(drive, speed - XFER_PIO_0); | ||
| 153 | break; | ||
| 154 | default: | ||
| 155 | return -1; | ||
| 156 | } | ||
| 157 | |||
| 158 | return ide_config_drive_speed(drive, speed); | ||
| 114 | } | 159 | } |
| 115 | 160 | ||
| 116 | /* | 161 | /* |
| @@ -120,7 +165,7 @@ static int sl82c105_ide_dma_check(ide_drive_t *drive) | |||
| 120 | { | 165 | { |
| 121 | DBG(("sl82c105_ide_dma_check(drive:%s)\n", drive->name)); | 166 | DBG(("sl82c105_ide_dma_check(drive:%s)\n", drive->name)); |
| 122 | 167 | ||
| 123 | if (ide_use_dma(drive) && config_for_dma(drive)) | 168 | if (ide_tune_dma(drive)) |
| 124 | return 0; | 169 | return 0; |
| 125 | 170 | ||
| 126 | return -1; | 171 | return -1; |
| @@ -219,7 +264,7 @@ static int sl82c105_ide_dma_on(ide_drive_t *drive) | |||
| 219 | 264 | ||
| 220 | rc = __ide_dma_on(drive); | 265 | rc = __ide_dma_on(drive); |
| 221 | if (rc == 0) { | 266 | if (rc == 0) { |
| 222 | pci_write_config_word(dev, reg, 0x0200); | 267 | pci_write_config_word(dev, reg, drive->drive_data >> 16); |
| 223 | 268 | ||
| 224 | printk(KERN_INFO "%s: DMA enabled\n", drive->name); | 269 | printk(KERN_INFO "%s: DMA enabled\n", drive->name); |
| 225 | } | 270 | } |
| @@ -304,7 +349,7 @@ static unsigned int sl82c105_bridge_revision(struct pci_dev *dev) | |||
| 304 | /* | 349 | /* |
| 305 | * The bridge should be part of the same device, but function 0. | 350 | * The bridge should be part of the same device, but function 0. |
| 306 | */ | 351 | */ |
| 307 | bridge = pci_find_slot(dev->bus->number, | 352 | bridge = pci_get_bus_and_slot(dev->bus->number, |
| 308 | PCI_DEVFN(PCI_SLOT(dev->devfn), 0)); | 353 | PCI_DEVFN(PCI_SLOT(dev->devfn), 0)); |
| 309 | if (!bridge) | 354 | if (!bridge) |
| 310 | return -1; | 355 | return -1; |
| @@ -314,13 +359,15 @@ static unsigned int sl82c105_bridge_revision(struct pci_dev *dev) | |||
| 314 | */ | 359 | */ |
| 315 | if (bridge->vendor != PCI_VENDOR_ID_WINBOND || | 360 | if (bridge->vendor != PCI_VENDOR_ID_WINBOND || |
| 316 | bridge->device != PCI_DEVICE_ID_WINBOND_83C553 || | 361 | bridge->device != PCI_DEVICE_ID_WINBOND_83C553 || |
| 317 | bridge->class >> 8 != PCI_CLASS_BRIDGE_ISA) | 362 | bridge->class >> 8 != PCI_CLASS_BRIDGE_ISA) { |
| 363 | pci_dev_put(bridge); | ||
| 318 | return -1; | 364 | return -1; |
| 319 | 365 | } | |
| 320 | /* | 366 | /* |
| 321 | * We need to find function 0's revision, not function 1 | 367 | * We need to find function 0's revision, not function 1 |
| 322 | */ | 368 | */ |
| 323 | pci_read_config_byte(bridge, PCI_REVISION_ID, &rev); | 369 | pci_read_config_byte(bridge, PCI_REVISION_ID, &rev); |
| 370 | pci_dev_put(bridge); | ||
| 324 | 371 | ||
| 325 | return rev; | 372 | return rev; |
| 326 | } | 373 | } |
| @@ -357,6 +404,7 @@ static void __devinit init_hwif_sl82c105(ide_hwif_t *hwif) | |||
| 357 | DBG(("init_hwif_sl82c105(hwif: ide%d)\n", hwif->index)); | 404 | DBG(("init_hwif_sl82c105(hwif: ide%d)\n", hwif->index)); |
| 358 | 405 | ||
| 359 | hwif->tuneproc = &sl82c105_tune_drive; | 406 | hwif->tuneproc = &sl82c105_tune_drive; |
| 407 | hwif->speedproc = &sl82c105_tune_chipset; | ||
| 360 | hwif->selectproc = &sl82c105_selectproc; | 408 | hwif->selectproc = &sl82c105_selectproc; |
| 361 | hwif->resetproc = &sl82c105_resetproc; | 409 | hwif->resetproc = &sl82c105_resetproc; |
| 362 | 410 | ||
| @@ -388,7 +436,7 @@ static void __devinit init_hwif_sl82c105(ide_hwif_t *hwif) | |||
| 388 | } | 436 | } |
| 389 | 437 | ||
| 390 | hwif->atapi_dma = 1; | 438 | hwif->atapi_dma = 1; |
| 391 | hwif->mwdma_mask = 0x04; | 439 | hwif->mwdma_mask = 0x07; |
| 392 | 440 | ||
| 393 | hwif->ide_dma_check = &sl82c105_ide_dma_check; | 441 | hwif->ide_dma_check = &sl82c105_ide_dma_check; |
| 394 | hwif->ide_dma_on = &sl82c105_ide_dma_on; | 442 | hwif->ide_dma_on = &sl82c105_ide_dma_on; |
diff --git a/include/linux/ide.h b/include/linux/ide.h index df4e6a510310..07aba87d369d 100644 --- a/include/linux/ide.h +++ b/include/linux/ide.h | |||
| @@ -1281,7 +1281,6 @@ struct drive_list_entry { | |||
| 1281 | int ide_in_drive_list(struct hd_driveid *, const struct drive_list_entry *); | 1281 | int ide_in_drive_list(struct hd_driveid *, const struct drive_list_entry *); |
| 1282 | int __ide_dma_bad_drive(ide_drive_t *); | 1282 | int __ide_dma_bad_drive(ide_drive_t *); |
| 1283 | int __ide_dma_good_drive(ide_drive_t *); | 1283 | int __ide_dma_good_drive(ide_drive_t *); |
| 1284 | int ide_use_dma(ide_drive_t *); | ||
| 1285 | u8 ide_max_dma_mode(ide_drive_t *); | 1284 | u8 ide_max_dma_mode(ide_drive_t *); |
| 1286 | int ide_tune_dma(ide_drive_t *); | 1285 | int ide_tune_dma(ide_drive_t *); |
| 1287 | void ide_dma_off(ide_drive_t *); | 1286 | void ide_dma_off(ide_drive_t *); |
| @@ -1309,7 +1308,6 @@ extern int __ide_dma_timeout(ide_drive_t *); | |||
| 1309 | #endif /* CONFIG_BLK_DEV_IDEDMA_PCI */ | 1308 | #endif /* CONFIG_BLK_DEV_IDEDMA_PCI */ |
| 1310 | 1309 | ||
| 1311 | #else | 1310 | #else |
| 1312 | static inline int ide_use_dma(ide_drive_t *drive) { return 0; } | ||
| 1313 | static inline u8 ide_max_dma_mode(ide_drive_t *drive) { return 0; } | 1311 | static inline u8 ide_max_dma_mode(ide_drive_t *drive) { return 0; } |
| 1314 | static inline int ide_tune_dma(ide_drive_t *drive) { return 0; } | 1312 | static inline int ide_tune_dma(ide_drive_t *drive) { return 0; } |
| 1315 | static inline void ide_dma_off(ide_drive_t *drive) { ; } | 1313 | static inline void ide_dma_off(ide_drive_t *drive) { ; } |
| @@ -1357,7 +1355,6 @@ static inline void ide_set_hwifdata (ide_hwif_t * hwif, void *data) | |||
| 1357 | 1355 | ||
| 1358 | /* ide-lib.c */ | 1356 | /* ide-lib.c */ |
| 1359 | u8 ide_rate_filter(ide_drive_t *, u8); | 1357 | u8 ide_rate_filter(ide_drive_t *, u8); |
| 1360 | extern int ide_dma_enable(ide_drive_t *drive); | ||
| 1361 | extern char *ide_xfer_verbose(u8 xfer_rate); | 1358 | extern char *ide_xfer_verbose(u8 xfer_rate); |
| 1362 | extern void ide_toggle_bounce(ide_drive_t *drive, int on); | 1359 | extern void ide_toggle_bounce(ide_drive_t *drive, int on); |
| 1363 | extern int ide_set_xfer_rate(ide_drive_t *drive, u8 rate); | 1360 | extern int ide_set_xfer_rate(ide_drive_t *drive, u8 rate); |
