⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 53c78xx.c

📁 GNU Mach 微内核源代码, 基于美国卡内基美隆大学的 Mach 研究项目
💻 C
📖 第 1 页 / 共 5 页
字号:
/* * PERM_OPTIONS are driver options which will be enabled for all NCR boards * in the system at driver initialization time. * * Don't THINK about touching these in PERM_OPTIONS :  *   OPTION_IO_MAPPED  * 	Memory mapped IO does not work under i86 Linux.  * *   OPTION_DEBUG_TEST1 *	Test 1 does bus mastering and interrupt tests, which will help weed  *	out brain damaged main boards. * * These are development kernel changes.  Code for them included in this * driver release may or may not work.  If you turn them on, you should be  * running the latest copy of the development sources from * *	ftp://tsx-11.mit.edu/pub/linux/ALPHA/scsi/53c7,8xx * * and be subscribed to the ncr53c810@colorado.edu mailing list.  To * subscribe, send mail to majordomo@colorado.edu with  * * 	subscribe ncr53c810 *  * in the text. * * *   OPTION_NO_ASYNC *	Don't negotiate for asynchronous transfers on the first command  *	when OPTION_ALWAYS_SYNCHRONOUS is set.  Useful for dain bramaged *	devices which do something bad rather than sending a MESSAGE  *	REJECT back to us like they should if they can't cope. * *   OPTION_SYNCHRONOUS *	Enable support for synchronous transfers.  Target negotiated  *	synchronous transfers will be responded to.  To initiate  *	a synchronous transfer request,  call  * *	    request_synchronous (hostno, target)  * *	from within KGDB. * *   OPTION_ALWAYS_SYNCHRONOUS *	Negotiate for synchronous transfers with every target after *	driver initialization or a SCSI bus reset.  This is a bit dangerous,  *	since there are some dain bramaged SCSI devices which will accept *	SDTR messages but keep talking asynchronously. * *   OPTION_DISCONNECT *	Enable support for disconnect/reconnect.  To change the  *	default setting on a given host adapter, call * *	    request_disconnect (hostno, allow) * *	where allow is non-zero to allow, 0 to disallow. *  *  If you really want to run 10MHz FAST SCSI-II transfers, you should  *  know that the NCR driver currently ignores parity information.  Most *  systems do 5MHz SCSI fine.  I've seen a lot that have problems faster *  than 8MHz.  To play it safe, we only request 5MHz transfers. * *  If you'd rather get 10MHz transfers, edit sdtr_message and change  *  the fourth byte from 50 to 25. */#include <linux/config.h>#ifdef CONFIG_SCSI_NCR53C7xx_sync#ifdef CONFIG_SCSI_NCR53C7xx_DISCONNECT#define PERM_OPTIONS (OPTION_IO_MAPPED|OPTION_DEBUG_TEST1|OPTION_DISCONNECT|\	OPTION_SYNCHRONOUS|OPTION_ALWAYS_SYNCHRONOUS)#else#define PERM_OPTIONS (OPTION_IO_MAPPED|OPTION_DEBUG_TEST1|\	OPTION_SYNCHRONOUS|OPTION_ALWAYS_SYNCHRONOUS)#endif#else#ifdef CONFIG_SCSI_NCR53C7xx_DISCONNECT#define PERM_OPTIONS (OPTION_IO_MAPPED|OPTION_DEBUG_TEST1|OPTION_DISCONNECT|\	OPTION_SYNCHRONOUS)#else#define PERM_OPTIONS (OPTION_IO_MAPPED|OPTION_DEBUG_TEST1|OPTION_SYNCHRONOUS)#endif#endif/* * Sponsored by  *	iX Multiuser Multitasking Magazine *	Hannover, Germany *	hm@ix.de * * Copyright 1993, 1994, 1995 Drew Eckhardt *      Visionary Computing  *      (Unix and Linux consulting and custom programming) *      drew@PoohSticks.ORG *	+1 (303) 786-7975 * * TolerANT and SCSI SCRIPTS are registered trademarks of NCR Corporation. *  * For more information, please consult  * * NCR53C810  * SCSI I/O Processor * Programmer's Guide * * NCR 53C810 * PCI-SCSI I/O Processor * Data Manual * * NCR 53C810/53C820 * PCI-SCSI I/O Processor Design In Guide * * For literature on Symbios Logic Inc. formerly NCR, SCSI,  * and Communication products please call (800) 334-5454 or * (719) 536-3300.  *  * PCI BIOS Specification Revision * PCI Local Bus Specification * PCI System Design Guide * * PCI Special Interest Group * M/S HF3-15A * 5200 N.E. Elam Young Parkway * Hillsboro, Oregon 97124-6497 * +1 (503) 696-2000  * +1 (800) 433-5177 *//* * Design issues :  * The cumulative latency needed to propagate a read/write request  * through the file system, buffer cache, driver stacks, SCSI host, and  * SCSI device is ultimately the limiting factor in throughput once we  * have a sufficiently fast host adapter. *   * So, to maximize performance we want to keep the ratio of latency to data  * transfer time to a minimum by * 1.  Minimizing the total number of commands sent (typical command latency *	including drive and bus mastering host overhead is as high as 4.5ms) *	to transfer a given amount of data.   * *      This is accomplished by placing no arbitrary limit on the number *	of scatter/gather buffers supported, since we can transfer 1K *	per scatter/gather buffer without Eric's cluster patches,  *	4K with.   * * 2.  Minimizing the number of fatal interrupts serviced, since * 	fatal interrupts halt the SCSI I/O processor.  Basically, *	this means offloading the practical maximum amount of processing  *	to the SCSI chip. *  *	On the NCR53c810/820/720,  this is accomplished by using  *		interrupt-on-the-fly signals when commands complete,  *		and only handling fatal errors and SDTR / WDTR 	messages  *		in the host code. * *	On the NCR53c710, interrupts are generated as on the NCR53c8x0, *		only the lack of a interrupt-on-the-fly facility complicates *		things.   Also, SCSI ID registers and commands are  *		bit fielded rather than binary encoded. *		 * 	On the NCR53c700 and NCR53c700-66, operations that are done via  *		indirect, table mode on the more advanced chips must be *	        replaced by calls through a jump table which  *		acts as a surrogate for the DSA.  Unfortunately, this  * 		will mean that we must service an interrupt for each  *		disconnect/reconnect. *  * 3.  Eliminating latency by pipelining operations at the different levels. * 	 *	This driver allows a configurable number of commands to be enqueued *	for each target/lun combination (experimentally, I have discovered *	that two seems to work best) and will ultimately allow for  *	SCSI-II tagged queuing. * 	 * * Architecture :  * This driver is built around a Linux queue of commands waiting to  * be executed, and a shared Linux/NCR array of commands to start.  Commands * are transfered to the array  by the run_process_issue_queue() function  * which is called whenever a command completes. * * As commands are completed, the interrupt routine is triggered, * looks for commands in the linked list of completed commands with * valid status, removes these commands from a list of running commands,  * calls the done routine, and flags their target/luns as not busy. * * Due to limitations in the intelligence of the NCR chips, certain * concessions are made.  In many cases, it is easier to dynamically  * generate/fix-up code rather than calculate on the NCR at run time.   * So, code is generated or fixed up for * * - Handling data transfers, using a variable number of MOVE instructions *	interspersed with CALL MSG_IN, WHEN MSGIN instructions. * * 	The DATAIN and DATAOUT routines	are separate, so that an incorrect *	direction can be trapped, and space isn't wasted.  * *	It may turn out that we're better off using some sort  *	of table indirect instruction in a loop with a variable *	sized table on the NCR53c710 and newer chips. * * - Checking for reselection (NCR53c710 and better) * * - Handling the details of SCSI context switches (NCR53c710 and better), *	such as reprogramming appropriate synchronous parameters,  *	removing the dsa structure from the NCR's queue of outstanding *	commands, etc. * *//*  * Accommodate differences between stock 1.2.x and 1.3.x asm-i386/types.h * so lusers can drop in 53c7,8xx.* and get something which compiles  * without warnings. */#if !defined(LINUX_1_2) && !defined(LINUX_1_3)#include <linux/version.h>#if LINUX_VERSION_CODE > 65536 + 3 * 256#define LINUX_1_3#else#define LINUX_1_2#endif#endif#ifdef LINUX_1_2#define u32 bogus_u32#define s32 bogus_s32#include <asm/types.h>#undef u32#undef s32typedef __signed__ int s32;typedef unsigned int  u32;#endif /* def LINUX_1_2 */#ifdef MODULE#include <linux/module.h>#endif#include <asm/dma.h>#include <asm/io.h>#include <asm/system.h>#include <linux/delay.h>#include <linux/signal.h>#include <linux/sched.h>#include <linux/errno.h>#include <linux/bios32.h>#include <linux/pci.h>#include <linux/proc_fs.h>#include <linux/string.h>#include <linux/malloc.h>#include <linux/mm.h>#include <linux/ioport.h>#include <linux/time.h>#ifdef LINUX_1_2#include "../block/blk.h"#else#include <linux/blk.h>#endif#undef current#include "scsi.h"#include "hosts.h"#include "53c7,8xx.h"#include "constants.h"#include "sd.h"#include <linux/stat.h>#include <linux/stddef.h>#ifndef LINUX_1_2struct proc_dir_entry proc_scsi_ncr53c7xx = {    PROC_SCSI_NCR53C7xx, 9, "ncr53c7xx",    S_IFDIR | S_IRUGO | S_IXUGO, 2};#endifstatic int check_address (unsigned long addr, int size);static void dump_events (struct Scsi_Host *host, int count);static Scsi_Cmnd * return_outstanding_commands (struct Scsi_Host *host,     int free, int issue);static void hard_reset (struct Scsi_Host *host);static void ncr_scsi_reset (struct Scsi_Host *host);static void print_lots (struct Scsi_Host *host);static void set_synchronous (struct Scsi_Host *host, int target, int sxfer,     int scntl3, int now_connected);static int datapath_residual (struct Scsi_Host *host);static const char * sbcl_to_phase (int sbcl);static void print_progress (Scsi_Cmnd *cmd);static void print_queues (struct Scsi_Host *host);static void process_issue_queue (unsigned long flags);static int shutdown (struct Scsi_Host *host);static void abnormal_finished (struct NCR53c7x0_cmd *cmd, int result);static int disable (struct Scsi_Host *host);static int NCR53c8xx_run_tests (struct Scsi_Host *host);static int NCR53c8xx_script_len;static int NCR53c8xx_dsa_len;static void NCR53c7x0_intr(int irq, void *dev_id, struct pt_regs * regs);static int ncr_halt (struct Scsi_Host *host);static void intr_phase_mismatch (struct Scsi_Host *host, struct NCR53c7x0_cmd     *cmd);static void intr_dma (struct Scsi_Host *host, struct NCR53c7x0_cmd *cmd);static void print_dsa (struct Scsi_Host *host, u32 *dsa,    const char *prefix);static int print_insn (struct Scsi_Host *host, const u32 *insn,    const char *prefix, int kernel);static void NCR53c8xx_dsa_fixup (struct NCR53c7x0_cmd *cmd);static void NCR53c8x0_init_fixup (struct Scsi_Host *host);static int NCR53c8x0_dstat_sir_intr (struct Scsi_Host *host, struct     NCR53c7x0_cmd *cmd);static void NCR53c8x0_soft_reset (struct Scsi_Host *host);/* INSMOD variables */static long long perm_options = PERM_OPTIONS;/* 14 = .5s; 15 is max; decreasing divides by two. */static int selection_timeout = 14;/* Size of event list (per host adapter) */static int track_events = 0;static struct Scsi_Host *first_host = NULL;	/* Head of list of NCR boards */static Scsi_Host_Template *the_template = NULL;	/* * KNOWN BUGS : * - There is some sort of conflict when the PPP driver is compiled with  * 	support for 16 channels? *  * - On systems which predate the 1.3.x initialization order change, *      the NCR driver will cause Cannot get free page messages to appear.   *      These are harmless, but I don't know of an easy way to avoid them. * * - With OPTION_DISCONNECT, on two systems under unknown circumstances, *	we get a PHASE MISMATCH with DSA set to zero (suggests that we  *	are occurring somewhere in the reselection code) where  *	DSP=some value DCMD|DBC=same value.   * 	 *	Closer inspection suggests that we may be trying to execute *	some portion of the DSA? * scsi0 : handling residual transfer (+ 0 bytes from DMA FIFO) * scsi0 : handling residual transfer (+ 0 bytes from DMA FIFO) * scsi0 : no current command : unexpected phase MSGIN. *         DSP=0x1c46cc, DCMD|DBC=0x1c46ac, DSA=0x0 *         DSPS=0x0, TEMP=0x1c3e70, DMODE=0x80 * scsi0 : DSP-> * 001c46cc : 0x001c46cc 0x00000000 * 001c46d4 : 0x001c5ea0 0x000011f8 * *	Changed the print code in the phase_mismatch handler so *	that we call print_lots to try to diagnose this. * *//*  * Possible future direction of architecture for max performance : * * We're using a single start array for the NCR chip.  This is  * sub-optimal, because we cannot add a command which would conflict with  * an executing command to this start queue, and therefore must insert the  * next command for a given I/T/L combination after the first has completed; * incurring our interrupt latency between SCSI commands. * * To allow further pipelining of the NCR and host CPU operation, we want  * to set things up so that immediately on termination of a command destined  * for a given LUN, we get that LUN busy again.   *  * To do this, we need to add a 32 bit pointer to which is jumped to  * on completion of a command.  If no new command is available, this  * would point to the usual DSA issue queue select routine. * * If one were, it would point to a per-NCR53c7x0_cmd select routine  * which starts execution immediately, inserting the command at the head  * of the start queue if the NCR chip is selected or reselected. * * We would change so that we keep a list of outstanding commands  * for each unit, rather than a single running_list.  We'd insert  * a new command into the right running list; if the NCR didn't  * have something running for that yet, we'd put it in the  * start queue as well.  Some magic needs to happen to handle the  * race condition between the first command terminating before the  * new one is written. * * Potential for profiling :  * Call do_gettimeofday(struct timeval *tv) to get 800ns resolution. *//* * TODO :  * 1.  To support WIDE transfers, not much needs to happen.  We *	should do CHMOVE instructions instead of MOVEs when *	we have scatter/gather segments of uneven length.  When

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -