aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/ide/legacy
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/ide/legacy')
-rw-r--r--drivers/ide/legacy/ali14xx.c30
-rw-r--r--drivers/ide/legacy/buddha.c2
-rw-r--r--drivers/ide/legacy/dtc2278.c22
-rw-r--r--drivers/ide/legacy/falconide.c9
-rw-r--r--drivers/ide/legacy/gayle.c2
-rw-r--r--drivers/ide/legacy/hd.c78
-rw-r--r--drivers/ide/legacy/ht6560b.c34
-rw-r--r--drivers/ide/legacy/ide-4drives.c36
-rw-r--r--drivers/ide/legacy/ide-cs.c2
-rw-r--r--drivers/ide/legacy/ide_platform.c7
-rw-r--r--drivers/ide/legacy/macide.c2
-rw-r--r--drivers/ide/legacy/q40ide.c2
-rw-r--r--drivers/ide/legacy/qd65xx.c165
-rw-r--r--drivers/ide/legacy/qd65xx.h1
-rw-r--r--drivers/ide/legacy/umc8672.c81
15 files changed, 251 insertions, 222 deletions
diff --git a/drivers/ide/legacy/ali14xx.c b/drivers/ide/legacy/ali14xx.c
index bc8b1f8de614..33bb7b87be5d 100644
--- a/drivers/ide/legacy/ali14xx.c
+++ b/drivers/ide/legacy/ali14xx.c
@@ -86,7 +86,7 @@ static u8 regOff; /* output to base port to close registers */
86/* 86/*
87 * Read a controller register. 87 * Read a controller register.
88 */ 88 */
89static inline u8 inReg (u8 reg) 89static inline u8 inReg(u8 reg)
90{ 90{
91 outb_p(reg, regPort); 91 outb_p(reg, regPort);
92 return inb(dataPort); 92 return inb(dataPort);
@@ -95,7 +95,7 @@ static inline u8 inReg (u8 reg)
95/* 95/*
96 * Write a controller register. 96 * Write a controller register.
97 */ 97 */
98static void outReg (u8 data, u8 reg) 98static void outReg(u8 data, u8 reg)
99{ 99{
100 outb_p(reg, regPort); 100 outb_p(reg, regPort);
101 outb_p(data, dataPort); 101 outb_p(data, dataPort);
@@ -143,7 +143,7 @@ static void ali14xx_set_pio_mode(ide_drive_t *drive, const u8 pio)
143/* 143/*
144 * Auto-detect the IDE controller port. 144 * Auto-detect the IDE controller port.
145 */ 145 */
146static int __init findPort (void) 146static int __init findPort(void)
147{ 147{
148 int i; 148 int i;
149 u8 t; 149 u8 t;
@@ -175,7 +175,8 @@ static int __init findPort (void)
175/* 175/*
176 * Initialize controller registers with default values. 176 * Initialize controller registers with default values.
177 */ 177 */
178static int __init initRegisters (void) { 178static int __init initRegisters(void)
179{
179 const RegInitializer *p; 180 const RegInitializer *p;
180 u8 t; 181 u8 t;
181 unsigned long flags; 182 unsigned long flags;
@@ -199,7 +200,8 @@ static const struct ide_port_info ali14xx_port_info = {
199 200
200static int __init ali14xx_probe(void) 201static int __init ali14xx_probe(void)
201{ 202{
202 static u8 idx[4] = { 0, 1, 0xff, 0xff }; 203 ide_hwif_t *hwif, *mate;
204 static u8 idx[4] = { 0xff, 0xff, 0xff, 0xff };
203 hw_regs_t hw[2]; 205 hw_regs_t hw[2];
204 206
205 printk(KERN_DEBUG "ali14xx: base=0x%03x, regOn=0x%02x.\n", 207 printk(KERN_DEBUG "ali14xx: base=0x%03x, regOn=0x%02x.\n",
@@ -219,18 +221,26 @@ static int __init ali14xx_probe(void)
219 ide_std_init_ports(&hw[1], 0x170, 0x376); 221 ide_std_init_ports(&hw[1], 0x170, 0x376);
220 hw[1].irq = 15; 222 hw[1].irq = 15;
221 223
222 ide_init_port_hw(&ide_hwifs[0], &hw[0]); 224 hwif = ide_find_port();
223 ide_init_port_hw(&ide_hwifs[1], &hw[1]); 225 if (hwif) {
226 ide_init_port_hw(hwif, &hw[0]);
227 hwif->set_pio_mode = &ali14xx_set_pio_mode;
228 idx[0] = hwif->index;
229 }
224 230
225 ide_hwifs[0].set_pio_mode = &ali14xx_set_pio_mode; 231 mate = ide_find_port();
226 ide_hwifs[1].set_pio_mode = &ali14xx_set_pio_mode; 232 if (mate) {
233 ide_init_port_hw(mate, &hw[1]);
234 mate->set_pio_mode = &ali14xx_set_pio_mode;
235 idx[1] = mate->index;
236 }
227 237
228 ide_device_add(idx, &ali14xx_port_info); 238 ide_device_add(idx, &ali14xx_port_info);
229 239
230 return 0; 240 return 0;
231} 241}
232 242
233int probe_ali14xx = 0; 243int probe_ali14xx;
234 244
235module_param_named(probe, probe_ali14xx, bool, 0); 245module_param_named(probe, probe_ali14xx, bool, 0);
236MODULE_PARM_DESC(probe, "probe for ALI M14xx chipsets"); 246MODULE_PARM_DESC(probe, "probe for ALI M14xx chipsets");
diff --git a/drivers/ide/legacy/buddha.c b/drivers/ide/legacy/buddha.c
index fdd3791e465f..6956eb8f2d5f 100644
--- a/drivers/ide/legacy/buddha.c
+++ b/drivers/ide/legacy/buddha.c
@@ -221,7 +221,7 @@ fail_base2:
221 221
222 buddha_setup_ports(&hw, base, ctl, irq_port, ack_intr); 222 buddha_setup_ports(&hw, base, ctl, irq_port, ack_intr);
223 223
224 hwif = ide_find_port(hw.io_ports[IDE_DATA_OFFSET]); 224 hwif = ide_find_port();
225 if (hwif) { 225 if (hwif) {
226 u8 index = hwif->index; 226 u8 index = hwif->index;
227 227
diff --git a/drivers/ide/legacy/dtc2278.c b/drivers/ide/legacy/dtc2278.c
index 5f69cd2ea6f7..9c6b3249a004 100644
--- a/drivers/ide/legacy/dtc2278.c
+++ b/drivers/ide/legacy/dtc2278.c
@@ -102,15 +102,9 @@ static int __init dtc2278_probe(void)
102{ 102{
103 unsigned long flags; 103 unsigned long flags;
104 ide_hwif_t *hwif, *mate; 104 ide_hwif_t *hwif, *mate;
105 static u8 idx[4] = { 0, 1, 0xff, 0xff }; 105 static u8 idx[4] = { 0xff, 0xff, 0xff, 0xff };
106 hw_regs_t hw[2]; 106 hw_regs_t hw[2];
107 107
108 hwif = &ide_hwifs[0];
109 mate = &ide_hwifs[1];
110
111 if (hwif->chipset != ide_unknown || mate->chipset != ide_unknown)
112 return 1;
113
114 local_irq_save(flags); 108 local_irq_save(flags);
115 /* 109 /*
116 * This enables the second interface 110 * This enables the second interface
@@ -137,10 +131,18 @@ static int __init dtc2278_probe(void)
137 ide_std_init_ports(&hw[1], 0x170, 0x376); 131 ide_std_init_ports(&hw[1], 0x170, 0x376);
138 hw[1].irq = 15; 132 hw[1].irq = 15;
139 133
140 ide_init_port_hw(hwif, &hw[0]); 134 hwif = ide_find_port();
141 ide_init_port_hw(mate, &hw[1]); 135 if (hwif) {
136 ide_init_port_hw(hwif, &hw[0]);
137 hwif->set_pio_mode = dtc2278_set_pio_mode;
138 idx[0] = hwif->index;
139 }
142 140
143 hwif->set_pio_mode = &dtc2278_set_pio_mode; 141 mate = ide_find_port();
142 if (mate) {
143 ide_init_port_hw(mate, &hw[1]);
144 idx[1] = mate->index;
145 }
144 146
145 ide_device_add(idx, &dtc2278_port_info); 147 ide_device_add(idx, &dtc2278_port_info);
146 148
diff --git a/drivers/ide/legacy/falconide.c b/drivers/ide/legacy/falconide.c
index e950afa5939c..8c9c9f7f54ca 100644
--- a/drivers/ide/legacy/falconide.c
+++ b/drivers/ide/legacy/falconide.c
@@ -22,6 +22,7 @@
22#include <asm/atariints.h> 22#include <asm/atariints.h>
23#include <asm/atari_stdma.h> 23#include <asm/atari_stdma.h>
24 24
25#define DRV_NAME "falconide"
25 26
26 /* 27 /*
27 * Base of the IDE interface 28 * Base of the IDE interface
@@ -74,15 +75,21 @@ static int __init falconide_init(void)
74 75
75 printk(KERN_INFO "ide: Falcon IDE controller\n"); 76 printk(KERN_INFO "ide: Falcon IDE controller\n");
76 77
78 if (!request_mem_region(ATA_HD_BASE, 0x40, DRV_NAME)) {
79 printk(KERN_ERR "%s: resources busy\n", DRV_NAME);
80 return -EBUSY;
81 }
82
77 falconide_setup_ports(&hw); 83 falconide_setup_ports(&hw);
78 84
79 hwif = ide_find_port(hw.io_ports[IDE_DATA_OFFSET]); 85 hwif = ide_find_port();
80 if (hwif) { 86 if (hwif) {
81 u8 index = hwif->index; 87 u8 index = hwif->index;
82 u8 idx[4] = { index, 0xff, 0xff, 0xff }; 88 u8 idx[4] = { index, 0xff, 0xff, 0xff };
83 89
84 ide_init_port_data(hwif, index); 90 ide_init_port_data(hwif, index);
85 ide_init_port_hw(hwif, &hw); 91 ide_init_port_hw(hwif, &hw);
92 hwif->mmio = 1;
86 93
87 ide_get_lock(NULL, NULL); 94 ide_get_lock(NULL, NULL);
88 ide_device_add(idx, NULL); 95 ide_device_add(idx, NULL);
diff --git a/drivers/ide/legacy/gayle.c b/drivers/ide/legacy/gayle.c
index e3b4638cc883..fcc8d52bf2a1 100644
--- a/drivers/ide/legacy/gayle.c
+++ b/drivers/ide/legacy/gayle.c
@@ -175,7 +175,7 @@ found:
175 175
176 gayle_setup_ports(&hw, base, ctrlport, irqport, ack_intr); 176 gayle_setup_ports(&hw, base, ctrlport, irqport, ack_intr);
177 177
178 hwif = ide_find_port(base); 178 hwif = ide_find_port();
179 if (hwif) { 179 if (hwif) {
180 u8 index = hwif->index; 180 u8 index = hwif->index;
181 181
diff --git a/drivers/ide/legacy/hd.c b/drivers/ide/legacy/hd.c
index 0b0d86731927..abdedf56643e 100644
--- a/drivers/ide/legacy/hd.c
+++ b/drivers/ide/legacy/hd.c
@@ -122,12 +122,12 @@ static int hd_error;
122 * This struct defines the HD's and their types. 122 * This struct defines the HD's and their types.
123 */ 123 */
124struct hd_i_struct { 124struct hd_i_struct {
125 unsigned int head,sect,cyl,wpcom,lzone,ctl; 125 unsigned int head, sect, cyl, wpcom, lzone, ctl;
126 int unit; 126 int unit;
127 int recalibrate; 127 int recalibrate;
128 int special_op; 128 int special_op;
129}; 129};
130 130
131#ifdef HD_TYPE 131#ifdef HD_TYPE
132static struct hd_i_struct hd_info[] = { HD_TYPE }; 132static struct hd_i_struct hd_info[] = { HD_TYPE };
133static int NR_HD = ARRAY_SIZE(hd_info); 133static int NR_HD = ARRAY_SIZE(hd_info);
@@ -168,7 +168,7 @@ unsigned long read_timer(void)
168 168
169 spin_lock_irqsave(&i8253_lock, flags); 169 spin_lock_irqsave(&i8253_lock, flags);
170 t = jiffies * 11932; 170 t = jiffies * 11932;
171 outb_p(0, 0x43); 171 outb_p(0, 0x43);
172 i = inb_p(0x40); 172 i = inb_p(0x40);
173 i |= inb(0x40) << 8; 173 i |= inb(0x40) << 8;
174 spin_unlock_irqrestore(&i8253_lock, flags); 174 spin_unlock_irqrestore(&i8253_lock, flags);
@@ -183,7 +183,7 @@ static void __init hd_setup(char *str, int *ints)
183 if (ints[0] != 3) 183 if (ints[0] != 3)
184 return; 184 return;
185 if (hd_info[0].head != 0) 185 if (hd_info[0].head != 0)
186 hdind=1; 186 hdind = 1;
187 hd_info[hdind].head = ints[2]; 187 hd_info[hdind].head = ints[2];
188 hd_info[hdind].sect = ints[3]; 188 hd_info[hdind].sect = ints[3];
189 hd_info[hdind].cyl = ints[1]; 189 hd_info[hdind].cyl = ints[1];
@@ -193,7 +193,7 @@ static void __init hd_setup(char *str, int *ints)
193 NR_HD = hdind+1; 193 NR_HD = hdind+1;
194} 194}
195 195
196static void dump_status (const char *msg, unsigned int stat) 196static void dump_status(const char *msg, unsigned int stat)
197{ 197{
198 char *name = "hd?"; 198 char *name = "hd?";
199 if (CURRENT) 199 if (CURRENT)
@@ -291,7 +291,6 @@ static int controller_ready(unsigned int drive, unsigned int head)
291 return 0; 291 return 0;
292} 292}
293 293
294
295static void hd_out(struct hd_i_struct *disk, 294static void hd_out(struct hd_i_struct *disk,
296 unsigned int nsect, 295 unsigned int nsect,
297 unsigned int sect, 296 unsigned int sect,
@@ -313,15 +312,15 @@ static void hd_out(struct hd_i_struct *disk,
313 return; 312 return;
314 } 313 }
315 SET_HANDLER(intr_addr); 314 SET_HANDLER(intr_addr);
316 outb_p(disk->ctl,HD_CMD); 315 outb_p(disk->ctl, HD_CMD);
317 port=HD_DATA; 316 port = HD_DATA;
318 outb_p(disk->wpcom>>2,++port); 317 outb_p(disk->wpcom >> 2, ++port);
319 outb_p(nsect,++port); 318 outb_p(nsect, ++port);
320 outb_p(sect,++port); 319 outb_p(sect, ++port);
321 outb_p(cyl,++port); 320 outb_p(cyl, ++port);
322 outb_p(cyl>>8,++port); 321 outb_p(cyl >> 8, ++port);
323 outb_p(0xA0|(disk->unit<<4)|head,++port); 322 outb_p(0xA0 | (disk->unit << 4) | head, ++port);
324 outb_p(cmd,++port); 323 outb_p(cmd, ++port);
325} 324}
326 325
327static void hd_request (void); 326static void hd_request (void);
@@ -344,14 +343,14 @@ static void reset_controller(void)
344{ 343{
345 int i; 344 int i;
346 345
347 outb_p(4,HD_CMD); 346 outb_p(4, HD_CMD);
348 for(i = 0; i < 1000; i++) barrier(); 347 for (i = 0; i < 1000; i++) barrier();
349 outb_p(hd_info[0].ctl & 0x0f,HD_CMD); 348 outb_p(hd_info[0].ctl & 0x0f, HD_CMD);
350 for(i = 0; i < 1000; i++) barrier(); 349 for (i = 0; i < 1000; i++) barrier();
351 if (drive_busy()) 350 if (drive_busy())
352 printk("hd: controller still busy\n"); 351 printk("hd: controller still busy\n");
353 else if ((hd_error = inb(HD_ERROR)) != 1) 352 else if ((hd_error = inb(HD_ERROR)) != 1)
354 printk("hd: controller reset failed: %02x\n",hd_error); 353 printk("hd: controller reset failed: %02x\n", hd_error);
355} 354}
356 355
357static void reset_hd(void) 356static void reset_hd(void)
@@ -371,8 +370,8 @@ repeat:
371 if (++i < NR_HD) { 370 if (++i < NR_HD) {
372 struct hd_i_struct *disk = &hd_info[i]; 371 struct hd_i_struct *disk = &hd_info[i];
373 disk->special_op = disk->recalibrate = 1; 372 disk->special_op = disk->recalibrate = 1;
374 hd_out(disk,disk->sect,disk->sect,disk->head-1, 373 hd_out(disk, disk->sect, disk->sect, disk->head-1,
375 disk->cyl,WIN_SPECIFY,&reset_hd); 374 disk->cyl, WIN_SPECIFY, &reset_hd);
376 if (reset) 375 if (reset)
377 goto repeat; 376 goto repeat;
378 } else 377 } else
@@ -393,7 +392,7 @@ static void unexpected_hd_interrupt(void)
393 unsigned int stat = inb_p(HD_STATUS); 392 unsigned int stat = inb_p(HD_STATUS);
394 393
395 if (stat & (BUSY_STAT|DRQ_STAT|ECC_STAT|ERR_STAT)) { 394 if (stat & (BUSY_STAT|DRQ_STAT|ECC_STAT|ERR_STAT)) {
396 dump_status ("unexpected interrupt", stat); 395 dump_status("unexpected interrupt", stat);
397 SET_TIMER; 396 SET_TIMER;
398 } 397 }
399} 398}
@@ -453,7 +452,7 @@ static void read_intr(void)
453 return; 452 return;
454ok_to_read: 453ok_to_read:
455 req = CURRENT; 454 req = CURRENT;
456 insw(HD_DATA,req->buffer,256); 455 insw(HD_DATA, req->buffer, 256);
457 req->sector++; 456 req->sector++;
458 req->buffer += 512; 457 req->buffer += 512;
459 req->errors = 0; 458 req->errors = 0;
@@ -507,7 +506,7 @@ ok_to_write:
507 end_request(req, 1); 506 end_request(req, 1);
508 if (i > 0) { 507 if (i > 0) {
509 SET_HANDLER(&write_intr); 508 SET_HANDLER(&write_intr);
510 outsw(HD_DATA,req->buffer,256); 509 outsw(HD_DATA, req->buffer, 256);
511 local_irq_enable(); 510 local_irq_enable();
512 } else { 511 } else {
513#if (HD_DELAY > 0) 512#if (HD_DELAY > 0)
@@ -560,11 +559,11 @@ static int do_special_op(struct hd_i_struct *disk, struct request *req)
560{ 559{
561 if (disk->recalibrate) { 560 if (disk->recalibrate) {
562 disk->recalibrate = 0; 561 disk->recalibrate = 0;
563 hd_out(disk,disk->sect,0,0,0,WIN_RESTORE,&recal_intr); 562 hd_out(disk, disk->sect, 0, 0, 0, WIN_RESTORE, &recal_intr);
564 return reset; 563 return reset;
565 } 564 }
566 if (disk->head > 16) { 565 if (disk->head > 16) {
567 printk ("%s: cannot handle device with more than 16 heads - giving up\n", req->rq_disk->disk_name); 566 printk("%s: cannot handle device with more than 16 heads - giving up\n", req->rq_disk->disk_name);
568 end_request(req, 0); 567 end_request(req, 0);
569 } 568 }
570 disk->special_op = 0; 569 disk->special_op = 0;
@@ -633,19 +632,21 @@ repeat:
633 if (blk_fs_request(req)) { 632 if (blk_fs_request(req)) {
634 switch (rq_data_dir(req)) { 633 switch (rq_data_dir(req)) {
635 case READ: 634 case READ:
636 hd_out(disk,nsect,sec,head,cyl,WIN_READ,&read_intr); 635 hd_out(disk, nsect, sec, head, cyl, WIN_READ,
636 &read_intr);
637 if (reset) 637 if (reset)
638 goto repeat; 638 goto repeat;
639 break; 639 break;
640 case WRITE: 640 case WRITE:
641 hd_out(disk,nsect,sec,head,cyl,WIN_WRITE,&write_intr); 641 hd_out(disk, nsect, sec, head, cyl, WIN_WRITE,
642 &write_intr);
642 if (reset) 643 if (reset)
643 goto repeat; 644 goto repeat;
644 if (wait_DRQ()) { 645 if (wait_DRQ()) {
645 bad_rw_intr(); 646 bad_rw_intr();
646 goto repeat; 647 goto repeat;
647 } 648 }
648 outsw(HD_DATA,req->buffer,256); 649 outsw(HD_DATA, req->buffer, 256);
649 break; 650 break;
650 default: 651 default:
651 printk("unknown hd-command\n"); 652 printk("unknown hd-command\n");
@@ -655,7 +656,7 @@ repeat:
655 } 656 }
656} 657}
657 658
658static void do_hd_request (struct request_queue * q) 659static void do_hd_request(struct request_queue *q)
659{ 660{
660 disable_irq(HD_IRQ); 661 disable_irq(HD_IRQ);
661 hd_request(); 662 hd_request();
@@ -708,12 +709,12 @@ static int __init hd_init(void)
708{ 709{
709 int drive; 710 int drive;
710 711
711 if (register_blkdev(MAJOR_NR,"hd")) 712 if (register_blkdev(MAJOR_NR, "hd"))
712 return -1; 713 return -1;
713 714
714 hd_queue = blk_init_queue(do_hd_request, &hd_lock); 715 hd_queue = blk_init_queue(do_hd_request, &hd_lock);
715 if (!hd_queue) { 716 if (!hd_queue) {
716 unregister_blkdev(MAJOR_NR,"hd"); 717 unregister_blkdev(MAJOR_NR, "hd");
717 return -ENOMEM; 718 return -ENOMEM;
718 } 719 }
719 720
@@ -742,7 +743,7 @@ static int __init hd_init(void)
742 goto out; 743 goto out;
743 } 744 }
744 745
745 for (drive=0 ; drive < NR_HD ; drive++) { 746 for (drive = 0 ; drive < NR_HD ; drive++) {
746 struct gendisk *disk = alloc_disk(64); 747 struct gendisk *disk = alloc_disk(64);
747 struct hd_i_struct *p = &hd_info[drive]; 748 struct hd_i_struct *p = &hd_info[drive];
748 if (!disk) 749 if (!disk)
@@ -756,7 +757,7 @@ static int __init hd_init(void)
756 disk->queue = hd_queue; 757 disk->queue = hd_queue;
757 p->unit = drive; 758 p->unit = drive;
758 hd_gendisk[drive] = disk; 759 hd_gendisk[drive] = disk;
759 printk ("%s: %luMB, CHS=%d/%d/%d\n", 760 printk("%s: %luMB, CHS=%d/%d/%d\n",
760 disk->disk_name, (unsigned long)get_capacity(disk)/2048, 761 disk->disk_name, (unsigned long)get_capacity(disk)/2048,
761 p->cyl, p->head, p->sect); 762 p->cyl, p->head, p->sect);
762 } 763 }
@@ -776,7 +777,7 @@ static int __init hd_init(void)
776 } 777 }
777 778
778 /* Let them fly */ 779 /* Let them fly */
779 for(drive=0; drive < NR_HD; drive++) 780 for (drive = 0; drive < NR_HD; drive++)
780 add_disk(hd_gendisk[drive]); 781 add_disk(hd_gendisk[drive]);
781 782
782 return 0; 783 return 0;
@@ -791,7 +792,7 @@ out1:
791 NR_HD = 0; 792 NR_HD = 0;
792out: 793out:
793 del_timer(&device_timer); 794 del_timer(&device_timer);
794 unregister_blkdev(MAJOR_NR,"hd"); 795 unregister_blkdev(MAJOR_NR, "hd");
795 blk_cleanup_queue(hd_queue); 796 blk_cleanup_queue(hd_queue);
796 return -1; 797 return -1;
797Enomem: 798Enomem:
@@ -800,7 +801,8 @@ Enomem:
800 goto out; 801 goto out;
801} 802}
802 803
803static int __init parse_hd_setup (char *line) { 804static int __init parse_hd_setup(char *line)
805{
804 int ints[6]; 806 int ints[6];
805 807
806 (void) get_options(line, ARRAY_SIZE(ints), ints); 808 (void) get_options(line, ARRAY_SIZE(ints), ints);
diff --git a/drivers/ide/legacy/ht6560b.c b/drivers/ide/legacy/ht6560b.c
index 88fe9070c9c3..60f52f5158c9 100644
--- a/drivers/ide/legacy/ht6560b.c
+++ b/drivers/ide/legacy/ht6560b.c
@@ -35,6 +35,7 @@
35 * Try: http://www.maf.iki.fi/~maf/ht6560b/ 35 * Try: http://www.maf.iki.fi/~maf/ht6560b/
36 */ 36 */
37 37
38#define DRV_NAME "ht6560b"
38#define HT6560B_VERSION "v0.08" 39#define HT6560B_VERSION "v0.08"
39 40
40#include <linux/module.h> 41#include <linux/module.h>
@@ -339,16 +340,13 @@ static const struct ide_port_info ht6560b_port_info __initdata = {
339static int __init ht6560b_init(void) 340static int __init ht6560b_init(void)
340{ 341{
341 ide_hwif_t *hwif, *mate; 342 ide_hwif_t *hwif, *mate;
342 static u8 idx[4] = { 0, 1, 0xff, 0xff }; 343 static u8 idx[4] = { 0xff, 0xff, 0xff, 0xff };
343 hw_regs_t hw[2]; 344 hw_regs_t hw[2];
344 345
345 if (probe_ht6560b == 0) 346 if (probe_ht6560b == 0)
346 return -ENODEV; 347 return -ENODEV;
347 348
348 hwif = &ide_hwifs[0]; 349 if (!request_region(HT_CONFIG_PORT, 1, DRV_NAME)) {
349 mate = &ide_hwifs[1];
350
351 if (!request_region(HT_CONFIG_PORT, 1, hwif->name)) {
352 printk(KERN_NOTICE "%s: HT_CONFIG_PORT not found\n", 350 printk(KERN_NOTICE "%s: HT_CONFIG_PORT not found\n",
353 __FUNCTION__); 351 __FUNCTION__);
354 return -ENODEV; 352 return -ENODEV;
@@ -367,17 +365,23 @@ static int __init ht6560b_init(void)
367 ide_std_init_ports(&hw[1], 0x170, 0x376); 365 ide_std_init_ports(&hw[1], 0x170, 0x376);
368 hw[1].irq = 15; 366 hw[1].irq = 15;
369 367
370 ide_init_port_hw(hwif, &hw[0]); 368 hwif = ide_find_port();
371 ide_init_port_hw(mate, &hw[1]); 369 if (hwif) {
372 370 ide_init_port_hw(hwif, &hw[0]);
373 hwif->selectproc = &ht6560b_selectproc; 371 hwif->selectproc = ht6560b_selectproc;
374 hwif->set_pio_mode = &ht6560b_set_pio_mode; 372 hwif->set_pio_mode = ht6560b_set_pio_mode;
375 373 hwif->port_init_devs = ht6560b_port_init_devs;
376 mate->selectproc = &ht6560b_selectproc; 374 idx[0] = hwif->index;
377 mate->set_pio_mode = &ht6560b_set_pio_mode; 375 }
378 376
379 hwif->port_init_devs = ht6560b_port_init_devs; 377 mate = ide_find_port();
380 mate->port_init_devs = ht6560b_port_init_devs; 378 if (mate) {
379 ide_init_port_hw(mate, &hw[1]);
380 mate->selectproc = ht6560b_selectproc;
381 mate->set_pio_mode = ht6560b_set_pio_mode;
382 mate->port_init_devs = ht6560b_port_init_devs;
383 idx[1] = mate->index;
384 }
381 385
382 ide_device_add(idx, &ht6560b_port_info); 386 ide_device_add(idx, &ht6560b_port_info);
383 387
diff --git a/drivers/ide/legacy/ide-4drives.c b/drivers/ide/legacy/ide-4drives.c
index ecd7f3553554..c352f12348af 100644
--- a/drivers/ide/legacy/ide-4drives.c
+++ b/drivers/ide/legacy/ide-4drives.c
@@ -4,7 +4,7 @@
4#include <linux/module.h> 4#include <linux/module.h>
5#include <linux/ide.h> 5#include <linux/ide.h>
6 6
7int probe_4drives = 0; 7int probe_4drives;
8 8
9module_param_named(probe, probe_4drives, bool, 0); 9module_param_named(probe, probe_4drives, bool, 0);
10MODULE_PARM_DESC(probe, "probe for generic IDE chipset with 4 drives/port"); 10MODULE_PARM_DESC(probe, "probe for generic IDE chipset with 4 drives/port");
@@ -12,31 +12,37 @@ MODULE_PARM_DESC(probe, "probe for generic IDE chipset with 4 drives/port");
12static int __init ide_4drives_init(void) 12static int __init ide_4drives_init(void)
13{ 13{
14 ide_hwif_t *hwif, *mate; 14 ide_hwif_t *hwif, *mate;
15 u8 idx[4] = { 0, 1, 0xff, 0xff }; 15 u8 idx[4] = { 0xff, 0xff, 0xff, 0xff };
16 hw_regs_t hw; 16 hw_regs_t hw;
17 17
18 if (probe_4drives == 0) 18 if (probe_4drives == 0)
19 return -ENODEV; 19 return -ENODEV;
20 20
21 hwif = &ide_hwifs[0];
22 mate = &ide_hwifs[1];
23
24 memset(&hw, 0, sizeof(hw)); 21 memset(&hw, 0, sizeof(hw));
25 22
26 ide_std_init_ports(&hw, 0x1f0, 0x3f6); 23 ide_std_init_ports(&hw, 0x1f0, 0x3f6);
27 hw.irq = 14; 24 hw.irq = 14;
28 hw.chipset = ide_4drives; 25 hw.chipset = ide_4drives;
29 26
30 ide_init_port_hw(hwif, &hw); 27 hwif = ide_find_port();
31 ide_init_port_hw(mate, &hw); 28 if (hwif) {
32 29 ide_init_port_hw(hwif, &hw);
33 mate->drives[0].select.all ^= 0x20; 30 idx[0] = hwif->index;
34 mate->drives[1].select.all ^= 0x20; 31 }
35 32
36 hwif->mate = mate; 33 mate = ide_find_port();
37 mate->mate = hwif; 34 if (mate) {
38 35 ide_init_port_hw(mate, &hw);
39 hwif->serialized = mate->serialized = 1; 36 mate->drives[0].select.all ^= 0x20;
37 mate->drives[1].select.all ^= 0x20;
38 idx[1] = mate->index;
39
40 if (hwif) {
41 hwif->mate = mate;
42 mate->mate = hwif;
43 hwif->serialized = mate->serialized = 1;
44 }
45 }
40 46
41 ide_device_add(idx, NULL); 47 ide_device_add(idx, NULL);
42 48
diff --git a/drivers/ide/legacy/ide-cs.c b/drivers/ide/legacy/ide-cs.c
index 9a23b94f2939..b97b8d51b3eb 100644
--- a/drivers/ide/legacy/ide-cs.c
+++ b/drivers/ide/legacy/ide-cs.c
@@ -156,7 +156,7 @@ static int idecs_register(unsigned long io, unsigned long ctl, unsigned long irq
156 hw.chipset = ide_pci; 156 hw.chipset = ide_pci;
157 hw.dev = &handle->dev; 157 hw.dev = &handle->dev;
158 158
159 hwif = ide_find_port(hw.io_ports[IDE_DATA_OFFSET]); 159 hwif = ide_find_port();
160 if (hwif == NULL) 160 if (hwif == NULL)
161 return -1; 161 return -1;
162 162
diff --git a/drivers/ide/legacy/ide_platform.c b/drivers/ide/legacy/ide_platform.c
index 361b1bb544bf..bf240775531e 100644
--- a/drivers/ide/legacy/ide_platform.c
+++ b/drivers/ide/legacy/ide_platform.c
@@ -89,7 +89,7 @@ static int __devinit plat_ide_probe(struct platform_device *pdev)
89 res_alt->start, res_alt->end - res_alt->start + 1); 89 res_alt->start, res_alt->end - res_alt->start + 1);
90 } 90 }
91 91
92 hwif = ide_find_port((unsigned long)base); 92 hwif = ide_find_port();
93 if (!hwif) { 93 if (!hwif) {
94 ret = -ENODEV; 94 ret = -ENODEV;
95 goto out; 95 goto out;
@@ -100,11 +100,10 @@ static int __devinit plat_ide_probe(struct platform_device *pdev)
100 hw.dev = &pdev->dev; 100 hw.dev = &pdev->dev;
101 101
102 ide_init_port_hw(hwif, &hw); 102 ide_init_port_hw(hwif, &hw);
103 hwif->mmio = 1;
103 104
104 if (mmio) { 105 if (mmio)
105 hwif->mmio = 1;
106 default_hwif_mmiops(hwif); 106 default_hwif_mmiops(hwif);
107 }
108 107
109 idx[0] = hwif->index; 108 idx[0] = hwif->index;
110 109
diff --git a/drivers/ide/legacy/macide.c b/drivers/ide/legacy/macide.c
index eaf5dbe58bc2..7429b80cb089 100644
--- a/drivers/ide/legacy/macide.c
+++ b/drivers/ide/legacy/macide.c
@@ -120,7 +120,7 @@ static int __init macide_init(void)
120 120
121 macide_setup_ports(&hw, base, irq, ack_intr); 121 macide_setup_ports(&hw, base, irq, ack_intr);
122 122
123 hwif = ide_find_port(hw.io_ports[IDE_DATA_OFFSET]); 123 hwif = ide_find_port();
124 if (hwif) { 124 if (hwif) {
125 u8 index = hwif->index; 125 u8 index = hwif->index;
126 u8 idx[4] = { index, 0xff, 0xff, 0xff }; 126 u8 idx[4] = { index, 0xff, 0xff, 0xff };
diff --git a/drivers/ide/legacy/q40ide.c b/drivers/ide/legacy/q40ide.c
index 2da28759686e..fcbff0eced1b 100644
--- a/drivers/ide/legacy/q40ide.c
+++ b/drivers/ide/legacy/q40ide.c
@@ -137,7 +137,7 @@ static int __init q40ide_init(void)
137// m68kide_iops, 137// m68kide_iops,
138 q40ide_default_irq(pcide_bases[i])); 138 q40ide_default_irq(pcide_bases[i]));
139 139
140 hwif = ide_find_port(hw.io_ports[IDE_DATA_OFFSET]); 140 hwif = ide_find_port();
141 if (hwif) { 141 if (hwif) {
142 ide_init_port_data(hwif, hwif->index); 142 ide_init_port_data(hwif, hwif->index);
143 ide_init_port_hw(hwif, &hw); 143 ide_init_port_hw(hwif, &hw);
diff --git a/drivers/ide/legacy/qd65xx.c b/drivers/ide/legacy/qd65xx.c
index 7016bdf4fcc1..6e820c7c5c6b 100644
--- a/drivers/ide/legacy/qd65xx.c
+++ b/drivers/ide/legacy/qd65xx.c
@@ -88,12 +88,12 @@
88static int timings[4]={-1,-1,-1,-1}; /* stores current timing for each timer */ 88static int timings[4]={-1,-1,-1,-1}; /* stores current timing for each timer */
89 89
90/* 90/*
91 * qd_select: 91 * qd65xx_select:
92 * 92 *
93 * This routine is invoked from ide.c to prepare for access to a given drive. 93 * This routine is invoked to prepare for access to a given drive.
94 */ 94 */
95 95
96static void qd_select (ide_drive_t *drive) 96static void qd65xx_select(ide_drive_t *drive)
97{ 97{
98 u8 index = (( (QD_TIMREG(drive)) & 0x80 ) >> 7) | 98 u8 index = (( (QD_TIMREG(drive)) & 0x80 ) >> 7) |
99 (QD_TIMREG(drive) & 0x02); 99 (QD_TIMREG(drive) & 0x02);
@@ -168,36 +168,15 @@ static int qd_find_disk_type (ide_drive_t *drive,
168} 168}
169 169
170/* 170/*
171 * qd_timing_ok:
172 *
173 * check whether timings don't conflict
174 */
175
176static int qd_timing_ok (ide_drive_t drives[])
177{
178 return (IDE_IMPLY(drives[0].present && drives[1].present,
179 IDE_IMPLY(QD_TIMREG(drives) == QD_TIMREG(drives+1),
180 QD_TIMING(drives) == QD_TIMING(drives+1))));
181 /* if same timing register, must be same timing */
182}
183
184/*
185 * qd_set_timing: 171 * qd_set_timing:
186 * 172 *
187 * records the timing, and enables selectproc as needed 173 * records the timing
188 */ 174 */
189 175
190static void qd_set_timing (ide_drive_t *drive, u8 timing) 176static void qd_set_timing (ide_drive_t *drive, u8 timing)
191{ 177{
192 ide_hwif_t *hwif = HWIF(drive);
193
194 drive->drive_data &= 0xff00; 178 drive->drive_data &= 0xff00;
195 drive->drive_data |= timing; 179 drive->drive_data |= timing;
196 if (qd_timing_ok(hwif->drives)) {
197 qd_select(drive); /* selects once */
198 hwif->selectproc = NULL;
199 } else
200 hwif->selectproc = &qd_select;
201 180
202 printk(KERN_DEBUG "%s: %#x\n", drive->name, timing); 181 printk(KERN_DEBUG "%s: %#x\n", drive->name, timing);
203} 182}
@@ -225,10 +204,11 @@ static void qd6500_set_pio_mode(ide_drive_t *drive, const u8 pio)
225 204
226static void qd6580_set_pio_mode(ide_drive_t *drive, const u8 pio) 205static void qd6580_set_pio_mode(ide_drive_t *drive, const u8 pio)
227{ 206{
228 int base = HWIF(drive)->select_data; 207 ide_hwif_t *hwif = drive->hwif;
229 unsigned int cycle_time; 208 unsigned int cycle_time;
230 int active_time = 175; 209 int active_time = 175;
231 int recovery_time = 415; /* worst case values from the dos driver */ 210 int recovery_time = 415; /* worst case values from the dos driver */
211 u8 base = (hwif->config_data & 0xff00) >> 8;
232 212
233 if (drive->id && !qd_find_disk_type(drive, &active_time, &recovery_time)) { 213 if (drive->id && !qd_find_disk_type(drive, &active_time, &recovery_time)) {
234 cycle_time = ide_pio_cycle_time(drive, pio); 214 cycle_time = ide_pio_cycle_time(drive, pio);
@@ -299,21 +279,10 @@ static int __init qd_testreg(int port)
299 return (readreg != QD_TESTVAL); 279 return (readreg != QD_TESTVAL);
300} 280}
301 281
302/*
303 * qd_setup:
304 *
305 * called to setup an ata channel : adjusts attributes & links for tuning
306 */
307
308static void __init qd_setup(ide_hwif_t *hwif, int base, int config)
309{
310 hwif->select_data = base;
311 hwif->config_data = config;
312}
313
314static void __init qd6500_port_init_devs(ide_hwif_t *hwif) 282static void __init qd6500_port_init_devs(ide_hwif_t *hwif)
315{ 283{
316 u8 base = hwif->select_data, config = QD_CONFIG(hwif); 284 u8 base = (hwif->config_data & 0xff00) >> 8;
285 u8 config = QD_CONFIG(hwif);
317 286
318 hwif->drives[0].drive_data = QD6500_DEF_DATA; 287 hwif->drives[0].drive_data = QD6500_DEF_DATA;
319 hwif->drives[1].drive_data = QD6500_DEF_DATA; 288 hwif->drives[1].drive_data = QD6500_DEF_DATA;
@@ -322,9 +291,10 @@ static void __init qd6500_port_init_devs(ide_hwif_t *hwif)
322static void __init qd6580_port_init_devs(ide_hwif_t *hwif) 291static void __init qd6580_port_init_devs(ide_hwif_t *hwif)
323{ 292{
324 u16 t1, t2; 293 u16 t1, t2;
325 u8 base = hwif->select_data, config = QD_CONFIG(hwif); 294 u8 base = (hwif->config_data & 0xff00) >> 8;
295 u8 config = QD_CONFIG(hwif);
326 296
327 if (QD_CONTROL(hwif) & QD_CONTR_SEC_DISABLED) { 297 if (hwif->host_flags & IDE_HFLAG_SINGLE) {
328 t1 = QD6580_DEF_DATA; 298 t1 = QD6580_DEF_DATA;
329 t2 = QD6580_DEF_DATA2; 299 t2 = QD6580_DEF_DATA2;
330 } else 300 } else
@@ -355,14 +325,18 @@ static int __init qd_probe(int base)
355 u8 config, unit; 325 u8 config, unit;
356 u8 idx[4] = { 0xff, 0xff, 0xff, 0xff }; 326 u8 idx[4] = { 0xff, 0xff, 0xff, 0xff };
357 hw_regs_t hw[2]; 327 hw_regs_t hw[2];
328 struct ide_port_info d = qd65xx_port_info;
358 329
359 config = inb(QD_CONFIG_PORT); 330 config = inb(QD_CONFIG_PORT);
360 331
361 if (! ((config & QD_CONFIG_BASEPORT) >> 1 == (base == 0xb0)) ) 332 if (! ((config & QD_CONFIG_BASEPORT) >> 1 == (base == 0xb0)) )
362 return 1; 333 return -ENODEV;
363 334
364 unit = ! (config & QD_CONFIG_IDE_BASEPORT); 335 unit = ! (config & QD_CONFIG_IDE_BASEPORT);
365 336
337 if (unit)
338 d.host_flags |= IDE_HFLAG_QD_2ND_PORT;
339
366 memset(&hw, 0, sizeof(hw)); 340 memset(&hw, 0, sizeof(hw));
367 341
368 ide_std_init_ports(&hw[0], 0x1f0, 0x3f6); 342 ide_std_init_ports(&hw[0], 0x1f0, 0x3f6);
@@ -373,30 +347,37 @@ static int __init qd_probe(int base)
373 347
374 if ((config & 0xf0) == QD_CONFIG_QD6500) { 348 if ((config & 0xf0) == QD_CONFIG_QD6500) {
375 349
376 if (qd_testreg(base)) return 1; /* bad register */ 350 if (qd_testreg(base))
351 return -ENODEV; /* bad register */
377 352
378 /* qd6500 found */ 353 /* qd6500 found */
379 354
380 hwif = &ide_hwifs[unit];
381 printk(KERN_NOTICE "%s: qd6500 at %#x\n", hwif->name, base);
382 printk(KERN_DEBUG "qd6500: config=%#x, ID3=%u\n",
383 config, QD_ID3);
384
385 if (config & QD_CONFIG_DISABLED) { 355 if (config & QD_CONFIG_DISABLED) {
386 printk(KERN_WARNING "qd6500 is disabled !\n"); 356 printk(KERN_WARNING "qd6500 is disabled !\n");
387 return 1; 357 return -ENODEV;
388 } 358 }
389 359
360 printk(KERN_NOTICE "qd6500 at %#x\n", base);
361 printk(KERN_DEBUG "qd6500: config=%#x, ID3=%u\n",
362 config, QD_ID3);
363
364 d.host_flags |= IDE_HFLAG_SINGLE;
365
366 hwif = ide_find_port_slot(&d);
367 if (hwif == NULL)
368 return -ENOENT;
369
390 ide_init_port_hw(hwif, &hw[unit]); 370 ide_init_port_hw(hwif, &hw[unit]);
391 371
392 qd_setup(hwif, base, config); 372 hwif->config_data = (base << 8) | config;
393 373
394 hwif->port_init_devs = qd6500_port_init_devs; 374 hwif->port_init_devs = qd6500_port_init_devs;
395 hwif->set_pio_mode = &qd6500_set_pio_mode; 375 hwif->set_pio_mode = qd6500_set_pio_mode;
376 hwif->selectproc = qd65xx_select;
396 377
397 idx[unit] = unit; 378 idx[unit] = hwif->index;
398 379
399 ide_device_add(idx, &qd65xx_port_info); 380 ide_device_add(idx, &d);
400 381
401 return 1; 382 return 1;
402 } 383 }
@@ -406,8 +387,8 @@ static int __init qd_probe(int base)
406 387
407 u8 control; 388 u8 control;
408 389
409 if (qd_testreg(base) || qd_testreg(base+0x02)) return 1; 390 if (qd_testreg(base) || qd_testreg(base + 0x02))
410 /* bad registers */ 391 return -ENODEV; /* bad registers */
411 392
412 /* qd6580 found */ 393 /* qd6580 found */
413 394
@@ -422,46 +403,52 @@ static int __init qd_probe(int base)
422 if (control & QD_CONTR_SEC_DISABLED) { 403 if (control & QD_CONTR_SEC_DISABLED) {
423 /* secondary disabled */ 404 /* secondary disabled */
424 405
425 hwif = &ide_hwifs[unit]; 406 printk(KERN_INFO "qd6580: single IDE board\n");
426 printk(KERN_INFO "%s: qd6580: single IDE board\n", 407
427 hwif->name); 408 d.host_flags |= IDE_HFLAG_SINGLE;
409
410 hwif = ide_find_port_slot(&d);
411 if (hwif == NULL)
412 return -ENOENT;
428 413
429 ide_init_port_hw(hwif, &hw[unit]); 414 ide_init_port_hw(hwif, &hw[unit]);
430 415
431 qd_setup(hwif, base, config | (control << 8)); 416 hwif->config_data = (base << 8) | config;
432 417
433 hwif->port_init_devs = qd6580_port_init_devs; 418 hwif->port_init_devs = qd6580_port_init_devs;
434 hwif->set_pio_mode = &qd6580_set_pio_mode; 419 hwif->set_pio_mode = qd6580_set_pio_mode;
420 hwif->selectproc = qd65xx_select;
435 421
436 idx[unit] = unit; 422 idx[unit] = hwif->index;
437 423
438 ide_device_add(idx, &qd65xx_port_info); 424 ide_device_add(idx, &d);
439 425
440 return 1; 426 return 1;
441 } else { 427 } else {
442 ide_hwif_t *mate; 428 ide_hwif_t *mate;
443 429
444 hwif = &ide_hwifs[0];
445 mate = &ide_hwifs[1];
446 /* secondary enabled */ 430 /* secondary enabled */
447 printk(KERN_INFO "%s&%s: qd6580: dual IDE board\n", 431 printk(KERN_INFO "qd6580: dual IDE board\n");
448 hwif->name, mate->name); 432
449 433 hwif = ide_find_port();
450 ide_init_port_hw(hwif, &hw[0]); 434 if (hwif) {
451 ide_init_port_hw(mate, &hw[1]); 435 ide_init_port_hw(hwif, &hw[0]);
452 436 hwif->config_data = (base << 8) | config;
453 qd_setup(hwif, base, config | (control << 8)); 437 hwif->port_init_devs = qd6580_port_init_devs;
454 438 hwif->set_pio_mode = qd6580_set_pio_mode;
455 hwif->port_init_devs = qd6580_port_init_devs; 439 hwif->selectproc = qd65xx_select;
456 hwif->set_pio_mode = &qd6580_set_pio_mode; 440 idx[0] = hwif->index;
457 441 }
458 qd_setup(mate, base, config | (control << 8)); 442
459 443 mate = ide_find_port();
460 mate->port_init_devs = qd6580_port_init_devs; 444 if (mate) {
461 mate->set_pio_mode = &qd6580_set_pio_mode; 445 ide_init_port_hw(mate, &hw[1]);
462 446 mate->config_data = (base << 8) | config;
463 idx[0] = 0; 447 mate->port_init_devs = qd6580_port_init_devs;
464 idx[1] = 1; 448 mate->set_pio_mode = qd6580_set_pio_mode;
449 mate->selectproc = qd65xx_select;
450 idx[1] = mate->index;
451 }
465 452
466 ide_device_add(idx, &qd65xx_port_info); 453 ide_device_add(idx, &qd65xx_port_info);
467 454
@@ -469,7 +456,7 @@ static int __init qd_probe(int base)
469 } 456 }
470 } 457 }
471 /* no qd65xx found */ 458 /* no qd65xx found */
472 return 1; 459 return -ENODEV;
473} 460}
474 461
475int probe_qd65xx = 0; 462int probe_qd65xx = 0;
@@ -479,14 +466,18 @@ MODULE_PARM_DESC(probe, "probe for QD65xx chipsets");
479 466
480static int __init qd65xx_init(void) 467static int __init qd65xx_init(void)
481{ 468{
469 int rc1, rc2 = -ENODEV;
470
482 if (probe_qd65xx == 0) 471 if (probe_qd65xx == 0)
483 return -ENODEV; 472 return -ENODEV;
484 473
485 if (qd_probe(0x30)) 474 rc1 = qd_probe(0x30);
486 qd_probe(0xb0); 475 if (rc1)
487 if (ide_hwifs[0].chipset != ide_qd65xx && 476 rc2 = qd_probe(0xb0);
488 ide_hwifs[1].chipset != ide_qd65xx) 477
478 if (rc1 < 0 && rc2 < 0)
489 return -ENODEV; 479 return -ENODEV;
480
490 return 0; 481 return 0;
491} 482}
492 483
diff --git a/drivers/ide/legacy/qd65xx.h b/drivers/ide/legacy/qd65xx.h
index 28dd50a15d55..c83dea85e621 100644
--- a/drivers/ide/legacy/qd65xx.h
+++ b/drivers/ide/legacy/qd65xx.h
@@ -30,7 +30,6 @@
30#define QD_ID3 ((config & QD_CONFIG_ID3)!=0) 30#define QD_ID3 ((config & QD_CONFIG_ID3)!=0)
31 31
32#define QD_CONFIG(hwif) ((hwif)->config_data & 0x00ff) 32#define QD_CONFIG(hwif) ((hwif)->config_data & 0x00ff)
33#define QD_CONTROL(hwif) (((hwif)->config_data & 0xff00) >> 8)
34 33
35#define QD_TIMING(drive) (byte)(((drive)->drive_data) & 0x00ff) 34#define QD_TIMING(drive) (byte)(((drive)->drive_data) & 0x00ff)
36#define QD_TIMREG(drive) (byte)((((drive)->drive_data) & 0xff00) >> 8) 35#define QD_TIMREG(drive) (byte)((((drive)->drive_data) & 0xff00) >> 8)
diff --git a/drivers/ide/legacy/umc8672.c b/drivers/ide/legacy/umc8672.c
index bc1944811b99..4d90badd2bda 100644
--- a/drivers/ide/legacy/umc8672.c
+++ b/drivers/ide/legacy/umc8672.c
@@ -19,7 +19,7 @@
19 */ 19 */
20 20
21/* 21/*
22 * VLB Controller Support from 22 * VLB Controller Support from
23 * Wolfram Podien 23 * Wolfram Podien
24 * Rohoefe 3 24 * Rohoefe 3
25 * D28832 Achim 25 * D28832 Achim
@@ -32,7 +32,7 @@
32 * #define UMC_DRIVE0 11 32 * #define UMC_DRIVE0 11
33 * in the beginning of the driver, which sets the speed of drive 0 to 11 (there 33 * in the beginning of the driver, which sets the speed of drive 0 to 11 (there
34 * are some lines present). 0 - 11 are allowed speed values. These values are 34 * are some lines present). 0 - 11 are allowed speed values. These values are
35 * the results from the DOS speed test program supplied from UMC. 11 is the 35 * the results from the DOS speed test program supplied from UMC. 11 is the
36 * highest speed (about PIO mode 3) 36 * highest speed (about PIO mode 3)
37 */ 37 */
38#define REALLY_SLOW_IO /* some systems can safely undef this */ 38#define REALLY_SLOW_IO /* some systems can safely undef this */
@@ -60,62 +60,62 @@
60#define UMC_DRIVE3 1 /* In case of crash reduce speed */ 60#define UMC_DRIVE3 1 /* In case of crash reduce speed */
61 61
62static u8 current_speeds[4] = {UMC_DRIVE0, UMC_DRIVE1, UMC_DRIVE2, UMC_DRIVE3}; 62static u8 current_speeds[4] = {UMC_DRIVE0, UMC_DRIVE1, UMC_DRIVE2, UMC_DRIVE3};
63static const u8 pio_to_umc [5] = {0,3,7,10,11}; /* rough guesses */ 63static const u8 pio_to_umc [5] = {0, 3, 7, 10, 11}; /* rough guesses */
64 64
65/* 0 1 2 3 4 5 6 7 8 9 10 11 */ 65/* 0 1 2 3 4 5 6 7 8 9 10 11 */
66static const u8 speedtab [3][12] = { 66static const u8 speedtab [3][12] = {
67 {0xf, 0xb, 0x2, 0x2, 0x2, 0x1, 0x1, 0x1, 0x1, 0x1, 0x1, 0x1 }, 67 {0x0f, 0x0b, 0x02, 0x02, 0x02, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x1},
68 {0x3, 0x2, 0x2, 0x2, 0x2, 0x2, 0x1, 0x1, 0x1, 0x1, 0x1, 0x1 }, 68 {0x03, 0x02, 0x02, 0x02, 0x02, 0x02, 0x01, 0x01, 0x01, 0x01, 0x01, 0x1},
69 {0xff,0xcb,0xc0,0x58,0x36,0x33,0x23,0x22,0x21,0x11,0x10,0x0}}; 69 {0xff, 0xcb, 0xc0, 0x58, 0x36, 0x33, 0x23, 0x22, 0x21, 0x11, 0x10, 0x0}
70};
70 71
71static void out_umc (char port,char wert) 72static void out_umc(char port, char wert)
72{ 73{
73 outb_p(port,0x108); 74 outb_p(port, 0x108);
74 outb_p(wert,0x109); 75 outb_p(wert, 0x109);
75} 76}
76 77
77static inline u8 in_umc (char port) 78static inline u8 in_umc(char port)
78{ 79{
79 outb_p(port,0x108); 80 outb_p(port, 0x108);
80 return inb_p(0x109); 81 return inb_p(0x109);
81} 82}
82 83
83static void umc_set_speeds (u8 speeds[]) 84static void umc_set_speeds(u8 speeds[])
84{ 85{
85 int i, tmp; 86 int i, tmp;
86 87
87 outb_p(0x5A,0x108); /* enable umc */ 88 outb_p(0x5A, 0x108); /* enable umc */
88 89
89 out_umc (0xd7,(speedtab[0][speeds[2]] | (speedtab[0][speeds[3]]<<4))); 90 out_umc(0xd7, (speedtab[0][speeds[2]] | (speedtab[0][speeds[3]]<<4)));
90 out_umc (0xd6,(speedtab[0][speeds[0]] | (speedtab[0][speeds[1]]<<4))); 91 out_umc(0xd6, (speedtab[0][speeds[0]] | (speedtab[0][speeds[1]]<<4)));
91 tmp = 0; 92 tmp = 0;
92 for (i = 3; i >= 0; i--) { 93 for (i = 3; i >= 0; i--)
93 tmp = (tmp << 2) | speedtab[1][speeds[i]]; 94 tmp = (tmp << 2) | speedtab[1][speeds[i]];
95 out_umc(0xdc, tmp);
96 for (i = 0; i < 4; i++) {
97 out_umc(0xd0 + i, speedtab[2][speeds[i]]);
98 out_umc(0xd8 + i, speedtab[2][speeds[i]]);
94 } 99 }
95 out_umc (0xdc,tmp); 100 outb_p(0xa5, 0x108); /* disable umc */
96 for (i = 0;i < 4; i++) {
97 out_umc (0xd0+i,speedtab[2][speeds[i]]);
98 out_umc (0xd8+i,speedtab[2][speeds[i]]);
99 }
100 outb_p(0xa5,0x108); /* disable umc */
101 101
102 printk ("umc8672: drive speeds [0 to 11]: %d %d %d %d\n", 102 printk("umc8672: drive speeds [0 to 11]: %d %d %d %d\n",
103 speeds[0], speeds[1], speeds[2], speeds[3]); 103 speeds[0], speeds[1], speeds[2], speeds[3]);
104} 104}
105 105
106static void umc_set_pio_mode(ide_drive_t *drive, const u8 pio) 106static void umc_set_pio_mode(ide_drive_t *drive, const u8 pio)
107{ 107{
108 ide_hwif_t *hwif = drive->hwif;
108 unsigned long flags; 109 unsigned long flags;
109 ide_hwgroup_t *hwgroup = ide_hwifs[HWIF(drive)->index^1].hwgroup;
110 110
111 printk("%s: setting umc8672 to PIO mode%d (speed %d)\n", 111 printk("%s: setting umc8672 to PIO mode%d (speed %d)\n",
112 drive->name, pio, pio_to_umc[pio]); 112 drive->name, pio, pio_to_umc[pio]);
113 spin_lock_irqsave(&ide_lock, flags); 113 spin_lock_irqsave(&ide_lock, flags);
114 if (hwgroup && hwgroup->handler != NULL) { 114 if (hwif->mate && hwif->mate->hwgroup->handler) {
115 printk(KERN_ERR "umc8672: other interface is busy: exiting tune_umc()\n"); 115 printk(KERN_ERR "umc8672: other interface is busy: exiting tune_umc()\n");
116 } else { 116 } else {
117 current_speeds[drive->name[2] - 'a'] = pio_to_umc[pio]; 117 current_speeds[drive->name[2] - 'a'] = pio_to_umc[pio];
118 umc_set_speeds (current_speeds); 118 umc_set_speeds(current_speeds);
119 } 119 }
120 spin_unlock_irqrestore(&ide_lock, flags); 120 spin_unlock_irqrestore(&ide_lock, flags);
121} 121}
@@ -128,8 +128,9 @@ static const struct ide_port_info umc8672_port_info __initdata = {
128 128
129static int __init umc8672_probe(void) 129static int __init umc8672_probe(void)
130{ 130{
131 ide_hwif_t *hwif, *mate;
131 unsigned long flags; 132 unsigned long flags;
132 static u8 idx[4] = { 0, 1, 0xff, 0xff }; 133 static u8 idx[4] = { 0xff, 0xff, 0xff, 0xff };
133 hw_regs_t hw[2]; 134 hw_regs_t hw[2];
134 135
135 if (!request_region(0x108, 2, "umc8672")) { 136 if (!request_region(0x108, 2, "umc8672")) {
@@ -137,16 +138,16 @@ static int __init umc8672_probe(void)
137 return 1; 138 return 1;
138 } 139 }
139 local_irq_save(flags); 140 local_irq_save(flags);
140 outb_p(0x5A,0x108); /* enable umc */ 141 outb_p(0x5A, 0x108); /* enable umc */
141 if (in_umc (0xd5) != 0xa0) { 142 if (in_umc (0xd5) != 0xa0) {
142 local_irq_restore(flags); 143 local_irq_restore(flags);
143 printk(KERN_ERR "umc8672: not found\n"); 144 printk(KERN_ERR "umc8672: not found\n");
144 release_region(0x108, 2); 145 release_region(0x108, 2);
145 return 1; 146 return 1;
146 } 147 }
147 outb_p(0xa5,0x108); /* disable umc */ 148 outb_p(0xa5, 0x108); /* disable umc */
148 149
149 umc_set_speeds (current_speeds); 150 umc_set_speeds(current_speeds);
150 local_irq_restore(flags); 151 local_irq_restore(flags);
151 152
152 memset(&hw, 0, sizeof(hw)); 153 memset(&hw, 0, sizeof(hw));
@@ -157,18 +158,26 @@ static int __init umc8672_probe(void)
157 ide_std_init_ports(&hw[1], 0x170, 0x376); 158 ide_std_init_ports(&hw[1], 0x170, 0x376);
158 hw[1].irq = 15; 159 hw[1].irq = 15;
159 160
160 ide_init_port_hw(&ide_hwifs[0], &hw[0]); 161 hwif = ide_find_port();
161 ide_init_port_hw(&ide_hwifs[1], &hw[1]); 162 if (hwif) {
163 ide_init_port_hw(hwif, &hw[0]);
164 hwif->set_pio_mode = umc_set_pio_mode;
165 idx[0] = hwif->index;
166 }
162 167
163 ide_hwifs[0].set_pio_mode = &umc_set_pio_mode; 168 mate = ide_find_port();
164 ide_hwifs[1].set_pio_mode = &umc_set_pio_mode; 169 if (mate) {
170 ide_init_port_hw(mate, &hw[1]);
171 mate->set_pio_mode = umc_set_pio_mode;
172 idx[1] = mate->index;
173 }
165 174
166 ide_device_add(idx, &umc8672_port_info); 175 ide_device_add(idx, &umc8672_port_info);
167 176
168 return 0; 177 return 0;
169} 178}
170 179
171int probe_umc8672 = 0; 180int probe_umc8672;
172 181
173module_param_named(probe, probe_umc8672, bool, 0); 182module_param_named(probe, probe_umc8672, bool, 0);
174MODULE_PARM_DESC(probe, "probe for UMC8672 chipset"); 183MODULE_PARM_DESC(probe, "probe for UMC8672 chipset");