Index: README.tmscsim =================================================================== RCS file: /usr/local/cvsroot/dc390/README.tmscsim,v retrieving revision 2.24 retrieving revision 2.25 diff -u -r2.24 -r2.25 --- README.tmscsim 1999/07/18 12:00:41 2.24 +++ README.tmscsim 1999/08/26 19:48:56 2.25 @@ -60,7 +60,8 @@ If you got an old kernel (pre 2.1.127, pre 2.0.37p1) with an old version of this driver: Get dc390-21125-20b.diff.gz or dc390-2036p21-20b1.diff.gz from - my website and apply the patch. + my web page and apply the patch. Apply further patches to upgrade to the + latest version of the driver. If you want to do it manually, you should copy the files (dc390.h, tmscsim.h, tmscsim.c, scsiiom.c and README.tmscsim) from this directory to @@ -124,7 +125,7 @@ * Dynamically configurable by writing to /proc/scsi/tmscsim/? * Dynamic allocation of resources * SMP support: Locking on io_request lock (Linux 2.1/2.2) or adapter - specific locks (Linux 2.3) + specific locks (Linux 2.5?) * Uniform source code for Linux-2.x.y * Support for dyn. addition/removal of devices via add/remove-single-device (Try: echo "scsi add-single-device C B T U" >/proc/scsi/scsi @@ -143,8 +144,8 @@ the attached devices and their settings. Here's an example: -garloff@kg1:/home/garloff > cat /proc/scsi/tmscsim/0 -Tekram DC390/AM53C974 PCI SCSI Host Adapter, Driver Version 2.0d17 1999/07/16 +garloff@kurt:/home/garloff > cat /proc/scsi/tmscsim/0 +Tekram DC390/AM53C974 PCI SCSI Host Adapter, Driver Version 2.0e 1999/08/30 SCSI Host Nr 1, AM53C974 Adapter Nr 0 IOPortBase 0xb000, IRQ 10 MaxID 8, MaxLUN 8, AdapterID 6, SelTimeout 250 ms, DelayReset 1 s @@ -346,7 +347,7 @@ * Cleanly separate per-Target and per-LUN properties (DCB) * More intelligent abort() routine -* Implement new_eh code (Linux-2.1+) +* Use new_eh code (Linux-2.1+) * Have the mid-level (ML) code (and not the driver) handle more of the various conditions. * Command queueing in the driver: Eliminate Query list and use ML instead. @@ -361,33 +362,29 @@ * Changing the parameters of multi-lun by the tmscsim/? interface will cause problems, cause these settings are mostly per Target and not per LUN - and should be updated accordingly. + and should be updated accordingly. To be fixed for 2.0d24. * CDRs (eg Yam CRW4416) not recognized, because some buggy devices don't - recover from a SCSI reset in time. See problems page. + recover from a SCSI reset in time. Use a higher delay or don't issue + a SCSI bus reset on driver initialization. See problems page. + For the CRW4416S, this seems to be solved with firmware 1.0g (reported by + Jean-Yves Barbier). * Scanners (eg. Astra UMAX 1220S) don't work: Disable Sync Negotiation. If this does not help, try echo "INQUIRY t" >/proc/scsi/tmscsim/? (t replaced by the dev index of your scanner). You may try to reset your SCSI bus afterwards (echo "RESET" >/proc/scsi/tmscsim/?). The problem seems to be solved as of 2.0d18, thanks to Andreas Rick. * If there is a valid partition table, the driver will use it for determing - the mapping. Other operating systems may not like this mapping, though + the mapping. If there's none, a reasonable mapping (Symbios-like) will be + assumed. Other operating systems may not like this mapping, though it's consistent with the BIOS' behaviour. Old DC390 drivers ignored the partition table and used a H/S = 64/32 or 255/63 translation. So if you want to be compatible to those, use this old mapping when creating partition tables. Even worse, on bootup the DC390 might complain if other mappings are found, so auto rebooting will fail. -* In some situations, the driver will get stuck in an abort loop. Please - disable DsCn, if you meet this problem. Please contact me for further - debugging. -* 2.1.115+: Linux misses locks in sr_ioctl.c and scsi_ioctl.c - There used to be a patch included here, which partially solved the - problem. I suggest you contact Chiaki Ishikawa , - Richard Waltham or Doug Ledford - , if you want to help further debugging it. -* 2.0.35: CD changers (e.g. NAKAMICHI MBR-7.{0,2}) have problems because - the mid-level code doesn't handle BLIST_SINGLELUN correctly. There used - to be a patch included here to fix this, but I was told that it is fixed - in 2.0.36. +* In some situations, the driver will get stuck in an abort loop. This is a + bad interaction between the Mid-Layer of Linux' SCSI code and the driver. + Try to disable DsCn, if you meet this problem. Please contact me for + further debugging. 7. Bug reports, debugging and updates @@ -417,9 +414,8 @@ 8. Acknowledgements ------------------- -Thanks to Linus Torvalds, Alan Cox, David Miller, Rik v. Riel, the FSF -people, the XFree86 team and all the others for the wonderful OS and -software. +Thanks to Linus Torvalds, Alan Cox, David Miller, the FSF people, the +XFree86 team and all the others for the wonderful OS and software. Thanks to C.L. Huang and Philip Giang (Tekram) for the initial driver release and support. Thanks to Doug Ledford, Gerard Roudier for support with SCSI coding. @@ -441,5 +437,5 @@ ------------------------------------------------------------------------- Written by Kurt Garloff 1998/06/11 -Last updated 1999/07/18, driver revision 2.0d18 -$Id: README.tmscsim,v 2.24 1999/07/18 12:00:41 garloff Exp $ +Last updated 1999/08/26, driver revision 2.0e +$Id: README.tmscsim,v 2.25 1999/08/26 19:48:56 garloff Exp $ Index: dc390.h =================================================================== RCS file: /usr/local/cvsroot/dc390/dc390.h,v retrieving revision 2.41 retrieving revision 2.43 diff -u -r2.41 -r2.43 --- dc390.h 1999/08/15 15:47:31 2.41 +++ dc390.h 1999/08/26 19:48:56 2.43 @@ -4,7 +4,7 @@ * Description: Device Driver for Tekram DC-390(T) PCI SCSI * * Bus Master Host Adapter * ***********************************************************************/ -/* $Id: dc390.h,v 2.41 1999/08/15 15:47:31 garloff Exp $ */ +/* $Id: dc390.h,v 2.43 1999/08/26 19:48:56 garloff Exp $ */ /* * DC390/AMD 53C974 driver, header file @@ -19,7 +19,7 @@ #endif #define DC390_BANNER "Tekram DC390/AM53C974" -#define DC390_VERSION "2.0d21 1999/08/15" +#define DC390_VERSION "2.0d23 1999/08/26" #if defined(HOSTS_C) || defined(MODULE) @@ -54,7 +54,7 @@ abort: DC390_abort, \ reset: DC390_reset, \ bios_param: DC390_bios_param, \ - can_queue: 17, \ + can_queue: 42, \ this_id: 7, \ sg_tablesize: SG_ALL, \ cmd_per_lun: 8, \ Index: scsiiom.c =================================================================== RCS file: /usr/local/cvsroot/dc390/scsiiom.c,v retrieving revision 2.51 diff -u -r2.51 scsiiom.c --- scsiiom.c 1999/08/15 15:47:31 2.51 +++ scsiiom.c 1999/08/28 15:22:03 @@ -4,7 +4,7 @@ * Description: Device Driver for Tekram DC-390 (T) PCI SCSI * * Bus Master Host Adapter * ***********************************************************************/ -/* $Id: scsiiom.c,v 2.51 1999/08/15 15:47:31 garloff Exp $ */ +/* $Id: scsiiom.c,v 2.55 1999/08/28 10:57:34 garloff Exp $ */ static void __inline__ dc390_freetag (PDCB pDCB, PSRB pSRB) @@ -209,49 +209,34 @@ void __inline__ DC390_Interrupt( int irq, void *dev_id, struct pt_regs *regs) { - PACB pACB; + PACB pACB, pACB2; PDCB pDCB; PSRB pSRB; UCHAR sstatus=0; - UCHAR phase, i; + UCHAR phase; void (*stateV)( PACB, PSRB, PUCHAR ); UCHAR istate, istatus; #if DMA_INT UCHAR dstatus; #endif - DC390_AFLAGS DC390_IFLAGS DC390_DFLAGS + DC390_AFLAGS DC390_IFLAGS //DC390_DFLAGS - pACB = dc390_pACB_start; - - if (pACB == 0) + pACB = (PACB)dev_id; + for (pACB2 = dc390_pACB_start; (pACB2 && pACB2 != pACB); pACB2 = pACB2->pNextACB); + if (!pACB2) { - printk(KERN_WARNING "DC390: Interrupt on uninitialized adapter!\n"); + printk ("DC390: IRQ called with foreign dev_id %p!\n", pACB); return; } - DC390_ASSUMELOCK (dc390_drvlock, 0, "scsiiom.c:Interrupt 221, drv"); - DC390_LOCK_DRV; + //DC390_LOCK_DRV; - for( i=0; i < dc390_adapterCnt; i++ ) - { - if( pACB->IRQLevel == (UCHAR) irq ) - { - sstatus = DC390_read8 (Scsi_Status); - if( sstatus & INTERRUPT ) - break; - else - pACB = pACB->pNextACB; - } - else - { - pACB = pACB->pNextACB; - } - } + sstatus = DC390_read8 (Scsi_Status); + if( !(sstatus & INTERRUPT) ) + { /*DC390_UNLOCK_DRV;*/ return; }; DEBUG1(printk (KERN_DEBUG "sstatus=%02x,", sstatus);) - if( !pACB ) { DC390_UNLOCK_DRV; return; }; - #if DMA_INT DC390_LOCK_IO; DC390_LOCK_ACB; @@ -263,7 +248,7 @@ if (! (dstatus & SCSI_INTERRUPT)) { DEBUG0(printk (KERN_WARNING "DC390 Int w/o SCSI actions (only DMA?)\n");) - DC390_UNLOCK_DRV; + //DC390_UNLOCK_DRV; return; }; #else @@ -272,11 +257,9 @@ //DC390_write32 (DMA_ScsiBusCtrl, EN_INT_ON_PCI_ABORT); #endif - //DC390_ASSUMELOCK (io_request_lock, 0, "scsiiom.c:Interrupt 264, io"); - //DC390_ASSUMELOCK (pACB->lock, 0, "scsiiom.c:Interrupt 265, acb"); DC390_LOCK_IO; DC390_LOCK_ACB; - DC390_UNLOCK_DRV_NI; /* Allow _other_ CPUs to process IRQ (useful for shared IRQs) */ + //DC390_UNLOCK_DRV_NI; /* Allow _other_ CPUs to process IRQ (useful for shared IRQs) */ istate = DC390_read8 (Intern_State); istatus = DC390_read8 (INT_Status); /* This clears Scsi_Status, Intern_State and INT_Status ! */ @@ -293,6 +276,7 @@ else if (istatus & INVALID_CMD) { + printk ("DC390: Invalid Command detected (%08x)!\n", dc390_laststatus); dc390_InvalidCmd( pACB ); goto unlock; } @@ -347,10 +331,10 @@ } unlock: - DC390_LOCK_DRV_NI; + //DC390_LOCK_DRV_NI; DC390_UNLOCK_ACB; DC390_UNLOCK_IO; - DC390_UNLOCK_DRV; /* Restore initial flags */ + //DC390_UNLOCK_DRV; /* Restore initial flags */ } void Index: tmscsim.c =================================================================== RCS file: /usr/local/cvsroot/dc390/tmscsim.c,v retrieving revision 2.55 retrieving revision 2.60 diff -u -r2.55 -r2.60 --- tmscsim.c 1999/08/15 15:47:31 2.55 +++ tmscsim.c 1999/08/26 20:14:02 2.60 @@ -7,7 +7,7 @@ ***********************************************************************/ /* (C) Copyright: put under GNU GPL in 10/96 (see README.tmscsim) * *************************************************************************/ -/* $Id: tmscsim.c,v 2.55 1999/08/15 15:47:31 garloff Exp $ */ +/* $Id: tmscsim.c,v 2.60 1999/08/26 20:14:02 garloff Exp $ */ /* Enhancements and bugfixes by * * Kurt Garloff * ***********************************************************************/ @@ -135,6 +135,9 @@ * 2.0d2199/08/15 KG dev_id for request/free_irq, cmnd[0] for* * RETRY, SRBdone does DID_ABORT for the * * cmd passed by DC390_reset() * + * 2.0d2299/08/25 KG dev_id fixed. can_queue: 42 * + * 2.0d2399/08/25 KG Removed some debugging code. dev_id * + * now is set to pACB. Use u8,u16,u32. * ***********************************************************************/ /* Uncomment SA_INTERRUPT, if the driver refuses to share its IRQ with other devices */ @@ -176,14 +179,6 @@ #endif #define DCBDEBUG1(x) -#ifdef DC390_LOCKDEBUG -# define DC390_ASSUMELOCK(x,y,z) if (x.lock != y) { \ - printk (KERN_CRIT "DC390: (%s): Lock %p in unexpected state %i (exp: %i)!!\n", z, &x, x.lock, y); \ -} -#else -# define DC390_ASSUMELOCK(x,y,z) -#endif - /* Includes */ #ifdef MODULE # include @@ -222,8 +217,7 @@ /* Note: Starting from 2.1.9x, the mid-level scsi code issues a * spinlock_irqsave (&io_request_lock) before calling the driver's - * routines, so we don't need to lock. - * TODO: Verify, if we are locked in every case! + * routines, so we don't need to lock, except in the IRQ handler. * The policy 3, let the midlevel scsi code do the io_request_locks * and us locking on a driver specific lock, shouldn't hurt anybody; it * just causes a minor performance degradation for setting the locks. @@ -762,6 +756,22 @@ */ +#if 0 +/* Look for a SCSI cmd in a SRB queue */ +static PSRB dc390_find_cmd_in_SRBq (PSCSICMD cmd, PSRB queue) +{ + PSRB q = queue; + while (q) + { + if (q->pcmd == cmd) return q; + q = q->pNextSRB; + if (q == queue) return 0; + } + return q; +}; +#endif + + /* Append to Query List */ static void dc390_Query_append( PSCSICMD cmd, PACB pACB ) { @@ -1083,8 +1093,6 @@ printk(KERN_INFO "DC390: Queue Cmd=%02x,ID=%d,LUN=%d (pid=%li)\n",\ cmd->cmnd[0],cmd->target,cmd->lun,cmd->pid);) - DC390_ASSUMELOCK (io_request_lock, 1, "tmscsim.c:queue 1072, io"); - //DC390_ASSUMELOCK (pACB->lock, 0, "tmscsim.c:queue 1073, acb"); DC390_LOCK_ACB; /* Assume BAD_TARGET; will be cleared later */ @@ -1384,8 +1392,6 @@ DC390_AFLAGS PACB pACB = (PACB) cmd->host->hostdata; - DC390_ASSUMELOCK (io_request_lock, 1, "tmscsim.c:abort 1373, io"); - //DC390_ASSUMELOCK (pACB->lock, 0, "tmscsim.c:abort 1374, acb"); DC390_LOCK_ACB; printk ("DC390: Abort command (pid %li, Device %02i-%02i)\n", @@ -1622,8 +1628,6 @@ printk(KERN_INFO "DC390: RESET ... "); - DC390_ASSUMELOCK (io_request_lock, 1, "tmscsim.c:reset 1610, io"); - //DC390_ASSUMELOCK (pACB->lock, 0, "tmscsim.c:reset 1611, acb"); DC390_LOCK_ACB; bval = DC390_read8 (CtrlReg1); bval |= DIS_INT_ON_SCSI_RST; @@ -1674,8 +1678,9 @@ UCHAR index; PDCB pDCB, pDCB2; + /* TODO: kmalloc wastes resources, as it allocates a page at least */ pDCB = kmalloc (sizeof(DC390_DCB), GFP_ATOMIC); - DCBDEBUG(printk (KERN_INFO "DC390: alloc mem for DCB (ID %i, LUN %i): %p\n", \ + DCBDEBUG(printk (KERN_INFO "DC390: alloc mem for DCB (ID %i, LUN %i): %p\n" \ id, lun, pDCB);) *ppDCB = pDCB; pDCB2 = 0; @@ -1907,22 +1912,11 @@ int __init dc390_initAdapter (PSH psh, ULONG io_port, UCHAR Irq, UCHAR index) { PACB pACB, pACB2; - UCHAR used_irq = 0, dstate; + UCHAR dstate; int i; pACB = (PACB) psh->hostdata; - for ( pACB2 = dc390_pACB_start; pACB2 ; ) - { - if( pACB2->IRQLevel == Irq ) - { - used_irq = 1; - break; - } - else - pACB2 = pACB2->pNextACB; - } - if (check_region (io_port, psh->n_io_port)) { printk(KERN_ERR "DC390: register IO ports error!\n"); @@ -1933,14 +1927,11 @@ DC390_read8_ (INT_Status, io_port); /* Reset Pending INT */ - if( !used_irq ) - { - if( (i = request_irq(Irq, do_DC390_Interrupt, DC390_IRQ, "tmscsim", pACB) )) - { - printk(KERN_ERR "DC390: register IRQ error!\n"); - return( -1 ); - } - } + if( (i = request_irq(Irq, do_DC390_Interrupt, DC390_IRQ, "tmscsim", pACB) )) + { + printk(KERN_ERR "DC390: register IRQ error!\n"); + return( -1 ); + } if( !dc390_pACB_start ) { @@ -2134,9 +2125,6 @@ UINT io_port; DC390_IFLAGS DC390_DFLAGS - DC390_ASSUMELOCK (io_request_lock, 0, "tmscsim.c:detect 2121, io"); - DC390_ASSUMELOCK (dc390_drvlock, 0, "tmscsim.c:detect 2122, drv"); - DC390_LOCK_DRV; //dc390_pSHT_start = psht; dc390_pACB_start = NULL; @@ -2191,7 +2179,6 @@ dc390_updateDCB (pACB, pDCB); }; }; - kfree (cmd->buffer); kfree (cmd); }; @@ -2199,13 +2186,11 @@ { char* buffer; Scsi_Cmnd* cmd; - buffer = kmalloc (256, GFP_ATOMIC); - if (!buffer) { printk ("DC390: kmalloc (buffer) failed!\n"); return; }; - cmd = kmalloc (sizeof (Scsi_Cmnd), GFP_ATOMIC); - if (!cmd) { printk ("DC390: kmalloc (cmd) failed!\n"); kfree (buffer); return; }; + cmd = kmalloc (sizeof(Scsi_Cmnd) + 256, GFP_ATOMIC); + if (!cmd) { printk ("DC390: kmalloc failed in inquiry!\n"); return; }; + buffer = (char*)cmd + sizeof(Scsi_Cmnd); - memset (buffer, 0, 256); - memset (cmd, 0, sizeof(Scsi_Cmnd)); + memset (cmd, 0, sizeof(Scsi_Cmnd) + 256); cmd->cmnd[0] = INQUIRY; cmd->cmnd[1] = (pDCB->UnitSCSILUN << 5) & 0xe0; cmd->cmnd[4] = 0xff; @@ -2330,8 +2315,6 @@ DC390_AFLAGS pos[length] = 0; - DC390_ASSUMELOCK (io_request_lock, 0, "tmscsim.c:set_info 2317, io"); - //DC390_ASSUMELOCK (pACB->lock, 0, "tmscsim.c:set_info 2318, acb"); DC390_LOCK_IO; DC390_LOCK_ACB; /* UPPERCASE */ @@ -2626,8 +2609,6 @@ SPRINTF("Tekram DC390/AM53C974 PCI SCSI Host Adapter, "); SPRINTF("Driver Version %s\n", DC390_VERSION); - DC390_ASSUMELOCK (io_request_lock, 0, "tmscsim.c:proc_info 2605, io"); - //DC390_ASSUMELOCK (pACB->lock, 0, "tmscsim.c:proc_info 2606, acb"); DC390_LOCK_ACB; SPRINTF("SCSI Host Nr %i, ", shpnt->host_no); @@ -2742,15 +2723,9 @@ int DC390_release(struct Scsi_Host *host) { - int irq_count; - PACB pACB; DC390_AFLAGS DC390_IFLAGS -#if USE_SPINLOCKS > 1 PACB pACB = (PACB)(host->hostdata); -#endif - DC390_ASSUMELOCK (io_request_lock, 0, "tmscsim.c:release 2728, io"); - //DC390_ASSUMELOCK (pACB->lock, 0, "tmscsim.c:release 2729, acb"); DC390_LOCK_IO; DC390_LOCK_ACB; @@ -2759,17 +2734,8 @@ if (host->irq != IRQ_NONE) { - for (irq_count = 0, pACB = dc390_pACB_start; - pACB; pACB = pACB->pNextACB) - { - if ( pACB->IRQLevel == host->irq ) - ++irq_count; - } - if (irq_count == 1) - { - DEBUG0(printk(KERN_INFO "DC390: Free IRQ %i\n",host->irq);) - free_irq(host->irq, pACB); - } + DEBUG0(printk(KERN_INFO "DC390: Free IRQ %i\n",host->irq);) + free_irq (host->irq, pACB); } release_region(host->io_port,host->n_io_port); Index: tmscsim.h =================================================================== RCS file: /usr/local/cvsroot/dc390/tmscsim.h,v retrieving revision 2.14 retrieving revision 2.15 diff -u -r2.14 -r2.15 --- tmscsim.h 1999/07/16 08:23:03 2.14 +++ tmscsim.h 1999/08/26 19:48:57 2.15 @@ -3,11 +3,13 @@ ;* TEKRAM DC-390(T) PCI SCSI Bus Master Host Adapter * ;* Device Driver * ;***********************************************************************/ -/* $Id: tmscsim.h,v 2.14 1999/07/16 08:23:03 garloff Exp $ */ +/* $Id: tmscsim.h,v 2.15 1999/08/26 19:48:57 garloff Exp $ */ #ifndef _TMSCSIM_H #define _TMSCSIM_H +#include + #define IRQ_NONE 255 #define MAX_ADAPTER_NUM 4 @@ -21,9 +23,9 @@ #define END_SCAN 2 -typedef unsigned char UCHAR; /* 8 bits */ -typedef unsigned short USHORT; /* 16 bits */ -typedef unsigned int UINT; /* 32 bits */ +typedef u8 UCHAR; /* 8 bits */ +typedef u16 USHORT; /* 16 bits */ +typedef u32 UINT; /* 32 bits */ typedef unsigned long ULONG; /* 32/64 bits */ typedef UCHAR *PUCHAR; @@ -172,7 +174,7 @@ /* 0x30:*/ //UCHAR InqDataBuf[8]; //UCHAR CapacityBuf[8]; -/* 0x40: */ +///* 0x40: */ }; typedef struct _DCB DC390_DCB, *PDCB;