This source file includes following definitions.
- find_and_clear_bit_16
- xchgb
- log_ultrastor_abort
- ultrastor_14f_detect
- ARRAY_SIZE
- request_irq
- request_dma
- ultrastor_24f_detect
- ultrastor_detect
- ultrastor_info
- build_sg_list
- ultrastor_queuecommand
- ultrastor_abort
- ultrastor_reset
- ultrastor_biosparam
- ultrastor_interrupt
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127 #include <linux/stddef.h>
128 #include <linux/string.h>
129 #include <linux/sched.h>
130 #include <linux/kernel.h>
131 #include <linux/ioport.h>
132
133 #include <asm/io.h>
134 #include <asm/bitops.h>
135 #include <asm/system.h>
136 #include <asm/dma.h>
137
138 #define ULTRASTOR_PRIVATE
139 #include "../block/blk.h"
140 #include "scsi.h"
141 #include "hosts.h"
142 #include "ultrastor.h"
143 #include "sd.h"
144
145 #define FALSE 0
146 #define TRUE 1
147
148 #ifndef ULTRASTOR_DEBUG
149 #define ULTRASTOR_DEBUG (UD_ABORT|UD_CSIR|UD_RESET)
150 #endif
151
152 #define VERSION "1.12"
153
154 #define ARRAY_SIZE(arr) (sizeof (arr) / sizeof (arr)[0])
155
156 #define PACKED __attribute__((packed))
157 #define ALIGNED(x) __attribute__((aligned(x)))
158
159
160
161
162
163
164
165 typedef struct {
166 unsigned int address;
167 unsigned int num_bytes;
168 } ultrastor_sg_list;
169
170
171
172
173 struct mscp {
174 unsigned char opcode: 3;
175 unsigned char xdir: 2;
176 unsigned char dcn: 1;
177 unsigned char ca: 1;
178 unsigned char sg: 1;
179 unsigned char target_id: 3;
180 unsigned char ch_no: 2;
181 unsigned char lun: 3;
182 unsigned int transfer_data PACKED;
183 unsigned int transfer_data_length PACKED;
184 unsigned int command_link PACKED;
185 unsigned char scsi_command_link_id;
186 unsigned char number_of_sg_list;
187 unsigned char length_of_sense_byte;
188 unsigned char length_of_scsi_cdbs;
189 unsigned char scsi_cdbs[12];
190 unsigned char adapter_status;
191 unsigned char target_status;
192 unsigned int sense_data PACKED;
193
194
195 void (*done)(Scsi_Cmnd *);
196 Scsi_Cmnd *SCint;
197 ultrastor_sg_list sglist[ULTRASTOR_24F_MAX_SG];
198 };
199
200
201
202 #define U14F_PRODUCT_ID(port) ((port) + 0x4)
203 #define CONFIG(port) ((port) + 0x6)
204
205
206 #define LCL_DOORBELL_MASK(port) ((port) + 0x0)
207 #define LCL_DOORBELL_INTR(port) ((port) + 0x1)
208 #define SYS_DOORBELL_MASK(port) ((port) + 0x2)
209 #define SYS_DOORBELL_INTR(port) ((port) + 0x3)
210
211
212
213
214
215
216
217
218
219
220
221 static struct ultrastor_config
222 {
223 unsigned short port_address;
224 unsigned short doorbell_address;
225 unsigned short ogm_address;
226 unsigned short icm_address;
227 const void *bios_segment;
228 unsigned char interrupt: 4;
229 unsigned char dma_channel: 3;
230 unsigned char bios_drive_number: 1;
231 unsigned char heads;
232 unsigned char sectors;
233 unsigned char ha_scsi_id: 3;
234 unsigned char subversion: 4;
235 unsigned char revision;
236
237
238 unsigned char slot;
239
240 #ifdef PRINT_U24F_VERSION
241 volatile int csir_done;
242 #endif
243
244
245
246
247
248 #if ULTRASTOR_MAX_CMDS == 1
249 unsigned char mscp_busy;
250 #else
251 unsigned short mscp_free;
252 #endif
253 volatile unsigned char aborted[ULTRASTOR_MAX_CMDS];
254 struct mscp mscp[ULTRASTOR_MAX_CMDS];
255 } config = {0};
256
257
258 int ultrastor_bus_reset = 0;
259
260
261
262 static const void *const bios_segment_table[8] = {
263 NULL, (void *)0xC4000, (void *)0xC8000, (void *)0xCC000,
264 (void *)0xD0000, (void *)0xD4000, (void *)0xD8000, (void *)0xDC000,
265 };
266
267
268 static const unsigned char interrupt_table_14f[4] = { 15, 14, 11, 10 };
269
270
271 static const unsigned char dma_channel_table_14f[4] = { 5, 6, 7, 0 };
272
273
274 static const struct {
275 unsigned char heads;
276 unsigned char sectors;
277 } mapping_table[4] = { { 16, 63 }, { 64, 32 }, { 64, 63 }, { 64, 32 } };
278
279 #ifndef PORT_OVERRIDE
280
281 static const unsigned short ultrastor_ports_14f[] = {
282 0x330, 0x340, 0x230, 0x240, 0x210, 0x130, 0x140,
283 };
284 #endif
285
286 static void ultrastor_interrupt(int cpl);
287 static inline void build_sg_list(struct mscp *, Scsi_Cmnd *SCpnt);
288
289
290 static inline int find_and_clear_bit_16(unsigned short *field)
291 {
292 int rv;
293 cli();
294 if (*field == 0) panic("No free mscp");
295 asm("xorl %0,%0\n0:\tbsfw %1,%w0\n\tbtr %0,%1\n\tjnc 0b"
296 : "=&r" (rv), "=m" (*field) : "1" (*field));
297 sti();
298 return rv;
299 }
300
301
302
303
304 static inline unsigned char xchgb(unsigned char reg,
305 volatile unsigned char *mem)
306 {
307 asm("xchgb %0,%1" :
308 "=r" (reg), "=m" (*(unsigned char *)mem) :
309 "0" (reg), "1" (*(unsigned char *)mem));
310 return reg;
311 }
312
313 #if ULTRASTOR_DEBUG & (UD_COMMAND | UD_ABORT)
314
315 static void log_ultrastor_abort(register struct ultrastor_config *config,
316 int command)
317 {
318 static char fmt[80] = "abort %d (%x); MSCP free pool: %x;";
319 register int i;
320 int flags;
321 save_flags(flags);
322 cli();
323
324 for (i = 0; i < ULTRASTOR_MAX_CMDS; i++)
325 {
326 fmt[20 + i*2] = ' ';
327 if (! (config->mscp_free & (1 << i)))
328 fmt[21 + i*2] = '0' + config->mscp[i].target_id;
329 else
330 fmt[21 + i*2] = '-';
331 }
332 fmt[20 + ULTRASTOR_MAX_CMDS * 2] = '\n';
333 fmt[21 + ULTRASTOR_MAX_CMDS * 2] = 0;
334 printk(fmt, command, &config->mscp[command], config->mscp_free);
335 restore_flags(flags);
336 }
337 #endif
338
339 static int ultrastor_14f_detect(Scsi_Host_Template * tpnt)
340 {
341 size_t i;
342 unsigned char in_byte, version_byte = 0;
343 struct config_1 {
344 unsigned char bios_segment: 3;
345 unsigned char removable_disks_as_fixed: 1;
346 unsigned char interrupt: 2;
347 unsigned char dma_channel: 2;
348 } config_1;
349 struct config_2 {
350 unsigned char ha_scsi_id: 3;
351 unsigned char mapping_mode: 2;
352 unsigned char bios_drive_number: 1;
353 unsigned char tfr_port: 2;
354 } config_2;
355
356 #if (ULTRASTOR_DEBUG & UD_DETECT)
357 printk("US14F: detect: called\n");
358 #endif
359
360
361 if (config.bios_segment)
362 return FALSE;
363
364 #ifdef PORT_OVERRIDE
365 if(check_region(PORT_OVERRIDE, 0xc)) {
366 printk("Ultrastor I/O space already in use\n");
367 return FALSE;
368 };
369 config.port_address = PORT_OVERRIDE;
370 #else
371 for (i = 0; i < ARRAY_SIZE(ultrastor_ports_14f); i++) {
372 if(check_region(ultrastor_ports_14f[i], 0x0c)) continue;
373 config.port_address = ultrastor_ports_14f[i];
374 #endif
375
376 #if (ULTRASTOR_DEBUG & UD_DETECT)
377 printk("US14F: detect: testing port address %03X\n", config.port_address);
378 #endif
379
380 in_byte = inb(U14F_PRODUCT_ID(config.port_address));
381 if (in_byte != US14F_PRODUCT_ID_0) {
382 #if (ULTRASTOR_DEBUG & UD_DETECT)
383 # ifdef PORT_OVERRIDE
384 printk("US14F: detect: wrong product ID 0 - %02X\n", in_byte);
385 # else
386 printk("US14F: detect: no adapter at port %03X\n", config.port_address);
387 # endif
388 #endif
389 #ifdef PORT_OVERRIDE
390 return FALSE;
391 #else
392 continue;
393 #endif
394 }
395 in_byte = inb(U14F_PRODUCT_ID(config.port_address) + 1);
396
397 if ((in_byte & 0xF0) != US14F_PRODUCT_ID_1) {
398 #if (ULTRASTOR_DEBUG & UD_DETECT)
399 # ifdef PORT_OVERRIDE
400 printk("US14F: detect: wrong product ID 1 - %02X\n", in_byte);
401 # else
402 printk("US14F: detect: no adapter at port %03X\n", config.port_address);
403 # endif
404 #endif
405 #ifdef PORT_OVERRIDE
406 return FALSE;
407 #else
408 continue;
409 #endif
410 }
411 version_byte = in_byte;
412 #ifndef PORT_OVERRIDE
413 break;
414 }
415 if (i == ARRAY_SIZE(ultrastor_ports_14f)) {
416 # if (ULTRASTOR_DEBUG & UD_DETECT)
417 printk("US14F: detect: no port address found!\n");
418 # endif
419 return FALSE;
420 }
421 #endif
422
423 #if (ULTRASTOR_DEBUG & UD_DETECT)
424 printk("US14F: detect: adapter found at port address %03X\n",
425 config.port_address);
426 #endif
427
428
429
430 outb(ultrastor_bus_reset ? 0xc2 : 0x82, LCL_DOORBELL_MASK(config.port_address));
431
432
433
434
435 snarf_region(config.port_address, 0x0c);
436
437 *(char *)&config_1 = inb(CONFIG(config.port_address + 0));
438 *(char *)&config_2 = inb(CONFIG(config.port_address + 1));
439 config.bios_segment = bios_segment_table[config_1.bios_segment];
440 config.doorbell_address = config.port_address;
441 config.ogm_address = config.port_address + 0x8;
442 config.icm_address = config.port_address + 0xC;
443 config.interrupt = interrupt_table_14f[config_1.interrupt];
444 config.ha_scsi_id = config_2.ha_scsi_id;
445 config.heads = mapping_table[config_2.mapping_mode].heads;
446 config.sectors = mapping_table[config_2.mapping_mode].sectors;
447 config.bios_drive_number = config_2.bios_drive_number;
448 config.subversion = (version_byte & 0x0F);
449 if (config.subversion == U34F)
450 config.dma_channel = 0;
451 else
452 config.dma_channel = dma_channel_table_14f[config_1.dma_channel];
453
454 if (!config.bios_segment) {
455 #if (ULTRASTOR_DEBUG & UD_DETECT)
456 printk("US14F: detect: not detected.\n");
457 #endif
458 return FALSE;
459 }
460
461
462 if (config.subversion != U34F)
463 if (!config.dma_channel || !(config_2.tfr_port & 0x2)) {
464 #if (ULTRASTOR_DEBUG & UD_DETECT)
465 printk("US14F: detect: consistancy check failed\n");
466 #endif
467 return FALSE;
468 }
469
470
471
472
473
474
475 #if (ULTRASTOR_DEBUG & UD_DETECT)
476 printk("US14F: detect: detect succeeded\n"
477 " Port address: %03X\n"
478 " BIOS segment: %05X\n"
479 " Interrupt: %u\n"
480 " DMA channel: %u\n"
481 " H/A SCSI ID: %u\n"
482 " Subversion: %u\n",
483 config.port_address, config.bios_segment, config.interrupt,
484 config.dma_channel, config.ha_scsi_id, config.subversion);
485 #endif
486 tpnt->this_id = config.ha_scsi_id;
487 tpnt->unchecked_isa_dma = (config.subversion != U34F);
488
489 #if ULTRASTOR_MAX_CMDS > 1
490 config.mscp_free = ~0;
491 #endif
492
493 if (request_irq(config.interrupt, ultrastor_interrupt)) {
494 printk("Unable to allocate IRQ%u for UltraStor controller.\n",
495 config.interrupt);
496 return FALSE;
497 }
498 if (config.dma_channel && request_dma(config.dma_channel)) {
499 printk("Unable to allocate DMA channel %u for UltraStor controller.\n",
500 config.dma_channel);
501 free_irq(config.interrupt);
502 return FALSE;
503 }
504 tpnt->sg_tablesize = ULTRASTOR_14F_MAX_SG;
505 printk("UltraStor driver version" VERSION ". Using %d SG lists.\n",
506 ULTRASTOR_14F_MAX_SG);
507
508 return TRUE;
509 }
510
511 static int ultrastor_24f_detect(Scsi_Host_Template * tpnt)
512 {
513 register int i;
514 struct Scsi_Host * shpnt = NULL;
515
516 #if (ULTRASTOR_DEBUG & UD_DETECT)
517 printk("US24F: detect");
518 #endif
519
520
521 for (i = 1; i < 15; i++)
522 {
523 unsigned char config_1, config_2;
524 unsigned short addr = (i << 12) | ULTRASTOR_24F_PORT;
525
526 if (inb(addr) != US24F_PRODUCT_ID_0 &&
527 inb(addr+1) != US24F_PRODUCT_ID_1 &&
528 inb(addr+2) != US24F_PRODUCT_ID_2)
529 continue;
530
531 config.revision = inb(addr+3);
532 config.slot = i;
533 if (! (inb(addr+4) & 1))
534 {
535 #if (ULTRASTOR_DEBUG & UD_DETECT)
536 printk("U24F: found disabled card in slot %u\n", i);
537 #endif
538 continue;
539 }
540 #if (ULTRASTOR_DEBUG & UD_DETECT)
541 printk("U24F: found card in slot %u\n", i);
542 #endif
543 config_1 = inb(addr + 5);
544 config.bios_segment = bios_segment_table[config_1 & 7];
545 switch(config_1 >> 4)
546 {
547 case 1:
548 config.interrupt = 15;
549 break;
550 case 2:
551 config.interrupt = 14;
552 break;
553 case 4:
554 config.interrupt = 11;
555 break;
556 case 8:
557 config.interrupt = 10;
558 break;
559 default:
560 printk("U24F: invalid IRQ\n");
561 return FALSE;
562 }
563 if (request_irq(config.interrupt, ultrastor_interrupt))
564 {
565 printk("Unable to allocate IRQ%u for UltraStor controller.\n",
566 config.interrupt);
567 return FALSE;
568 }
569
570
571 config.port_address = addr;
572 config.doorbell_address = addr + 12;
573 config.ogm_address = addr + 0x17;
574 config.icm_address = addr + 0x1C;
575 config_2 = inb(addr + 7);
576 config.ha_scsi_id = config_2 & 7;
577 config.heads = mapping_table[(config_2 >> 3) & 3].heads;
578 config.sectors = mapping_table[(config_2 >> 3) & 3].sectors;
579 #if (ULTRASTOR_DEBUG & UD_DETECT)
580 printk("US24F: detect: detect succeeded\n"
581 " Port address: %03X\n"
582 " BIOS segment: %05X\n"
583 " Interrupt: %u\n"
584 " H/A SCSI ID: %u\n",
585 config.port_address, config.bios_segment,
586 config.interrupt, config.ha_scsi_id);
587 #endif
588 tpnt->this_id = config.ha_scsi_id;
589 tpnt->unchecked_isa_dma = 0;
590 tpnt->sg_tablesize = ULTRASTOR_24F_MAX_SG;
591
592 shpnt = scsi_register(tpnt, 0);
593 shpnt->irq = config.interrupt;
594 shpnt->dma_channel = config.dma_channel;
595 shpnt->io_port = config.port_address;
596
597 #if ULTRASTOR_MAX_CMDS > 1
598 config.mscp_free = ~0;
599 #endif
600
601 outb(0, addr + 0x16);
602 outb(0, addr + 0x1B);
603
604
605
606 outb(ultrastor_bus_reset ? 0xc2 : 0x82, LCL_DOORBELL_MASK(addr+12));
607 outb(0x02, SYS_DOORBELL_MASK(addr+12));
608 printk("UltraStor driver version " VERSION ". Using %d SG lists.\n",
609 tpnt->sg_tablesize);
610 return TRUE;
611 }
612 return FALSE;
613 }
614
615 int ultrastor_detect(Scsi_Host_Template * tpnt)
616 {
617 return ultrastor_14f_detect(tpnt) || ultrastor_24f_detect(tpnt);
618 }
619
620 const char *ultrastor_info(void)
621 {
622 static char buf[64];
623
624 if (config.slot)
625 sprintf(buf, "UltraStor 24F SCSI @ Slot %u IRQ%u\n",
626 config.slot, config.interrupt);
627 else if (config.subversion)
628 sprintf(buf, "UltraStor 34F SCSI @ Port %03X BIOS %05X IRQ%u\n",
629 config.port_address, (int)config.bios_segment,
630 config.interrupt);
631 else
632 sprintf(buf, "UltraStor 14F SCSI @ Port %03X BIOS %05X IRQ%u DMA%u\n",
633 config.port_address, (int)config.bios_segment,
634 config.interrupt, config.dma_channel);
635 return buf;
636 }
637
638 static inline void build_sg_list(register struct mscp *mscp, Scsi_Cmnd *SCpnt)
639 {
640 struct scatterlist *sl;
641 long transfer_length = 0;
642 int i, max;
643
644 sl = (struct scatterlist *) SCpnt->request_buffer;
645 max = SCpnt->use_sg;
646 for (i = 0; i < max; i++) {
647 mscp->sglist[i].address = (unsigned int)sl[i].address;
648 mscp->sglist[i].num_bytes = sl[i].length;
649 transfer_length += sl[i].length;
650 }
651 mscp->number_of_sg_list = max;
652 mscp->transfer_data = (unsigned int)mscp->sglist;
653
654
655
656 mscp->transfer_data_length = transfer_length;
657 }
658
659 int ultrastor_queuecommand(Scsi_Cmnd *SCpnt, void (*done)(Scsi_Cmnd *))
660 {
661 register struct mscp *my_mscp;
662 #if ULTRASTOR_MAX_CMDS > 1
663 int mscp_index;
664 #endif
665 unsigned int status;
666 int flags;
667
668
669 if ((config.mscp_free & ((1U << ULTRASTOR_MAX_CMDS) - 1)) == 0)
670 panic("ultrastor_queuecommand: no free MSCP\n");
671 mscp_index = find_and_clear_bit_16(&config.mscp_free);
672
673
674 if (xchgb(0xff, &config.aborted[mscp_index]) != 0)
675 {
676 status = DID_ABORT << 16;
677 goto aborted;
678 }
679
680 my_mscp = &config.mscp[mscp_index];
681
682 #if 1
683
684 *(unsigned char *)my_mscp = OP_SCSI | (DTD_SCSI << 3);
685 #else
686 my_mscp->opcode = OP_SCSI;
687 my_mscp->xdir = DTD_SCSI;
688 my_mscp->dcn = FALSE;
689 #endif
690
691
692
693
694
695
696
697 my_mscp->ca = SCpnt->device->type != TYPE_TAPE;
698 my_mscp->target_id = SCpnt->target;
699 my_mscp->ch_no = 0;
700 my_mscp->lun = SCpnt->lun;
701 if (SCpnt->use_sg) {
702
703 my_mscp->sg = TRUE;
704 build_sg_list(my_mscp, SCpnt);
705 } else {
706
707 my_mscp->sg = FALSE;
708 my_mscp->transfer_data = (unsigned int)SCpnt->request_buffer;
709 my_mscp->transfer_data_length = SCpnt->request_bufflen;
710 }
711 my_mscp->command_link = 0;
712 my_mscp->scsi_command_link_id = 0;
713 my_mscp->length_of_sense_byte = sizeof SCpnt->sense_buffer;
714 my_mscp->length_of_scsi_cdbs = COMMAND_SIZE(*(unsigned char *)SCpnt->cmnd);
715 memcpy(my_mscp->scsi_cdbs, SCpnt->cmnd, my_mscp->length_of_scsi_cdbs);
716 my_mscp->adapter_status = 0;
717 my_mscp->target_status = 0;
718 my_mscp->sense_data = (unsigned int)&SCpnt->sense_buffer;
719 my_mscp->done = done;
720 my_mscp->SCint = SCpnt;
721 SCpnt->host_scribble = (unsigned char *)my_mscp;
722
723
724
725
726 retry:
727 if (config.slot)
728 while (inb(config.ogm_address - 1) != 0 &&
729 config.aborted[mscp_index] == 0xff);
730
731
732
733 while ((inb(LCL_DOORBELL_INTR(config.doorbell_address)) &
734 (config.slot ? 2 : 1))
735 && config.aborted[mscp_index] == 0xff);
736
737
738
739
740 save_flags(flags);
741 cli();
742
743 if (inb(LCL_DOORBELL_INTR(config.doorbell_address)) &
744 (config.slot ? 2 : 1))
745 {
746 restore_flags(flags);
747 goto retry;
748 }
749
750 status = xchgb(0, &config.aborted[mscp_index]);
751 if (status != 0xff) {
752 restore_flags(flags);
753
754 #if ULTRASTOR_DEBUG & (UD_COMMAND | UD_ABORT)
755 printk("USx4F: queuecommand: aborted\n");
756 #if ULTRASTOR_MAX_CMDS > 1
757 log_ultrastor_abort(&config, mscp_index);
758 #endif
759 #endif
760 status <<= 16;
761
762 aborted:
763 set_bit(mscp_index, &config.mscp_free);
764
765
766 #if ULTRASTOR_MAX_CMDS > 1
767 SCpnt->result = status;
768 done(SCpnt);
769 return 0;
770 #else
771 return status;
772 #endif
773 }
774
775
776 outl((unsigned int)my_mscp, config.ogm_address);
777
778
779 if (config.slot) {
780
781 outb(1, config.ogm_address - 1);
782 outb(0x2, LCL_DOORBELL_INTR(config.doorbell_address));
783 } else {
784 outb(0x1, LCL_DOORBELL_INTR(config.doorbell_address));
785 }
786
787 restore_flags(flags);
788
789 #if (ULTRASTOR_DEBUG & UD_COMMAND)
790 printk("USx4F: queuecommand: returning\n");
791 #endif
792
793 return 0;
794 }
795
796
797
798
799
800
801
802
803
804
805
806
807
808
809
810
811 int ultrastor_abort(Scsi_Cmnd *SCpnt)
812 {
813 #if ULTRASTOR_DEBUG & UD_ABORT
814 char out[108];
815 unsigned char icm_status = 0, ogm_status = 0;
816 unsigned int icm_addr = 0, ogm_addr = 0;
817 #endif
818 unsigned int mscp_index;
819 unsigned char old_aborted;
820 void (*done)(Scsi_Cmnd *);
821
822 if(config.slot)
823 return SCSI_ABORT_SNOOZE;
824
825
826 if(!SCpnt->host_scribble)
827 return SCSI_ABORT_NOT_RUNNING;
828
829 mscp_index = ((struct mscp *)SCpnt->host_scribble) - config.mscp;
830 if (mscp_index >= ULTRASTOR_MAX_CMDS)
831 panic("Ux4F aborting invalid MSCP");
832
833 #if ULTRASTOR_DEBUG & UD_ABORT
834 if (config.slot)
835 {
836 int port0 = (config.slot << 12) | 0xc80;
837 int i;
838 int flags;
839 save_flags(flags);
840 cli();
841 strcpy(out, "OGM %d:%x ICM %d:%x ports: ");
842 for (i = 0; i < 16; i++)
843 {
844 unsigned char p = inb(port0 + i);
845 out[28 + i * 3] = "0123456789abcdef"[p >> 4];
846 out[29 + i * 3] = "0123456789abcdef"[p & 15];
847 out[30 + i * 3] = ' ';
848 }
849 out[28 + i * 3] = '\n';
850 out[29 + i * 3] = 0;
851 ogm_status = inb(port0 + 22);
852 ogm_addr = inl(port0 + 23);
853 icm_status = inb(port0 + 27);
854 icm_addr = inl(port0 + 28);
855 restore_flags(flags);
856 }
857
858
859
860
861 if (config.slot ? inb(config.icm_address - 1) == 2 :
862 (inb(SYS_DOORBELL_INTR(config.doorbell_address)) & 1))
863 {
864 int flags;
865 save_flags(flags);
866 printk("Ux4F: abort while completed command pending\n");
867 restore_flags(flags);
868 cli();
869 ultrastor_interrupt(0);
870 restore_flags(flags);
871 return SCSI_ABORT_SUCCESS;
872 }
873 #endif
874
875 old_aborted = xchgb(DID_ABORT, &config.aborted[mscp_index]);
876
877
878
879 if (old_aborted == 0xff)
880 return SCSI_ABORT_SUCCESS;
881
882
883
884 if (config.slot && inb(config.ogm_address - 1) == 0)
885 {
886 int flags;
887
888 save_flags(flags);
889 cli();
890 outl((int)&config.mscp[mscp_index], config.ogm_address);
891 inb(0xc80);
892 outb(0x80, config.ogm_address - 1);
893 outb(0x2, LCL_DOORBELL_INTR(config.doorbell_address));
894 #if ULTRASTOR_DEBUG & UD_ABORT
895 log_ultrastor_abort(&config, mscp_index);
896 printk(out, ogm_status, ogm_addr, icm_status, icm_addr);
897 #endif
898 restore_flags(flags);
899 return SCSI_ABORT_PENDING;
900 }
901
902 #if ULTRASTOR_DEBUG & UD_ABORT
903 log_ultrastor_abort(&config, mscp_index);
904 #endif
905
906
907
908
909
910
911
912
913
914
915
916 #if ULTRASTOR_DEBUG & UD_ABORT
917 if (config.mscp[mscp_index].SCint != SCpnt)
918 printk("abort: command mismatch, %p != %p\n",
919 config.mscp[mscp_index].SCint, SCpnt);
920 #endif
921 if (config.mscp[mscp_index].SCint == 0)
922 return SCSI_ABORT_NOT_RUNNING;
923
924 if (config.mscp[mscp_index].SCint != SCpnt) panic("Bad abort");
925 config.mscp[mscp_index].SCint = 0;
926 done = config.mscp[mscp_index].done;
927 config.mscp[mscp_index].done = 0;
928 SCpnt->result = DID_ABORT << 16;
929
930 done(SCpnt);
931
932
933 return SCSI_ABORT_SUCCESS;
934 }
935
936 int ultrastor_reset(Scsi_Cmnd * SCpnt)
937 {
938 int flags;
939 register int i;
940 #if (ULTRASTOR_DEBUG & UD_RESET)
941 printk("US14F: reset: called\n");
942 #endif
943
944 if(config.slot)
945 return SCSI_RESET_PUNT;
946
947 save_flags(flags);
948 cli();
949
950
951
952 outb(0xc0, LCL_DOORBELL_INTR(config.doorbell_address));
953 if (config.slot)
954 {
955 outb(0, config.ogm_address - 1);
956 outb(0, config.icm_address - 1);
957 }
958
959 #if ULTRASTOR_MAX_CMDS == 1
960 if (config.mscp_busy && config.mscp->done && config.mscp->SCint)
961 {
962 config.mscp->SCint->result = DID_RESET << 16;
963 config.mscp->done(config.mscp->SCint);
964 }
965 config.mscp->SCint = 0;
966 #else
967 for (i = 0; i < ULTRASTOR_MAX_CMDS; i++)
968 {
969 if (! (config.mscp_free & (1 << i)) &&
970 config.mscp[i].done && config.mscp[i].SCint)
971 {
972 config.mscp[i].SCint->result = DID_RESET << 16;
973 config.mscp[i].done(config.mscp[i].SCint);
974 config.mscp[i].done = 0;
975 }
976 config.mscp[i].SCint = 0;
977 }
978 #endif
979
980
981
982
983 memset((unsigned char *)config.aborted, 0, sizeof config.aborted);
984 #if ULTRASTOR_MAX_CMDS == 1
985 config.mscp_busy = 0;
986 #else
987 config.mscp_free = ~0;
988 #endif
989
990 restore_flags(flags);
991 return SCSI_RESET_SUCCESS;
992
993 }
994
995 int ultrastor_biosparam(Disk * disk, int dev, int * dkinfo)
996 {
997 int size = disk->capacity;
998 unsigned int s = config.heads * config.sectors;
999
1000 dkinfo[0] = config.heads;
1001 dkinfo[1] = config.sectors;
1002 dkinfo[2] = size / s;
1003 #if 0
1004 if (dkinfo[2] > 1024)
1005 dkinfo[2] = 1024;
1006 #endif
1007 return 0;
1008 }
1009
1010 static void ultrastor_interrupt(int cpl)
1011 {
1012 unsigned int status;
1013 #if ULTRASTOR_MAX_CMDS > 1
1014 unsigned int mscp_index;
1015 #endif
1016 register struct mscp *mscp;
1017 void (*done)(Scsi_Cmnd *);
1018 Scsi_Cmnd *SCtmp;
1019
1020 #if ULTRASTOR_MAX_CMDS == 1
1021 mscp = &config.mscp[0];
1022 #else
1023 mscp = (struct mscp *)inl(config.icm_address);
1024 mscp_index = mscp - config.mscp;
1025 if (mscp_index >= ULTRASTOR_MAX_CMDS) {
1026 printk("Ux4F interrupt: bad MSCP address %x\n", (unsigned int) mscp);
1027
1028
1029 ultrastor_reset(NULL);
1030 return;
1031 }
1032 #endif
1033
1034
1035 if (config.slot) {
1036 unsigned char icm_status = inb(config.icm_address - 1);
1037 #if ULTRASTOR_DEBUG & (UD_INTERRUPT|UD_ERROR|UD_ABORT)
1038 if (icm_status != 1 && icm_status != 2)
1039 printk("US24F: ICM status %x for MSCP %d (%x)\n", icm_status,
1040 mscp_index, (unsigned int) mscp);
1041 #endif
1042
1043
1044 outb(2, SYS_DOORBELL_INTR(config.doorbell_address));
1045 outb(0, config.icm_address - 1);
1046 if (icm_status == 4) {
1047 printk("UltraStor abort command failed\n");
1048 return;
1049 }
1050 if (icm_status == 3) {
1051 void (*done)(Scsi_Cmnd *) = mscp->done;
1052 if (done) {
1053 mscp->done = 0;
1054 mscp->SCint->result = DID_ABORT << 16;
1055 done(mscp->SCint);
1056 }
1057 return;
1058 }
1059 } else {
1060 outb(1, SYS_DOORBELL_INTR(config.doorbell_address));
1061 }
1062
1063 SCtmp = mscp->SCint;
1064 mscp->SCint = NULL;
1065
1066 if (SCtmp == 0)
1067 {
1068 #if ULTRASTOR_DEBUG & (UD_ABORT|UD_INTERRUPT)
1069 printk("MSCP %d (%x): no command\n", mscp_index, (unsigned int) mscp);
1070 #endif
1071 #if ULTRASTOR_MAX_CMDS == 1
1072 config.mscp_busy = FALSE;
1073 #else
1074 set_bit(mscp_index, &config.mscp_free);
1075 #endif
1076 config.aborted[mscp_index] = 0;
1077 return;
1078 }
1079
1080
1081
1082
1083 done = mscp->done;
1084 mscp->done = 0;
1085
1086
1087 switch (mscp->adapter_status)
1088 {
1089 case 0:
1090 status = DID_OK << 16;
1091 break;
1092 case 0x01:
1093 case 0x02:
1094 case 0x03:
1095 default:
1096 status = DID_ERROR << 16;
1097 break;
1098 case 0x84:
1099 status = DID_ABORT << 16;
1100 break;
1101 case 0x91:
1102 status = DID_TIME_OUT << 16;
1103 break;
1104 }
1105
1106 SCtmp->result = status | mscp->target_status;
1107
1108 SCtmp->host_scribble = 0;
1109
1110
1111 #if ULTRASTOR_MAX_CMDS == 1
1112 config.mscp_busy = FALSE;
1113 #else
1114 set_bit(mscp_index, &config.mscp_free);
1115 #endif
1116
1117 #if ULTRASTOR_DEBUG & (UD_ABORT|UD_INTERRUPT)
1118 if (config.aborted[mscp_index])
1119 printk("Ux4 interrupt: MSCP %d (%x) aborted = %d\n",
1120 mscp_index, (unsigned int) mscp, config.aborted[mscp_index]);
1121 #endif
1122 config.aborted[mscp_index] = 0;
1123
1124 if (done)
1125 done(SCtmp);
1126 else
1127 printk("US14F: interrupt: unexpected interrupt\n");
1128
1129 if (config.slot ? inb(config.icm_address - 1) : (inb(SYS_DOORBELL_INTR(config.doorbell_address)) & 1))
1130 printk("Ux4F: multiple commands completed\n");
1131
1132 #if (ULTRASTOR_DEBUG & UD_INTERRUPT)
1133 printk("USx4F: interrupt: returning\n");
1134 #endif
1135 }