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#include <scsi/scsi_dbg.h>
73#include <scsi/scsi_transport_spi.h>
74
75
76
77
78
79
80
81#if (NDEBUG & NDEBUG_LISTS)
82#define LIST(x,y) \
83 { printk("LINE:%d Adding %p to %p\n", __LINE__, (void*)(x), (void*)(y)); \
84 if ((x)==(y)) udelay(5); }
85#define REMOVE(w,x,y,z) \
86 { printk("LINE:%d Removing: %p->%p %p->%p \n", __LINE__, \
87 (void*)(w), (void*)(x), (void*)(y), (void*)(z)); \
88 if ((x)==(y)) udelay(5); }
89#else
90#define LIST(x,y)
91#define REMOVE(w,x,y,z)
92#endif
93
94#ifndef notyet
95#undef LINKED
96#endif
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
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
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
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260static struct Scsi_Host *first_instance = NULL;
261static struct scsi_host_template *the_template = NULL;
262
263
264#define SETUP_HOSTDATA(in) \
265 struct NCR5380_hostdata *hostdata = \
266 (struct NCR5380_hostdata *)(in)->hostdata
267#define HOSTDATA(in) ((struct NCR5380_hostdata *)(in)->hostdata)
268
269#define NEXT(cmd) (*(struct scsi_cmnd **)&((cmd)->host_scribble))
270#define NEXTADDR(cmd) ((struct scsi_cmnd **)&((cmd)->host_scribble))
271
272#define HOSTNO instance->host_no
273#define H_NO(cmd) (cmd)->device->host->host_no
274
275#define SGADDR(buffer) (void *)(((unsigned long)sg_virt(((buffer)))))
276
277#ifdef SUPPORT_TAGS
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315#undef TAG_NONE
316#define TAG_NONE 0xff
317
318
319#if (MAX_TAGS % 32) != 0
320#error "MAX_TAGS must be a multiple of 32!"
321#endif
322
323typedef struct {
324 char allocated[MAX_TAGS/8];
325 int nr_allocated;
326 int queue_size;
327} TAG_ALLOC;
328
329static TAG_ALLOC TagAlloc[8][8];
330
331
332static void __init init_tags( void )
333{
334 int target, lun;
335 TAG_ALLOC *ta;
336
337 if (!setup_use_tagged_queuing)
338 return;
339
340 for( target = 0; target < 8; ++target ) {
341 for( lun = 0; lun < 8; ++lun ) {
342 ta = &TagAlloc[target][lun];
343 memset( &ta->allocated, 0, MAX_TAGS/8 );
344 ta->nr_allocated = 0;
345
346
347
348
349 ta->queue_size = MAX_TAGS;
350 }
351 }
352}
353
354
355
356
357
358
359
360
361
362static int is_lun_busy(struct scsi_cmnd *cmd, int should_be_tagged)
363{
364 SETUP_HOSTDATA(cmd->device->host);
365
366 if (hostdata->busy[cmd->device->id] & (1 << cmd->device->lun))
367 return( 1 );
368 if (!should_be_tagged ||
369 !setup_use_tagged_queuing || !cmd->device->tagged_supported)
370 return( 0 );
371 if (TagAlloc[cmd->device->id][cmd->device->lun].nr_allocated >=
372 TagAlloc[cmd->device->id][cmd->device->lun].queue_size ) {
373 TAG_PRINTK( "scsi%d: target %d lun %d: no free tags\n",
374 H_NO(cmd), cmd->device->id, cmd->device->lun );
375 return( 1 );
376 }
377 return( 0 );
378}
379
380
381
382
383
384
385
386static void cmd_get_tag(struct scsi_cmnd *cmd, int should_be_tagged)
387{
388 SETUP_HOSTDATA(cmd->device->host);
389
390
391
392
393 if (!should_be_tagged ||
394 !setup_use_tagged_queuing || !cmd->device->tagged_supported) {
395 cmd->tag = TAG_NONE;
396 hostdata->busy[cmd->device->id] |= (1 << cmd->device->lun);
397 TAG_PRINTK( "scsi%d: target %d lun %d now allocated by untagged "
398 "command\n", H_NO(cmd), cmd->device->id, cmd->device->lun );
399 }
400 else {
401 TAG_ALLOC *ta = &TagAlloc[cmd->device->id][cmd->device->lun];
402
403 cmd->tag = find_first_zero_bit( &ta->allocated, MAX_TAGS );
404 set_bit( cmd->tag, &ta->allocated );
405 ta->nr_allocated++;
406 TAG_PRINTK( "scsi%d: using tag %d for target %d lun %d "
407 "(now %d tags in use)\n",
408 H_NO(cmd), cmd->tag, cmd->device->id, cmd->device->lun,
409 ta->nr_allocated );
410 }
411}
412
413
414
415
416
417
418static void cmd_free_tag(struct scsi_cmnd *cmd)
419{
420 SETUP_HOSTDATA(cmd->device->host);
421
422 if (cmd->tag == TAG_NONE) {
423 hostdata->busy[cmd->device->id] &= ~(1 << cmd->device->lun);
424 TAG_PRINTK( "scsi%d: target %d lun %d untagged cmd finished\n",
425 H_NO(cmd), cmd->device->id, cmd->device->lun );
426 }
427 else if (cmd->tag >= MAX_TAGS) {
428 printk(KERN_NOTICE "scsi%d: trying to free bad tag %d!\n",
429 H_NO(cmd), cmd->tag );
430 }
431 else {
432 TAG_ALLOC *ta = &TagAlloc[cmd->device->id][cmd->device->lun];
433 clear_bit( cmd->tag, &ta->allocated );
434 ta->nr_allocated--;
435 TAG_PRINTK( "scsi%d: freed tag %d for target %d lun %d\n",
436 H_NO(cmd), cmd->tag, cmd->device->id, cmd->device->lun );
437 }
438}
439
440
441static void free_all_tags( void )
442{
443 int target, lun;
444 TAG_ALLOC *ta;
445
446 if (!setup_use_tagged_queuing)
447 return;
448
449 for( target = 0; target < 8; ++target ) {
450 for( lun = 0; lun < 8; ++lun ) {
451 ta = &TagAlloc[target][lun];
452 memset( &ta->allocated, 0, MAX_TAGS/8 );
453 ta->nr_allocated = 0;
454 }
455 }
456}
457
458#endif
459
460
461
462
463
464
465
466
467
468
469
470
471
472
473static void merge_contiguous_buffers(struct scsi_cmnd *cmd)
474{
475 unsigned long endaddr;
476#if (NDEBUG & NDEBUG_MERGING)
477 unsigned long oldlen = cmd->SCp.this_residual;
478 int cnt = 1;
479#endif
480
481 for (endaddr = virt_to_phys(cmd->SCp.ptr + cmd->SCp.this_residual - 1) + 1;
482 cmd->SCp.buffers_residual &&
483 virt_to_phys(SGADDR(&(cmd->SCp.buffer[1]))) == endaddr; ) {
484
485 MER_PRINTK("VTOP(%p) == %08lx -> merging\n",
486 SGADDR(&(cmd->SCp.buffer[1])), endaddr);
487#if (NDEBUG & NDEBUG_MERGING)
488 ++cnt;
489#endif
490 ++cmd->SCp.buffer;
491 --cmd->SCp.buffers_residual;
492 cmd->SCp.this_residual += cmd->SCp.buffer->length;
493 endaddr += cmd->SCp.buffer->length;
494 }
495#if (NDEBUG & NDEBUG_MERGING)
496 if (oldlen != cmd->SCp.this_residual)
497 MER_PRINTK("merged %d buffers from %p, new length %08x\n",
498 cnt, cmd->SCp.ptr, cmd->SCp.this_residual);
499#endif
500}
501
502
503
504
505
506
507
508
509
510
511static __inline__ void initialize_SCp(struct scsi_cmnd *cmd)
512{
513
514
515
516
517
518 if (scsi_bufflen(cmd)) {
519 cmd->SCp.buffer = scsi_sglist(cmd);
520 cmd->SCp.buffers_residual = scsi_sg_count(cmd) - 1;
521 cmd->SCp.ptr = (char *) SGADDR(cmd->SCp.buffer);
522 cmd->SCp.this_residual = cmd->SCp.buffer->length;
523
524
525
526
527
528 } else {
529 cmd->SCp.buffer = NULL;
530 cmd->SCp.buffers_residual = 0;
531 cmd->SCp.ptr = NULL;
532 cmd->SCp.this_residual = 0;
533 }
534
535}
536
537#include <linux/delay.h>
538
539#if 1
540static struct {
541 unsigned char mask;
542 const char * name;}
543signals[] = {{ SR_DBP, "PARITY"}, { SR_RST, "RST" }, { SR_BSY, "BSY" },
544 { SR_REQ, "REQ" }, { SR_MSG, "MSG" }, { SR_CD, "CD" }, { SR_IO, "IO" },
545 { SR_SEL, "SEL" }, {0, NULL}},
546basrs[] = {{BASR_ATN, "ATN"}, {BASR_ACK, "ACK"}, {0, NULL}},
547icrs[] = {{ICR_ASSERT_RST, "ASSERT RST"},{ICR_ASSERT_ACK, "ASSERT ACK"},
548 {ICR_ASSERT_BSY, "ASSERT BSY"}, {ICR_ASSERT_SEL, "ASSERT SEL"},
549 {ICR_ASSERT_ATN, "ASSERT ATN"}, {ICR_ASSERT_DATA, "ASSERT DATA"},
550 {0, NULL}},
551mrs[] = {{MR_BLOCK_DMA_MODE, "MODE BLOCK DMA"}, {MR_TARGET, "MODE TARGET"},
552 {MR_ENABLE_PAR_CHECK, "MODE PARITY CHECK"}, {MR_ENABLE_PAR_INTR,
553 "MODE PARITY INTR"}, {MR_ENABLE_EOP_INTR,"MODE EOP INTR"},
554 {MR_MONITOR_BSY, "MODE MONITOR BSY"},
555 {MR_DMA_MODE, "MODE DMA"}, {MR_ARBITRATE, "MODE ARBITRATION"},
556 {0, NULL}};
557
558
559
560
561
562
563
564
565
566static void NCR5380_print(struct Scsi_Host *instance) {
567 unsigned char status, data, basr, mr, icr, i;
568 unsigned long flags;
569
570 local_irq_save(flags);
571 data = NCR5380_read(CURRENT_SCSI_DATA_REG);
572 status = NCR5380_read(STATUS_REG);
573 mr = NCR5380_read(MODE_REG);
574 icr = NCR5380_read(INITIATOR_COMMAND_REG);
575 basr = NCR5380_read(BUS_AND_STATUS_REG);
576 local_irq_restore(flags);
577 printk("STATUS_REG: %02x ", status);
578 for (i = 0; signals[i].mask ; ++i)
579 if (status & signals[i].mask)
580 printk(",%s", signals[i].name);
581 printk("\nBASR: %02x ", basr);
582 for (i = 0; basrs[i].mask ; ++i)
583 if (basr & basrs[i].mask)
584 printk(",%s", basrs[i].name);
585 printk("\nICR: %02x ", icr);
586 for (i = 0; icrs[i].mask; ++i)
587 if (icr & icrs[i].mask)
588 printk(",%s", icrs[i].name);
589 printk("\nMODE: %02x ", mr);
590 for (i = 0; mrs[i].mask; ++i)
591 if (mr & mrs[i].mask)
592 printk(",%s", mrs[i].name);
593 printk("\n");
594}
595
596static struct {
597 unsigned char value;
598 const char *name;
599} phases[] = {
600 {PHASE_DATAOUT, "DATAOUT"}, {PHASE_DATAIN, "DATAIN"}, {PHASE_CMDOUT, "CMDOUT"},
601 {PHASE_STATIN, "STATIN"}, {PHASE_MSGOUT, "MSGOUT"}, {PHASE_MSGIN, "MSGIN"},
602 {PHASE_UNKNOWN, "UNKNOWN"}};
603
604
605
606
607
608
609
610
611
612static void NCR5380_print_phase(struct Scsi_Host *instance)
613{
614 unsigned char status;
615 int i;
616
617 status = NCR5380_read(STATUS_REG);
618 if (!(status & SR_REQ))
619 printk(KERN_DEBUG "scsi%d: REQ not asserted, phase unknown.\n", HOSTNO);
620 else {
621 for (i = 0; (phases[i].value != PHASE_UNKNOWN) &&
622 (phases[i].value != (status & PHASE_MASK)); ++i);
623 printk(KERN_DEBUG "scsi%d: phase %s\n", HOSTNO, phases[i].name);
624 }
625}
626
627#else
628
629
630__inline__ void NCR5380_print(struct Scsi_Host *instance) { };
631__inline__ void NCR5380_print_phase(struct Scsi_Host *instance) { };
632
633#endif
634
635
636
637
638
639
640
641
642
643
644
645
646
647
648#include <linux/gfp.h>
649#include <linux/workqueue.h>
650#include <linux/interrupt.h>
651
652static volatile int main_running = 0;
653static DECLARE_WORK(NCR5380_tqueue, NCR5380_main);
654
655static __inline__ void queue_main(void)
656{
657 if (!main_running) {
658
659
660
661
662 schedule_work(&NCR5380_tqueue);
663 }
664
665
666}
667
668
669static inline void NCR5380_all_init (void)
670{
671 static int done = 0;
672 if (!done) {
673 INI_PRINTK("scsi : NCR5380_all_init()\n");
674 done = 1;
675 }
676}
677
678
679
680
681
682
683
684
685
686
687
688static void __init NCR5380_print_options (struct Scsi_Host *instance)
689{
690 printk(" generic options"
691#ifdef AUTOSENSE
692 " AUTOSENSE"
693#endif
694#ifdef REAL_DMA
695 " REAL DMA"
696#endif
697#ifdef PARITY
698 " PARITY"
699#endif
700#ifdef SUPPORT_TAGS
701 " SCSI-2 TAGGED QUEUING"
702#endif
703 );
704 printk(" generic release=%d", NCR5380_PUBLIC_RELEASE);
705}
706
707
708
709
710
711
712
713
714
715
716static void NCR5380_print_status (struct Scsi_Host *instance)
717{
718 char *pr_bfr;
719 char *start;
720 int len;
721
722 NCR_PRINT(NDEBUG_ANY);
723 NCR_PRINT_PHASE(NDEBUG_ANY);
724
725 pr_bfr = (char *) __get_free_page(GFP_ATOMIC);
726 if (!pr_bfr) {
727 printk("NCR5380_print_status: no memory for print buffer\n");
728 return;
729 }
730 len = NCR5380_proc_info(instance, pr_bfr, &start, 0, PAGE_SIZE, 0);
731 pr_bfr[len] = 0;
732 printk("\n%s\n", pr_bfr);
733 free_page((unsigned long) pr_bfr);
734}
735
736
737
738
739
740
741
742
743
744
745
746
747
748
749
750
751#undef SPRINTF
752#define SPRINTF(fmt,args...) \
753 do { if (pos + strlen(fmt) + 20 < buffer + length) \
754 pos += sprintf(pos, fmt , ## args); } while(0)
755static
756char *lprint_Scsi_Cmnd(struct scsi_cmnd *cmd, char *pos, char *buffer,
757 int length);
758
759static int NCR5380_proc_info(struct Scsi_Host *instance, char *buffer,
760 char **start, off_t offset, int length, int inout)
761{
762 char *pos = buffer;
763 struct NCR5380_hostdata *hostdata;
764 struct scsi_cmnd *ptr;
765 unsigned long flags;
766 off_t begin = 0;
767#define check_offset() \
768 do { \
769 if (pos - buffer < offset - begin) { \
770 begin += pos - buffer; \
771 pos = buffer; \
772 } \
773 } while (0)
774
775 hostdata = (struct NCR5380_hostdata *)instance->hostdata;
776
777 if (inout) {
778 return(-ENOSYS);
779 }
780 SPRINTF("NCR5380 core release=%d.\n", NCR5380_PUBLIC_RELEASE);
781 check_offset();
782 local_irq_save(flags);
783 SPRINTF("NCR5380: coroutine is%s running.\n", main_running ? "" : "n't");
784 check_offset();
785 if (!hostdata->connected)
786 SPRINTF("scsi%d: no currently connected command\n", HOSTNO);
787 else
788 pos = lprint_Scsi_Cmnd ((struct scsi_cmnd *) hostdata->connected,
789 pos, buffer, length);
790 SPRINTF("scsi%d: issue_queue\n", HOSTNO);
791 check_offset();
792 for (ptr = (struct scsi_cmnd *) hostdata->issue_queue; ptr; ptr = NEXT(ptr))
793 {
794 pos = lprint_Scsi_Cmnd (ptr, pos, buffer, length);
795 check_offset();
796 }
797
798 SPRINTF("scsi%d: disconnected_queue\n", HOSTNO);
799 check_offset();
800 for (ptr = (struct scsi_cmnd *) hostdata->disconnected_queue; ptr;
801 ptr = NEXT(ptr)) {
802 pos = lprint_Scsi_Cmnd (ptr, pos, buffer, length);
803 check_offset();
804 }
805
806 local_irq_restore(flags);
807 *start = buffer + (offset - begin);
808 if (pos - buffer < offset - begin)
809 return 0;
810 else if (pos - buffer - (offset - begin) < length)
811 return pos - buffer - (offset - begin);
812 return length;
813}
814
815static char *lprint_Scsi_Cmnd(struct scsi_cmnd *cmd, char *pos, char *buffer,
816 int length)
817{
818 int i, s;
819 unsigned char *command;
820 SPRINTF("scsi%d: destination target %d, lun %d\n",
821 H_NO(cmd), cmd->device->id, cmd->device->lun);
822 SPRINTF(" command = ");
823 command = cmd->cmnd;
824 SPRINTF("%2d (0x%02x)", command[0], command[0]);
825 for (i = 1, s = COMMAND_SIZE(command[0]); i < s; ++i)
826 SPRINTF(" %02x", command[i]);
827 SPRINTF("\n");
828 return pos;
829}
830
831
832
833
834
835
836
837
838
839
840
841
842
843
844static int NCR5380_init (struct Scsi_Host *instance, int flags)
845{
846 int i;
847 SETUP_HOSTDATA(instance);
848
849 NCR5380_all_init();
850
851 hostdata->aborted = 0;
852 hostdata->id_mask = 1 << instance->this_id;
853 hostdata->id_higher_mask = 0;
854 for (i = hostdata->id_mask; i <= 0x80; i <<= 1)
855 if (i > hostdata->id_mask)
856 hostdata->id_higher_mask |= i;
857 for (i = 0; i < 8; ++i)
858 hostdata->busy[i] = 0;
859#ifdef SUPPORT_TAGS
860 init_tags();
861#endif
862#if defined (REAL_DMA)
863 hostdata->dma_len = 0;
864#endif
865 hostdata->targets_present = 0;
866 hostdata->connected = NULL;
867 hostdata->issue_queue = NULL;
868 hostdata->disconnected_queue = NULL;
869 hostdata->flags = FLAG_CHECK_LAST_BYTE_SENT;
870
871 if (!the_template) {
872 the_template = instance->hostt;
873 first_instance = instance;
874 }
875
876
877#ifndef AUTOSENSE
878 if ((instance->cmd_per_lun > 1) || (instance->can_queue > 1))
879 printk("scsi%d: WARNING : support for multiple outstanding commands enabled\n"
880 " without AUTOSENSE option, contingent allegiance conditions may\n"
881 " be incorrectly cleared.\n", HOSTNO);
882#endif
883
884 NCR5380_write(INITIATOR_COMMAND_REG, ICR_BASE);
885 NCR5380_write(MODE_REG, MR_BASE);
886 NCR5380_write(TARGET_COMMAND_REG, 0);
887 NCR5380_write(SELECT_ENABLE_REG, 0);
888
889 return 0;
890}
891
892
893
894
895
896
897
898
899
900
901
902
903
904
905
906
907
908
909
910
911static int NCR5380_queue_command_lck(struct scsi_cmnd *cmd,
912 void (*done)(struct scsi_cmnd *))
913{
914 SETUP_HOSTDATA(cmd->device->host);
915 struct scsi_cmnd *tmp;
916 unsigned long flags;
917
918#if (NDEBUG & NDEBUG_NO_WRITE)
919 switch (cmd->cmnd[0]) {
920 case WRITE_6:
921 case WRITE_10:
922 printk(KERN_NOTICE "scsi%d: WRITE attempted with NO_WRITE debugging flag set\n",
923 H_NO(cmd));
924 cmd->result = (DID_ERROR << 16);
925 done(cmd);
926 return 0;
927 }
928#endif
929
930
931#ifdef NCR5380_STATS
932# if 0
933 if (!hostdata->connected && !hostdata->issue_queue &&
934 !hostdata->disconnected_queue) {
935 hostdata->timebase = jiffies;
936 }
937# endif
938# ifdef NCR5380_STAT_LIMIT
939 if (scsi_bufflen(cmd) > NCR5380_STAT_LIMIT)
940# endif
941 switch (cmd->cmnd[0])
942 {
943 case WRITE:
944 case WRITE_6:
945 case WRITE_10:
946 hostdata->time_write[cmd->device->id] -= (jiffies - hostdata->timebase);
947 hostdata->bytes_write[cmd->device->id] += scsi_bufflen(cmd);
948 hostdata->pendingw++;
949 break;
950 case READ:
951 case READ_6:
952 case READ_10:
953 hostdata->time_read[cmd->device->id] -= (jiffies - hostdata->timebase);
954 hostdata->bytes_read[cmd->device->id] += scsi_bufflen(cmd);
955 hostdata->pendingr++;
956 break;
957 }
958#endif
959
960
961
962
963
964
965 NEXT(cmd) = NULL;
966 cmd->scsi_done = done;
967
968 cmd->result = 0;
969
970
971
972
973
974
975
976
977
978 local_irq_save(flags);
979
980
981
982
983
984
985
986
987
988
989
990
991 if (!(hostdata->issue_queue) || (cmd->cmnd[0] == REQUEST_SENSE)) {
992 LIST(cmd, hostdata->issue_queue);
993 NEXT(cmd) = hostdata->issue_queue;
994 hostdata->issue_queue = cmd;
995 } else {
996 for (tmp = (struct scsi_cmnd *)hostdata->issue_queue;
997 NEXT(tmp); tmp = NEXT(tmp))
998 ;
999 LIST(cmd, tmp);
1000 NEXT(tmp) = cmd;
1001 }
1002
1003 local_irq_restore(flags);
1004
1005 QU_PRINTK("scsi%d: command added to %s of queue\n", H_NO(cmd),
1006 (cmd->cmnd[0] == REQUEST_SENSE) ? "head" : "tail");
1007
1008
1009
1010
1011
1012
1013
1014
1015 if (in_interrupt() || ((flags >> 8) & 7) >= 6)
1016 queue_main();
1017 else
1018 NCR5380_main(NULL);
1019 return 0;
1020}
1021
1022static DEF_SCSI_QCMD(NCR5380_queue_command)
1023
1024
1025
1026
1027
1028
1029
1030
1031
1032
1033
1034
1035
1036static void NCR5380_main (struct work_struct *bl)
1037{
1038 struct scsi_cmnd *tmp, *prev;
1039 struct Scsi_Host *instance = first_instance;
1040 struct NCR5380_hostdata *hostdata = HOSTDATA(instance);
1041 int done;
1042 unsigned long flags;
1043
1044
1045
1046
1047
1048
1049
1050
1051
1052
1053
1054
1055
1056
1057
1058
1059
1060
1061
1062
1063
1064
1065 if (main_running)
1066 return;
1067 main_running = 1;
1068
1069 local_save_flags(flags);
1070 do {
1071 local_irq_disable();
1072 done = 1;
1073
1074 if (!hostdata->connected) {
1075 MAIN_PRINTK( "scsi%d: not connected\n", HOSTNO );
1076
1077
1078
1079
1080#if (NDEBUG & NDEBUG_LISTS)
1081 for (tmp = (struct scsi_cmnd *) hostdata->issue_queue, prev = NULL;
1082 tmp && (tmp != prev); prev = tmp, tmp = NEXT(tmp))
1083 ;
1084 if ((tmp == prev) && tmp) printk(" LOOP\n");
1085#endif
1086 for (tmp = (struct scsi_cmnd *) hostdata->issue_queue,
1087 prev = NULL; tmp; prev = tmp, tmp = NEXT(tmp) ) {
1088
1089#if (NDEBUG & NDEBUG_LISTS)
1090 if (prev != tmp)
1091 printk("MAIN tmp=%p target=%d busy=%d lun=%d\n",
1092 tmp, tmp->target, hostdata->busy[tmp->target],
1093 tmp->lun);
1094#endif
1095
1096
1097 if (
1098#ifdef SUPPORT_TAGS
1099 !is_lun_busy( tmp, tmp->cmnd[0] != REQUEST_SENSE)
1100#else
1101 !(hostdata->busy[tmp->device->id] & (1 << tmp->device->lun))
1102#endif
1103 ) {
1104
1105 local_irq_disable();
1106 if (prev) {
1107 REMOVE(prev, NEXT(prev), tmp, NEXT(tmp));
1108 NEXT(prev) = NEXT(tmp);
1109 } else {
1110 REMOVE(-1, hostdata->issue_queue, tmp, NEXT(tmp));
1111 hostdata->issue_queue = NEXT(tmp);
1112 }
1113 NEXT(tmp) = NULL;
1114
1115
1116 local_irq_restore(flags);
1117
1118
1119
1120
1121
1122
1123
1124 MAIN_PRINTK("scsi%d: main(): command for target %d "
1125 "lun %d removed from issue_queue\n",
1126 HOSTNO, tmp->target, tmp->lun);
1127
1128
1129
1130
1131
1132
1133
1134
1135
1136
1137#ifdef SUPPORT_TAGS
1138 cmd_get_tag( tmp, tmp->cmnd[0] != REQUEST_SENSE );
1139#endif
1140 if (!NCR5380_select(instance, tmp,
1141 (tmp->cmnd[0] == REQUEST_SENSE) ? TAG_NONE :
1142 TAG_NEXT)) {
1143 break;
1144 } else {
1145 local_irq_disable();
1146 LIST(tmp, hostdata->issue_queue);
1147 NEXT(tmp) = hostdata->issue_queue;
1148 hostdata->issue_queue = tmp;
1149#ifdef SUPPORT_TAGS
1150 cmd_free_tag( tmp );
1151#endif
1152 local_irq_restore(flags);
1153 MAIN_PRINTK("scsi%d: main(): select() failed, "
1154 "returned to issue_queue\n", HOSTNO);
1155 if (hostdata->connected)
1156 break;
1157 }
1158 }
1159 }
1160 }
1161 if (hostdata->connected
1162#ifdef REAL_DMA
1163 && !hostdata->dma_len
1164#endif
1165 ) {
1166 local_irq_restore(flags);
1167 MAIN_PRINTK("scsi%d: main: performing information transfer\n",
1168 HOSTNO);
1169 NCR5380_information_transfer(instance);
1170 MAIN_PRINTK("scsi%d: main: done set false\n", HOSTNO);
1171 done = 0;
1172 }
1173 } while (!done);
1174
1175
1176
1177
1178 main_running = 0;
1179 local_irq_restore(flags);
1180}
1181
1182
1183#ifdef REAL_DMA
1184
1185
1186
1187
1188
1189
1190
1191
1192
1193
1194static void NCR5380_dma_complete( struct Scsi_Host *instance )
1195{
1196 SETUP_HOSTDATA(instance);
1197 int transfered;
1198 unsigned char **data;
1199 volatile int *count;
1200
1201 if (!hostdata->connected) {
1202 printk(KERN_WARNING "scsi%d: received end of DMA interrupt with "
1203 "no connected cmd\n", HOSTNO);
1204 return;
1205 }
1206
1207 DMA_PRINTK("scsi%d: real DMA transfer complete, basr 0x%X, sr 0x%X\n",
1208 HOSTNO, NCR5380_read(BUS_AND_STATUS_REG),
1209 NCR5380_read(STATUS_REG));
1210
1211 if((sun3scsi_dma_finish(rq_data_dir(hostdata->connected->request)))) {
1212 printk("scsi%d: overrun in UDC counter -- not prepared to deal with this!\n", HOSTNO);
1213 printk("please e-mail sammy@sammy.net with a description of how this\n");
1214 printk("error was produced.\n");
1215 BUG();
1216 }
1217
1218
1219 if((NCR5380_read(BUS_AND_STATUS_REG) & (BASR_PHASE_MATCH |
1220 BASR_ACK)) ==
1221 (BASR_PHASE_MATCH | BASR_ACK)) {
1222 printk("scsi%d: BASR %02x\n", HOSTNO, NCR5380_read(BUS_AND_STATUS_REG));
1223 printk("scsi%d: bus stuck in data phase -- probably a single byte "
1224 "overrun!\n", HOSTNO);
1225 printk("not prepared for this error!\n");
1226 printk("please e-mail sammy@sammy.net with a description of how this\n");
1227 printk("error was produced.\n");
1228 BUG();
1229 }
1230
1231
1232
1233 (void) NCR5380_read(RESET_PARITY_INTERRUPT_REG);
1234 NCR5380_write(MODE_REG, MR_BASE);
1235 NCR5380_write(INITIATOR_COMMAND_REG, ICR_BASE);
1236
1237 transfered = hostdata->dma_len - NCR5380_dma_residual(instance);
1238 hostdata->dma_len = 0;
1239
1240 data = (unsigned char **) &(hostdata->connected->SCp.ptr);
1241 count = &(hostdata->connected->SCp.this_residual);
1242 *data += transfered;
1243 *count -= transfered;
1244
1245}
1246#endif
1247
1248
1249
1250
1251
1252
1253
1254
1255
1256
1257
1258
1259
1260static irqreturn_t NCR5380_intr (int irq, void *dev_id)
1261{
1262 struct Scsi_Host *instance = first_instance;
1263 int done = 1, handled = 0;
1264 unsigned char basr;
1265
1266 INT_PRINTK("scsi%d: NCR5380 irq triggered\n", HOSTNO);
1267
1268
1269 basr = NCR5380_read(BUS_AND_STATUS_REG);
1270 INT_PRINTK("scsi%d: BASR=%02x\n", HOSTNO, basr);
1271
1272 if (basr & BASR_IRQ) {
1273 NCR_PRINT(NDEBUG_INTR);
1274 if ((NCR5380_read(STATUS_REG) & (SR_SEL|SR_IO)) == (SR_SEL|SR_IO)) {
1275 done = 0;
1276
1277 INT_PRINTK("scsi%d: SEL interrupt\n", HOSTNO);
1278 NCR5380_reselect(instance);
1279 (void) NCR5380_read(RESET_PARITY_INTERRUPT_REG);
1280 }
1281 else if (basr & BASR_PARITY_ERROR) {
1282 INT_PRINTK("scsi%d: PARITY interrupt\n", HOSTNO);
1283 (void) NCR5380_read(RESET_PARITY_INTERRUPT_REG);
1284 }
1285 else if ((NCR5380_read(STATUS_REG) & SR_RST) == SR_RST) {
1286 INT_PRINTK("scsi%d: RESET interrupt\n", HOSTNO);
1287 (void)NCR5380_read(RESET_PARITY_INTERRUPT_REG);
1288 }
1289 else {
1290
1291
1292
1293
1294
1295#if defined(REAL_DMA)
1296
1297
1298
1299
1300
1301
1302 if ((NCR5380_read(MODE_REG) & MR_DMA_MODE) &&
1303 ((basr & BASR_END_DMA_TRANSFER) ||
1304 !(basr & BASR_PHASE_MATCH))) {
1305
1306 INT_PRINTK("scsi%d: PHASE MISM or EOP interrupt\n", HOSTNO);
1307 NCR5380_dma_complete( instance );
1308 done = 0;
1309
1310 } else
1311#endif
1312 {
1313
1314 if (basr & BASR_PHASE_MATCH)
1315 INT_PRINTK("scsi%d: unknown interrupt, "
1316 "BASR 0x%x, MR 0x%x, SR 0x%x\n",
1317 HOSTNO, basr, NCR5380_read(MODE_REG),
1318 NCR5380_read(STATUS_REG));
1319 (void) NCR5380_read(RESET_PARITY_INTERRUPT_REG);
1320#ifdef SUN3_SCSI_VME
1321 dregs->csr |= CSR_DMA_ENABLE;
1322#endif
1323 }
1324 }
1325 handled = 1;
1326 }
1327 else {
1328
1329 printk(KERN_NOTICE "scsi%d: interrupt without IRQ bit set in BASR, "
1330 "BASR 0x%X, MR 0x%X, SR 0x%x\n", HOSTNO, basr,
1331 NCR5380_read(MODE_REG), NCR5380_read(STATUS_REG));
1332 (void) NCR5380_read(RESET_PARITY_INTERRUPT_REG);
1333#ifdef SUN3_SCSI_VME
1334 dregs->csr |= CSR_DMA_ENABLE;
1335#endif
1336 }
1337
1338 if (!done) {
1339 INT_PRINTK("scsi%d: in int routine, calling main\n", HOSTNO);
1340
1341 queue_main();
1342 }
1343 return IRQ_RETVAL(handled);
1344}
1345
1346#ifdef NCR5380_STATS
1347static void collect_stats(struct NCR5380_hostdata *hostdata,
1348 struct scsi_cmnd *cmd)
1349{
1350# ifdef NCR5380_STAT_LIMIT
1351 if (scsi_bufflen(cmd) > NCR5380_STAT_LIMIT)
1352# endif
1353 switch (cmd->cmnd[0])
1354 {
1355 case WRITE:
1356 case WRITE_6:
1357 case WRITE_10:
1358 hostdata->time_write[cmd->device->id] += (jiffies - hostdata->timebase);
1359
1360 hostdata->pendingw--;
1361 break;
1362 case READ:
1363 case READ_6:
1364 case READ_10:
1365 hostdata->time_read[cmd->device->id] += (jiffies - hostdata->timebase);
1366
1367 hostdata->pendingr--;
1368 break;
1369 }
1370}
1371#endif
1372
1373
1374
1375
1376
1377
1378
1379
1380
1381
1382
1383
1384
1385
1386
1387
1388
1389
1390
1391
1392
1393
1394
1395
1396
1397
1398
1399
1400
1401
1402
1403
1404static int NCR5380_select(struct Scsi_Host *instance, struct scsi_cmnd *cmd,
1405 int tag)
1406{
1407 SETUP_HOSTDATA(instance);
1408 unsigned char tmp[3], phase;
1409 unsigned char *data;
1410 int len;
1411 unsigned long timeout;
1412 unsigned long flags;
1413
1414 hostdata->restart_select = 0;
1415 NCR_PRINT(NDEBUG_ARBITRATION);
1416 ARB_PRINTK("scsi%d: starting arbitration, id = %d\n", HOSTNO,
1417 instance->this_id);
1418
1419
1420
1421
1422
1423
1424 local_irq_save(flags);
1425 if (hostdata->connected) {
1426 local_irq_restore(flags);
1427 return -1;
1428 }
1429 NCR5380_write(TARGET_COMMAND_REG, 0);
1430
1431
1432
1433
1434
1435
1436 NCR5380_write(OUTPUT_DATA_REG, hostdata->id_mask);
1437 NCR5380_write(MODE_REG, MR_ARBITRATE);
1438
1439 local_irq_restore(flags);
1440
1441
1442#if NCR_TIMEOUT
1443 {
1444 unsigned long timeout = jiffies + 2*NCR_TIMEOUT;
1445
1446 while (!(NCR5380_read(INITIATOR_COMMAND_REG) & ICR_ARBITRATION_PROGRESS)
1447 && time_before(jiffies, timeout) && !hostdata->connected)
1448 ;
1449 if (time_after_eq(jiffies, timeout))
1450 {
1451 printk("scsi : arbitration timeout at %d\n", __LINE__);
1452 NCR5380_write(MODE_REG, MR_BASE);
1453 NCR5380_write(SELECT_ENABLE_REG, hostdata->id_mask);
1454 return -1;
1455 }
1456 }
1457#else
1458 while (!(NCR5380_read(INITIATOR_COMMAND_REG) & ICR_ARBITRATION_PROGRESS)
1459 && !hostdata->connected);
1460#endif
1461
1462 ARB_PRINTK("scsi%d: arbitration complete\n", HOSTNO);
1463
1464 if (hostdata->connected) {
1465 NCR5380_write(MODE_REG, MR_BASE);
1466 return -1;
1467 }
1468
1469
1470
1471
1472
1473
1474
1475 udelay(3);
1476
1477
1478 if ((NCR5380_read(INITIATOR_COMMAND_REG) & ICR_ARBITRATION_LOST) ||
1479 (NCR5380_read(CURRENT_SCSI_DATA_REG) & hostdata->id_higher_mask) ||
1480 (NCR5380_read(INITIATOR_COMMAND_REG) & ICR_ARBITRATION_LOST) ||
1481 hostdata->connected) {
1482 NCR5380_write(MODE_REG, MR_BASE);
1483 ARB_PRINTK("scsi%d: lost arbitration, deasserting MR_ARBITRATE\n",
1484 HOSTNO);
1485 return -1;
1486 }
1487
1488
1489
1490
1491 NCR5380_write(INITIATOR_COMMAND_REG, ICR_BASE | ICR_ASSERT_SEL |
1492 ICR_ASSERT_BSY ) ;
1493
1494 if ((NCR5380_read(INITIATOR_COMMAND_REG) & ICR_ARBITRATION_LOST) ||
1495 hostdata->connected) {
1496 NCR5380_write(MODE_REG, MR_BASE);
1497 NCR5380_write(INITIATOR_COMMAND_REG, ICR_BASE);
1498 ARB_PRINTK("scsi%d: lost arbitration, deasserting ICR_ASSERT_SEL\n",
1499 HOSTNO);
1500 return -1;
1501 }
1502
1503
1504
1505
1506
1507
1508#ifdef CONFIG_ATARI_SCSI_TOSHIBA_DELAY
1509
1510 udelay(15);
1511#else
1512 udelay(2);
1513#endif
1514
1515 if (hostdata->connected) {
1516 NCR5380_write(MODE_REG, MR_BASE);
1517 NCR5380_write(INITIATOR_COMMAND_REG, ICR_BASE);
1518 return -1;
1519 }
1520
1521 ARB_PRINTK("scsi%d: won arbitration\n", HOSTNO);
1522
1523
1524
1525
1526
1527
1528 NCR5380_write(OUTPUT_DATA_REG, (hostdata->id_mask | (1 << cmd->device->id)));
1529
1530
1531
1532
1533
1534
1535
1536 NCR5380_write(INITIATOR_COMMAND_REG, (ICR_BASE | ICR_ASSERT_BSY |
1537 ICR_ASSERT_DATA | ICR_ASSERT_ATN | ICR_ASSERT_SEL ));
1538 NCR5380_write(MODE_REG, MR_BASE);
1539
1540
1541
1542
1543
1544
1545 if (hostdata->connected) {
1546 NCR5380_write(INITIATOR_COMMAND_REG, ICR_BASE);
1547 return -1;
1548 }
1549
1550 NCR5380_write(SELECT_ENABLE_REG, 0);
1551
1552
1553
1554
1555
1556 udelay(1);
1557
1558
1559 NCR5380_write(INITIATOR_COMMAND_REG, (ICR_BASE | ICR_ASSERT_DATA |
1560 ICR_ASSERT_ATN | ICR_ASSERT_SEL));
1561
1562
1563
1564
1565
1566
1567
1568
1569
1570
1571
1572
1573
1574
1575
1576
1577
1578
1579 udelay(1);
1580
1581 SEL_PRINTK("scsi%d: selecting target %d\n", HOSTNO, cmd->device->id);
1582
1583
1584
1585
1586
1587
1588 timeout = jiffies + 25;
1589
1590
1591
1592
1593
1594
1595
1596#if 0
1597
1598
1599
1600
1601
1602
1603
1604 while (time_before(jiffies, timeout) && !(NCR5380_read(STATUS_REG) &
1605 (SR_BSY | SR_IO)));
1606
1607 if ((NCR5380_read(STATUS_REG) & (SR_SEL | SR_IO)) ==
1608 (SR_SEL | SR_IO)) {
1609 NCR5380_write(INITIATOR_COMMAND_REG, ICR_BASE);
1610 NCR5380_reselect(instance);
1611 printk (KERN_ERR "scsi%d: reselection after won arbitration?\n",
1612 HOSTNO);
1613 NCR5380_write(SELECT_ENABLE_REG, hostdata->id_mask);
1614 return -1;
1615 }
1616#else
1617 while (time_before(jiffies, timeout) && !(NCR5380_read(STATUS_REG) & SR_BSY));
1618#endif
1619
1620
1621
1622
1623
1624
1625
1626 udelay(1);
1627
1628 NCR5380_write(INITIATOR_COMMAND_REG, ICR_BASE | ICR_ASSERT_ATN);
1629
1630 if (!(NCR5380_read(STATUS_REG) & SR_BSY)) {
1631 NCR5380_write(INITIATOR_COMMAND_REG, ICR_BASE);
1632 if (hostdata->targets_present & (1 << cmd->device->id)) {
1633 printk(KERN_ERR "scsi%d: weirdness\n", HOSTNO);
1634 if (hostdata->restart_select)
1635 printk(KERN_NOTICE "\trestart select\n");
1636 NCR_PRINT(NDEBUG_ANY);
1637 NCR5380_write(SELECT_ENABLE_REG, hostdata->id_mask);
1638 return -1;
1639 }
1640 cmd->result = DID_BAD_TARGET << 16;
1641#ifdef NCR5380_STATS
1642 collect_stats(hostdata, cmd);
1643#endif
1644#ifdef SUPPORT_TAGS
1645 cmd_free_tag( cmd );
1646#endif
1647 cmd->scsi_done(cmd);
1648 NCR5380_write(SELECT_ENABLE_REG, hostdata->id_mask);
1649 SEL_PRINTK("scsi%d: target did not respond within 250ms\n", HOSTNO);
1650 NCR5380_write(SELECT_ENABLE_REG, hostdata->id_mask);
1651 return 0;
1652 }
1653
1654 hostdata->targets_present |= (1 << cmd->device->id);
1655
1656
1657
1658
1659
1660
1661
1662
1663
1664
1665
1666
1667
1668
1669
1670
1671
1672 while (!(NCR5380_read(STATUS_REG) & SR_REQ));
1673
1674 SEL_PRINTK("scsi%d: target %d selected, going into MESSAGE OUT phase.\n",
1675 HOSTNO, cmd->device->id);
1676 tmp[0] = IDENTIFY(1, cmd->device->lun);
1677
1678#ifdef SUPPORT_TAGS
1679 if (cmd->tag != TAG_NONE) {
1680 tmp[1] = hostdata->last_message = SIMPLE_QUEUE_TAG;
1681 tmp[2] = cmd->tag;
1682 len = 3;
1683 } else
1684 len = 1;
1685#else
1686 len = 1;
1687 cmd->tag=0;
1688#endif
1689
1690
1691 data = tmp;
1692 phase = PHASE_MSGOUT;
1693 NCR5380_transfer_pio(instance, &phase, &len, &data);
1694 SEL_PRINTK("scsi%d: nexus established.\n", HOSTNO);
1695
1696 hostdata->connected = cmd;
1697#ifndef SUPPORT_TAGS
1698 hostdata->busy[cmd->device->id] |= (1 << cmd->device->lun);
1699#endif
1700#ifdef SUN3_SCSI_VME
1701 dregs->csr |= CSR_INTR;
1702#endif
1703 initialize_SCp(cmd);
1704
1705
1706 return 0;
1707}
1708
1709
1710
1711
1712
1713
1714
1715
1716
1717
1718
1719
1720
1721
1722
1723
1724
1725
1726
1727
1728
1729
1730
1731
1732
1733
1734static int NCR5380_transfer_pio( struct Scsi_Host *instance,
1735 unsigned char *phase, int *count,
1736 unsigned char **data)
1737{
1738 register unsigned char p = *phase, tmp;
1739 register int c = *count;
1740 register unsigned char *d = *data;
1741
1742
1743
1744
1745
1746
1747
1748 NCR5380_write(TARGET_COMMAND_REG, PHASE_SR_TO_TCR(p));
1749
1750 do {
1751
1752
1753
1754
1755 while (!((tmp = NCR5380_read(STATUS_REG)) & SR_REQ));
1756
1757 HSH_PRINTK("scsi%d: REQ detected\n", HOSTNO);
1758
1759
1760 if ((tmp & PHASE_MASK) != p) {
1761 PIO_PRINTK("scsi%d: phase mismatch\n", HOSTNO);
1762 NCR_PRINT_PHASE(NDEBUG_PIO);
1763 break;
1764 }
1765
1766
1767 if (!(p & SR_IO))
1768 NCR5380_write(OUTPUT_DATA_REG, *d);
1769 else
1770 *d = NCR5380_read(CURRENT_SCSI_DATA_REG);
1771
1772 ++d;
1773
1774
1775
1776
1777
1778
1779
1780
1781 if (!(p & SR_IO)) {
1782 if (!((p & SR_MSG) && c > 1)) {
1783 NCR5380_write(INITIATOR_COMMAND_REG, ICR_BASE |
1784 ICR_ASSERT_DATA);
1785 NCR_PRINT(NDEBUG_PIO);
1786 NCR5380_write(INITIATOR_COMMAND_REG, ICR_BASE |
1787 ICR_ASSERT_DATA | ICR_ASSERT_ACK);
1788 } else {
1789 NCR5380_write(INITIATOR_COMMAND_REG, ICR_BASE |
1790 ICR_ASSERT_DATA | ICR_ASSERT_ATN);
1791 NCR_PRINT(NDEBUG_PIO);
1792 NCR5380_write(INITIATOR_COMMAND_REG, ICR_BASE |
1793 ICR_ASSERT_DATA | ICR_ASSERT_ATN | ICR_ASSERT_ACK);
1794 }
1795 } else {
1796 NCR_PRINT(NDEBUG_PIO);
1797 NCR5380_write(INITIATOR_COMMAND_REG, ICR_BASE | ICR_ASSERT_ACK);
1798 }
1799
1800 while (NCR5380_read(STATUS_REG) & SR_REQ);
1801
1802 HSH_PRINTK("scsi%d: req false, handshake complete\n", HOSTNO);
1803
1804
1805
1806
1807
1808
1809
1810
1811
1812
1813
1814
1815 if (!(p == PHASE_MSGIN && c == 1)) {
1816 if (p == PHASE_MSGOUT && c > 1)
1817 NCR5380_write(INITIATOR_COMMAND_REG, ICR_BASE | ICR_ASSERT_ATN);
1818 else
1819 NCR5380_write(INITIATOR_COMMAND_REG, ICR_BASE);
1820 }
1821 } while (--c);
1822
1823 PIO_PRINTK("scsi%d: residual %d\n", HOSTNO, c);
1824
1825 *count = c;
1826 *data = d;
1827 tmp = NCR5380_read(STATUS_REG);
1828
1829
1830
1831 if ((tmp & SR_REQ) || (p == PHASE_MSGIN && c == 0))
1832 *phase = tmp & PHASE_MASK;
1833 else
1834 *phase = PHASE_UNKNOWN;
1835
1836 if (!c || (*phase == p))
1837 return 0;
1838 else
1839 return -1;
1840}
1841
1842
1843
1844
1845
1846
1847
1848
1849
1850
1851static int do_abort (struct Scsi_Host *host)
1852{
1853 unsigned char tmp, *msgptr, phase;
1854 int len;
1855
1856
1857 NCR5380_write(INITIATOR_COMMAND_REG, ICR_BASE | ICR_ASSERT_ATN);
1858
1859
1860
1861
1862
1863
1864
1865
1866
1867
1868
1869 while (!((tmp = NCR5380_read(STATUS_REG)) & SR_REQ));
1870
1871 NCR5380_write(TARGET_COMMAND_REG, PHASE_SR_TO_TCR(tmp));
1872
1873 if ((tmp & PHASE_MASK) != PHASE_MSGOUT) {
1874 NCR5380_write(INITIATOR_COMMAND_REG, ICR_BASE | ICR_ASSERT_ATN |
1875 ICR_ASSERT_ACK);
1876 while (NCR5380_read(STATUS_REG) & SR_REQ);
1877 NCR5380_write(INITIATOR_COMMAND_REG, ICR_BASE | ICR_ASSERT_ATN);
1878 }
1879
1880 tmp = ABORT;
1881 msgptr = &tmp;
1882 len = 1;
1883 phase = PHASE_MSGOUT;
1884 NCR5380_transfer_pio (host, &phase, &len, &msgptr);
1885
1886
1887
1888
1889
1890
1891 return len ? -1 : 0;
1892}
1893
1894#if defined(REAL_DMA)
1895
1896
1897
1898
1899
1900
1901
1902
1903
1904
1905
1906
1907
1908
1909
1910
1911
1912
1913
1914
1915static int NCR5380_transfer_dma( struct Scsi_Host *instance,
1916 unsigned char *phase, int *count,
1917 unsigned char **data)
1918{
1919 SETUP_HOSTDATA(instance);
1920 register int c = *count;
1921 register unsigned char p = *phase;
1922 unsigned long flags;
1923
1924
1925 if(!sun3_dma_setup_done) {
1926 printk("scsi%d: transfer_dma without setup!\n", HOSTNO);
1927 BUG();
1928 }
1929 hostdata->dma_len = c;
1930
1931 DMA_PRINTK("scsi%d: initializing DMA for %s, %d bytes %s %p\n",
1932 HOSTNO, (p & SR_IO) ? "reading" : "writing",
1933 c, (p & SR_IO) ? "to" : "from", *data);
1934
1935
1936 local_irq_save(flags);
1937
1938
1939 sun3scsi_dma_start(c, *data);
1940
1941 if (p & SR_IO) {
1942 NCR5380_write(TARGET_COMMAND_REG, 1);
1943 NCR5380_read(RESET_PARITY_INTERRUPT_REG);
1944 NCR5380_write(INITIATOR_COMMAND_REG, 0);
1945 NCR5380_write(MODE_REG, (NCR5380_read(MODE_REG) | MR_DMA_MODE | MR_ENABLE_EOP_INTR));
1946 NCR5380_write(START_DMA_INITIATOR_RECEIVE_REG, 0);
1947 } else {
1948 NCR5380_write(TARGET_COMMAND_REG, 0);
1949 NCR5380_read(RESET_PARITY_INTERRUPT_REG);
1950 NCR5380_write(INITIATOR_COMMAND_REG, ICR_ASSERT_DATA);
1951 NCR5380_write(MODE_REG, (NCR5380_read(MODE_REG) | MR_DMA_MODE | MR_ENABLE_EOP_INTR));
1952 NCR5380_write(START_DMA_SEND_REG, 0);
1953 }
1954
1955#ifdef SUN3_SCSI_VME
1956 dregs->csr |= CSR_DMA_ENABLE;
1957#endif
1958
1959 local_irq_restore(flags);
1960
1961 sun3_dma_active = 1;
1962 return 0;
1963}
1964#endif
1965
1966
1967
1968
1969
1970
1971
1972
1973
1974
1975
1976
1977
1978
1979
1980
1981
1982
1983static void NCR5380_information_transfer (struct Scsi_Host *instance)
1984{
1985 SETUP_HOSTDATA(instance);
1986 unsigned long flags;
1987 unsigned char msgout = NOP;
1988 int sink = 0;
1989 int len;
1990#if defined(REAL_DMA)
1991 int transfersize;
1992#endif
1993 unsigned char *data;
1994 unsigned char phase, tmp, extended_msg[10], old_phase=0xff;
1995 struct scsi_cmnd *cmd = (struct scsi_cmnd *) hostdata->connected;
1996
1997#ifdef SUN3_SCSI_VME
1998 dregs->csr |= CSR_INTR;
1999#endif
2000
2001 while (1) {
2002 tmp = NCR5380_read(STATUS_REG);
2003
2004 if (tmp & SR_REQ) {
2005 phase = (tmp & PHASE_MASK);
2006 if (phase != old_phase) {
2007 old_phase = phase;
2008 NCR_PRINT_PHASE(NDEBUG_INFORMATION);
2009 }
2010
2011 if(phase == PHASE_CMDOUT) {
2012 void *d;
2013 unsigned long count;
2014
2015 if (!cmd->SCp.this_residual && cmd->SCp.buffers_residual) {
2016 count = cmd->SCp.buffer->length;
2017 d = SGADDR(cmd->SCp.buffer);
2018 } else {
2019 count = cmd->SCp.this_residual;
2020 d = cmd->SCp.ptr;
2021 }
2022#ifdef REAL_DMA
2023
2024 if((count > SUN3_DMA_MINSIZE) && (sun3_dma_setup_done
2025 != cmd))
2026 {
2027 if (cmd->request->cmd_type == REQ_TYPE_FS) {
2028 sun3scsi_dma_setup(d, count,
2029 rq_data_dir(cmd->request));
2030 sun3_dma_setup_done = cmd;
2031 }
2032 }
2033#endif
2034#ifdef SUN3_SCSI_VME
2035 dregs->csr |= CSR_INTR;
2036#endif
2037 }
2038
2039
2040 if (sink && (phase != PHASE_MSGOUT)) {
2041 NCR5380_write(TARGET_COMMAND_REG, PHASE_SR_TO_TCR(tmp));
2042
2043 NCR5380_write(INITIATOR_COMMAND_REG, ICR_BASE | ICR_ASSERT_ATN |
2044 ICR_ASSERT_ACK);
2045 while (NCR5380_read(STATUS_REG) & SR_REQ);
2046 NCR5380_write(INITIATOR_COMMAND_REG, ICR_BASE |
2047 ICR_ASSERT_ATN);
2048 sink = 0;
2049 continue;
2050 }
2051
2052 switch (phase) {
2053 case PHASE_DATAOUT:
2054#if (NDEBUG & NDEBUG_NO_DATAOUT)
2055 printk("scsi%d: NDEBUG_NO_DATAOUT set, attempted DATAOUT "
2056 "aborted\n", HOSTNO);
2057 sink = 1;
2058 do_abort(instance);
2059 cmd->result = DID_ERROR << 16;
2060 cmd->scsi_done(cmd);
2061 return;
2062#endif
2063 case PHASE_DATAIN:
2064
2065
2066
2067
2068 if (!cmd->SCp.this_residual && cmd->SCp.buffers_residual) {
2069 ++cmd->SCp.buffer;
2070 --cmd->SCp.buffers_residual;
2071 cmd->SCp.this_residual = cmd->SCp.buffer->length;
2072 cmd->SCp.ptr = SGADDR(cmd->SCp.buffer);
2073
2074
2075
2076
2077
2078 INF_PRINTK("scsi%d: %d bytes and %d buffers left\n",
2079 HOSTNO, cmd->SCp.this_residual,
2080 cmd->SCp.buffers_residual);
2081 }
2082
2083
2084
2085
2086
2087
2088
2089
2090
2091
2092
2093
2094
2095
2096
2097
2098#if defined(REAL_DMA)
2099
2100 if((transfersize =
2101 NCR5380_dma_xfer_len(instance,cmd,phase)) > SUN3_DMA_MINSIZE) {
2102 len = transfersize;
2103 cmd->SCp.phase = phase;
2104
2105 if (NCR5380_transfer_dma(instance, &phase,
2106 &len, (unsigned char **) &cmd->SCp.ptr)) {
2107
2108
2109
2110
2111 printk(KERN_NOTICE "scsi%d: switching target %d "
2112 "lun %d to slow handshake\n", HOSTNO,
2113 cmd->device->id, cmd->device->lun);
2114 cmd->device->borken = 1;
2115 NCR5380_write(INITIATOR_COMMAND_REG, ICR_BASE |
2116 ICR_ASSERT_ATN);
2117 sink = 1;
2118 do_abort(instance);
2119 cmd->result = DID_ERROR << 16;
2120 cmd->scsi_done(cmd);
2121
2122 } else {
2123#ifdef REAL_DMA
2124
2125
2126
2127
2128
2129 return;
2130#else
2131 cmd->SCp.this_residual -= transfersize - len;
2132#endif
2133 }
2134 } else
2135#endif
2136 NCR5380_transfer_pio(instance, &phase,
2137 (int *) &cmd->SCp.this_residual, (unsigned char **)
2138 &cmd->SCp.ptr);
2139#ifdef REAL_DMA
2140
2141 if(sun3_dma_setup_done == cmd)
2142 sun3_dma_setup_done = NULL;
2143#endif
2144
2145 break;
2146 case PHASE_MSGIN:
2147 len = 1;
2148 data = &tmp;
2149 NCR5380_write(SELECT_ENABLE_REG, 0);
2150 NCR5380_transfer_pio(instance, &phase, &len, &data);
2151 cmd->SCp.Message = tmp;
2152
2153 switch (tmp) {
2154
2155
2156
2157
2158
2159
2160
2161
2162
2163
2164#ifdef LINKED
2165 case LINKED_CMD_COMPLETE:
2166 case LINKED_FLG_CMD_COMPLETE:
2167
2168 NCR5380_write(INITIATOR_COMMAND_REG, ICR_BASE);
2169
2170 LNK_PRINTK("scsi%d: target %d lun %d linked command "
2171 "complete.\n", HOSTNO, cmd->device->id, cmd->device->lun);
2172
2173
2174 NCR5380_write(SELECT_ENABLE_REG, hostdata->id_mask);
2175
2176
2177
2178
2179
2180
2181 if (!cmd->next_link) {
2182 printk(KERN_NOTICE "scsi%d: target %d lun %d "
2183 "linked command complete, no next_link\n",
2184 HOSTNO, cmd->device->id, cmd->device->lun);
2185 sink = 1;
2186 do_abort (instance);
2187 return;
2188 }
2189
2190 initialize_SCp(cmd->next_link);
2191
2192
2193 cmd->next_link->tag = cmd->tag;
2194 cmd->result = cmd->SCp.Status | (cmd->SCp.Message << 8);
2195 LNK_PRINTK("scsi%d: target %d lun %d linked request "
2196 "done, calling scsi_done().\n",
2197 HOSTNO, cmd->device->id, cmd->device->lun);
2198#ifdef NCR5380_STATS
2199 collect_stats(hostdata, cmd);
2200#endif
2201 cmd->scsi_done(cmd);
2202 cmd = hostdata->connected;
2203 break;
2204#endif
2205 case ABORT:
2206 case COMMAND_COMPLETE:
2207
2208 NCR5380_write(INITIATOR_COMMAND_REG, ICR_BASE);
2209 hostdata->connected = NULL;
2210 QU_PRINTK("scsi%d: command for target %d, lun %d "
2211 "completed\n", HOSTNO, cmd->device->id, cmd->device->lun);
2212#ifdef SUPPORT_TAGS
2213 cmd_free_tag( cmd );
2214 if (status_byte(cmd->SCp.Status) == QUEUE_FULL) {
2215
2216
2217
2218
2219
2220
2221
2222
2223 TAG_ALLOC *ta = &TagAlloc[cmd->device->id][cmd->device->lun];
2224 TAG_PRINTK("scsi%d: target %d lun %d returned "
2225 "QUEUE_FULL after %d commands\n",
2226 HOSTNO, cmd->device->id, cmd->device->lun,
2227 ta->nr_allocated);
2228 if (ta->queue_size > ta->nr_allocated)
2229 ta->nr_allocated = ta->queue_size;
2230 }
2231#else
2232 hostdata->busy[cmd->device->id] &= ~(1 << cmd->device->lun);
2233#endif
2234
2235 NCR5380_write(SELECT_ENABLE_REG, hostdata->id_mask);
2236
2237
2238
2239
2240
2241
2242
2243
2244
2245
2246
2247
2248
2249
2250
2251
2252
2253 if (cmd->cmnd[0] != REQUEST_SENSE)
2254 cmd->result = cmd->SCp.Status | (cmd->SCp.Message << 8);
2255 else if (status_byte(cmd->SCp.Status) != GOOD)
2256 cmd->result = (cmd->result & 0x00ffff) | (DID_ERROR << 16);
2257
2258#ifdef AUTOSENSE
2259 if ((cmd->cmnd[0] == REQUEST_SENSE) &&
2260 hostdata->ses.cmd_len) {
2261 scsi_eh_restore_cmnd(cmd, &hostdata->ses);
2262 hostdata->ses.cmd_len = 0 ;
2263 }
2264
2265 if ((cmd->cmnd[0] != REQUEST_SENSE) &&
2266 (status_byte(cmd->SCp.Status) == CHECK_CONDITION)) {
2267 scsi_eh_prep_cmnd(cmd, &hostdata->ses, NULL, 0, ~0);
2268 ASEN_PRINTK("scsi%d: performing request sense\n",
2269 HOSTNO);
2270
2271
2272
2273
2274
2275 local_irq_save(flags);
2276 LIST(cmd,hostdata->issue_queue);
2277 NEXT(cmd) = hostdata->issue_queue;
2278 hostdata->issue_queue = (struct scsi_cmnd *) cmd;
2279 local_irq_restore(flags);
2280 QU_PRINTK("scsi%d: REQUEST SENSE added to head of "
2281 "issue queue\n", H_NO(cmd));
2282 } else
2283#endif
2284 {
2285#ifdef NCR5380_STATS
2286 collect_stats(hostdata, cmd);
2287#endif
2288 cmd->scsi_done(cmd);
2289 }
2290
2291 NCR5380_write(SELECT_ENABLE_REG, hostdata->id_mask);
2292
2293
2294
2295
2296 NCR5380_write(TARGET_COMMAND_REG, 0);
2297
2298 while ((NCR5380_read(STATUS_REG) & SR_BSY) && !hostdata->connected)
2299 barrier();
2300
2301 return;
2302 case MESSAGE_REJECT:
2303
2304 NCR5380_write(INITIATOR_COMMAND_REG, ICR_BASE);
2305
2306 NCR5380_write(SELECT_ENABLE_REG, hostdata->id_mask);
2307 switch (hostdata->last_message) {
2308 case HEAD_OF_QUEUE_TAG:
2309 case ORDERED_QUEUE_TAG:
2310 case SIMPLE_QUEUE_TAG:
2311
2312
2313
2314
2315
2316
2317 cmd->device->tagged_supported = 0;
2318 hostdata->busy[cmd->device->id] |= (1 << cmd->device->lun);
2319 cmd->tag = TAG_NONE;
2320 TAG_PRINTK("scsi%d: target %d lun %d rejected "
2321 "QUEUE_TAG message; tagged queuing "
2322 "disabled\n",
2323 HOSTNO, cmd->device->id, cmd->device->lun);
2324 break;
2325 }
2326 break;
2327 case DISCONNECT:
2328
2329 NCR5380_write(INITIATOR_COMMAND_REG, ICR_BASE);
2330 local_irq_save(flags);
2331 cmd->device->disconnect = 1;
2332 LIST(cmd,hostdata->disconnected_queue);
2333 NEXT(cmd) = hostdata->disconnected_queue;
2334 hostdata->connected = NULL;
2335 hostdata->disconnected_queue = cmd;
2336 local_irq_restore(flags);
2337 QU_PRINTK("scsi%d: command for target %d lun %d was "
2338 "moved from connected to the "
2339 "disconnected_queue\n", HOSTNO,
2340 cmd->device->id, cmd->device->lun);
2341
2342
2343
2344
2345 NCR5380_write(TARGET_COMMAND_REG, 0);
2346
2347
2348 NCR5380_write(SELECT_ENABLE_REG, hostdata->id_mask);
2349
2350 while ((NCR5380_read(STATUS_REG) & SR_BSY) && !hostdata->connected)
2351 barrier();
2352#ifdef SUN3_SCSI_VME
2353 dregs->csr |= CSR_DMA_ENABLE;
2354#endif
2355 return;
2356
2357
2358
2359
2360
2361
2362
2363
2364
2365
2366 case SAVE_POINTERS:
2367 case RESTORE_POINTERS:
2368
2369 NCR5380_write(INITIATOR_COMMAND_REG, ICR_BASE);
2370
2371 NCR5380_write(SELECT_ENABLE_REG, hostdata->id_mask);
2372 break;
2373 case EXTENDED_MESSAGE:
2374
2375
2376
2377
2378
2379
2380
2381
2382
2383
2384
2385
2386 extended_msg[0] = EXTENDED_MESSAGE;
2387
2388 NCR5380_write(INITIATOR_COMMAND_REG, ICR_BASE);
2389
2390 EXT_PRINTK("scsi%d: receiving extended message\n", HOSTNO);
2391
2392 len = 2;
2393 data = extended_msg + 1;
2394 phase = PHASE_MSGIN;
2395 NCR5380_transfer_pio(instance, &phase, &len, &data);
2396 EXT_PRINTK("scsi%d: length=%d, code=0x%02x\n", HOSTNO,
2397 (int)extended_msg[1], (int)extended_msg[2]);
2398
2399 if (!len && extended_msg[1] <=
2400 (sizeof (extended_msg) - 1)) {
2401
2402 NCR5380_write(INITIATOR_COMMAND_REG, ICR_BASE);
2403 len = extended_msg[1] - 1;
2404 data = extended_msg + 3;
2405 phase = PHASE_MSGIN;
2406
2407 NCR5380_transfer_pio(instance, &phase, &len, &data);
2408 EXT_PRINTK("scsi%d: message received, residual %d\n",
2409 HOSTNO, len);
2410
2411 switch (extended_msg[2]) {
2412 case EXTENDED_SDTR:
2413 case EXTENDED_WDTR:
2414 case EXTENDED_MODIFY_DATA_POINTER:
2415 case EXTENDED_EXTENDED_IDENTIFY:
2416 tmp = 0;
2417 }
2418 } else if (len) {
2419 printk(KERN_NOTICE "scsi%d: error receiving "
2420 "extended message\n", HOSTNO);
2421 tmp = 0;
2422 } else {
2423 printk(KERN_NOTICE "scsi%d: extended message "
2424 "code %02x length %d is too long\n",
2425 HOSTNO, extended_msg[2], extended_msg[1]);
2426 tmp = 0;
2427 }
2428
2429
2430
2431
2432
2433
2434 default:
2435 if (!tmp) {
2436 printk(KERN_DEBUG "scsi%d: rejecting message ", HOSTNO);
2437 spi_print_msg(extended_msg);
2438 printk("\n");
2439 } else if (tmp != EXTENDED_MESSAGE)
2440 printk(KERN_DEBUG "scsi%d: rejecting unknown "
2441 "message %02x from target %d, lun %d\n",
2442 HOSTNO, tmp, cmd->device->id, cmd->device->lun);
2443 else
2444 printk(KERN_DEBUG "scsi%d: rejecting unknown "
2445 "extended message "
2446 "code %02x, length %d from target %d, lun %d\n",
2447 HOSTNO, extended_msg[1], extended_msg[0],
2448 cmd->device->id, cmd->device->lun);
2449
2450
2451 msgout = MESSAGE_REJECT;
2452 NCR5380_write(INITIATOR_COMMAND_REG, ICR_BASE |
2453 ICR_ASSERT_ATN);
2454 break;
2455 }
2456 break;
2457 case PHASE_MSGOUT:
2458 len = 1;
2459 data = &msgout;
2460 hostdata->last_message = msgout;
2461 NCR5380_transfer_pio(instance, &phase, &len, &data);
2462 if (msgout == ABORT) {
2463#ifdef SUPPORT_TAGS
2464 cmd_free_tag( cmd );
2465#else
2466 hostdata->busy[cmd->device->id] &= ~(1 << cmd->device->lun);
2467#endif
2468 hostdata->connected = NULL;
2469 cmd->result = DID_ERROR << 16;
2470#ifdef NCR5380_STATS
2471 collect_stats(hostdata, cmd);
2472#endif
2473 cmd->scsi_done(cmd);
2474 NCR5380_write(SELECT_ENABLE_REG, hostdata->id_mask);
2475 return;
2476 }
2477 msgout = NOP;
2478 break;
2479 case PHASE_CMDOUT:
2480 len = cmd->cmd_len;
2481 data = cmd->cmnd;
2482
2483
2484
2485
2486
2487 NCR5380_transfer_pio(instance, &phase, &len,
2488 &data);
2489 break;
2490 case PHASE_STATIN:
2491 len = 1;
2492 data = &tmp;
2493 NCR5380_transfer_pio(instance, &phase, &len, &data);
2494 cmd->SCp.Status = tmp;
2495 break;
2496 default:
2497 printk("scsi%d: unknown phase\n", HOSTNO);
2498 NCR_PRINT(NDEBUG_ANY);
2499 }
2500 }
2501 }
2502}
2503
2504
2505
2506
2507
2508
2509
2510
2511
2512
2513
2514
2515
2516
2517
2518static void NCR5380_reselect (struct Scsi_Host *instance)
2519{
2520 SETUP_HOSTDATA(instance);
2521 unsigned char target_mask;
2522 unsigned char lun;
2523#ifdef SUPPORT_TAGS
2524 unsigned char tag;
2525#endif
2526 unsigned char msg[3];
2527 struct scsi_cmnd *tmp = NULL, *prev;
2528
2529
2530
2531
2532
2533
2534
2535 NCR5380_write(MODE_REG, MR_BASE);
2536 hostdata->restart_select = 1;
2537
2538 target_mask = NCR5380_read(CURRENT_SCSI_DATA_REG) & ~(hostdata->id_mask);
2539
2540 RSL_PRINTK("scsi%d: reselect\n", HOSTNO);
2541
2542
2543
2544
2545
2546
2547
2548
2549
2550
2551 NCR5380_write(INITIATOR_COMMAND_REG, ICR_BASE | ICR_ASSERT_BSY);
2552
2553 while (NCR5380_read(STATUS_REG) & SR_SEL);
2554 NCR5380_write(INITIATOR_COMMAND_REG, ICR_BASE);
2555
2556
2557
2558
2559
2560 while (!(NCR5380_read(STATUS_REG) & SR_REQ));
2561
2562#if 1
2563
2564 NCR5380_write(TARGET_COMMAND_REG, PHASE_SR_TO_TCR(PHASE_MSGIN));
2565
2566
2567 msg[0] = NCR5380_read(CURRENT_SCSI_DATA_REG);
2568#endif
2569
2570 if (!(msg[0] & 0x80)) {
2571 printk(KERN_DEBUG "scsi%d: expecting IDENTIFY message, got ", HOSTNO);
2572 spi_print_msg(msg);
2573 do_abort(instance);
2574 return;
2575 }
2576 lun = (msg[0] & 0x07);
2577
2578
2579
2580
2581
2582
2583 for (tmp = (struct scsi_cmnd *) hostdata->disconnected_queue, prev = NULL;
2584 tmp; prev = tmp, tmp = NEXT(tmp) ) {
2585 if ((target_mask == (1 << tmp->device->id)) && (lun == tmp->device->lun)
2586#ifdef SUPPORT_TAGS
2587 && (tag == tmp->tag)
2588#endif
2589 ) {
2590 if (prev) {
2591 REMOVE(prev, NEXT(prev), tmp, NEXT(tmp));
2592 NEXT(prev) = NEXT(tmp);
2593 } else {
2594 REMOVE(-1, hostdata->disconnected_queue, tmp, NEXT(tmp));
2595 hostdata->disconnected_queue = NEXT(tmp);
2596 }
2597 NEXT(tmp) = NULL;
2598 break;
2599 }
2600 }
2601
2602 if (!tmp) {
2603 printk(KERN_WARNING "scsi%d: warning: target bitmask %02x lun %d "
2604#ifdef SUPPORT_TAGS
2605 "tag %d "
2606#endif
2607 "not in disconnected_queue.\n",
2608 HOSTNO, target_mask, lun
2609#ifdef SUPPORT_TAGS
2610 , tag
2611#endif
2612 );
2613
2614
2615
2616
2617 do_abort(instance);
2618 return;
2619 }
2620#if 1
2621
2622 {
2623 void *d;
2624 unsigned long count;
2625
2626 if (!tmp->SCp.this_residual && tmp->SCp.buffers_residual) {
2627 count = tmp->SCp.buffer->length;
2628 d = SGADDR(tmp->SCp.buffer);
2629 } else {
2630 count = tmp->SCp.this_residual;
2631 d = tmp->SCp.ptr;
2632 }
2633#ifdef REAL_DMA
2634
2635 if((count > SUN3_DMA_MINSIZE) && (sun3_dma_setup_done != tmp))
2636 {
2637 sun3scsi_dma_setup(d, count, rq_data_dir(tmp->request));
2638 sun3_dma_setup_done = tmp;
2639 }
2640#endif
2641 }
2642#endif
2643
2644 NCR5380_write(INITIATOR_COMMAND_REG, ICR_BASE | ICR_ASSERT_ACK);
2645
2646 NCR5380_write(INITIATOR_COMMAND_REG, ICR_BASE);
2647
2648#ifdef SUPPORT_TAGS
2649
2650
2651
2652
2653 tag = TAG_NONE;
2654 if (phase == PHASE_MSGIN && setup_use_tagged_queuing) {
2655
2656 NCR5380_write( INITIATOR_COMMAND_REG, ICR_BASE );
2657 len = 2;
2658 data = msg+1;
2659 if (!NCR5380_transfer_pio(instance, &phase, &len, &data) &&
2660 msg[1] == SIMPLE_QUEUE_TAG)
2661 tag = msg[2];
2662 TAG_PRINTK("scsi%d: target mask %02x, lun %d sent tag %d at "
2663 "reselection\n", HOSTNO, target_mask, lun, tag);
2664 }
2665#endif
2666
2667 hostdata->connected = tmp;
2668 RSL_PRINTK("scsi%d: nexus established, target = %d, lun = %d, tag = %d\n",
2669 HOSTNO, tmp->target, tmp->lun, tmp->tag);
2670}
2671
2672
2673
2674
2675
2676
2677
2678
2679
2680
2681
2682
2683
2684
2685
2686
2687
2688
2689
2690static int NCR5380_abort(struct scsi_cmnd *cmd)
2691{
2692 struct Scsi_Host *instance = cmd->device->host;
2693 SETUP_HOSTDATA(instance);
2694 struct scsi_cmnd *tmp, **prev;
2695 unsigned long flags;
2696
2697 printk(KERN_NOTICE "scsi%d: aborting command\n", HOSTNO);
2698 scsi_print_command(cmd);
2699
2700 NCR5380_print_status (instance);
2701
2702 local_irq_save(flags);
2703
2704 ABRT_PRINTK("scsi%d: abort called basr 0x%02x, sr 0x%02x\n", HOSTNO,
2705 NCR5380_read(BUS_AND_STATUS_REG),
2706 NCR5380_read(STATUS_REG));
2707
2708#if 1
2709
2710
2711
2712
2713
2714
2715 if (hostdata->connected == cmd) {
2716
2717 ABRT_PRINTK("scsi%d: aborting connected command\n", HOSTNO);
2718
2719
2720
2721
2722
2723
2724
2725
2726
2727
2728
2729
2730
2731
2732
2733
2734
2735 if (do_abort(instance) == 0) {
2736 hostdata->aborted = 1;
2737 hostdata->connected = NULL;
2738 cmd->result = DID_ABORT << 16;
2739#ifdef SUPPORT_TAGS
2740 cmd_free_tag( cmd );
2741#else
2742 hostdata->busy[cmd->device->id] &= ~(1 << cmd->device->lun);
2743#endif
2744 local_irq_restore(flags);
2745 cmd->scsi_done(cmd);
2746 return SCSI_ABORT_SUCCESS;
2747 } else {
2748
2749 printk("scsi%d: abort of connected command failed!\n", HOSTNO);
2750 return SCSI_ABORT_ERROR;
2751 }
2752 }
2753#endif
2754
2755
2756
2757
2758
2759 for (prev = (struct scsi_cmnd **) &(hostdata->issue_queue),
2760 tmp = (struct scsi_cmnd *) hostdata->issue_queue;
2761 tmp; prev = NEXTADDR(tmp), tmp = NEXT(tmp))
2762 if (cmd == tmp) {
2763 REMOVE(5, *prev, tmp, NEXT(tmp));
2764 (*prev) = NEXT(tmp);
2765 NEXT(tmp) = NULL;
2766 tmp->result = DID_ABORT << 16;
2767 local_irq_restore(flags);
2768 ABRT_PRINTK("scsi%d: abort removed command from issue queue.\n",
2769 HOSTNO);
2770
2771
2772 tmp->scsi_done(tmp);
2773 return SCSI_ABORT_SUCCESS;
2774 }
2775
2776
2777
2778
2779
2780
2781
2782
2783
2784
2785
2786
2787 if (hostdata->connected) {
2788 local_irq_restore(flags);
2789 ABRT_PRINTK("scsi%d: abort failed, command connected.\n", HOSTNO);
2790 return SCSI_ABORT_SNOOZE;
2791 }
2792
2793
2794
2795
2796
2797
2798
2799
2800
2801
2802
2803
2804
2805
2806
2807
2808
2809
2810
2811
2812
2813
2814
2815
2816
2817
2818 for (tmp = (struct scsi_cmnd *) hostdata->disconnected_queue; tmp;
2819 tmp = NEXT(tmp))
2820 if (cmd == tmp) {
2821 local_irq_restore(flags);
2822 ABRT_PRINTK("scsi%d: aborting disconnected command.\n", HOSTNO);
2823
2824 if (NCR5380_select (instance, cmd, (int) cmd->tag))
2825 return SCSI_ABORT_BUSY;
2826
2827 ABRT_PRINTK("scsi%d: nexus reestablished.\n", HOSTNO);
2828
2829 do_abort (instance);
2830
2831 local_irq_save(flags);
2832 for (prev = (struct scsi_cmnd **) &(hostdata->disconnected_queue),
2833 tmp = (struct scsi_cmnd *) hostdata->disconnected_queue;
2834 tmp; prev = NEXTADDR(tmp), tmp = NEXT(tmp) )
2835 if (cmd == tmp) {
2836 REMOVE(5, *prev, tmp, NEXT(tmp));
2837 *prev = NEXT(tmp);
2838 NEXT(tmp) = NULL;
2839 tmp->result = DID_ABORT << 16;
2840
2841
2842
2843
2844#ifdef SUPPORT_TAGS
2845 cmd_free_tag( tmp );
2846#else
2847 hostdata->busy[cmd->device->id] &= ~(1 << cmd->device->lun);
2848#endif
2849 local_irq_restore(flags);
2850 tmp->scsi_done(tmp);
2851 return SCSI_ABORT_SUCCESS;
2852 }
2853 }
2854
2855
2856
2857
2858
2859
2860
2861
2862
2863
2864
2865 local_irq_restore(flags);
2866 printk(KERN_INFO "scsi%d: warning : SCSI command probably completed successfully before abortion\n", HOSTNO);
2867
2868 return SCSI_ABORT_NOT_RUNNING;
2869}
2870
2871
2872
2873
2874
2875
2876
2877
2878
2879
2880
2881static int NCR5380_bus_reset(struct scsi_cmnd *cmd)
2882{
2883 SETUP_HOSTDATA(cmd->device->host);
2884 int i;
2885 unsigned long flags;
2886#if 1
2887 struct scsi_cmnd *connected, *disconnected_queue;
2888#endif
2889
2890
2891 NCR5380_print_status (cmd->device->host);
2892
2893
2894 NCR5380_write( TARGET_COMMAND_REG,
2895 PHASE_SR_TO_TCR( NCR5380_read(STATUS_REG) ));
2896
2897 NCR5380_write( INITIATOR_COMMAND_REG, ICR_BASE | ICR_ASSERT_RST );
2898 udelay (40);
2899
2900 NCR5380_write( INITIATOR_COMMAND_REG, ICR_BASE );
2901 NCR5380_write( MODE_REG, MR_BASE );
2902 NCR5380_write( TARGET_COMMAND_REG, 0 );
2903 NCR5380_write( SELECT_ENABLE_REG, 0 );
2904
2905
2906 (void)NCR5380_read( RESET_PARITY_INTERRUPT_REG );
2907
2908#if 1
2909
2910
2911
2912
2913
2914
2915
2916
2917
2918 local_irq_save(flags);
2919 connected = (struct scsi_cmnd *)hostdata->connected;
2920 hostdata->connected = NULL;
2921 disconnected_queue = (struct scsi_cmnd *)hostdata->disconnected_queue;
2922 hostdata->disconnected_queue = NULL;
2923#ifdef SUPPORT_TAGS
2924 free_all_tags();
2925#endif
2926 for( i = 0; i < 8; ++i )
2927 hostdata->busy[i] = 0;
2928#ifdef REAL_DMA
2929 hostdata->dma_len = 0;
2930#endif
2931 local_irq_restore(flags);
2932
2933
2934
2935
2936
2937
2938 if ((cmd = connected)) {
2939 ABRT_PRINTK("scsi%d: reset aborted a connected command\n", H_NO(cmd));
2940 cmd->result = (cmd->result & 0xffff) | (DID_RESET << 16);
2941 cmd->scsi_done( cmd );
2942 }
2943
2944 for (i = 0; (cmd = disconnected_queue); ++i) {
2945 disconnected_queue = NEXT(cmd);
2946 NEXT(cmd) = NULL;
2947 cmd->result = (cmd->result & 0xffff) | (DID_RESET << 16);
2948 cmd->scsi_done( cmd );
2949 }
2950 if (i > 0)
2951 ABRT_PRINTK("scsi: reset aborted %d disconnected command(s)\n", i);
2952
2953
2954
2955
2956
2957
2958 return SCSI_RESET_SUCCESS | SCSI_RESET_BUS_RESET;
2959#else
2960
2961
2962
2963
2964
2965
2966
2967
2968
2969
2970
2971
2972
2973
2974
2975
2976
2977
2978
2979
2980
2981
2982
2983
2984 if (hostdata->issue_queue)
2985 ABRT_PRINTK("scsi%d: reset aborted issued command(s)\n", H_NO(cmd));
2986 if (hostdata->connected)
2987 ABRT_PRINTK("scsi%d: reset aborted a connected command\n", H_NO(cmd));
2988 if (hostdata->disconnected_queue)
2989 ABRT_PRINTK("scsi%d: reset aborted disconnected command(s)\n", H_NO(cmd));
2990
2991 local_irq_save(flags);
2992 hostdata->issue_queue = NULL;
2993 hostdata->connected = NULL;
2994 hostdata->disconnected_queue = NULL;
2995#ifdef SUPPORT_TAGS
2996 free_all_tags();
2997#endif
2998 for( i = 0; i < 8; ++i )
2999 hostdata->busy[i] = 0;
3000#ifdef REAL_DMA
3001 hostdata->dma_len = 0;
3002#endif
3003 local_irq_restore(flags);
3004
3005
3006 return SCSI_RESET_WAKEUP | SCSI_RESET_BUS_RESET;
3007#endif
3008}
3009
3010
3011
3012
3013