This source file includes following definitions.
- st0x_setup
- tmc8xx_setup
- borken_init
- borken_wait
- seagate_st0x_detect
- seagate_st0x_info
- seagate_reconnect_intr
- seagate_st0x_queue_command
- seagate_st0x_command
- internal_command
- seagate_st0x_abort
- seagate_st0x_reset
- seagate_st0x_biosparam
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 #include <asm/io.h>
51 #include <asm/system.h>
52 #include <linux/signal.h>
53 #include <linux/sched.h>
54 #include <linux/string.h>
55 #include <linux/config.h>
56
57 #include "../block/blk.h"
58 #include "scsi.h"
59 #include "hosts.h"
60 #include "seagate.h"
61 #include "constants.h"
62
63
64 #ifndef IRQ
65 #define IRQ 5
66 #endif
67
68 #if (defined(FAST32) && !defined(FAST))
69 #define FAST
70 #endif
71
72 #if defined(SLOW_RATE) && !defined(SLOW_HANDSHAKE)
73 #define SLOW_HANDSHAKE
74 #endif
75
76 #if defined(SLOW_HANDSHAKE) && !defined(SLOW_RATE)
77 #define SLOW_RATE 50
78 #endif
79
80
81 #if defined(LINKED)
82 #undef LINKED
83 #endif
84
85 static int internal_command(unsigned char target, unsigned char lun,
86 const void *cmnd,
87 void *buff, int bufflen, int reselect);
88
89 static int incommand;
90
91
92
93
94 static void *base_address = NULL;
95
96
97
98
99 static volatile int abort_confirm = 0;
100
101 static volatile void *st0x_cr_sr;
102
103
104
105
106
107
108
109
110
111
112 static volatile void *st0x_dr;
113
114
115
116
117
118 static volatile int st0x_aborted=0;
119
120
121
122 static unsigned char controller_type = 0;
123 static unsigned char irq = IRQ;
124
125 #define retcode(result) (((result) << 16) | (message << 8) | status)
126 #define STATUS (*(volatile unsigned char *) st0x_cr_sr)
127 #define CONTROL STATUS
128 #define DATA (*(volatile unsigned char *) st0x_dr)
129
130 void st0x_setup (char *str, int *ints) {
131 controller_type = SEAGATE;
132 base_address = (void *) ints[1];
133 irq = ints[2];
134 }
135
136 void tmc8xx_setup (char *str, int *ints) {
137 controller_type = FD;
138 base_address = (void *) ints[1];
139 irq = ints[2];
140 }
141
142
143 #ifndef OVERRIDE
144 static const char * seagate_bases[] = {
145 (char *) 0xc8000, (char *) 0xca000, (char *) 0xcc000,
146 (char *) 0xce000, (char *) 0xdc000, (char *) 0xde000
147 };
148
149 typedef struct {
150 char *signature ;
151 unsigned offset;
152 unsigned length;
153 unsigned char type;
154 } Signature;
155
156 static const Signature signatures[] = {
157 #ifdef CONFIG_SCSI_SEAGATE
158 {"ST01 v1.7 (C) Copyright 1987 Seagate", 15, 37, SEAGATE},
159 {"SCSI BIOS 2.00 (C) Copyright 1987 Seagate", 15, 40, SEAGATE},
160
161
162
163
164
165
166
167
168 {"SEAGATE SCSI BIOS ",16, 17, SEAGATE},
169 {"SEAGATE SCSI BIOS ",17, 17, SEAGATE},
170
171
172
173
174
175
176 {"FUTURE DOMAIN CORP. (C) 1986-1989 V5.0C2/14/89", 5, 46, FD},
177 {"FUTURE DOMAIN CORP. (C) 1986-1989 V6.0A7/28/89", 5, 46, FD},
178 {"FUTURE DOMAIN CORP. (C) 1986-1990 V6.0105/31/90",5, 47, FD},
179 {"FUTURE DOMAIN CORP. (C) 1986-1990 V6.0209/18/90",5, 47, FD},
180 {"FUTURE DOMAIN CORP. (C) 1986-1990 V7.009/18/90", 5, 46, FD},
181 {"FUTURE DOMAIN CORP. (C) 1992 V8.00.004/02/92", 5, 44, FD},
182 {"FUTURE DOMAIN TMC-950", 5, 21, FD},
183 #endif
184 }
185 ;
186
187 #define NUM_SIGNATURES (sizeof(signatures) / sizeof(Signature))
188 #endif
189
190
191
192
193
194 static int hostno = -1;
195 static void seagate_reconnect_intr(int);
196
197 #ifdef FAST
198 static int fast = 1;
199 #endif
200
201 #ifdef SLOW_HANDSHAKE
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239 static int borken_calibration = 0;
240 static void borken_init (void) {
241 register int count = 0, start = jiffies + 1, stop = start + 25;
242
243 while (jiffies < start);
244 for (;jiffies < stop; ++count);
245
246
247
248
249
250
251 borken_calibration = (count * 4) / (SLOW_RATE*1024);
252
253 if (borken_calibration < 1)
254 borken_calibration = 1;
255 #if (DEBUG & DEBUG_BORKEN)
256 printk("scsi%d : borken calibrated to %dK/sec, %d cycles per transfer\n",
257 hostno, BORKEN_RATE, borken_calibration);
258 #endif
259 }
260
261 static inline void borken_wait(void) {
262 register int count;
263 for (count = borken_calibration; count && (STATUS & STAT_REQ);
264 --count);
265 #if (DEBUG & DEBUG_BORKEN)
266 if (count)
267 printk("scsi%d : borken timeout\n", hostno);
268 #endif
269 }
270
271 #endif
272
273 int seagate_st0x_detect (Scsi_Host_Template * tpnt)
274 {
275 struct Scsi_Host *instance;
276 #ifndef OVERRIDE
277 int i,j;
278 #endif
279
280
281
282
283 #ifdef DEBUG
284 printk("Autodetecting seagate ST0x\n");
285 #endif
286
287 if (hostno != -1)
288 {
289 printk ("ERROR : seagate_st0x_detect() called twice.\n");
290 return 0;
291 }
292
293
294
295
296 if (!controller_type) {
297 #ifdef OVERRIDE
298 base_address = (void *) OVERRIDE;
299
300
301 #ifdef CONTROLLER
302 controller_type = CONTROLLER;
303 #else
304 #error Please use -DCONTROLLER=SEAGATE or -DCONTROLLER=FD to override controller type
305 #endif
306 #ifdef DEBUG
307 printk("Base address overridden to %x, controller type is %s\n",
308 base_address,controller_type == SEAGATE ? "SEAGATE" : "FD");
309 #endif
310 #else
311
312
313
314
315
316
317
318
319
320
321 for (i = 0; i < (sizeof (seagate_bases) / sizeof (char * )); ++i)
322 for (j = 0; !base_address && j < NUM_SIGNATURES; ++j)
323 if (!memcmp ((void *) (seagate_bases[i] +
324 signatures[j].offset), (void *) signatures[j].signature,
325 signatures[j].length)) {
326 base_address = (void *) seagate_bases[i];
327 controller_type = signatures[j].type;
328 }
329 #endif
330 }
331
332 tpnt->this_id = (controller_type == SEAGATE) ? 7 : 6;
333 tpnt->name = (controller_type == SEAGATE) ? ST0X_ID_STR : FD_ID_STR;
334
335 if (base_address)
336 {
337 st0x_cr_sr =(void *) (((unsigned char *) base_address) + (controller_type == SEAGATE ? 0x1a00 : 0x1c00));
338 st0x_dr = (void *) (((unsigned char *) base_address ) + (controller_type == SEAGATE ? 0x1c00 : 0x1e00));
339 #ifdef DEBUG
340 printk("%s detected. Base address = %x, cr = %x, dr = %x\n", tpnt->name, base_address, st0x_cr_sr, st0x_dr);
341 #endif
342
343
344
345
346 instance = scsi_register(tpnt, 0);
347 hostno = instance->host_no;
348 if (request_irq((int) irq, seagate_reconnect_intr, SA_INTERRUPT, "seagate")) {
349 printk("scsi%d : unable to allocate IRQ%d\n",
350 hostno, (int) irq);
351 return 0;
352 }
353 #ifdef SLOW_HANDSHAKE
354 borken_init();
355 #endif
356
357 return 1;
358 }
359 else
360 {
361 #ifdef DEBUG
362 printk("ST0x not detected.\n");
363 #endif
364 return 0;
365 }
366 }
367
368 const char *seagate_st0x_info(struct Scsi_Host * shpnt) {
369 static char buffer[256];
370 sprintf(buffer, "scsi%d : %s at irq %d address %p options :"
371 #ifdef ARBITRATE
372 " ARBITRATE"
373 #endif
374 #ifdef SLOW_HANDSHAKE
375 " SLOW_HANDSHAKE"
376 #endif
377 #ifdef FAST
378 #ifdef FAST32
379 " FAST32"
380 #else
381 " FAST"
382 #endif
383 #endif
384
385 #ifdef LINKED
386 " LINKED"
387 #endif
388 "\n", hostno, (controller_type == SEAGATE) ? ST0X_ID_STR :
389 FD_ID_STR, irq, base_address);
390 return buffer;
391 }
392
393
394
395
396
397
398 static unsigned char current_target, current_lun;
399 static unsigned char *current_cmnd, *current_data;
400 static int current_nobuffs;
401 static struct scatterlist *current_buffer;
402 static int current_bufflen;
403
404 #ifdef LINKED
405
406
407
408
409
410
411
412 static int linked_connected = 0;
413 static unsigned char linked_target, linked_lun;
414 #endif
415
416
417 static void (*done_fn)(Scsi_Cmnd *) = NULL;
418 static Scsi_Cmnd * SCint = NULL;
419
420
421
422
423
424
425 #define NO_RECONNECT 0
426 #define RECONNECT_NOW 1
427 #define CAN_RECONNECT 2
428
429 #ifdef LINKED
430
431
432
433
434
435
436
437 #define LINKED_RIGHT 3
438 #define LINKED_WRONG 4
439 #endif
440
441
442
443
444
445 static int should_reconnect = 0;
446
447
448
449
450
451
452
453 static void seagate_reconnect_intr (int unused)
454 {
455 int temp;
456 Scsi_Cmnd * SCtmp;
457
458
459 sti();
460 #if (DEBUG & PHASE_RESELECT)
461 printk("scsi%d : seagate_reconnect_intr() called\n", hostno);
462 #endif
463
464 if (!should_reconnect)
465 printk("scsi%d: unexpected interrupt.\n", hostno);
466 else {
467 should_reconnect = 0;
468
469 #if (DEBUG & PHASE_RESELECT)
470 printk("scsi%d : internal_command("
471 "%d, %08x, %08x, %d, RECONNECT_NOW\n", hostno,
472 current_target, current_data, current_bufflen);
473 #endif
474
475 temp = internal_command (current_target, current_lun,
476 current_cmnd, current_data, current_bufflen,
477 RECONNECT_NOW);
478
479 if (msg_byte(temp) != DISCONNECT) {
480 if (done_fn) {
481 #if (DEBUG & PHASE_RESELECT)
482 printk("scsi%d : done_fn(%d,%08x)", hostno,
483 hostno, temp);
484 #endif
485 if(!SCint) panic("SCint == NULL in seagate");
486 SCtmp = SCint;
487 SCint = NULL;
488 SCtmp->result = temp;
489 done_fn (SCtmp);
490 } else
491 printk("done_fn() not defined.\n");
492 }
493 }
494 }
495
496
497
498
499
500
501
502
503
504
505
506
507 static int recursion_depth = 0;
508
509 int seagate_st0x_queue_command (Scsi_Cmnd * SCpnt, void (*done)(Scsi_Cmnd *))
510 {
511 int result, reconnect;
512 Scsi_Cmnd * SCtmp;
513
514 done_fn = done;
515 current_target = SCpnt->target;
516 current_lun = SCpnt->lun;
517 (const void *) current_cmnd = SCpnt->cmnd;
518 current_data = (unsigned char *) SCpnt->request_buffer;
519 current_bufflen = SCpnt->request_bufflen;
520 SCint = SCpnt;
521 if(recursion_depth) {
522 return 0;
523 };
524 recursion_depth++;
525 do{
526 #ifdef LINKED
527
528
529
530
531 current_cmnd[SCpnt->cmd_len] |= 0x01;
532 if (linked_connected) {
533 #if (DEBUG & DEBUG_LINKED)
534 printk("scsi%d : using linked commands, current I_T_L nexus is ",
535 hostno);
536 #endif
537 if ((linked_target == current_target) &&
538 (linked_lun == current_lun)) {
539 #if (DEBUG & DEBUG_LINKED)
540 printk("correct\n");
541 #endif
542 reconnect = LINKED_RIGHT;
543 } else {
544 #if (DEBUG & DEBUG_LINKED)
545 printk("incorrect\n");
546 #endif
547 reconnect = LINKED_WRONG;
548 }
549 } else
550 #endif
551 reconnect = CAN_RECONNECT;
552
553
554
555
556
557 result = internal_command (SCint->target, SCint->lun, SCint->cmnd, SCint->request_buffer,
558 SCint->request_bufflen,
559 reconnect);
560 if (msg_byte(result) == DISCONNECT) break;
561 SCtmp = SCint;
562 SCint = NULL;
563 SCtmp->result = result;
564 done_fn (SCtmp);
565 } while(SCint);
566 recursion_depth--;
567 return 0;
568 }
569
570 int seagate_st0x_command (Scsi_Cmnd * SCpnt) {
571 return internal_command (SCpnt->target, SCpnt->lun, SCpnt->cmnd, SCpnt->request_buffer,
572 SCpnt->request_bufflen,
573 (int) NO_RECONNECT);
574 }
575
576 static int internal_command(unsigned char target, unsigned char lun, const void *cmnd,
577 void *buff, int bufflen, int reselect) {
578 int len = 0;
579 unsigned char *data = NULL;
580 struct scatterlist *buffer = NULL;
581 int nobuffs = 0;
582 int clock;
583 int temp;
584 #ifdef SLOW_HANDSHAKE
585 int borken;
586 #endif
587
588
589 #if (DEBUG & PHASE_DATAIN) || (DEBUG & PHASE_DATOUT)
590 int transfered = 0;
591 #endif
592
593 #if (((DEBUG & PHASE_ETC) == PHASE_ETC) || (DEBUG & PRINT_COMMAND) || \
594 (DEBUG & PHASE_EXIT))
595 int i;
596 #endif
597
598 #if ((DEBUG & PHASE_ETC) == PHASE_ETC)
599 int phase=0, newphase;
600 #endif
601
602 int done = 0;
603 unsigned char status = 0;
604 unsigned char message = 0;
605 register unsigned char status_read;
606
607 unsigned transfersize = 0, underflow = 0;
608
609 incommand = 0;
610 st0x_aborted = 0;
611
612 #ifdef SLOW_HANDSHAKE
613 borken = (int) SCint->device->borken;
614 #endif
615
616 #if (DEBUG & PRINT_COMMAND)
617 printk ("scsi%d : target = %d, command = ", hostno, target);
618 print_command((unsigned char *) cmnd);
619 printk("\n");
620 #endif
621
622 #if (DEBUG & PHASE_RESELECT)
623 switch (reselect) {
624 case RECONNECT_NOW :
625 printk("scsi%d : reconnecting\n", hostno);
626 break;
627 #ifdef LINKED
628 case LINKED_RIGHT :
629 printk("scsi%d : connected, can reconnect\n", hostno);
630 break;
631 case LINKED_WRONG :
632 printk("scsi%d : connected to wrong target, can reconnect\n",
633 hostno);
634 break;
635 #endif
636 case CAN_RECONNECT :
637 printk("scsi%d : allowed to reconnect\n", hostno);
638 break;
639 default :
640 printk("scsi%d : not allowed to reconnect\n", hostno);
641 }
642 #endif
643
644
645 if (target == (controller_type == SEAGATE ? 7 : 6))
646 return DID_BAD_TARGET;
647
648
649
650
651
652
653
654 switch (reselect) {
655 case RECONNECT_NOW:
656 #if (DEBUG & PHASE_RESELECT)
657 printk("scsi%d : phase RESELECT \n", hostno);
658 #endif
659
660
661
662
663
664
665
666
667
668 clock = jiffies + 10;
669 for (;;) {
670 temp = STATUS;
671 if ((temp & STAT_IO) && !(temp & STAT_BSY))
672 break;
673
674 if (jiffies > clock) {
675 #if (DEBUG & PHASE_RESELECT)
676 printk("scsi%d : RESELECT timed out while waiting for IO .\n",
677 hostno);
678 #endif
679 return (DID_BAD_INTR << 16);
680 }
681 }
682
683
684
685
686
687
688 if (!((temp = DATA) & (controller_type == SEAGATE ? 0x80 : 0x40)))
689 {
690 #if (DEBUG & PHASE_RESELECT)
691 printk("scsi%d : detected reconnect request to different target.\n"
692 "\tData bus = %d\n", hostno, temp);
693 #endif
694 return (DID_BAD_INTR << 16);
695 }
696
697 if (!(temp & (1 << current_target)))
698 {
699 printk("scsi%d : Unexpected reselect interrupt. Data bus = %d\n",
700 hostno, temp);
701 return (DID_BAD_INTR << 16);
702 }
703
704 buffer=current_buffer;
705 cmnd=current_cmnd;
706 data=current_data;
707 len=current_bufflen;
708 nobuffs=current_nobuffs;
709
710
711
712
713
714
715 #if 1
716 CONTROL = (BASE_CMD | CMD_DRVR_ENABLE | CMD_BSY);
717 #else
718 CONTROL = (BASE_CMD | CMD_BSY);
719 #endif
720
721
722
723
724
725
726 for (clock = jiffies + 10; (jiffies < clock) && (STATUS & STAT_SEL););
727
728 if (jiffies >= clock)
729 {
730 CONTROL = (BASE_CMD | CMD_INTR);
731 #if (DEBUG & PHASE_RESELECT)
732 printk("scsi%d : RESELECT timed out while waiting for SEL.\n",
733 hostno);
734 #endif
735 return (DID_BAD_INTR << 16);
736 }
737
738 CONTROL = BASE_CMD;
739
740
741
742
743
744 break;
745 case CAN_RECONNECT:
746
747 #ifdef LINKED
748
749
750
751
752
753
754
755 connect_loop :
756
757 #endif
758
759 #if (DEBUG & PHASE_BUS_FREE)
760 printk ("scsi%d : phase = BUS FREE \n", hostno);
761 #endif
762
763
764
765
766
767
768
769
770
771
772 clock = jiffies + ST0X_BUS_FREE_DELAY;
773
774 #if !defined (ARBITRATE)
775 while (((STATUS | STATUS | STATUS) &
776 (STAT_BSY | STAT_SEL)) &&
777 (!st0x_aborted) && (jiffies < clock));
778
779 if (jiffies > clock)
780 return retcode(DID_BUS_BUSY);
781 else if (st0x_aborted)
782 return retcode(st0x_aborted);
783 #endif
784
785 #if (DEBUG & PHASE_SELECTION)
786 printk("scsi%d : phase = SELECTION\n", hostno);
787 #endif
788
789 clock = jiffies + ST0X_SELECTION_DELAY;
790
791
792
793
794
795
796
797
798
799
800
801
802 #if defined(ARBITRATE)
803 cli();
804 CONTROL = 0;
805 DATA = (controller_type == SEAGATE) ? 0x80 : 0x40;
806 CONTROL = CMD_START_ARB;
807 sti();
808 while (!((status_read = STATUS) & (STAT_ARB_CMPL | STAT_SEL)) &&
809 (jiffies < clock) && !st0x_aborted);
810
811 if (!(status_read & STAT_ARB_CMPL)) {
812 #if (DEBUG & PHASE_SELECTION)
813 if (status_read & STAT_SEL)
814 printk("scsi%d : arbitration lost\n", hostno);
815 else
816 printk("scsi%d : arbitration timeout.\n", hostno);
817 #endif
818 CONTROL = BASE_CMD;
819 return retcode(DID_NO_CONNECT);
820 };
821
822 #if (DEBUG & PHASE_SELECTION)
823 printk("scsi%d : arbitration complete\n", hostno);
824 #endif
825 #endif
826
827
828
829
830
831
832
833
834
835
836
837
838
839
840 cli();
841 DATA = (unsigned char) ((1 << target) | (controller_type == SEAGATE ? 0x80 : 0x40));
842 CONTROL = BASE_CMD | CMD_DRVR_ENABLE | CMD_SEL |
843 (reselect ? CMD_ATTN : 0);
844 sti();
845 while (!((status_read = STATUS) & STAT_BSY) &&
846 (jiffies < clock) && !st0x_aborted)
847
848 #if 0 && (DEBUG & PHASE_SELECTION)
849 {
850 temp = clock - jiffies;
851
852 if (!(jiffies % 5))
853 printk("seagate_st0x_timeout : %d \r",temp);
854
855 }
856 printk("Done. \n");
857 printk("scsi%d : status = %02x, seagate_st0x_timeout = %d, aborted = %02x \n",
858 hostno, status_read, temp, st0x_aborted);
859 #else
860 ;
861 #endif
862
863
864 if ((jiffies >= clock) && !(status_read & STAT_BSY))
865 {
866 #if (DEBUG & PHASE_SELECTION)
867 printk ("scsi%d : NO CONNECT with target %d, status = %x \n",
868 hostno, target, STATUS);
869 #endif
870 return retcode(DID_NO_CONNECT);
871 }
872
873
874
875
876
877
878
879 if (st0x_aborted) {
880 CONTROL = BASE_CMD;
881 if (STATUS & STAT_BSY) {
882 printk("scsi%d : BST asserted after we've been aborted.\n",
883 hostno);
884 seagate_st0x_reset(NULL);
885 return retcode(DID_RESET);
886 }
887 return retcode(st0x_aborted);
888 }
889
890
891
892 if ((nobuffs = SCint->use_sg)) {
893 #if (DEBUG & DEBUG_SG)
894 {
895 int i;
896 printk("scsi%d : scatter gather requested, using %d buffers.\n",
897 hostno, nobuffs);
898 for (i = 0; i < nobuffs; ++i)
899 printk("scsi%d : buffer %d address = %08x length = %d\n",
900 hostno, i, buffer[i].address, buffer[i].length);
901 }
902 #endif
903
904 buffer = (struct scatterlist *) SCint->buffer;
905 len = buffer->length;
906 data = (unsigned char *) buffer->address;
907 } else {
908 #if (DEBUG & DEBUG_SG)
909 printk("scsi%d : scatter gather not requested.\n", hostno);
910 #endif
911 buffer = NULL;
912 len = SCint->request_bufflen;
913 data = (unsigned char *) SCint->request_buffer;
914 }
915
916 #if (DEBUG & (PHASE_DATAIN | PHASE_DATAOUT))
917 printk("scsi%d : len = %d\n", hostno, len);
918 #endif
919
920 break;
921 #ifdef LINKED
922 case LINKED_RIGHT:
923 break;
924 case LINKED_WRONG:
925 break;
926 #endif
927 }
928
929
930
931
932
933
934
935
936
937
938
939 CONTROL = BASE_CMD | CMD_DRVR_ENABLE |
940 (((reselect == CAN_RECONNECT)
941 #ifdef LINKED
942 || (reselect == LINKED_WRONG)
943 #endif
944 ) ? CMD_ATTN : 0) ;
945
946
947
948
949
950
951
952
953
954
955 #if ((DEBUG & PHASE_ETC) == PHASE_ETC)
956 printk("scsi%d : phase = INFORMATION TRANSFER\n", hostno);
957 #endif
958
959 incommand = 1;
960 transfersize = SCint->transfersize;
961 underflow = SCint->underflow;
962
963
964
965
966
967
968
969
970
971
972 while (((status_read = STATUS) & STAT_BSY) && !st0x_aborted && !done)
973 {
974 #ifdef PARITY
975 if (status_read & STAT_PARITY)
976 {
977 printk("scsi%d : got parity error\n", hostno);
978 st0x_aborted = DID_PARITY;
979 }
980 #endif
981
982 if (status_read & STAT_REQ)
983 {
984 #if ((DEBUG & PHASE_ETC) == PHASE_ETC)
985 if ((newphase = (status_read & REQ_MASK)) != phase)
986 {
987 phase = newphase;
988 switch (phase)
989 {
990 case REQ_DATAOUT:
991 printk("scsi%d : phase = DATA OUT\n",
992 hostno);
993 break;
994 case REQ_DATAIN :
995 printk("scsi%d : phase = DATA IN\n",
996 hostno);
997 break;
998 case REQ_CMDOUT :
999 printk("scsi%d : phase = COMMAND OUT\n",
1000 hostno);
1001 break;
1002 case REQ_STATIN :
1003 printk("scsi%d : phase = STATUS IN\n",
1004 hostno);
1005 break;
1006 case REQ_MSGOUT :
1007 printk("scsi%d : phase = MESSAGE OUT\n",
1008 hostno);
1009 break;
1010 case REQ_MSGIN :
1011 printk("scsi%d : phase = MESSAGE IN\n",
1012 hostno);
1013 break;
1014 default :
1015 printk("scsi%d : phase = UNKNOWN\n",
1016 hostno);
1017 st0x_aborted = DID_ERROR;
1018 }
1019 }
1020 #endif
1021 switch (status_read & REQ_MASK)
1022 {
1023 case REQ_DATAOUT :
1024
1025
1026
1027
1028
1029 #ifdef FAST
1030 if (!len) {
1031 #if 0
1032 printk("scsi%d: underflow to target %d lun %d \n",
1033 hostno, target, lun);
1034 st0x_aborted = DID_ERROR;
1035 fast = 0;
1036 #endif
1037 break;
1038 }
1039
1040 if (fast && transfersize && !(len % transfersize) && (len >= transfersize)
1041 #ifdef FAST32
1042 && !(transfersize % 4)
1043 #endif
1044 ) {
1045 #if (DEBUG & DEBUG_FAST)
1046 printk("scsi%d : FAST transfer, underflow = %d, transfersize = %d\n"
1047 " len = %d, data = %08x\n", hostno, SCint->underflow,
1048 SCint->transfersize, len, data);
1049 #endif
1050
1051 __asm__("
1052 cld;
1053 "
1054 #ifdef FAST32
1055 " shr $2, %%ecx;
1056 1: lodsl;
1057 movl %%eax, (%%edi);
1058 "
1059 #else
1060 "1: lodsb;
1061 movb %%al, (%%edi);
1062 "
1063 #endif
1064 " loop 1b;" : :
1065
1066 "D" (st0x_dr), "S" (data), "c" (SCint->transfersize) :
1067
1068 "eax", "ecx", "esi" );
1069
1070 len -= transfersize;
1071 data += transfersize;
1072
1073 #if (DEBUG & DEBUG_FAST)
1074 printk("scsi%d : FAST transfer complete len = %d data = %08x\n",
1075 hostno, len, data);
1076 #endif
1077
1078
1079 } else
1080 #endif
1081
1082 {
1083
1084
1085
1086
1087 __asm__ (
1088
1089
1090
1091
1092
1093
1094
1095
1096
1097
1098 "\torl %%ecx, %%ecx
1099 jz 2f
1100
1101 cld
1102
1103 movl _st0x_cr_sr, %%ebx
1104 movl _st0x_dr, %%edi
1105
1106 1: movb (%%ebx), %%al\n"
1107
1108
1109
1110
1111 "\ttest $1, %%al
1112 jz 2f\n"
1113
1114
1115
1116
1117 "\ttest $0xe, %%al
1118 jnz 2f \n"
1119
1120
1121
1122 "\ttest $0x10, %%al
1123 jz 1b
1124 lodsb
1125 movb %%al, (%%edi)
1126 loop 1b
1127
1128 2:
1129 ":
1130
1131 "=S" (data), "=c" (len) :
1132
1133 "0" (data), "1" (len) :
1134
1135 "eax", "ebx", "edi");
1136 }
1137
1138 if (!len && nobuffs) {
1139 --nobuffs;
1140 ++buffer;
1141 len = buffer->length;
1142 data = (unsigned char *) buffer->address;
1143 #if (DEBUG & DEBUG_SG)
1144 printk("scsi%d : next scatter-gather buffer len = %d address = %08x\n",
1145 hostno, len, data);
1146 #endif
1147 }
1148 break;
1149
1150 case REQ_DATAIN :
1151 #ifdef SLOW_HANDSHAKE
1152 if (borken) {
1153 #if (DEBUG & (PHASE_DATAIN))
1154 transfered += len;
1155 #endif
1156 for (; len && (STATUS & (REQ_MASK | STAT_REQ)) == (REQ_DATAIN |
1157 STAT_REQ); --len) {
1158 *data++ = DATA;
1159 borken_wait();
1160 }
1161 #if (DEBUG & (PHASE_DATAIN))
1162 transfered -= len;
1163 #endif
1164 } else
1165 #endif
1166 #ifdef FAST
1167 if (fast && transfersize && !(len % transfersize) && (len >= transfersize)
1168 #ifdef FAST32
1169 && !(transfersize % 4)
1170 #endif
1171 ) {
1172 #if (DEBUG & DEBUG_FAST)
1173 printk("scsi%d : FAST transfer, underflow = %d, transfersize = %d\n"
1174 " len = %d, data = %08x\n", hostno, SCint->underflow,
1175 SCint->transfersize, len, data);
1176 #endif
1177 __asm__("
1178 cld;
1179 "
1180 #ifdef FAST32
1181 " shr $2, %%ecx;
1182 1: movl (%%esi), %%eax;
1183 stosl;
1184 "
1185 #else
1186 "1: movb (%%esi), %%al;
1187 stosb;
1188 "
1189 #endif
1190
1191 " loop 1b;" : :
1192
1193 "S" (st0x_dr), "D" (data), "c" (SCint->transfersize) :
1194
1195 "eax", "ecx", "edi");
1196
1197 len -= transfersize;
1198 data += transfersize;
1199
1200 #if (DEBUG & PHASE_DATAIN)
1201 printk("scsi%d: transfered += %d\n", hostno, transfersize);
1202 transfered += transfersize;
1203 #endif
1204
1205 #if (DEBUG & DEBUG_FAST)
1206 printk("scsi%d : FAST transfer complete len = %d data = %08x\n",
1207 hostno, len, data);
1208 #endif
1209
1210 } else
1211 #endif
1212 {
1213
1214 #if (DEBUG & PHASE_DATAIN)
1215 printk("scsi%d: transfered += %d\n", hostno, len);
1216 transfered += len;
1217
1218 #endif
1219
1220
1221
1222
1223
1224
1225 __asm__ (
1226
1227
1228
1229
1230
1231
1232
1233
1234
1235 "\torl %%ecx, %%ecx
1236 jz 2f
1237
1238 cld
1239 movl _st0x_cr_sr, %%esi
1240 movl _st0x_dr, %%ebx
1241
1242 1: movb (%%esi), %%al\n"
1243
1244
1245
1246
1247 "\ttest $1, %%al
1248 jz 2f\n"
1249
1250
1251
1252
1253 "\tmovb $0xe, %%ah
1254 andb %%al, %%ah
1255 cmpb $0x04, %%ah
1256 jne 2f\n"
1257
1258
1259
1260
1261 "\ttest $0x10, %%al
1262 jz 1b
1263
1264 movb (%%ebx), %%al
1265 stosb
1266 loop 1b\n"
1267
1268 "2:\n"
1269 :
1270
1271 "=D" (data), "=c" (len) :
1272
1273 "0" (data), "1" (len) :
1274
1275 "eax","ebx", "esi");
1276
1277 #if (DEBUG & PHASE_DATAIN)
1278 printk("scsi%d: transfered -= %d\n", hostno, len);
1279 transfered -= len;
1280
1281 #endif
1282 }
1283
1284 if (!len && nobuffs) {
1285 --nobuffs;
1286 ++buffer;
1287 len = buffer->length;
1288 data = (unsigned char *) buffer->address;
1289 #if (DEBUG & DEBUG_SG)
1290 printk("scsi%d : next scatter-gather buffer len = %d address = %08x\n",
1291 hostno, len, data);
1292 #endif
1293 }
1294
1295 break;
1296
1297 case REQ_CMDOUT :
1298 while (((status_read = STATUS) & STAT_BSY) &&
1299 ((status_read & REQ_MASK) == REQ_CMDOUT))
1300 if (status_read & STAT_REQ) {
1301 DATA = *(unsigned char *) cmnd;
1302 cmnd = 1+(unsigned char *) cmnd;
1303 #ifdef SLOW_HANDSHAKE
1304 if (borken)
1305 borken_wait();
1306 #endif
1307 }
1308 break;
1309
1310 case REQ_STATIN :
1311 status = DATA;
1312 break;
1313
1314 case REQ_MSGOUT :
1315
1316
1317
1318
1319
1320 CONTROL = BASE_CMD | CMD_DRVR_ENABLE;
1321
1322
1323
1324
1325 switch (reselect) {
1326 case CAN_RECONNECT:
1327 DATA = IDENTIFY(1, lun);
1328
1329 #if (DEBUG & (PHASE_RESELECT | PHASE_MSGOUT))
1330 printk("scsi%d : sent IDENTIFY message.\n", hostno);
1331 #endif
1332 break;
1333 #ifdef LINKED
1334 case LINKED_WRONG:
1335 DATA = ABORT;
1336 linked_connected = 0;
1337 reselect = CAN_RECONNECT;
1338 goto connect_loop;
1339 #if (DEBUG & (PHASE_MSGOUT | DEBUG_LINKED))
1340 printk("scsi%d : sent ABORT message to cancel incorrect I_T_L nexus.\n", hostno);
1341 #endif
1342 #endif
1343 #if (DEBUG & DEBUG_LINKED)
1344 printk("correct\n");
1345 #endif
1346 default:
1347 DATA = NOP;
1348 printk("scsi%d : target %d requested MSGOUT, sent NOP message.\n", hostno, target);
1349 }
1350 break;
1351
1352 case REQ_MSGIN :
1353 switch (message = DATA) {
1354 case DISCONNECT :
1355 should_reconnect = 1;
1356 current_data = data;
1357 current_buffer = buffer;
1358 current_bufflen = len;
1359 current_nobuffs = nobuffs;
1360 #ifdef LINKED
1361 linked_connected = 0;
1362 #endif
1363 done=1;
1364 #if (DEBUG & (PHASE_RESELECT | PHASE_MSGIN))
1365 printk("scsi%d : disconnected.\n", hostno);
1366 #endif
1367 break;
1368
1369 #ifdef LINKED
1370 case LINKED_CMD_COMPLETE:
1371 case LINKED_FLG_CMD_COMPLETE:
1372 #endif
1373 case COMMAND_COMPLETE :
1374
1375
1376
1377 #if (DEBUG & PHASE_MSGIN)
1378 printk("scsi%d : command complete.\n", hostno);
1379 #endif
1380 done = 1;
1381 break;
1382 case ABORT :
1383 #if (DEBUG & PHASE_MSGIN)
1384 printk("scsi%d : abort message.\n", hostno);
1385 #endif
1386 done=1;
1387 break;
1388 case SAVE_POINTERS :
1389 current_buffer = buffer;
1390 current_bufflen = len;
1391 current_data = data;
1392 current_nobuffs = nobuffs;
1393 #if (DEBUG & PHASE_MSGIN)
1394 printk("scsi%d : pointers saved.\n", hostno);
1395 #endif
1396 break;
1397 case RESTORE_POINTERS:
1398 buffer=current_buffer;
1399 cmnd=current_cmnd;
1400 data=current_data;
1401 len=current_bufflen;
1402 nobuffs=current_nobuffs;
1403 #if (DEBUG & PHASE_MSGIN)
1404 printk("scsi%d : pointers restored.\n", hostno);
1405 #endif
1406 break;
1407 default:
1408
1409
1410
1411
1412
1413
1414
1415
1416
1417
1418 if (message & 0x80) {
1419 #if (DEBUG & PHASE_MSGIN)
1420 printk("scsi%d : IDENTIFY message received from id %d, lun %d.\n",
1421 hostno, target, message & 7);
1422 #endif
1423 } else {
1424
1425
1426
1427
1428
1429
1430
1431 #if (DEBUG & PHASE_MSGIN)
1432 printk("scsi%d : unknown message %d from target %d.\n",
1433 hostno, message, target);
1434 #endif
1435 }
1436 }
1437 break;
1438
1439 default :
1440 printk("scsi%d : unknown phase.\n", hostno);
1441 st0x_aborted = DID_ERROR;
1442 }
1443
1444 #ifdef SLOW_HANDSHAKE
1445
1446
1447
1448
1449
1450 if (borken)
1451 borken_wait();
1452 #endif
1453
1454 }
1455 }
1456
1457 #if (DEBUG & (PHASE_DATAIN | PHASE_DATAOUT | PHASE_EXIT))
1458 printk("scsi%d : Transfered %d bytes\n", hostno, transfered);
1459 #endif
1460
1461 #if (DEBUG & PHASE_EXIT)
1462 #if 0
1463 printk("Buffer : \n");
1464 for (i = 0; i < 20; ++i)
1465 printk ("%02x ", ((unsigned char *) data)[i]);
1466 printk("\n");
1467 #endif
1468 printk("scsi%d : status = ", hostno);
1469 print_status(status);
1470 printk("message = %02x\n", message);
1471 #endif
1472
1473
1474
1475 #ifdef notyet
1476 if (st0x_aborted) {
1477 if (STATUS & STAT_BSY) {
1478 seagate_st0x_reset(NULL);
1479 st0x_aborted = DID_RESET;
1480 }
1481 abort_confirm = 1;
1482 }
1483 #endif
1484
1485 #ifdef LINKED
1486 else {
1487
1488
1489
1490
1491
1492
1493
1494
1495
1496
1497 switch (message) {
1498 case LINKED_CMD_COMPLETE :
1499 case LINKED_FLG_CMD_COMPLETE :
1500 message = COMMAND_COMPLETE;
1501 linked_target = current_target;
1502 linked_lun = current_lun;
1503 linked_connected = 1;
1504 #if (DEBUG & DEBUG_LINKED)
1505 printk("scsi%d : keeping I_T_L nexus established for linked command.\n",
1506 hostno);
1507 #endif
1508
1509
1510
1511 if ((status == INTERMEDIATE_GOOD) ||
1512 (status == INTERMEDIATE_C_GOOD))
1513 status = GOOD;
1514
1515 break;
1516
1517
1518
1519
1520
1521
1522 default :
1523 #if (DEBUG & DEBUG_LINKED)
1524 printk("scsi%d : closing I_T_L nexus.\n", hostno);
1525 #endif
1526 linked_connected = 0;
1527 }
1528 }
1529 #endif
1530
1531
1532
1533
1534 if (should_reconnect) {
1535 #if (DEBUG & PHASE_RESELECT)
1536 printk("scsi%d : exiting seagate_st0x_queue_command() with reconnect enabled.\n",
1537 hostno);
1538 #endif
1539 CONTROL = BASE_CMD | CMD_INTR ;
1540 } else
1541 CONTROL = BASE_CMD;
1542
1543 return retcode (st0x_aborted);
1544 }
1545
1546 int seagate_st0x_abort (Scsi_Cmnd * SCpnt)
1547 {
1548 st0x_aborted = DID_ABORT;
1549
1550 return SCSI_ABORT_PENDING;
1551 }
1552
1553
1554
1555
1556
1557 int seagate_st0x_reset (Scsi_Cmnd * SCpnt)
1558 {
1559 unsigned clock;
1560
1561
1562
1563
1564
1565 #ifdef DEBUG
1566 printk("In seagate_st0x_reset()\n");
1567 #endif
1568
1569
1570
1571
1572 CONTROL = BASE_CMD | CMD_RST;
1573 clock=jiffies+2;
1574
1575
1576
1577
1578 while (jiffies < clock);
1579
1580 CONTROL = BASE_CMD;
1581
1582 st0x_aborted = DID_RESET;
1583
1584 #ifdef DEBUG
1585 printk("SCSI bus reset.\n");
1586 #endif
1587 return SCSI_RESET_WAKEUP;
1588 }
1589
1590 #include <asm/segment.h>
1591 #include "sd.h"
1592 #include "scsi_ioctl.h"
1593
1594 int seagate_st0x_biosparam(Disk * disk, int dev, int* ip) {
1595 unsigned char buf[256 + sizeof(int) * 2], cmd[6], *data, *page;
1596 int *sizes, result, formatted_sectors, total_sectors;
1597 int cylinders, heads, sectors;
1598
1599
1600
1601
1602
1603
1604 if (disk->device->scsi_level < 2)
1605 return -1;
1606
1607 sizes = (int *) buf;
1608 data = (unsigned char *) (sizes + 2);
1609
1610 cmd[0] = MODE_SENSE;
1611 cmd[1] = (disk->device->lun << 5) & 0xe5;
1612 cmd[2] = 0x04;
1613 cmd[3] = 0;
1614 cmd[4] = 255;
1615 cmd[5] = 0;
1616
1617
1618
1619
1620
1621
1622 sizes[0] = 0;
1623 sizes[1] = 256;
1624
1625 memcpy (data, cmd, 6);
1626
1627 if (!(result = kernel_scsi_ioctl (disk->device, SCSI_IOCTL_SEND_COMMAND, (void *) buf))) {
1628
1629
1630
1631
1632
1633 page = data + 4 + data[3];
1634 heads = (int) page[5];
1635 cylinders = (page[2] << 16) | (page[3] << 8) | page[4];
1636
1637 cmd[2] = 0x03;
1638 memcpy (data, cmd, 6);
1639
1640 if (!(result = kernel_scsi_ioctl (disk->device, SCSI_IOCTL_SEND_COMMAND, (void *) buf))) {
1641 page = data + 4 + data[3];
1642 sectors = (page[10] << 8) | page[11];
1643
1644
1645
1646
1647
1648
1649
1650 formatted_sectors = (data[4 + 1] << 16) | (data[4 + 2] << 8) |
1651 data[4 + 3] ;
1652
1653 total_sectors = (heads * cylinders * sectors);
1654
1655
1656
1657
1658
1659
1660
1661
1662
1663 printk("scsi%d : heads = %d cylinders = %d sectors = %d total = %d formatted = %d\n",
1664 hostno, heads, cylinders, sectors, total_sectors, formatted_sectors);
1665
1666 if (!heads || !sectors || !cylinders)
1667 result = -1;
1668 else
1669 cylinders -= ((total_sectors - formatted_sectors) / (heads * sectors));
1670
1671
1672
1673
1674
1675
1676
1677 if ((cylinders > 1024) || (sectors > 64))
1678 result = -1;
1679 else {
1680 ip[0] = heads;
1681 ip[1] = sectors;
1682 ip[2] = cylinders;
1683 }
1684
1685
1686
1687
1688
1689
1690 }
1691 }
1692
1693 return result;
1694 }