summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorsos <sos@FreeBSD.org>2003-01-19 11:47:32 +0000
committersos <sos@FreeBSD.org>2003-01-19 11:47:32 +0000
commit0243c6a097a811d17f26c37cd9580249f7f9a4c5 (patch)
tree9e856aa022309c97f2ecdfe7d7b06e0bc6e04b58
parentc5c41f4b01e34c1db6bfbdcb4d4440eb4172ea19 (diff)
downloadFreeBSD-src-0243c6a097a811d17f26c37cd9580249f7f9a4c5.zip
FreeBSD-src-0243c6a097a811d17f26c37cd9580249f7f9a4c5.tar.gz
Fix the 48bit access support for the older Promise 66/100 controllers, the
first attempt was wrong and could cause r/w timeouts. Add yet another Promise PCI id.
-rw-r--r--sys/dev/ata/ata-all.c1
-rw-r--r--sys/dev/ata/ata-all.h1
-rw-r--r--sys/dev/ata/ata-dma.c37
-rw-r--r--sys/dev/ata/ata-pci.c3
4 files changed, 26 insertions, 16 deletions
diff --git a/sys/dev/ata/ata-all.c b/sys/dev/ata/ata-all.c
index 05984d5..91b8bb9 100644
--- a/sys/dev/ata/ata-all.c
+++ b/sys/dev/ata/ata-all.c
@@ -1105,6 +1105,7 @@ ata_command(struct ata_device *atadev, u_int8_t command,
ata_prtdev(atadev, "can't translate cmd to 48bit version\n");
return -1;
}
+ atadev->channel->flags |= ATA_48BIT_ACTIVE;
}
else {
ATA_OUTB(atadev->channel->r_io, ATA_FEATURE, feature);
diff --git a/sys/dev/ata/ata-all.h b/sys/dev/ata/ata-all.h
index d32a7b6..30352f0 100644
--- a/sys/dev/ata/ata-all.h
+++ b/sys/dev/ata/ata-all.h
@@ -217,6 +217,7 @@ struct ata_channel {
#define ATA_ATAPI_DMA_RO 0x08
#define ATA_QUEUED 0x10
#define ATA_DMA_ACTIVE 0x20
+#define ATA_48BIT_ACTIVE 0x40
struct ata_device device[2]; /* devices on this channel */
#define MASTER 0x00
diff --git a/sys/dev/ata/ata-dma.c b/sys/dev/ata/ata-dma.c
index 12a8b9e..2e149e5 100644
--- a/sys/dev/ata/ata-dma.c
+++ b/sys/dev/ata/ata-dma.c
@@ -1051,8 +1051,9 @@ ata_dmainit(struct ata_device *atadev, int apiomode, int wdmamode, int udmamode)
break;
case 0x4d69105a: /* Promise TX2 ATA133 controllers */
- case 0x5275105a: /* Promise TX2 ATA133 controllers */
case 0x6269105a: /* Promise TX2 ATA133 controllers */
+ case 0x1275105a: /* Promise TX2 ATA133 controllers */
+ case 0x5275105a: /* Promise TX2 ATA133 controllers */
case 0x7275105a: /* Promise TX2 ATA133 controllers */
ATA_OUTB(atadev->channel->r_bmio, ATA_BMDEVSPEC_0, 0x0b);
if (udmamode >= 6 &&
@@ -1527,12 +1528,13 @@ ata_dmastart(struct ata_device *atadev, caddr_t data, int32_t count, int dir)
case 0x4d38105a: /* Promise Ultra/Fasttrak 66 */
case 0x0d30105a: /* Promise OEM ATA 100 */
case 0x4d30105a: /* Promise Ultra/Fasttrak 100 */
- ATA_OUTB(ch->r_bmio, 0x11,
- ATA_INB(ch->r_bmio, 0x11) | (atadev->unit ? 0x08 : 0x02));
-
- ATA_OUTL(ch->r_bmio, (atadev->unit ? 0x24 : 0x20),
+ if (ch->flags & ATA_48BIT_ACTIVE) {
+ ATA_OUTB(ch->r_bmio, (ch->unit ? 0x09 : 0x11),
+ ATA_INB(ch->r_bmio, (ch->unit ? 0x09 : 0x11)) |
+ (ch->unit ? 0x08 : 0x02));
+ ATA_OUTL(ch->r_bmio, (ch->unit ? 0x1c : 0x20),
(dir ? 0x05000000 : 0x06000000) | (count >> 1));
- break;
+ }
}
cba.dmatab = ds->dmatab;
@@ -1570,21 +1572,24 @@ ata_dmadone(struct ata_device *atadev)
case 0x4d38105a: /* Promise Ultra/Fasttrak 66 */
case 0x0d30105a: /* Promise OEM ATA 100 */
case 0x4d30105a: /* Promise Ultra/Fasttrak 100 */
- ATA_OUTL(ch->r_bmio, (atadev->unit ? 0x24 : 0x20), 0);
- ATA_OUTB(ch->r_bmio, 0x11,
- ATA_INB(ch->r_bmio, 0x11) & ~(atadev->unit ? 0x08 : 0x02));
- break;
+ if (ch->flags & ATA_48BIT_ACTIVE) {
+ ATA_OUTB(ch->r_bmio, (ch->unit ? 0x09 : 0x11),
+ ATA_INB(ch->r_bmio, (ch->unit ? 0x09 : 0x11)) &
+ ~(ch->unit ? 0x08 : 0x02));
+ ATA_OUTL(ch->r_bmio, (ch->unit ? 0x1c : 0x20), 0);
+ ch->flags &= ~ATA_48BIT_ACTIVE;
+ }
}
+ error = ATA_INB(ch->r_bmio, ATA_BMSTAT_PORT);
+ ATA_OUTB(ch->r_bmio, ATA_BMCMD_PORT,
+ ATA_INB(ch->r_bmio, ATA_BMCMD_PORT) & ~ATA_BMCMD_START_STOP);
+ ATA_OUTB(ch->r_bmio, ATA_BMSTAT_PORT,ATA_BMSTAT_INTERRUPT|ATA_BMSTAT_ERROR);
+
bus_dmamap_sync(ds->ddmatag, ds->ddmamap, (ds->flags & ATA_DS_READ) != 0 ?
BUS_DMASYNC_POSTREAD : BUS_DMASYNC_POSTWRITE);
bus_dmamap_unload(ds->ddmatag, ds->ddmamap);
-
- ATA_OUTB(ch->r_bmio, ATA_BMCMD_PORT,
- ATA_INB(ch->r_bmio, ATA_BMCMD_PORT) & ~ATA_BMCMD_START_STOP);
- error = ATA_INB(ch->r_bmio, ATA_BMSTAT_PORT);
- ATA_OUTB(ch->r_bmio, ATA_BMSTAT_PORT,
- error | ATA_BMSTAT_INTERRUPT | ATA_BMSTAT_ERROR);
+
ch->flags &= ~ATA_DMA_ACTIVE;
ds->flags = 0;
return (error & ATA_BMSTAT_MASK);
diff --git a/sys/dev/ata/ata-pci.c b/sys/dev/ata/ata-pci.c
index d4375fa..f855c48 100644
--- a/sys/dev/ata/ata-pci.c
+++ b/sys/dev/ata/ata-pci.c
@@ -287,6 +287,7 @@ ata_pci_match(device_t dev)
}
return "Promise TX2 ATA100 controller";
+ case 0x1275105a:
case 0x5275105a:
case 0x7275105a:
{
@@ -628,6 +629,7 @@ ata_pci_intr(struct ata_channel *ch)
case 0x4d68105a: /* Promise TX2 ATA100 */
case 0x6268105a: /* Promise TX2 ATA100 */
case 0x4d69105a: /* Promise TX2 ATA133 */
+ case 0x1275105a: /* Promise TX2 ATA133 */
case 0x5275105a: /* Promise TX2 ATA133 */
case 0x6269105a: /* Promise TX2 ATA133 */
case 0x7275105a: /* Promise TX2 ATA133 */
@@ -694,6 +696,7 @@ ata_pci_serialize(struct ata_channel *ch, int flags)
if (scp->lock == -1 || scp->lock != ch->unit)
break;
atomic_store_rel_int(&scp->lock, -1);
+ wakeup((caddr_t)ch->lock_func);
break;
}
return;
OpenPOWER on IntegriCloud