mirror of
https://github.com/torvalds/linux.git
synced 2024-11-29 07:31:29 +00:00
pata_legacy: unify QDI ->set_piomode methods
Add controller type field to struct legacy_data and then use it to merge together all ->set_piomode methods for QDI controllers. Signed-off-by: Bartlomiej Zolnierkiewicz <bzolnier@gmail.com> Signed-off-by: Jeff Garzik <jgarzik@redhat.com>
This commit is contained in:
parent
0dcd0a7637
commit
8c7e8f947f
@ -79,15 +79,6 @@ static int all;
|
||||
module_param(all, int, 0444);
|
||||
MODULE_PARM_DESC(all, "Grab all legacy port devices, even if PCI(0=off, 1=on)");
|
||||
|
||||
struct legacy_data {
|
||||
unsigned long timing;
|
||||
u8 clock[2];
|
||||
u8 last;
|
||||
int fast;
|
||||
struct platform_device *platform_dev;
|
||||
|
||||
};
|
||||
|
||||
enum controller {
|
||||
BIOS = 0,
|
||||
SNOOP = 1,
|
||||
@ -104,6 +95,14 @@ enum controller {
|
||||
UNKNOWN = -1
|
||||
};
|
||||
|
||||
struct legacy_data {
|
||||
unsigned long timing;
|
||||
u8 clock[2];
|
||||
u8 last;
|
||||
int fast;
|
||||
enum controller type;
|
||||
struct platform_device *platform_dev;
|
||||
};
|
||||
|
||||
struct legacy_probe {
|
||||
unsigned char *name;
|
||||
@ -637,77 +636,20 @@ static struct ata_port_operations opti82c46x_port_ops = {
|
||||
.qc_issue = opti82c46x_qc_issue,
|
||||
};
|
||||
|
||||
static void qdi6500_set_piomode(struct ata_port *ap, struct ata_device *adev)
|
||||
{
|
||||
struct ata_timing t;
|
||||
struct legacy_data *ld_qdi = ap->host->private_data;
|
||||
int active, recovery;
|
||||
u8 timing;
|
||||
|
||||
/* Get the timing data in cycles */
|
||||
ata_timing_compute(adev, adev->pio_mode, &t, 30303, 1000);
|
||||
|
||||
if (ld_qdi->fast) {
|
||||
active = 8 - clamp_val(t.active, 1, 8);
|
||||
recovery = 18 - clamp_val(t.recover, 3, 18);
|
||||
} else {
|
||||
active = 9 - clamp_val(t.active, 2, 9);
|
||||
recovery = 15 - clamp_val(t.recover, 0, 15);
|
||||
}
|
||||
timing = (recovery << 4) | active | 0x08;
|
||||
|
||||
ld_qdi->clock[adev->devno] = timing;
|
||||
|
||||
outb(timing, ld_qdi->timing);
|
||||
}
|
||||
|
||||
/**
|
||||
* qdi6580dp_set_piomode - PIO setup for dual channel
|
||||
* @ap: Port
|
||||
* @adev: Device
|
||||
*
|
||||
* In dual channel mode the 6580 has one clock per channel and we have
|
||||
* to software clockswitch in qc_issue.
|
||||
*/
|
||||
|
||||
static void qdi6580dp_set_piomode(struct ata_port *ap, struct ata_device *adev)
|
||||
{
|
||||
struct ata_timing t;
|
||||
struct legacy_data *ld_qdi = ap->host->private_data;
|
||||
int active, recovery;
|
||||
u8 timing;
|
||||
|
||||
/* Get the timing data in cycles */
|
||||
ata_timing_compute(adev, adev->pio_mode, &t, 30303, 1000);
|
||||
|
||||
if (ld_qdi->fast) {
|
||||
active = 8 - clamp_val(t.active, 1, 8);
|
||||
recovery = 18 - clamp_val(t.recover, 3, 18);
|
||||
} else {
|
||||
active = 9 - clamp_val(t.active, 2, 9);
|
||||
recovery = 15 - clamp_val(t.recover, 0, 15);
|
||||
}
|
||||
timing = (recovery << 4) | active | 0x08;
|
||||
|
||||
ld_qdi->clock[adev->devno] = timing;
|
||||
|
||||
outb(timing, ld_qdi->timing + 2 * ap->port_no);
|
||||
/* Clear the FIFO */
|
||||
if (adev->class != ATA_DEV_ATA)
|
||||
outb(0x5F, (ld_qdi->timing & 0xFFF0) + 3);
|
||||
}
|
||||
|
||||
/**
|
||||
* qdi6580_set_piomode - PIO setup for single channel
|
||||
* qdi65x0_set_piomode - PIO setup for QDI65x0
|
||||
* @ap: Port
|
||||
* @adev: Device
|
||||
*
|
||||
* In single channel mode the 6580 has one clock per device and we can
|
||||
* avoid the requirement to clock switch. We also have to load the timing
|
||||
* into the right clock according to whether we are master or slave.
|
||||
*
|
||||
* In dual channel mode the 6580 has one clock per channel and we have
|
||||
* to software clockswitch in qc_issue.
|
||||
*/
|
||||
|
||||
static void qdi6580_set_piomode(struct ata_port *ap, struct ata_device *adev)
|
||||
static void qdi65x0_set_piomode(struct ata_port *ap, struct ata_device *adev)
|
||||
{
|
||||
struct ata_timing t;
|
||||
struct legacy_data *ld_qdi = ap->host->private_data;
|
||||
@ -726,9 +668,14 @@ static void qdi6580_set_piomode(struct ata_port *ap, struct ata_device *adev)
|
||||
}
|
||||
timing = (recovery << 4) | active | 0x08;
|
||||
ld_qdi->clock[adev->devno] = timing;
|
||||
outb(timing, ld_qdi->timing + 2 * adev->devno);
|
||||
|
||||
if (ld_qdi->type == QDI6580)
|
||||
outb(timing, ld_qdi->timing + 2 * adev->devno);
|
||||
else
|
||||
outb(timing, ld_qdi->timing + 2 * ap->port_no);
|
||||
|
||||
/* Clear the FIFO */
|
||||
if (adev->class != ATA_DEV_ATA)
|
||||
if (ld_qdi->type != QDI6500 && adev->class != ATA_DEV_ATA)
|
||||
outb(0x5F, (ld_qdi->timing & 0xFFF0) + 3);
|
||||
}
|
||||
|
||||
@ -795,20 +742,20 @@ static int qdi_port(struct platform_device *dev,
|
||||
|
||||
static struct ata_port_operations qdi6500_port_ops = {
|
||||
.inherits = &legacy_base_port_ops,
|
||||
.set_piomode = qdi6500_set_piomode,
|
||||
.set_piomode = qdi65x0_set_piomode,
|
||||
.qc_issue = qdi_qc_issue,
|
||||
.sff_data_xfer = vlb32_data_xfer,
|
||||
};
|
||||
|
||||
static struct ata_port_operations qdi6580_port_ops = {
|
||||
.inherits = &legacy_base_port_ops,
|
||||
.set_piomode = qdi6580_set_piomode,
|
||||
.set_piomode = qdi65x0_set_piomode,
|
||||
.sff_data_xfer = vlb32_data_xfer,
|
||||
};
|
||||
|
||||
static struct ata_port_operations qdi6580dp_port_ops = {
|
||||
.inherits = &legacy_base_port_ops,
|
||||
.set_piomode = qdi6580dp_set_piomode,
|
||||
.set_piomode = qdi65x0_set_piomode,
|
||||
.qc_issue = qdi_qc_issue,
|
||||
.sff_data_xfer = vlb32_data_xfer,
|
||||
};
|
||||
@ -1028,6 +975,7 @@ static __init int legacy_init_one(struct legacy_probe *probe)
|
||||
ctrl_addr = devm_ioport_map(&pdev->dev, io + 0x0206, 1);
|
||||
if (!io_addr || !ctrl_addr)
|
||||
goto fail;
|
||||
ld->type = probe->type;
|
||||
if (controller->setup)
|
||||
if (controller->setup(pdev, probe, ld) < 0)
|
||||
goto fail;
|
||||
|
Loading…
Reference in New Issue
Block a user