1 /* fd_mcs.c -- Future Domain MCS 600/700 (or IBM OEM) driver
2  *
3  * FutureDomain MCS-600/700 v0.2 03/11/1998 by ZP Gu (zpg@castle.net)
4  *
5  * This driver is cloned from fdomain.* to specifically support
6  * the Future Domain MCS 600/700 MCA SCSI adapters. Some PS/2s
7  * also equipped with IBM Fast SCSI Adapter/A which is an OEM
8  * of MCS 700.
9  *
10  * This driver also supports Reply SB16/SCSI card (the SCSI part).
11  *
12  * What makes this driver different is that this driver is MCA only
13  * and it supports multiple adapters in the same system, IRQ
14  * sharing, some driver statistics, and maps highest SCSI id to sda.
15  * All cards are auto-detected.
16  *
17  * Assumptions: TMC-1800/18C50/18C30, BIOS >= 3.4
18  *
19  * LILO command-line options:
20  *   fd_mcs=<FIFO_COUNT>[,<FIFO_SIZE>]
21  *
22  * ********************************************************
23  * Please see Copyrights/Comments in fdomain.* for credits.
24  * Following is from fdomain.c for acknowledgement:
25  *
26  * Created: Sun May  3 18:53:19 1992 by faith@cs.unc.edu
27  * Revised: Wed Oct  2 11:10:55 1996 by r.faith@ieee.org
28  * Author: Rickard E. Faith, faith@cs.unc.edu
29  * Copyright 1992, 1993, 1994, 1995, 1996 Rickard E. Faith
30  *
31  * $Id: fdomain.c,v 5.45 1996/10/02 15:13:06 root Exp $
32 
33  * This program is free software; you can redistribute it and/or modify it
34  * under the terms of the GNU General Public License as published by the
35  * Free Software Foundation; either version 2, or (at your option) any
36  * later version.
37 
38  * This program is distributed in the hope that it will be useful, but
39  * WITHOUT ANY WARRANTY; without even the implied warranty of
40  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
41  * General Public License for more details.
42 
43  * You should have received a copy of the GNU General Public License along
44  * with this program; if not, write to the Free Software Foundation, Inc.,
45  * 675 Mass Ave, Cambridge, MA 02139, USA.
46 
47  **************************************************************************
48 
49  NOTES ON USER DEFINABLE OPTIONS:
50 
51  DEBUG: This turns on the printing of various debug information.
52 
53  ENABLE_PARITY: This turns on SCSI parity checking.  With the current
54  driver, all attached devices must support SCSI parity.  If none of your
55  devices support parity, then you can probably get the driver to work by
56  turning this option off.  I have no way of testing this, however, and it
57  would appear that no one ever uses this option.
58 
59  FIFO_COUNT: The host adapter has an 8K cache (host adapters based on the
60  18C30 chip have a 2k cache).  When this many 512 byte blocks are filled by
61  the SCSI device, an interrupt will be raised.  Therefore, this could be as
62  low as 0, or as high as 16.  Note, however, that values which are too high
63  or too low seem to prevent any interrupts from occurring, and thereby lock
64  up the machine.  I have found that 2 is a good number, but throughput may
65  be increased by changing this value to values which are close to 2.
66  Please let me know if you try any different values.
67  [*****Now a runtime option*****]
68 
69  RESELECTION: This is no longer an option, since I gave up trying to
70  implement it in version 4.x of this driver.  It did not improve
71  performance at all and made the driver unstable (because I never found one
72  of the two race conditions which were introduced by the multiple
73  outstanding command code).  The instability seems a very high price to pay
74  just so that you don't have to wait for the tape to rewind.  If you want
75  this feature implemented, send me patches.  I'll be happy to send a copy
76  of my (broken) driver to anyone who would like to see a copy.
77 
78  **************************************************************************/
79 
80 #include <linux/module.h>
81 #include <linux/init.h>
82 #include <linux/interrupt.h>
83 #include <linux/blkdev.h>
84 #include <linux/errno.h>
85 #include <linux/string.h>
86 #include <linux/ioport.h>
87 #include <linux/proc_fs.h>
88 #include <linux/delay.h>
89 #include <linux/mca.h>
90 #include <linux/spinlock.h>
91 #include <linux/slab.h>
92 #include <scsi/scsicam.h>
93 #include <linux/mca-legacy.h>
94 
95 #include <asm/io.h>
96 #include <asm/system.h>
97 
98 #include "scsi.h"
99 #include <scsi/scsi_host.h>
100 
101 #define DRIVER_VERSION "v0.2 by ZP Gu<zpg@castle.net>"
102 
103 /* START OF USER DEFINABLE OPTIONS */
104 
105 #define DEBUG            0	/* Enable debugging output */
106 #define ENABLE_PARITY    1	/* Enable SCSI Parity */
107 
108 /* END OF USER DEFINABLE OPTIONS */
109 
110 #if DEBUG
111 #define EVERY_ACCESS     0	/* Write a line on every scsi access */
112 #define ERRORS_ONLY      1	/* Only write a line if there is an error */
113 #define DEBUG_MESSAGES   1	/* Debug MESSAGE IN phase */
114 #define DEBUG_ABORT      1	/* Debug abort() routine */
115 #define DEBUG_RESET      1	/* Debug reset() routine */
116 #define DEBUG_RACE       1	/* Debug interrupt-driven race condition */
117 #else
118 #define EVERY_ACCESS     0	/* LEAVE THESE ALONE--CHANGE THE ONES ABOVE */
119 #define ERRORS_ONLY      0
120 #define DEBUG_MESSAGES   0
121 #define DEBUG_ABORT      0
122 #define DEBUG_RESET      0
123 #define DEBUG_RACE       0
124 #endif
125 
126 /* Errors are reported on the line, so we don't need to report them again */
127 #if EVERY_ACCESS
128 #undef ERRORS_ONLY
129 #define ERRORS_ONLY      0
130 #endif
131 
132 #if ENABLE_PARITY
133 #define PARITY_MASK      0x08
134 #else
135 #define PARITY_MASK      0x00
136 #endif
137 
138 enum chip_type {
139 	unknown = 0x00,
140 	tmc1800 = 0x01,
141 	tmc18c50 = 0x02,
142 	tmc18c30 = 0x03,
143 };
144 
145 enum {
146 	in_arbitration = 0x02,
147 	in_selection = 0x04,
148 	in_other = 0x08,
149 	disconnect = 0x10,
150 	aborted = 0x20,
151 	sent_ident = 0x40,
152 };
153 
154 enum in_port_type {
155 	Read_SCSI_Data = 0,
156 	SCSI_Status = 1,
157 	TMC_Status = 2,
158 	FIFO_Status = 3,	/* tmc18c50/tmc18c30 only */
159 	Interrupt_Cond = 4,	/* tmc18c50/tmc18c30 only */
160 	LSB_ID_Code = 5,
161 	MSB_ID_Code = 6,
162 	Read_Loopback = 7,
163 	SCSI_Data_NoACK = 8,
164 	Interrupt_Status = 9,
165 	Configuration1 = 10,
166 	Configuration2 = 11,	/* tmc18c50/tmc18c30 only */
167 	Read_FIFO = 12,
168 	FIFO_Data_Count = 14
169 };
170 
171 enum out_port_type {
172 	Write_SCSI_Data = 0,
173 	SCSI_Cntl = 1,
174 	Interrupt_Cntl = 2,
175 	SCSI_Mode_Cntl = 3,
176 	TMC_Cntl = 4,
177 	Memory_Cntl = 5,	/* tmc18c50/tmc18c30 only */
178 	Write_Loopback = 7,
179 	IO_Control = 11,	/* tmc18c30 only */
180 	Write_FIFO = 12
181 };
182 
183 struct fd_hostdata {
184 	unsigned long _bios_base;
185 	int _bios_major;
186 	int _bios_minor;
187 	volatile int _in_command;
188 	Scsi_Cmnd *_current_SC;
189 	enum chip_type _chip;
190 	int _adapter_mask;
191 	int _fifo_count;	/* Number of 512 byte blocks before INTR */
192 
193 	char _adapter_name[64];
194 #if DEBUG_RACE
195 	volatile int _in_interrupt_flag;
196 #endif
197 
198 	int _SCSI_Mode_Cntl_port;
199 	int _FIFO_Data_Count_port;
200 	int _Interrupt_Cntl_port;
201 	int _Interrupt_Status_port;
202 	int _Interrupt_Cond_port;
203 	int _Read_FIFO_port;
204 	int _Read_SCSI_Data_port;
205 	int _SCSI_Cntl_port;
206 	int _SCSI_Data_NoACK_port;
207 	int _SCSI_Status_port;
208 	int _TMC_Cntl_port;
209 	int _TMC_Status_port;
210 	int _Write_FIFO_port;
211 	int _Write_SCSI_Data_port;
212 
213 	int _FIFO_Size;		/* = 0x2000;  8k FIFO for
214 				   pre-tmc18c30 chips */
215 	/* simple stats */
216 	int _Bytes_Read;
217 	int _Bytes_Written;
218 	int _INTR_Processed;
219 };
220 
221 #define FD_MAX_HOSTS 3		/* enough? */
222 
223 #define HOSTDATA(shpnt) ((struct fd_hostdata *) shpnt->hostdata)
224 #define bios_base             (HOSTDATA(shpnt)->_bios_base)
225 #define bios_major            (HOSTDATA(shpnt)->_bios_major)
226 #define bios_minor            (HOSTDATA(shpnt)->_bios_minor)
227 #define in_command            (HOSTDATA(shpnt)->_in_command)
228 #define current_SC            (HOSTDATA(shpnt)->_current_SC)
229 #define chip                  (HOSTDATA(shpnt)->_chip)
230 #define adapter_mask          (HOSTDATA(shpnt)->_adapter_mask)
231 #define FIFO_COUNT            (HOSTDATA(shpnt)->_fifo_count)
232 #define adapter_name          (HOSTDATA(shpnt)->_adapter_name)
233 #if DEBUG_RACE
234 #define in_interrupt_flag     (HOSTDATA(shpnt)->_in_interrupt_flag)
235 #endif
236 #define SCSI_Mode_Cntl_port   (HOSTDATA(shpnt)->_SCSI_Mode_Cntl_port)
237 #define FIFO_Data_Count_port  (HOSTDATA(shpnt)->_FIFO_Data_Count_port)
238 #define Interrupt_Cntl_port   (HOSTDATA(shpnt)->_Interrupt_Cntl_port)
239 #define Interrupt_Status_port (HOSTDATA(shpnt)->_Interrupt_Status_port)
240 #define Interrupt_Cond_port   (HOSTDATA(shpnt)->_Interrupt_Cond_port)
241 #define Read_FIFO_port        (HOSTDATA(shpnt)->_Read_FIFO_port)
242 #define Read_SCSI_Data_port   (HOSTDATA(shpnt)->_Read_SCSI_Data_port)
243 #define SCSI_Cntl_port        (HOSTDATA(shpnt)->_SCSI_Cntl_port)
244 #define SCSI_Data_NoACK_port  (HOSTDATA(shpnt)->_SCSI_Data_NoACK_port)
245 #define SCSI_Status_port      (HOSTDATA(shpnt)->_SCSI_Status_port)
246 #define TMC_Cntl_port         (HOSTDATA(shpnt)->_TMC_Cntl_port)
247 #define TMC_Status_port       (HOSTDATA(shpnt)->_TMC_Status_port)
248 #define Write_FIFO_port       (HOSTDATA(shpnt)->_Write_FIFO_port)
249 #define Write_SCSI_Data_port  (HOSTDATA(shpnt)->_Write_SCSI_Data_port)
250 #define FIFO_Size             (HOSTDATA(shpnt)->_FIFO_Size)
251 #define Bytes_Read            (HOSTDATA(shpnt)->_Bytes_Read)
252 #define Bytes_Written         (HOSTDATA(shpnt)->_Bytes_Written)
253 #define INTR_Processed        (HOSTDATA(shpnt)->_INTR_Processed)
254 
255 struct fd_mcs_adapters_struct {
256 	char *name;
257 	int id;
258 	enum chip_type fd_chip;
259 	int fifo_size;
260 	int fifo_count;
261 };
262 
263 #define REPLY_ID 0x5137
264 
265 static struct fd_mcs_adapters_struct fd_mcs_adapters[] = {
266 	{"Future Domain SCSI Adapter MCS-700(18C50)",
267 	 0x60e9,
268 	 tmc18c50,
269 	 0x2000,
270 	 4},
271 	{"Future Domain SCSI Adapter MCS-600/700(TMC-1800)",
272 	 0x6127,
273 	 tmc1800,
274 	 0x2000,
275 	 4},
276 	{"Reply Sound Blaster/SCSI Adapter",
277 	 REPLY_ID,
278 	 tmc18c30,
279 	 0x800,
280 	 2},
281 };
282 
283 #define FD_BRDS ARRAY_SIZE(fd_mcs_adapters)
284 
285 static irqreturn_t fd_mcs_intr(int irq, void *dev_id);
286 
287 static unsigned long addresses[] = { 0xc8000, 0xca000, 0xce000, 0xde000 };
288 static unsigned short ports[] = { 0x140, 0x150, 0x160, 0x170 };
289 static unsigned short interrupts[] = { 3, 5, 10, 11, 12, 14, 15, 0 };
290 
291 /* host information */
292 static int found = 0;
293 static struct Scsi_Host *hosts[FD_MAX_HOSTS + 1] = { NULL };
294 
295 static int user_fifo_count = 0;
296 static int user_fifo_size = 0;
297 
298 #ifndef MODULE
fd_mcs_setup(char * str)299 static int __init fd_mcs_setup(char *str)
300 {
301 	static int done_setup = 0;
302 	int ints[3];
303 
304 	get_options(str, 3, ints);
305 	if (done_setup++ || ints[0] < 1 || ints[0] > 2 || ints[1] < 1 || ints[1] > 16) {
306 		printk("fd_mcs: usage: fd_mcs=FIFO_COUNT, FIFO_SIZE\n");
307 		return 0;
308 	}
309 
310 	user_fifo_count = ints[0] >= 1 ? ints[1] : 0;
311 	user_fifo_size = ints[0] >= 2 ? ints[2] : 0;
312 	return 1;
313 }
314 
315 __setup("fd_mcs=", fd_mcs_setup);
316 #endif /* !MODULE */
317 
print_banner(struct Scsi_Host * shpnt)318 static void print_banner(struct Scsi_Host *shpnt)
319 {
320 	printk("scsi%d <fd_mcs>: ", shpnt->host_no);
321 
322 	if (bios_base) {
323 		printk("BIOS at 0x%lX", bios_base);
324 	} else {
325 		printk("No BIOS");
326 	}
327 
328 	printk(", HostID %d, %s Chip, IRQ %d, IO 0x%lX\n", shpnt->this_id, chip == tmc18c50 ? "TMC-18C50" : (chip == tmc18c30 ? "TMC-18C30" : (chip == tmc1800 ? "TMC-1800" : "Unknown")), shpnt->irq, shpnt->io_port);
329 }
330 
331 
do_pause(unsigned amount)332 static void do_pause(unsigned amount)
333 {				/* Pause for amount*10 milliseconds */
334 	do {
335 		mdelay(10);
336 	} while (--amount);
337 }
338 
fd_mcs_make_bus_idle(struct Scsi_Host * shpnt)339 static void fd_mcs_make_bus_idle(struct Scsi_Host *shpnt)
340 {
341 	outb(0, SCSI_Cntl_port);
342 	outb(0, SCSI_Mode_Cntl_port);
343 	if (chip == tmc18c50 || chip == tmc18c30)
344 		outb(0x21 | PARITY_MASK, TMC_Cntl_port);	/* Clear forced intr. */
345 	else
346 		outb(0x01 | PARITY_MASK, TMC_Cntl_port);
347 }
348 
fd_mcs_detect(struct scsi_host_template * tpnt)349 static int fd_mcs_detect(struct scsi_host_template * tpnt)
350 {
351 	int loop;
352 	struct Scsi_Host *shpnt;
353 
354 	/* get id, port, bios, irq */
355 	int slot;
356 	u_char pos2, pos3, pos4;
357 	int id, port, irq;
358 	unsigned long bios;
359 
360 	/* if not MCA machine, return */
361 	if (!MCA_bus)
362 		return 0;
363 
364 	/* changeable? */
365 	id = 7;
366 
367 	for (loop = 0; loop < FD_BRDS; loop++) {
368 		slot = 0;
369 		while (MCA_NOTFOUND != (slot = mca_find_adapter(fd_mcs_adapters[loop].id, slot))) {
370 
371 			/* if we get this far, an adapter has been detected and is
372 			   enabled */
373 
374 			printk(KERN_INFO "scsi  <fd_mcs>: %s at slot %d\n", fd_mcs_adapters[loop].name, slot + 1);
375 
376 			pos2 = mca_read_stored_pos(slot, 2);
377 			pos3 = mca_read_stored_pos(slot, 3);
378 			pos4 = mca_read_stored_pos(slot, 4);
379 
380 			/* ready for next probe */
381 			slot++;
382 
383 			if (fd_mcs_adapters[loop].id == REPLY_ID) {	/* reply card */
384 				static int reply_irq[] = { 10, 11, 14, 15 };
385 
386 				bios = 0;	/* no bios */
387 
388 				if (pos2 & 0x2)
389 					port = ports[pos4 & 0x3];
390 				else
391 					continue;
392 
393 				/* can't really disable it, same as irq=10 */
394 				irq = reply_irq[((pos4 >> 2) & 0x1) + 2 * ((pos4 >> 4) & 0x1)];
395 			} else {
396 				bios = addresses[pos2 >> 6];
397 				port = ports[(pos2 >> 4) & 0x03];
398 				irq = interrupts[(pos2 >> 1) & 0x07];
399 			}
400 
401 			if (irq) {
402 				/* claim the slot */
403 				mca_set_adapter_name(slot - 1, fd_mcs_adapters[loop].name);
404 
405 				/* check irq/region */
406 				if (request_irq(irq, fd_mcs_intr, IRQF_SHARED, "fd_mcs", hosts)) {
407 					printk(KERN_ERR "fd_mcs: interrupt is not available, skipping...\n");
408 					continue;
409 				}
410 
411 				/* request I/O region */
412 				if (request_region(port, 0x10, "fd_mcs")) {
413 					printk(KERN_ERR "fd_mcs: I/O region is already in use, skipping...\n");
414 					continue;
415 				}
416 				/* register */
417 				if (!(shpnt = scsi_register(tpnt, sizeof(struct fd_hostdata)))) {
418 					printk(KERN_ERR "fd_mcs: scsi_register() failed\n");
419 					release_region(port, 0x10);
420 					free_irq(irq, hosts);
421 					continue;
422 				}
423 
424 
425 				/* save name */
426 				strcpy(adapter_name, fd_mcs_adapters[loop].name);
427 
428 				/* chip/fifo */
429 				chip = fd_mcs_adapters[loop].fd_chip;
430 				/* use boot time value if available */
431 				FIFO_COUNT = user_fifo_count ? user_fifo_count : fd_mcs_adapters[loop].fifo_count;
432 				FIFO_Size = user_fifo_size ? user_fifo_size : fd_mcs_adapters[loop].fifo_size;
433 
434 /* FIXME: Do we need to keep this bit of code inside NOT_USED around at all? */
435 #ifdef NOT_USED
436 				/* *************************************************** */
437 				/* Try to toggle 32-bit mode.  This only
438 				   works on an 18c30 chip.  (User reports
439 				   say this works, so we should switch to
440 				   it in the near future.) */
441 				outb(0x80, port + IO_Control);
442 				if ((inb(port + Configuration2) & 0x80) == 0x80) {
443 					outb(0x00, port + IO_Control);
444 					if ((inb(port + Configuration2) & 0x80) == 0x00) {
445 						chip = tmc18c30;
446 						FIFO_Size = 0x800;	/* 2k FIFO */
447 
448 						printk("FIRST: chip=%s, fifo_size=0x%x\n", (chip == tmc18c30) ? "tmc18c30" : "tmc18c50", FIFO_Size);
449 					}
450 				}
451 
452 				/* That should have worked, but appears to
453 				   have problems.  Let's assume it is an
454 				   18c30 if the RAM is disabled. */
455 
456 				if (inb(port + Configuration2) & 0x02) {
457 					chip = tmc18c30;
458 					FIFO_Size = 0x800;	/* 2k FIFO */
459 
460 					printk("SECOND: chip=%s, fifo_size=0x%x\n", (chip == tmc18c30) ? "tmc18c30" : "tmc18c50", FIFO_Size);
461 				}
462 				/* *************************************************** */
463 #endif
464 
465 				/* IBM/ANSI scsi scan ordering */
466 				/* Stick this back in when the scsi.c changes are there */
467 				shpnt->reverse_ordering = 1;
468 
469 
470 				/* saving info */
471 				hosts[found++] = shpnt;
472 
473 				shpnt->this_id = id;
474 				shpnt->irq = irq;
475 				shpnt->io_port = port;
476 				shpnt->n_io_port = 0x10;
477 
478 				/* save */
479 				bios_base = bios;
480 				adapter_mask = (1 << id);
481 
482 				/* save more */
483 				SCSI_Mode_Cntl_port = port + SCSI_Mode_Cntl;
484 				FIFO_Data_Count_port = port + FIFO_Data_Count;
485 				Interrupt_Cntl_port = port + Interrupt_Cntl;
486 				Interrupt_Status_port = port + Interrupt_Status;
487 				Interrupt_Cond_port = port + Interrupt_Cond;
488 				Read_FIFO_port = port + Read_FIFO;
489 				Read_SCSI_Data_port = port + Read_SCSI_Data;
490 				SCSI_Cntl_port = port + SCSI_Cntl;
491 				SCSI_Data_NoACK_port = port + SCSI_Data_NoACK;
492 				SCSI_Status_port = port + SCSI_Status;
493 				TMC_Cntl_port = port + TMC_Cntl;
494 				TMC_Status_port = port + TMC_Status;
495 				Write_FIFO_port = port + Write_FIFO;
496 				Write_SCSI_Data_port = port + Write_SCSI_Data;
497 
498 				Bytes_Read = 0;
499 				Bytes_Written = 0;
500 				INTR_Processed = 0;
501 
502 				/* say something */
503 				print_banner(shpnt);
504 
505 				/* reset */
506 				outb(1, SCSI_Cntl_port);
507 				do_pause(2);
508 				outb(0, SCSI_Cntl_port);
509 				do_pause(115);
510 				outb(0, SCSI_Mode_Cntl_port);
511 				outb(PARITY_MASK, TMC_Cntl_port);
512 				/* done reset */
513 			}
514 		}
515 
516 		if (found == FD_MAX_HOSTS) {
517 			printk("fd_mcs: detecting reached max=%d host adapters.\n", FD_MAX_HOSTS);
518 			break;
519 		}
520 	}
521 
522 	return found;
523 }
524 
fd_mcs_info(struct Scsi_Host * shpnt)525 static const char *fd_mcs_info(struct Scsi_Host *shpnt)
526 {
527 	return adapter_name;
528 }
529 
530 static int TOTAL_INTR = 0;
531 
532 /*
533  * inout : decides on the direction of the dataflow and the meaning of the
534  *         variables
535  * buffer: If inout==FALSE data is being written to it else read from it
536  * *start: If inout==FALSE start of the valid data in the buffer
537  * offset: If inout==FALSE offset from the beginning of the imaginary file
538  *         from which we start writing into the buffer
539  * length: If inout==FALSE max number of bytes to be written into the buffer
540  *         else number of bytes in the buffer
541  */
fd_mcs_proc_info(struct Scsi_Host * shpnt,char * buffer,char ** start,off_t offset,int length,int inout)542 static int fd_mcs_proc_info(struct Scsi_Host *shpnt, char *buffer, char **start, off_t offset, int length, int inout)
543 {
544 	int len = 0;
545 
546 	if (inout)
547 		return (-ENOSYS);
548 
549 	*start = buffer + offset;
550 
551 	len += sprintf(buffer + len, "Future Domain MCS-600/700 Driver %s\n", DRIVER_VERSION);
552 	len += sprintf(buffer + len, "HOST #%d: %s\n", shpnt->host_no, adapter_name);
553 	len += sprintf(buffer + len, "FIFO Size=0x%x, FIFO Count=%d\n", FIFO_Size, FIFO_COUNT);
554 	len += sprintf(buffer + len, "DriverCalls=%d, Interrupts=%d, BytesRead=%d, BytesWrite=%d\n\n", TOTAL_INTR, INTR_Processed, Bytes_Read, Bytes_Written);
555 
556 	if ((len -= offset) <= 0)
557 		return 0;
558 	if (len > length)
559 		len = length;
560 	return len;
561 }
562 
fd_mcs_select(struct Scsi_Host * shpnt,int target)563 static int fd_mcs_select(struct Scsi_Host *shpnt, int target)
564 {
565 	int status;
566 	unsigned long timeout;
567 
568 	outb(0x82, SCSI_Cntl_port);	/* Bus Enable + Select */
569 	outb(adapter_mask | (1 << target), SCSI_Data_NoACK_port);
570 
571 	/* Stop arbitration and enable parity */
572 	outb(PARITY_MASK, TMC_Cntl_port);
573 
574 	timeout = 350;		/* 350mS -- because of timeouts
575 				   (was 250mS) */
576 
577 	do {
578 		status = inb(SCSI_Status_port);	/* Read adapter status */
579 		if (status & 1) {	/* Busy asserted */
580 			/* Enable SCSI Bus (on error, should make bus idle with 0) */
581 			outb(0x80, SCSI_Cntl_port);
582 			return 0;
583 		}
584 		udelay(1000);	/* wait one msec */
585 	} while (--timeout);
586 
587 	/* Make bus idle */
588 	fd_mcs_make_bus_idle(shpnt);
589 #if EVERY_ACCESS
590 	if (!target)
591 		printk("Selection failed\n");
592 #endif
593 #if ERRORS_ONLY
594 	if (!target) {
595 		static int flag = 0;
596 
597 		if (!flag)	/* Skip first failure for all chips. */
598 			++flag;
599 		else
600 			printk("fd_mcs: Selection failed\n");
601 	}
602 #endif
603 	return 1;
604 }
605 
my_done(struct Scsi_Host * shpnt,int error)606 static void my_done(struct Scsi_Host *shpnt, int error)
607 {
608 	if (in_command) {
609 		in_command = 0;
610 		outb(0x00, Interrupt_Cntl_port);
611 		fd_mcs_make_bus_idle(shpnt);
612 		current_SC->result = error;
613 		current_SC->scsi_done(current_SC);
614 	} else {
615 		panic("fd_mcs: my_done() called outside of command\n");
616 	}
617 #if DEBUG_RACE
618 	in_interrupt_flag = 0;
619 #endif
620 }
621 
622 /* only my_done needs to be protected  */
fd_mcs_intr(int irq,void * dev_id)623 static irqreturn_t fd_mcs_intr(int irq, void *dev_id)
624 {
625 	unsigned long flags;
626 	int status;
627 	int done = 0;
628 	unsigned data_count, tmp_count;
629 
630 	int i = 0;
631 	struct Scsi_Host *shpnt;
632 
633 	TOTAL_INTR++;
634 
635 	/* search for one adapter-response on shared interrupt */
636 	while ((shpnt = hosts[i++])) {
637 		if ((inb(TMC_Status_port)) & 1)
638 			break;
639 	}
640 
641 	/* return if some other device on this IRQ caused the interrupt */
642 	if (!shpnt) {
643 		return IRQ_NONE;
644 	}
645 
646 	INTR_Processed++;
647 
648 	outb(0x00, Interrupt_Cntl_port);
649 
650 	/* Abort calls my_done, so we do nothing here. */
651 	if (current_SC->SCp.phase & aborted) {
652 #if DEBUG_ABORT
653 		printk("Interrupt after abort, ignoring\n");
654 #endif
655 		/* return IRQ_HANDLED; */
656 	}
657 #if DEBUG_RACE
658 	++in_interrupt_flag;
659 #endif
660 
661 	if (current_SC->SCp.phase & in_arbitration) {
662 		status = inb(TMC_Status_port);	/* Read adapter status */
663 		if (!(status & 0x02)) {
664 #if EVERY_ACCESS
665 			printk(" AFAIL ");
666 #endif
667 			spin_lock_irqsave(shpnt->host_lock, flags);
668 			my_done(shpnt, DID_BUS_BUSY << 16);
669 			spin_unlock_irqrestore(shpnt->host_lock, flags);
670 			return IRQ_HANDLED;
671 		}
672 		current_SC->SCp.phase = in_selection;
673 
674 		outb(0x40 | FIFO_COUNT, Interrupt_Cntl_port);
675 
676 		outb(0x82, SCSI_Cntl_port);	/* Bus Enable + Select */
677 		outb(adapter_mask | (1 << scmd_id(current_SC)), SCSI_Data_NoACK_port);
678 
679 		/* Stop arbitration and enable parity */
680 		outb(0x10 | PARITY_MASK, TMC_Cntl_port);
681 #if DEBUG_RACE
682 		in_interrupt_flag = 0;
683 #endif
684 		return IRQ_HANDLED;
685 	} else if (current_SC->SCp.phase & in_selection) {
686 		status = inb(SCSI_Status_port);
687 		if (!(status & 0x01)) {
688 			/* Try again, for slow devices */
689 			if (fd_mcs_select(shpnt, scmd_id(current_SC))) {
690 #if EVERY_ACCESS
691 				printk(" SFAIL ");
692 #endif
693 				spin_lock_irqsave(shpnt->host_lock, flags);
694 				my_done(shpnt, DID_NO_CONNECT << 16);
695 				spin_unlock_irqrestore(shpnt->host_lock, flags);
696 				return IRQ_HANDLED;
697 			} else {
698 #if EVERY_ACCESS
699 				printk(" AltSel ");
700 #endif
701 				/* Stop arbitration and enable parity */
702 				outb(0x10 | PARITY_MASK, TMC_Cntl_port);
703 			}
704 		}
705 		current_SC->SCp.phase = in_other;
706 		outb(0x90 | FIFO_COUNT, Interrupt_Cntl_port);
707 		outb(0x80, SCSI_Cntl_port);
708 #if DEBUG_RACE
709 		in_interrupt_flag = 0;
710 #endif
711 		return IRQ_HANDLED;
712 	}
713 
714 	/* current_SC->SCp.phase == in_other: this is the body of the routine */
715 
716 	status = inb(SCSI_Status_port);
717 
718 	if (status & 0x10) {	/* REQ */
719 
720 		switch (status & 0x0e) {
721 
722 		case 0x08:	/* COMMAND OUT */
723 			outb(current_SC->cmnd[current_SC->SCp.sent_command++], Write_SCSI_Data_port);
724 #if EVERY_ACCESS
725 			printk("CMD = %x,", current_SC->cmnd[current_SC->SCp.sent_command - 1]);
726 #endif
727 			break;
728 		case 0x00:	/* DATA OUT -- tmc18c50/tmc18c30 only */
729 			if (chip != tmc1800 && !current_SC->SCp.have_data_in) {
730 				current_SC->SCp.have_data_in = -1;
731 				outb(0xd0 | PARITY_MASK, TMC_Cntl_port);
732 			}
733 			break;
734 		case 0x04:	/* DATA IN -- tmc18c50/tmc18c30 only */
735 			if (chip != tmc1800 && !current_SC->SCp.have_data_in) {
736 				current_SC->SCp.have_data_in = 1;
737 				outb(0x90 | PARITY_MASK, TMC_Cntl_port);
738 			}
739 			break;
740 		case 0x0c:	/* STATUS IN */
741 			current_SC->SCp.Status = inb(Read_SCSI_Data_port);
742 #if EVERY_ACCESS
743 			printk("Status = %x, ", current_SC->SCp.Status);
744 #endif
745 #if ERRORS_ONLY
746 			if (current_SC->SCp.Status && current_SC->SCp.Status != 2 && current_SC->SCp.Status != 8) {
747 				printk("ERROR fd_mcs: target = %d, command = %x, status = %x\n", current_SC->device->id, current_SC->cmnd[0], current_SC->SCp.Status);
748 			}
749 #endif
750 			break;
751 		case 0x0a:	/* MESSAGE OUT */
752 			outb(MESSAGE_REJECT, Write_SCSI_Data_port);	/* Reject */
753 			break;
754 		case 0x0e:	/* MESSAGE IN */
755 			current_SC->SCp.Message = inb(Read_SCSI_Data_port);
756 #if EVERY_ACCESS
757 			printk("Message = %x, ", current_SC->SCp.Message);
758 #endif
759 			if (!current_SC->SCp.Message)
760 				++done;
761 #if DEBUG_MESSAGES || EVERY_ACCESS
762 			if (current_SC->SCp.Message) {
763 				printk("fd_mcs: message = %x\n", current_SC->SCp.Message);
764 			}
765 #endif
766 			break;
767 		}
768 	}
769 
770 	if (chip == tmc1800 && !current_SC->SCp.have_data_in && (current_SC->SCp.sent_command >= current_SC->cmd_len)) {
771 		/* We have to get the FIFO direction
772 		   correct, so I've made a table based
773 		   on the SCSI Standard of which commands
774 		   appear to require a DATA OUT phase.
775 		 */
776 		/*
777 		   p. 94: Command for all device types
778 		   CHANGE DEFINITION            40 DATA OUT
779 		   COMPARE                      39 DATA OUT
780 		   COPY                         18 DATA OUT
781 		   COPY AND VERIFY              3a DATA OUT
782 		   INQUIRY                      12
783 		   LOG SELECT                   4c DATA OUT
784 		   LOG SENSE                    4d
785 		   MODE SELECT (6)              15 DATA OUT
786 		   MODE SELECT (10)             55 DATA OUT
787 		   MODE SENSE (6)               1a
788 		   MODE SENSE (10)              5a
789 		   READ BUFFER                  3c
790 		   RECEIVE DIAGNOSTIC RESULTS   1c
791 		   REQUEST SENSE                03
792 		   SEND DIAGNOSTIC              1d DATA OUT
793 		   TEST UNIT READY              00
794 		   WRITE BUFFER                 3b DATA OUT
795 
796 		   p.178: Commands for direct-access devices (not listed on p. 94)
797 		   FORMAT UNIT                  04 DATA OUT
798 		   LOCK-UNLOCK CACHE            36
799 		   PRE-FETCH                    34
800 		   PREVENT-ALLOW MEDIUM REMOVAL 1e
801 		   READ (6)/RECEIVE             08
802 		   READ (10)                    3c
803 		   READ CAPACITY                25
804 		   READ DEFECT DATA (10)        37
805 		   READ LONG                    3e
806 		   REASSIGN BLOCKS              07 DATA OUT
807 		   RELEASE                      17
808 		   RESERVE                      16 DATA OUT
809 		   REZERO UNIT/REWIND           01
810 		   SEARCH DATA EQUAL (10)       31 DATA OUT
811 		   SEARCH DATA HIGH (10)        30 DATA OUT
812 		   SEARCH DATA LOW (10)         32 DATA OUT
813 		   SEEK (6)                     0b
814 		   SEEK (10)                    2b
815 		   SET LIMITS (10)              33
816 		   START STOP UNIT              1b
817 		   SYNCHRONIZE CACHE            35
818 		   VERIFY (10)                  2f
819 		   WRITE (6)/PRINT/SEND         0a DATA OUT
820 		   WRITE (10)/SEND              2a DATA OUT
821 		   WRITE AND VERIFY (10)        2e DATA OUT
822 		   WRITE LONG                   3f DATA OUT
823 		   WRITE SAME                   41 DATA OUT ?
824 
825 		   p. 261: Commands for sequential-access devices (not previously listed)
826 		   ERASE                        19
827 		   LOAD UNLOAD                  1b
828 		   LOCATE                       2b
829 		   READ BLOCK LIMITS            05
830 		   READ POSITION                34
831 		   READ REVERSE                 0f
832 		   RECOVER BUFFERED DATA        14
833 		   SPACE                        11
834 		   WRITE FILEMARKS              10 ?
835 
836 		   p. 298: Commands for printer devices (not previously listed)
837 		   ****** NOT SUPPORTED BY THIS DRIVER, since 0b is SEEK (6) *****
838 		   SLEW AND PRINT               0b DATA OUT  -- same as seek
839 		   STOP PRINT                   1b
840 		   SYNCHRONIZE BUFFER           10
841 
842 		   p. 315: Commands for processor devices (not previously listed)
843 
844 		   p. 321: Commands for write-once devices (not previously listed)
845 		   MEDIUM SCAN                  38
846 		   READ (12)                    a8
847 		   SEARCH DATA EQUAL (12)       b1 DATA OUT
848 		   SEARCH DATA HIGH (12)        b0 DATA OUT
849 		   SEARCH DATA LOW (12)         b2 DATA OUT
850 		   SET LIMITS (12)              b3
851 		   VERIFY (12)                  af
852 		   WRITE (12)                   aa DATA OUT
853 		   WRITE AND VERIFY (12)        ae DATA OUT
854 
855 		   p. 332: Commands for CD-ROM devices (not previously listed)
856 		   PAUSE/RESUME                 4b
857 		   PLAY AUDIO (10)              45
858 		   PLAY AUDIO (12)              a5
859 		   PLAY AUDIO MSF               47
860 		   PLAY TRACK RELATIVE (10)     49
861 		   PLAY TRACK RELATIVE (12)     a9
862 		   READ HEADER                  44
863 		   READ SUB-CHANNEL             42
864 		   READ TOC                     43
865 
866 		   p. 370: Commands for scanner devices (not previously listed)
867 		   GET DATA BUFFER STATUS       34
868 		   GET WINDOW                   25
869 		   OBJECT POSITION              31
870 		   SCAN                         1b
871 		   SET WINDOW                   24 DATA OUT
872 
873 		   p. 391: Commands for optical memory devices (not listed)
874 		   ERASE (10)                   2c
875 		   ERASE (12)                   ac
876 		   MEDIUM SCAN                  38 DATA OUT
877 		   READ DEFECT DATA (12)        b7
878 		   READ GENERATION              29
879 		   READ UPDATED BLOCK           2d
880 		   UPDATE BLOCK                 3d DATA OUT
881 
882 		   p. 419: Commands for medium changer devices (not listed)
883 		   EXCHANGE MEDIUM              46
884 		   INITIALIZE ELEMENT STATUS    07
885 		   MOVE MEDIUM                  a5
886 		   POSITION TO ELEMENT          2b
887 		   READ ELEMENT STATUS          b8
888 		   REQUEST VOL. ELEMENT ADDRESS b5
889 		   SEND VOLUME TAG              b6 DATA OUT
890 
891 		   p. 454: Commands for communications devices (not listed previously)
892 		   GET MESSAGE (6)              08
893 		   GET MESSAGE (10)             28
894 		   GET MESSAGE (12)             a8
895 		 */
896 
897 		switch (current_SC->cmnd[0]) {
898 		case CHANGE_DEFINITION:
899 		case COMPARE:
900 		case COPY:
901 		case COPY_VERIFY:
902 		case LOG_SELECT:
903 		case MODE_SELECT:
904 		case MODE_SELECT_10:
905 		case SEND_DIAGNOSTIC:
906 		case WRITE_BUFFER:
907 
908 		case FORMAT_UNIT:
909 		case REASSIGN_BLOCKS:
910 		case RESERVE:
911 		case SEARCH_EQUAL:
912 		case SEARCH_HIGH:
913 		case SEARCH_LOW:
914 		case WRITE_6:
915 		case WRITE_10:
916 		case WRITE_VERIFY:
917 		case 0x3f:
918 		case 0x41:
919 
920 		case 0xb1:
921 		case 0xb0:
922 		case 0xb2:
923 		case 0xaa:
924 		case 0xae:
925 
926 		case 0x24:
927 
928 		case 0x38:
929 		case 0x3d:
930 
931 		case 0xb6:
932 
933 		case 0xea:	/* alternate number for WRITE LONG */
934 
935 			current_SC->SCp.have_data_in = -1;
936 			outb(0xd0 | PARITY_MASK, TMC_Cntl_port);
937 			break;
938 
939 		case 0x00:
940 		default:
941 
942 			current_SC->SCp.have_data_in = 1;
943 			outb(0x90 | PARITY_MASK, TMC_Cntl_port);
944 			break;
945 		}
946 	}
947 
948 	if (current_SC->SCp.have_data_in == -1) {	/* DATA OUT */
949 		while ((data_count = FIFO_Size - inw(FIFO_Data_Count_port)) > 512) {
950 #if EVERY_ACCESS
951 			printk("DC=%d, ", data_count);
952 #endif
953 			if (data_count > current_SC->SCp.this_residual)
954 				data_count = current_SC->SCp.this_residual;
955 			if (data_count > 0) {
956 #if EVERY_ACCESS
957 				printk("%d OUT, ", data_count);
958 #endif
959 				if (data_count == 1) {
960 					Bytes_Written++;
961 
962 					outb(*current_SC->SCp.ptr++, Write_FIFO_port);
963 					--current_SC->SCp.this_residual;
964 				} else {
965 					data_count >>= 1;
966 					tmp_count = data_count << 1;
967 					outsw(Write_FIFO_port, current_SC->SCp.ptr, data_count);
968 					current_SC->SCp.ptr += tmp_count;
969 					Bytes_Written += tmp_count;
970 					current_SC->SCp.this_residual -= tmp_count;
971 				}
972 			}
973 			if (!current_SC->SCp.this_residual) {
974 				if (current_SC->SCp.buffers_residual) {
975 					--current_SC->SCp.buffers_residual;
976 					++current_SC->SCp.buffer;
977 					current_SC->SCp.ptr = sg_virt(current_SC->SCp.buffer);
978 					current_SC->SCp.this_residual = current_SC->SCp.buffer->length;
979 				} else
980 					break;
981 			}
982 		}
983 	} else if (current_SC->SCp.have_data_in == 1) {	/* DATA IN */
984 		while ((data_count = inw(FIFO_Data_Count_port)) > 0) {
985 #if EVERY_ACCESS
986 			printk("DC=%d, ", data_count);
987 #endif
988 			if (data_count > current_SC->SCp.this_residual)
989 				data_count = current_SC->SCp.this_residual;
990 			if (data_count) {
991 #if EVERY_ACCESS
992 				printk("%d IN, ", data_count);
993 #endif
994 				if (data_count == 1) {
995 					Bytes_Read++;
996 					*current_SC->SCp.ptr++ = inb(Read_FIFO_port);
997 					--current_SC->SCp.this_residual;
998 				} else {
999 					data_count >>= 1;	/* Number of words */
1000 					tmp_count = data_count << 1;
1001 					insw(Read_FIFO_port, current_SC->SCp.ptr, data_count);
1002 					current_SC->SCp.ptr += tmp_count;
1003 					Bytes_Read += tmp_count;
1004 					current_SC->SCp.this_residual -= tmp_count;
1005 				}
1006 			}
1007 			if (!current_SC->SCp.this_residual && current_SC->SCp.buffers_residual) {
1008 				--current_SC->SCp.buffers_residual;
1009 				++current_SC->SCp.buffer;
1010 				current_SC->SCp.ptr = sg_virt(current_SC->SCp.buffer);
1011 				current_SC->SCp.this_residual = current_SC->SCp.buffer->length;
1012 			}
1013 		}
1014 	}
1015 
1016 	if (done) {
1017 #if EVERY_ACCESS
1018 		printk(" ** IN DONE %d ** ", current_SC->SCp.have_data_in);
1019 #endif
1020 
1021 #if EVERY_ACCESS
1022 		printk("BEFORE MY_DONE. . .");
1023 #endif
1024 		spin_lock_irqsave(shpnt->host_lock, flags);
1025 		my_done(shpnt, (current_SC->SCp.Status & 0xff)
1026 			| ((current_SC->SCp.Message & 0xff) << 8) | (DID_OK << 16));
1027 		spin_unlock_irqrestore(shpnt->host_lock, flags);
1028 #if EVERY_ACCESS
1029 		printk("RETURNING.\n");
1030 #endif
1031 
1032 	} else {
1033 		if (current_SC->SCp.phase & disconnect) {
1034 			outb(0xd0 | FIFO_COUNT, Interrupt_Cntl_port);
1035 			outb(0x00, SCSI_Cntl_port);
1036 		} else {
1037 			outb(0x90 | FIFO_COUNT, Interrupt_Cntl_port);
1038 		}
1039 	}
1040 #if DEBUG_RACE
1041 	in_interrupt_flag = 0;
1042 #endif
1043 	return IRQ_HANDLED;
1044 }
1045 
fd_mcs_release(struct Scsi_Host * shpnt)1046 static int fd_mcs_release(struct Scsi_Host *shpnt)
1047 {
1048 	int i, this_host, irq_usage;
1049 
1050 	release_region(shpnt->io_port, shpnt->n_io_port);
1051 
1052 	this_host = -1;
1053 	irq_usage = 0;
1054 	for (i = 0; i < found; i++) {
1055 		if (shpnt == hosts[i])
1056 			this_host = i;
1057 		if (shpnt->irq == hosts[i]->irq)
1058 			irq_usage++;
1059 	}
1060 
1061 	/* only for the last one */
1062 	if (1 == irq_usage)
1063 		free_irq(shpnt->irq, hosts);
1064 
1065 	found--;
1066 
1067 	for (i = this_host; i < found; i++)
1068 		hosts[i] = hosts[i + 1];
1069 
1070 	hosts[found] = NULL;
1071 
1072 	return 0;
1073 }
1074 
fd_mcs_queue_lck(Scsi_Cmnd * SCpnt,void (* done)(Scsi_Cmnd *))1075 static int fd_mcs_queue_lck(Scsi_Cmnd * SCpnt, void (*done) (Scsi_Cmnd *))
1076 {
1077 	struct Scsi_Host *shpnt = SCpnt->device->host;
1078 
1079 	if (in_command) {
1080 		panic("fd_mcs: fd_mcs_queue() NOT REENTRANT!\n");
1081 	}
1082 #if EVERY_ACCESS
1083 	printk("queue: target = %d cmnd = 0x%02x pieces = %d size = %u\n",
1084 		SCpnt->target, *(unsigned char *) SCpnt->cmnd,
1085 		scsi_sg_count(SCpnt), scsi_bufflen(SCpnt));
1086 #endif
1087 
1088 	fd_mcs_make_bus_idle(shpnt);
1089 
1090 	SCpnt->scsi_done = done;	/* Save this for the done function */
1091 	current_SC = SCpnt;
1092 
1093 	/* Initialize static data */
1094 
1095 	if (scsi_bufflen(current_SC)) {
1096 		current_SC->SCp.buffer = scsi_sglist(current_SC);
1097 		current_SC->SCp.ptr = sg_virt(current_SC->SCp.buffer);
1098 		current_SC->SCp.this_residual = current_SC->SCp.buffer->length;
1099 		current_SC->SCp.buffers_residual = scsi_sg_count(current_SC) - 1;
1100 	} else {
1101 		current_SC->SCp.ptr = NULL;
1102 		current_SC->SCp.this_residual = 0;
1103 		current_SC->SCp.buffer = NULL;
1104 		current_SC->SCp.buffers_residual = 0;
1105 	}
1106 
1107 
1108 	current_SC->SCp.Status = 0;
1109 	current_SC->SCp.Message = 0;
1110 	current_SC->SCp.have_data_in = 0;
1111 	current_SC->SCp.sent_command = 0;
1112 	current_SC->SCp.phase = in_arbitration;
1113 
1114 	/* Start arbitration */
1115 	outb(0x00, Interrupt_Cntl_port);
1116 	outb(0x00, SCSI_Cntl_port);	/* Disable data drivers */
1117 	outb(adapter_mask, SCSI_Data_NoACK_port);	/* Set our id bit */
1118 	in_command = 1;
1119 	outb(0x20, Interrupt_Cntl_port);
1120 	outb(0x14 | PARITY_MASK, TMC_Cntl_port);	/* Start arbitration */
1121 
1122 	return 0;
1123 }
1124 
DEF_SCSI_QCMD(fd_mcs_queue)1125 static DEF_SCSI_QCMD(fd_mcs_queue)
1126 
1127 #if DEBUG_ABORT || DEBUG_RESET
1128 static void fd_mcs_print_info(Scsi_Cmnd * SCpnt)
1129 {
1130 	unsigned int imr;
1131 	unsigned int irr;
1132 	unsigned int isr;
1133 	struct Scsi_Host *shpnt = SCpnt->host;
1134 
1135 	if (!SCpnt || !SCpnt->host) {
1136 		printk("fd_mcs: cannot provide detailed information\n");
1137 	}
1138 
1139 	printk("%s\n", fd_mcs_info(SCpnt->host));
1140 	print_banner(SCpnt->host);
1141 	switch (SCpnt->SCp.phase) {
1142 	case in_arbitration:
1143 		printk("arbitration ");
1144 		break;
1145 	case in_selection:
1146 		printk("selection ");
1147 		break;
1148 	case in_other:
1149 		printk("other ");
1150 		break;
1151 	default:
1152 		printk("unknown ");
1153 		break;
1154 	}
1155 
1156 	printk("(%d), target = %d cmnd = 0x%02x pieces = %d size = %u\n",
1157 		SCpnt->SCp.phase, SCpnt->device->id, *(unsigned char *) SCpnt->cmnd,
1158 		scsi_sg_count(SCpnt), scsi_bufflen(SCpnt));
1159 	printk("sent_command = %d, have_data_in = %d, timeout = %d\n", SCpnt->SCp.sent_command, SCpnt->SCp.have_data_in, SCpnt->timeout);
1160 #if DEBUG_RACE
1161 	printk("in_interrupt_flag = %d\n", in_interrupt_flag);
1162 #endif
1163 
1164 	imr = (inb(0x0a1) << 8) + inb(0x21);
1165 	outb(0x0a, 0xa0);
1166 	irr = inb(0xa0) << 8;
1167 	outb(0x0a, 0x20);
1168 	irr += inb(0x20);
1169 	outb(0x0b, 0xa0);
1170 	isr = inb(0xa0) << 8;
1171 	outb(0x0b, 0x20);
1172 	isr += inb(0x20);
1173 
1174 	/* Print out interesting information */
1175 	printk("IMR = 0x%04x", imr);
1176 	if (imr & (1 << shpnt->irq))
1177 		printk(" (masked)");
1178 	printk(", IRR = 0x%04x, ISR = 0x%04x\n", irr, isr);
1179 
1180 	printk("SCSI Status      = 0x%02x\n", inb(SCSI_Status_port));
1181 	printk("TMC Status       = 0x%02x", inb(TMC_Status_port));
1182 	if (inb(TMC_Status_port) & 1)
1183 		printk(" (interrupt)");
1184 	printk("\n");
1185 	printk("Interrupt Status = 0x%02x", inb(Interrupt_Status_port));
1186 	if (inb(Interrupt_Status_port) & 0x08)
1187 		printk(" (enabled)");
1188 	printk("\n");
1189 	if (chip == tmc18c50 || chip == tmc18c30) {
1190 		printk("FIFO Status      = 0x%02x\n", inb(shpnt->io_port + FIFO_Status));
1191 		printk("Int. Condition   = 0x%02x\n", inb(shpnt->io_port + Interrupt_Cond));
1192 	}
1193 	printk("Configuration 1  = 0x%02x\n", inb(shpnt->io_port + Configuration1));
1194 	if (chip == tmc18c50 || chip == tmc18c30)
1195 		printk("Configuration 2  = 0x%02x\n", inb(shpnt->io_port + Configuration2));
1196 }
1197 #endif
1198 
fd_mcs_abort(Scsi_Cmnd * SCpnt)1199 static int fd_mcs_abort(Scsi_Cmnd * SCpnt)
1200 {
1201 	struct Scsi_Host *shpnt = SCpnt->device->host;
1202 
1203 	unsigned long flags;
1204 #if EVERY_ACCESS || ERRORS_ONLY || DEBUG_ABORT
1205 	printk("fd_mcs: abort ");
1206 #endif
1207 
1208 	spin_lock_irqsave(shpnt->host_lock, flags);
1209 	if (!in_command) {
1210 #if EVERY_ACCESS || ERRORS_ONLY
1211 		printk(" (not in command)\n");
1212 #endif
1213 		spin_unlock_irqrestore(shpnt->host_lock, flags);
1214 		return FAILED;
1215 	} else
1216 		printk("\n");
1217 
1218 #if DEBUG_ABORT
1219 	fd_mcs_print_info(SCpnt);
1220 #endif
1221 
1222 	fd_mcs_make_bus_idle(shpnt);
1223 
1224 	current_SC->SCp.phase |= aborted;
1225 
1226 	current_SC->result = DID_ABORT << 16;
1227 
1228 	/* Aborts are not done well. . . */
1229 	my_done(shpnt, DID_ABORT << 16);
1230 
1231 	spin_unlock_irqrestore(shpnt->host_lock, flags);
1232 	return SUCCESS;
1233 }
1234 
fd_mcs_bus_reset(Scsi_Cmnd * SCpnt)1235 static int fd_mcs_bus_reset(Scsi_Cmnd * SCpnt) {
1236 	struct Scsi_Host *shpnt = SCpnt->device->host;
1237 	unsigned long flags;
1238 
1239 #if DEBUG_RESET
1240 	static int called_once = 0;
1241 #endif
1242 
1243 #if ERRORS_ONLY
1244 	if (SCpnt)
1245 		printk("fd_mcs: SCSI Bus Reset\n");
1246 #endif
1247 
1248 #if DEBUG_RESET
1249 	if (called_once)
1250 		fd_mcs_print_info(current_SC);
1251 	called_once = 1;
1252 #endif
1253 
1254 	spin_lock_irqsave(shpnt->host_lock, flags);
1255 
1256 	outb(1, SCSI_Cntl_port);
1257 	do_pause(2);
1258 	outb(0, SCSI_Cntl_port);
1259 	do_pause(115);
1260 	outb(0, SCSI_Mode_Cntl_port);
1261 	outb(PARITY_MASK, TMC_Cntl_port);
1262 
1263 	spin_unlock_irqrestore(shpnt->host_lock, flags);
1264 
1265 	/* Unless this is the very first call (i.e., SCPnt == NULL), everything
1266 	   is probably hosed at this point.  We will, however, try to keep
1267 	   things going by informing the high-level code that we need help. */
1268 		return SUCCESS;
1269 }
1270 
1271 #include <scsi/scsi_ioctl.h>
1272 
fd_mcs_biosparam(struct scsi_device * disk,struct block_device * bdev,sector_t capacity,int * info_array)1273 static int fd_mcs_biosparam(struct scsi_device * disk, struct block_device *bdev,
1274 			    sector_t capacity, int *info_array)
1275 {
1276 	unsigned char *p = scsi_bios_ptable(bdev);
1277 	int size = capacity;
1278 
1279 	/* BIOS >= 3.4 for MCA cards */
1280 	/* This algorithm was provided by Future Domain (much thanks!). */
1281 
1282 	if (p && p[65] == 0xaa && p[64] == 0x55	/* Partition table valid */
1283 	    && p[4]) {	/* Partition type */
1284 		/* The partition table layout is as follows:
1285 
1286 		   Start: 0x1b3h
1287 		   Offset: 0 = partition status
1288 		   1 = starting head
1289 		   2 = starting sector and cylinder (word, encoded)
1290 		   4 = partition type
1291 		   5 = ending head
1292 		   6 = ending sector and cylinder (word, encoded)
1293 		   8 = starting absolute sector (double word)
1294 		   c = number of sectors (double word)
1295 		   Signature: 0x1fe = 0x55aa
1296 
1297 		   So, this algorithm assumes:
1298 		   1) the first partition table is in use,
1299 		   2) the data in the first entry is correct, and
1300 		   3) partitions never divide cylinders
1301 
1302 		   Note that (1) may be FALSE for NetBSD (and other BSD flavors),
1303 		   as well as for Linux.  Note also, that Linux doesn't pay any
1304 		   attention to the fields that are used by this algorithm -- it
1305 		   only uses the absolute sector data.  Recent versions of Linux's
1306 		   fdisk(1) will fill this data in correctly, and forthcoming
1307 		   versions will check for consistency.
1308 
1309 		   Checking for a non-zero partition type is not part of the
1310 		   Future Domain algorithm, but it seemed to be a reasonable thing
1311 		   to do, especially in the Linux and BSD worlds. */
1312 
1313 		info_array[0] = p[5] + 1;	/* heads */
1314 		info_array[1] = p[6] & 0x3f;	/* sectors */
1315 	} else {
1316 		/* Note that this new method guarantees that there will always be
1317 		   less than 1024 cylinders on a platter.  This is good for drives
1318 		   up to approximately 7.85GB (where 1GB = 1024 * 1024 kB). */
1319 		if ((unsigned int) size >= 0x7e0000U)
1320 		{
1321 			info_array[0] = 0xff;	/* heads   = 255 */
1322 			info_array[1] = 0x3f;	/* sectors =  63 */
1323 		} else if ((unsigned int) size >= 0x200000U) {
1324 			info_array[0] = 0x80;	/* heads   = 128 */
1325 			info_array[1] = 0x3f;	/* sectors =  63 */
1326 		} else {
1327 			info_array[0] = 0x40;	/* heads   =  64 */
1328 			info_array[1] = 0x20;	/* sectors =  32 */
1329 		}
1330 	}
1331 	/* For both methods, compute the cylinders */
1332 	info_array[2] = (unsigned int) size / (info_array[0] * info_array[1]);
1333 	kfree(p);
1334 	return 0;
1335 }
1336 
1337 static struct scsi_host_template driver_template = {
1338 	.proc_name			= "fd_mcs",
1339 	.proc_info			= fd_mcs_proc_info,
1340 	.detect				= fd_mcs_detect,
1341 	.release			= fd_mcs_release,
1342 	.info				= fd_mcs_info,
1343 	.queuecommand   		= fd_mcs_queue,
1344 	.eh_abort_handler		= fd_mcs_abort,
1345 	.eh_bus_reset_handler		= fd_mcs_bus_reset,
1346 	.bios_param     		= fd_mcs_biosparam,
1347 	.can_queue      		= 1,
1348 	.this_id        		= 7,
1349 	.sg_tablesize   		= 64,
1350 	.cmd_per_lun    		= 1,
1351 	.use_clustering 		= DISABLE_CLUSTERING,
1352 };
1353 #include "scsi_module.c"
1354 
1355 MODULE_LICENSE("GPL");
1356