root/drivers/scsi/aha1542.c

/* [previous][next][first][last][top][bottom][index][help] */

DEFINITIONS

This source file includes following definitions.
  1. aha1542_stat
  2. aha1542_out
  3. aha1542_in
  4. aha1542_in1
  5. makecode
  6. aha1542_test_port
  7. aha1542_intr_handle
  8. aha1542_queuecommand
  9. internal_done
  10. aha1542_command
  11. setup_mailboxes
  12. aha1542_getconfig
  13. aha1542_mbenable
  14. aha1542_query
  15. aha1542_setup
  16. aha1542_detect
  17. aha1542_restart
  18. aha1542_abort
  19. aha1542_reset
  20. aha1542_biosparam

   1 /* $Id: aha1542.c,v 1.1 1992/07/24 06:27:38 root Exp root $
   2  *  linux/kernel/aha1542.c
   3  *
   4  *  Copyright (C) 1992  Tommy Thorn
   5  *  Copyright (C) 1993, 1994, 1995 Eric Youngdale
   6  *
   7  *  Modified by Eric Youngdale
   8  *        Use request_irq and request_dma to help prevent unexpected conflicts
   9  *        Set up on-board DMA controller, such that we do not have to
  10  *        have the bios enabled to use the aha1542.
  11  *  Modified by David Gentzel
  12  *        Don't call request_dma if dma mask is 0 (for BusLogic BT-445S VL-Bus controller).
  13  *  Modified by Matti Aarnio
  14  *        Accept parameters from LILO cmd-line. -- 1-Oct-94
  15  */
  16 
  17 #ifdef MODULE
  18 #include <linux/autoconf.h>
  19 #include <linux/module.h>
  20 #endif
  21 
  22 #include <linux/kernel.h>
  23 #include <linux/head.h>
  24 #include <linux/types.h>
  25 #include <linux/string.h>
  26 #include <linux/ioport.h>
  27 #include <linux/delay.h>
  28 #include <linux/sched.h>
  29 #include <linux/proc_fs.h>
  30 #include <asm/dma.h>
  31 #include <asm/system.h>
  32 #include <asm/io.h>
  33 #include "../block/blk.h"
  34 #include "scsi.h"
  35 #include "hosts.h"
  36 
  37 
  38 #include "aha1542.h"
  39 
  40 #ifdef DEBUG
  41 #define DEB(x) x
  42 #else
  43 #define DEB(x)
  44 #endif
  45 /*
  46 static const char RCSid[] = "$Header: /usr/src/linux/kernel/blk_drv/scsi/RCS/aha1542.c,v 1.1 1992/07/24 06:27:38 root Exp root $";
  47 */
  48 
  49 /* The adaptec can be configured for quite a number of addresses, but
  50 I generally do not want the card poking around at random.  We allow
  51 two addresses - this allows people to use the Adaptec with a Midi
  52 card, which also used 0x330 -- can be overridden with LILO! */
  53 
  54 #define MAXBOARDS 2     /* Increase this and the sizes of the
  55                            arrays below, if you need more.. */
  56 
  57 static unsigned int bases[MAXBOARDS]={0x330, 0x334};
  58 
  59 /* set by aha1542_setup according to the command line */
  60 static int setup_called[MAXBOARDS]   = {0,0};
  61 static int setup_buson[MAXBOARDS]    = {0,0};
  62 static int setup_busoff[MAXBOARDS]   = {0,0};
  63 static int setup_dmaspeed[MAXBOARDS] = {-1,-1};
  64 
  65 static char *setup_str[MAXBOARDS] = {(char *)NULL,(char *)NULL};
  66 
  67 /*
  68  * LILO params:  aha1542=<PORTBASE>[,<BUSON>,<BUSOFF>[,<DMASPEED>]]
  69  *
  70  * Where:  <PORTBASE> is any of the valid AHA addresses:
  71  *                      0x130, 0x134, 0x230, 0x234, 0x330, 0x334
  72  *         <BUSON>  is the time (in microsecs) that AHA spends on the AT-bus
  73  *                  when transferring data.  1542A power-on default is 11us,
  74  *                  valid values are in range: 2..15 (decimal)
  75  *         <BUSOFF> is the time that AHA spends OFF THE BUS after while
  76  *                  it is transferring data (not to monopolize the bus).
  77  *                  Power-on default is 4us, valid range: 1..64 microseconds.
  78  *         <DMASPEED> Default is jumper selected (1542A: on the J1),
  79  *                  but experimenter can alter it with this.
  80  *                  Valid values: 5, 6, 7, 8, 10 (MB/s)
  81  *                  Factory default is 5 MB/s.
  82  */
  83 
  84 
  85 /* The DMA-Controller.  We need to fool with this because we want to 
  86    be able to use the aha1542 without having to have the bios enabled */
  87 #define DMA_MODE_REG    0xd6
  88 #define DMA_MASK_REG    0xd4
  89 #define CASCADE         0xc0
  90 
  91 #define BIOS_TRANSLATION_1632 0  /* Used by some old 1542A boards */
  92 #define BIOS_TRANSLATION_6432 1 /* Default case these days */
  93 #define BIOS_TRANSLATION_25563 2 /* Big disk case */
  94 
  95 struct aha1542_hostdata{
  96         /* This will effectively start both of them at the first mailbox */
  97         int bios_translation;   /* Mapping bios uses - for compatibility */
  98         int aha1542_last_mbi_used;
  99         int aha1542_last_mbo_used;
 100         Scsi_Cmnd * SCint[AHA1542_MAILBOXES];
 101         struct mailbox mb[2*AHA1542_MAILBOXES];
 102         struct ccb ccb[AHA1542_MAILBOXES];
 103 };
 104 
 105 #define HOSTDATA(host) ((struct aha1542_hostdata *) &host->hostdata)
 106 
 107 static struct Scsi_Host * aha_host[7] = {NULL,};  /* One for each IRQ level (9-15) */
 108 
 109 
 110 
 111 
 112 #define WAITnexttimeout 3000000
 113 
 114 static void setup_mailboxes(int base_io, struct Scsi_Host * shpnt);
 115 static int aha1542_restart(struct Scsi_Host * shost);
 116 
 117 #define aha1542_intr_reset(base)  outb(IRST, CONTROL(base))
 118 
 119 #define WAIT(port, mask, allof, noneof)                                 \
 120  { register WAITbits;                                                   \
 121    register WAITtimeout = WAITnexttimeout;                              \
 122    while (1) {                                                          \
 123      WAITbits = inb(port) & (mask);                                     \
 124      if ((WAITbits & (allof)) == (allof) && ((WAITbits & (noneof)) == 0)) \
 125        break;                                                           \
 126      if (--WAITtimeout == 0) goto fail;                                 \
 127    }                                                                    \
 128  }
 129 
 130 /* Similar to WAIT, except we use the udelay call to regulate the
 131    amount of time we wait.  */
 132 #define WAITd(port, mask, allof, noneof, timeout)                       \
 133  { register WAITbits;                                                   \
 134    register WAITtimeout = timeout;                                      \
 135    while (1) {                                                          \
 136      WAITbits = inb(port) & (mask);                                     \
 137      if ((WAITbits & (allof)) == (allof) && ((WAITbits & (noneof)) == 0)) \
 138        break;                                                           \
 139      udelay(1000);                                                      \
 140      if (--WAITtimeout == 0) goto fail;                                 \
 141    }                                                                    \
 142  }
 143 
 144 static void aha1542_stat(void)
     /* [previous][next][first][last][top][bottom][index][help] */
 145 {
 146 /*    int s = inb(STATUS), i = inb(INTRFLAGS);
 147   printk("status=%x intrflags=%x\n", s, i, WAITnexttimeout-WAITtimeout); */
 148 }
 149 
 150 /* This is a bit complicated, but we need to make sure that an interrupt
 151    routine does not send something out while we are in the middle of this.
 152    Fortunately, it is only at boot time that multi-byte messages
 153    are ever sent. */
 154 static int aha1542_out(unsigned int base, unchar *cmdp, int len)
     /* [previous][next][first][last][top][bottom][index][help] */
 155 {
 156   unsigned long flags = 0;
 157   
 158   if(len == 1) {
 159     while(1==1){
 160         WAIT(STATUS(base), CDF, 0, CDF);
 161         save_flags(flags);
 162         cli();
 163         if(inb(STATUS(base)) & CDF) {restore_flags(flags); continue;}
 164         outb(*cmdp, DATA(base));
 165         restore_flags(flags);
 166         return 0;
 167       }
 168   } else {
 169     save_flags(flags);
 170     cli();
 171     while (len--)
 172       {
 173         WAIT(STATUS(base), CDF, 0, CDF);
 174         outb(*cmdp++, DATA(base));
 175       }
 176     restore_flags(flags);
 177   }
 178     return 0;
 179   fail:
 180     restore_flags(flags);
 181     printk("aha1542_out failed(%d): ", len+1); aha1542_stat();
 182     return 1;
 183 }
 184 
 185 /* Only used at boot time, so we do not need to worry about latency as much
 186    here */
 187 static int aha1542_in(unsigned int base, unchar *cmdp, int len)
     /* [previous][next][first][last][top][bottom][index][help] */
 188 {
 189     unsigned long flags;
 190 
 191     save_flags(flags);
 192     cli();
 193     while (len--)
 194       {
 195           WAIT(STATUS(base), DF, DF, 0);
 196           *cmdp++ = inb(DATA(base));
 197       }
 198     restore_flags(flags);
 199     return 0;
 200   fail:
 201     restore_flags(flags);
 202     printk("aha1542_in failed(%d): ", len+1); aha1542_stat();
 203     return 1;
 204 }
 205 
 206 /* Similar to aha1542_in, except that we wait a very short period of time.
 207    We use this if we know the board is alive and awake, but we are not sure
 208    if the board will respond the the command we are about to send or not */
 209 static int aha1542_in1(unsigned int base, unchar *cmdp, int len)
     /* [previous][next][first][last][top][bottom][index][help] */
 210 {
 211     unsigned long flags;
 212     
 213     save_flags(flags);
 214     cli();
 215     while (len--)
 216       {
 217           WAITd(STATUS(base), DF, DF, 0, 100);
 218           *cmdp++ = inb(DATA(base));
 219       }
 220     restore_flags(flags);
 221     return 0;
 222   fail:
 223     restore_flags(flags);
 224     return 1;
 225 }
 226 
 227 static int makecode(unsigned hosterr, unsigned scsierr)
     /* [previous][next][first][last][top][bottom][index][help] */
 228 {
 229     switch (hosterr) {
 230       case 0x0:
 231       case 0xa: /* Linked command complete without error and linked normally */
 232       case 0xb: /* Linked command complete without error, interrupt generated */
 233         hosterr = 0;
 234         break;
 235 
 236       case 0x11: /* Selection time out-The initiator selection or target
 237                     reselection was not complete within the SCSI Time out period */
 238         hosterr = DID_TIME_OUT;
 239         break;
 240 
 241       case 0x12: /* Data overrun/underrun-The target attempted to transfer more data
 242                     than was allocated by the Data Length field or the sum of the
 243                     Scatter / Gather Data Length fields. */
 244 
 245       case 0x13: /* Unexpected bus free-The target dropped the SCSI BSY at an unexpected time. */
 246 
 247       case 0x15: /* MBO command was not 00, 01 or 02-The first byte of the CB was
 248                     invalid. This usually indicates a software failure. */
 249 
 250       case 0x16: /* Invalid CCB Operation Code-The first byte of the CCB was invalid.
 251                     This usually indicates a software failure. */
 252 
 253       case 0x17: /* Linked CCB does not have the same LUN-A subsequent CCB of a set
 254                     of linked CCB's does not specify the same logical unit number as
 255                     the first. */
 256       case 0x18: /* Invalid Target Direction received from Host-The direction of a
 257                     Target Mode CCB was invalid. */
 258 
 259       case 0x19: /* Duplicate CCB Received in Target Mode-More than once CCB was
 260                     received to service data transfer between the same target LUN
 261                     and initiator SCSI ID in the same direction. */
 262 
 263       case 0x1a: /* Invalid CCB or Segment List Parameter-A segment list with a zero
 264                     length segment or invalid segment list boundaries was received.
 265                     A CCB parameter was invalid. */
 266         DEB(printk("Aha1542: %x %x\n", hosterr, scsierr));
 267         hosterr = DID_ERROR; /* Couldn't find any better */
 268         break;
 269 
 270       case 0x14: /* Target bus phase sequence failure-An invalid bus phase or bus
 271                     phase sequence was requested by the target. The host adapter
 272                     will generate a SCSI Reset Condition, notifying the host with
 273                     a SCRD interrupt */
 274         hosterr = DID_RESET;
 275         break;
 276       default:
 277         printk("makecode: unknown hoststatus %x\n", hosterr);
 278         break;
 279     }
 280     return scsierr|(hosterr << 16);
 281 }
 282 
 283 static int aha1542_test_port(int bse, struct Scsi_Host * shpnt)
     /* [previous][next][first][last][top][bottom][index][help] */
 284 {
 285     int i;
 286     unchar inquiry_cmd[] = {CMD_INQUIRY };
 287     unchar inquiry_result[4];
 288     unchar *cmdp;
 289     int len;
 290     volatile int debug = 0;
 291     
 292     /* Quick and dirty test for presence of the card. */
 293     if(inb(STATUS(bse)) == 0xff) return 0;
 294 
 295     /* Reset the adapter. I ought to make a hard reset, but it's not really necessary */
 296     
 297     /*  DEB(printk("aha1542_test_port called \n")); */
 298 
 299     /* In case some other card was probing here, reset interrupts */
 300     aha1542_intr_reset(bse);     /* reset interrupts, so they don't block */    
 301 
 302     outb(SRST|IRST/*|SCRST*/, CONTROL(bse));
 303 
 304     i = jiffies + 2;
 305     while (i>jiffies); /* Wait a little bit for things to settle down. */
 306     
 307     debug = 1;
 308     /* Expect INIT and IDLE, any of the others are bad */
 309     WAIT(STATUS(bse), STATMASK, INIT|IDLE, STST|DIAGF|INVDCMD|DF|CDF);
 310     
 311     debug = 2;
 312     /* Shouldn't have generated any interrupts during reset */
 313     if (inb(INTRFLAGS(bse))&INTRMASK) goto fail;
 314 
 315 
 316     /* Perform a host adapter inquiry instead so we do not need to set
 317        up the mailboxes ahead of time */
 318 
 319     aha1542_out(bse, inquiry_cmd, 1);
 320 
 321     debug = 3;
 322     len = 4;
 323     cmdp = &inquiry_result[0];
 324 
 325     while (len--)
 326       {
 327           WAIT(STATUS(bse), DF, DF, 0);
 328           *cmdp++ = inb(DATA(bse));
 329       }
 330     
 331     debug = 8;
 332     /* Reading port should reset DF */
 333     if (inb(STATUS(bse)) & DF) goto fail;
 334     
 335     debug = 9;
 336     /* When HACC, command is completed, and we're though testing */
 337     WAIT(INTRFLAGS(bse), HACC, HACC, 0);
 338     /* now initialize adapter */
 339     
 340     debug = 10;
 341     /* Clear interrupts */
 342     outb(IRST, CONTROL(bse));
 343     
 344     debug = 11;
 345 
 346     return debug;                               /* 1 = ok */
 347   fail:
 348     return 0;                                   /* 0 = not ok */
 349 }
 350 
 351 /* A "high" level interrupt handler */
 352 static void aha1542_intr_handle(int irq, struct pt_regs *regs)
     /* [previous][next][first][last][top][bottom][index][help] */
 353 {
 354     void (*my_done)(Scsi_Cmnd *) = NULL;
 355     int errstatus, mbi, mbo, mbistatus;
 356     int number_serviced;
 357     unsigned int flags;
 358     struct Scsi_Host * shost;
 359     Scsi_Cmnd * SCtmp;
 360     int flag;
 361     int needs_restart;
 362     struct mailbox * mb;
 363     struct ccb  *ccb;
 364 
 365     shost = aha_host[irq - 9];
 366     if(!shost) panic("Splunge!");
 367 
 368     mb = HOSTDATA(shost)->mb;
 369     ccb = HOSTDATA(shost)->ccb;
 370 
 371 #ifdef DEBUG
 372     {
 373     flag = inb(INTRFLAGS(shost->io_port));
 374     printk("aha1542_intr_handle: ");
 375     if (!(flag&ANYINTR)) printk("no interrupt?");
 376     if (flag&MBIF) printk("MBIF ");
 377     if (flag&MBOA) printk("MBOF ");
 378     if (flag&HACC) printk("HACC ");
 379     if (flag&SCRD) printk("SCRD ");
 380     printk("status %02x\n", inb(STATUS(shost->io_port)));
 381   };
 382 #endif
 383     number_serviced = 0;
 384     needs_restart = 0;
 385 
 386     while(1==1){
 387       flag = inb(INTRFLAGS(shost->io_port));
 388 
 389       /* Check for unusual interrupts.  If any of these happen, we should
 390          probably do something special, but for now just printing a message
 391          is sufficient.  A SCSI reset detected is something that we really
 392          need to deal with in some way. */
 393       if (flag & ~MBIF) {
 394         if (flag&MBOA) printk("MBOF ");
 395         if (flag&HACC) printk("HACC ");
 396         if (flag&SCRD) {
 397           needs_restart = 1;
 398           printk("SCRD ");
 399         }
 400       }
 401 
 402       aha1542_intr_reset(shost->io_port);
 403 
 404       save_flags(flags);
 405       cli();
 406       mbi = HOSTDATA(shost)->aha1542_last_mbi_used + 1;
 407       if (mbi >= 2*AHA1542_MAILBOXES) mbi = AHA1542_MAILBOXES;
 408       
 409       do{
 410         if(mb[mbi].status != 0) break;
 411         mbi++;
 412         if (mbi >= 2*AHA1542_MAILBOXES) mbi = AHA1542_MAILBOXES;
 413       } while (mbi != HOSTDATA(shost)->aha1542_last_mbi_used);
 414       
 415       if(mb[mbi].status == 0){
 416         restore_flags(flags);
 417         /* Hmm, no mail.  Must have read it the last time around */
 418         if (!number_serviced && !needs_restart)
 419           printk("aha1542.c: interrupt received, but no mail.\n");
 420         /* We detected a reset.  Restart all pending commands for
 421            devices that use the hard reset option */
 422         if(needs_restart) aha1542_restart(shost);
 423         return;
 424       };
 425 
 426       mbo = (scsi2int(mb[mbi].ccbptr) - ((unsigned int) &ccb[0])) / sizeof(struct ccb);
 427       mbistatus = mb[mbi].status;
 428       mb[mbi].status = 0;
 429       HOSTDATA(shost)->aha1542_last_mbi_used = mbi;
 430       restore_flags(flags);
 431       
 432 #ifdef DEBUG
 433       {
 434         if (ccb[mbo].tarstat|ccb[mbo].hastat)
 435           printk("aha1542_command: returning %x (status %d)\n", 
 436                  ccb[mbo].tarstat + ((int) ccb[mbo].hastat << 16), mb[mbi].status);
 437       };
 438 #endif
 439 
 440       if(mbistatus == 3) continue; /* Aborted command not found */
 441 
 442 #ifdef DEBUG
 443       printk("...done %d %d\n",mbo, mbi);
 444 #endif
 445       
 446       SCtmp = HOSTDATA(shost)->SCint[mbo];
 447 
 448       if (!SCtmp || !SCtmp->scsi_done) {
 449         printk("aha1542_intr_handle: Unexpected interrupt\n");
 450         printk("tarstat=%x, hastat=%x idlun=%x ccb#=%d \n", ccb[mbo].tarstat, 
 451                ccb[mbo].hastat, ccb[mbo].idlun, mbo);
 452         return;
 453       }
 454       
 455       my_done = SCtmp->scsi_done;
 456       if (SCtmp->host_scribble) scsi_free(SCtmp->host_scribble, 512);
 457       
 458       /* Fetch the sense data, and tuck it away, in the required slot.  The
 459          Adaptec automatically fetches it, and there is no guarantee that
 460          we will still have it in the cdb when we come back */
 461       if (ccb[mbo].tarstat == 2)
 462         memcpy(SCtmp->sense_buffer, &ccb[mbo].cdb[ccb[mbo].cdblen], 
 463                sizeof(SCtmp->sense_buffer));
 464       
 465       
 466       /* is there mail :-) */
 467       
 468       /* more error checking left out here */
 469       if (mbistatus != 1)
 470         /* This is surely wrong, but I don't know what's right */
 471         errstatus = makecode(ccb[mbo].hastat, ccb[mbo].tarstat);
 472       else
 473         errstatus = 0;
 474       
 475 #ifdef DEBUG
 476       if(errstatus) printk("(aha1542 error:%x %x %x) ",errstatus, 
 477                            ccb[mbo].hastat, ccb[mbo].tarstat);
 478 #endif
 479 
 480       if (ccb[mbo].tarstat == 2) {
 481 #ifdef DEBUG
 482         int i;
 483 #endif
 484         DEB(printk("aha1542_intr_handle: sense:"));
 485 #ifdef DEBUG
 486         for (i = 0; i < 12; i++)
 487           printk("%02x ", ccb[mbo].cdb[ccb[mbo].cdblen+i]);
 488         printk("\n");
 489 #endif
 490         /*
 491           DEB(printk("aha1542_intr_handle: buf:"));
 492           for (i = 0; i < bufflen; i++)
 493           printk("%02x ", ((unchar *)buff)[i]);
 494           printk("\n");
 495           */
 496       }
 497       DEB(if (errstatus) printk("aha1542_intr_handle: returning %6x\n", errstatus));
 498       SCtmp->result = errstatus;
 499       HOSTDATA(shost)->SCint[mbo] = NULL;  /* This effectively frees up the mailbox slot, as
 500                              far as queuecommand is concerned */
 501       my_done(SCtmp);
 502       number_serviced++;
 503     };
 504 }
 505 
 506 int aha1542_queuecommand(Scsi_Cmnd * SCpnt, void (*done)(Scsi_Cmnd *))
     /* [previous][next][first][last][top][bottom][index][help] */
 507 {
 508     unchar ahacmd = CMD_START_SCSI;
 509     unchar direction;
 510     unchar *cmd = (unchar *) SCpnt->cmnd;
 511     unchar target = SCpnt->target;
 512     unchar lun = SCpnt->lun;
 513     unsigned long flags;
 514     void *buff = SCpnt->request_buffer;
 515     int bufflen = SCpnt->request_bufflen;
 516     int mbo;
 517     struct mailbox * mb;
 518     struct ccb  *ccb;
 519 
 520     DEB(int i);
 521 
 522     mb = HOSTDATA(SCpnt->host)->mb;
 523     ccb = HOSTDATA(SCpnt->host)->ccb;
 524 
 525     DEB(if (target > 1) {
 526       SCpnt->result = DID_TIME_OUT << 16;
 527       done(SCpnt); return 0;});
 528     
 529     if(*cmd == REQUEST_SENSE){
 530 #ifndef DEBUG
 531       if (bufflen != sizeof(SCpnt->sense_buffer)) {
 532         printk("Wrong buffer length supplied for request sense (%d)\n",bufflen);
 533       };
 534 #endif
 535       SCpnt->result = 0;
 536       done(SCpnt); 
 537       return 0;
 538     };
 539 
 540 #ifdef DEBUG
 541     if (*cmd == READ_10 || *cmd == WRITE_10)
 542       i = xscsi2int(cmd+2);
 543     else if (*cmd == READ_6 || *cmd == WRITE_6)
 544       i = scsi2int(cmd+2);
 545     else
 546       i = -1;
 547     if (done)
 548       printk("aha1542_queuecommand: dev %d cmd %02x pos %d len %d ", target, *cmd, i, bufflen);
 549     else
 550       printk("aha1542_command: dev %d cmd %02x pos %d len %d ", target, *cmd, i, bufflen);
 551     aha1542_stat();
 552     printk("aha1542_queuecommand: dumping scsi cmd:");
 553     for (i = 0; i < SCpnt->cmd_len; i++) printk("%02x ", cmd[i]);
 554     printk("\n");
 555     if (*cmd == WRITE_10 || *cmd == WRITE_6)
 556       return 0; /* we are still testing, so *don't* write */
 557 #endif
 558 /* Use the outgoing mailboxes in a round-robin fashion, because this
 559    is how the host adapter will scan for them */
 560 
 561     save_flags(flags);
 562     cli();
 563     mbo = HOSTDATA(SCpnt->host)->aha1542_last_mbo_used + 1;
 564     if (mbo >= AHA1542_MAILBOXES) mbo = 0;
 565 
 566     do{
 567       if(mb[mbo].status == 0 && HOSTDATA(SCpnt->host)->SCint[mbo] == NULL)
 568         break;
 569       mbo++;
 570       if (mbo >= AHA1542_MAILBOXES) mbo = 0;
 571     } while (mbo != HOSTDATA(SCpnt->host)->aha1542_last_mbo_used);
 572 
 573     if(mb[mbo].status || HOSTDATA(SCpnt->host)->SCint[mbo])
 574       panic("Unable to find empty mailbox for aha1542.\n");
 575 
 576     HOSTDATA(SCpnt->host)->SCint[mbo] = SCpnt;  /* This will effectively prevent someone else from
 577                             screwing with this cdb. */
 578 
 579     HOSTDATA(SCpnt->host)->aha1542_last_mbo_used = mbo;    
 580     restore_flags(flags);
 581 
 582 #ifdef DEBUG
 583     printk("Sending command (%d %x)...",mbo, done);
 584 #endif
 585 
 586     any2scsi(mb[mbo].ccbptr, &ccb[mbo]); /* This gets trashed for some reason*/
 587 
 588     memset(&ccb[mbo], 0, sizeof(struct ccb));
 589 
 590     ccb[mbo].cdblen = SCpnt->cmd_len;
 591 
 592     direction = 0;
 593     if (*cmd == READ_10 || *cmd == READ_6)
 594         direction = 8;
 595     else if (*cmd == WRITE_10 || *cmd == WRITE_6)
 596         direction = 16;
 597 
 598     memcpy(ccb[mbo].cdb, cmd, ccb[mbo].cdblen);
 599 
 600     if (SCpnt->use_sg) {
 601       struct scatterlist * sgpnt;
 602       struct chain * cptr;
 603 #ifdef DEBUG
 604       unsigned char * ptr;
 605 #endif
 606       int i;
 607       ccb[mbo].op = 2;        /* SCSI Initiator Command  w/scatter-gather*/
 608       SCpnt->host_scribble = (unsigned char *) scsi_malloc(512);
 609       sgpnt = (struct scatterlist *) SCpnt->request_buffer;
 610       cptr = (struct chain *) SCpnt->host_scribble; 
 611       if (cptr == NULL) panic("aha1542.c: unable to allocate DMA memory\n");
 612       for(i=0; i<SCpnt->use_sg; i++) {
 613         if(sgpnt[i].length == 0 || SCpnt->use_sg > 16 || 
 614            (((int)sgpnt[i].address) & 1) || (sgpnt[i].length & 1)){
 615           unsigned char * ptr;
 616           printk("Bad segment list supplied to aha1542.c (%d, %d)\n",SCpnt->use_sg,i);
 617           for(i=0;i<SCpnt->use_sg;i++){
 618             printk("%d: %x %x %d\n",i,(unsigned int) sgpnt[i].address, (unsigned int) sgpnt[i].alt_address,
 619                    sgpnt[i].length);
 620           };
 621           printk("cptr %x: ",(unsigned int) cptr);
 622           ptr = (unsigned char *) &cptr[i];
 623           for(i=0;i<18;i++) printk("%02x ", ptr[i]);
 624           panic("Foooooooood fight!");
 625         };
 626         any2scsi(cptr[i].dataptr, sgpnt[i].address);
 627         if(((unsigned  int) sgpnt[i].address) & 0xff000000) goto baddma;
 628         any2scsi(cptr[i].datalen, sgpnt[i].length);
 629       };
 630       any2scsi(ccb[mbo].datalen, SCpnt->use_sg * sizeof(struct chain));
 631       any2scsi(ccb[mbo].dataptr, cptr);
 632 #ifdef DEBUG
 633       printk("cptr %x: ",cptr);
 634       ptr = (unsigned char *) cptr;
 635       for(i=0;i<18;i++) printk("%02x ", ptr[i]);
 636 #endif
 637     } else {
 638       ccb[mbo].op = 0;        /* SCSI Initiator Command */
 639       SCpnt->host_scribble = NULL;
 640       any2scsi(ccb[mbo].datalen, bufflen);
 641       if(((unsigned int) buff & 0xff000000)) goto baddma;
 642       any2scsi(ccb[mbo].dataptr, buff);
 643     };
 644     ccb[mbo].idlun = (target&7)<<5 | direction | (lun & 7); /*SCSI Target Id*/
 645     ccb[mbo].rsalen = 12;
 646     ccb[mbo].linkptr[0] = ccb[mbo].linkptr[1] = ccb[mbo].linkptr[2] = 0;
 647     ccb[mbo].commlinkid = 0;
 648 
 649 #ifdef DEBUG
 650     { int i;
 651     printk("aha1542_command: sending.. ");
 652     for (i = 0; i < sizeof(ccb[mbo])-10; i++)
 653       printk("%02x ", ((unchar *)&ccb[mbo])[i]);
 654     };
 655 #endif
 656     
 657     if (done) {
 658         DEB(printk("aha1542_queuecommand: now waiting for interrupt "); aha1542_stat());
 659         SCpnt->scsi_done = done;
 660         mb[mbo].status = 1;
 661         aha1542_out(SCpnt->host->io_port, &ahacmd, 1);          /* start scsi command */
 662         DEB(aha1542_stat());
 663     }
 664     else
 665       printk("aha1542_queuecommand: done can't be NULL\n");
 666     
 667     return 0;
 668  baddma:
 669     panic("Buffer at address  > 16Mb used for 1542B");
 670 }
 671 
 672 static void internal_done(Scsi_Cmnd * SCpnt)
     /* [previous][next][first][last][top][bottom][index][help] */
 673 {
 674         SCpnt->SCp.Status++;
 675 }
 676 
 677 int aha1542_command(Scsi_Cmnd * SCpnt)
     /* [previous][next][first][last][top][bottom][index][help] */
 678 {
 679     DEB(printk("aha1542_command: ..calling aha1542_queuecommand\n"));
 680 
 681     aha1542_queuecommand(SCpnt, internal_done);
 682 
 683     SCpnt->SCp.Status = 0;
 684     while (!SCpnt->SCp.Status)
 685         barrier();
 686     return SCpnt->result;
 687 }
 688 
 689 /* Initialize mailboxes */
 690 static void setup_mailboxes(int bse, struct Scsi_Host * shpnt)
     /* [previous][next][first][last][top][bottom][index][help] */
 691 {
 692     int i;
 693     struct mailbox * mb;
 694     struct ccb  *ccb;
 695 
 696     unchar cmd[5] = {CMD_MBINIT, AHA1542_MAILBOXES, 0, 0, 0};
 697 
 698     mb = HOSTDATA(shpnt)->mb;
 699     ccb = HOSTDATA(shpnt)->ccb;
 700 
 701     for(i=0; i<AHA1542_MAILBOXES; i++){
 702       mb[i].status = mb[AHA1542_MAILBOXES+i].status = 0;
 703       any2scsi(mb[i].ccbptr, &ccb[i]);
 704     };
 705     aha1542_intr_reset(bse);     /* reset interrupts, so they don't block */    
 706     any2scsi((cmd+2), mb);
 707     aha1542_out(bse, cmd, 5);
 708     WAIT(INTRFLAGS(bse), INTRMASK, HACC, 0);
 709     while (0) {
 710       fail:
 711         printk("aha1542_detect: failed setting up mailboxes\n");
 712     }
 713     aha1542_intr_reset(bse);
 714 }
 715 
 716 static int aha1542_getconfig(int base_io, unsigned char * irq_level, unsigned char * dma_chan)
     /* [previous][next][first][last][top][bottom][index][help] */
 717 {
 718   unchar inquiry_cmd[] = {CMD_RETCONF };
 719   unchar inquiry_result[3];
 720   int i;
 721   i = inb(STATUS(base_io));
 722   if (i & DF) {
 723     i = inb(DATA(base_io));
 724   };
 725   aha1542_out(base_io, inquiry_cmd, 1);
 726   aha1542_in(base_io, inquiry_result, 3);
 727   WAIT(INTRFLAGS(base_io), INTRMASK, HACC, 0);
 728   while (0) {
 729   fail:
 730     printk("aha1542_detect: query board settings\n");
 731   }
 732   aha1542_intr_reset(base_io);
 733   switch(inquiry_result[0]){
 734   case 0x80:
 735     *dma_chan = 7;
 736     break;
 737   case 0x40:
 738     *dma_chan = 6;
 739     break;
 740   case 0x20:
 741     *dma_chan = 5;
 742     break;
 743   case 0x01:
 744     printk("DMA priority 0 not available for Adaptec driver\n");
 745     return -1;
 746   case 0:
 747     /* This means that the adapter, although Adaptec 1542 compatible, doesn't use a DMA channel.
 748        Currently only aware of the BusLogic BT-445S VL-Bus adapter which needs this. */
 749     *dma_chan = 0xFF;
 750     break;
 751   default:
 752     printk("Unable to determine Adaptec DMA priority.  Disabling board\n");
 753     return -1;
 754   };
 755   switch(inquiry_result[1]){
 756   case 0x40:
 757     *irq_level = 15;
 758     break;
 759   case 0x20:
 760     *irq_level = 14;
 761     break;
 762   case 0x8:
 763     *irq_level = 12;
 764     break;
 765   case 0x4:
 766     *irq_level = 11;
 767     break;
 768   case 0x2:
 769     *irq_level = 10;
 770     break;
 771   case 0x1:
 772     *irq_level = 9;
 773     break;
 774   default:
 775     printk("Unable to determine Adaptec IRQ level.  Disabling board\n");
 776     return -1;
 777   };
 778   return 0;
 779 }
 780 
 781 /* This function should only be called for 1542C boards - we can detect
 782    the special firmware settings and unlock the board */
 783 
 784 static int aha1542_mbenable(int base)
     /* [previous][next][first][last][top][bottom][index][help] */
 785 {
 786   static unchar mbenable_cmd[3];
 787   static unchar mbenable_result[2];
 788   int retval;
 789   
 790   retval = BIOS_TRANSLATION_6432;
 791 
 792   mbenable_cmd[0]=CMD_EXTBIOS;
 793   aha1542_out(base,mbenable_cmd,1);
 794   if(aha1542_in1(base,mbenable_result,2))
 795     return retval;
 796   WAITd(INTRFLAGS(base),INTRMASK,HACC,0,100);
 797   aha1542_intr_reset(base);
 798   
 799   if ((mbenable_result[0] & 0x08) || mbenable_result[1]) {
 800      mbenable_cmd[0]=CMD_MBENABLE;
 801      mbenable_cmd[1]=0;
 802      mbenable_cmd[2]=mbenable_result[1];
 803      if(mbenable_result[1] & 1) retval = BIOS_TRANSLATION_25563;
 804      aha1542_out(base,mbenable_cmd,3);
 805      WAIT(INTRFLAGS(base),INTRMASK,HACC,0);
 806   };
 807   while(0) {
 808 fail:
 809     printk("aha1542_mbenable: Mailbox init failed\n");
 810   }
 811 aha1542_intr_reset(base);
 812 return retval;
 813 }
 814 
 815 /* Query the board to find out if it is a 1542 or a 1740, or whatever. */
 816 static int aha1542_query(int base_io, int * transl)
     /* [previous][next][first][last][top][bottom][index][help] */
 817 {
 818   unchar inquiry_cmd[] = {CMD_INQUIRY };
 819   unchar inquiry_result[4];
 820   int i;
 821   i = inb(STATUS(base_io));
 822   if (i & DF) {
 823     i = inb(DATA(base_io));
 824   };
 825   aha1542_out(base_io, inquiry_cmd, 1);
 826   aha1542_in(base_io, inquiry_result, 4);
 827   WAIT(INTRFLAGS(base_io), INTRMASK, HACC, 0);
 828   while (0) {
 829   fail:
 830     printk("aha1542_detect: query card type\n");
 831   }
 832   aha1542_intr_reset(base_io);
 833 
 834   *transl = BIOS_TRANSLATION_6432; /* Default case */
 835 
 836 /* For an AHA1740 series board, we ignore the board since there is a
 837    hardware bug which can lead to wrong blocks being returned if the board
 838    is operating in the 1542 emulation mode.  Since there is an extended mode
 839    driver, we simply ignore the board and let the 1740 driver pick it up.
 840 */
 841 
 842   if (inquiry_result[0] == 0x43) {
 843     printk("aha1542.c: Emulation mode not supported for AHA 174N hardware.\n");
 844     return 1;
 845   };
 846 
 847   /* Always call this - boards that do not support extended bios translation
 848      will ignore the command, and we will set the proper default */
 849 
 850   *transl = aha1542_mbenable(base_io);
 851 
 852   return 0;
 853 }
 854 
 855 /* called from init/main.c */
 856 void aha1542_setup( char *str, int *ints)
     /* [previous][next][first][last][top][bottom][index][help] */
 857 {
 858     char *ahausage = "aha1542: usage: aha1542=<PORTBASE>[,<BUSON>,<BUSOFF>[,<DMASPEED>]]\n";
 859     static int setup_idx = 0;
 860     int setup_portbase;
 861 
 862     if(setup_idx >= MAXBOARDS)
 863       {
 864         printk("aha1542: aha1542_setup called too many times! Bad LILO params ?\n");
 865         printk("   Entryline 1: %s\n",setup_str[0]);
 866         printk("   Entryline 2: %s\n",setup_str[1]);
 867         printk("   This line:   %s\n",str);
 868         return;
 869       }
 870     if (ints[0] < 1 || ints[0] > 4)
 871       {
 872         printk("aha1542: %s\n", str );
 873         printk(ahausage);
 874         printk("aha1542: Wrong parameters may cause system malfunction.. We try anyway..\n");
 875       }
 876 
 877     setup_called[setup_idx]=ints[0];
 878     setup_str[setup_idx]=str;
 879 
 880     setup_portbase             = ints[0] >= 1 ? ints[1] : 0; /* Preserve the default value.. */
 881     setup_buson   [setup_idx]  = ints[0] >= 2 ? ints[2] : 7;
 882     setup_busoff  [setup_idx]  = ints[0] >= 3 ? ints[3] : 5;
 883     if (ints[0] >= 4) {
 884       int atbt = -1;
 885       switch (ints[4]) {
 886         case 5:
 887             atbt = 0x00;
 888             break;
 889         case 6:
 890             atbt = 0x04;
 891             break;
 892         case 7:
 893             atbt = 0x01;
 894             break;
 895         case 8:
 896             atbt = 0x02;
 897             break;
 898         case 10:
 899             atbt = 0x03;
 900             break;
 901         default:
 902             printk("aha1542: %s\n", str );
 903             printk(ahausage);
 904             printk("aha1542: Valid values for DMASPEED are 5-8, 10 MB/s.  Using jumper defaults.\n");
 905             break;
 906       }
 907       setup_dmaspeed[setup_idx]  = atbt;
 908     }
 909 
 910     if (setup_portbase != 0)
 911       bases[setup_idx] = setup_portbase;
 912 
 913     ++setup_idx;
 914 }
 915 
 916 /* return non-zero on detection */
 917 int aha1542_detect(Scsi_Host_Template * tpnt)
     /* [previous][next][first][last][top][bottom][index][help] */
 918 {
 919     unsigned char dma_chan;
 920     unsigned char irq_level;
 921     unsigned long flags;
 922     unsigned int base_io;
 923     int trans;
 924     struct Scsi_Host * shpnt = NULL;
 925     int count = 0;
 926     int indx;
 927 
 928     DEB(printk("aha1542_detect: \n"));
 929 
 930     for(indx = 0; indx < sizeof(bases)/sizeof(bases[0]); indx++)
 931             if(bases[indx] != 0 && !check_region(bases[indx], 4)) { 
 932                     shpnt = scsi_register(tpnt,
 933                                           sizeof(struct aha1542_hostdata));
 934 
 935                     /* For now we do this - until kmalloc is more intelligent
 936                        we are resigned to stupid hacks like this */
 937                     if ((unsigned int) shpnt > 0xffffff) {
 938                       printk("Invalid address for shpnt with 1542.\n");
 939                       goto unregister;
 940                     }
 941 
 942                     if(!aha1542_test_port(bases[indx], shpnt)) goto unregister;
 943 
 944 
 945                     base_io = bases[indx];
 946                     
 947                     /* Set the Bus on/off-times as not to ruin floppy performance */
 948             {
 949                     unchar oncmd[] = {CMD_BUSON_TIME, 7};
 950                     unchar offcmd[] = {CMD_BUSOFF_TIME, 5};
 951 
 952                     if(setup_called[indx])
 953                       {
 954                         oncmd[1]  = setup_buson[indx];
 955                         offcmd[1] = setup_busoff[indx];
 956                       }
 957                     
 958                     aha1542_intr_reset(base_io);
 959                     aha1542_out(base_io, oncmd, 2);
 960                     WAIT(INTRFLAGS(base_io), INTRMASK, HACC, 0);
 961                     aha1542_intr_reset(base_io);
 962                     aha1542_out(base_io, offcmd, 2);
 963                     WAIT(INTRFLAGS(base_io), INTRMASK, HACC, 0);
 964                     if (setup_dmaspeed[indx] >= 0)
 965                       {
 966                         unchar dmacmd[] = {CMD_DMASPEED, 0};
 967                         dmacmd[1] = setup_dmaspeed[indx];
 968                         aha1542_intr_reset(base_io);
 969                         aha1542_out(base_io, dmacmd, 2);
 970                         WAIT(INTRFLAGS(base_io), INTRMASK, HACC, 0);
 971                       }
 972                     while (0) {
 973                     fail:
 974                             printk("aha1542_detect: setting bus on/off-time failed\n");
 975                     }
 976                     aha1542_intr_reset(base_io);
 977             }
 978                     if(aha1542_query(base_io, &trans))  goto unregister;
 979                     
 980                     if (aha1542_getconfig(base_io, &irq_level, &dma_chan) == -1)  goto unregister;
 981                     
 982                     printk("Configuring Adaptec at IO:%x, IRQ %d",base_io, irq_level);
 983                     if (dma_chan != 0xFF)
 984                             printk(", DMA priority %d", dma_chan);
 985                     printk("\n");
 986                     
 987                     DEB(aha1542_stat());
 988                     setup_mailboxes(base_io, shpnt);
 989                     
 990                     DEB(aha1542_stat());
 991                     
 992                     DEB(printk("aha1542_detect: enable interrupt channel %d\n", irq_level));
 993                     save_flags(flags);
 994                     cli();
 995                     if (request_irq(irq_level,aha1542_intr_handle, 0, "aha1542")) {
 996                             printk("Unable to allocate IRQ for adaptec controller.\n");
 997                             goto unregister;
 998                     }
 999                     
1000                     if (dma_chan != 0xFF) {
1001                             if (request_dma(dma_chan,"aha1542")) {
1002                                     printk("Unable to allocate DMA channel for Adaptec.\n");
1003                                     free_irq(irq_level);
1004                                     goto unregister;
1005                             }
1006                             
1007                             if (dma_chan >= 5) {
1008                                     outb((dma_chan - 4) | CASCADE, DMA_MODE_REG);
1009                                     outb(dma_chan - 4, DMA_MASK_REG);
1010                             }
1011                     }
1012                     aha_host[irq_level - 9] = shpnt;
1013                     shpnt->io_port = base_io;
1014                     shpnt->n_io_port = 4;  /* Number of bytes of I/O space used */
1015                     shpnt->dma_channel = dma_chan;
1016                     shpnt->irq = irq_level;
1017                     HOSTDATA(shpnt)->bios_translation  = trans;
1018                     if(trans == 2) 
1019                       printk("aha1542.c: Using extended bios translation\n");
1020                     HOSTDATA(shpnt)->aha1542_last_mbi_used  = (2*AHA1542_MAILBOXES - 1);
1021                     HOSTDATA(shpnt)->aha1542_last_mbo_used  = (AHA1542_MAILBOXES - 1);
1022                     memset(HOSTDATA(shpnt)->SCint, 0, sizeof(HOSTDATA(shpnt)->SCint));
1023                     restore_flags(flags);
1024 #if 0
1025                     DEB(printk(" *** READ CAPACITY ***\n"));
1026                     
1027             {
1028                     unchar buf[8];
1029                     static unchar cmd[] = {     READ_CAPACITY, 0, 0, 0, 0, 0, 0, 0, 0, 0};
1030                     int i;
1031                     
1032                     for (i = 0; i < sizeof(buf); ++i) buf[i] = 0x87;
1033                     for (i = 0; i < 2; ++i)
1034                             if (!aha1542_command(i, cmd, buf, sizeof(buf))) {
1035                                     printk("aha_detect: LU %d sector_size %d device_size %d\n",
1036                                            i, xscsi2int(buf+4), xscsi2int(buf));
1037                             }
1038             }
1039                     
1040                     DEB(printk(" *** NOW RUNNING MY OWN TEST *** \n"));
1041                     
1042                     for (i = 0; i < 4; ++i)
1043                     {
1044                             unsigned char cmd[10];
1045                             static buffer[512];
1046                             
1047                             cmd[0] = READ_10;
1048                             cmd[1] = 0;
1049                             xany2scsi(cmd+2, i);
1050                             cmd[6] = 0;
1051                             cmd[7] = 0;
1052                             cmd[8] = 1;
1053                             cmd[9] = 0;
1054                             aha1542_command(0, cmd, buffer, 512);
1055                     }
1056 #endif    
1057                     request_region(bases[indx], 4,"aha1542");  /* Register the IO ports that we use */
1058                     count++;
1059                     continue;
1060             unregister:
1061                     scsi_unregister(shpnt);
1062                     continue;
1063                     
1064             };
1065     return count;
1066 }
1067 
1068 static int aha1542_restart(struct Scsi_Host * shost)
     /* [previous][next][first][last][top][bottom][index][help] */
1069 {
1070   int i;
1071   int count = 0;
1072 #if 0
1073   unchar ahacmd = CMD_START_SCSI;
1074 #endif
1075 
1076   for(i=0; i< AHA1542_MAILBOXES; i++)
1077    if(HOSTDATA(shost)->SCint[i] && 
1078       !(HOSTDATA(shost)->SCint[i]->device->soft_reset))
1079      {
1080 #if 0
1081         HOSTDATA(shost)->mb[i].status = 1; /* Indicate ready to restart... */
1082 #endif
1083         count++;
1084      }     
1085 
1086   printk("Potential to restart %d stalled commands...\n", count);
1087 #if 0
1088   /* start scsi command */
1089   if (count) aha1542_out(shost->io_port, &ahacmd, 1);
1090 #endif
1091   return 0;
1092 }
1093 
1094 /* The abort command does not leave the device in a clean state where
1095    it is available to be used again.  Until this gets worked out, we will
1096    leave it commented out.  */
1097 
1098 int aha1542_abort(Scsi_Cmnd * SCpnt)
     /* [previous][next][first][last][top][bottom][index][help] */
1099 {
1100 #if 0
1101   unchar ahacmd = CMD_START_SCSI;
1102   unsigned long flags;
1103   struct mailbox * mb;
1104   int mbi, mbo, i;
1105 
1106   printk("In aha1542_abort: %x %x\n",
1107          inb(STATUS(SCpnt->host->io_port)),
1108          inb(INTRFLAGS(SCpnt->host->io_port)));
1109 
1110   save_flags(flags);
1111   cli();
1112   mb = HOSTDATA(SCpnt->host)->mb;
1113   mbi = HOSTDATA(SCpnt->host)->aha1542_last_mbi_used + 1;
1114   if (mbi >= 2*AHA1542_MAILBOXES) mbi = AHA1542_MAILBOXES;
1115   
1116   do{
1117     if(mb[mbi].status != 0) break;
1118     mbi++;
1119     if (mbi >= 2*AHA1542_MAILBOXES) mbi = AHA1542_MAILBOXES;
1120   } while (mbi != HOSTDATA(SCpnt->host)->aha1542_last_mbi_used);
1121   restore_flags(flags);
1122 
1123   if(mb[mbi].status) {
1124     printk("Lost interrupt discovered on irq %d - attempting to recover\n", 
1125            SCpnt->host->irq);
1126     aha1542_intr_handle(SCpnt->host->irq, NULL);
1127     return 0;
1128   }
1129 
1130   /* OK, no lost interrupt.  Try looking to see how many pending commands
1131      we think we have. */
1132 
1133   for(i=0; i< AHA1542_MAILBOXES; i++)
1134    if(HOSTDATA(SCpnt->host)->SCint[i])
1135      {
1136        if(HOSTDATA(SCpnt->host)->SCint[i] == SCpnt) {
1137          printk("Timed out command pending for %4.4x\n", SCpnt->request.dev);
1138          if (HOSTDATA(SCpnt->host)->mb[i].status) {
1139            printk("OGMB still full - restarting\n");
1140            aha1542_out(SCpnt->host->io_port, &ahacmd, 1);
1141          };
1142        } else
1143          printk("Other pending command %4.4x\n", SCpnt->request.dev);
1144      }
1145 
1146 #endif
1147 
1148     DEB(printk("aha1542_abort\n"));
1149 #if 0
1150     save_flags(flags);
1151     cli();
1152     for(mbo = 0; mbo < AHA1542_MAILBOXES; mbo++)
1153       if (SCpnt == HOSTDATA(SCpnt->host)->SCint[mbo]){
1154         mb[mbo].status = 2;  /* Abort command */
1155         aha1542_out(SCpnt->host->io_port, &ahacmd, 1); /* start scsi command */
1156         restore_flags(flags);
1157         break;
1158       };
1159 #endif
1160     return SCSI_ABORT_SNOOZE;
1161 }
1162 
1163 /* We do not implement a reset function here, but the upper level code
1164    assumes that it will get some kind of response for the command in
1165    SCpnt.  We must oblige, or the command will hang the scsi system.
1166    For a first go, we assume that the 1542 notifies us with all of the
1167    pending commands (it does implement soft reset, after all). */
1168 
1169 int aha1542_reset(Scsi_Cmnd * SCpnt)
     /* [previous][next][first][last][top][bottom][index][help] */
1170 {
1171     unchar ahacmd = CMD_START_SCSI;
1172     int i;
1173 
1174     DEB(printk("aha1542_reset called\n"));
1175 #if 0
1176     /* This does a scsi reset for all devices on the bus */
1177     outb(SCRST, CONTROL(SCpnt->host->io_port));
1178 #else
1179     /* This does a selective reset of just the one device */
1180     /* First locate the ccb for this command */
1181     for(i=0; i< AHA1542_MAILBOXES; i++)
1182       if(HOSTDATA(SCpnt->host)->SCint[i] == SCpnt)
1183         {
1184           HOSTDATA(SCpnt->host)->ccb[i].op = 0x81;  /* BUS DEVICE RESET */
1185           /* Now tell the 1542 to flush all pending commands for this target */
1186           aha1542_out(SCpnt->host->io_port, &ahacmd, 1);
1187 
1188           /* Here is the tricky part.  What to do next.  Do we get an interrupt
1189              for the commands that we aborted with the specified target, or
1190              do we generate this on our own?  Try it without first and see
1191              what happens */
1192           printk("Sent BUS DEVICE RESET to target %d\n", SCpnt->target);
1193 
1194           /* If the first does not work, then try the second.  I think the
1195              first option is more likely to be correct. Free the command
1196              block for all commands running on this target... */
1197 #if 1
1198           for(i=0; i< AHA1542_MAILBOXES; i++)
1199             if(HOSTDATA(SCpnt->host)->SCint[i] &&
1200                HOSTDATA(SCpnt->host)->SCint[i]->target == SCpnt->target)
1201             {
1202               Scsi_Cmnd * SCtmp;
1203               SCtmp = HOSTDATA(SCpnt->host)->SCint[i];
1204               SCtmp->result = DID_RESET << 16;
1205               if (SCtmp->host_scribble) scsi_free(SCtmp->host_scribble, 512);
1206               printk("Sending DID_RESET for target %d\n", SCpnt->target);
1207               SCtmp->scsi_done(SCpnt);
1208               
1209               HOSTDATA(SCpnt->host)->SCint[i] = NULL;
1210               HOSTDATA(SCpnt->host)->mb[i].status = 0;
1211             }
1212           return SCSI_RESET_SUCCESS;
1213 #else
1214           return SCSI_RESET_PENDING;
1215 #endif
1216         }
1217 
1218 #endif
1219     /* No active command at this time, so this means that each time we got
1220        some kind of response the last time through.  Tell the mid-level code
1221        to request sense information in order to decide what to do next. */
1222     return SCSI_RESET_PUNT;
1223 }
1224 
1225 #include "sd.h"
1226 
1227 int aha1542_biosparam(Scsi_Disk * disk, int dev, int * ip)
     /* [previous][next][first][last][top][bottom][index][help] */
1228 {
1229   int translation_algorithm;
1230   int size = disk->capacity;
1231 
1232   translation_algorithm = HOSTDATA(disk->device->host)->bios_translation;
1233   /* Should this be > 1024, or >= 1024?  Enquiring minds want to know. */
1234   if((size>>11) > 1024 && translation_algorithm == 2) {
1235     /* Please verify that this is the same as what DOS returns */
1236     ip[0] = 255;
1237     ip[1] = 63;
1238     ip[2] = size /255/63;
1239   } else {
1240     ip[0] = 64;
1241     ip[1] = 32;
1242     ip[2] = size >> 11;
1243   };
1244 /*  if (ip[2] >= 1024) ip[2] = 1024; */
1245   return 0;
1246 }
1247 
1248 
1249 #ifdef MODULE
1250 /* Eventually this will go into an include file, but this will be later */
1251 Scsi_Host_Template driver_template = AHA1542;
1252 
1253 #include "scsi_module.c"
1254 #endif
1255 

/* [previous][next][first][last][top][bottom][index][help] */