| 1 |
/* Driver for USB Mass Storage compliant devices |
|---|
| 2 |
* |
|---|
| 3 |
* $Id: usb.c,v 1.75 2002/04/22 03:39:43 mdharm Exp $ |
|---|
| 4 |
* |
|---|
| 5 |
* Current development and maintenance by: |
|---|
| 6 |
* (c) 1999-2003 Matthew Dharm (mdharm-usb@one-eyed-alien.net) |
|---|
| 7 |
* |
|---|
| 8 |
* Developed with the assistance of: |
|---|
| 9 |
* (c) 2000 David L. Brown, Jr. (usb-storage@davidb.org) |
|---|
| 10 |
* (c) 2003 Alan Stern (stern@rowland.harvard.edu) |
|---|
| 11 |
* |
|---|
| 12 |
* Initial work by: |
|---|
| 13 |
* (c) 1999 Michael Gee (michael@linuxspecific.com) |
|---|
| 14 |
* |
|---|
| 15 |
* usb_device_id support by Adam J. Richter (adam@yggdrasil.com): |
|---|
| 16 |
* (c) 2000 Yggdrasil Computing, Inc. |
|---|
| 17 |
* |
|---|
| 18 |
* This driver is based on the 'USB Mass Storage Class' document. This |
|---|
| 19 |
* describes in detail the protocol used to communicate with such |
|---|
| 20 |
* devices. Clearly, the designers had SCSI and ATAPI commands in |
|---|
| 21 |
* mind when they created this document. The commands are all very |
|---|
| 22 |
* similar to commands in the SCSI-II and ATAPI specifications. |
|---|
| 23 |
* |
|---|
| 24 |
* It is important to note that in a number of cases this class |
|---|
| 25 |
* exhibits class-specific exemptions from the USB specification. |
|---|
| 26 |
* Notably the usage of NAK, STALL and ACK differs from the norm, in |
|---|
| 27 |
* that they are used to communicate wait, failed and OK on commands. |
|---|
| 28 |
* |
|---|
| 29 |
* Also, for certain devices, the interrupt endpoint is used to convey |
|---|
| 30 |
* status of a command. |
|---|
| 31 |
* |
|---|
| 32 |
* Please see http://www.one-eyed-alien.net/~mdharm/linux-usb for more |
|---|
| 33 |
* information about this driver. |
|---|
| 34 |
* |
|---|
| 35 |
* This program is free software; you can redistribute it and/or modify it |
|---|
| 36 |
* under the terms of the GNU General Public License as published by the |
|---|
| 37 |
* Free Software Foundation; either version 2, or (at your option) any |
|---|
| 38 |
* later version. |
|---|
| 39 |
* |
|---|
| 40 |
* This program is distributed in the hope that it will be useful, but |
|---|
| 41 |
* WITHOUT ANY WARRANTY; without even the implied warranty of |
|---|
| 42 |
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU |
|---|
| 43 |
* General Public License for more details. |
|---|
| 44 |
* |
|---|
| 45 |
* You should have received a copy of the GNU General Public License along |
|---|
| 46 |
* with this program; if not, write to the Free Software Foundation, Inc., |
|---|
| 47 |
* 675 Mass Ave, Cambridge, MA 02139, USA. |
|---|
| 48 |
*/ |
|---|
| 49 |
|
|---|
| 50 |
#include <linux/sched.h> |
|---|
| 51 |
#include <linux/errno.h> |
|---|
| 52 |
#include <linux/freezer.h> |
|---|
| 53 |
#include <linux/module.h> |
|---|
| 54 |
#include <linux/init.h> |
|---|
| 55 |
#include <linux/slab.h> |
|---|
| 56 |
#include <linux/kthread.h> |
|---|
| 57 |
#include <linux/mutex.h> |
|---|
| 58 |
#include <linux/utsname.h> |
|---|
| 59 |
|
|---|
| 60 |
#include <scsi/scsi.h> |
|---|
| 61 |
#include <scsi/scsi_cmnd.h> |
|---|
| 62 |
#include <scsi/scsi_device.h> |
|---|
| 63 |
|
|---|
| 64 |
#include "usb.h" |
|---|
| 65 |
#include "scsiglue.h" |
|---|
| 66 |
#include "transport.h" |
|---|
| 67 |
#include "protocol.h" |
|---|
| 68 |
#include "debug.h" |
|---|
| 69 |
#include "initializers.h" |
|---|
| 70 |
|
|---|
| 71 |
#ifdef CONFIG_USB_STORAGE_USBAT |
|---|
| 72 |
#include "shuttle_usbat.h" |
|---|
| 73 |
#endif |
|---|
| 74 |
#ifdef CONFIG_USB_STORAGE_SDDR09 |
|---|
| 75 |
#include "sddr09.h" |
|---|
| 76 |
#endif |
|---|
| 77 |
#ifdef CONFIG_USB_STORAGE_SDDR55 |
|---|
| 78 |
#include "sddr55.h" |
|---|
| 79 |
#endif |
|---|
| 80 |
#ifdef CONFIG_USB_STORAGE_DPCM |
|---|
| 81 |
#include "dpcm.h" |
|---|
| 82 |
#endif |
|---|
| 83 |
#ifdef CONFIG_USB_STORAGE_FREECOM |
|---|
| 84 |
#include "freecom.h" |
|---|
| 85 |
#endif |
|---|
| 86 |
#ifdef CONFIG_USB_STORAGE_ISD200 |
|---|
| 87 |
#include "isd200.h" |
|---|
| 88 |
#endif |
|---|
| 89 |
#ifdef CONFIG_USB_STORAGE_DATAFAB |
|---|
| 90 |
#include "datafab.h" |
|---|
| 91 |
#endif |
|---|
| 92 |
#ifdef CONFIG_USB_STORAGE_JUMPSHOT |
|---|
| 93 |
#include "jumpshot.h" |
|---|
| 94 |
#endif |
|---|
| 95 |
#ifdef CONFIG_USB_STORAGE_ONETOUCH |
|---|
| 96 |
#include "onetouch.h" |
|---|
| 97 |
#endif |
|---|
| 98 |
#ifdef CONFIG_USB_STORAGE_ALAUDA |
|---|
| 99 |
#include "alauda.h" |
|---|
| 100 |
#endif |
|---|
| 101 |
#ifdef CONFIG_USB_STORAGE_KARMA |
|---|
| 102 |
#include "karma.h" |
|---|
| 103 |
#endif |
|---|
| 104 |
#include "sierra_ms.h" |
|---|
| 105 |
#include "option_ms.h" |
|---|
| 106 |
|
|---|
| 107 |
/* Some informational data */ |
|---|
| 108 |
MODULE_AUTHOR("Matthew Dharm <mdharm-usb@one-eyed-alien.net>"); |
|---|
| 109 |
MODULE_DESCRIPTION("USB Mass Storage driver for Linux"); |
|---|
| 110 |
MODULE_LICENSE("GPL"); |
|---|
| 111 |
|
|---|
| 112 |
static unsigned int delay_use = 5; |
|---|
| 113 |
module_param(delay_use, uint, S_IRUGO | S_IWUSR); |
|---|
| 114 |
MODULE_PARM_DESC(delay_use, "seconds to delay before using a new device"); |
|---|
| 115 |
|
|---|
| 116 |
|
|---|
| 117 |
/* |
|---|
| 118 |
* The entries in this table correspond, line for line, |
|---|
| 119 |
* with the entries of us_unusual_dev_list[]. |
|---|
| 120 |
*/ |
|---|
| 121 |
#ifndef CONFIG_USB_LIBUSUAL |
|---|
| 122 |
|
|---|
| 123 |
#define UNUSUAL_DEV(id_vendor, id_product, bcdDeviceMin, bcdDeviceMax, \ |
|---|
| 124 |
vendorName, productName,useProtocol, useTransport, \ |
|---|
| 125 |
initFunction, flags) \ |
|---|
| 126 |
{ USB_DEVICE_VER(id_vendor, id_product, bcdDeviceMin,bcdDeviceMax), \ |
|---|
| 127 |
.driver_info = (flags)|(USB_US_TYPE_STOR<<24) } |
|---|
| 128 |
|
|---|
| 129 |
#define USUAL_DEV(useProto, useTrans, useType) \ |
|---|
| 130 |
{ USB_INTERFACE_INFO(USB_CLASS_MASS_STORAGE, useProto, useTrans), \ |
|---|
| 131 |
.driver_info = (USB_US_TYPE_STOR<<24) } |
|---|
| 132 |
|
|---|
| 133 |
static struct usb_device_id storage_usb_ids [] = { |
|---|
| 134 |
|
|---|
| 135 |
# include "unusual_devs.h" |
|---|
| 136 |
#undef UNUSUAL_DEV |
|---|
| 137 |
#undef USUAL_DEV |
|---|
| 138 |
/* Terminating entry */ |
|---|
| 139 |
{ } |
|---|
| 140 |
}; |
|---|
| 141 |
|
|---|
| 142 |
MODULE_DEVICE_TABLE (usb, storage_usb_ids); |
|---|
| 143 |
#endif /* CONFIG_USB_LIBUSUAL */ |
|---|
| 144 |
|
|---|
| 145 |
/* This is the list of devices we recognize, along with their flag data */ |
|---|
| 146 |
|
|---|
| 147 |
/* The vendor name should be kept at eight characters or less, and |
|---|
| 148 |
* the product name should be kept at 16 characters or less. If a device |
|---|
| 149 |
* has the US_FL_FIX_INQUIRY flag, then the vendor and product names |
|---|
| 150 |
* normally generated by a device thorugh the INQUIRY response will be |
|---|
| 151 |
* taken from this list, and this is the reason for the above size |
|---|
| 152 |
* restriction. However, if the flag is not present, then you |
|---|
| 153 |
* are free to use as many characters as you like. |
|---|
| 154 |
*/ |
|---|
| 155 |
|
|---|
| 156 |
#define UNUSUAL_DEV(idVendor, idProduct, bcdDeviceMin, bcdDeviceMax, \ |
|---|
| 157 |
vendor_name, product_name, use_protocol, use_transport, \ |
|---|
| 158 |
init_function, Flags) \ |
|---|
| 159 |
{ \ |
|---|
| 160 |
.vendorName = vendor_name, \ |
|---|
| 161 |
.productName = product_name, \ |
|---|
| 162 |
.useProtocol = use_protocol, \ |
|---|
| 163 |
.useTransport = use_transport, \ |
|---|
| 164 |
.initFunction = init_function, \ |
|---|
| 165 |
} |
|---|
| 166 |
|
|---|
| 167 |
#define USUAL_DEV(use_protocol, use_transport, use_type) \ |
|---|
| 168 |
{ \ |
|---|
| 169 |
.useProtocol = use_protocol, \ |
|---|
| 170 |
.useTransport = use_transport, \ |
|---|
| 171 |
} |
|---|
| 172 |
|
|---|
| 173 |
static struct us_unusual_dev us_unusual_dev_list[] = { |
|---|
| 174 |
# include "unusual_devs.h" |
|---|
| 175 |
# undef UNUSUAL_DEV |
|---|
| 176 |
# undef USUAL_DEV |
|---|
| 177 |
|
|---|
| 178 |
/* Terminating entry */ |
|---|
| 179 |
{ NULL } |
|---|
| 180 |
}; |
|---|
| 181 |
|
|---|
| 182 |
|
|---|
| 183 |
#ifdef CONFIG_PM /* Minimal support for suspend and resume */ |
|---|
| 184 |
|
|---|
| 185 |
static int storage_suspend(struct usb_interface *iface, pm_message_t message) |
|---|
| 186 |
{ |
|---|
| 187 |
struct us_data *us = usb_get_intfdata(iface); |
|---|
| 188 |
|
|---|
| 189 |
/* Wait until no command is running */ |
|---|
| 190 |
mutex_lock(&us->dev_mutex); |
|---|
| 191 |
|
|---|
| 192 |
US_DEBUGP("%s\n", __FUNCTION__); |
|---|
| 193 |
if (us->suspend_resume_hook) |
|---|
| 194 |
(us->suspend_resume_hook)(us, US_SUSPEND); |
|---|
| 195 |
|
|---|
| 196 |
/* When runtime PM is working, we'll set a flag to indicate |
|---|
| 197 |
* whether we should autoresume when a SCSI request arrives. */ |
|---|
| 198 |
|
|---|
| 199 |
mutex_unlock(&us->dev_mutex); |
|---|
| 200 |
return 0; |
|---|
| 201 |
} |
|---|
| 202 |
|
|---|
| 203 |
static int storage_resume(struct usb_interface *iface) |
|---|
| 204 |
{ |
|---|
| 205 |
struct us_data *us = usb_get_intfdata(iface); |
|---|
| 206 |
|
|---|
| 207 |
mutex_lock(&us->dev_mutex); |
|---|
| 208 |
|
|---|
| 209 |
US_DEBUGP("%s\n", __FUNCTION__); |
|---|
| 210 |
if (us->suspend_resume_hook) |
|---|
| 211 |
(us->suspend_resume_hook)(us, US_RESUME); |
|---|
| 212 |
|
|---|
| 213 |
mutex_unlock(&us->dev_mutex); |
|---|
| 214 |
return 0; |
|---|
| 215 |
} |
|---|
| 216 |
|
|---|
| 217 |
static int storage_reset_resume(struct usb_interface *iface) |
|---|
| 218 |
{ |
|---|
| 219 |
struct us_data *us = usb_get_intfdata(iface); |
|---|
| 220 |
|
|---|
| 221 |
US_DEBUGP("%s\n", __FUNCTION__); |
|---|
| 222 |
|
|---|
| 223 |
/* Report the reset to the SCSI core */ |
|---|
| 224 |
usb_stor_report_bus_reset(us); |
|---|
| 225 |
|
|---|
| 226 |
/* FIXME: Notify the subdrivers that they need to reinitialize |
|---|
| 227 |
* the device */ |
|---|
| 228 |
return 0; |
|---|
| 229 |
} |
|---|
| 230 |
|
|---|
| 231 |
#endif /* CONFIG_PM */ |
|---|
| 232 |
|
|---|
| 233 |
/* |
|---|
| 234 |
* The next two routines get called just before and just after |
|---|
| 235 |
* a USB port reset, whether from this driver or a different one. |
|---|
| 236 |
*/ |
|---|
| 237 |
|
|---|
| 238 |
static int storage_pre_reset(struct usb_interface *iface) |
|---|
| 239 |
{ |
|---|
| 240 |
struct us_data *us = usb_get_intfdata(iface); |
|---|
| 241 |
|
|---|
| 242 |
US_DEBUGP("%s\n", __FUNCTION__); |
|---|
| 243 |
|
|---|
| 244 |
/* Make sure no command runs during the reset */ |
|---|
| 245 |
mutex_lock(&us->dev_mutex); |
|---|
| 246 |
return 0; |
|---|
| 247 |
} |
|---|
| 248 |
|
|---|
| 249 |
static int storage_post_reset(struct usb_interface *iface) |
|---|
| 250 |
{ |
|---|
| 251 |
struct us_data *us = usb_get_intfdata(iface); |
|---|
| 252 |
|
|---|
| 253 |
US_DEBUGP("%s\n", __FUNCTION__); |
|---|
| 254 |
|
|---|
| 255 |
/* Report the reset to the SCSI core */ |
|---|
| 256 |
usb_stor_report_bus_reset(us); |
|---|
| 257 |
|
|---|
| 258 |
/* FIXME: Notify the subdrivers that they need to reinitialize |
|---|
| 259 |
* the device */ |
|---|
| 260 |
|
|---|
| 261 |
mutex_unlock(&us->dev_mutex); |
|---|
| 262 |
return 0; |
|---|
| 263 |
} |
|---|
| 264 |
|
|---|
| 265 |
/* |
|---|
| 266 |
* fill_inquiry_response takes an unsigned char array (which must |
|---|
| 267 |
* be at least 36 characters) and populates the vendor name, |
|---|
| 268 |
* product name, and revision fields. Then the array is copied |
|---|
| 269 |
* into the SCSI command's response buffer (oddly enough |
|---|
| 270 |
* called request_buffer). data_len contains the length of the |
|---|
| 271 |
* data array, which again must be at least 36. |
|---|
| 272 |
*/ |
|---|
| 273 |
|
|---|
| 274 |
void fill_inquiry_response(struct us_data *us, unsigned char *data, |
|---|
| 275 |
unsigned int data_len) |
|---|
| 276 |
{ |
|---|
| 277 |
if (data_len<36) // You lose. |
|---|
| 278 |
return; |
|---|
| 279 |
|
|---|
| 280 |
if(data[0]&0x20) { /* USB device currently not connected. Return |
|---|
| 281 |
peripheral qualifier 001b ("...however, the |
|---|
| 282 |
physical device is not currently connected |
|---|
| 283 |
to this logical unit") and leave vendor and |
|---|
| 284 |
product identification empty. ("If the target |
|---|
| 285 |
does store some of the INQUIRY data on the |
|---|
| 286 |
device, it may return zeros or ASCII spaces |
|---|
| 287 |
(20h) in those fields until the data is |
|---|
| 288 |
available from the device."). */ |
|---|
| 289 |
memset(data+8,0,28); |
|---|
| 290 |
} else { |
|---|
| 291 |
u16 bcdDevice = le16_to_cpu(us->pusb_dev->descriptor.bcdDevice); |
|---|
| 292 |
memcpy(data+8, us->unusual_dev->vendorName, |
|---|
| 293 |
strlen(us->unusual_dev->vendorName) > 8 ? 8 : |
|---|
| 294 |
strlen(us->unusual_dev->vendorName)); |
|---|
| 295 |
memcpy(data+16, us->unusual_dev->productName, |
|---|
| 296 |
strlen(us->unusual_dev->productName) > 16 ? 16 : |
|---|
| 297 |
strlen(us->unusual_dev->productName)); |
|---|
| 298 |
data[32] = 0x30 + ((bcdDevice>>12) & 0x0F); |
|---|
| 299 |
data[33] = 0x30 + ((bcdDevice>>8) & 0x0F); |
|---|
| 300 |
data[34] = 0x30 + ((bcdDevice>>4) & 0x0F); |
|---|
| 301 |
data[35] = 0x30 + ((bcdDevice) & 0x0F); |
|---|
| 302 |
} |
|---|
| 303 |
|
|---|
| 304 |
usb_stor_set_xfer_buf(data, data_len, us->srb); |
|---|
| 305 |
} |
|---|
| 306 |
|
|---|
| 307 |
static int usb_stor_control_thread(void * __us) |
|---|
| 308 |
{ |
|---|
| 309 |
struct us_data *us = (struct us_data *)__us; |
|---|
| 310 |
struct Scsi_Host *host = us_to_host(us); |
|---|
| 311 |
|
|---|
| 312 |
for(;;) { |
|---|
| 313 |
US_DEBUGP("*** thread sleeping.\n"); |
|---|
| 314 |
if(down_interruptible(&us->sema)) |
|---|
| 315 |
break; |
|---|
| 316 |
|
|---|
| 317 |
US_DEBUGP("*** thread awakened.\n"); |
|---|
| 318 |
|
|---|
| 319 |
/* lock the device pointers */ |
|---|
| 320 |
mutex_lock(&(us->dev_mutex)); |
|---|
| 321 |
|
|---|
| 322 |
/* if the device has disconnected, we are free to exit */ |
|---|
| 323 |
if (test_bit(US_FLIDX_DISCONNECTING, &us->flags)) { |
|---|
| 324 |
US_DEBUGP("-- exiting\n"); |
|---|
| 325 |
mutex_unlock(&us->dev_mutex); |
|---|
| 326 |
break; |
|---|
| 327 |
} |
|---|
| 328 |
|
|---|
| 329 |
/* lock access to the state */ |
|---|
| 330 |
scsi_lock(host); |
|---|
| 331 |
|
|---|
| 332 |
/* has the command timed out *already* ? */ |
|---|
| 333 |
if (test_bit(US_FLIDX_TIMED_OUT, &us->flags)) { |
|---|
| 334 |
us->srb->result = DID_ABORT << 16; |
|---|
| 335 |
goto SkipForAbort; |
|---|
| 336 |
} |
|---|
| 337 |
|
|---|
| 338 |
scsi_unlock(host); |
|---|
| 339 |
|
|---|
| 340 |
/* reject the command if the direction indicator |
|---|
| 341 |
* is UNKNOWN |
|---|
| 342 |
*/ |
|---|
| 343 |
if (us->srb->sc_data_direction == DMA_BIDIRECTIONAL) { |
|---|
| 344 |
US_DEBUGP("UNKNOWN data direction\n"); |
|---|
| 345 |
us->srb->result = DID_ERROR << 16; |
|---|
| 346 |
} |
|---|
| 347 |
|
|---|
| 348 |
/* reject if target != 0 or if LUN is higher than |
|---|
| 349 |
* the maximum known LUN |
|---|
| 350 |
*/ |
|---|
| 351 |
else if (us->srb->device->id && |
|---|
| 352 |
!(us->flags & US_FL_SCM_MULT_TARG)) { |
|---|
| 353 |
US_DEBUGP("Bad target number (%d:%d)\n", |
|---|
| 354 |
us->srb->device->id, us->srb->device->lun); |
|---|
| 355 |
us->srb->result = DID_BAD_TARGET << 16; |
|---|
| 356 |
} |
|---|
| 357 |
|
|---|
| 358 |
else if (us->srb->device->lun > us->max_lun) { |
|---|
| 359 |
US_DEBUGP("Bad LUN (%d:%d)\n", |
|---|
| 360 |
us->srb->device->id, us->srb->device->lun); |
|---|
| 361 |
us->srb->result = DID_BAD_TARGET << 16; |
|---|
| 362 |
} |
|---|
| 363 |
|
|---|
| 364 |
/* Handle those devices which need us to fake |
|---|
| 365 |
* their inquiry data */ |
|---|
| 366 |
else if ((us->srb->cmnd[0] == INQUIRY) && |
|---|
| 367 |
(us->flags & US_FL_FIX_INQUIRY)) { |
|---|
| 368 |
unsigned char data_ptr[36] = { |
|---|
| 369 |
0x00, 0x80, 0x02, 0x02, |
|---|
| 370 |
0x1F, 0x00, 0x00, 0x00}; |
|---|
| 371 |
|
|---|
| 372 |
US_DEBUGP("Faking INQUIRY command\n"); |
|---|
| 373 |
fill_inquiry_response(us, data_ptr, 36); |
|---|
| 374 |
us->srb->result = SAM_STAT_GOOD; |
|---|
| 375 |
} |
|---|
| 376 |
|
|---|
| 377 |
/* we've got a command, let's do it! */ |
|---|
| 378 |
else { |
|---|
| 379 |
US_DEBUG(usb_stor_show_command(us->srb)); |
|---|
| 380 |
us->proto_handler(us->srb, us); |
|---|
| 381 |
} |
|---|
| 382 |
|
|---|
| 383 |
/* lock access to the state */ |
|---|
| 384 |
scsi_lock(host); |
|---|
| 385 |
|
|---|
| 386 |
/* did the command already complete because of a disconnect? */ |
|---|
| 387 |
if (!us->srb) |
|---|
| 388 |
; /* nothing to do */ |
|---|
| 389 |
|
|---|
| 390 |
/* indicate that the command is done */ |
|---|
| 391 |
else if (us->srb->result != DID_ABORT << 16) { |
|---|
| 392 |
US_DEBUGP("scsi cmd done, result=0x%x\n", |
|---|
| 393 |
us->srb->result); |
|---|
| 394 |
us->srb->scsi_done(us->srb); |
|---|
| 395 |
} else { |
|---|
| 396 |
SkipForAbort: |
|---|
| 397 |
US_DEBUGP("scsi command aborted\n"); |
|---|
| 398 |
} |
|---|
| 399 |
|
|---|
| 400 |
/* If an abort request was received we need to signal that |
|---|
| 401 |
* the abort has finished. The proper test for this is |
|---|
| 402 |
* the TIMED_OUT flag, not srb->result == DID_ABORT, because |
|---|
| 403 |
* the timeout might have occurred after the command had |
|---|
| 404 |
* already completed with a different result code. */ |
|---|
| 405 |
if (test_bit(US_FLIDX_TIMED_OUT, &us->flags)) { |
|---|
| 406 |
complete(&(us->notify)); |
|---|
| 407 |
|
|---|
| 408 |
/* Allow USB transfers to resume */ |
|---|
| 409 |
clear_bit(US_FLIDX_ABORTING, &us->flags); |
|---|
| 410 |
clear_bit(US_FLIDX_TIMED_OUT, &us->flags); |
|---|
| 411 |
} |
|---|
| 412 |
|
|---|
| 413 |
/* finished working on this command */ |
|---|
| 414 |
us->srb = NULL; |
|---|
| 415 |
scsi_unlock(host); |
|---|
| 416 |
|
|---|
| 417 |
/* unlock the device pointers */ |
|---|
| 418 |
mutex_unlock(&us->dev_mutex); |
|---|
| 419 |
} /* for (;;) */ |
|---|
| 420 |
|
|---|
| 421 |
/* Wait until we are told to stop */ |
|---|
| 422 |
for (;;) { |
|---|
| 423 |
set_current_state(TASK_INTERRUPTIBLE); |
|---|
| 424 |
if (kthread_should_stop()) |
|---|
| 425 |
break; |
|---|
| 426 |
schedule(); |
|---|
| 427 |
} |
|---|
| 428 |
__set_current_state(TASK_RUNNING); |
|---|
| 429 |
return 0; |
|---|
| 430 |
} |
|---|
| 431 |
|
|---|
| 432 |
/*********************************************************************** |
|---|
| 433 |
* Device probing and disconnecting |
|---|
| 434 |
***********************************************************************/ |
|---|
| 435 |
|
|---|
| 436 |
/* Associate our private data with the USB device */ |
|---|
| 437 |
static int associate_dev(struct us_data *us, struct usb_interface *intf) |
|---|
| 438 |
{ |
|---|
| 439 |
US_DEBUGP("-- %s\n", __FUNCTION__); |
|---|
| 440 |
|
|---|
| 441 |
/* Fill in the device-related fields */ |
|---|
| 442 |
us->pusb_dev = interface_to_usbdev(intf); |
|---|
| 443 |
us->pusb_intf = intf; |
|---|
| 444 |
us->ifnum = intf->cur_altsetting->desc.bInterfaceNumber; |
|---|
| 445 |
US_DEBUGP("Vendor: 0x%04x, Product: 0x%04x, Revision: 0x%04x\n", |
|---|
| 446 |
le16_to_cpu(us->pusb_dev->descriptor.idVendor), |
|---|
| 447 |
le16_to_cpu(us->pusb_dev->descriptor.idProduct), |
|---|
| 448 |
le16_to_cpu(us->pusb_dev->descriptor.bcdDevice)); |
|---|
| 449 |
US_DEBUGP("Interface Subclass: 0x%02x, Protocol: 0x%02x\n", |
|---|
| 450 |
intf->cur_altsetting->desc.bInterfaceSubClass, |
|---|
| 451 |
intf->cur_altsetting->desc.bInterfaceProtocol); |
|---|
| 452 |
|
|---|
| 453 |
/* Store our private data in the interface */ |
|---|
| 454 |
usb_set_intfdata(intf, us); |
|---|
| 455 |
|
|---|
| 456 |
/* Allocate the device-related DMA-mapped buffers */ |
|---|
| 457 |
us->cr = usb_buffer_alloc(us->pusb_dev, sizeof(*us->cr), |
|---|
| 458 |
GFP_KERNEL, &us->cr_dma); |
|---|
| 459 |
if (!us->cr) { |
|---|
| 460 |
US_DEBUGP("usb_ctrlrequest allocation failed\n"); |
|---|
| 461 |
return -ENOMEM; |
|---|
| 462 |
} |
|---|
| 463 |
|
|---|
| 464 |
us->iobuf = usb_buffer_alloc(us->pusb_dev, US_IOBUF_SIZE, |
|---|
| 465 |
GFP_KERNEL, &us->iobuf_dma); |
|---|
| 466 |
if (!us->iobuf) { |
|---|
| 467 |
US_DEBUGP("I/O buffer allocation failed\n"); |
|---|
| 468 |
return -ENOMEM; |
|---|
| 469 |
} |
|---|
| 470 |
|
|---|
| 471 |
us->sensebuf = kmalloc(US_SENSE_SIZE, GFP_KERNEL); |
|---|
| 472 |
if (!us->sensebuf) { |
|---|
| 473 |
US_DEBUGP("Sense buffer allocation failed\n"); |
|---|
| 474 |
return -ENOMEM; |
|---|
| 475 |
} |
|---|
| 476 |
return 0; |
|---|
| 477 |
} |
|---|
| 478 |
|
|---|
| 479 |
/* Find an unusual_dev descriptor (always succeeds in the current code) */ |
|---|
| 480 |
static struct us_unusual_dev *find_unusual(const struct usb_device_id *id) |
|---|
| 481 |
{ |
|---|
| 482 |
const int id_index = id - storage_usb_ids; |
|---|
| 483 |
return &us_unusual_dev_list[id_index]; |
|---|
| 484 |
} |
|---|
| 485 |
|
|---|
| 486 |
/* Get the unusual_devs entries and the string descriptors */ |
|---|
| 487 |
static int get_device_info(struct us_data *us, const struct usb_device_id *id) |
|---|
| 488 |
{ |
|---|
| 489 |
struct usb_device *dev = us->pusb_dev; |
|---|
| 490 |
struct usb_interface_descriptor *idesc = |
|---|
| 491 |
&us->pusb_intf->cur_altsetting->desc; |
|---|
| 492 |
struct us_unusual_dev *unusual_dev = find_unusual(id); |
|---|
| 493 |
|
|---|
| 494 |
/* Store the entries */ |
|---|
| 495 |
us->unusual_dev = unusual_dev; |
|---|
| 496 |
us->subclass = (unusual_dev->useProtocol == US_SC_DEVICE) ? |
|---|
| 497 |
idesc->bInterfaceSubClass : |
|---|
| 498 |
unusual_dev->useProtocol; |
|---|
| 499 |
us->protocol = (unusual_dev->useTransport == US_PR_DEVICE) ? |
|---|
| 500 |
idesc->bInterfaceProtocol : |
|---|
| 501 |
unusual_dev->useTransport; |
|---|
| 502 |
us->flags = USB_US_ORIG_FLAGS(id->driver_info); |
|---|
| 503 |
|
|---|
| 504 |
if (us->flags & US_FL_IGNORE_DEVICE) { |
|---|
| 505 |
printk(KERN_INFO USB_STORAGE "device ignored\n"); |
|---|
| 506 |
return -ENODEV; |
|---|
| 507 |
} |
|---|
| 508 |
|
|---|
| 509 |
/* |
|---|
| 510 |
* This flag is only needed when we're in high-speed, so let's |
|---|
| 511 |
* disable it if we're in full-speed |
|---|
| 512 |
*/ |
|---|
| 513 |
if (dev->speed != USB_SPEED_HIGH) |
|---|
| 514 |
us->flags &= ~US_FL_GO_SLOW; |
|---|
| 515 |
|
|---|
| 516 |
/* Log a message if a non-generic unusual_dev entry contains an |
|---|
| 517 |
* unnecessary subclass or protocol override. This may stimulate |
|---|
| 518 |
* reports from users that will help us remove unneeded entries |
|---|
| 519 |
* from the unusual_devs.h table. |
|---|
| 520 |
*/ |
|---|
| 521 |
if (id->idVendor || id->idProduct) { |
|---|
| 522 |
static const char *msgs[3] = { |
|---|
| 523 |
"an unneeded SubClass entry", |
|---|
| 524 |
"an unneeded Protocol entry", |
|---|
| 525 |
"unneeded SubClass and Protocol entries"}; |
|---|
| 526 |
struct usb_device_descriptor *ddesc = &dev->descriptor; |
|---|
| 527 |
int msg = -1; |
|---|
| 528 |
|
|---|
| 529 |
if (unusual_dev->useProtocol != US_SC_DEVICE && |
|---|
| 530 |
us->subclass == idesc->bInterfaceSubClass) |
|---|
| 531 |
msg += 1; |
|---|
| 532 |
if (unusual_dev->useTransport != US_PR_DEVICE && |
|---|
| 533 |
us->protocol == idesc->bInterfaceProtocol) |
|---|
| 534 |
msg += 2; |
|---|
| 535 |
if (msg >= 0 && !(us->flags & US_FL_NEED_OVERRIDE)) |
|---|
| 536 |
printk(KERN_NOTICE USB_STORAGE "This device " |
|---|
| 537 |
"(%04x,%04x,%04x S %02x P %02x)" |
|---|
| 538 |
" has %s in unusual_devs.h (kernel" |
|---|
| 539 |
" %s)\n" |
|---|
| 540 |
" Please send a copy of this message to " |
|---|
| 541 |
"<linux-usb-devel@lists.sourceforge.net>\n", |
|---|
| 542 |
le16_to_cpu(ddesc->idVendor), |
|---|
| 543 |
le16_to_cpu(ddesc->idProduct), |
|---|
| 544 |
le16_to_cpu(ddesc->bcdDevice), |
|---|
| 545 |
idesc->bInterfaceSubClass, |
|---|
| 546 |
idesc->bInterfaceProtocol, |
|---|
| 547 |
msgs[msg], |
|---|
| 548 |
utsname()->release); |
|---|
| 549 |
} |
|---|
| 550 |
|
|---|
| 551 |
return 0; |
|---|
| 552 |
} |
|---|
| 553 |
|
|---|
| 554 |
/* Get the transport settings */ |
|---|
| 555 |
static int get_transport(struct us_data *us) |
|---|
| 556 |
{ |
|---|
| 557 |
switch (us->protocol) { |
|---|
| 558 |
case US_PR_CB: |
|---|
| 559 |
us->transport_name = "Control/Bulk"; |
|---|
| 560 |
us->transport = usb_stor_CB_transport; |
|---|
| 561 |
us->transport_reset = usb_stor_CB_reset; |
|---|
| 562 |
us->max_lun = 7; |
|---|
| 563 |
break; |
|---|
| 564 |
|
|---|
| 565 |
case US_PR_CBI: |
|---|
| 566 |
us->transport_name = "Control/Bulk/Interrupt"; |
|---|
| 567 |
us->transport = usb_stor_CBI_transport; |
|---|
| 568 |
us->transport_reset = usb_stor_CB_reset; |
|---|
| 569 |
us->max_lun = 7; |
|---|
| 570 |
break; |
|---|
| 571 |
|
|---|
| 572 |
case US_PR_BULK: |
|---|
| 573 |
us->transport_name = "Bulk"; |
|---|
| 574 |
us->transport = usb_stor_Bulk_transport; |
|---|
| 575 |
us->transport_reset = usb_stor_Bulk_reset; |
|---|
| 576 |
break; |
|---|
| 577 |
|
|---|
| 578 |
#ifdef CONFIG_USB_STORAGE_USBAT |
|---|
| 579 |
case US_PR_USBAT: |
|---|
| 580 |
us->transport_name = "Shuttle USBAT"; |
|---|
| 581 |
us->transport = usbat_transport; |
|---|
| 582 |
us->transport_reset = usb_stor_CB_reset; |
|---|
| 583 |
us->max_lun = 1; |
|---|
| 584 |
break; |
|---|
| 585 |
#endif |
|---|
| 586 |
|
|---|
| 587 |
#ifdef CONFIG_USB_STORAGE_SDDR09 |
|---|
| 588 |
case US_PR_EUSB_SDDR09: |
|---|
| 589 |
us->transport_name = "EUSB/SDDR09"; |
|---|
| 590 |
us->transport = sddr09_transport; |
|---|
| 591 |
us->transport_reset = usb_stor_CB_reset; |
|---|
| 592 |
us->max_lun = 0; |
|---|
| 593 |
break; |
|---|
| 594 |
#endif |
|---|
| 595 |
|
|---|
| 596 |
#ifdef CONFIG_USB_STORAGE_SDDR55 |
|---|
| 597 |
case US_PR_SDDR55: |
|---|
| 598 |
us->transport_name = "SDDR55"; |
|---|
| 599 |
us->transport = sddr55_transport; |
|---|
| 600 |
us->transport_reset = sddr55_reset; |
|---|
| 601 |
us->max_lun = 0; |
|---|
| 602 |
break; |
|---|
| 603 |
#endif |
|---|
| 604 |
|
|---|
| 605 |
#ifdef CONFIG_USB_STORAGE_DPCM |
|---|
| 606 |
case US_PR_DPCM_USB: |
|---|
| 607 |
us->transport_name = "Control/Bulk-EUSB/SDDR09"; |
|---|
| 608 |
us->transport = dpcm_transport; |
|---|
| 609 |
us->transport_reset = usb_stor_CB_reset; |
|---|
| 610 |
us->max_lun = 1; |
|---|
| 611 |
break; |
|---|
| 612 |
#endif |
|---|
| 613 |
|
|---|
| 614 |
#ifdef CONFIG_USB_STORAGE_FREECOM |
|---|
| 615 |
case US_PR_FREECOM: |
|---|
| 616 |
us->transport_name = "Freecom"; |
|---|
| 617 |
us->transport = freecom_transport; |
|---|
| 618 |
us->transport_reset = usb_stor_freecom_reset; |
|---|
| 619 |
us->max_lun = 0; |
|---|
| 620 |
break; |
|---|
| 621 |
#endif |
|---|
| 622 |
|
|---|
| 623 |
#ifdef CONFIG_USB_STORAGE_DATAFAB |
|---|
| 624 |
case US_PR_DATAFAB: |
|---|
| 625 |
us->transport_name = "Datafab Bulk-Only"; |
|---|
| 626 |
us->transport = datafab_transport; |
|---|
| 627 |
us->transport_reset = usb_stor_Bulk_reset; |
|---|
| 628 |
us->max_lun = 1; |
|---|
| 629 |
break; |
|---|
| 630 |
#endif |
|---|
| 631 |
|
|---|
| 632 |
#ifdef CONFIG_USB_STORAGE_JUMPSHOT |
|---|
| 633 |
case US_PR_JUMPSHOT: |
|---|
| 634 |
us->transport_name = "Lexar Jumpshot Control/Bulk"; |
|---|
| 635 |
us->transport = jumpshot_transport; |
|---|
| 636 |
us->transport_reset = usb_stor_Bulk_reset; |
|---|
| 637 |
us->max_lun = 1; |
|---|
| 638 |
break; |
|---|
| 639 |
#endif |
|---|
| 640 |
|
|---|
| 641 |
#ifdef CONFIG_USB_STORAGE_ALAUDA |
|---|
| 642 |
case US_PR_ALAUDA: |
|---|
| 643 |
us->transport_name = "Alauda Control/Bulk"; |
|---|
| 644 |
us->transport = alauda_transport; |
|---|
| 645 |
us->transport_reset = usb_stor_Bulk_reset; |
|---|
| 646 |
us->max_lun = 1; |
|---|
| 647 |
break; |
|---|
| 648 |
#endif |
|---|
| 649 |
|
|---|
| 650 |
#ifdef CONFIG_USB_STORAGE_KARMA |
|---|
| 651 |
case US_PR_KARMA: |
|---|
| 652 |
us->transport_name = "Rio Karma/Bulk"; |
|---|
| 653 |
us->transport = rio_karma_transport; |
|---|
| 654 |
us->transport_reset = usb_stor_Bulk_reset; |
|---|
| 655 |
break; |
|---|
| 656 |
#endif |
|---|
| 657 |
|
|---|
| 658 |
default: |
|---|
| 659 |
return -EIO; |
|---|
| 660 |
} |
|---|
| 661 |
US_DEBUGP("Transport: %s\n", us->transport_name); |
|---|
| 662 |
|
|---|
| 663 |
/* fix for single-lun devices */ |
|---|
| 664 |
if (us->flags & US_FL_SINGLE_LUN) |
|---|
| 665 |
us->max_lun = 0; |
|---|
| 666 |
return 0; |
|---|
| 667 |
} |
|---|
| 668 |
|
|---|
| 669 |
/* Get the protocol settings */ |
|---|
| 670 |
static int get_protocol(struct us_data *us) |
|---|
| 671 |
{ |
|---|
| 672 |
switch (us->subclass) { |
|---|
| 673 |
case US_SC_RBC: |
|---|
| 674 |
us->protocol_name = "Reduced Block Commands (RBC)"; |
|---|
| 675 |
us->proto_handler = usb_stor_transparent_scsi_command; |
|---|
| 676 |
break; |
|---|
| 677 |
|
|---|
| 678 |
case US_SC_8020: |
|---|
| 679 |
us->protocol_name = "8020i"; |
|---|
| 680 |
us->proto_handler = usb_stor_ATAPI_command; |
|---|
| 681 |
us->max_lun = 0; |
|---|
| 682 |
break; |
|---|
| 683 |
|
|---|
| 684 |
case US_SC_QIC: |
|---|
| 685 |
us->protocol_name = "QIC-157"; |
|---|
| 686 |
us->proto_handler = usb_stor_qic157_command; |
|---|
| 687 |
us->max_lun = 0; |
|---|
| 688 |
break; |
|---|
| 689 |
|
|---|
| 690 |
case US_SC_8070: |
|---|
| 691 |
us->protocol_name = "8070i"; |
|---|
| 692 |
us->proto_handler = usb_stor_ATAPI_command; |
|---|
| 693 |
us->max_lun = 0; |
|---|
| 694 |
break; |
|---|
| 695 |
|
|---|
| 696 |
case US_SC_SCSI: |
|---|
| 697 |
us->protocol_name = "Transparent SCSI"; |
|---|
| 698 |
us->proto_handler = usb_stor_transparent_scsi_command; |
|---|
| 699 |
break; |
|---|
| 700 |
|
|---|
| 701 |
case US_SC_UFI: |
|---|
| 702 |
us->protocol_name = "Uniform Floppy Interface (UFI)"; |
|---|
| 703 |
us->proto_handler = usb_stor_ufi_command; |
|---|
| 704 |
break; |
|---|
| 705 |
|
|---|
| 706 |
#ifdef CONFIG_USB_STORAGE_ISD200 |
|---|
| 707 |
case US_SC_ISD200: |
|---|
| 708 |
us->protocol_name = "ISD200 ATA/ATAPI"; |
|---|
| 709 |
us->proto_handler = isd200_ata_command; |
|---|
| 710 |
break; |
|---|
| 711 |
#endif |
|---|
| 712 |
|
|---|
| 713 |
default: |
|---|
| 714 |
return -EIO; |
|---|
| 715 |
} |
|---|
| 716 |
US_DEBUGP("Protocol: %s\n", us->protocol_name); |
|---|
| 717 |
return 0; |
|---|
| 718 |
} |
|---|
| 719 |
|
|---|
| 720 |
/* Get the pipe settings */ |
|---|
| 721 |
static int get_pipes(struct us_data *us) |
|---|
| 722 |
{ |
|---|
| 723 |
struct usb_host_interface *altsetting = |
|---|
| 724 |
us->pusb_intf->cur_altsetting; |
|---|
| 725 |
int i; |
|---|
| 726 |
struct usb_endpoint_descriptor *ep; |
|---|
| 727 |
struct usb_endpoint_descriptor *ep_in = NULL; |
|---|
| 728 |
struct usb_endpoint_descriptor *ep_out = NULL; |
|---|
| 729 |
struct usb_endpoint_descriptor *ep_int = NULL; |
|---|
| 730 |
|
|---|
| 731 |
/* |
|---|
| 732 |
* Find the first endpoint of each type we need. |
|---|
| 733 |
* We are expecting a minimum of 2 endpoints - in and out (bulk). |
|---|
| 734 |
* An optional interrupt-in is OK (necessary for CBI protocol). |
|---|
| 735 |
* We will ignore any others. |
|---|
| 736 |
*/ |
|---|
| 737 |
for (i = 0; i < altsetting->desc.bNumEndpoints; i++) { |
|---|
| 738 |
ep = &altsetting->endpoint[i].desc; |
|---|
| 739 |
|
|---|
| 740 |
if (usb_endpoint_xfer_bulk(ep)) { |
|---|
| 741 |
if (usb_endpoint_dir_in(ep)) { |
|---|
| 742 |
if (!ep_in) |
|---|
| 743 |
ep_in = ep; |
|---|
| 744 |
} else { |
|---|
| 745 |
if (!ep_out) |
|---|
| 746 |
ep_out = ep; |
|---|
| 747 |
} |
|---|
| 748 |
} |
|---|
| 749 |
|
|---|
| 750 |
else if (usb_endpoint_is_int_in(ep)) { |
|---|
| 751 |
if (!ep_int) |
|---|
| 752 |
ep_int = ep; |
|---|
| 753 |
} |
|---|
| 754 |
} |
|---|
| 755 |
|
|---|
| 756 |
if (!ep_in || !ep_out || (us->protocol == US_PR_CBI && !ep_int)) { |
|---|
| 757 |
US_DEBUGP("Endpoint sanity check failed! Rejecting dev.\n"); |
|---|
| 758 |
return -EIO; |
|---|
| 759 |
} |
|---|
| 760 |
|
|---|
| 761 |
/* Calculate and store the pipe values */ |
|---|
| 762 |
us->send_ctrl_pipe = usb_sndctrlpipe(us->pusb_dev, 0); |
|---|
| 763 |
us->recv_ctrl_pipe = usb_rcvctrlpipe(us->pusb_dev, 0); |
|---|
| 764 |
us->send_bulk_pipe = usb_sndbulkpipe(us->pusb_dev, |
|---|
| 765 |
ep_out->bEndpointAddress & USB_ENDPOINT_NUMBER_MASK); |
|---|
| 766 |
us->recv_bulk_pipe = usb_rcvbulkpipe(us->pusb_dev, |
|---|
| 767 |
ep_in->bEndpointAddress & USB_ENDPOINT_NUMBER_MASK); |
|---|
| 768 |
if (ep_int) { |
|---|
| 769 |
us->recv_intr_pipe = usb_rcvintpipe(us->pusb_dev, |
|---|
| 770 |
ep_int->bEndpointAddress & USB_ENDPOINT_NUMBER_MASK); |
|---|
| 771 |
us->ep_bInterval = ep_int->bInterval; |
|---|
| 772 |
} |
|---|
| 773 |
return 0; |
|---|
| 774 |
} |
|---|
| 775 |
|
|---|
| 776 |
/* Initialize all the dynamic resources we need */ |
|---|
| 777 |
static int usb_stor_acquire_resources(struct us_data *us) |
|---|
| 778 |
{ |
|---|
| 779 |
int p; |
|---|
| 780 |
struct task_struct *th; |
|---|
| 781 |
|
|---|
| 782 |
us->current_urb = usb_alloc_urb(0, GFP_KERNEL); |
|---|
| 783 |
if (!us->current_urb) { |
|---|
| 784 |
US_DEBUGP("URB allocation failed\n"); |
|---|
| 785 |
return -ENOMEM; |
|---|
| 786 |
} |
|---|
| 787 |
|
|---|
| 788 |
/* Just before we start our control thread, initialize |
|---|
| 789 |
* the device if it needs initialization */ |
|---|
| 790 |
if (us->unusual_dev->initFunction) { |
|---|
| 791 |
p = us->unusual_dev->initFunction(us); |
|---|
| 792 |
if (p) |
|---|
| 793 |
return p; |
|---|
| 794 |
} |
|---|
| 795 |
|
|---|
| 796 |
/* Start up our control thread */ |
|---|
| 797 |
th = kthread_run(usb_stor_control_thread, us, "usb-storage"); |
|---|
| 798 |
if (IS_ERR(th)) { |
|---|
| 799 |
printk(KERN_WARNING USB_STORAGE |
|---|
| 800 |
"Unable to start control thread\n"); |
|---|
| 801 |
return PTR_ERR(th); |
|---|
| 802 |
} |
|---|
| 803 |
us->ctl_thread = th; |
|---|
| 804 |
|
|---|
| 805 |
return 0; |
|---|
| 806 |
} |
|---|
| 807 |
|
|---|
| 808 |
/* Release all our dynamic resources */ |
|---|
| 809 |
static void usb_stor_release_resources(struct us_data *us) |
|---|
| 810 |
{ |
|---|
| 811 |
US_DEBUGP("-- %s\n", __FUNCTION__); |
|---|
| 812 |
|
|---|
| 813 |
/* Tell the control thread to exit. The SCSI host must |
|---|
| 814 |
* already have been removed so it won't try to queue |
|---|
| 815 |
* any more commands. |
|---|
| 816 |
*/ |
|---|
| 817 |
US_DEBUGP("-- sending exit command to thread\n"); |
|---|
| 818 |
set_bit(US_FLIDX_DISCONNECTING, &us->flags); |
|---|
| 819 |
up(&us->sema); |
|---|
| 820 |
if (us->ctl_thread) |
|---|
| 821 |
kthread_stop(us->ctl_thread); |
|---|
| 822 |
|
|---|
| 823 |
/* Call the destructor routine, if it exists */ |
|---|
| 824 |
if (us->extra_destructor) { |
|---|
| 825 |
US_DEBUGP("-- calling extra_destructor()\n"); |
|---|
| 826 |
us->extra_destructor(us->extra); |
|---|
| 827 |
} |
|---|
| 828 |
|
|---|
| 829 |
/* Free the extra data and the URB */ |
|---|
| 830 |
kfree(us->extra); |
|---|
| 831 |
usb_free_urb(us->current_urb); |
|---|
| 832 |
} |
|---|
| 833 |
|
|---|
| 834 |
/* Dissociate from the USB device */ |
|---|
| 835 |
static void dissociate_dev(struct us_data *us) |
|---|
| 836 |
{ |
|---|
| 837 |
US_DEBUGP("-- %s\n", __FUNCTION__); |
|---|
| 838 |
|
|---|
| 839 |
kfree(us->sensebuf); |
|---|
| 840 |
|
|---|
| 841 |
/* Free the device-related DMA-mapped buffers */ |
|---|
| 842 |
if (us->cr) |
|---|
| 843 |
usb_buffer_free(us->pusb_dev, sizeof(*us->cr), us->cr, |
|---|
| 844 |
us->cr_dma); |
|---|
| 845 |
if (us->iobuf) |
|---|
| 846 |
usb_buffer_free(us->pusb_dev, US_IOBUF_SIZE, us->iobuf, |
|---|
| 847 |
us->iobuf_dma); |
|---|
| 848 |
|
|---|
| 849 |
/* Remove our private data from the interface */ |
|---|
| 850 |
usb_set_intfdata(us->pusb_intf, NULL); |
|---|
| 851 |
} |
|---|
| 852 |
|
|---|
| 853 |
/* First stage of disconnect processing: stop all commands and remove |
|---|
| 854 |
* the host */ |
|---|
| 855 |
static void quiesce_and_remove_host(struct us_data *us) |
|---|
| 856 |
{ |
|---|
| 857 |
struct Scsi_Host *host = us_to_host(us); |
|---|
| 858 |
|
|---|
| 859 |
/* Prevent new USB transfers, stop the current command, and |
|---|
| 860 |
* interrupt a SCSI-scan or device-reset delay */ |
|---|
| 861 |
scsi_lock(host); |
|---|
| 862 |
set_bit(US_FLIDX_DISCONNECTING, &us->flags); |
|---|
| 863 |
scsi_unlock(host); |
|---|
| 864 |
usb_stor_stop_transport(us); |
|---|
| 865 |
wake_up(&us->delay_wait); |
|---|
| 866 |
|
|---|
| 867 |
/* queuecommand won't accept any new commands and the control |
|---|
| 868 |
* thread won't execute a previously-queued command. If there |
|---|
| 869 |
* is such a command pending, complete it with an error. */ |
|---|
| 870 |
mutex_lock(&us->dev_mutex); |
|---|
| 871 |
if (us->srb) { |
|---|
| 872 |
us->srb->result = DID_NO_CONNECT << 16; |
|---|
| 873 |
scsi_lock(host); |
|---|
| 874 |
us->srb->scsi_done(us->srb); |
|---|
| 875 |
us->srb = NULL; |
|---|
| 876 |
complete(&us->notify); /* in case of an abort */ |
|---|
| 877 |
scsi_unlock(host); |
|---|
| 878 |
} |
|---|
| 879 |
mutex_unlock(&us->dev_mutex); |
|---|
| 880 |
|
|---|
| 881 |
/* Now we own no commands so it's safe to remove the SCSI host */ |
|---|
| 882 |
scsi_remove_host(host); |
|---|
| 883 |
|
|---|
| 884 |
/* Wait for the SCSI-scanning thread to stop */ |
|---|
| 885 |
wait_for_completion(&us->scanning_done); |
|---|
| 886 |
} |
|---|
| 887 |
|
|---|
| 888 |
/* Second stage of disconnect processing: deallocate all resources */ |
|---|
| 889 |
static void release_everything(struct us_data *us) |
|---|
| 890 |
{ |
|---|
| 891 |
usb_stor_release_resources(us); |
|---|
| 892 |
dissociate_dev(us); |
|---|
| 893 |
|
|---|
| 894 |
/* Drop our reference to the host; the SCSI core will free it |
|---|
| 895 |
* (and "us" along with it) when the refcount becomes 0. */ |
|---|
| 896 |
scsi_host_put(us_to_host(us)); |
|---|
| 897 |
} |
|---|
| 898 |
|
|---|
| 899 |
/* Thread to carry out delayed SCSI-device scanning */ |
|---|
| 900 |
static int usb_stor_scan_thread(void * __us) |
|---|
| 901 |
{ |
|---|
| 902 |
struct us_data *us = (struct us_data *)__us; |
|---|
| 903 |
|
|---|
| 904 |
printk(KERN_DEBUG |
|---|
| 905 |
"usb-storage: device found at %d\n", us->pusb_dev->devnum); |
|---|
| 906 |
|
|---|
| 907 |
set_freezable(); |
|---|
| 908 |
/* Wait for the timeout to expire or for a disconnect */ |
|---|
| 909 |
if (delay_use > 0) { |
|---|
| 910 |
printk(KERN_DEBUG "usb-storage: waiting for device " |
|---|
| 911 |
"to settle before scanning\n"); |
|---|
| 912 |
retry: |
|---|
| 913 |
wait_event_interruptible_timeout(us->delay_wait, |
|---|
| 914 |
test_bit(US_FLIDX_DISCONNECTING, &us->flags), |
|---|
| 915 |
delay_use * HZ); |
|---|
| 916 |
if (try_to_freeze()) |
|---|
| 917 |
goto retry; |
|---|
| 918 |
} |
|---|
| 919 |
|
|---|
| 920 |
/* If the device is still connected, perform the scanning */ |
|---|
| 921 |
if (!test_bit(US_FLIDX_DISCONNECTING, &us->flags)) { |
|---|
| 922 |
|
|---|
| 923 |
/* For bulk-only devices, determine the max LUN value */ |
|---|
| 924 |
if (us->protocol == US_PR_BULK && |
|---|
| 925 |
!(us->flags & US_FL_SINGLE_LUN)) { |
|---|
| 926 |
mutex_lock(&us->dev_mutex); |
|---|
| 927 |
us->max_lun = usb_stor_Bulk_max_lun(us); |
|---|
| 928 |
mutex_unlock(&us->dev_mutex); |
|---|
| 929 |
} |
|---|
| 930 |
scsi_scan_host(us_to_host(us)); |
|---|
| 931 |
printk(KERN_DEBUG "usb-storage: device scan complete\n"); |
|---|
| 932 |
|
|---|
| 933 |
/* Should we unbind if no devices were detected? */ |
|---|
| 934 |
} |
|---|
| 935 |
|
|---|
| 936 |
complete_and_exit(&us->scanning_done, 0); |
|---|
| 937 |
} |
|---|
| 938 |
|
|---|
| 939 |
|
|---|
| 940 |
/* Probe to see if we can drive a newly-connected USB device */ |
|---|
| 941 |
static int storage_probe(struct usb_interface *intf, |
|---|
| 942 |
const struct usb_device_id *id) |
|---|
| 943 |
{ |
|---|
| 944 |
struct Scsi_Host *host; |
|---|
| 945 |
struct us_data *us; |
|---|
| 946 |
int result; |
|---|
| 947 |
struct task_struct *th; |
|---|
| 948 |
|
|---|
| 949 |
if (usb_usual_check_type(id, USB_US_TYPE_STOR)) |
|---|
| 950 |
return -ENXIO; |
|---|
| 951 |
|
|---|
| 952 |
US_DEBUGP("USB Mass Storage device detected\n"); |
|---|
| 953 |
|
|---|
| 954 |
/* |
|---|
| 955 |
* Ask the SCSI layer to allocate a host structure, with extra |
|---|
| 956 |
* space at the end for our private us_data structure. |
|---|
| 957 |
*/ |
|---|
| 958 |
host = scsi_host_alloc(&usb_stor_host_template, sizeof(*us)); |
|---|
| 959 |
if (!host) { |
|---|
| 960 |
printk(KERN_WARNING USB_STORAGE |
|---|
| 961 |
"Unable to allocate the scsi host\n"); |
|---|
| 962 |
return -ENOMEM; |
|---|
| 963 |
} |
|---|
| 964 |
|
|---|
| 965 |
us = host_to_us(host); |
|---|
| 966 |
memset(us, 0, sizeof(struct us_data)); |
|---|
| 967 |
mutex_init(&(us->dev_mutex)); |
|---|
| 968 |
init_MUTEX_LOCKED(&(us->sema)); |
|---|
| 969 |
init_completion(&(us->notify)); |
|---|
| 970 |
init_waitqueue_head(&us->delay_wait); |
|---|
| 971 |
init_completion(&us->scanning_done); |
|---|
| 972 |
|
|---|
| 973 |
/* Associate the us_data structure with the USB device */ |
|---|
| 974 |
result = associate_dev(us, intf); |
|---|
| 975 |
if (result) |
|---|
| 976 |
goto BadDevice; |
|---|
| 977 |
|
|---|
| 978 |
/* |
|---|
| 979 |
* Get the unusual_devs entries and the descriptors |
|---|
| 980 |
* |
|---|
| 981 |
* id_index is calculated in the declaration to be the index number |
|---|
| 982 |
* of the match from the usb_device_id table, so we can find the |
|---|
| 983 |
* corresponding entry in the private table. |
|---|
| 984 |
*/ |
|---|
| 985 |
result = get_device_info(us, id); |
|---|
| 986 |
if (result) |
|---|
| 987 |
goto BadDevice; |
|---|
| 988 |
|
|---|
| 989 |
/* Get the transport, protocol, and pipe settings */ |
|---|
| 990 |
result = get_transport(us); |
|---|
| 991 |
if (result) |
|---|
| 992 |
goto BadDevice; |
|---|
| 993 |
result = get_protocol(us); |
|---|
| 994 |
if (result) |
|---|
| 995 |
goto BadDevice; |
|---|
| 996 |
result = get_pipes(us); |
|---|
| 997 |
if (result) |
|---|
| 998 |
goto BadDevice; |
|---|
| 999 |
|
|---|
| 1000 |
/* Acquire all the other resources and add the host */ |
|---|
| 1001 |
result = usb_stor_acquire_resources(us); |
|---|
| 1002 |
if (result) |
|---|
| 1003 |
goto BadDevice; |
|---|
| 1004 |
result = scsi_add_host(host, &intf->dev); |
|---|
| 1005 |
if (result) { |
|---|
| 1006 |
printk(KERN_WARNING USB_STORAGE |
|---|
| 1007 |
"Unable to add the scsi host\n"); |
|---|
| 1008 |
goto BadDevice; |
|---|
| 1009 |
} |
|---|
| 1010 |
|
|---|
| 1011 |
/* Start up the thread for delayed SCSI-device scanning */ |
|---|
| 1012 |
th = kthread_create(usb_stor_scan_thread, us, "usb-stor-scan"); |
|---|
| 1013 |
if (IS_ERR(th)) { |
|---|
| 1014 |
printk(KERN_WARNING USB_STORAGE |
|---|
| 1015 |
"Unable to start the device-scanning thread\n"); |
|---|
| 1016 |
quiesce_and_remove_host(us); |
|---|
| 1017 |
result = PTR_ERR(th); |
|---|
| 1018 |
goto BadDevice; |
|---|
| 1019 |
} |
|---|
| 1020 |
|
|---|
| 1021 |
wake_up_process(th); |
|---|
| 1022 |
|
|---|
| 1023 |
return 0; |
|---|
| 1024 |
|
|---|
| 1025 |
/* We come here if there are any problems */ |
|---|
| 1026 |
BadDevice: |
|---|
| 1027 |
US_DEBUGP("storage_probe() failed\n"); |
|---|
| 1028 |
release_everything(us); |
|---|
| 1029 |
return result; |
|---|
| 1030 |
} |
|---|
| 1031 |
|
|---|
| 1032 |
/* Handle a disconnect event from the USB core */ |
|---|
| 1033 |
static void storage_disconnect(struct usb_interface *intf) |
|---|
| 1034 |
{ |
|---|
| 1035 |
struct us_data *us = usb_get_intfdata(intf); |
|---|
| 1036 |
|
|---|
| 1037 |
US_DEBUGP("storage_disconnect() called\n"); |
|---|
| 1038 |
quiesce_and_remove_host(us); |
|---|
| 1039 |
release_everything(us); |
|---|
| 1040 |
} |
|---|
| 1041 |
|
|---|
| 1042 |
/*********************************************************************** |
|---|
| 1043 |
* Initialization and registration |
|---|
| 1044 |
***********************************************************************/ |
|---|
| 1045 |
|
|---|
| 1046 |
static struct usb_driver usb_storage_driver = { |
|---|
| 1047 |
.name = "usb-storage", |
|---|
| 1048 |
.probe = storage_probe, |
|---|
| 1049 |
.disconnect = storage_disconnect, |
|---|
| 1050 |
#ifdef CONFIG_PM |
|---|
| 1051 |
.suspend = storage_suspend, |
|---|
| 1052 |
.resume = storage_resume, |
|---|
| 1053 |
.reset_resume = storage_reset_resume, |
|---|
| 1054 |
#endif |
|---|
| 1055 |
.pre_reset = storage_pre_reset, |
|---|
| 1056 |
.post_reset = storage_post_reset, |
|---|
| 1057 |
.id_table = storage_usb_ids, |
|---|
| 1058 |
}; |
|---|
| 1059 |
|
|---|
| 1060 |
static int __init usb_stor_init(void) |
|---|
| 1061 |
{ |
|---|
| 1062 |
int retval; |
|---|
| 1063 |
printk(KERN_INFO "Initializing USB Mass Storage driver...\n"); |
|---|
| 1064 |
|
|---|
| 1065 |
/* register the driver, return usb_register return code if error */ |
|---|
| 1066 |
retval = usb_register(&usb_storage_driver); |
|---|
| 1067 |
if (retval == 0) { |
|---|
| 1068 |
printk(KERN_INFO "USB Mass Storage support registered.\n"); |
|---|
| 1069 |
usb_usual_set_present(USB_US_TYPE_STOR); |
|---|
| 1070 |
} |
|---|
| 1071 |
return retval; |
|---|
| 1072 |
} |
|---|
| 1073 |
|
|---|
| 1074 |
static void __exit usb_stor_exit(void) |
|---|
| 1075 |
{ |
|---|
| 1076 |
US_DEBUGP("usb_stor_exit() called\n"); |
|---|
| 1077 |
|
|---|
| 1078 |
/* Deregister the driver |
|---|
| 1079 |
* This will cause disconnect() to be called for each |
|---|
| 1080 |
* attached unit |
|---|
| 1081 |
*/ |
|---|
| 1082 |
US_DEBUGP("-- calling usb_deregister()\n"); |
|---|
| 1083 |
usb_deregister(&usb_storage_driver) ; |
|---|
| 1084 |
|
|---|
| 1085 |
usb_usual_clear_present(USB_US_TYPE_STOR); |
|---|
| 1086 |
} |
|---|
| 1087 |
|
|---|
| 1088 |
module_init(usb_stor_init); |
|---|
| 1089 |
module_exit(usb_stor_exit); |
|---|