亚洲欧美第一页_禁久久精品乱码_粉嫩av一区二区三区免费野_久草精品视频

? 歡迎來到蟲蟲下載站! | ?? 資源下載 ?? 資源專輯 ?? 關于我們
? 蟲蟲下載站

?? scsi.c

?? linux0.99源代碼用于研究linux操作系統(tǒng)
?? C
?? 第 1 頁 / 共 3 頁
字號:
/* *	scsi.c Copyright (C) 1992 Drew Eckhardt  *	generic mid-level SCSI driver by *		Drew Eckhardt  * *	<drew@colorado.edu> * *	Bug correction thanks go to :  *		Rik Faith <faith@cs.unc.edu> *		Tommy Thorn <tthorn> *		Thomas Wuensche <tw@fgb1.fgb.mw.tu-muenchen.de> *  *       Modified by Eric Youngdale eric@tantalus.nrl.navy.mil to *       add scatter-gather, multiple outstanding request, and other *       enhancements. */#include <asm/system.h>#include <linux/sched.h>#include <linux/timer.h>#include <linux/string.h>#include "../blk.h"#include "scsi.h"#include "hosts.h"/*static const char RCSid[] = "$Header: /usr/src/linux/kernel/blk_drv/scsi/RCS/scsi.c,v 1.1 1992/07/24 06:27:38 root Exp root $";*/#define INTERNAL_ERROR (printk ("Internal error in file %s, line %d.\n", __FILE__, __LINE__), panic(""))static void scsi_done (Scsi_Cmnd *SCpnt);static int update_timeout (Scsi_Cmnd *, int);static void print_inquiry(unsigned char *data);static void scsi_times_out (Scsi_Cmnd * SCpnt);static int time_start;static int time_elapsed;/*	global variables : 	NR_SCSI_DEVICES is the number of SCSI devices we have detected, 	scsi_devices an array of these specifing the address for each 	(host, id, LUN)*/	int NR_SCSI_DEVICES=0;Scsi_Device * scsi_devices = NULL;static unsigned char generic_sense[6] = {REQUEST_SENSE, 0,0,0, 255, 0};/* We make this not static so that we can read the array with gdb. *//* static */ Scsi_Cmnd * last_cmnd = NULL;/* *	As the scsi do command functions are inteligent, and may need to  *	redo a command, we need to keep track of the last command  *	executed on each one. */#define WAS_RESET 	0x01#define WAS_TIMEDOUT 	0x02#define WAS_SENSE	0x04#define IS_RESETTING	0x08extern int last_reset[];/* *	This is the number  of clock ticks we should wait before we time out  *	and abort the command.  This is for  where the scsi.c module generates  *	the command, not where it originates from a higher level, in which *	case the timeout is specified there. * *	ABORT_TIMEOUT and RESET_TIMEOUT are the timeouts for RESET and ABORT *	respectively. */#ifdef DEBUG	#define SCSI_TIMEOUT 500#else	#define SCSI_TIMEOUT 100#endif#ifdef DEBUG	#define SENSE_TIMEOUT SCSI_TIMEOUT	#define ABORT_TIMEOUT SCSI_TIMEOUT	#define RESET_TIMEOUT SCSI_TIMEOUT#else	#define SENSE_TIMEOUT 50	#define RESET_TIMEOUT 50	#define ABORT_TIMEOUT 50	#define MIN_RESET_DELAY 25#endif/* The following devices are known not to tolerate a lun != 0 scan for   one reason or another.  Some will respond to all luns, others will   lock up. */     struct blist{       char * vendor;       char * model;       char * revision; /* Latest revision known to be bad.  Not used yet */     };#if 0static struct blist blacklist[] = {{"TANDBERG","TDC 3600","U07"},  /* Locks up if polled for lun != 0 */   {"SEAGATE","ST296","921"},   /* Responds to all lun */   {"NEWBURY","NDR3380S","2.10"},   /* Responds to all lun */   {NULL, NULL, NULL}};	static int blacklisted(char * response_data){  int i = 0;  for(i=0; 1; i++){    if(blacklist[i].vendor == NULL) return 0;    if(strncmp(blacklist[i].vendor, &response_data[8],	       strlen(blacklist[i].vendor))) continue;    if(strncmp(blacklist[i].model, &response_data[16],	       strlen(blacklist[i].model))) continue;    return 1;  };	};#endif/* *	As the actual SCSI command runs in the background, we must set up a  *	flag that tells scan_scsis() when the result it has is valid.   *	scan_scsis can set the_result to -1, and watch for it to become the  *	actual return code for that call.  the scan_scsis_done function() is  *	our user specified completion function that is passed on to the   *	scsi_do_cmd() function. */static volatile int in_scan = 0;static int the_result;static void scan_scsis_done (Scsi_Cmnd * SCpnt)	{	#ifdef DEBUG	printk ("scan_scsis_done(%d, %06x)\n\r", SCpnt->host, SCpnt->result);#endif		SCpnt->request.dev = 0xfffe;	}/* *	Detecting SCSI devices :	 *	We scan all present host adapter's busses,  from ID 0 to ID 6.   *	We use the INQUIRY command, determine device type, and pass the ID /  *	lun address of all sequential devices to the tape driver, all random  *	devices to the disk driver. */static void scan_scsis (void){  int host_nr , dev, lun, type;  unsigned char scsi_cmd [12];  unsigned char scsi_result [256];  Scsi_Cmnd  SCmd;    ++in_scan;  lun = 0;    SCmd.next = NULL;  SCmd.prev = NULL;  for (host_nr = 0; host_nr < max_scsi_hosts; ++host_nr)    if (scsi_hosts[host_nr].present)      {	host_queue[host_nr] = &SCmd;  /* We need this so that commands can					time out */	for (dev = 0; dev < 8; ++dev)	  if (scsi_hosts[host_nr].this_id != dev)	    for (lun = 0; lun < 8; ++lun)	      {		scsi_devices[NR_SCSI_DEVICES].host_no = host_nr;		scsi_devices[NR_SCSI_DEVICES].id = dev;		scsi_devices[NR_SCSI_DEVICES].lun = lun;		scsi_devices[NR_SCSI_DEVICES].index = NR_SCSI_DEVICES;		scsi_devices[NR_SCSI_DEVICES].device_wait = NULL;				scsi_cmd[0] = TEST_UNIT_READY;		scsi_cmd[1] = lun << 5;		scsi_cmd[2] = scsi_cmd[3] = scsi_cmd[5] = 0;		scsi_cmd[4] = 0;		SCmd.host = host_nr;		SCmd.target = dev;		SCmd.lun = lun;		SCmd.request.dev = 0xffff; /* Mark not busy */		SCmd.use_sg  = 0;		scsi_do_cmd (&SCmd,			     (void *)  scsi_cmd, (void *) 			     scsi_result, 256,  scan_scsis_done, 			     SCSI_TIMEOUT + 400, 3);				while (SCmd.request.dev != 0xfffe);		if(SCmd.result) {		  if ((driver_byte(SCmd.result)  & DRIVER_SENSE) &&		      ((SCmd.sense_buffer[0] & 0x70) >> 4) == 7) {		    if (SCmd.sense_buffer[2] &0xe0)		      continue; /* No devices here... */		    if((SCmd.sense_buffer[2] & 0xf != NOT_READY) &&		       (SCmd.sense_buffer[2] & 0xf != UNIT_ATTENTION))		      continue;		  }		  else		    break;		};		/*		 * Build an INQUIRY command block.  		 */				scsi_cmd[0] = INQUIRY;		scsi_cmd[1] = (lun << 5) & 0xe0;		scsi_cmd[2] = 0;		scsi_cmd[3] = 0;		scsi_cmd[4] = 255;		scsi_cmd[5] = 0;				SCmd.request.dev = 0xffff; /* Mark not busy */				scsi_do_cmd (&SCmd,			     (void *)  scsi_cmd, (void *) 			     scsi_result, 256,  scan_scsis_done, 			     SCSI_TIMEOUT, 3);				while (SCmd.request.dev != 0xfffe);				the_result = SCmd.result;				if(the_result) break; 		/* skip other luns on this device */				if (!the_result)		  {		    scsi_devices[NR_SCSI_DEVICES].		      removable = (0x80 & 				   scsi_result[1]) >> 7;		    scsi_devices[NR_SCSI_DEVICES].		      changed = 0;		    scsi_devices[NR_SCSI_DEVICES].		      access_count = 0;		    scsi_devices[NR_SCSI_DEVICES].		      busy = 0;/*  *	Currently, all sequential devices are assumed to be tapes, *	all random devices disk, with the appropriate read only  *	flags set for ROM / WORM treated as RO. */ 		    switch (type = scsi_result[0])		      {		      case TYPE_TAPE :		      case TYPE_DISK :		      case TYPE_MOD :			scsi_devices[NR_SCSI_DEVICES].writeable = 1;			break;		      case TYPE_WORM :		      case TYPE_ROM :			scsi_devices[NR_SCSI_DEVICES].writeable = 0;			break;			default :			  type = -1;		      }		    scsi_devices[NR_SCSI_DEVICES].random = 		      (type == TYPE_TAPE) ? 0 : 1;		    scsi_devices[NR_SCSI_DEVICES].type = type;		    if (type != -1)		      {			print_inquiry(scsi_result);			switch(type){			case TYPE_TAPE:			  printk("Detected scsi tape st%d at scsi%d, id %d, lun %d\n", MAX_ST,				 host_nr , dev, lun); 			  if(NR_ST != -1) ++MAX_ST;			  break;			case TYPE_ROM:			  printk("Detected scsi CD-ROM sr%d at scsi%d, id %d, lun %d\n", MAX_SR,				 host_nr , dev, lun); 			  if(NR_SR != -1) ++MAX_SR;			  break;			case TYPE_DISK:			case TYPE_MOD:			  printk("Detected scsi disk sd%d at scsi%d, id %d, lun %d\n", MAX_SD,				 host_nr , dev, lun); 			  if(NR_SD != -1) ++MAX_SD;			  break;			default:			  break;			};			scsi_devices[NR_SCSI_DEVICES].scsi_level =			  scsi_result[2] & 0x07;			if (scsi_devices[NR_SCSI_DEVICES].scsi_level >= 2 ||			    (scsi_devices[NR_SCSI_DEVICES].scsi_level == 1 &&			     (scsi_result[3] & 0x0f) == 1))			  scsi_devices[NR_SCSI_DEVICES].scsi_level++;			/* These devices need this "key" to unlock the device			   so we can use it */			if(strncmp("INSITE", &scsi_result[8], 6) == 0 &&			   strncmp("Floptical   F*8I", &scsi_result[16], 16) == 0) {			  scsi_cmd[0] = MODE_SENSE;			  scsi_cmd[1] = (lun << 5) & 0xe0;			  scsi_cmd[2] = 0x2e;			  scsi_cmd[3] = 0;			  scsi_cmd[4] = 0x2a;			  scsi_cmd[5] = 0;					  SCmd.request.dev = 0xffff; /* Mark not busy */			  			  scsi_do_cmd (&SCmd,				       (void *)  scsi_cmd, (void *) 				       scsi_result, 0x2a,  scan_scsis_done, 				       SCSI_TIMEOUT, 3);					  while (SCmd.request.dev != 0xfffe);			};			++NR_SCSI_DEVICES;#if 0			/* Some scsi devices cannot be polled for lun != 0			   due to firmware bugs */			if(blacklisted(scsi_result)) break;#endif			/* Some scsi-1 peripherals do not handle lun != 0.			   I am assuming that scsi-2 peripherals do better */			if((scsi_result[2] & 0x07) == 1 && 			   (scsi_result[3] & 0x0f) == 0) break;			}		  }       /* if result == DID_OK ends */	      }       /* for lun ends */	host_queue[host_nr] = NULL;  /* No longer needed here */      }      	/* if present */      for (host_nr = 0; host_nr < max_scsi_hosts; ++host_nr)    if (scsi_hosts[host_nr].present)      if(host_queue[host_nr]) panic("host_queue not cleared");  printk("scsi : detected ");  if(NR_SD != -1)    printk("%d SCSI disk%s ", MAX_SD, (MAX_SD != 1) ? "s" : "");	   if(NR_ST != -1)    printk("%d tape%s ", MAX_ST, (MAX_ST != 1) ? "s" : "");  if(NR_SR != -1)    printk("%d CD-ROM drive%s ", MAX_SR, (MAX_SR != 1) ? "s" : "");  printk("total.\n");  in_scan = 0;}       /* scan_scsis  ends *//* *	Flag bits for the internal_timeout array  */#define NORMAL_TIMEOUT 0#define IN_ABORT 1#define IN_RESET 2/*	This is our time out function, called when the timer expires for a 	given host adapter.  It will attempt to abort the currently executing 	command, that failing perform a kernel panic.*/ static void scsi_times_out (Scsi_Cmnd * SCpnt)	{	 	switch (SCpnt->internal_timeout & (IN_ABORT | IN_RESET))		{		case NORMAL_TIMEOUT:			if (!in_scan)			      printk("SCSI host %d timed out - aborting command \r\n",				SCpnt->host);						if (!scsi_abort	(SCpnt, DID_TIME_OUT))				return;						case IN_ABORT:			printk("SCSI host %d abort() timed out - reseting \r\n",				SCpnt->host);			if (!scsi_reset (SCpnt)) 				return;		case IN_RESET:		case (IN_ABORT | IN_RESET):			printk("Unable to reset scsi host %d\r\n",SCpnt->host);			panic("");		default:			INTERNAL_ERROR;		}						}/* This function takes a quick look at a request, and decides if itcan be queued now, or if there would be a stall while waiting forsomething else to finish.  This routine assumes that interrupts areturned off when entering the routine.  It is the responsibilityof the calling code to ensure that this is the case. */Scsi_Cmnd * request_queueable (struct request * req, int index){  int host;  Scsi_Cmnd * SCpnt = NULL;  if ((index < 0) ||  (index > NR_SCSI_DEVICES))    panic ("Index number in allocate_device() is out of range.\n");    if (req && req->dev <= 0)    panic("Invalid device in allocate_device");    host = scsi_devices[index].host_no;  SCpnt = host_queue[host];    while(SCpnt){      if(SCpnt->target == scsi_devices[index].id &&	 SCpnt->lun == scsi_devices[index].lun)	if(SCpnt->request.dev < 0) break;      SCpnt = SCpnt->next;    };  if (!SCpnt) return NULL;  if (scsi_hosts[host].can_queue      && host_busy[host] >= scsi_hosts[host].can_queue) return NULL;  if (req) {    memcpy(&SCpnt->request, req, sizeof(struct request));    req->dev = -1;  } else    SCpnt->request.dev = 0xffff; /* Busy, but no request */  SCpnt->use_sg = 0;  /* Reset the scatter-gather flag */  return SCpnt;}/* This function returns a structure pointer that will be valid forthe device.  The wait parameter tells us whether we should wait forthe unit to become free or not.  We are also able to tell this routinenot to return a descriptor if the host is unable to accept any morecommands for the time being.  We need to keep in mind that there is noguarantee that the host remain not busy.  Keep in mind therequest_queueable function also knows the internal allocation schemeof the packets for each device */Scsi_Cmnd * allocate_device (struct request ** reqp, int index, int wait){  int host, dev = -1;  struct request * req = NULL;  Scsi_Cmnd * SCpnt = NULL;  Scsi_Cmnd * SCwait = NULL;  if ((index < 0) ||  (index > NR_SCSI_DEVICES))    panic ("Index number in allocate_device() is out of range.\n");    if (reqp) req = *reqp;  if (req && (dev = req->dev) <= 0)    panic("Invalid device in allocate_device");    host = scsi_devices[index].host_no;    while (1==1){    SCpnt = host_queue[host];    while(SCpnt){      if(SCpnt->target == scsi_devices[index].id &&	 SCpnt->lun == scsi_devices[index].lun) {	SCwait = SCpnt;	if(SCpnt->request.dev < 0) break;      };      SCpnt = SCpnt->next;    };    cli();    /* See if this request has already been queued by an interrupt routine */    if (req && ((req->dev < 0) || (req->dev != dev))) return NULL;    if (!SCpnt || SCpnt->request.dev >= 0)  /* Might have changed */      {	sti();	if(!wait) return NULL;	if (!SCwait) {	  printk("Attempt to allocate device index %d, target %d, lun %d\n",		 index, scsi_devices[index].id ,scsi_devices[index].lun);	  panic("No device found in allocate_device\n");	};	SCSI_SLEEP(&scsi_devices[SCwait->index].device_wait, 		   (SCwait->request.dev > 0));

?? 快捷鍵說明

復制代碼 Ctrl + C
搜索代碼 Ctrl + F
全屏模式 F11
切換主題 Ctrl + Shift + D
顯示快捷鍵 ?
增大字號 Ctrl + =
減小字號 Ctrl + -
亚洲欧美第一页_禁久久精品乱码_粉嫩av一区二区三区免费野_久草精品视频
久久精品一区八戒影视| 欧美久久久久免费| 欧美国产精品一区| 成人免费av在线| 亚洲精品免费电影| 欧美三级日韩三级| 日本中文字幕不卡| 久久先锋影音av鲁色资源网| 国产99精品在线观看| 国产精品天美传媒| 欧美最猛黑人xxxxx猛交| 首页欧美精品中文字幕| 2023国产一二三区日本精品2022| 福利视频网站一区二区三区| 亚洲蜜臀av乱码久久精品 | 91美女片黄在线观看91美女| 一区二区成人在线| 日韩精品中午字幕| 波多野结衣的一区二区三区| 亚洲天堂福利av| 91精品国产色综合久久久蜜香臀| 国产一区二区三区在线看麻豆| 一色屋精品亚洲香蕉网站| 欧美天堂亚洲电影院在线播放| 韩国成人福利片在线播放| 亚洲免费av观看| 日韩欧美国产三级电影视频| av亚洲精华国产精华| 日韩av在线发布| 日韩一区欧美一区| 欧美成人性福生活免费看| 97精品国产97久久久久久久久久久久| 首页欧美精品中文字幕| 国产精品伦一区二区三级视频| 欧美精品黑人性xxxx| 国产成人免费视| 秋霞午夜av一区二区三区| 中文字幕免费在线观看视频一区| 欧美绝品在线观看成人午夜影视| 成人av在线电影| 美腿丝袜一区二区三区| 亚洲日本va在线观看| 精品国免费一区二区三区| 在线观看视频欧美| 不卡大黄网站免费看| 久久69国产一区二区蜜臀| 亚洲综合一区二区精品导航| 中文子幕无线码一区tr| 精品欧美一区二区久久| 欧美日韩高清影院| 色综合视频在线观看| 国产精品77777| 激情图区综合网| 日韩精品一级中文字幕精品视频免费观看 | 亚洲一区视频在线观看视频| 日本一区二区高清| 久久久久久久久久久久电影| 日韩一区二区影院| 3d动漫精品啪啪1区2区免费| 色伊人久久综合中文字幕| 成人av网在线| 国产成人精品免费| 国产成人自拍网| 国产精品中文字幕一区二区三区| 日韩国产一区二| 午夜天堂影视香蕉久久| 亚洲电影视频在线| 午夜一区二区三区视频| 亚洲一区二区三区在线| 一区二区三区四区不卡在线| 亚洲免费高清视频在线| 亚洲品质自拍视频| 亚洲精品免费在线观看| 亚洲人一二三区| 亚洲综合在线观看视频| 一区二区不卡在线播放 | 欧美精品欧美精品系列| 欧美亚洲一区二区在线| 日本乱码高清不卡字幕| 欧洲人成人精品| 欧美三级电影网| 欧美高清一级片在线| 3atv一区二区三区| 精品国产乱码久久久久久夜甘婷婷| 日韩一区二区在线观看视频播放| 日韩三级伦理片妻子的秘密按摩| 欧美成人欧美edvon| 2020国产精品自拍| 国产精品乱人伦中文| 中文字幕欧美一| 亚洲国产成人av| 日韩电影一区二区三区| 久久精品av麻豆的观看方式| 国产美女av一区二区三区| 成人永久免费视频| 99这里只有精品| 欧美少妇xxx| 26uuu亚洲综合色欧美| 欧美激情一区二区三区全黄| 日韩伦理av电影| 日韩国产一二三区| 高潮精品一区videoshd| 在线看日韩精品电影| 日韩一卡二卡三卡四卡| 国产日韩av一区| 亚洲国产人成综合网站| 久久国产精品一区二区| 成人av网址在线| 欧美日韩国产一级| 337p粉嫩大胆色噜噜噜噜亚洲 | 26uuu国产电影一区二区| 中文无字幕一区二区三区| 亚洲精品久久久蜜桃| 麻豆中文一区二区| 91女厕偷拍女厕偷拍高清| 欧美丰满少妇xxxxx高潮对白 | 中文字幕亚洲精品在线观看| 亚洲va韩国va欧美va精品| 国产一区视频在线看| 91久久精品国产91性色tv| 欧美xxxx在线观看| 亚洲一区二区五区| 国产精品亚洲а∨天堂免在线| 欧美最新大片在线看| 久久久亚洲午夜电影| 亚洲国产欧美日韩另类综合| 国产不卡视频一区二区三区| 欧美精品在线一区二区| 国产精品久久久久久久第一福利| 男女激情视频一区| 欧美亚洲国产怡红院影院| 久久伊人中文字幕| 天天综合日日夜夜精品| 成人av资源下载| 2020国产精品自拍| 青青草国产成人av片免费| 色中色一区二区| 欧美激情资源网| 久久精品国产免费| 制服丝袜中文字幕亚洲| 亚洲欧美区自拍先锋| 国产成人午夜99999| 精品国产乱码久久久久久久久| 亚洲国产视频在线| 色狠狠一区二区| 最新不卡av在线| 成人爱爱电影网址| 国产欧美一区二区精品久导航| 免费看黄色91| 欧美一区三区四区| 亚洲国产综合视频在线观看| 99re这里都是精品| 国产精品美女久久久久久| 国产乱码精品一区二区三| 欧美mv和日韩mv国产网站| 蜜臀久久99精品久久久久久9 | 国产欧美一区二区三区沐欲| 久久国产麻豆精品| 精品人在线二区三区| 久久国产生活片100| 精品国产凹凸成av人网站| 麻豆国产91在线播放| 日韩欧美中文字幕一区| 久久99九九99精品| 精品国产免费一区二区三区四区| 美日韩黄色大片| 精品国一区二区三区| 精品亚洲成av人在线观看| 久久只精品国产| 成人免费电影视频| 亚洲欧美激情插| 欧美色综合影院| 免费一级欧美片在线观看| 精品日韩一区二区三区 | 麻豆精品视频在线观看免费| 日韩三级在线观看| 国产精品亚洲综合一区在线观看| 国产偷v国产偷v亚洲高清| 波多野结衣亚洲| 亚洲国产精品一区二区久久恐怖片 | 不卡免费追剧大全电视剧网站| 国产精品国产自产拍在线| 91日韩精品一区| 婷婷六月综合亚洲| 久久综合九色综合久久久精品综合| 国产**成人网毛片九色| 国产精品的网站| 欧美日韩一二三区| 久久66热re国产| 国产精品久久久久aaaa| 欧美在线综合视频| 国模少妇一区二区三区| 国产精品国产三级国产| 欧美日韩精品一区视频| 精品综合免费视频观看| 亚洲欧美在线aaa| 欧美老年两性高潮| 成人丝袜高跟foot| 日韩不卡一区二区| 国产女人水真多18毛片18精品视频|