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

📄 scsiglue.c

📁 底层驱动开发
💻 C
📖 第 1 页 / 共 2 页
字号:
/* Driver for USB Mass Storage compliant devices * SCSI layer glue code * * $Id: scsiglue.c,v 1.26 2002/04/22 03:39:43 mdharm Exp $ * * Current development and maintenance by: *   (c) 1999-2002 Matthew Dharm (mdharm-usb@one-eyed-alien.net) * * Developed with the assistance of: *   (c) 2000 David L. Brown, Jr. (usb-storage@davidb.org) *   (c) 2000 Stephen J. Gowdy (SGowdy@lbl.gov) * * Initial work by: *   (c) 1999 Michael Gee (michael@linuxspecific.com) * * This driver is based on the 'USB Mass Storage Class' document. This * describes in detail the protocol used to communicate with such * devices.  Clearly, the designers had SCSI and ATAPI commands in * mind when they created this document.  The commands are all very * similar to commands in the SCSI-II and ATAPI specifications. * * It is important to note that in a number of cases this class * exhibits class-specific exemptions from the USB specification. * Notably the usage of NAK, STALL and ACK differs from the norm, in * that they are used to communicate wait, failed and OK on commands. * * Also, for certain devices, the interrupt endpoint is used to convey * status of a command. * * Please see http://www.one-eyed-alien.net/~mdharm/linux-usb for more * information about this driver. * * This program is free software; you can redistribute it and/or modify it * under the terms of the GNU General Public License as published by the * Free Software Foundation; either version 2, or (at your option) any * later version. * * This program is distributed in the hope that it will be useful, but * WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU * General Public License for more details. * * You should have received a copy of the GNU General Public License along * with this program; if not, write to the Free Software Foundation, Inc., * 675 Mass Ave, Cambridge, MA 02139, USA. */#include <linux/slab.h>#include <linux/module.h>#include <scsi/scsi.h>#include <scsi/scsi_cmnd.h>#include <scsi/scsi_devinfo.h>#include <scsi/scsi_device.h>#include <scsi/scsi_eh.h>#include "usb.h"#include "scsiglue.h"#include "debug.h"#include "transport.h"#include "protocol.h"/*********************************************************************** * Host functions  ***********************************************************************/static const char* host_info(struct Scsi_Host *host){	return "SCSI emulation for USB Mass Storage devices";}static int slave_alloc (struct scsi_device *sdev){	/*	 * Set the INQUIRY transfer length to 36.  We don't use any of	 * the extra data and many devices choke if asked for more or	 * less than 36 bytes.	 */	sdev->inquiry_len = 36;	return 0;}static int slave_configure(struct scsi_device *sdev){	struct us_data *us = host_to_us(sdev->host);	/* Scatter-gather buffers (all but the last) must have a length	 * divisible by the bulk maxpacket size.  Otherwise a data packet	 * would end up being short, causing a premature end to the data	 * transfer.  Since high-speed bulk pipes have a maxpacket size	 * of 512, we'll use that as the scsi device queue's DMA alignment	 * mask.  Guaranteeing proper alignment of the first buffer will	 * have the desired effect because, except at the beginning and	 * the end, scatter-gather buffers follow page boundaries. */	blk_queue_dma_alignment(sdev->request_queue, (512 - 1));	/* Set the SCSI level to at least 2.  We'll leave it at 3 if that's	 * what is originally reported.  We need this to avoid confusing	 * the SCSI layer with devices that report 0 or 1, but need 10-byte	 * commands (ala ATAPI devices behind certain bridges, or devices	 * which simply have broken INQUIRY data).	 *	 * NOTE: This means /dev/sg programs (ala cdrecord) will get the	 * actual information.  This seems to be the preference for	 * programs like that.	 *	 * NOTE: This also means that /proc/scsi/scsi and sysfs may report	 * the actual value or the modified one, depending on where the	 * data comes from.	 */	if (sdev->scsi_level < SCSI_2)		sdev->scsi_level = SCSI_2;	/* According to the technical support people at Genesys Logic,	 * devices using their chips have problems transferring more than	 * 32 KB at a time.  In practice people have found that 64 KB	 * works okay and that's what Windows does.  But we'll be	 * conservative; people can always use the sysfs interface to	 * increase max_sectors. */	if (le16_to_cpu(us->pusb_dev->descriptor.idVendor) == USB_VENDOR_ID_GENESYS &&			sdev->request_queue->max_sectors > 64)		blk_queue_max_sectors(sdev->request_queue, 64);	/* We can't put these settings in slave_alloc() because that gets	 * called before the device type is known.  Consequently these	 * settings can't be overridden via the scsi devinfo mechanism. */	if (sdev->type == TYPE_DISK) {		/* Disk-type devices use MODE SENSE(6) if the protocol		 * (SubClass) is Transparent SCSI, otherwise they use		 * MODE SENSE(10). */		if (us->subclass != US_SC_SCSI)			sdev->use_10_for_ms = 1;		/* Many disks only accept MODE SENSE transfer lengths of		 * 192 bytes (that's what Windows uses). */		sdev->use_192_bytes_for_3f = 1;		/* Some devices don't like MODE SENSE with page=0x3f,		 * which is the command used for checking if a device		 * is write-protected.  Now that we tell the sd driver		 * to do a 192-byte transfer with this command the		 * majority of devices work fine, but a few still can't		 * handle it.  The sd driver will simply assume those		 * devices are write-enabled. */		if (us->flags & US_FL_NO_WP_DETECT)			sdev->skip_ms_page_3f = 1;		/* A number of devices have problems with MODE SENSE for		 * page x08, so we will skip it. */		sdev->skip_ms_page_8 = 1;		/* Some disks return the total number of blocks in response		 * to READ CAPACITY rather than the highest block number.		 * If this device makes that mistake, tell the sd driver. */		if (us->flags & US_FL_FIX_CAPACITY)			sdev->fix_capacity = 1;		/* Some devices report a SCSI revision level above 2 but are		 * unable to handle the REPORT LUNS command (for which		 * support is mandatory at level 3).  Since we already have		 * a Get-Max-LUN request, we won't lose much by setting the		 * revision level down to 2.  The only devices that would be		 * affected are those with sparse LUNs. */		sdev->scsi_level = SCSI_2;		/* USB-IDE bridges tend to report SK = 0x04 (Non-recoverable		 * Hardware Error) when any low-level error occurs,		 * recoverable or not.  Setting this flag tells the SCSI		 * midlayer to retry such commands, which frequently will		 * succeed and fix the error.  The worst this can lead to		 * is an occasional series of retries that will all fail. */		sdev->retry_hwerror = 1;	} else {		/* Non-disk-type devices don't need to blacklist any pages		 * or to force 192-byte transfer lengths for MODE SENSE.		 * But they do need to use MODE SENSE(10). */		sdev->use_10_for_ms = 1;	}	/* Some devices choke when they receive a PREVENT-ALLOW MEDIUM	 * REMOVAL command, so suppress those commands. */	if (us->flags & US_FL_NOT_LOCKABLE)		sdev->lockable = 0;	/* this is to satisfy the compiler, tho I don't think the 	 * return code is ever checked anywhere. */	return 0;}/* queue a command *//* This is always called with scsi_lock(host) held */static int queuecommand(struct scsi_cmnd *srb,			void (*done)(struct scsi_cmnd *)){	struct us_data *us = host_to_us(srb->device->host);	US_DEBUGP("%s called\n", __FUNCTION__);	/* check for state-transition errors */	if (us->srb != NULL) {		printk(KERN_ERR USB_STORAGE "Error in %s: us->srb = %p\n",			__FUNCTION__, us->srb);		return SCSI_MLQUEUE_HOST_BUSY;	}	/* fail the command if we are disconnecting */	if (test_bit(US_FLIDX_DISCONNECTING, &us->flags)) {		US_DEBUGP("Fail command during disconnect\n");		srb->result = DID_NO_CONNECT << 16;		done(srb);		return 0;	}	/* enqueue the command and wake up the control thread */	srb->scsi_done = done;	us->srb = srb;	up(&(us->sema));	return 0;}/*********************************************************************** * Error handling functions ***********************************************************************//* Command timeout and abort */static int command_abort(struct scsi_cmnd *srb){	struct us_data *us = host_to_us(srb->device->host);	US_DEBUGP("%s called\n", __FUNCTION__);	/* us->srb together with the TIMED_OUT, RESETTING, and ABORTING	 * bits are protected by the host lock. */	scsi_lock(us_to_host(us));	/* Is this command still active? */	if (us->srb != srb) {		scsi_unlock(us_to_host(us));		US_DEBUGP ("-- nothing to abort\n");		return FAILED;

⌨️ 快捷键说明

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