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

📄 stc.c

📁 <B>Digital的Unix操作系统VAX 4.2源码</B>
💻 C
📖 第 1 页 / 共 5 页
字号:
#ifndef lintstatic char *sccsid = "@(#)stc.c	4.1	ULTRIX	7/2/90";#endif lint/************************************************************************ *									* *		Copyright (c) 1984, 1986, 1987, 1988, 1989 by		* *		Digital Equipment Corporation, Maynard, MA		* *			All rights reserved.				* *									* *   This software is furnished under a license and may be used and	* *   copied  only  in accordance with the terms of such license and	* *   with the  inclusion  of  the  above  copyright  notice.   This	* *   software  or  any	other copies thereof may not be provided or	* *   otherwise made available to any other person.  No title to and	* *   ownership of the software is hereby transferred.			* *									* *   This software is  derived	from  software	received  from	the	* *   University    of	California,   Berkeley,   and	from   Bell	* *   Laboratories.  Use, duplication, or disclosure is	subject  to	* *   restrictions  under  license  agreements  with  University  of	* *   California and with AT&T.						* *									* *   The information in this software is subject to change  without	* *   notice  and should not be construed as a commitment by Digital	* *   Equipment Corporation.						* *									* *   Digital assumes no responsibility for the use  or	reliability	* *   of its software on equipment which is not supplied by Digital.	* *									* ************************************************************************//************************************************************************ * stc.c 	02-Mar-89 * * Modification history * * TZK50 Tape Driver * * 02-Dec-89	Fred Canter *	Bug fix; mprintf to error log printed address of sense data *	bytes instead of the data in the sense data bytes. *	Bug fix; restore issues a MTNOCACHE ioctl which causes a hardware *	error on the TZK50. This prevented TK50 installtaions to MV2000 *	and VS2000 systems. * * 17-May-89	Fred Canter *	Yet another bug fix. Back/forward space thru a file mark should *	fail but wasn't. * * 13-May-89	Fred Canter *	Fixed yet another bug uncovered by the V3.1 installation. There *	were many errors in the DEV_TPMARK flag handling. Code changes *	identified with "#ifdef TM_NO_FIX". To include the fix, don't *	define TM_NO_FIX. * * 10-May-89	Fred Canter *	Fix to last bug fix. Caused driver to return error on filemark *	read instead of returning the users' byte count. * * 25-Apr-89	Fred Canter *	Cleared all flags in the open routine. This fixed a bug which *	caused the driver to fail all reads after any fatal error, until *	the system was rebooted. * *	Changed printf to printd1 for the "Didn't space back over second *	filemark" debug message. * * 24-Apr-89	Fred Canter *	Rev 45 of the TZK50 firmware caused this driver to fail, because *	it did not expect a save data pointer message with no data *	remaining to be transferred (i.e., DMA count register = 0). * * 02-Mar-89	John A. Gallant *	In st_start(), correctly initialized the um pointer. * * 28-Sep-88	Fred Canter *	Clean up comments. * * 01-Sep-88	darrell *	ST_W_DMA: now saves a copy of sc_stflags which it restore, as *	the call to st_scsistart() clears sc_stflags.  Also corrected *	the check in ST_SP_CONT: that determines if the REQUEST SENSE *	succeeded.  This fixes a P1 bug that was elevated to a CLD *	(SPR 4st-00571) * * 06-Jun-88	Fred Canter *	Changes to allow this driver to use PVAX extended data buffer *	I/O mode. * * 15-Feb-88	Fred Canter *	Changes for VAX420 (CVAXstar/PVAX) support. * * 12-Jan-88	darrell *	Rewrote st_timer().  I had forgotten about the fact that a *	space command could take up to approximately 40 minutes to  *	complete.  The timer was set to go off every 3 minutes and  *	if a command had not completed as of the second time timeout *	the drive was assumed to be dead.  Each command is now looked *	up in a table and timed separately. * * 15-Sep-87	darrell *	Copied most if stintr() into another routine st_scsistart() which *	is used to start the scsi transfer.  stintr used to be called by *	st_start() to start the scsi transfer which was clearly not how *	an interrupt routine is supposed to work, and it also made *	returning from stintr() and st_start() quite complex.  As a result *	of these latest changes, st_start calls st_scsistart() to start *	the transfer, and stintr() is only called from interrupt -- which *	is much cleaner, and the "right" thing to do.  At the same time *	the sc_stflags field in the ST_R_DMA: case is restored after the *	Request Sense Command -- which fixes a panic which was happening *	in vs_bufctl. * * 20-Aug-87	darrell *	Added a timeout routine (st_timer) to timeout commands and reset  *	the controller.  A request diagnostic results command is now send *	to read the controller firmware and refuse to be opened if the *	firmware rev is below REV 34.  The first command sent to the drive *	now is a Receive Diagnostic Results command.  This should always *	return success if the drive is there and working, so we no longer  *	need to wait for three minutes with a Test Unit Ready of "not ready" *	in order to tell if the tape is there. * * 23-Apr-87	darrell *	Changed the calls to vs_bufctl to pass a pointer to a structure *	that contains a pointer to the function	that vs_bufctl is to call. *	This is the first step of cleaning up some of this code, and making *	it more maintainable. * * 15-Mar-87	darrell *	Removed the code that does a bus reset.  The bus reset was being *	done on all error conditions.  Now a bus reset is never done. * * 03-Mar-87	darrell *	Added multi-volume support.  Fixed various small bugs.  Increased *	the default number of fills to seven (7).  If the drive exists, but *	the tape is not loaded, and the open routine is called with FNDELAY, *	the driver now waits to make sure that there is not an outstanding *	rewind. * * 27-Jan-87	darrell *	Added support for the change in V32 of the TZK50 microcode that *	allows the reselect timeout (TZK50 timing out the host) to be *	disabled.  A change was also made to catch and return an iodone *	on buffers that were queued as a result of nbuffio, after a *	hard error was detected.  Also OR'ed the density bits into the *	category_stat field in the DEVIOGET case of stioctl -- so now *	dump can calculate the correct length of tape needed. * * 15-Jan-87	darrell *	Rewrote about half of this driver to support *	disconnects/reselects, make the tape stream, and * 	reduce the adverse performance impact this driver *	had on the system.  Seems to work well.  EOT is *	still not tested. * * 23-Oct-86	darrell *	Fixed a FNDELAY problem so finder now works. * * 26-Sep-86	darrell *	Cleaned up error message printouts, and fixed a problem where *	opening the device FNDELAY allowed the first command after *	changing a tape to fail. * * 26-Sep-86	darrell *	Removed a debug printf I had left in my last delta. * * 26-Sep-86	darrell *	Fixed a problem queueing multiple requests so that nbuf *	I/O will work.  Also enabled buffered writing. * * 12-Sep-86	darrell *	Fixed remaining ioctl's, put in the devioctl code to *	to work with the utilities using nbufio.  bp->b_resid *	is now returned correctly.  Fixed many other little bugs. * * 04-Sep-86	darrell *	Made ioctls work - all except MTIOCGET:, put in code to *	handle EOM, EOT, and other tape end contition, and did a *	lot of cleanup in removing old unused code, and comments, *	and changed ST_SP_COMPL: DATAI: to only read as many *	characters as are expected in program I/O -- as the STATUS *	byte was getting sucked in. * *  4-Sep-86    darrell (Darrell Dunnuck) *	First semi-working driver. * * 26-Aug-86	rsp (Ricky Palmer) *	Cleaned up devioctl code to (1) zero out devget structure *	upon entry and (2) use strlen instead of fixed storage *	for bcopy's. * *  5-Aug-86	darrell *	First pass of real driver (compiles but not debugged). * * 12-Jun-86	darrell *	started with ht.c, and made it into this file. * *//*********************************************************************** * TODO: * *	1. This driver needs to support record sizes greater that 16k. *	   The maximum size supported by the TZK50 is 64k.  This driver  *	   should be changed to support record sizes up to 64k. *********************************************************************** */  /*  */#if NST > 0 || defined(BINARY)#include "../data/stc_data.c"extern int cvs_exmode_on;u_char inicmd_tmp;  /* keep this around since we can't |=  the scs_inicmd reg */int st_from_open;   /* used to tell when the command was initiated from stopen*/int st_retries = 0; /* retry counter					      */int st_max_numof_fills = ST_DEFAULT_FILLS; /* Maximum number of fills to write*/					   /* in order to try to keep the tape*/					   /* drive streaming.		      */extern struct vsbuf vsbuf;struct vsdev vstapedev = { VS_ST, 0, 0 };int	stprobe(), stslave(), stattach(), stintr(), st_start(),	sterror(), st_timer(), st_scsistart();u_short	ststd[] = { 0 };struct	uba_driver stcdriver = { stprobe, stslave, stattach, st_start,				ststd, "st", stdinfo, "stc", stminfo,				0 };int wakeup();extern int hz;extern struct nexus nexus[];struct	stspace	ST_bufmap[];extern	int	cpu;extern	int	cpu_subtype;#define ST_TIMERRATE	30	/* how often the timer goes off		      */int	unit_attn = 1;	/* An indication that the tape was removed *//* * The following table is the timeout value for each command assuming that * the timer is set to go off every 30 seconds. */char st_timetable[48] = {	 2,	/* ST_TUR		0x00	*/				 6,	/* ST_REWIND		0x01	*/				 0,	/* unused		0x02	*/				 2,	/* ST_RQSNS		0x03	*/				 0,	/* unused		0x04	*/				 0,	/* ST_RBL		0x05	*/				 0,	/* unused		0x06	*/				 0,	/* unused		0x07	*/				 8,	/* ST_READ		0x08	*/				 0,	/* unused		0x09	*/				 8,	/* ST_WRITE		0x0a	*/				 2,	/* ST_TRKSEL		0x0b	*/				 0,	/* unused		0x0c	*/				 0,	/* unused		0x0d	*/				 0,	/* unused		0x0e	*/				 0,	/* unused		0x0f	*/				 2,	/* ST_WFM		0x10	*/				90,	/* ST_SPACE		0x11	*/				 2,	/* ST_INQ		0x12	*/				 0,	/* ST_VFY		0x13	*/				 0,	/* ST_RBD		0x14	*/				 2,	/* ST_MODSEL		0x15	*/				 0,	/* ST_RESUNIT		0x16	*/				 0,	/* ST_RELUNIT		0x17	*/				 0,	/* unused		0x18	*/				 0,	/* ST_ERASE		0x19	*/				 2,	/* ST_MODSNS		0x1a	*/				 6,	/* ST_LOAD/ST_UNLOAD	0x1b	*/				 6,	/* ST_RCVDIAG		0x1c	*/				 0,	/* ST_SNDDIAG		0x1d	*/				90,	/* ST_FSPACER		0x1e	*/				90,	/* ST_FSPACEF		0x1f	*/				 0,	/* unused		0x20	*/				 0,	/* unused		0x21	*/				 0,	/* unused		0x22	*/				 0,	/* unused		0x23	*/				 0,	/* unused		0x24	*/				 0,	/* unused		0x25	*/				 0,	/* unused		0x26	*/				 0,	/* unused		0x27	*/				 0,	/* unused		0x28	*/				 0,	/* unused		0x29	*/				 0,	/* unused		0x2a	*/				 0,	/* unused		0x2b	*/				 2,	/* ST_P_CACHE		0x2c	*/				 2,	/* ST_P_NOCACHE		0x2d	*/				90,	/* ST_BSPACER		0x2e	*/				90	/* ST_BSPACEF		0x2f	*/};/* STDEBUG intentionally left defined */#define STDEBUG#ifdef STDEBUG#define ST_TRACK_SIZE     100	/* size of the tracking buffer */#define ST_CMDTRACK_SIZE  600	/* size of the command tracking buffer */char sttrack[ST_TRACK_SIZE];char stcmdtrack[ST_CMDTRACK_SIZE];int st_cmdindex = ((ST_CMDTRACK_SIZE) - 1);int st_index = ST_TRACK_SIZE - 1;/* * ST_TRACK - a macro that writes into the ST_TRACK_SIZE * array that is used as a trail of what this driver has * done.  The data is written into the array starting from * the highest address down to the lowest address to make * it easier to trace backwards using adb. * */#define ST_TRACK(a) if(st_index < 0 )				\			st_index = (ST_TRACK_SIZE - 1);		\		    sttrack[st_index--] = a/* * ST_CMDTRACK - a macro that writes into an array the command * that was sent to the drive -- to be used as a trail of  * what this driver has done. The data is written into the array  * starting from the highest address down to the lowest address * to make it easier to trace backwards using adb. */#define ST_CMDTRACK(a) if(st_cmdindex < 0 )				\			st_cmdindex = ((ST_CMDTRACK_SIZE) - 1);	\		    stcmdtrack[st_cmdindex--] = aint stdebug = 0;#define printd if(stdebug)printf#define printd1 if (stdebug > 1) printf#define printd2 if (stdebug > 2) printf#define printd3 if (stdebug > 3) printf#define printd4 if (stdebug > 4) printf#define printd5 if (stdebug > 5) printf#define printd6 if (stdebug > 6) printfint st_direct_track_mode = 0;	/* for testing multivolume dump */u_char st_prev_cmd;	/* keeps track of the previous command sent to drive *//* * Trace Tables */char	*trace_xstate [] = {	"ST_NEXT",	"ST_SP_START",	"ST_SP_CONT",	"ST_RW_START",	"ST_R_STDMA",	"ST_W_STDMA",	"ST_R_DMA",	"ST_W_DMA",	"ST_R_COPY",	"ST_R_DMACONT",	"ST_W_DMACONT",	"ST_ERR"};char	*trace_fstate [] = {	"ST_SP_ARB",	"ST_SP_SEL",	"ST_CMD_PHA",	"ST_DATAO_PHA",	"ST_DATAI_PHA",	"ST_STATUS_PHA",	"ST_MESSI_PHA",	"ST_MESSO_PHA",	"ST_RELBUS",	"ST_ABORT"};char	*trace_event [] = {	"ST_CONT",	"ST_BEGIN",	"ST_DMA_DONE",	"ST_PAR_ERR",	"ST_PHA_MIS",	"ST_RESET",	"ST_CMD",	"ST_DMA",	"ST_ABRT",	"ST_ERROR",	"ST_TIMEOUT",	"ST_FREEB"};#endif STDEBUG/*  */stprobe(reg, cntlr)	int cntlr;	caddr_t reg;{	register struct nb1_regs *staddr = (struct nb1_regs *)qmem;	register struct nb_regs *stiaddr = (struct nb_regs *)nexus;#ifdef STDEBUG	printd6("stprobe: probing TZK50\n");#endif STDEBUG	/*	 * This driver only runs on VAXstar/Teammate.	 * It cannot be used with CVAXstar/PVAX.	 */	if (cpu != VAXSTAR)		return(0);	stiaddr->nb_int_reqclr = SCS_INT_TAPE;	/* clear SCSI in INT_REQ reg */	stiaddr->nb_int_msk |= SCS_INT_TAPE;	/* enable SCSI interrupts */	/* the reset of the SCSI bus may cause an interrupt */	staddr->scs_inicmd = SCS_INI_RST;	/* reset the SCSI bus */	DELAY(100000);	/* clear RST */	staddr->scs_inicmd = 0;	/* make the controller interrupt */	/* may not need this stuff, the reset may cause an interrupt */	if((stiaddr->nb_int_reqclr&SCS_INT_TAPE) == 0) {	/* didn't cause intr */		staddr->scs_selena = SCS_ID0;		staddr->scs_outdata = (SCS_ID0 | SCS_ID1);		staddr->scs_inicmd = (SCS_INI_SEL | SCS_INI_ENOUT);		DELAY(100000);	/* may not need this */		staddr->scs_inicmd = 0;		staddr->scs_selena = 0;	}	stiaddr->nb_int_reqclr = SCS_INT_TAPE;	/* clear SCSI in INT_REQ reg */#ifdef STDEBUG	if (cvec && cvec == 0x200)	/* check for interrupt */		printd6("stprobe: controller didn't interrupt\n");	else		printd6("stprobe: controller found at vector %o\n", cvec);#endif STDEBUG	return(1);	/*	 * Determine if the drive exists, and is a TK50.	 * We can get away with using a dev of zero in the 	 * stcommand because it is not checked anywhere in	 * this driver.	 */}/*  */stattach(ui)	register struct uba_device *ui;{	register struct uba_ctlr *um;	ui->ui_flags = 0;	/*	 * Link the drive buffer to the controller queue and	 * leave it there since there is only one drive.  We'll	 * check for outstanding requests queued for the drive.	 */	um = ui->ui_mi;	um->um_tab.b_actf = &stutab[0];	um->um_tab.b_actl = &stutab[0];	um->um_tab.b_actf->b_actf = NULL;}/*  */stslave(ui)	register struct uba_device *ui;{	register struct st_softc *sc;	register int s = spl5();	sc = &st_softc[0];	bcopy(DEV_TK50, sc->sc_device, strlen(DEV_TK50));	splx(s);	if (ui->ui_slave)		return(0);	return(1);}/*  */stopen(dev, flag)	register dev_t dev;	register int flag;{	register struct uba_device *ui;	register struct st_softc *sc;	int unit = UNIT(dev);	int retry = 0;	int retval;#ifdef STDEBUG	ST_TRACK('o');#endif STDEBUG	if (unit >= nNST || (sc = &st_softc[unit])->sc_openf ||	    (ui = stdinfo[unit]) == 0 || ui->ui_alive == 0) {		return (ENXIO);	}	/*	 * This is a strange use of the FNDELAY flag.  It	 * is here to allow the installation finder program	 * to open the device when the tape cartridge is not	 * inserted.  The installation finder program needs	 * to do an ioctl, so open must succeed whether or

⌨️ 快捷键说明

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