16 #include <linux/types.h>
17 #include <linux/stddef.h>
18 #include <linux/ctype.h>
21 #include <linux/module.h>
22 #include <linux/signal.h>
31 #include <asm/idprom.h>
32 #include <asm/machines.h>
36 #undef SUN3_SCSI_DEBUG
43 #define NDEBUG_ABORT 0x00100000
44 #define NDEBUG_TAGS 0x00200000
45 #define NDEBUG_MERGING 0x00400000
73 static inline unsigned char sun3scsi_read(
int reg);
74 static inline void sun3scsi_write(
int reg,
int value);
76 static int setup_can_queue = -1;
78 static int setup_cmd_per_lun = -1;
80 static int setup_sg_tablesize = -1;
83 static int setup_use_tagged_queuing = -1;
86 static int setup_hostid = -1;
91 #define AFTER_RESET_DELAY (HZ/2)
94 #define SUN3_DMA_DELAY 10
97 #define SUN3_DVMA_BUFSIZE 0xe000
100 #define SUN3_DMA_MINSIZE 128
102 static volatile unsigned char *sun3_scsi_regp;
105 static unsigned char *dmabuf =
NULL;
107 static unsigned char *sun3_dma_orig_addr =
NULL;
108 static unsigned long sun3_dma_orig_count = 0;
109 static int sun3_dma_active = 0;
110 static unsigned long last_residual = 0;
116 static inline unsigned char sun3scsi_read(
int reg)
118 return( sun3_scsi_regp[reg] );
121 static inline void sun3scsi_write(
int reg,
int value)
129 static struct Scsi_Host *default_instance;
145 unsigned long ioaddr,
irq = 0;
146 static int called = 0;
172 (setup_can_queue > 0) ? setup_can_queue :
CAN_QUEUE;
174 (setup_cmd_per_lun > 0) ? setup_cmd_per_lun :
CMD_PER_LUN;
176 (setup_sg_tablesize >= 0) ? setup_sg_tablesize :
SG_TABLESIZE;
178 if (setup_hostid >= 0)
186 for(i = 0; addrs[
i] != 0; i++) {
192 sun3_scsi_regp = (
unsigned char *)ioaddr;
194 dregs = (
struct sun3_dma_regs *)(((
unsigned char *)ioaddr) + 8);
197 unsigned short oldcsr;
202 if(dregs->
csr == 0x1400)
216 if (setup_use_tagged_queuing < 0)
224 default_instance = instance;
229 NCR5380_init(instance, 0);
236 0,
"Sun3SCSI-5380VME", instance)) {
238 printk(
"scsi%d: IRQ%d not free, interrupts disabled\n",
242 printk(
"scsi%d: IRQ%d not free, bailing out\n",
253 printk(
" options CAN_QUEUE=%d CMD_PER_LUN=%d release=%d",
257 NCR5380_print_options(instance);
276 sun3_scsi_reset_boot(instance);
287 iounmap((
void *)sun3_scsi_regp);
298 static void sun3_scsi_reset_boot(
struct Scsi_Host *instance)
310 printk(
"Sun3 SCSI: resetting the SCSI bus..." );
344 #define CSR_GOOD 0x060f
348 unsigned short csr = dregs->
csr;
354 #ifdef SUN3_SCSI_DEBUG
355 printk(
"scsi_intr csr %x\n", csr);
360 printk(
"scsi%d: bus error in dma\n", default_instance->
host_no);
361 #ifdef SUN3_SCSI_DEBUG
362 printk(
"scsi: residual %x count %x addr %p dmaaddr %x\n",
391 void sun3_sun3_debug (
void)
396 if (default_instance) {
398 NCR5380_print_status(default_instance);
406 static unsigned long sun3scsi_dma_setup(
void *
data,
unsigned long count,
int write_flag)
410 if(sun3_dma_orig_addr !=
NULL)
416 sun3_dma_orig_addr =
addr;
417 sun3_dma_orig_count =
count;
419 #ifdef SUN3_SCSI_DEBUG
420 printk(
"scsi: dma_setup addr %p count %x\n", addr, count);
449 #ifdef SUN3_SCSI_DEBUG
450 printk(
"scsi: dma_setup done csr %x\n", dregs->
csr);
456 static inline unsigned long sun3scsi_dma_residual(
struct Scsi_Host *instance)
458 return last_residual;
461 static inline unsigned long sun3scsi_dma_xfer_len(
unsigned long wanted,
465 if (cmd->
request->cmd_type == REQ_TYPE_FS)
471 static int sun3scsi_dma_start(
unsigned long count,
char *data)
477 #ifdef SUN3_SCSI_DEBUG
478 printk(
"scsi: dma_start data %p count %x csr %x fifo %x\n", data, count, csr, dregs->
fifo_count);
485 dregs->
fifo_count = (sun3_dma_orig_count & 0xffff);
494 static int sun3scsi_dma_finish(
int write_flag)
505 if((fifo > 0) && (fifo < sun3_dma_orig_count))
509 last_residual = fifo;
510 #ifdef SUN3_SCSI_DEBUG
511 printk(
"scsi: residual %x total %x\n", fifo, sun3_dma_orig_count);
515 unsigned char *
vaddr;
517 #ifdef SUN3_SCSI_DEBUG
518 printk(
"scsi: got left over bytes\n");
521 vaddr = (
unsigned char *)dvma_vmetov(sun3_dma_orig_addr);
523 vaddr += (sun3_dma_orig_count - fifo);
528 *vaddr = (dregs->
bpack_lo & 0xff00) >> 8;
532 *vaddr = (dregs->
bpack_hi & 0x00ff);
536 *vaddr = (dregs->
bpack_hi & 0xff00) >> 8;
544 sun3_dma_orig_addr =
NULL;
563 sun3_dma_setup_done =
NULL;
576 .queuecommand = sun3scsi_queue_command,
577 .eh_abort_handler = sun3scsi_abort,
578 .eh_bus_reset_handler = sun3scsi_bus_reset,