|
|
1.1 ! root 1: /* aha152x.c -- Adaptec AHA-152x driver ! 2: * Author: J�rgen E. Fischer, [email protected] ! 3: * Copyright 1993, 1994, 1995, 1996 J�rgen E. Fischer ! 4: * ! 5: * ! 6: * This driver is based on ! 7: * fdomain.c -- Future Domain TMC-16x0 driver ! 8: * which is ! 9: * Copyright 1992, 1993 Rickard E. Faith ([email protected]) ! 10: * ! 11: * ! 12: * This program is free software; you can redistribute it and/or modify it ! 13: * under the terms of the GNU General Public License as published by the ! 14: * Free Software Foundation; either version 2, or (at your option) any ! 15: * later version. ! 16: * ! 17: * This program is distributed in the hope that it will be useful, but ! 18: * WITHOUT ANY WARRANTY; without even the implied warranty of ! 19: * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU ! 20: * General Public License for more details. ! 21: * ! 22: * ! 23: * $Id: aha152x.c,v 1.1 1999/04/26 05:44:22 tb Exp $ ! 24: * ! 25: * $Log: aha152x.c,v $ ! 26: * Revision 1.1 1999/04/26 05:44:22 tb ! 27: * 1999-04-12 OKUJI Yoshinori <[email protected]> ! 28: * ! 29: * * linux/dev/drivers/block/ide.c (init_hwif_data) [MACH]: Print Mach ! 30: * device name instead of Linux one. ! 31: * * linux/dev/drivers/block/genhd.c (disk_name): Likewise. ! 32: * * linux/dev/drivers/scsi/sd.c (sd_init_onedisk): Likewise. ! 33: * (sd_detect): Likewise. ! 34: * * linux/dev/drivers/sr.c (sr_detect): Likewise. ! 35: * (get_sectorsize): Likewise. ! 36: * ! 37: * 1999-02-04 OKUJI Yoshinori <[email protected]> ! 38: * ! 39: * * device/kmsg.c (kmsginit): Add a missing semicolon. ! 40: * (kmsggetstat): Fix typos, ! 41: * DEV_GET_DEVICE_SIZE -> DEV_GET_SIZE_DEVICE_SIZE and ! 42: * DEV_GET_RECORD_SIZE -> DEV_GET_SIZE_RECORD_SIZE. ! 43: * (kmsg_putchar): Fix a typo kmsg_done_init -> kmsg_init_done. ! 44: * * linux/dev/glue/block.c (device_get_status): Allocate a hd_geometry ! 45: * on the stack. ! 46: * * linux/dev/drivers/block/ide.c: New file. ! 47: * * linux/dev/drivers/scsi/sd_ioctl.c: New file. ! 48: * ! 49: * Revision 1.18 1996/09/07 20:10:40 fischer ! 50: * - fixed can_queue handling (multiple outstanding commands working again) ! 51: * ! 52: * Revision 1.17 1996/08/17 16:05:14 fischer ! 53: * - biosparam improved ! 54: * - interrupt verification ! 55: * - updated documentation ! 56: * - cleanups ! 57: * ! 58: * Revision 1.16 1996/06/09 00:04:56 root ! 59: * - added configuration symbols for insmod (aha152x/aha152x1) ! 60: * ! 61: * Revision 1.15 1996/04/30 14:52:06 fischer ! 62: * - proc info fixed ! 63: * - support for extended translation for >1GB disks ! 64: * ! 65: * Revision 1.14 1996/01/17 15:11:20 fischer ! 66: * - fixed lockup in MESSAGE IN phase after reconnection ! 67: * ! 68: * Revision 1.13 1996/01/09 02:15:53 fischer ! 69: * - some cleanups ! 70: * - moved request_irq behind controller initialization ! 71: * (to avoid spurious interrupts) ! 72: * ! 73: * Revision 1.12 1995/12/16 12:26:07 fischer ! 74: * - barrier()s added ! 75: * - configurable RESET delay added ! 76: * ! 77: * Revision 1.11 1995/12/06 21:18:35 fischer ! 78: * - some minor updates ! 79: * ! 80: * Revision 1.10 1995/07/22 19:18:45 fischer ! 81: * - support for 2 controllers ! 82: * - started synchronous data transfers (not working yet) ! 83: * ! 84: * Revision 1.9 1995/03/18 09:20:24 root ! 85: * - patches for PCMCIA and modules ! 86: * ! 87: * Revision 1.8 1995/01/21 22:07:19 root ! 88: * - snarf_region => request_region ! 89: * - aha152x_intr interface change ! 90: * ! 91: * Revision 1.7 1995/01/02 23:19:36 root ! 92: * - updated COMMAND_SIZE to cmd_len ! 93: * - changed sti() to restore_flags() ! 94: * - fixed some #ifdef which generated warnings ! 95: * ! 96: * Revision 1.6 1994/11/24 20:35:27 root ! 97: * - problem with odd number of bytes in fifo fixed ! 98: * ! 99: * Revision 1.5 1994/10/30 14:39:56 root ! 100: * - abort code fixed ! 101: * - debugging improved ! 102: * ! 103: * Revision 1.4 1994/09/12 11:33:01 root ! 104: * - irqaction to request_irq ! 105: * - abortion updated ! 106: * ! 107: * Revision 1.3 1994/08/04 13:53:05 root ! 108: * - updates for mid-level-driver changes ! 109: * - accept unexpected BUSFREE phase as error condition ! 110: * - parity check now configurable ! 111: * ! 112: * Revision 1.2 1994/07/03 12:56:36 root ! 113: * - cleaned up debugging code ! 114: * - more tweaking on reset delays ! 115: * - updated abort/reset code (pretty untested...) ! 116: * ! 117: * Revision 1.1 1994/05/28 21:18:49 root ! 118: * - update for mid-level interface change (abort-reset) ! 119: * - delays after resets adjusted for some slow devices ! 120: * ! 121: * Revision 1.0 1994/03/25 12:52:00 root ! 122: * - Fixed "more data than expected" problem ! 123: * - added new BIOS signatures ! 124: * ! 125: * Revision 0.102 1994/01/31 20:44:12 root ! 126: * - minor changes in insw/outsw handling ! 127: * ! 128: * Revision 0.101 1993/12/13 01:16:27 root ! 129: * - fixed STATUS phase (non-GOOD stati were dropped sometimes; ! 130: * fixes problems with CD-ROM sector size detection & media change) ! 131: * ! 132: * Revision 0.100 1993/12/10 16:58:47 root ! 133: * - fix for unsuccessful selections in case of non-continuous id assignments ! 134: * on the scsi bus. ! 135: * ! 136: * Revision 0.99 1993/10/24 16:19:59 root ! 137: * - fixed DATA IN (rare read errors gone) ! 138: * ! 139: * Revision 0.98 1993/10/17 12:54:44 root ! 140: * - fixed some recent fixes (shame on me) ! 141: * - moved initialization of scratch area to aha152x_queue ! 142: * ! 143: * Revision 0.97 1993/10/09 18:53:53 root ! 144: * - DATA IN fixed. Rarely left data in the fifo. ! 145: * ! 146: * Revision 0.96 1993/10/03 00:53:59 root ! 147: * - minor changes on DATA IN ! 148: * ! 149: * Revision 0.95 1993/09/24 10:36:01 root ! 150: * - change handling of MSGI after reselection ! 151: * - fixed sti/cli ! 152: * - minor changes ! 153: * ! 154: * Revision 0.94 1993/09/18 14:08:22 root ! 155: * - fixed bug in multiple outstanding command code ! 156: * - changed detection ! 157: * - support for kernel command line configuration ! 158: * - reset corrected ! 159: * - changed message handling ! 160: * ! 161: * Revision 0.93 1993/09/15 20:41:19 root ! 162: * - fixed bugs with multiple outstanding commands ! 163: * ! 164: * Revision 0.92 1993/09/13 02:46:33 root ! 165: * - multiple outstanding commands work (no problems with IBM drive) ! 166: * ! 167: * Revision 0.91 1993/09/12 20:51:46 root ! 168: * added multiple outstanding commands ! 169: * (some problem with this $%&? IBM device remain) ! 170: * ! 171: * Revision 0.9 1993/09/12 11:11:22 root ! 172: * - corrected auto-configuration ! 173: * - changed the auto-configuration (added some '#define's) ! 174: * - added support for dis-/reconnection ! 175: * ! 176: * Revision 0.8 1993/09/06 23:09:39 root ! 177: * - added support for the drive activity light ! 178: * - minor changes ! 179: * ! 180: * Revision 0.7 1993/09/05 14:30:15 root ! 181: * - improved phase detection ! 182: * - now using the new snarf_region code of 0.99pl13 ! 183: * ! 184: * Revision 0.6 1993/09/02 11:01:38 root ! 185: * first public release; added some signatures and biosparam() ! 186: * ! 187: * Revision 0.5 1993/08/30 10:23:30 root ! 188: * fixed timing problems with my IBM drive ! 189: * ! 190: * Revision 0.4 1993/08/29 14:06:52 root ! 191: * fixed some problems with timeouts due incomplete commands ! 192: * ! 193: * Revision 0.3 1993/08/28 15:55:03 root ! 194: * writing data works too. mounted and worked on a dos partition ! 195: * ! 196: * Revision 0.2 1993/08/27 22:42:07 root ! 197: * reading data works. Mounted a msdos partition. ! 198: * ! 199: * Revision 0.1 1993/08/25 13:38:30 root ! 200: * first "damn thing doesn't work" version ! 201: * ! 202: * Revision 0.0 1993/08/14 19:54:25 root ! 203: * empty function bodies; detect() works. ! 204: * ! 205: * ! 206: ************************************************************************** ! 207: ! 208: ! 209: ! 210: DESCRIPTION: ! 211: ! 212: This is the Linux low-level SCSI driver for Adaptec AHA-1520/1522 SCSI ! 213: host adapters. ! 214: ! 215: ! 216: CONFIGURATION ARGUMENTS: ! 217: ! 218: IOPORT base io address (0x340/0x140) ! 219: IRQ interrupt level (9-12; default 11) ! 220: SCSI_ID scsi id of controller (0-7; default 7) ! 221: RECONNECT allow targets to disconnect from the bus (0/1; default 1 [on]) ! 222: PARITY enable parity checking (0/1; default 1 [on]) ! 223: SYNCHRONOUS enable synchronous transfers (0/1; default 0 [off]) ! 224: (NOT WORKING YET) ! 225: DELAY: bus reset delay (default 100) ! 226: EXT_TRANS: enable extended translation (0/1: default 0 [off]) ! 227: (see NOTES below) ! 228: ! 229: COMPILE TIME CONFIGURATION (put into AHA152X in drivers/scsi/Makefile): ! 230: ! 231: -DAUTOCONF ! 232: use configuration the controller reports (AHA-152x only) ! 233: ! 234: -DSKIP_BIOSTEST ! 235: Don't test for BIOS signature (AHA-1510 or disabled BIOS) ! 236: ! 237: -DSETUP0="{ IOPORT, IRQ, SCSI_ID, RECONNECT, PARITY, SYNCHRONOUS, DELAY, EXT_TRANS }" ! 238: override for the first controller ! 239: ! 240: -DSETUP1="{ IOPORT, IRQ, SCSI_ID, RECONNECT, PARITY, SYNCHRONOUS, DELAY, EXT_TRANS }" ! 241: override for the second controller ! 242: ! 243: ! 244: LILO COMMAND LINE OPTIONS: ! 245: ! 246: aha152x=<IOPORT>[,<IRQ>[,<SCSI-ID>[,<RECONNECT>[,<PARITY>[,<SYNCHRONOUS>[,<DELAY> [,<EXT_TRANS]]]]]]] ! 247: ! 248: The normal configuration can be overridden by specifying a command line. ! 249: When you do this, the BIOS test is skipped. Entered values have to be ! 250: valid (known). Don't use values that aren't supported under normal ! 251: operation. If you think that you need other values: contact me. ! 252: For two controllers use the aha152x statement twice. ! 253: ! 254: ! 255: SYMBOLS FOR MODULE CONFIGURATION: ! 256: ! 257: aha152x=IOPORT,IRQ,SCSI_ID,RECONNECT,PARITY,SYNCHRONOUS,DELAY,EXT_TRANS ! 258: configuration override of first controller ! 259: ! 260: ! 261: aha152x1=IOPORT,IRQ,SCSI_ID,RECONNECT,PARITY,SYNCHRONOUS,DELAY,EXT_TRANS ! 262: configuration override of second controller ! 263: ! 264: ! 265: NOTES ON EXT_TRANS: ! 266: ! 267: SCSI uses block numbers to address blocks/sectors on a device. ! 268: The BIOS uses a cylinder/head/sector addressing scheme (C/H/S) ! 269: scheme instead. DOS expects a BIOS or driver that understands this ! 270: C/H/S addressing. ! 271: ! 272: The number of cylinders/heads/sectors is called geometry and is required ! 273: as base for requests in C/H/S adressing. SCSI only knows about the ! 274: total capacity of disks in blocks (sectors). ! 275: ! 276: Therefore the SCSI BIOS/DOS driver has to calculate a logical/virtual ! 277: geometry just to be able to support that addressing scheme. The geometry ! 278: returned by the SCSI BIOS is a pure calculation and has nothing to ! 279: do with the real/physical geometry of the disk (which is usually ! 280: irrelevant anyway). ! 281: ! 282: Basically this has no impact at all on Linux, because it also uses block ! 283: instead of C/H/S addressing. Unfortunately C/H/S addressing is also used ! 284: in the partition table and therefore every operating system has to know ! 285: the right geometry to be able to interpret it. ! 286: ! 287: Moreover there are certain limitations to the C/H/S addressing scheme, ! 288: namely the address space is limited to upto 255 heads, upto 63 sectors ! 289: and a maximum of 1023 cylinders. ! 290: ! 291: The AHA-1522 BIOS calculates the geometry by fixing the number of heads ! 292: to 64, the number of sectors to 32 and by calculating the number of ! 293: cylinders by dividing the capacity reported by the disk by 64*32 (1 MB). ! 294: This is considered to be the default translation. ! 295: ! 296: With respect to the limit of 1023 cylinders using C/H/S you can only ! 297: address the first GB of your disk in the partition table. Therefore ! 298: BIOSes of some newer controllers based on the AIC-6260/6360 support ! 299: extended translation. This means that the BIOS uses 255 for heads, ! 300: 63 for sectors and then divides the capacity of the disk by 255*63 ! 301: (about 8 MB), as soon it sees a disk greater than 1 GB. That results ! 302: in a maximum of about 8 GB adressable diskspace in the partition table ! 303: (but there are already bigger disks out there today). ! 304: ! 305: To make it even more complicated the translation mode might/might ! 306: not be configurable in certain BIOS setups. ! 307: ! 308: This driver does some more or less failsafe guessing to get the ! 309: geometry right in most cases: ! 310: ! 311: - for disks<1GB: use default translation (C/32/64) ! 312: - for disks>1GB: ! 313: - take current geometry from the partition table ! 314: (using scsicam_bios_param and accept only `valid' geometries, ! 315: ie. either (C/32/64) or (C/63/255)). This can be extended ! 316: translation even if it's not enabled in the driver. ! 317: - if that fails, take extended translation if enabled by override, ! 318: kernel or module parameter, otherwise take default translation and ! 319: ask the user for verification. This might on not yet partitioned ! 320: disks or ! 321: ! 322: ! 323: REFERENCES USED: ! 324: ! 325: "AIC-6260 SCSI Chip Specification", Adaptec Corporation. ! 326: ! 327: "SCSI COMPUTER SYSTEM INTERFACE - 2 (SCSI-2)", X3T9.2/86-109 rev. 10h ! 328: ! 329: "Writing a SCSI device driver for Linux", Rik Faith ([email protected]) ! 330: ! 331: "Kernel Hacker's Guide", Michael K. Johnson ([email protected]) ! 332: ! 333: "Adaptec 1520/1522 User's Guide", Adaptec Corporation. ! 334: ! 335: Michael K. Johnson ([email protected]) ! 336: ! 337: Drew Eckhardt ([email protected]) ! 338: ! 339: Eric Youngdale ([email protected]) ! 340: ! 341: special thanks to Eric Youngdale for the free(!) supplying the ! 342: documentation on the chip. ! 343: ! 344: **************************************************************************/ ! 345: ! 346: #ifdef MACH ! 347: #define AUTOCONF 1 ! 348: #endif ! 349: ! 350: #ifdef PCMCIA ! 351: #define MODULE ! 352: #endif ! 353: ! 354: #include <linux/module.h> ! 355: ! 356: #ifdef PCMCIA ! 357: #undef MODULE ! 358: #endif ! 359: ! 360: #include <linux/sched.h> ! 361: #include <asm/io.h> ! 362: #include <linux/blk.h> ! 363: #include "scsi.h" ! 364: #include "sd.h" ! 365: #include "hosts.h" ! 366: #include "constants.h" ! 367: #include <asm/system.h> ! 368: #include <linux/errno.h> ! 369: #include <linux/string.h> ! 370: #include <linux/wait.h> ! 371: #include <linux/ioport.h> ! 372: #include <linux/proc_fs.h> ! 373: ! 374: #include "aha152x.h" ! 375: #include <linux/stat.h> ! 376: ! 377: #include <scsi/scsicam.h> ! 378: ! 379: struct proc_dir_entry proc_scsi_aha152x = { ! 380: PROC_SCSI_AHA152X, 7, "aha152x", ! 381: S_IFDIR | S_IRUGO | S_IXUGO, 2 ! 382: }; ! 383: ! 384: /* DEFINES */ ! 385: ! 386: /* For PCMCIA cards, always use AUTOCONF */ ! 387: #if defined(PCMCIA) || defined(MODULE) ! 388: #if !defined(AUTOCONF) ! 389: #define AUTOCONF ! 390: #endif ! 391: #endif ! 392: ! 393: #if !defined(AUTOCONF) && !defined(SETUP0) ! 394: #error define AUTOCONF or SETUP0 ! 395: #endif ! 396: ! 397: #if defined(DEBUG_AHA152X) ! 398: ! 399: #undef SKIP_PORTS /* don't display ports */ ! 400: ! 401: #undef DEBUG_QUEUE /* debug queue() */ ! 402: #undef DEBUG_RESET /* debug reset() */ ! 403: #undef DEBUG_INTR /* debug intr() */ ! 404: #undef DEBUG_SELECTION /* debug selection part in intr() */ ! 405: #undef DEBUG_MSGO /* debug message out phase in intr() */ ! 406: #undef DEBUG_MSGI /* debug message in phase in intr() */ ! 407: #undef DEBUG_STATUS /* debug status phase in intr() */ ! 408: #undef DEBUG_CMD /* debug command phase in intr() */ ! 409: #undef DEBUG_DATAI /* debug data in phase in intr() */ ! 410: #undef DEBUG_DATAO /* debug data out phase in intr() */ ! 411: #undef DEBUG_ABORT /* debug abort() */ ! 412: #undef DEBUG_DONE /* debug done() */ ! 413: #undef DEBUG_BIOSPARAM /* debug biosparam() */ ! 414: ! 415: #undef DEBUG_RACE /* debug race conditions */ ! 416: #undef DEBUG_PHASES /* debug phases (useful to trace) */ ! 417: #undef DEBUG_QUEUES /* debug reselection */ ! 418: ! 419: /* recently used for debugging */ ! 420: #if 0 ! 421: #endif ! 422: ! 423: #define DEBUG_SELECTION ! 424: #define DEBUG_PHASES ! 425: #define DEBUG_RESET ! 426: #define DEBUG_ABORT ! 427: ! 428: #define DEBUG_DEFAULT (debug_reset|debug_abort) ! 429: ! 430: #endif ! 431: ! 432: /* END OF DEFINES */ ! 433: ! 434: extern unsigned long loops_per_sec; ! 435: ! 436: #define DELAY_DEFAULT 100 ! 437: ! 438: /* some additional "phases" for getphase() */ ! 439: #define P_BUSFREE 1 ! 440: #define P_PARITY 2 ! 441: ! 442: /* possible irq range */ ! 443: #define IRQ_MIN 9 ! 444: #define IRQ_MAX 12 ! 445: #define IRQS IRQ_MAX-IRQ_MIN+1 ! 446: ! 447: enum { ! 448: not_issued = 0x0001, ! 449: in_selection = 0x0002, ! 450: disconnected = 0x0004, ! 451: aborted = 0x0008, ! 452: sent_ident = 0x0010, ! 453: in_other = 0x0020, ! 454: in_sync = 0x0040, ! 455: sync_ok = 0x0080, ! 456: }; ! 457: ! 458: #if defined(MODULE) ! 459: #if defined(DEBUG_AHA152X) ! 460: int aha152x[] = { 0, 11, 7, 1, 1, 0, DELAY_DEFAULT, 0, DEBUG_DEFAULT }; ! 461: int aha152x1[] = { 0, 11, 7, 1, 1, 0, DELAY_DEFAULT, 0, DEBUG_DEFAULT }; ! 462: #else ! 463: int aha152x[] = { 0, 11, 7, 1, 1, 0, DELAY_DEFAULT, 0 }; ! 464: int aha152x1[] = { 0, 11, 7, 1, 1, 0, DELAY_DEFAULT, 0 }; ! 465: #endif ! 466: #endif ! 467: ! 468: /* set by aha152x_setup according to the command line */ ! 469: static int setup_count=0; ! 470: static struct aha152x_setup { ! 471: int io_port; ! 472: int irq; ! 473: int scsiid; ! 474: int reconnect; ! 475: int parity; ! 476: int synchronous; ! 477: int delay; ! 478: int ext_trans; ! 479: #ifdef DEBUG_AHA152X ! 480: int debug; ! 481: #endif ! 482: char *conf; ! 483: } setup[2]; ! 484: ! 485: static struct Scsi_Host *aha152x_host[IRQS]; ! 486: ! 487: #define HOSTDATA(shpnt) ((struct aha152x_hostdata *) &shpnt->hostdata) ! 488: #define CURRENT_SC (HOSTDATA(shpnt)->current_SC) ! 489: #define ISSUE_SC (HOSTDATA(shpnt)->issue_SC) ! 490: #define DISCONNECTED_SC (HOSTDATA(shpnt)->disconnected_SC) ! 491: #define DELAY (HOSTDATA(shpnt)->delay) ! 492: #define EXT_TRANS (HOSTDATA(shpnt)->ext_trans) ! 493: #define SYNCRATE (HOSTDATA(shpnt)->syncrate[CURRENT_SC->target]) ! 494: #define MSG(i) (HOSTDATA(shpnt)->message[i]) ! 495: #define MSGLEN (HOSTDATA(shpnt)->message_len) ! 496: #define ADDMSG(x) (MSG(MSGLEN++)=x) ! 497: ! 498: struct aha152x_hostdata { ! 499: Scsi_Cmnd *issue_SC; ! 500: Scsi_Cmnd *current_SC; ! 501: Scsi_Cmnd *disconnected_SC; ! 502: int aborting; ! 503: int abortion_complete; ! 504: int abort_result; ! 505: int commands; ! 506: ! 507: int reconnect; ! 508: int parity; ! 509: int synchronous; ! 510: int delay; ! 511: int ext_trans; ! 512: ! 513: int swint; ! 514: ! 515: unsigned char syncrate[8]; ! 516: ! 517: unsigned char message[256]; ! 518: int message_len; ! 519: ! 520: #ifdef DEBUG_AHA152X ! 521: int debug; ! 522: #endif ! 523: }; ! 524: ! 525: void aha152x_intr(int irq, void *dev_id, struct pt_regs *); ! 526: void aha152x_done(struct Scsi_Host *shpnt, int error); ! 527: void aha152x_setup(char *str, int *ints); ! 528: int aha152x_checksetup(struct aha152x_setup *setup); ! 529: ! 530: static void aha152x_reset_ports(struct Scsi_Host *shpnt); ! 531: static void aha152x_panic(struct Scsi_Host *shpnt, char *msg); ! 532: ! 533: static void disp_ports(struct Scsi_Host *shpnt); ! 534: static void show_command(Scsi_Cmnd *ptr); ! 535: static void show_queues(struct Scsi_Host *shpnt); ! 536: static void disp_enintr(struct Scsi_Host *shpnt); ! 537: ! 538: #if defined(DEBUG_RACE) ! 539: static void enter_driver(const char *); ! 540: static void leave_driver(const char *); ! 541: #endif ! 542: ! 543: /* possible i/o addresses for the AIC-6260 */ ! 544: static unsigned short ports[] = ! 545: { ! 546: 0x340, /* default first */ ! 547: 0x140 ! 548: }; ! 549: #define PORT_COUNT (sizeof(ports) / sizeof(unsigned short)) ! 550: ! 551: #if !defined(SKIP_BIOSTEST) ! 552: /* possible locations for the Adaptec BIOS */ ! 553: static void *addresses[] = ! 554: { ! 555: (void *) 0xdc000, /* default first */ ! 556: (void *) 0xc8000, ! 557: (void *) 0xcc000, ! 558: (void *) 0xd0000, ! 559: (void *) 0xd4000, ! 560: (void *) 0xd8000, ! 561: (void *) 0xe0000, ! 562: (void *) 0xeb800, /* VTech Platinum SMP */ ! 563: (void *) 0xf0000, ! 564: }; ! 565: #define ADDRESS_COUNT (sizeof(addresses) / sizeof(void *)) ! 566: ! 567: /* signatures for various AIC-6[23]60 based controllers. ! 568: The point in detecting signatures is to avoid useless and maybe ! 569: harmful probes on ports. I'm not sure that all listed boards pass ! 570: auto-configuration. For those which fail the BIOS signature is ! 571: obsolete, because user intervention to supply the configuration is ! 572: needed anyway. May be an information whether or not the BIOS supports ! 573: extended translation could be also useful here. */ ! 574: static struct signature { ! 575: char *signature; ! 576: int sig_offset; ! 577: int sig_length; ! 578: } signatures[] = ! 579: { ! 580: { "Adaptec AHA-1520 BIOS", 0x102e, 21 }, /* Adaptec 152x */ ! 581: { "Adaptec AHA-1520B", 0x0b, 17 }, /* Adaptec 152x rev B */ ! 582: { "Adaptec AHA-1520B/1522B", 0x3e20, 23 }, /* Adaptec 1520B/1522B */ ! 583: { "Adaptec ASW-B626 BIOS", 0x1029, 21 }, /* on-board controller */ ! 584: { "Adaptec BIOS: ASW-B626", 0x0f, 22 }, /* on-board controller */ ! 585: { "Adaptec ASW-B626 S2", 0x2e6c, 19 }, /* on-board controller */ ! 586: { "Adaptec BIOS:AIC-6360", 0xc, 21 }, /* on-board controller */ ! 587: { "ScsiPro SP-360 BIOS", 0x2873, 19 }, /* ScsiPro-Controller */ ! 588: { "GA-400 LOCAL BUS SCSI BIOS", 0x102e, 26 }, /* Gigabyte Local-Bus-SCSI */ ! 589: { "Adaptec BIOS:AVA-282X", 0xc, 21 }, /* Adaptec 282x */ ! 590: { "Adaptec IBM Dock II SCSI", 0x2edd, 24 }, /* IBM Thinkpad Dock II */ ! 591: { "Adaptec BIOS:AHA-1532P", 0x1c, 22 }, /* IBM Thinkpad Dock II SCSI */ ! 592: }; ! 593: #define SIGNATURE_COUNT (sizeof(signatures) / sizeof(struct signature)) ! 594: #endif ! 595: ! 596: ! 597: static void do_pause(unsigned amount) /* Pause for amount*10 milliseconds */ ! 598: { ! 599: unsigned long the_time = jiffies + amount; /* 0.01 seconds per jiffy */ ! 600: ! 601: while (jiffies < the_time) ! 602: barrier(); ! 603: } ! 604: ! 605: /* ! 606: * queue services: ! 607: */ ! 608: static inline void append_SC(Scsi_Cmnd **SC, Scsi_Cmnd *new_SC) ! 609: { ! 610: Scsi_Cmnd *end; ! 611: ! 612: new_SC->host_scribble = (unsigned char *) NULL; ! 613: if(!*SC) ! 614: *SC=new_SC; ! 615: else { ! 616: for(end=*SC; end->host_scribble; end = (Scsi_Cmnd *) end->host_scribble) ! 617: ; ! 618: end->host_scribble = (unsigned char *) new_SC; ! 619: } ! 620: } ! 621: ! 622: static inline Scsi_Cmnd *remove_first_SC(Scsi_Cmnd **SC) ! 623: { ! 624: Scsi_Cmnd *ptr; ! 625: ! 626: ptr=*SC; ! 627: if(ptr) ! 628: *SC= (Scsi_Cmnd *) (*SC)->host_scribble; ! 629: return ptr; ! 630: } ! 631: ! 632: static inline Scsi_Cmnd *remove_SC(Scsi_Cmnd **SC, int target, int lun) ! 633: { ! 634: Scsi_Cmnd *ptr, *prev; ! 635: ! 636: for(ptr=*SC, prev=NULL; ! 637: ptr && ((ptr->target!=target) || (ptr->lun!=lun)); ! 638: prev = ptr, ptr = (Scsi_Cmnd *) ptr->host_scribble) ! 639: ; ! 640: ! 641: if(ptr){ ! 642: if(prev) ! 643: prev->host_scribble = ptr->host_scribble; ! 644: else ! 645: *SC= (Scsi_Cmnd *) ptr->host_scribble; ! 646: } ! 647: ! 648: return ptr; ! 649: } ! 650: ! 651: /* ! 652: * read inbound byte and wait for ACK to get low ! 653: */ ! 654: static void make_acklow(struct Scsi_Host *shpnt) ! 655: { ! 656: SETPORT(SXFRCTL0, CH1|SPIOEN); ! 657: GETPORT(SCSIDAT); ! 658: SETPORT(SXFRCTL0, CH1); ! 659: ! 660: while(TESTHI(SCSISIG, ACKI)) ! 661: barrier(); ! 662: } ! 663: ! 664: /* ! 665: * detect current phase more reliable: ! 666: * phase is valid, when the target asserts REQ after we've deasserted ACK. ! 667: * ! 668: * return value is a valid phase or an error code. ! 669: * ! 670: * errorcodes: ! 671: * P_BUSFREE BUS FREE phase detected ! 672: * P_PARITY parity error in DATA phase ! 673: */ ! 674: static int getphase(struct Scsi_Host *shpnt) ! 675: { ! 676: int phase, sstat1; ! 677: ! 678: while(1) { ! 679: do { ! 680: while(!((sstat1 = GETPORT(SSTAT1)) & (BUSFREE|SCSIRSTI|REQINIT))) ! 681: barrier(); ! 682: if(sstat1 & BUSFREE) ! 683: return P_BUSFREE; ! 684: if(sstat1 & SCSIRSTI) { ! 685: printk("aha152x: RESET IN\n"); ! 686: SETPORT(SSTAT1, SCSIRSTI); ! 687: } ! 688: } while(TESTHI(SCSISIG, ACKI) || TESTLO(SSTAT1, REQINIT)); ! 689: ! 690: SETPORT(SSTAT1, CLRSCSIPERR); ! 691: ! 692: phase = GETPORT(SCSISIG) & P_MASK ; ! 693: ! 694: if(TESTHI(SSTAT1, SCSIPERR)) { ! 695: if((phase & (CDO|MSGO))==0) /* DATA phase */ ! 696: return P_PARITY; ! 697: ! 698: make_acklow(shpnt); ! 699: } else ! 700: return phase; ! 701: } ! 702: } ! 703: ! 704: /* called from init/main.c */ ! 705: void aha152x_setup(char *str, int *ints) ! 706: { ! 707: if(setup_count>2) ! 708: panic("aha152x: you can only configure up to two controllers\n"); ! 709: ! 710: setup[setup_count].conf = str; ! 711: setup[setup_count].io_port = ints[0] >= 1 ? ints[1] : 0x340; ! 712: setup[setup_count].irq = ints[0] >= 2 ? ints[2] : 11; ! 713: setup[setup_count].scsiid = ints[0] >= 3 ? ints[3] : 7; ! 714: setup[setup_count].reconnect = ints[0] >= 4 ? ints[4] : 1; ! 715: setup[setup_count].parity = ints[0] >= 5 ? ints[5] : 1; ! 716: setup[setup_count].synchronous = ints[0] >= 6 ? ints[6] : 0 /* FIXME: 1 */; ! 717: setup[setup_count].delay = ints[0] >= 7 ? ints[7] : DELAY_DEFAULT; ! 718: setup[setup_count].ext_trans = ints[0] >= 8 ? ints[8] : 0; ! 719: #ifdef DEBUG_AHA152X ! 720: setup[setup_count].debug = ints[0] >= 9 ? ints[9] : DEBUG_DEFAULT; ! 721: if(ints[0]>9) { ! 722: printk("aha152x: usage: aha152x=<IOBASE>[,<IRQ>[,<SCSI ID>" ! 723: "[,<RECONNECT>[,<PARITY>[,<SYNCHRONOUS>[,<DELAY>[,<EXT_TRANS>[,<DEBUG>]]]]]]]]\n"); ! 724: #else ! 725: if(ints[0]>8) { ! 726: printk("aha152x: usage: aha152x=<IOBASE>[,<IRQ>[,<SCSI ID>" ! 727: "[,<RECONNECT>[,<PARITY>[,<SYNCHRONOUS>[,<DELAY>[,<EXT_TRANS>]]]]]]]\n"); ! 728: #endif ! 729: } else ! 730: setup_count++; ! 731: } ! 732: ! 733: /* ! 734: * Test, if port_base is valid. ! 735: */ ! 736: static int aha152x_porttest(int io_port) ! 737: { ! 738: int i; ! 739: ! 740: if(check_region(io_port, IO_RANGE)) ! 741: return 0; ! 742: ! 743: SETPORT(io_port+O_DMACNTRL1, 0); /* reset stack pointer */ ! 744: for(i=0; i<16; i++) ! 745: SETPORT(io_port+O_STACK, i); ! 746: ! 747: SETPORT(io_port+O_DMACNTRL1, 0); /* reset stack pointer */ ! 748: for(i=0; i<16 && GETPORT(io_port+O_STACK)==i; i++) ! 749: ; ! 750: ! 751: return(i==16); ! 752: } ! 753: ! 754: int aha152x_checksetup(struct aha152x_setup *setup) ! 755: { ! 756: int i; ! 757: ! 758: #ifndef PCMCIA ! 759: for(i=0; i<PORT_COUNT && (setup->io_port != ports[i]); i++) ! 760: ; ! 761: ! 762: if(i==PORT_COUNT) ! 763: return 0; ! 764: #endif ! 765: ! 766: if(!aha152x_porttest(setup->io_port)) ! 767: return 0; ! 768: ! 769: if(setup->irq<IRQ_MIN && setup->irq>IRQ_MAX) ! 770: return 0; ! 771: ! 772: if((setup->scsiid < 0) || (setup->scsiid > 7)) ! 773: return 0; ! 774: ! 775: if((setup->reconnect < 0) || (setup->reconnect > 1)) ! 776: return 0; ! 777: ! 778: if((setup->parity < 0) || (setup->parity > 1)) ! 779: return 0; ! 780: ! 781: if((setup->synchronous < 0) || (setup->synchronous > 1)) ! 782: return 0; ! 783: ! 784: if((setup->ext_trans < 0) || (setup->ext_trans > 1)) ! 785: return 0; ! 786: ! 787: ! 788: return 1; ! 789: } ! 790: ! 791: void aha152x_swintr(int irqno, void *dev_id, struct pt_regs * regs) ! 792: { ! 793: struct Scsi_Host *shpnt = aha152x_host[irqno-IRQ_MIN]; ! 794: ! 795: if(!shpnt) ! 796: panic("aha152x: catched software interrupt for unknown controller.\n"); ! 797: ! 798: HOSTDATA(shpnt)->swint++; ! 799: } ! 800: ! 801: ! 802: int aha152x_detect(Scsi_Host_Template * tpnt) ! 803: { ! 804: int i, j, ok; ! 805: #if defined(AUTOCONF) ! 806: aha152x_config conf; ! 807: #endif ! 808: ! 809: tpnt->proc_dir = &proc_scsi_aha152x; ! 810: ! 811: for(i=0; i<IRQS; i++) ! 812: aha152x_host[i] = (struct Scsi_Host *) NULL; ! 813: ! 814: if(setup_count) { ! 815: printk("aha152x: processing commandline: "); ! 816: ! 817: for(i=0; i<setup_count; i++) ! 818: if(!aha152x_checksetup(&setup[i])) { ! 819: printk("\naha152x: %s\n", setup[i].conf); ! 820: printk("aha152x: invalid line (controller=%d)\n", i+1); ! 821: } ! 822: ! 823: printk("ok\n"); ! 824: } ! 825: ! 826: #ifdef SETUP0 ! 827: if(setup_count<2) { ! 828: struct aha152x_setup override = SETUP0; ! 829: ! 830: if(setup_count==0 || (override.io_port != setup[0].io_port)) ! 831: if(!aha152x_checksetup(&override)) { ! 832: printk("\naha152x: invalid override SETUP0={0x%x,%d,%d,%d,%d,%d,%d,%d}\n", ! 833: override.io_port, ! 834: override.irq, ! 835: override.scsiid, ! 836: override.reconnect, ! 837: override.parity, ! 838: override.synchronous, ! 839: override.delay, ! 840: override.ext_trans); ! 841: } else ! 842: setup[setup_count++] = override; ! 843: } ! 844: #endif ! 845: ! 846: #ifdef SETUP1 ! 847: if(setup_count<2) { ! 848: struct aha152x_setup override = SETUP1; ! 849: ! 850: if(setup_count==0 || (override.io_port != setup[0].io_port)) ! 851: if(!aha152x_checksetup(&override)) { ! 852: printk("\naha152x: invalid override SETUP1={0x%x,%d,%d,%d,%d,%d,%d,%d}\n", ! 853: override.io_port, ! 854: override.irq, ! 855: override.scsiid, ! 856: override.reconnect, ! 857: override.parity, ! 858: override.synchronous, ! 859: override.delay, ! 860: override.ext_trans); ! 861: } else ! 862: setup[setup_count++] = override; ! 863: } ! 864: #endif ! 865: ! 866: #if defined(MODULE) ! 867: if(setup_count<2 && aha152x[0]!=0) { ! 868: setup[setup_count].conf = ""; ! 869: setup[setup_count].io_port = aha152x[0]; ! 870: setup[setup_count].irq = aha152x[1]; ! 871: setup[setup_count].scsiid = aha152x[2]; ! 872: setup[setup_count].reconnect = aha152x[3]; ! 873: setup[setup_count].parity = aha152x[4]; ! 874: setup[setup_count].synchronous = aha152x[5]; ! 875: setup[setup_count].delay = aha152x[6]; ! 876: setup[setup_count].ext_trans = aha152x[7]; ! 877: #ifdef DEBUG_AHA152X ! 878: setup[setup_count].debug = aha152x[8]; ! 879: #endif ! 880: if(aha152x_checksetup(&setup[setup_count])) ! 881: setup_count++; ! 882: else ! 883: printk("\naha152x: invalid module argument aha152x=0x%x,%d,%d,%d,%d,%d,%d,%d\n", ! 884: setup[setup_count].io_port, ! 885: setup[setup_count].irq, ! 886: setup[setup_count].scsiid, ! 887: setup[setup_count].reconnect, ! 888: setup[setup_count].parity, ! 889: setup[setup_count].synchronous, ! 890: setup[setup_count].delay, ! 891: setup[setup_count].ext_trans); ! 892: } ! 893: ! 894: if(setup_count<2 && aha152x1[0]!=0) { ! 895: setup[setup_count].conf = ""; ! 896: setup[setup_count].io_port = aha152x1[0]; ! 897: setup[setup_count].irq = aha152x1[1]; ! 898: setup[setup_count].scsiid = aha152x1[2]; ! 899: setup[setup_count].reconnect = aha152x1[3]; ! 900: setup[setup_count].parity = aha152x1[4]; ! 901: setup[setup_count].synchronous = aha152x1[5]; ! 902: setup[setup_count].delay = aha152x1[6]; ! 903: setup[setup_count].ext_trans = aha152x1[7]; ! 904: #ifdef DEBUG_AHA152X ! 905: setup[setup_count].debug = aha152x1[8]; ! 906: #endif ! 907: if(aha152x_checksetup(&setup[setup_count])) ! 908: setup_count++; ! 909: else ! 910: printk("\naha152x: invalid module argument aha152x1=0x%x,%d,%d,%d,%d,%d,%d,%d\n", ! 911: setup[setup_count].io_port, ! 912: setup[setup_count].irq, ! 913: setup[setup_count].scsiid, ! 914: setup[setup_count].reconnect, ! 915: setup[setup_count].parity, ! 916: setup[setup_count].synchronous, ! 917: setup[setup_count].delay, ! 918: setup[setup_count].ext_trans); ! 919: } ! 920: #endif ! 921: ! 922: #if defined(AUTOCONF) ! 923: if(setup_count<2) { ! 924: #if !defined(SKIP_BIOSTEST) ! 925: ok=0; ! 926: for(i=0; i < ADDRESS_COUNT && !ok; i++) ! 927: for(j=0; (j < SIGNATURE_COUNT) && !ok; j++) ! 928: ok=!memcmp((void *) addresses[i]+signatures[j].sig_offset, ! 929: (void *) signatures[j].signature, ! 930: (int) signatures[j].sig_length); ! 931: ! 932: if(!ok && setup_count==0) ! 933: return 0; ! 934: ! 935: printk("aha152x: BIOS test: passed, "); ! 936: #else ! 937: printk("aha152x: "); ! 938: #endif /* !SKIP_BIOSTEST */ ! 939: ! 940: ok=0; ! 941: for(i=0; i<PORT_COUNT && setup_count<2; i++) { ! 942: if((setup_count==1) && (setup[0].io_port == ports[i])) ! 943: continue; ! 944: ! 945: if(aha152x_porttest(ports[i])) { ! 946: ok++; ! 947: setup[setup_count].io_port = ports[i]; ! 948: ! 949: conf.cf_port = ! 950: (GETPORT(ports[i]+O_PORTA)<<8) + GETPORT(ports[i]+O_PORTB); ! 951: ! 952: setup[setup_count].irq = IRQ_MIN + conf.cf_irq; ! 953: setup[setup_count].scsiid = conf.cf_id; ! 954: setup[setup_count].reconnect = conf.cf_tardisc; ! 955: setup[setup_count].parity = !conf.cf_parity; ! 956: setup[setup_count].synchronous = 0 /* FIXME: conf.cf_syncneg */; ! 957: setup[setup_count].delay = DELAY_DEFAULT; ! 958: setup[setup_count].ext_trans = 0; ! 959: #ifdef DEBUG_AHA152X ! 960: setup[setup_count].debug = DEBUG_DEFAULT; ! 961: #endif ! 962: setup_count++; ! 963: } ! 964: } ! 965: ! 966: if(ok) ! 967: printk("auto configuration: ok, "); ! 968: } ! 969: #endif ! 970: ! 971: printk("detected %d controller(s)\n", setup_count); ! 972: ! 973: for(i=0; i<setup_count; i++) { ! 974: struct Scsi_Host *shpnt; ! 975: unsigned long int the_time; ! 976: ! 977: shpnt = aha152x_host[setup[i].irq-IRQ_MIN] = ! 978: scsi_register(tpnt, sizeof(struct aha152x_hostdata)); ! 979: ! 980: shpnt->io_port = setup[i].io_port; ! 981: shpnt->n_io_port = IO_RANGE; ! 982: shpnt->irq = setup[i].irq; ! 983: ! 984: ISSUE_SC = (Scsi_Cmnd *) NULL; ! 985: CURRENT_SC = (Scsi_Cmnd *) NULL; ! 986: DISCONNECTED_SC = (Scsi_Cmnd *) NULL; ! 987: ! 988: HOSTDATA(shpnt)->reconnect = setup[i].reconnect; ! 989: HOSTDATA(shpnt)->parity = setup[i].parity; ! 990: HOSTDATA(shpnt)->synchronous = setup[i].synchronous; ! 991: HOSTDATA(shpnt)->delay = setup[i].delay; ! 992: HOSTDATA(shpnt)->ext_trans = setup[i].ext_trans; ! 993: #ifdef DEBUG_AHA152X ! 994: HOSTDATA(shpnt)->debug = setup[i].debug; ! 995: #endif ! 996: ! 997: HOSTDATA(shpnt)->aborting = 0; ! 998: HOSTDATA(shpnt)->abortion_complete = 0; ! 999: HOSTDATA(shpnt)->abort_result = 0; ! 1000: HOSTDATA(shpnt)->commands = 0; ! 1001: ! 1002: HOSTDATA(shpnt)->message_len = 0; ! 1003: ! 1004: for(j=0; j<8; j++) ! 1005: HOSTDATA(shpnt)->syncrate[j] = 0; ! 1006: ! 1007: SETPORT(SCSIID, setup[i].scsiid << 4); ! 1008: shpnt->this_id=setup[i].scsiid; ! 1009: ! 1010: if(setup[i].reconnect) ! 1011: shpnt->can_queue=AHA152X_MAXQUEUE; ! 1012: ! 1013: /* RESET OUT */ ! 1014: SETBITS(SCSISEQ, SCSIRSTO); ! 1015: do_pause(30); ! 1016: CLRBITS(SCSISEQ, SCSIRSTO); ! 1017: do_pause(setup[i].delay); ! 1018: ! 1019: aha152x_reset_ports(shpnt); ! 1020: ! 1021: printk("aha152x%d: vital data: PORTBASE=0x%03x, IRQ=%d, SCSI ID=%d," ! 1022: " reconnect=%s, parity=%s, synchronous=%s, delay=%d, extended translation=%s\n", ! 1023: i, ! 1024: shpnt->io_port, ! 1025: shpnt->irq, ! 1026: shpnt->this_id, ! 1027: HOSTDATA(shpnt)->reconnect ? "enabled" : "disabled", ! 1028: HOSTDATA(shpnt)->parity ? "enabled" : "disabled", ! 1029: HOSTDATA(shpnt)->synchronous ? "enabled" : "disabled", ! 1030: HOSTDATA(shpnt)->delay, ! 1031: HOSTDATA(shpnt)->ext_trans ? "enabled" : "disabled"); ! 1032: ! 1033: request_region(shpnt->io_port, IO_RANGE, "aha152x"); /* Register */ ! 1034: ! 1035: /* not expecting any interrupts */ ! 1036: SETPORT(SIMODE0, 0); ! 1037: SETPORT(SIMODE1, 0); ! 1038: ! 1039: SETBITS(DMACNTRL0, INTEN); ! 1040: ! 1041: ok = request_irq(shpnt->irq, aha152x_swintr, SA_INTERRUPT, "aha152x", NULL); ! 1042: if(ok<0) { ! 1043: if(ok == -EINVAL) ! 1044: printk("aha152x%d: bad IRQ %d.\n", i, shpnt->irq); ! 1045: else if(ok == -EBUSY) ! 1046: printk("aha152x%d: IRQ %d already in use.\n", i, shpnt->irq); ! 1047: else ! 1048: printk("\naha152x%d: Unexpected error code %d on requesting IRQ %d.\n", i, ok, shpnt->irq); ! 1049: printk("aha152x: driver needs an IRQ.\n"); ! 1050: ! 1051: scsi_unregister(shpnt); ! 1052: shpnt=aha152x_host[shpnt->irq-IRQ_MIN]=0; ! 1053: continue; ! 1054: } ! 1055: ! 1056: HOSTDATA(shpnt)->swint=0; ! 1057: ! 1058: printk("aha152x: trying software interrupt, "); ! 1059: SETBITS(DMACNTRL0, SWINT); ! 1060: ! 1061: the_time=jiffies+100; ! 1062: while(!HOSTDATA(shpnt)->swint && jiffies<the_time) ! 1063: barrier(); ! 1064: ! 1065: free_irq(shpnt->irq,0); ! 1066: ! 1067: if(!HOSTDATA(shpnt)->swint) { ! 1068: if(TESTHI(DMASTAT, INTSTAT)) { ! 1069: printk("lost.\n"); ! 1070: } else { ! 1071: printk("failed.\n"); ! 1072: } ! 1073: ! 1074: printk("aha152x: IRQ %d possibly wrong. Please verify.\n", shpnt->irq); ! 1075: ! 1076: scsi_unregister(shpnt); ! 1077: shpnt=aha152x_host[shpnt->irq-IRQ_MIN]=0; ! 1078: continue; ! 1079: } ! 1080: ! 1081: printk("ok.\n"); ! 1082: ! 1083: CLRBITS(DMACNTRL0, SWINT); ! 1084: ! 1085: /* clear interrupts */ ! 1086: SETPORT(SSTAT0, 0x7f); ! 1087: SETPORT(SSTAT1, 0xef); ! 1088: ! 1089: if(request_irq(shpnt->irq,aha152x_intr,SA_INTERRUPT,"aha152x",NULL)<0) { ! 1090: printk("aha152x: failed to reassign interrupt.\n"); ! 1091: } ! 1092: } ! 1093: ! 1094: return (setup_count>0); ! 1095: } ! 1096: ! 1097: /* ! 1098: * Queue a command and setup interrupts for a free bus. ! 1099: */ ! 1100: int aha152x_queue(Scsi_Cmnd * SCpnt, void (*done)(Scsi_Cmnd *)) ! 1101: { ! 1102: struct Scsi_Host *shpnt = SCpnt->host; ! 1103: unsigned long flags; ! 1104: ! 1105: #if defined(DEBUG_RACE) ! 1106: enter_driver("queue"); ! 1107: #else ! 1108: #if defined(DEBUG_QUEUE) ! 1109: if(HOSTDATA(shpnt)->debug & debug_queue) ! 1110: printk("aha152x: queue(), "); ! 1111: #endif ! 1112: #endif ! 1113: ! 1114: #if defined(DEBUG_QUEUE) ! 1115: if(HOSTDATA(shpnt)->debug & debug_queue) { ! 1116: printk("SCpnt (target = %d lun = %d cmnd = ", ! 1117: SCpnt->target, SCpnt->lun); ! 1118: print_command(SCpnt->cmnd); ! 1119: printk(", cmd_len=%d, pieces = %d size = %u), ", ! 1120: SCpnt->cmd_len, SCpnt->use_sg, SCpnt->request_bufflen); ! 1121: disp_ports(shpnt); ! 1122: } ! 1123: #endif ! 1124: ! 1125: SCpnt->scsi_done = done; ! 1126: ! 1127: /* setup scratch area ! 1128: SCp.ptr : buffer pointer ! 1129: SCp.this_residual : buffer length ! 1130: SCp.buffer : next buffer ! 1131: SCp.buffers_residual : left buffers in list ! 1132: SCp.phase : current state of the command */ ! 1133: SCpnt->SCp.phase = not_issued; ! 1134: if (SCpnt->use_sg) { ! 1135: SCpnt->SCp.buffer = (struct scatterlist *) SCpnt->request_buffer; ! 1136: SCpnt->SCp.ptr = SCpnt->SCp.buffer->address; ! 1137: SCpnt->SCp.this_residual = SCpnt->SCp.buffer->length; ! 1138: SCpnt->SCp.buffers_residual = SCpnt->use_sg - 1; ! 1139: } else { ! 1140: SCpnt->SCp.ptr = (char *)SCpnt->request_buffer; ! 1141: SCpnt->SCp.this_residual = SCpnt->request_bufflen; ! 1142: SCpnt->SCp.buffer = NULL; ! 1143: SCpnt->SCp.buffers_residual = 0; ! 1144: } ! 1145: ! 1146: SCpnt->SCp.Status = CHECK_CONDITION; ! 1147: SCpnt->SCp.Message = 0; ! 1148: SCpnt->SCp.have_data_in = 0; ! 1149: SCpnt->SCp.sent_command = 0; ! 1150: ! 1151: /* Turn led on, when this is the first command. */ ! 1152: save_flags(flags); ! 1153: cli(); ! 1154: HOSTDATA(shpnt)->commands++; ! 1155: if(HOSTDATA(shpnt)->commands==1) ! 1156: SETPORT(PORTA, 1); ! 1157: ! 1158: #if defined(DEBUG_QUEUES) ! 1159: if(HOSTDATA(shpnt)->debug & debug_queues) ! 1160: printk("i+ (%d), ", HOSTDATA(shpnt)->commands); ! 1161: #endif ! 1162: append_SC(&ISSUE_SC, SCpnt); ! 1163: ! 1164: /* Enable bus free interrupt, when we aren't currently on the bus */ ! 1165: if(!CURRENT_SC) { ! 1166: SETPORT(SIMODE0, DISCONNECTED_SC ? ENSELDI : 0); ! 1167: SETPORT(SIMODE1, ISSUE_SC ? ENBUSFREE : 0); ! 1168: } ! 1169: restore_flags(flags); ! 1170: ! 1171: #if defined(DEBUG_RACE) ! 1172: leave_driver("queue"); ! 1173: #endif ! 1174: ! 1175: return 0; ! 1176: } ! 1177: ! 1178: /* ! 1179: * We only support commands in interrupt-driven fashion ! 1180: */ ! 1181: int aha152x_command(Scsi_Cmnd *SCpnt) ! 1182: { ! 1183: printk("aha152x: interrupt driven driver; use aha152x_queue()\n"); ! 1184: return -1; ! 1185: } ! 1186: ! 1187: /* ! 1188: * Abort a queued command ! 1189: * (commands that are on the bus can't be aborted easily) ! 1190: */ ! 1191: int aha152x_abort(Scsi_Cmnd *SCpnt) ! 1192: { ! 1193: struct Scsi_Host *shpnt = SCpnt->host; ! 1194: unsigned long flags; ! 1195: Scsi_Cmnd *ptr, *prev; ! 1196: ! 1197: save_flags(flags); ! 1198: cli(); ! 1199: ! 1200: #if defined(DEBUG_ABORT) ! 1201: if(HOSTDATA(shpnt)->debug & debug_abort) { ! 1202: printk("aha152x: abort(), SCpnt=0x%08x, ", (unsigned int) SCpnt); ! 1203: show_queues(shpnt); ! 1204: } ! 1205: #endif ! 1206: ! 1207: /* look for command in issue queue */ ! 1208: for(ptr=ISSUE_SC, prev=NULL; ! 1209: ptr && ptr!=SCpnt; ! 1210: prev=ptr, ptr=(Scsi_Cmnd *) ptr->host_scribble) ! 1211: ; ! 1212: ! 1213: if(ptr) { ! 1214: /* dequeue */ ! 1215: if(prev) ! 1216: prev->host_scribble = ptr->host_scribble; ! 1217: else ! 1218: ISSUE_SC = (Scsi_Cmnd *) ptr->host_scribble; ! 1219: ! 1220: HOSTDATA(shpnt)->commands--; ! 1221: ! 1222: restore_flags(flags); ! 1223: ! 1224: ptr->host_scribble = NULL; ! 1225: ptr->result = DID_ABORT << 16; ! 1226: ptr->scsi_done(ptr); ! 1227: ! 1228: return SCSI_ABORT_SUCCESS; ! 1229: } ! 1230: ! 1231: /* if the bus is busy or a command is currently processed, ! 1232: we can't do anything more */ ! 1233: if (TESTLO(SSTAT1, BUSFREE) || (CURRENT_SC && CURRENT_SC!=SCpnt)) { ! 1234: /* fail abortion, if bus is busy */ ! 1235: ! 1236: if(!CURRENT_SC) ! 1237: printk("bus busy w/o current command, "); ! 1238: ! 1239: restore_flags(flags); ! 1240: ! 1241: return SCSI_ABORT_BUSY; ! 1242: } ! 1243: ! 1244: /* bus is free */ ! 1245: ! 1246: if(CURRENT_SC) { ! 1247: HOSTDATA(shpnt)->commands--; ! 1248: ! 1249: /* target entered bus free before COMMAND COMPLETE, nothing to abort */ ! 1250: restore_flags(flags); ! 1251: CURRENT_SC->result = DID_ERROR << 16; ! 1252: CURRENT_SC->scsi_done(CURRENT_SC); ! 1253: CURRENT_SC = (Scsi_Cmnd *) NULL; ! 1254: ! 1255: return SCSI_ABORT_SUCCESS; ! 1256: } ! 1257: ! 1258: /* look for command in disconnected queue */ ! 1259: for(ptr=DISCONNECTED_SC, prev=NULL; ! 1260: ptr && ptr!=SCpnt; ! 1261: prev=ptr, ptr=(Scsi_Cmnd *) ptr->host_scribble) ! 1262: ; ! 1263: ! 1264: if(!ptr) { ! 1265: /* command wasn't found */ ! 1266: printk("command not found\n"); ! 1267: restore_flags(flags); ! 1268: ! 1269: return SCSI_ABORT_NOT_RUNNING; ! 1270: } ! 1271: ! 1272: if(!HOSTDATA(shpnt)->aborting) { ! 1273: /* dequeue */ ! 1274: if(prev) ! 1275: prev->host_scribble = ptr->host_scribble; ! 1276: else ! 1277: DISCONNECTED_SC = (Scsi_Cmnd *) ptr->host_scribble; ! 1278: ! 1279: HOSTDATA(shpnt)->commands--; ! 1280: ! 1281: /* set command current and initiate selection, ! 1282: let the interrupt routine take care of the abortion */ ! 1283: CURRENT_SC = ptr; ! 1284: ptr->SCp.phase = in_selection|aborted; ! 1285: SETPORT(SCSIID, (shpnt->this_id << OID_) | CURRENT_SC->target); ! 1286: ! 1287: ADDMSG(ABORT); ! 1288: ! 1289: /* enable interrupts for SELECTION OUT DONE and SELECTION TIME OUT */ ! 1290: SETPORT(SIMODE0, ENSELDO | (DISCONNECTED_SC ? ENSELDI : 0)); ! 1291: SETPORT(SIMODE1, ENSELTIMO); ! 1292: ! 1293: /* Enable SELECTION OUT sequence */ ! 1294: SETBITS(SCSISEQ, ENSELO | ENAUTOATNO); ! 1295: ! 1296: SETBITS(DMACNTRL0, INTEN); ! 1297: HOSTDATA(shpnt)->abort_result=SCSI_ABORT_SUCCESS; ! 1298: HOSTDATA(shpnt)->aborting++; ! 1299: HOSTDATA(shpnt)->abortion_complete=0; ! 1300: ! 1301: sti(); /* Hi Eric, guess what ;-) */ ! 1302: ! 1303: /* sleep until the abortion is complete */ ! 1304: while(!HOSTDATA(shpnt)->abortion_complete) ! 1305: barrier(); ! 1306: HOSTDATA(shpnt)->aborting=0; ! 1307: ! 1308: return HOSTDATA(shpnt)->abort_result; ! 1309: } else { ! 1310: /* we're already aborting a command */ ! 1311: restore_flags(flags); ! 1312: ! 1313: return SCSI_ABORT_BUSY; ! 1314: } ! 1315: } ! 1316: ! 1317: /* ! 1318: * Restore default values to the AIC-6260 registers and reset the fifos ! 1319: */ ! 1320: static void aha152x_reset_ports(struct Scsi_Host *shpnt) ! 1321: { ! 1322: /* disable interrupts */ ! 1323: SETPORT(DMACNTRL0, RSTFIFO); ! 1324: ! 1325: SETPORT(SCSISEQ, 0); ! 1326: ! 1327: SETPORT(SXFRCTL1, 0); ! 1328: SETPORT(SCSISIG, 0); ! 1329: SETPORT(SCSIRATE, 0); ! 1330: ! 1331: /* clear all interrupt conditions */ ! 1332: SETPORT(SSTAT0, 0x7f); ! 1333: SETPORT(SSTAT1, 0xef); ! 1334: ! 1335: SETPORT(SSTAT4, SYNCERR|FWERR|FRERR); ! 1336: ! 1337: SETPORT(DMACNTRL0, 0); ! 1338: SETPORT(DMACNTRL1, 0); ! 1339: ! 1340: SETPORT(BRSTCNTRL, 0xf1); ! 1341: ! 1342: /* clear SCSI fifo and transfer count */ ! 1343: SETPORT(SXFRCTL0, CH1|CLRCH1|CLRSTCNT); ! 1344: SETPORT(SXFRCTL0, CH1); ! 1345: ! 1346: /* enable interrupts */ ! 1347: SETPORT(SIMODE0, DISCONNECTED_SC ? ENSELDI : 0); ! 1348: SETPORT(SIMODE1, ISSUE_SC ? ENBUSFREE : 0); ! 1349: } ! 1350: ! 1351: /* ! 1352: * Reset registers, reset a hanging bus and ! 1353: * kill active and disconnected commands for target w/o soft reset ! 1354: */ ! 1355: int aha152x_reset(Scsi_Cmnd *SCpnt, unsigned int unused) ! 1356: { ! 1357: struct Scsi_Host *shpnt = SCpnt->host; ! 1358: unsigned long flags; ! 1359: Scsi_Cmnd *ptr, *prev, *next; ! 1360: ! 1361: aha152x_reset_ports(shpnt); ! 1362: ! 1363: /* Reset, if bus hangs */ ! 1364: if(TESTLO(SSTAT1, BUSFREE)) { ! 1365: CLRBITS(DMACNTRL0, INTEN); ! 1366: ! 1367: #if defined(DEBUG_RESET) ! 1368: if(HOSTDATA(shpnt)->debug & debug_reset) { ! 1369: printk("aha152x: reset(), bus not free: SCSI RESET OUT\n"); ! 1370: show_queues(shpnt); ! 1371: } ! 1372: #endif ! 1373: ! 1374: ptr=CURRENT_SC; ! 1375: if(ptr && !ptr->device->soft_reset) { ! 1376: ptr->host_scribble = NULL; ! 1377: ptr->result = DID_RESET << 16; ! 1378: ptr->scsi_done(CURRENT_SC); ! 1379: CURRENT_SC=NULL; ! 1380: } ! 1381: ! 1382: save_flags(flags); ! 1383: cli(); ! 1384: prev=NULL; ptr=DISCONNECTED_SC; ! 1385: while(ptr) { ! 1386: if(!ptr->device->soft_reset) { ! 1387: if(prev) ! 1388: prev->host_scribble = ptr->host_scribble; ! 1389: else ! 1390: DISCONNECTED_SC = (Scsi_Cmnd *) ptr->host_scribble; ! 1391: ! 1392: next = (Scsi_Cmnd *) ptr->host_scribble; ! 1393: ! 1394: ptr->host_scribble = NULL; ! 1395: ptr->result = DID_RESET << 16; ! 1396: ptr->scsi_done(ptr); ! 1397: ! 1398: ptr = next; ! 1399: } else { ! 1400: prev=ptr; ! 1401: ptr = (Scsi_Cmnd *) ptr->host_scribble; ! 1402: } ! 1403: } ! 1404: restore_flags(flags); ! 1405: ! 1406: #if defined(DEBUG_RESET) ! 1407: if(HOSTDATA(shpnt)->debug & debug_reset) { ! 1408: printk("commands on targets w/ soft-resets:\n"); ! 1409: show_queues(shpnt); ! 1410: } ! 1411: #endif ! 1412: ! 1413: /* RESET OUT */ ! 1414: SETPORT(SCSISEQ, SCSIRSTO); ! 1415: do_pause(30); ! 1416: SETPORT(SCSISEQ, 0); ! 1417: do_pause(DELAY); ! 1418: ! 1419: SETPORT(SIMODE0, DISCONNECTED_SC ? ENSELDI : 0); ! 1420: SETPORT(SIMODE1, ISSUE_SC ? ENBUSFREE : 0); ! 1421: ! 1422: SETPORT(DMACNTRL0, INTEN); ! 1423: } ! 1424: ! 1425: return SCSI_RESET_SUCCESS; ! 1426: } ! 1427: ! 1428: /* ! 1429: * Return the "logical geometry" ! 1430: */ ! 1431: int aha152x_biosparam(Scsi_Disk * disk, kdev_t dev, int *info_array) ! 1432: { ! 1433: struct Scsi_Host *shpnt=disk->device->host; ! 1434: ! 1435: #if defined(DEBUG_BIOSPARAM) ! 1436: if(HOSTDATA(shpnt)->debug & debug_biosparam) ! 1437: printk("aha152x_biosparam: dev=%s, size=%d, ", ! 1438: kdevname(dev), disk->capacity); ! 1439: #endif ! 1440: ! 1441: /* try default translation */ ! 1442: info_array[0]=64; ! 1443: info_array[1]=32; ! 1444: info_array[2]=disk->capacity / (64 * 32); ! 1445: ! 1446: /* for disks >1GB do some guessing */ ! 1447: if(info_array[2]>=1024) { ! 1448: int info[3]; ! 1449: ! 1450: /* try to figure out the geometry from the partition table */ ! 1451: if(scsicam_bios_param(disk, dev, info)<0 || ! 1452: !((info[0]==64 && info[1]==32) || (info[0]==255 && info[1]==63))) { ! 1453: if(EXT_TRANS) { ! 1454: printk("aha152x: unable to verify geometry for disk with >1GB.\n" ! 1455: " using extended translation.\n"); ! 1456: info_array[0] = 255; ! 1457: info_array[1] = 63; ! 1458: info_array[2] = disk->capacity / (255 * 63); ! 1459: } else { ! 1460: printk("aha152x: unable to verify geometry for disk with >1GB.\n" ! 1461: " Using default translation. Please verify yourself.\n" ! 1462: " Perhaps you need to enable extended translation in the driver.\n" ! 1463: " See /usr/src/linux/drivers/scsi/aha152x.c for details.\n"); ! 1464: } ! 1465: } else { ! 1466: info_array[0]=info[0]; ! 1467: info_array[1]=info[1]; ! 1468: info_array[2]=info[2]; ! 1469: ! 1470: if(info[0]==255 && !EXT_TRANS) { ! 1471: printk("aha152x: current partition table is using extended translation.\n" ! 1472: " using it also, although it's not explicty enabled.\n"); ! 1473: } ! 1474: } ! 1475: } ! 1476: ! 1477: #if defined(DEBUG_BIOSPARAM) ! 1478: if(HOSTDATA(shpnt)->debug & debug_biosparam) { ! 1479: printk("bios geometry: head=%d, sec=%d, cyl=%d\n", ! 1480: info_array[0], info_array[1], info_array[2]); ! 1481: printk("WARNING: check, if the bios geometry is correct.\n"); ! 1482: } ! 1483: #endif ! 1484: ! 1485: return 0; ! 1486: } ! 1487: ! 1488: /* ! 1489: * Internal done function ! 1490: */ ! 1491: void aha152x_done(struct Scsi_Host *shpnt, int error) ! 1492: { ! 1493: unsigned long flags; ! 1494: Scsi_Cmnd *done_SC; ! 1495: ! 1496: #if defined(DEBUG_DONE) ! 1497: if(HOSTDATA(shpnt)->debug & debug_done) { ! 1498: printk("\naha152x: done(), "); ! 1499: disp_ports(shpnt); ! 1500: } ! 1501: #endif ! 1502: ! 1503: if(CURRENT_SC) { ! 1504: #if defined(DEBUG_DONE) ! 1505: if(HOSTDATA(shpnt)->debug & debug_done) ! 1506: printk("done(%x), ", error); ! 1507: #endif ! 1508: ! 1509: save_flags(flags); ! 1510: cli(); ! 1511: ! 1512: done_SC = CURRENT_SC; ! 1513: CURRENT_SC = NULL; ! 1514: ! 1515: /* turn led off, when no commands are in the driver */ ! 1516: HOSTDATA(shpnt)->commands--; ! 1517: if(!HOSTDATA(shpnt)->commands) ! 1518: SETPORT(PORTA, 0); /* turn led off */ ! 1519: ! 1520: #if defined(DEBUG_QUEUES) ! 1521: if(HOSTDATA(shpnt)->debug & debug_queues) ! 1522: printk("ok (%d), ", HOSTDATA(shpnt)->commands); ! 1523: #endif ! 1524: restore_flags(flags); ! 1525: ! 1526: SETPORT(SIMODE0, DISCONNECTED_SC ? ENSELDI : 0); ! 1527: SETPORT(SIMODE1, ISSUE_SC ? ENBUSFREE : 0); ! 1528: ! 1529: #if 0 ! 1530: /* Why poll for the BUS FREE phase, when we have setup the interrupt!? */ ! 1531: #if defined(DEBUG_PHASES) ! 1532: if(HOSTDATA(shpnt)->debug & debug_phases) ! 1533: printk("BUS FREE loop, "); ! 1534: #endif ! 1535: while(TESTLO(SSTAT1, BUSFREE)) ! 1536: barrier(); ! 1537: #if defined(DEBUG_PHASES) ! 1538: if(HOSTDATA(shpnt)->debug & debug_phases) ! 1539: printk("BUS FREE\n"); ! 1540: #endif ! 1541: #endif ! 1542: ! 1543: done_SC->result = error; ! 1544: if(done_SC->scsi_done) { ! 1545: #if defined(DEBUG_DONE) ! 1546: if(HOSTDATA(shpnt)->debug & debug_done) ! 1547: printk("calling scsi_done, "); ! 1548: #endif ! 1549: done_SC->scsi_done(done_SC); ! 1550: #if defined(DEBUG_DONE) ! 1551: if(HOSTDATA(shpnt)->debug & debug_done) ! 1552: printk("done returned, "); ! 1553: #endif ! 1554: } else ! 1555: panic("aha152x: current_SC->scsi_done() == NULL"); ! 1556: } else ! 1557: aha152x_panic(shpnt, "done() called outside of command"); ! 1558: } ! 1559: ! 1560: /* ! 1561: * Interrupts handler (main routine of the driver) ! 1562: */ ! 1563: void aha152x_intr(int irqno, void *dev_id, struct pt_regs * regs) ! 1564: { ! 1565: struct Scsi_Host *shpnt = aha152x_host[irqno-IRQ_MIN]; ! 1566: unsigned int flags; ! 1567: int done=0, phase; ! 1568: ! 1569: #if defined(DEBUG_RACE) ! 1570: enter_driver("intr"); ! 1571: #else ! 1572: #if defined(DEBUG_INTR) ! 1573: if(HOSTDATA(shpnt)->debug & debug_intr) ! 1574: printk("\naha152x: intr(), "); ! 1575: #endif ! 1576: #endif ! 1577: ! 1578: if(!shpnt) ! 1579: panic("aha152x: catched interrupt for unknown controller.\n"); ! 1580: ! 1581: /* no more interrupts from the controller, while we're busy. ! 1582: INTEN has to be restored, when we're ready to leave ! 1583: intr(). To avoid race conditions, we have to return ! 1584: immediately afterwards. */ ! 1585: CLRBITS(DMACNTRL0, INTEN); ! 1586: sti(); /* Yes, sti() really needs to be here */ ! 1587: ! 1588: /* disconnected target is trying to reconnect. ! 1589: Only possible, if we have disconnected nexuses and ! 1590: nothing is occupying the bus. ! 1591: */ ! 1592: if(TESTHI(SSTAT0, SELDI) && ! 1593: DISCONNECTED_SC && ! 1594: (!CURRENT_SC || (CURRENT_SC->SCp.phase & in_selection)) ) { ! 1595: int identify_msg, target, i; ! 1596: ! 1597: /* Avoid conflicts when a target reconnects ! 1598: while we are trying to connect to another. */ ! 1599: if(CURRENT_SC) { ! 1600: #if defined(DEBUG_QUEUES) ! 1601: if(HOSTDATA(shpnt)->debug & debug_queues) ! 1602: printk("i+, "); ! 1603: #endif ! 1604: save_flags(flags); ! 1605: cli(); ! 1606: append_SC(&ISSUE_SC, CURRENT_SC); ! 1607: CURRENT_SC=NULL; ! 1608: restore_flags(flags); ! 1609: } ! 1610: ! 1611: /* disable sequences */ ! 1612: SETPORT(SCSISEQ, 0); ! 1613: SETPORT(SSTAT0, CLRSELDI); ! 1614: SETPORT(SSTAT1, CLRBUSFREE); ! 1615: ! 1616: #if defined(DEBUG_QUEUES) || defined(DEBUG_PHASES) ! 1617: if(HOSTDATA(shpnt)->debug & (debug_queues|debug_phases)) ! 1618: printk("reselected, "); ! 1619: #endif ! 1620: ! 1621: i = GETPORT(SELID) & ~(1 << shpnt->this_id); ! 1622: target=0; ! 1623: ! 1624: if(i==0) ! 1625: aha152x_panic(shpnt, "reconnecting target unknown"); ! 1626: ! 1627: for(; (i & 1)==0; target++, i>>=1) ! 1628: ; ! 1629: ! 1630: #if defined(DEBUG_QUEUES) ! 1631: if(HOSTDATA(shpnt)->debug & debug_queues) ! 1632: printk("SELID=%02x, target=%d, ", GETPORT(SELID), target); ! 1633: #endif ! 1634: SETPORT(SCSIID, (shpnt->this_id << OID_) | target); ! 1635: SETPORT(SCSISEQ, ENRESELI); ! 1636: ! 1637: if(TESTLO(SSTAT0, SELDI)) ! 1638: aha152x_panic(shpnt, "RESELI failed"); ! 1639: ! 1640: SETPORT(SCSIRATE, HOSTDATA(shpnt)->syncrate[target]&0x7f); ! 1641: ! 1642: SETPORT(SCSISIG, P_MSGI); ! 1643: ! 1644: /* Get identify message */ ! 1645: if((i=getphase(shpnt))!=P_MSGI) { ! 1646: printk("target doesn't enter MSGI to identify (phase=%02x)\n", i); ! 1647: aha152x_panic(shpnt, "unknown lun"); ! 1648: } ! 1649: SETPORT(SCSISEQ, 0); ! 1650: ! 1651: SETPORT(SXFRCTL0, CH1); ! 1652: ! 1653: identify_msg = GETPORT(SCSIBUS); ! 1654: ! 1655: if(!(identify_msg & IDENTIFY_BASE)) { ! 1656: printk("target=%d, inbound message (%02x) != IDENTIFY\n", ! 1657: target, identify_msg); ! 1658: aha152x_panic(shpnt, "unknown lun"); ! 1659: } ! 1660: ! 1661: ! 1662: #if defined(DEBUG_QUEUES) ! 1663: if(HOSTDATA(shpnt)->debug & debug_queues) ! 1664: printk("identify=%02x, lun=%d, ", identify_msg, identify_msg & 0x3f); ! 1665: #endif ! 1666: ! 1667: save_flags(flags); ! 1668: cli(); ! 1669: ! 1670: #if defined(DEBUG_QUEUES) ! 1671: if(HOSTDATA(shpnt)->debug & debug_queues) ! 1672: printk("d-, "); ! 1673: #endif ! 1674: CURRENT_SC = remove_SC(&DISCONNECTED_SC, target, identify_msg & 0x3f); ! 1675: ! 1676: if(!CURRENT_SC) { ! 1677: printk("lun=%d, ", identify_msg & 0x3f); ! 1678: aha152x_panic(shpnt, "no disconnected command for that lun"); ! 1679: } ! 1680: ! 1681: CURRENT_SC->SCp.phase &= ~disconnected; ! 1682: restore_flags(flags); ! 1683: ! 1684: make_acklow(shpnt); ! 1685: if(getphase(shpnt)!=P_MSGI) { ! 1686: SETPORT(SIMODE0, 0); ! 1687: SETPORT(SIMODE1, ENPHASEMIS|ENBUSFREE); ! 1688: #if defined(DEBUG_RACE) ! 1689: leave_driver("(reselected) intr"); ! 1690: #endif ! 1691: SETBITS(DMACNTRL0, INTEN); ! 1692: return; ! 1693: } ! 1694: } ! 1695: ! 1696: /* Check, if we aren't busy with a command */ ! 1697: if(!CURRENT_SC) { ! 1698: /* bus is free to issue a queued command */ ! 1699: if(TESTHI(SSTAT1, BUSFREE) && ISSUE_SC) { ! 1700: save_flags(flags); ! 1701: cli(); ! 1702: #if defined(DEBUG_QUEUES) ! 1703: if(HOSTDATA(shpnt)->debug & debug_queues) ! 1704: printk("i-, "); ! 1705: #endif ! 1706: CURRENT_SC = remove_first_SC(&ISSUE_SC); ! 1707: restore_flags(flags); ! 1708: ! 1709: #if defined(DEBUG_INTR) || defined(DEBUG_SELECTION) || defined(DEBUG_PHASES) ! 1710: if(HOSTDATA(shpnt)->debug & (debug_intr|debug_selection|debug_phases)) ! 1711: printk("issuing command, "); ! 1712: #endif ! 1713: CURRENT_SC->SCp.phase = in_selection; ! 1714: ! 1715: #if defined(DEBUG_INTR) || defined(DEBUG_SELECTION) || defined(DEBUG_PHASES) ! 1716: if(HOSTDATA(shpnt)->debug & (debug_intr|debug_selection|debug_phases)) ! 1717: printk("selecting %d, ", CURRENT_SC->target); ! 1718: #endif ! 1719: SETPORT(SCSIID, (shpnt->this_id << OID_) | CURRENT_SC->target); ! 1720: ! 1721: /* Enable interrupts for SELECTION OUT DONE and SELECTION OUT INITIATED */ ! 1722: SETPORT(SXFRCTL1, HOSTDATA(shpnt)->parity ? (ENSPCHK|ENSTIMER) : ENSTIMER); ! 1723: ! 1724: /* enable interrupts for SELECTION OUT DONE and SELECTION TIME OUT */ ! 1725: SETPORT(SIMODE0, ENSELDO | (DISCONNECTED_SC ? ENSELDI : 0)); ! 1726: SETPORT(SIMODE1, ENSELTIMO); ! 1727: ! 1728: /* Enable SELECTION OUT sequence */ ! 1729: SETBITS(SCSISEQ, ENSELO | ENAUTOATNO); ! 1730: ! 1731: } else { ! 1732: /* No command we are busy with and no new to issue */ ! 1733: printk("aha152x: ignoring spurious interrupt, nothing to do\n"); ! 1734: if(TESTHI(DMACNTRL0, SWINT)) { ! 1735: printk("aha152x: SWINT is set! Why?\n"); ! 1736: CLRBITS(DMACNTRL0, SWINT); ! 1737: } ! 1738: show_queues(shpnt); ! 1739: } ! 1740: ! 1741: #if defined(DEBUG_RACE) ! 1742: leave_driver("(selecting) intr"); ! 1743: #endif ! 1744: SETBITS(DMACNTRL0, INTEN); ! 1745: return; ! 1746: } ! 1747: ! 1748: /* the bus is busy with something */ ! 1749: ! 1750: #if defined(DEBUG_INTR) ! 1751: if(HOSTDATA(shpnt)->debug & debug_intr) ! 1752: disp_ports(shpnt); ! 1753: #endif ! 1754: ! 1755: /* we are waiting for the result of a selection attempt */ ! 1756: if(CURRENT_SC->SCp.phase & in_selection) { ! 1757: if(TESTLO(SSTAT1, SELTO)) { ! 1758: /* no timeout */ ! 1759: if(TESTHI(SSTAT0, SELDO)) { ! 1760: /* clear BUS FREE interrupt */ ! 1761: SETPORT(SSTAT1, CLRBUSFREE); ! 1762: ! 1763: /* Disable SELECTION OUT sequence */ ! 1764: CLRBITS(SCSISEQ, ENSELO|ENAUTOATNO); ! 1765: ! 1766: /* Disable SELECTION OUT DONE interrupt */ ! 1767: CLRBITS(SIMODE0, ENSELDO); ! 1768: CLRBITS(SIMODE1, ENSELTIMO); ! 1769: ! 1770: if(TESTLO(SSTAT0, SELDO)) { ! 1771: printk("aha152x: passing bus free condition\n"); ! 1772: ! 1773: #if defined(DEBUG_RACE) ! 1774: leave_driver("(passing bus free) intr"); ! 1775: #endif ! 1776: SETBITS(DMACNTRL0, INTEN); ! 1777: ! 1778: if(CURRENT_SC->SCp.phase & aborted) { ! 1779: HOSTDATA(shpnt)->abort_result=SCSI_ABORT_ERROR; ! 1780: HOSTDATA(shpnt)->abortion_complete++; ! 1781: } ! 1782: ! 1783: aha152x_done(shpnt, DID_NO_CONNECT << 16); ! 1784: ! 1785: return; ! 1786: } ! 1787: #if defined(DEBUG_SELECTION) || defined(DEBUG_PHASES) ! 1788: if(HOSTDATA(shpnt)->debug & (debug_selection|debug_phases)) ! 1789: printk("SELDO (SELID=%x), ", GETPORT(SELID)); ! 1790: #endif ! 1791: ! 1792: /* selection was done */ ! 1793: SETPORT(SSTAT0, CLRSELDO); ! 1794: ! 1795: #if defined(DEBUG_ABORT) ! 1796: if((HOSTDATA(shpnt)->debug & debug_abort) && (CURRENT_SC->SCp.phase & aborted)) ! 1797: printk("(ABORT) target selected, "); ! 1798: #endif ! 1799: ! 1800: CURRENT_SC->SCp.phase &= ~in_selection; ! 1801: CURRENT_SC->SCp.phase |= in_other; ! 1802: ! 1803: ADDMSG(IDENTIFY(HOSTDATA(shpnt)->reconnect,CURRENT_SC->lun)); ! 1804: ! 1805: if(!(SYNCRATE&0x80) && HOSTDATA(shpnt)->synchronous) { ! 1806: ADDMSG(EXTENDED_MESSAGE); ! 1807: ADDMSG(3); ! 1808: ADDMSG(EXTENDED_SDTR); ! 1809: ADDMSG(50); ! 1810: ADDMSG(8); ! 1811: ! 1812: printk("outbound SDTR: "); ! 1813: print_msg(&MSG(MSGLEN-5)); ! 1814: ! 1815: SYNCRATE=0x80; ! 1816: CURRENT_SC->SCp.phase |= in_sync; ! 1817: } ! 1818: ! 1819: #if defined(DEBUG_RACE) ! 1820: leave_driver("(SELDO) intr"); ! 1821: #endif ! 1822: SETPORT(SCSIRATE, SYNCRATE&0x7f); ! 1823: ! 1824: SETPORT(SCSISIG, P_MSGO); ! 1825: ! 1826: SETPORT(SIMODE0, 0); ! 1827: SETPORT(SIMODE1, ENREQINIT|ENBUSFREE); ! 1828: SETBITS(DMACNTRL0, INTEN); ! 1829: ! 1830: return; ! 1831: } else ! 1832: aha152x_panic(shpnt, "neither timeout nor selection\007"); ! 1833: } else { ! 1834: #if defined(DEBUG_SELECTION) || defined(DEBUG_PHASES) ! 1835: if(HOSTDATA(shpnt)->debug & (debug_selection|debug_phases)) ! 1836: printk("SELTO, "); ! 1837: #endif ! 1838: /* end selection attempt */ ! 1839: CLRBITS(SCSISEQ, ENSELO|ENAUTOATNO); ! 1840: ! 1841: /* timeout */ ! 1842: SETPORT(SSTAT1, CLRSELTIMO); ! 1843: ! 1844: SETPORT(SIMODE0, DISCONNECTED_SC ? ENSELDI : 0); ! 1845: SETPORT(SIMODE1, ISSUE_SC ? ENBUSFREE : 0); ! 1846: SETBITS(DMACNTRL0, INTEN); ! 1847: #if defined(DEBUG_RACE) ! 1848: leave_driver("(SELTO) intr"); ! 1849: #endif ! 1850: ! 1851: if(CURRENT_SC->SCp.phase & aborted) { ! 1852: #if defined(DEBUG_ABORT) ! 1853: if(HOSTDATA(shpnt)->debug & debug_abort) ! 1854: printk("(ABORT) selection timeout, "); ! 1855: #endif ! 1856: HOSTDATA(shpnt)->abort_result=SCSI_ABORT_ERROR; ! 1857: HOSTDATA(shpnt)->abortion_complete++; ! 1858: } ! 1859: ! 1860: if(TESTLO(SSTAT0, SELINGO)) ! 1861: /* ARBITRATION not won */ ! 1862: aha152x_done(shpnt, DID_BUS_BUSY << 16); ! 1863: else ! 1864: /* ARBITRATION won, but SELECTION failed */ ! 1865: aha152x_done(shpnt, DID_NO_CONNECT << 16); ! 1866: ! 1867: return; ! 1868: } ! 1869: } ! 1870: ! 1871: /* enable interrupt, when target leaves current phase */ ! 1872: phase = getphase(shpnt); ! 1873: if(!(phase & ~P_MASK)) /* "real" phase */ ! 1874: SETPORT(SCSISIG, phase); ! 1875: SETPORT(SSTAT1, CLRPHASECHG); ! 1876: CURRENT_SC->SCp.phase = ! 1877: (CURRENT_SC->SCp.phase & ~((P_MASK|1)<<16)) | (phase << 16); ! 1878: ! 1879: /* information transfer phase */ ! 1880: switch(phase) { ! 1881: case P_MSGO: /* MESSAGE OUT */ ! 1882: { ! 1883: int i, identify=0, abort=0; ! 1884: ! 1885: #if defined(DEBUG_INTR) || defined(DEBUG_MSGO) || defined(DEBUG_PHASES) ! 1886: if(HOSTDATA(shpnt)->debug & (debug_intr|debug_msgo|debug_phases)) ! 1887: printk("MESSAGE OUT, "); ! 1888: #endif ! 1889: if(MSGLEN==0) { ! 1890: ADDMSG(MESSAGE_REJECT); ! 1891: #if defined(DEBUG_MSGO) ! 1892: if(HOSTDATA(shpnt)->debug & debug_msgo) ! 1893: printk("unexpected MESSAGE OUT phase; rejecting, "); ! 1894: #endif ! 1895: } ! 1896: ! 1897: CLRBITS(SXFRCTL0, ENDMA); ! 1898: ! 1899: SETPORT(SIMODE0, 0); ! 1900: SETPORT(SIMODE1, ENPHASEMIS|ENREQINIT|ENBUSFREE); ! 1901: ! 1902: /* wait for data latch to become ready or a phase change */ ! 1903: while(TESTLO(DMASTAT, INTSTAT)) ! 1904: barrier(); ! 1905: ! 1906: #if defined(DEBUG_MSGO) ! 1907: if(HOSTDATA(shpnt)->debug & debug_msgo) { ! 1908: int i; ! 1909: ! 1910: printk("messages ("); ! 1911: for(i=0; i<MSGLEN; i+=print_msg(&MSG(i)), printk(" ")) ! 1912: ; ! 1913: printk("), "); ! 1914: } ! 1915: #endif ! 1916: ! 1917: for(i=0; i<MSGLEN && TESTLO(SSTAT1, PHASEMIS); i++) { ! 1918: #if defined(DEBUG_MSGO) ! 1919: if(HOSTDATA(shpnt)->debug & debug_msgo) ! 1920: printk("%x ", MSG(i)); ! 1921: #endif ! 1922: if(i==MSGLEN-1) { ! 1923: /* Leave MESSAGE OUT after transfer */ ! 1924: SETPORT(SSTAT1, CLRATNO); ! 1925: } ! 1926: ! 1927: SETPORT(SCSIDAT, MSG(i)); ! 1928: ! 1929: make_acklow(shpnt); ! 1930: getphase(shpnt); ! 1931: ! 1932: if(MSG(i)==IDENTIFY(HOSTDATA(shpnt)->reconnect,CURRENT_SC->lun)) ! 1933: identify++; ! 1934: ! 1935: if(MSG(i)==ABORT) ! 1936: abort++; ! 1937: ! 1938: } ! 1939: ! 1940: MSGLEN=0; ! 1941: ! 1942: if(identify) ! 1943: CURRENT_SC->SCp.phase |= sent_ident; ! 1944: ! 1945: if(abort) { ! 1946: /* revive abort(); abort() enables interrupts */ ! 1947: HOSTDATA(shpnt)->abort_result=SCSI_ABORT_SUCCESS; ! 1948: HOSTDATA(shpnt)->abortion_complete++; ! 1949: ! 1950: CURRENT_SC->SCp.phase &= ~(P_MASK<<16); ! 1951: ! 1952: /* exit */ ! 1953: SETBITS(DMACNTRL0, INTEN); ! 1954: #if defined(DEBUG_RACE) ! 1955: leave_driver("(ABORT) intr"); ! 1956: #endif ! 1957: aha152x_done(shpnt, DID_ABORT<<16); ! 1958: ! 1959: return; ! 1960: } ! 1961: } ! 1962: break; ! 1963: ! 1964: case P_CMD: /* COMMAND phase */ ! 1965: #if defined(DEBUG_INTR) || defined(DEBUG_CMD) || defined(DEBUG_PHASES) ! 1966: if(HOSTDATA(shpnt)->debug & (debug_intr|debug_cmd|debug_phases)) ! 1967: printk("COMMAND, "); ! 1968: #endif ! 1969: if(!(CURRENT_SC->SCp.sent_command)) { ! 1970: int i; ! 1971: ! 1972: CLRBITS(SXFRCTL0, ENDMA); ! 1973: ! 1974: SETPORT(SIMODE0, 0); ! 1975: SETPORT(SIMODE1, ENPHASEMIS|ENREQINIT|ENBUSFREE); ! 1976: ! 1977: /* wait for data latch to become ready or a phase change */ ! 1978: while(TESTLO(DMASTAT, INTSTAT)) ! 1979: barrier(); ! 1980: ! 1981: for(i=0; i<CURRENT_SC->cmd_len && TESTLO(SSTAT1, PHASEMIS); i++) { ! 1982: SETPORT(SCSIDAT, CURRENT_SC->cmnd[i]); ! 1983: ! 1984: make_acklow(shpnt); ! 1985: getphase(shpnt); ! 1986: } ! 1987: ! 1988: if(i<CURRENT_SC->cmd_len && TESTHI(SSTAT1, PHASEMIS)) ! 1989: aha152x_panic(shpnt, "target left COMMAND"); ! 1990: ! 1991: CURRENT_SC->SCp.sent_command++; ! 1992: } else ! 1993: aha152x_panic(shpnt, "Nothing to send while in COMMAND"); ! 1994: break; ! 1995: ! 1996: case P_MSGI: /* MESSAGE IN phase */ ! 1997: { ! 1998: int start_sync=0; ! 1999: ! 2000: #if defined(DEBUG_INTR) || defined(DEBUG_MSGI) || defined(DEBUG_PHASES) ! 2001: if(HOSTDATA(shpnt)->debug & (debug_intr|debug_msgi|debug_phases)) ! 2002: printk("MESSAGE IN, "); ! 2003: #endif ! 2004: SETPORT(SXFRCTL0, CH1); ! 2005: ! 2006: SETPORT(SIMODE0, 0); ! 2007: SETPORT(SIMODE1, ENBUSFREE); ! 2008: ! 2009: while(phase == P_MSGI) { ! 2010: CURRENT_SC->SCp.Message = GETPORT(SCSIDAT); ! 2011: switch(CURRENT_SC->SCp.Message) { ! 2012: case DISCONNECT: ! 2013: #if defined(DEBUG_MSGI) || defined(DEBUG_PHASES) ! 2014: if(HOSTDATA(shpnt)->debug & (debug_msgi|debug_phases)) ! 2015: printk("target disconnected, "); ! 2016: #endif ! 2017: CURRENT_SC->SCp.Message = 0; ! 2018: CURRENT_SC->SCp.phase |= disconnected; ! 2019: if(!HOSTDATA(shpnt)->reconnect) ! 2020: aha152x_panic(shpnt, "target was not allowed to disconnect"); ! 2021: ! 2022: break; ! 2023: ! 2024: case COMMAND_COMPLETE: ! 2025: #if defined(DEBUG_MSGI) || defined(DEBUG_PHASES) ! 2026: if(HOSTDATA(shpnt)->debug & (debug_msgi|debug_phases)) ! 2027: printk("inbound message (COMMAND COMPLETE), "); ! 2028: #endif ! 2029: done++; ! 2030: break; ! 2031: ! 2032: case MESSAGE_REJECT: ! 2033: if(CURRENT_SC->SCp.phase & in_sync) { ! 2034: CURRENT_SC->SCp.phase &= ~in_sync; ! 2035: SYNCRATE=0x80; ! 2036: printk("synchronous rejected, "); ! 2037: } else ! 2038: printk("inbound message (MESSAGE REJECT), "); ! 2039: #if defined(DEBUG_MSGI) ! 2040: if(HOSTDATA(shpnt)->debug & debug_msgi) ! 2041: printk("inbound message (MESSAGE REJECT), "); ! 2042: #endif ! 2043: break; ! 2044: ! 2045: case SAVE_POINTERS: ! 2046: #if defined(DEBUG_MSGI) ! 2047: if(HOSTDATA(shpnt)->debug & debug_msgi) ! 2048: printk("inbound message (SAVE DATA POINTERS), "); ! 2049: #endif ! 2050: break; ! 2051: ! 2052: case RESTORE_POINTERS: ! 2053: #if defined(DEBUG_MSGI) ! 2054: if(HOSTDATA(shpnt)->debug & debug_msgi) ! 2055: printk("inbound message (RESTORE DATA POINTERS), "); ! 2056: #endif ! 2057: break; ! 2058: ! 2059: case EXTENDED_MESSAGE: ! 2060: { ! 2061: char buffer[16]; ! 2062: int i; ! 2063: ! 2064: #if defined(DEBUG_MSGI) ! 2065: if(HOSTDATA(shpnt)->debug & debug_msgi) ! 2066: printk("inbound message (EXTENDED MESSAGE), "); ! 2067: #endif ! 2068: make_acklow(shpnt); ! 2069: if(getphase(shpnt)!=P_MSGI) ! 2070: break; ! 2071: ! 2072: buffer[0]=EXTENDED_MESSAGE; ! 2073: buffer[1]=GETPORT(SCSIDAT); ! 2074: ! 2075: for(i=0; i<buffer[1] && ! 2076: (make_acklow(shpnt), getphase(shpnt)==P_MSGI); i++) ! 2077: buffer[2+i]=GETPORT(SCSIDAT); ! 2078: ! 2079: #if defined(DEBUG_MSGI) ! 2080: if(HOSTDATA(shpnt)->debug & debug_msgi) ! 2081: print_msg(buffer); ! 2082: #endif ! 2083: ! 2084: switch(buffer [2]) { ! 2085: case EXTENDED_SDTR: ! 2086: { ! 2087: long ticks; ! 2088: ! 2089: if(buffer[1]!=3) ! 2090: aha152x_panic(shpnt, "SDTR message length != 3"); ! 2091: ! 2092: if(!HOSTDATA(shpnt)->synchronous) ! 2093: break; ! 2094: ! 2095: printk("inbound SDTR: "); print_msg(buffer); ! 2096: ! 2097: ticks=(buffer[3]*4+49)/50; ! 2098: ! 2099: if(CURRENT_SC->SCp.phase & in_sync) { ! 2100: /* we initiated SDTR */ ! 2101: if(ticks>9 || buffer[4]<1 || buffer[4]>8) ! 2102: aha152x_panic(shpnt, "received SDTR invalid"); ! 2103: ! 2104: SYNCRATE |= ((ticks-2)<<4) + buffer[4]; ! 2105: } else if(ticks<=9 && buffer[4]>=1) { ! 2106: if(buffer[4]>8) ! 2107: buffer[4]=8; ! 2108: ! 2109: ADDMSG(EXTENDED_MESSAGE); ! 2110: ADDMSG(3); ! 2111: ADDMSG(EXTENDED_SDTR); ! 2112: if(ticks<4) { ! 2113: ticks=4; ! 2114: ADDMSG(50); ! 2115: } else ! 2116: ADDMSG(buffer[3]); ! 2117: ! 2118: ADDMSG(buffer[4]); ! 2119: ! 2120: printk("outbound SDTR: "); ! 2121: print_msg(&MSG(MSGLEN-5)); ! 2122: ! 2123: CURRENT_SC->SCp.phase |= in_sync; ! 2124: ! 2125: SYNCRATE |= ((ticks-2)<<4) + buffer[4]; ! 2126: ! 2127: start_sync++; ! 2128: } else { ! 2129: /* requested SDTR is too slow, do it asynchronously */ ! 2130: ADDMSG(MESSAGE_REJECT); ! 2131: SYNCRATE = 0; ! 2132: } ! 2133: ! 2134: SETPORT(SCSIRATE, SYNCRATE&0x7f); ! 2135: } ! 2136: break; ! 2137: ! 2138: case EXTENDED_MODIFY_DATA_POINTER: ! 2139: case EXTENDED_EXTENDED_IDENTIFY: ! 2140: case EXTENDED_WDTR: ! 2141: default: ! 2142: ADDMSG(MESSAGE_REJECT); ! 2143: break; ! 2144: } ! 2145: } ! 2146: break; ! 2147: ! 2148: default: ! 2149: printk("unsupported inbound message %x, ", CURRENT_SC->SCp.Message); ! 2150: break; ! 2151: ! 2152: } ! 2153: ! 2154: make_acklow(shpnt); ! 2155: phase=getphase(shpnt); ! 2156: } ! 2157: ! 2158: if(start_sync) ! 2159: CURRENT_SC->SCp.phase |= in_sync; ! 2160: else ! 2161: CURRENT_SC->SCp.phase &= ~in_sync; ! 2162: ! 2163: if(MSGLEN>0) ! 2164: SETPORT(SCSISIG, P_MSGI|ATNO); ! 2165: ! 2166: /* clear SCSI fifo on BUSFREE */ ! 2167: if(phase==P_BUSFREE) ! 2168: SETPORT(SXFRCTL0, CH1|CLRCH1); ! 2169: ! 2170: if(CURRENT_SC->SCp.phase & disconnected) { ! 2171: save_flags(flags); ! 2172: cli(); ! 2173: #if defined(DEBUG_QUEUES) ! 2174: if(HOSTDATA(shpnt)->debug & debug_queues) ! 2175: printk("d+, "); ! 2176: #endif ! 2177: append_SC(&DISCONNECTED_SC, CURRENT_SC); ! 2178: CURRENT_SC->SCp.phase |= 1<<16; ! 2179: CURRENT_SC = NULL; ! 2180: restore_flags(flags); ! 2181: ! 2182: SETBITS(SCSISEQ, ENRESELI); ! 2183: ! 2184: SETPORT(SIMODE0, DISCONNECTED_SC ? ENSELDI : 0); ! 2185: SETPORT(SIMODE1, ISSUE_SC ? ENBUSFREE : 0); ! 2186: ! 2187: SETBITS(DMACNTRL0, INTEN); ! 2188: ! 2189: return; ! 2190: } ! 2191: } ! 2192: break; ! 2193: ! 2194: case P_STATUS: /* STATUS IN phase */ ! 2195: #if defined(DEBUG_STATUS) || defined(DEBUG_INTR) || defined(DEBUG_PHASES) ! 2196: if(HOSTDATA(shpnt)->debug & (debug_status|debug_intr|debug_phases)) ! 2197: printk("STATUS, "); ! 2198: #endif ! 2199: SETPORT(SXFRCTL0, CH1); ! 2200: ! 2201: SETPORT(SIMODE0, 0); ! 2202: SETPORT(SIMODE1, ENREQINIT|ENBUSFREE); ! 2203: ! 2204: if(TESTHI(SSTAT1, PHASEMIS)) ! 2205: printk("aha152x: passing STATUS phase"); ! 2206: ! 2207: CURRENT_SC->SCp.Status = GETPORT(SCSIBUS); ! 2208: make_acklow(shpnt); ! 2209: getphase(shpnt); ! 2210: ! 2211: #if defined(DEBUG_STATUS) ! 2212: if(HOSTDATA(shpnt)->debug & debug_status) { ! 2213: printk("inbound status "); ! 2214: print_status(CURRENT_SC->SCp.Status); ! 2215: printk(", "); ! 2216: } ! 2217: #endif ! 2218: break; ! 2219: ! 2220: case P_DATAI: /* DATA IN phase */ ! 2221: { ! 2222: int fifodata, data_count, done; ! 2223: ! 2224: #if defined(DEBUG_DATAI) || defined(DEBUG_INTR) || defined(DEBUG_PHASES) ! 2225: if(HOSTDATA(shpnt)->debug & (debug_datai|debug_intr|debug_phases)) ! 2226: printk("DATA IN, "); ! 2227: #endif ! 2228: ! 2229: #if 0 ! 2230: if(GETPORT(FIFOSTAT) || GETPORT(SSTAT2) & (SFULL|SFCNT)) ! 2231: printk("aha152x: P_DATAI: %d(%d) bytes left in FIFO, resetting\n", ! 2232: GETPORT(FIFOSTAT), GETPORT(SSTAT2) & (SFULL|SFCNT)); ! 2233: #endif ! 2234: ! 2235: /* reset host fifo */ ! 2236: SETPORT(DMACNTRL0, RSTFIFO); ! 2237: SETPORT(DMACNTRL0, RSTFIFO|ENDMA); ! 2238: ! 2239: SETPORT(SXFRCTL0, CH1|SCSIEN|DMAEN); ! 2240: ! 2241: SETPORT(SIMODE0, 0); ! 2242: SETPORT(SIMODE1, ENPHASEMIS|ENBUSFREE); ! 2243: ! 2244: /* done is set when the FIFO is empty after the target left DATA IN */ ! 2245: done=0; ! 2246: ! 2247: /* while the target stays in DATA to transfer data */ ! 2248: while (!done) { ! 2249: #if defined(DEBUG_DATAI) ! 2250: if(HOSTDATA(shpnt)->debug & debug_datai) ! 2251: printk("expecting data, "); ! 2252: #endif ! 2253: /* wait for PHASEMIS or full FIFO */ ! 2254: while(TESTLO(DMASTAT, DFIFOFULL|INTSTAT)) ! 2255: barrier(); ! 2256: ! 2257: #if defined(DEBUG_DATAI) ! 2258: if(HOSTDATA(shpnt)->debug & debug_datai) ! 2259: printk("ok, "); ! 2260: #endif ! 2261: ! 2262: if(TESTHI(DMASTAT, DFIFOFULL)) ! 2263: fifodata=GETPORT(FIFOSTAT); ! 2264: else { ! 2265: /* wait for SCSI fifo to get empty */ ! 2266: while(TESTLO(SSTAT2, SEMPTY)) ! 2267: barrier(); ! 2268: ! 2269: /* rest of data in FIFO */ ! 2270: fifodata=GETPORT(FIFOSTAT); ! 2271: #if defined(DEBUG_DATAI) ! 2272: if(HOSTDATA(shpnt)->debug & debug_datai) ! 2273: printk("last transfer, "); ! 2274: #endif ! 2275: done=1; ! 2276: } ! 2277: ! 2278: #if defined(DEBUG_DATAI) ! 2279: if(HOSTDATA(shpnt)->debug & debug_datai) ! 2280: printk("fifodata=%d, ", fifodata); ! 2281: #endif ! 2282: ! 2283: while(fifodata && CURRENT_SC->SCp.this_residual) { ! 2284: data_count=fifodata; ! 2285: ! 2286: /* limit data transfer to size of first sg buffer */ ! 2287: if(data_count > CURRENT_SC->SCp.this_residual) ! 2288: data_count = CURRENT_SC->SCp.this_residual; ! 2289: ! 2290: fifodata -= data_count; ! 2291: ! 2292: #if defined(DEBUG_DATAI) ! 2293: if(HOSTDATA(shpnt)->debug & debug_datai) ! 2294: printk("data_count=%d, ", data_count); ! 2295: #endif ! 2296: ! 2297: if(data_count&1) { ! 2298: /* get a single byte in byte mode */ ! 2299: SETBITS(DMACNTRL0, _8BIT); ! 2300: *CURRENT_SC->SCp.ptr++ = GETPORT(DATAPORT); ! 2301: CURRENT_SC->SCp.this_residual--; ! 2302: } ! 2303: ! 2304: if(data_count>1) { ! 2305: CLRBITS(DMACNTRL0, _8BIT); ! 2306: data_count >>= 1; /* Number of words */ ! 2307: insw(DATAPORT, CURRENT_SC->SCp.ptr, data_count); ! 2308: #if defined(DEBUG_DATAI) ! 2309: if(HOSTDATA(shpnt)->debug & debug_datai) ! 2310: /* show what comes with the last transfer */ ! 2311: if(done) { ! 2312: #if 0 ! 2313: int i; ! 2314: unsigned char *data; ! 2315: #endif ! 2316: ! 2317: printk("data on last transfer (%d bytes) ", ! 2318: 2*data_count); ! 2319: #if 0 ! 2320: printk("data on last transfer (%d bytes: ", ! 2321: 2*data_count); ! 2322: data = (unsigned char *) CURRENT_SC->SCp.ptr; ! 2323: for(i=0; i<2*data_count; i++) ! 2324: printk("%2x ", *data++); ! 2325: printk("), "); ! 2326: #endif ! 2327: } ! 2328: #endif ! 2329: CURRENT_SC->SCp.ptr += 2 * data_count; ! 2330: CURRENT_SC->SCp.this_residual -= 2 * data_count; ! 2331: } ! 2332: ! 2333: /* if this buffer is full and there are more buffers left */ ! 2334: if(!CURRENT_SC->SCp.this_residual && ! 2335: CURRENT_SC->SCp.buffers_residual) { ! 2336: /* advance to next buffer */ ! 2337: CURRENT_SC->SCp.buffers_residual--; ! 2338: CURRENT_SC->SCp.buffer++; ! 2339: CURRENT_SC->SCp.ptr = CURRENT_SC->SCp.buffer->address; ! 2340: CURRENT_SC->SCp.this_residual = CURRENT_SC->SCp.buffer->length; ! 2341: } ! 2342: } ! 2343: ! 2344: /* ! 2345: * FIFO should be empty ! 2346: */ ! 2347: if(fifodata>0) { ! 2348: printk("aha152x: more data than expected (%d bytes)\n", ! 2349: GETPORT(FIFOSTAT)); ! 2350: SETBITS(DMACNTRL0, _8BIT); ! 2351: printk("aha152x: data ("); ! 2352: while(fifodata--) ! 2353: printk("%2x ", GETPORT(DATAPORT)); ! 2354: printk(")\n"); ! 2355: } ! 2356: ! 2357: #if defined(DEBUG_DATAI) ! 2358: if(HOSTDATA(shpnt)->debug & debug_datai) ! 2359: if(!fifodata) ! 2360: printk("fifo empty, "); ! 2361: else ! 2362: printk("something left in fifo, "); ! 2363: #endif ! 2364: } ! 2365: ! 2366: #if defined(DEBUG_DATAI) ! 2367: if((HOSTDATA(shpnt)->debug & debug_datai) && ! 2368: (CURRENT_SC->SCp.buffers_residual || ! 2369: CURRENT_SC->SCp.this_residual)) ! 2370: printk("left buffers (buffers=%d, bytes=%d), ", ! 2371: CURRENT_SC->SCp.buffers_residual, CURRENT_SC->SCp.this_residual); ! 2372: #endif ! 2373: /* transfer can be considered ended, when SCSIEN reads back zero */ ! 2374: CLRBITS(SXFRCTL0, SCSIEN|DMAEN); ! 2375: while(TESTHI(SXFRCTL0, SCSIEN)) ! 2376: barrier(); ! 2377: CLRBITS(DMACNTRL0, ENDMA); ! 2378: ! 2379: #if defined(DEBUG_DATAI) || defined(DEBUG_INTR) ! 2380: if(HOSTDATA(shpnt)->debug & (debug_datai|debug_intr)) ! 2381: printk("got %d bytes, ", GETSTCNT()); ! 2382: #endif ! 2383: ! 2384: CURRENT_SC->SCp.have_data_in++; ! 2385: } ! 2386: break; ! 2387: ! 2388: case P_DATAO: /* DATA OUT phase */ ! 2389: { ! 2390: int data_count; ! 2391: ! 2392: #if defined(DEBUG_DATAO) || defined(DEBUG_INTR) || defined(DEBUG_PHASES) ! 2393: if(HOSTDATA(shpnt)->debug & (debug_datao|debug_intr|debug_phases)) ! 2394: printk("DATA OUT, "); ! 2395: #endif ! 2396: #if defined(DEBUG_DATAO) ! 2397: if(HOSTDATA(shpnt)->debug & debug_datao) ! 2398: printk("got data to send (bytes=%d, buffers=%d), ", ! 2399: CURRENT_SC->SCp.this_residual, ! 2400: CURRENT_SC->SCp.buffers_residual); ! 2401: #endif ! 2402: ! 2403: if(GETPORT(FIFOSTAT) || GETPORT(SSTAT2) & (SFULL|SFCNT)) { ! 2404: printk("%d(%d) left in FIFO, ", ! 2405: GETPORT(FIFOSTAT), GETPORT(SSTAT2) & (SFULL|SFCNT)); ! 2406: aha152x_panic(shpnt, "FIFO should be empty"); ! 2407: } ! 2408: ! 2409: SETPORT(SXFRCTL0, CH1|CLRSTCNT|CLRCH1); ! 2410: SETPORT(SXFRCTL0, SCSIEN|DMAEN|CH1); ! 2411: ! 2412: SETPORT(DMACNTRL0, WRITE_READ|RSTFIFO); ! 2413: SETPORT(DMACNTRL0, ENDMA|WRITE_READ); ! 2414: ! 2415: SETPORT(SIMODE0, 0); ! 2416: SETPORT(SIMODE1, ENPHASEMIS|ENBUSFREE); ! 2417: ! 2418: /* while current buffer is not empty or ! 2419: there are more buffers to transfer */ ! 2420: while(TESTLO(SSTAT1, PHASEMIS) && ! 2421: (CURRENT_SC->SCp.this_residual || ! 2422: CURRENT_SC->SCp.buffers_residual)) { ! 2423: #if defined(DEBUG_DATAO) ! 2424: if(HOSTDATA(shpnt)->debug & debug_datao) ! 2425: printk("sending data (left: bytes=%d, buffers=%d), waiting, ", ! 2426: CURRENT_SC->SCp.this_residual, ! 2427: CURRENT_SC->SCp.buffers_residual); ! 2428: #endif ! 2429: /* transfer rest of buffer, but max. 128 byte */ ! 2430: data_count = ! 2431: CURRENT_SC->SCp.this_residual > 128 ? ! 2432: 128 : CURRENT_SC->SCp.this_residual ; ! 2433: ! 2434: #if defined(DEBUG_DATAO) ! 2435: if(HOSTDATA(shpnt)->debug & debug_datao) ! 2436: printk("data_count=%d, ", data_count); ! 2437: #endif ! 2438: ! 2439: if(data_count&1) { ! 2440: /* put a single byte in byte mode */ ! 2441: SETBITS(DMACNTRL0, _8BIT); ! 2442: SETPORT(DATAPORT, *CURRENT_SC->SCp.ptr++); ! 2443: CURRENT_SC->SCp.this_residual--; ! 2444: } ! 2445: if(data_count>1) { ! 2446: CLRBITS(DMACNTRL0, _8BIT); ! 2447: data_count >>= 1; /* number of words */ ! 2448: outsw(DATAPORT, CURRENT_SC->SCp.ptr, data_count); ! 2449: CURRENT_SC->SCp.ptr += 2 * data_count; ! 2450: CURRENT_SC->SCp.this_residual -= 2 * data_count; ! 2451: } ! 2452: ! 2453: /* wait for FIFO to get empty */ ! 2454: while(TESTLO(DMASTAT, DFIFOEMP|INTSTAT)) ! 2455: barrier(); ! 2456: ! 2457: #if defined(DEBUG_DATAO) ! 2458: if(HOSTDATA(shpnt)->debug & debug_datao) ! 2459: printk("fifo (%d bytes), transfered (%d bytes), ", ! 2460: GETPORT(FIFOSTAT), GETSTCNT()); ! 2461: #endif ! 2462: ! 2463: /* if this buffer is empty and there are more buffers left */ ! 2464: if(TESTLO(SSTAT1, PHASEMIS) && ! 2465: !CURRENT_SC->SCp.this_residual && ! 2466: CURRENT_SC->SCp.buffers_residual) { ! 2467: /* advance to next buffer */ ! 2468: CURRENT_SC->SCp.buffers_residual--; ! 2469: CURRENT_SC->SCp.buffer++; ! 2470: CURRENT_SC->SCp.ptr = CURRENT_SC->SCp.buffer->address; ! 2471: CURRENT_SC->SCp.this_residual = CURRENT_SC->SCp.buffer->length; ! 2472: } ! 2473: } ! 2474: ! 2475: if(CURRENT_SC->SCp.this_residual || CURRENT_SC->SCp.buffers_residual) { ! 2476: /* target leaves DATA OUT for an other phase (perhaps disconnect) */ ! 2477: ! 2478: /* data in fifos has to be resend */ ! 2479: data_count = GETPORT(SSTAT2) & (SFULL|SFCNT); ! 2480: ! 2481: data_count += GETPORT(FIFOSTAT) ; ! 2482: CURRENT_SC->SCp.ptr -= data_count; ! 2483: CURRENT_SC->SCp.this_residual += data_count; ! 2484: #if defined(DEBUG_DATAO) ! 2485: if(HOSTDATA(shpnt)->debug & debug_datao) ! 2486: printk("left data (bytes=%d, buffers=%d), fifos (bytes=%d), " ! 2487: "transfer incomplete, resetting fifo, ", ! 2488: CURRENT_SC->SCp.this_residual, ! 2489: CURRENT_SC->SCp.buffers_residual, ! 2490: data_count); ! 2491: #endif ! 2492: SETPORT(DMACNTRL0, WRITE_READ|RSTFIFO); ! 2493: CLRBITS(SXFRCTL0, SCSIEN|DMAEN); ! 2494: CLRBITS(DMACNTRL0, ENDMA); ! 2495: } else { ! 2496: #if defined(DEBUG_DATAO) ! 2497: if(HOSTDATA(shpnt)->debug & debug_datao) ! 2498: printk("waiting for SCSI fifo to get empty, "); ! 2499: #endif ! 2500: /* wait for SCSI fifo to get empty */ ! 2501: while(TESTLO(SSTAT2, SEMPTY)) ! 2502: barrier(); ! 2503: #if defined(DEBUG_DATAO) ! 2504: if(HOSTDATA(shpnt)->debug & debug_datao) ! 2505: printk("ok, left data (bytes=%d, buffers=%d) ", ! 2506: CURRENT_SC->SCp.this_residual, ! 2507: CURRENT_SC->SCp.buffers_residual); ! 2508: #endif ! 2509: CLRBITS(SXFRCTL0, SCSIEN|DMAEN); ! 2510: ! 2511: /* transfer can be considered ended, when SCSIEN reads back zero */ ! 2512: while(TESTHI(SXFRCTL0, SCSIEN)) ! 2513: barrier(); ! 2514: ! 2515: CLRBITS(DMACNTRL0, ENDMA); ! 2516: } ! 2517: ! 2518: #if defined(DEBUG_DATAO) || defined(DEBUG_INTR) ! 2519: if(HOSTDATA(shpnt)->debug & (debug_datao|debug_intr)) ! 2520: printk("sent %d data bytes, ", GETSTCNT()); ! 2521: #endif ! 2522: } ! 2523: break; ! 2524: ! 2525: case P_BUSFREE: /* BUSFREE */ ! 2526: #if defined(DEBUG_RACE) ! 2527: leave_driver("(BUSFREE) intr"); ! 2528: #endif ! 2529: #if defined(DEBUG_PHASES) ! 2530: if(HOSTDATA(shpnt)->debug & debug_phases) ! 2531: printk("unexpected BUS FREE, "); ! 2532: #endif ! 2533: CURRENT_SC->SCp.phase &= ~(P_MASK<<16); ! 2534: ! 2535: aha152x_done(shpnt, DID_ERROR << 16); /* Don't know any better */ ! 2536: return; ! 2537: break; ! 2538: ! 2539: case P_PARITY: /* parity error in DATA phase */ ! 2540: #if defined(DEBUG_RACE) ! 2541: leave_driver("(DID_PARITY) intr"); ! 2542: #endif ! 2543: printk("PARITY error in DATA phase, "); ! 2544: ! 2545: CURRENT_SC->SCp.phase &= ~(P_MASK<<16); ! 2546: ! 2547: SETBITS(DMACNTRL0, INTEN); ! 2548: aha152x_done(shpnt, DID_PARITY << 16); ! 2549: return; ! 2550: break; ! 2551: ! 2552: default: ! 2553: printk("aha152x: unexpected phase\n"); ! 2554: break; ! 2555: } ! 2556: ! 2557: if(done) { ! 2558: #if defined(DEBUG_INTR) ! 2559: if(HOSTDATA(shpnt)->debug & debug_intr) ! 2560: printk("command done.\n"); ! 2561: #endif ! 2562: #if defined(DEBUG_RACE) ! 2563: leave_driver("(done) intr"); ! 2564: #endif ! 2565: ! 2566: SETPORT(SIMODE0, DISCONNECTED_SC ? ENSELDI : 0); ! 2567: SETPORT(SIMODE1, ISSUE_SC ? ENBUSFREE : 0); ! 2568: SETPORT(SCSISEQ, DISCONNECTED_SC ? ENRESELI : 0); ! 2569: ! 2570: SETBITS(DMACNTRL0, INTEN); ! 2571: ! 2572: aha152x_done(shpnt, ! 2573: (CURRENT_SC->SCp.Status & 0xff) ! 2574: | ((CURRENT_SC->SCp.Message & 0xff) << 8) ! 2575: | (DID_OK << 16)); ! 2576: ! 2577: #if defined(DEBUG_RACE) ! 2578: printk("done returned (DID_OK: Status=%x; Message=%x).\n", ! 2579: CURRENT_SC->SCp.Status, CURRENT_SC->SCp.Message); ! 2580: #endif ! 2581: return; ! 2582: } ! 2583: ! 2584: if(CURRENT_SC) ! 2585: CURRENT_SC->SCp.phase |= 1<<16; ! 2586: ! 2587: SETPORT(SIMODE0, 0); ! 2588: SETPORT(SIMODE1, ENPHASEMIS|ENBUSFREE); ! 2589: #if defined(DEBUG_INTR) ! 2590: if(HOSTDATA(shpnt)->debug & debug_intr) ! 2591: disp_enintr(shpnt); ! 2592: #endif ! 2593: #if defined(DEBUG_RACE) ! 2594: leave_driver("(PHASEEND) intr"); ! 2595: #endif ! 2596: ! 2597: SETBITS(DMACNTRL0, INTEN); ! 2598: return; ! 2599: } ! 2600: ! 2601: /* ! 2602: * Dump the current driver status and panic... ! 2603: */ ! 2604: static void aha152x_panic(struct Scsi_Host *shpnt, char *msg) ! 2605: { ! 2606: printk("\naha152x: %s\n", msg); ! 2607: show_queues(shpnt); ! 2608: panic("aha152x panic"); ! 2609: } ! 2610: ! 2611: /* ! 2612: * Display registers of AIC-6260 ! 2613: */ ! 2614: static void disp_ports(struct Scsi_Host *shpnt) ! 2615: { ! 2616: #ifdef DEBUG_AHA152X ! 2617: int s; ! 2618: ! 2619: #ifdef SKIP_PORTS ! 2620: if(HOSTDATA(shpnt)->debug & debug_skipports) ! 2621: return; ! 2622: #endif ! 2623: ! 2624: printk("\n%s: ", CURRENT_SC ? "on bus" : "waiting"); ! 2625: ! 2626: s=GETPORT(SCSISEQ); ! 2627: printk("SCSISEQ ("); ! 2628: if(s & TEMODEO) printk("TARGET MODE "); ! 2629: if(s & ENSELO) printk("SELO "); ! 2630: if(s & ENSELI) printk("SELI "); ! 2631: if(s & ENRESELI) printk("RESELI "); ! 2632: if(s & ENAUTOATNO) printk("AUTOATNO "); ! 2633: if(s & ENAUTOATNI) printk("AUTOATNI "); ! 2634: if(s & ENAUTOATNP) printk("AUTOATNP "); ! 2635: if(s & SCSIRSTO) printk("SCSIRSTO "); ! 2636: printk(");"); ! 2637: ! 2638: printk(" SCSISIG ("); ! 2639: s=GETPORT(SCSISIG); ! 2640: switch(s & P_MASK) { ! 2641: case P_DATAO: ! 2642: printk("DATA OUT"); ! 2643: break; ! 2644: case P_DATAI: ! 2645: printk("DATA IN"); ! 2646: break; ! 2647: case P_CMD: ! 2648: printk("COMMAND"); ! 2649: break; ! 2650: case P_STATUS: ! 2651: printk("STATUS"); ! 2652: break; ! 2653: case P_MSGO: ! 2654: printk("MESSAGE OUT"); ! 2655: break; ! 2656: case P_MSGI: ! 2657: printk("MESSAGE IN"); ! 2658: break; ! 2659: default: ! 2660: printk("*illegal*"); ! 2661: break; ! 2662: } ! 2663: ! 2664: printk("); "); ! 2665: ! 2666: printk("INTSTAT (%s); ", TESTHI(DMASTAT, INTSTAT) ? "hi" : "lo"); ! 2667: ! 2668: printk("SSTAT ("); ! 2669: s=GETPORT(SSTAT0); ! 2670: if(s & TARGET) printk("TARGET "); ! 2671: if(s & SELDO) printk("SELDO "); ! 2672: if(s & SELDI) printk("SELDI "); ! 2673: if(s & SELINGO) printk("SELINGO "); ! 2674: if(s & SWRAP) printk("SWRAP "); ! 2675: if(s & SDONE) printk("SDONE "); ! 2676: if(s & SPIORDY) printk("SPIORDY "); ! 2677: if(s & DMADONE) printk("DMADONE "); ! 2678: ! 2679: s=GETPORT(SSTAT1); ! 2680: if(s & SELTO) printk("SELTO "); ! 2681: if(s & ATNTARG) printk("ATNTARG "); ! 2682: if(s & SCSIRSTI) printk("SCSIRSTI "); ! 2683: if(s & PHASEMIS) printk("PHASEMIS "); ! 2684: if(s & BUSFREE) printk("BUSFREE "); ! 2685: if(s & SCSIPERR) printk("SCSIPERR "); ! 2686: if(s & PHASECHG) printk("PHASECHG "); ! 2687: if(s & REQINIT) printk("REQINIT "); ! 2688: printk("); "); ! 2689: ! 2690: ! 2691: printk("SSTAT ("); ! 2692: ! 2693: s=GETPORT(SSTAT0) & GETPORT(SIMODE0); ! 2694: ! 2695: if(s & TARGET) printk("TARGET "); ! 2696: if(s & SELDO) printk("SELDO "); ! 2697: if(s & SELDI) printk("SELDI "); ! 2698: if(s & SELINGO) printk("SELINGO "); ! 2699: if(s & SWRAP) printk("SWRAP "); ! 2700: if(s & SDONE) printk("SDONE "); ! 2701: if(s & SPIORDY) printk("SPIORDY "); ! 2702: if(s & DMADONE) printk("DMADONE "); ! 2703: ! 2704: s=GETPORT(SSTAT1) & GETPORT(SIMODE1); ! 2705: ! 2706: if(s & SELTO) printk("SELTO "); ! 2707: if(s & ATNTARG) printk("ATNTARG "); ! 2708: if(s & SCSIRSTI) printk("SCSIRSTI "); ! 2709: if(s & PHASEMIS) printk("PHASEMIS "); ! 2710: if(s & BUSFREE) printk("BUSFREE "); ! 2711: if(s & SCSIPERR) printk("SCSIPERR "); ! 2712: if(s & PHASECHG) printk("PHASECHG "); ! 2713: if(s & REQINIT) printk("REQINIT "); ! 2714: printk("); "); ! 2715: ! 2716: printk("SXFRCTL0 ("); ! 2717: ! 2718: s=GETPORT(SXFRCTL0); ! 2719: if(s & SCSIEN) printk("SCSIEN "); ! 2720: if(s & DMAEN) printk("DMAEN "); ! 2721: if(s & CH1) printk("CH1 "); ! 2722: if(s & CLRSTCNT) printk("CLRSTCNT "); ! 2723: if(s & SPIOEN) printk("SPIOEN "); ! 2724: if(s & CLRCH1) printk("CLRCH1 "); ! 2725: printk("); "); ! 2726: ! 2727: printk("SIGNAL ("); ! 2728: ! 2729: s=GETPORT(SCSISIG); ! 2730: if(s & ATNI) printk("ATNI "); ! 2731: if(s & SELI) printk("SELI "); ! 2732: if(s & BSYI) printk("BSYI "); ! 2733: if(s & REQI) printk("REQI "); ! 2734: if(s & ACKI) printk("ACKI "); ! 2735: printk("); "); ! 2736: ! 2737: printk("SELID (%02x), ", GETPORT(SELID)); ! 2738: ! 2739: printk("SSTAT2 ("); ! 2740: ! 2741: s=GETPORT(SSTAT2); ! 2742: if(s & SOFFSET) printk("SOFFSET "); ! 2743: if(s & SEMPTY) printk("SEMPTY "); ! 2744: if(s & SFULL) printk("SFULL "); ! 2745: printk("); SFCNT (%d); ", s & (SFULL|SFCNT)); ! 2746: ! 2747: s=GETPORT(SSTAT3); ! 2748: printk("SCSICNT (%d), OFFCNT(%d), ", (s&0xf0)>>4, s&0x0f); ! 2749: ! 2750: printk("SSTAT4 ("); ! 2751: s=GETPORT(SSTAT4); ! 2752: if(s & SYNCERR) printk("SYNCERR "); ! 2753: if(s & FWERR) printk("FWERR "); ! 2754: if(s & FRERR) printk("FRERR "); ! 2755: printk("); "); ! 2756: ! 2757: printk("DMACNTRL0 ("); ! 2758: s=GETPORT(DMACNTRL0); ! 2759: printk("%s ", s & _8BIT ? "8BIT" : "16BIT"); ! 2760: printk("%s ", s & DMA ? "DMA" : "PIO" ); ! 2761: printk("%s ", s & WRITE_READ ? "WRITE" : "READ" ); ! 2762: if(s & ENDMA) printk("ENDMA "); ! 2763: if(s & INTEN) printk("INTEN "); ! 2764: if(s & RSTFIFO) printk("RSTFIFO "); ! 2765: if(s & SWINT) printk("SWINT "); ! 2766: printk("); "); ! 2767: ! 2768: printk("DMASTAT ("); ! 2769: s=GETPORT(DMASTAT); ! 2770: if(s & ATDONE) printk("ATDONE "); ! 2771: if(s & WORDRDY) printk("WORDRDY "); ! 2772: if(s & DFIFOFULL) printk("DFIFOFULL "); ! 2773: if(s & DFIFOEMP) printk("DFIFOEMP "); ! 2774: printk(")"); ! 2775: ! 2776: printk("\n"); ! 2777: #endif ! 2778: } ! 2779: ! 2780: /* ! 2781: * display enabled interrupts ! 2782: */ ! 2783: static void disp_enintr(struct Scsi_Host *shpnt) ! 2784: { ! 2785: int s; ! 2786: ! 2787: printk("enabled interrupts ("); ! 2788: ! 2789: s=GETPORT(SIMODE0); ! 2790: if(s & ENSELDO) printk("ENSELDO "); ! 2791: if(s & ENSELDI) printk("ENSELDI "); ! 2792: if(s & ENSELINGO) printk("ENSELINGO "); ! 2793: if(s & ENSWRAP) printk("ENSWRAP "); ! 2794: if(s & ENSDONE) printk("ENSDONE "); ! 2795: if(s & ENSPIORDY) printk("ENSPIORDY "); ! 2796: if(s & ENDMADONE) printk("ENDMADONE "); ! 2797: ! 2798: s=GETPORT(SIMODE1); ! 2799: if(s & ENSELTIMO) printk("ENSELTIMO "); ! 2800: if(s & ENATNTARG) printk("ENATNTARG "); ! 2801: if(s & ENPHASEMIS) printk("ENPHASEMIS "); ! 2802: if(s & ENBUSFREE) printk("ENBUSFREE "); ! 2803: if(s & ENSCSIPERR) printk("ENSCSIPERR "); ! 2804: if(s & ENPHASECHG) printk("ENPHASECHG "); ! 2805: if(s & ENREQINIT) printk("ENREQINIT "); ! 2806: printk(")\n"); ! 2807: } ! 2808: ! 2809: #if defined(DEBUG_RACE) ! 2810: ! 2811: static const char *should_leave; ! 2812: static int in_driver=0; ! 2813: ! 2814: /* ! 2815: * Only one routine can be in the driver at once. ! 2816: */ ! 2817: static void enter_driver(const char *func) ! 2818: { ! 2819: unsigned long flags; ! 2820: ! 2821: save_flags(flags); ! 2822: cli(); ! 2823: printk("aha152x: entering %s() (%x)\n", func, jiffies); ! 2824: if(in_driver) { ! 2825: printk("%s should leave first.\n", should_leave); ! 2826: panic("aha152x: already in driver\n"); ! 2827: } ! 2828: ! 2829: in_driver++; ! 2830: should_leave=func; ! 2831: restore_flags(flags); ! 2832: } ! 2833: ! 2834: static void leave_driver(const char *func) ! 2835: { ! 2836: unsigned long flags; ! 2837: ! 2838: save_flags(flags); ! 2839: cli(); ! 2840: printk("\naha152x: leaving %s() (%x)\n", func, jiffies); ! 2841: if(!in_driver) { ! 2842: printk("aha152x: %s already left.\n", should_leave); ! 2843: panic("aha152x: %s already left driver.\n"); ! 2844: } ! 2845: ! 2846: in_driver--; ! 2847: should_leave=func; ! 2848: restore_flags(flags); ! 2849: } ! 2850: #endif ! 2851: ! 2852: /* ! 2853: * Show the command data of a command ! 2854: */ ! 2855: static void show_command(Scsi_Cmnd *ptr) ! 2856: { ! 2857: printk("0x%08x: target=%d; lun=%d; cmnd=(", ! 2858: (unsigned int) ptr, ptr->target, ptr->lun); ! 2859: ! 2860: print_command(ptr->cmnd); ! 2861: ! 2862: printk("); residual=%d; buffers=%d; phase |", ! 2863: ptr->SCp.this_residual, ptr->SCp.buffers_residual); ! 2864: ! 2865: if(ptr->SCp.phase & not_issued ) printk("not issued|"); ! 2866: if(ptr->SCp.phase & in_selection) printk("in selection|"); ! 2867: if(ptr->SCp.phase & disconnected) printk("disconnected|"); ! 2868: if(ptr->SCp.phase & aborted ) printk("aborted|"); ! 2869: if(ptr->SCp.phase & sent_ident ) printk("send_ident|"); ! 2870: if(ptr->SCp.phase & in_other) { ! 2871: printk("; in other("); ! 2872: switch((ptr->SCp.phase >> 16) & P_MASK) { ! 2873: case P_DATAO: ! 2874: printk("DATA OUT"); ! 2875: break; ! 2876: case P_DATAI: ! 2877: printk("DATA IN"); ! 2878: break; ! 2879: case P_CMD: ! 2880: printk("COMMAND"); ! 2881: break; ! 2882: case P_STATUS: ! 2883: printk("STATUS"); ! 2884: break; ! 2885: case P_MSGO: ! 2886: printk("MESSAGE OUT"); ! 2887: break; ! 2888: case P_MSGI: ! 2889: printk("MESSAGE IN"); ! 2890: break; ! 2891: default: ! 2892: printk("*illegal*"); ! 2893: break; ! 2894: } ! 2895: printk(")"); ! 2896: if(ptr->SCp.phase & (1<<16)) ! 2897: printk("; phaseend"); ! 2898: } ! 2899: printk("; next=0x%08x\n", (unsigned int) ptr->host_scribble); ! 2900: } ! 2901: ! 2902: /* ! 2903: * Dump the queued data ! 2904: */ ! 2905: static void show_queues(struct Scsi_Host *shpnt) ! 2906: { ! 2907: unsigned long flags; ! 2908: Scsi_Cmnd *ptr; ! 2909: ! 2910: save_flags(flags); ! 2911: cli(); ! 2912: printk("QUEUE STATUS:\nissue_SC:\n"); ! 2913: for(ptr=ISSUE_SC; ptr; ptr = (Scsi_Cmnd *) ptr->host_scribble) ! 2914: show_command(ptr); ! 2915: ! 2916: printk("current_SC:\n"); ! 2917: if(CURRENT_SC) ! 2918: show_command(CURRENT_SC); ! 2919: else ! 2920: printk("none\n"); ! 2921: ! 2922: printk("disconnected_SC:\n"); ! 2923: for(ptr=DISCONNECTED_SC; ptr; ptr = (Scsi_Cmnd *) ptr->host_scribble) ! 2924: show_command(ptr); ! 2925: ! 2926: disp_ports(shpnt); ! 2927: disp_enintr(shpnt); ! 2928: restore_flags(flags); ! 2929: } ! 2930: ! 2931: int aha152x_set_info(char *buffer, int length, struct Scsi_Host *shpnt) ! 2932: { ! 2933: return(-ENOSYS); /* Currently this is a no-op */ ! 2934: } ! 2935: ! 2936: #undef SPRINTF ! 2937: #define SPRINTF(args...) pos += sprintf(pos, ## args) ! 2938: ! 2939: static int get_command(char *pos, Scsi_Cmnd *ptr) ! 2940: { ! 2941: char *start = pos; ! 2942: int i; ! 2943: ! 2944: SPRINTF("0x%08x: target=%d; lun=%d; cmnd=( ", ! 2945: (unsigned int) ptr, ptr->target, ptr->lun); ! 2946: ! 2947: for(i=0; i<COMMAND_SIZE(ptr->cmnd[0]); i++) ! 2948: SPRINTF("0x%02x ", ptr->cmnd[i]); ! 2949: ! 2950: SPRINTF("); residual=%d; buffers=%d; phase |", ! 2951: ptr->SCp.this_residual, ptr->SCp.buffers_residual); ! 2952: ! 2953: if(ptr->SCp.phase & not_issued ) SPRINTF("not issued|"); ! 2954: if(ptr->SCp.phase & in_selection) SPRINTF("in selection|"); ! 2955: if(ptr->SCp.phase & disconnected) SPRINTF("disconnected|"); ! 2956: if(ptr->SCp.phase & aborted ) SPRINTF("aborted|"); ! 2957: if(ptr->SCp.phase & sent_ident ) SPRINTF("send_ident|"); ! 2958: if(ptr->SCp.phase & in_other) { ! 2959: SPRINTF("; in other("); ! 2960: switch((ptr->SCp.phase >> 16) & P_MASK) { ! 2961: case P_DATAO: ! 2962: SPRINTF("DATA OUT"); ! 2963: break; ! 2964: case P_DATAI: ! 2965: SPRINTF("DATA IN"); ! 2966: break; ! 2967: case P_CMD: ! 2968: SPRINTF("COMMAND"); ! 2969: break; ! 2970: case P_STATUS: ! 2971: SPRINTF("STATUS"); ! 2972: break; ! 2973: case P_MSGO: ! 2974: SPRINTF("MESSAGE OUT"); ! 2975: break; ! 2976: case P_MSGI: ! 2977: SPRINTF("MESSAGE IN"); ! 2978: break; ! 2979: default: ! 2980: SPRINTF("*illegal*"); ! 2981: break; ! 2982: } ! 2983: SPRINTF(")"); ! 2984: if(ptr->SCp.phase & (1<<16)) ! 2985: SPRINTF("; phaseend"); ! 2986: } ! 2987: SPRINTF("; next=0x%08x\n", (unsigned int) ptr->host_scribble); ! 2988: ! 2989: return(pos-start); ! 2990: } ! 2991: ! 2992: static int get_ports(struct Scsi_Host *shpnt, char *pos) ! 2993: { ! 2994: char *start = pos; ! 2995: int s; ! 2996: ! 2997: #ifdef SKIP_PORTS ! 2998: if(HOSTDATA(shpnt)->debug & debug_skipports) ! 2999: return; ! 3000: #endif ! 3001: ! 3002: SPRINTF("\n%s: ", CURRENT_SC ? "on bus" : "waiting"); ! 3003: ! 3004: s=GETPORT(SCSISEQ); ! 3005: SPRINTF("SCSISEQ ("); ! 3006: if(s & TEMODEO) SPRINTF("TARGET MODE "); ! 3007: if(s & ENSELO) SPRINTF("SELO "); ! 3008: if(s & ENSELI) SPRINTF("SELI "); ! 3009: if(s & ENRESELI) SPRINTF("RESELI "); ! 3010: if(s & ENAUTOATNO) SPRINTF("AUTOATNO "); ! 3011: if(s & ENAUTOATNI) SPRINTF("AUTOATNI "); ! 3012: if(s & ENAUTOATNP) SPRINTF("AUTOATNP "); ! 3013: if(s & SCSIRSTO) SPRINTF("SCSIRSTO "); ! 3014: SPRINTF(");"); ! 3015: ! 3016: SPRINTF(" SCSISIG ("); ! 3017: s=GETPORT(SCSISIG); ! 3018: switch(s & P_MASK) { ! 3019: case P_DATAO: ! 3020: SPRINTF("DATA OUT"); ! 3021: break; ! 3022: case P_DATAI: ! 3023: SPRINTF("DATA IN"); ! 3024: break; ! 3025: case P_CMD: ! 3026: SPRINTF("COMMAND"); ! 3027: break; ! 3028: case P_STATUS: ! 3029: SPRINTF("STATUS"); ! 3030: break; ! 3031: case P_MSGO: ! 3032: SPRINTF("MESSAGE OUT"); ! 3033: break; ! 3034: case P_MSGI: ! 3035: SPRINTF("MESSAGE IN"); ! 3036: break; ! 3037: default: ! 3038: SPRINTF("*illegal*"); ! 3039: break; ! 3040: } ! 3041: ! 3042: SPRINTF("); "); ! 3043: ! 3044: SPRINTF("INTSTAT (%s); ", TESTHI(DMASTAT, INTSTAT) ? "hi" : "lo"); ! 3045: ! 3046: SPRINTF("SSTAT ("); ! 3047: s=GETPORT(SSTAT0); ! 3048: if(s & TARGET) SPRINTF("TARGET "); ! 3049: if(s & SELDO) SPRINTF("SELDO "); ! 3050: if(s & SELDI) SPRINTF("SELDI "); ! 3051: if(s & SELINGO) SPRINTF("SELINGO "); ! 3052: if(s & SWRAP) SPRINTF("SWRAP "); ! 3053: if(s & SDONE) SPRINTF("SDONE "); ! 3054: if(s & SPIORDY) SPRINTF("SPIORDY "); ! 3055: if(s & DMADONE) SPRINTF("DMADONE "); ! 3056: ! 3057: s=GETPORT(SSTAT1); ! 3058: if(s & SELTO) SPRINTF("SELTO "); ! 3059: if(s & ATNTARG) SPRINTF("ATNTARG "); ! 3060: if(s & SCSIRSTI) SPRINTF("SCSIRSTI "); ! 3061: if(s & PHASEMIS) SPRINTF("PHASEMIS "); ! 3062: if(s & BUSFREE) SPRINTF("BUSFREE "); ! 3063: if(s & SCSIPERR) SPRINTF("SCSIPERR "); ! 3064: if(s & PHASECHG) SPRINTF("PHASECHG "); ! 3065: if(s & REQINIT) SPRINTF("REQINIT "); ! 3066: SPRINTF("); "); ! 3067: ! 3068: ! 3069: SPRINTF("SSTAT ("); ! 3070: ! 3071: s=GETPORT(SSTAT0) & GETPORT(SIMODE0); ! 3072: ! 3073: if(s & TARGET) SPRINTF("TARGET "); ! 3074: if(s & SELDO) SPRINTF("SELDO "); ! 3075: if(s & SELDI) SPRINTF("SELDI "); ! 3076: if(s & SELINGO) SPRINTF("SELINGO "); ! 3077: if(s & SWRAP) SPRINTF("SWRAP "); ! 3078: if(s & SDONE) SPRINTF("SDONE "); ! 3079: if(s & SPIORDY) SPRINTF("SPIORDY "); ! 3080: if(s & DMADONE) SPRINTF("DMADONE "); ! 3081: ! 3082: s=GETPORT(SSTAT1) & GETPORT(SIMODE1); ! 3083: ! 3084: if(s & SELTO) SPRINTF("SELTO "); ! 3085: if(s & ATNTARG) SPRINTF("ATNTARG "); ! 3086: if(s & SCSIRSTI) SPRINTF("SCSIRSTI "); ! 3087: if(s & PHASEMIS) SPRINTF("PHASEMIS "); ! 3088: if(s & BUSFREE) SPRINTF("BUSFREE "); ! 3089: if(s & SCSIPERR) SPRINTF("SCSIPERR "); ! 3090: if(s & PHASECHG) SPRINTF("PHASECHG "); ! 3091: if(s & REQINIT) SPRINTF("REQINIT "); ! 3092: SPRINTF("); "); ! 3093: ! 3094: SPRINTF("SXFRCTL0 ("); ! 3095: ! 3096: s=GETPORT(SXFRCTL0); ! 3097: if(s & SCSIEN) SPRINTF("SCSIEN "); ! 3098: if(s & DMAEN) SPRINTF("DMAEN "); ! 3099: if(s & CH1) SPRINTF("CH1 "); ! 3100: if(s & CLRSTCNT) SPRINTF("CLRSTCNT "); ! 3101: if(s & SPIOEN) SPRINTF("SPIOEN "); ! 3102: if(s & CLRCH1) SPRINTF("CLRCH1 "); ! 3103: SPRINTF("); "); ! 3104: ! 3105: SPRINTF("SIGNAL ("); ! 3106: ! 3107: s=GETPORT(SCSISIG); ! 3108: if(s & ATNI) SPRINTF("ATNI "); ! 3109: if(s & SELI) SPRINTF("SELI "); ! 3110: if(s & BSYI) SPRINTF("BSYI "); ! 3111: if(s & REQI) SPRINTF("REQI "); ! 3112: if(s & ACKI) SPRINTF("ACKI "); ! 3113: SPRINTF("); "); ! 3114: ! 3115: SPRINTF("SELID (%02x), ", GETPORT(SELID)); ! 3116: ! 3117: SPRINTF("SSTAT2 ("); ! 3118: ! 3119: s=GETPORT(SSTAT2); ! 3120: if(s & SOFFSET) SPRINTF("SOFFSET "); ! 3121: if(s & SEMPTY) SPRINTF("SEMPTY "); ! 3122: if(s & SFULL) SPRINTF("SFULL "); ! 3123: SPRINTF("); SFCNT (%d); ", s & (SFULL|SFCNT)); ! 3124: ! 3125: s=GETPORT(SSTAT3); ! 3126: SPRINTF("SCSICNT (%d), OFFCNT(%d), ", (s&0xf0)>>4, s&0x0f); ! 3127: ! 3128: SPRINTF("SSTAT4 ("); ! 3129: s=GETPORT(SSTAT4); ! 3130: if(s & SYNCERR) SPRINTF("SYNCERR "); ! 3131: if(s & FWERR) SPRINTF("FWERR "); ! 3132: if(s & FRERR) SPRINTF("FRERR "); ! 3133: SPRINTF("); "); ! 3134: ! 3135: SPRINTF("DMACNTRL0 ("); ! 3136: s=GETPORT(DMACNTRL0); ! 3137: SPRINTF("%s ", s & _8BIT ? "8BIT" : "16BIT"); ! 3138: SPRINTF("%s ", s & DMA ? "DMA" : "PIO" ); ! 3139: SPRINTF("%s ", s & WRITE_READ ? "WRITE" : "READ" ); ! 3140: if(s & ENDMA) SPRINTF("ENDMA "); ! 3141: if(s & INTEN) SPRINTF("INTEN "); ! 3142: if(s & RSTFIFO) SPRINTF("RSTFIFO "); ! 3143: if(s & SWINT) SPRINTF("SWINT "); ! 3144: SPRINTF("); "); ! 3145: ! 3146: SPRINTF("DMASTAT ("); ! 3147: s=GETPORT(DMASTAT); ! 3148: if(s & ATDONE) SPRINTF("ATDONE "); ! 3149: if(s & WORDRDY) SPRINTF("WORDRDY "); ! 3150: if(s & DFIFOFULL) SPRINTF("DFIFOFULL "); ! 3151: if(s & DFIFOEMP) SPRINTF("DFIFOEMP "); ! 3152: SPRINTF(")\n\n"); ! 3153: ! 3154: SPRINTF("enabled interrupts ("); ! 3155: ! 3156: s=GETPORT(SIMODE0); ! 3157: if(s & ENSELDO) SPRINTF("ENSELDO "); ! 3158: if(s & ENSELDI) SPRINTF("ENSELDI "); ! 3159: if(s & ENSELINGO) SPRINTF("ENSELINGO "); ! 3160: if(s & ENSWRAP) SPRINTF("ENSWRAP "); ! 3161: if(s & ENSDONE) SPRINTF("ENSDONE "); ! 3162: if(s & ENSPIORDY) SPRINTF("ENSPIORDY "); ! 3163: if(s & ENDMADONE) SPRINTF("ENDMADONE "); ! 3164: ! 3165: s=GETPORT(SIMODE1); ! 3166: if(s & ENSELTIMO) SPRINTF("ENSELTIMO "); ! 3167: if(s & ENATNTARG) SPRINTF("ENATNTARG "); ! 3168: if(s & ENPHASEMIS) SPRINTF("ENPHASEMIS "); ! 3169: if(s & ENBUSFREE) SPRINTF("ENBUSFREE "); ! 3170: if(s & ENSCSIPERR) SPRINTF("ENSCSIPERR "); ! 3171: if(s & ENPHASECHG) SPRINTF("ENPHASECHG "); ! 3172: if(s & ENREQINIT) SPRINTF("ENREQINIT "); ! 3173: SPRINTF(")\n"); ! 3174: ! 3175: return (pos-start); ! 3176: } ! 3177: ! 3178: #undef SPRINTF ! 3179: #define SPRINTF(args...) do { if(pos < buffer + length) pos += sprintf(pos, ## args); } while(0) ! 3180: ! 3181: int aha152x_proc_info(char *buffer, char **start, ! 3182: off_t offset, int length, int hostno, int inout) ! 3183: { ! 3184: int i; ! 3185: char *pos = buffer; ! 3186: struct Scsi_Host *shpnt; ! 3187: unsigned long flags; ! 3188: Scsi_Cmnd *ptr; ! 3189: ! 3190: for(i=0, shpnt= (struct Scsi_Host *) NULL; i<IRQS; i++) ! 3191: if(aha152x_host[i] && aha152x_host[i]->host_no == hostno) ! 3192: shpnt=aha152x_host[i]; ! 3193: ! 3194: if(!shpnt) ! 3195: return(-ESRCH); ! 3196: ! 3197: if(inout) /* Has data been written to the file ? */ ! 3198: return(aha152x_set_info(buffer, length, shpnt)); ! 3199: ! 3200: SPRINTF(AHA152X_REVID "\n"); ! 3201: ! 3202: save_flags(flags); ! 3203: cli(); ! 3204: ! 3205: SPRINTF("ioports 0x%04x to 0x%04x\n", ! 3206: shpnt->io_port, shpnt->io_port+shpnt->n_io_port-1); ! 3207: SPRINTF("interrupt 0x%02x\n", shpnt->irq); ! 3208: SPRINTF("disconnection/reconnection %s\n", ! 3209: HOSTDATA(shpnt)->reconnect ? "enabled" : "disabled"); ! 3210: SPRINTF("parity checking %s\n", ! 3211: HOSTDATA(shpnt)->parity ? "enabled" : "disabled"); ! 3212: SPRINTF("synchronous transfers %s\n", ! 3213: HOSTDATA(shpnt)->synchronous ? "enabled" : "disabled"); ! 3214: SPRINTF("%d commands currently queued\n", HOSTDATA(shpnt)->commands); ! 3215: ! 3216: if(HOSTDATA(shpnt)->synchronous) { ! 3217: #if 0 ! 3218: SPRINTF("synchronously operating targets (tick=%ld ns):\n", ! 3219: 250000000/loops_per_sec); ! 3220: for(i=0; i<8; i++) ! 3221: if(HOSTDATA(shpnt)->syncrate[i]&0x7f) ! 3222: SPRINTF("target %d: period %dT/%ldns; req/ack offset %d\n", ! 3223: i, ! 3224: (((HOSTDATA(shpnt)->syncrate[i]&0x70)>>4)+2), ! 3225: (((HOSTDATA(shpnt)->syncrate[i]&0x70)>>4)+2)* ! 3226: 250000000/loops_per_sec, ! 3227: HOSTDATA(shpnt)->syncrate[i]&0x0f); ! 3228: #else ! 3229: SPRINTF("synchronously operating targets (tick=50 ns):\n"); ! 3230: for(i=0; i<8; i++) ! 3231: if(HOSTDATA(shpnt)->syncrate[i]&0x7f) ! 3232: SPRINTF("target %d: period %dT/%dns; req/ack offset %d\n", ! 3233: i, ! 3234: (((HOSTDATA(shpnt)->syncrate[i]&0x70)>>4)+2), ! 3235: (((HOSTDATA(shpnt)->syncrate[i]&0x70)>>4)+2)*50, ! 3236: HOSTDATA(shpnt)->syncrate[i]&0x0f); ! 3237: #endif ! 3238: } ! 3239: ! 3240: #ifdef DEBUG_AHA152X ! 3241: #define PDEBUG(flags,txt) if(HOSTDATA(shpnt)->debug & flags) SPRINTF("(%s) ", txt); ! 3242: ! 3243: SPRINTF("enabled debugging options: "); ! 3244: ! 3245: PDEBUG(debug_skipports, "skip ports"); ! 3246: PDEBUG(debug_queue, "queue"); ! 3247: PDEBUG(debug_intr, "interrupt"); ! 3248: PDEBUG(debug_selection, "selection"); ! 3249: PDEBUG(debug_msgo, "message out"); ! 3250: PDEBUG(debug_msgi, "message in"); ! 3251: PDEBUG(debug_status, "status"); ! 3252: PDEBUG(debug_cmd, "command"); ! 3253: PDEBUG(debug_datai, "data in"); ! 3254: PDEBUG(debug_datao, "data out"); ! 3255: PDEBUG(debug_abort, "abort"); ! 3256: PDEBUG(debug_done, "done"); ! 3257: PDEBUG(debug_biosparam, "bios parameters"); ! 3258: PDEBUG(debug_phases, "phases"); ! 3259: PDEBUG(debug_queues, "queues"); ! 3260: PDEBUG(debug_reset, "reset"); ! 3261: ! 3262: SPRINTF("\n"); ! 3263: #endif ! 3264: ! 3265: SPRINTF("\nqueue status:\n"); ! 3266: if(ISSUE_SC) { ! 3267: SPRINTF("not yet issued commands:\n"); ! 3268: for(ptr=ISSUE_SC; ptr; ptr = (Scsi_Cmnd *) ptr->host_scribble) ! 3269: pos += get_command(pos, ptr); ! 3270: } else ! 3271: SPRINTF("no not yet issued commands\n"); ! 3272: ! 3273: if(CURRENT_SC) { ! 3274: SPRINTF("current command:\n"); ! 3275: pos += get_command(pos, CURRENT_SC); ! 3276: } else ! 3277: SPRINTF("no current command\n"); ! 3278: ! 3279: if(DISCONNECTED_SC) { ! 3280: SPRINTF("disconnected commands:\n"); ! 3281: for(ptr=DISCONNECTED_SC; ptr; ptr = (Scsi_Cmnd *) ptr->host_scribble) ! 3282: pos += get_command(pos, ptr); ! 3283: } else ! 3284: SPRINTF("no disconnected commands\n"); ! 3285: ! 3286: restore_flags(flags); ! 3287: ! 3288: pos += get_ports(shpnt, pos); ! 3289: ! 3290: *start=buffer+offset; ! 3291: if (pos - buffer < offset) ! 3292: return 0; ! 3293: else if (pos - buffer - offset < length) ! 3294: return pos - buffer - offset; ! 3295: else ! 3296: return length; ! 3297: } ! 3298: ! 3299: #ifdef MODULE ! 3300: /* Eventually this will go into an include file, but this will be later */ ! 3301: Scsi_Host_Template driver_template = AHA152X; ! 3302: ! 3303: #include "scsi_module.c" ! 3304: #endif
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.