11da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds/* 21da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * scsi_lib.c Copyright (C) 1999 Eric Youngdale 31da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * 41da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * SCSI queueing library. 51da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Initial versions: Eric Youngdale (eric@andante.org). 61da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Based upon conversations with large numbers 71da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * of people at Linux Expo. 81da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds */ 91da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 101da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds#include <linux/bio.h> 11d3f46f39b7092594b498abc12f0c73b0b9913bdeJames Bottomley#include <linux/bitops.h> 121da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds#include <linux/blkdev.h> 131da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds#include <linux/completion.h> 141da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds#include <linux/kernel.h> 1509703660edf83b8b6d175440bf745f30580d85abPaul Gortmaker#include <linux/export.h> 161da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds#include <linux/mempool.h> 171da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds#include <linux/slab.h> 181da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds#include <linux/init.h> 191da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds#include <linux/pci.h> 201da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds#include <linux/delay.h> 21faead26d7a06605add627f29aee73ba654ce11f9James Bottomley#include <linux/hardirq.h> 22c6132da1704be252ee6c923f47501083d835c238Jens Axboe#include <linux/scatterlist.h> 231da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 241da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds#include <scsi/scsi.h> 25beb40487508290f5d6565598c60a3f44261beef2Christoph Hellwig#include <scsi/scsi_cmnd.h> 261da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds#include <scsi/scsi_dbg.h> 271da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds#include <scsi/scsi_device.h> 281da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds#include <scsi/scsi_driver.h> 291da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds#include <scsi/scsi_eh.h> 301da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds#include <scsi/scsi_host.h> 311da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 321da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds#include "scsi_priv.h" 331da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds#include "scsi_logging.h" 341da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 351da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 366391a11375de5e2bb1eb8481e54619761dc65d9fTobias Klauser#define SG_MEMPOOL_NR ARRAY_SIZE(scsi_sg_pools) 375972511b77809cb7c9ccdb79b825c54921c5c546Jens Axboe#define SG_MEMPOOL_SIZE 2 381da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 391da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldsstruct scsi_host_sg_pool { 401da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds size_t size; 41a8474ce23a73185dd2bae4c884b1716474032d31Jens Axboe char *name; 42e18b890bb0881bbab6f4f1a6cd20d9c60d66b003Christoph Lameter struct kmem_cache *slab; 431da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds mempool_t *pool; 441da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds}; 451da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 46d3f46f39b7092594b498abc12f0c73b0b9913bdeJames Bottomley#define SP(x) { x, "sgpool-" __stringify(x) } 47d3f46f39b7092594b498abc12f0c73b0b9913bdeJames Bottomley#if (SCSI_MAX_SG_SEGMENTS < 32) 48d3f46f39b7092594b498abc12f0c73b0b9913bdeJames Bottomley#error SCSI_MAX_SG_SEGMENTS is too small (must be 32 or greater) 49d3f46f39b7092594b498abc12f0c73b0b9913bdeJames Bottomley#endif 5052c1da39534fb382c061de58b65f678ad74b59f5Adrian Bunkstatic struct scsi_host_sg_pool scsi_sg_pools[] = { 511da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds SP(8), 521da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds SP(16), 53fd820f405574a30aacf9a859886e173d641f080bFUJITA Tomonori#if (SCSI_MAX_SG_SEGMENTS > 32) 54d3f46f39b7092594b498abc12f0c73b0b9913bdeJames Bottomley SP(32), 55fd820f405574a30aacf9a859886e173d641f080bFUJITA Tomonori#if (SCSI_MAX_SG_SEGMENTS > 64) 56d3f46f39b7092594b498abc12f0c73b0b9913bdeJames Bottomley SP(64), 57d3f46f39b7092594b498abc12f0c73b0b9913bdeJames Bottomley#if (SCSI_MAX_SG_SEGMENTS > 128) 581da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds SP(128), 59d3f46f39b7092594b498abc12f0c73b0b9913bdeJames Bottomley#if (SCSI_MAX_SG_SEGMENTS > 256) 60d3f46f39b7092594b498abc12f0c73b0b9913bdeJames Bottomley#error SCSI_MAX_SG_SEGMENTS is too large (256 MAX) 61fd820f405574a30aacf9a859886e173d641f080bFUJITA Tomonori#endif 62fd820f405574a30aacf9a859886e173d641f080bFUJITA Tomonori#endif 63fd820f405574a30aacf9a859886e173d641f080bFUJITA Tomonori#endif 64d3f46f39b7092594b498abc12f0c73b0b9913bdeJames Bottomley#endif 65d3f46f39b7092594b498abc12f0c73b0b9913bdeJames Bottomley SP(SCSI_MAX_SG_SEGMENTS) 66a8474ce23a73185dd2bae4c884b1716474032d31Jens Axboe}; 671da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds#undef SP 681da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 697027ad72a689797475973c6feb5f0b673382f779Martin K. Petersenstruct kmem_cache *scsi_sdb_cache; 706f9a35e2dafa0f855ab051c11bdbf739745ff6f5Boaz Harrosh 71a488e74976bf0a9bccecdd094378394942dacef1Jens Axboe/* 72a488e74976bf0a9bccecdd094378394942dacef1Jens Axboe * When to reinvoke queueing after a resource shortage. It's 3 msecs to 73a488e74976bf0a9bccecdd094378394942dacef1Jens Axboe * not change behaviour from the previous unplug mechanism, experimentation 74a488e74976bf0a9bccecdd094378394942dacef1Jens Axboe * may prove this needs changing. 75a488e74976bf0a9bccecdd094378394942dacef1Jens Axboe */ 76a488e74976bf0a9bccecdd094378394942dacef1Jens Axboe#define SCSI_QUEUE_DELAY 3 77a488e74976bf0a9bccecdd094378394942dacef1Jens Axboe 78e91442b635be776ea205fba233bdd5bc74b62bc3James Bottomley/* 79e91442b635be776ea205fba233bdd5bc74b62bc3James Bottomley * Function: scsi_unprep_request() 80e91442b635be776ea205fba233bdd5bc74b62bc3James Bottomley * 81e91442b635be776ea205fba233bdd5bc74b62bc3James Bottomley * Purpose: Remove all preparation done for a request, including its 82e91442b635be776ea205fba233bdd5bc74b62bc3James Bottomley * associated scsi_cmnd, so that it can be requeued. 83e91442b635be776ea205fba233bdd5bc74b62bc3James Bottomley * 84e91442b635be776ea205fba233bdd5bc74b62bc3James Bottomley * Arguments: req - request to unprepare 85e91442b635be776ea205fba233bdd5bc74b62bc3James Bottomley * 86e91442b635be776ea205fba233bdd5bc74b62bc3James Bottomley * Lock status: Assumed that no locks are held upon entry. 87e91442b635be776ea205fba233bdd5bc74b62bc3James Bottomley * 88e91442b635be776ea205fba233bdd5bc74b62bc3James Bottomley * Returns: Nothing. 89e91442b635be776ea205fba233bdd5bc74b62bc3James Bottomley */ 90e91442b635be776ea205fba233bdd5bc74b62bc3James Bottomleystatic void scsi_unprep_request(struct request *req) 91e91442b635be776ea205fba233bdd5bc74b62bc3James Bottomley{ 92e91442b635be776ea205fba233bdd5bc74b62bc3James Bottomley struct scsi_cmnd *cmd = req->special; 93e91442b635be776ea205fba233bdd5bc74b62bc3James Bottomley 9428018c242a4ec7017bbbf81d2d3952f820a27118James Bottomley blk_unprep_request(req); 95beb40487508290f5d6565598c60a3f44261beef2Christoph Hellwig req->special = NULL; 96e91442b635be776ea205fba233bdd5bc74b62bc3James Bottomley 97e91442b635be776ea205fba233bdd5bc74b62bc3James Bottomley scsi_put_command(cmd); 98e91442b635be776ea205fba233bdd5bc74b62bc3James Bottomley} 99a1bf9d1d9272708922e83e465104106131f6415fTejun Heo 1004f5299ac4e3a03d5c596c00d726fa932c600609dJames Bottomley/** 1014f5299ac4e3a03d5c596c00d726fa932c600609dJames Bottomley * __scsi_queue_insert - private queue insertion 1024f5299ac4e3a03d5c596c00d726fa932c600609dJames Bottomley * @cmd: The SCSI command being requeued 1034f5299ac4e3a03d5c596c00d726fa932c600609dJames Bottomley * @reason: The reason for the requeue 1044f5299ac4e3a03d5c596c00d726fa932c600609dJames Bottomley * @unbusy: Whether the queue should be unbusied 1051da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * 1064f5299ac4e3a03d5c596c00d726fa932c600609dJames Bottomley * This is a private queue insertion. The public interface 1074f5299ac4e3a03d5c596c00d726fa932c600609dJames Bottomley * scsi_queue_insert() always assumes the queue should be unbusied 1084f5299ac4e3a03d5c596c00d726fa932c600609dJames Bottomley * because it's always called before the completion. This function is 1094f5299ac4e3a03d5c596c00d726fa932c600609dJames Bottomley * for a requeue after completion, which should only occur in this 1104f5299ac4e3a03d5c596c00d726fa932c600609dJames Bottomley * file. 1111da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds */ 1124f5299ac4e3a03d5c596c00d726fa932c600609dJames Bottomleystatic int __scsi_queue_insert(struct scsi_cmnd *cmd, int reason, int unbusy) 1131da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds{ 1141da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds struct Scsi_Host *host = cmd->device->host; 1151da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds struct scsi_device *device = cmd->device; 116f0c0a376d0fcd4c5579ecf5e95f88387cba85211Mike Christie struct scsi_target *starget = scsi_target(device); 117a1bf9d1d9272708922e83e465104106131f6415fTejun Heo struct request_queue *q = device->request_queue; 118a1bf9d1d9272708922e83e465104106131f6415fTejun Heo unsigned long flags; 1191da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 1201da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds SCSI_LOG_MLQUEUE(1, 1211da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds printk("Inserting command %p into mlqueue\n", cmd)); 1221da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 1231da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds /* 124d8c37e7b9a619855e05d5d4e56c68f799b1f539cTejun Heo * Set the appropriate busy bit for the device/host. 1251da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * 1261da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * If the host/device isn't busy, assume that something actually 1271da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * completed, and that we should be able to queue a command now. 1281da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * 1291da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Note that the prior mid-layer assumption that any host could 1301da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * always queue at least one command is now broken. The mid-layer 1311da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * will implement a user specifiable stall (see 1321da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * scsi_host.max_host_blocked and scsi_device.max_device_blocked) 1331da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * if a command is requeued with no other commands outstanding 1341da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * either for the device or for the host. 1351da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds */ 136f0c0a376d0fcd4c5579ecf5e95f88387cba85211Mike Christie switch (reason) { 137f0c0a376d0fcd4c5579ecf5e95f88387cba85211Mike Christie case SCSI_MLQUEUE_HOST_BUSY: 1381da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds host->host_blocked = host->max_host_blocked; 139f0c0a376d0fcd4c5579ecf5e95f88387cba85211Mike Christie break; 140f0c0a376d0fcd4c5579ecf5e95f88387cba85211Mike Christie case SCSI_MLQUEUE_DEVICE_BUSY: 141573e5913536a1393362265cfea9e708aa10fdf16James Smart case SCSI_MLQUEUE_EH_RETRY: 1421da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds device->device_blocked = device->max_device_blocked; 143f0c0a376d0fcd4c5579ecf5e95f88387cba85211Mike Christie break; 144f0c0a376d0fcd4c5579ecf5e95f88387cba85211Mike Christie case SCSI_MLQUEUE_TARGET_BUSY: 145f0c0a376d0fcd4c5579ecf5e95f88387cba85211Mike Christie starget->target_blocked = starget->max_target_blocked; 146f0c0a376d0fcd4c5579ecf5e95f88387cba85211Mike Christie break; 147f0c0a376d0fcd4c5579ecf5e95f88387cba85211Mike Christie } 1481da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 1491da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds /* 1501da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Decrement the counters, since these commands are no longer 1511da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * active on the host/device. 1521da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds */ 1534f5299ac4e3a03d5c596c00d726fa932c600609dJames Bottomley if (unbusy) 1544f5299ac4e3a03d5c596c00d726fa932c600609dJames Bottomley scsi_device_unbusy(device); 1551da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 1561da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds /* 157a1bf9d1d9272708922e83e465104106131f6415fTejun Heo * Requeue this command. It will go before all other commands 158a1bf9d1d9272708922e83e465104106131f6415fTejun Heo * that are already in the queue. 159a488e74976bf0a9bccecdd094378394942dacef1Jens Axboe */ 160a1bf9d1d9272708922e83e465104106131f6415fTejun Heo spin_lock_irqsave(q->queue_lock, flags); 16159897dad98d63ac15e1e36fcc3a107c892b1826cJames Bottomley blk_requeue_request(q, cmd->request); 162a1bf9d1d9272708922e83e465104106131f6415fTejun Heo spin_unlock_irqrestore(q->queue_lock, flags); 163a1bf9d1d9272708922e83e465104106131f6415fTejun Heo 1649937a5e2f32892db0dbeefc2b3bc74b3ae3ea9c7Jens Axboe kblockd_schedule_work(q, &device->requeue_work); 165a1bf9d1d9272708922e83e465104106131f6415fTejun Heo 1661da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds return 0; 1671da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds} 1681da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 1694f5299ac4e3a03d5c596c00d726fa932c600609dJames Bottomley/* 1704f5299ac4e3a03d5c596c00d726fa932c600609dJames Bottomley * Function: scsi_queue_insert() 1714f5299ac4e3a03d5c596c00d726fa932c600609dJames Bottomley * 1724f5299ac4e3a03d5c596c00d726fa932c600609dJames Bottomley * Purpose: Insert a command in the midlevel queue. 1734f5299ac4e3a03d5c596c00d726fa932c600609dJames Bottomley * 1744f5299ac4e3a03d5c596c00d726fa932c600609dJames Bottomley * Arguments: cmd - command that we are adding to queue. 1754f5299ac4e3a03d5c596c00d726fa932c600609dJames Bottomley * reason - why we are inserting command to queue. 1764f5299ac4e3a03d5c596c00d726fa932c600609dJames Bottomley * 1774f5299ac4e3a03d5c596c00d726fa932c600609dJames Bottomley * Lock status: Assumed that lock is not held upon entry. 1784f5299ac4e3a03d5c596c00d726fa932c600609dJames Bottomley * 1794f5299ac4e3a03d5c596c00d726fa932c600609dJames Bottomley * Returns: Nothing. 1804f5299ac4e3a03d5c596c00d726fa932c600609dJames Bottomley * 1814f5299ac4e3a03d5c596c00d726fa932c600609dJames Bottomley * Notes: We do this for one of two cases. Either the host is busy 1824f5299ac4e3a03d5c596c00d726fa932c600609dJames Bottomley * and it cannot accept any more commands for the time being, 1834f5299ac4e3a03d5c596c00d726fa932c600609dJames Bottomley * or the device returned QUEUE_FULL and can accept no more 1844f5299ac4e3a03d5c596c00d726fa932c600609dJames Bottomley * commands. 1854f5299ac4e3a03d5c596c00d726fa932c600609dJames Bottomley * Notes: This could be called either from an interrupt context or a 1864f5299ac4e3a03d5c596c00d726fa932c600609dJames Bottomley * normal process context. 1874f5299ac4e3a03d5c596c00d726fa932c600609dJames Bottomley */ 1884f5299ac4e3a03d5c596c00d726fa932c600609dJames Bottomleyint scsi_queue_insert(struct scsi_cmnd *cmd, int reason) 1894f5299ac4e3a03d5c596c00d726fa932c600609dJames Bottomley{ 1904f5299ac4e3a03d5c596c00d726fa932c600609dJames Bottomley return __scsi_queue_insert(cmd, reason, 1); 1914f5299ac4e3a03d5c596c00d726fa932c600609dJames Bottomley} 192392160335c798bbe94ab3aae6ea0c85d32b81bbcJames Bottomley/** 19333aa687db90dd8541bd5e9a762eebf880eaee767James Bottomley * scsi_execute - insert request and wait for the result 194392160335c798bbe94ab3aae6ea0c85d32b81bbcJames Bottomley * @sdev: scsi device 195392160335c798bbe94ab3aae6ea0c85d32b81bbcJames Bottomley * @cmd: scsi command 196392160335c798bbe94ab3aae6ea0c85d32b81bbcJames Bottomley * @data_direction: data direction 197392160335c798bbe94ab3aae6ea0c85d32b81bbcJames Bottomley * @buffer: data buffer 198392160335c798bbe94ab3aae6ea0c85d32b81bbcJames Bottomley * @bufflen: len of buffer 199392160335c798bbe94ab3aae6ea0c85d32b81bbcJames Bottomley * @sense: optional sense buffer 200392160335c798bbe94ab3aae6ea0c85d32b81bbcJames Bottomley * @timeout: request timeout in seconds 201392160335c798bbe94ab3aae6ea0c85d32b81bbcJames Bottomley * @retries: number of times to retry request 20233aa687db90dd8541bd5e9a762eebf880eaee767James Bottomley * @flags: or into request flags; 203f4f4e47e4af6b02dd1c425b931c65d0165356e33FUJITA Tomonori * @resid: optional residual length 204392160335c798bbe94ab3aae6ea0c85d32b81bbcJames Bottomley * 20559c51591a0ac7568824f541f57de967e88adaa07Michael Opdenacker * returns the req->errors value which is the scsi_cmnd result 206ea73a9f23906c374b697cd5b0d64f6dceced63deJames Bottomley * field. 207eb44820c28bc9a042e1157b41c677018a8fdfc74Rob Landley */ 20833aa687db90dd8541bd5e9a762eebf880eaee767James Bottomleyint scsi_execute(struct scsi_device *sdev, const unsigned char *cmd, 20933aa687db90dd8541bd5e9a762eebf880eaee767James Bottomley int data_direction, void *buffer, unsigned bufflen, 210f4f4e47e4af6b02dd1c425b931c65d0165356e33FUJITA Tomonori unsigned char *sense, int timeout, int retries, int flags, 211f4f4e47e4af6b02dd1c425b931c65d0165356e33FUJITA Tomonori int *resid) 212392160335c798bbe94ab3aae6ea0c85d32b81bbcJames Bottomley{ 213392160335c798bbe94ab3aae6ea0c85d32b81bbcJames Bottomley struct request *req; 214392160335c798bbe94ab3aae6ea0c85d32b81bbcJames Bottomley int write = (data_direction == DMA_TO_DEVICE); 215392160335c798bbe94ab3aae6ea0c85d32b81bbcJames Bottomley int ret = DRIVER_ERROR << 24; 216392160335c798bbe94ab3aae6ea0c85d32b81bbcJames Bottomley 217392160335c798bbe94ab3aae6ea0c85d32b81bbcJames Bottomley req = blk_get_request(sdev->request_queue, write, __GFP_WAIT); 218bfe159a51203c15d23cb3158fffdc25ec4b4dda1James Bottomley if (!req) 219bfe159a51203c15d23cb3158fffdc25ec4b4dda1James Bottomley return ret; 220392160335c798bbe94ab3aae6ea0c85d32b81bbcJames Bottomley 221392160335c798bbe94ab3aae6ea0c85d32b81bbcJames Bottomley if (bufflen && blk_rq_map_kern(sdev->request_queue, req, 222392160335c798bbe94ab3aae6ea0c85d32b81bbcJames Bottomley buffer, bufflen, __GFP_WAIT)) 223392160335c798bbe94ab3aae6ea0c85d32b81bbcJames Bottomley goto out; 224392160335c798bbe94ab3aae6ea0c85d32b81bbcJames Bottomley 225392160335c798bbe94ab3aae6ea0c85d32b81bbcJames Bottomley req->cmd_len = COMMAND_SIZE(cmd[0]); 226392160335c798bbe94ab3aae6ea0c85d32b81bbcJames Bottomley memcpy(req->cmd, cmd, req->cmd_len); 227392160335c798bbe94ab3aae6ea0c85d32b81bbcJames Bottomley req->sense = sense; 228392160335c798bbe94ab3aae6ea0c85d32b81bbcJames Bottomley req->sense_len = 0; 22917e01f216b611fc46956dcd9063aec4de75991e3Mike Christie req->retries = retries; 230392160335c798bbe94ab3aae6ea0c85d32b81bbcJames Bottomley req->timeout = timeout; 2314aff5e2333c9a1609662f2091f55c3f6fffdad36Jens Axboe req->cmd_type = REQ_TYPE_BLOCK_PC; 2324aff5e2333c9a1609662f2091f55c3f6fffdad36Jens Axboe req->cmd_flags |= flags | REQ_QUIET | REQ_PREEMPT; 233392160335c798bbe94ab3aae6ea0c85d32b81bbcJames Bottomley 234392160335c798bbe94ab3aae6ea0c85d32b81bbcJames Bottomley /* 235392160335c798bbe94ab3aae6ea0c85d32b81bbcJames Bottomley * head injection *required* here otherwise quiesce won't work 236392160335c798bbe94ab3aae6ea0c85d32b81bbcJames Bottomley */ 237392160335c798bbe94ab3aae6ea0c85d32b81bbcJames Bottomley blk_execute_rq(req->q, NULL, req, 1); 238392160335c798bbe94ab3aae6ea0c85d32b81bbcJames Bottomley 239bdb2b8cab4392ce41ddfbd6773a3da3334daf836Alan Stern /* 240bdb2b8cab4392ce41ddfbd6773a3da3334daf836Alan Stern * Some devices (USB mass-storage in particular) may transfer 241bdb2b8cab4392ce41ddfbd6773a3da3334daf836Alan Stern * garbage data together with a residue indicating that the data 242bdb2b8cab4392ce41ddfbd6773a3da3334daf836Alan Stern * is invalid. Prevent the garbage from being misinterpreted 243bdb2b8cab4392ce41ddfbd6773a3da3334daf836Alan Stern * and prevent security leaks by zeroing out the excess data. 244bdb2b8cab4392ce41ddfbd6773a3da3334daf836Alan Stern */ 245c3a4d78c580de4edc9ef0f7c59812fb02ceb037fTejun Heo if (unlikely(req->resid_len > 0 && req->resid_len <= bufflen)) 246c3a4d78c580de4edc9ef0f7c59812fb02ceb037fTejun Heo memset(buffer + (bufflen - req->resid_len), 0, req->resid_len); 247bdb2b8cab4392ce41ddfbd6773a3da3334daf836Alan Stern 248f4f4e47e4af6b02dd1c425b931c65d0165356e33FUJITA Tomonori if (resid) 249c3a4d78c580de4edc9ef0f7c59812fb02ceb037fTejun Heo *resid = req->resid_len; 250392160335c798bbe94ab3aae6ea0c85d32b81bbcJames Bottomley ret = req->errors; 251392160335c798bbe94ab3aae6ea0c85d32b81bbcJames Bottomley out: 252392160335c798bbe94ab3aae6ea0c85d32b81bbcJames Bottomley blk_put_request(req); 253392160335c798bbe94ab3aae6ea0c85d32b81bbcJames Bottomley 254392160335c798bbe94ab3aae6ea0c85d32b81bbcJames Bottomley return ret; 255392160335c798bbe94ab3aae6ea0c85d32b81bbcJames Bottomley} 25633aa687db90dd8541bd5e9a762eebf880eaee767James BottomleyEXPORT_SYMBOL(scsi_execute); 257392160335c798bbe94ab3aae6ea0c85d32b81bbcJames Bottomley 258ea73a9f23906c374b697cd5b0d64f6dceced63deJames Bottomley 259ea73a9f23906c374b697cd5b0d64f6dceced63deJames Bottomleyint scsi_execute_req(struct scsi_device *sdev, const unsigned char *cmd, 260ea73a9f23906c374b697cd5b0d64f6dceced63deJames Bottomley int data_direction, void *buffer, unsigned bufflen, 261f4f4e47e4af6b02dd1c425b931c65d0165356e33FUJITA Tomonori struct scsi_sense_hdr *sshdr, int timeout, int retries, 262f4f4e47e4af6b02dd1c425b931c65d0165356e33FUJITA Tomonori int *resid) 263ea73a9f23906c374b697cd5b0d64f6dceced63deJames Bottomley{ 264ea73a9f23906c374b697cd5b0d64f6dceced63deJames Bottomley char *sense = NULL; 2651ccb48bb163853c24840c0a50c2a6df1affe029cAndrew Morton int result; 2661ccb48bb163853c24840c0a50c2a6df1affe029cAndrew Morton 267ea73a9f23906c374b697cd5b0d64f6dceced63deJames Bottomley if (sshdr) { 26824669f75a3231fa37444977c92d1f4838bec1233Jes Sorensen sense = kzalloc(SCSI_SENSE_BUFFERSIZE, GFP_NOIO); 269ea73a9f23906c374b697cd5b0d64f6dceced63deJames Bottomley if (!sense) 270ea73a9f23906c374b697cd5b0d64f6dceced63deJames Bottomley return DRIVER_ERROR << 24; 271ea73a9f23906c374b697cd5b0d64f6dceced63deJames Bottomley } 2721ccb48bb163853c24840c0a50c2a6df1affe029cAndrew Morton result = scsi_execute(sdev, cmd, data_direction, buffer, bufflen, 273f4f4e47e4af6b02dd1c425b931c65d0165356e33FUJITA Tomonori sense, timeout, retries, 0, resid); 274ea73a9f23906c374b697cd5b0d64f6dceced63deJames Bottomley if (sshdr) 275e514385be2b355c1f3fc6385a98a6a0fc04235aeJames Bottomley scsi_normalize_sense(sense, SCSI_SENSE_BUFFERSIZE, sshdr); 276ea73a9f23906c374b697cd5b0d64f6dceced63deJames Bottomley 277ea73a9f23906c374b697cd5b0d64f6dceced63deJames Bottomley kfree(sense); 278ea73a9f23906c374b697cd5b0d64f6dceced63deJames Bottomley return result; 279ea73a9f23906c374b697cd5b0d64f6dceced63deJames Bottomley} 280ea73a9f23906c374b697cd5b0d64f6dceced63deJames BottomleyEXPORT_SYMBOL(scsi_execute_req); 281ea73a9f23906c374b697cd5b0d64f6dceced63deJames Bottomley 2821da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds/* 2831da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Function: scsi_init_cmd_errh() 2841da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * 2851da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Purpose: Initialize cmd fields related to error handling. 2861da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * 2871da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Arguments: cmd - command that is ready to be queued. 2881da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * 2891da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Notes: This function has the job of initializing a number of 2901da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * fields related to error handling. Typically this will 2911da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * be called once for each command, as required. 2921da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds */ 293631c228cd09bd5b93090fa60bd9803ec14aa0586Christoph Hellwigstatic void scsi_init_cmd_errh(struct scsi_cmnd *cmd) 2941da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds{ 2951da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds cmd->serial_number = 0; 29630b0c37b27485a9cb897bfe3824f6f517b8c80d6Boaz Harrosh scsi_set_resid(cmd, 0); 297b80ca4f7ee36c26d300c5a8f429e73372d153379FUJITA Tomonori memset(cmd->sense_buffer, 0, SCSI_SENSE_BUFFERSIZE); 2981da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds if (cmd->cmd_len == 0) 299db4742dd8f0aa9125b74f9b2516336a75f3d9106Boaz Harrosh cmd->cmd_len = scsi_command_size(cmd->cmnd); 3001da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds} 3011da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 3021da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldsvoid scsi_device_unbusy(struct scsi_device *sdev) 3031da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds{ 3041da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds struct Scsi_Host *shost = sdev->host; 305f0c0a376d0fcd4c5579ecf5e95f88387cba85211Mike Christie struct scsi_target *starget = scsi_target(sdev); 3061da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds unsigned long flags; 3071da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 3081da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds spin_lock_irqsave(shost->host_lock, flags); 3091da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds shost->host_busy--; 310f0c0a376d0fcd4c5579ecf5e95f88387cba85211Mike Christie starget->target_busy--; 311939647ee308e0ad924e776657704c7bedd498664James Bottomley if (unlikely(scsi_host_in_recovery(shost) && 312ee7863bc68fa6ad6fe7cfcc0e5ebe9efe0c0664eTejun Heo (shost->host_failed || shost->host_eh_scheduled))) 3131da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds scsi_eh_wakeup(shost); 3141da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds spin_unlock(shost->host_lock); 315152587deb8903c0edf483a5b889f975bc6bea7e0<axboe@suse.de> spin_lock(sdev->request_queue->queue_lock); 3161da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds sdev->device_busy--; 317152587deb8903c0edf483a5b889f975bc6bea7e0<axboe@suse.de> spin_unlock_irqrestore(sdev->request_queue->queue_lock, flags); 3181da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds} 3191da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 3201da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds/* 3211da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Called for single_lun devices on IO completion. Clear starget_sdev_user, 3221da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * and call blk_run_queue for all the scsi_devices on the target - 3231da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * including current_sdev first. 3241da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * 3251da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Called with *no* scsi locks held. 3261da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds */ 3271da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldsstatic void scsi_single_lun_run(struct scsi_device *current_sdev) 3281da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds{ 3291da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds struct Scsi_Host *shost = current_sdev->host; 3301da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds struct scsi_device *sdev, *tmp; 3311da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds struct scsi_target *starget = scsi_target(current_sdev); 3321da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds unsigned long flags; 3331da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 3341da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds spin_lock_irqsave(shost->host_lock, flags); 3351da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds starget->starget_sdev_user = NULL; 3361da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds spin_unlock_irqrestore(shost->host_lock, flags); 3371da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 3381da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds /* 3391da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Call blk_run_queue for all LUNs on the target, starting with 3401da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * current_sdev. We race with others (to set starget_sdev_user), 3411da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * but in most cases, we will be first. Ideally, each LU on the 3421da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * target would get some limited time or requests on the target. 3431da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds */ 3441da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds blk_run_queue(current_sdev->request_queue); 3451da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 3461da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds spin_lock_irqsave(shost->host_lock, flags); 3471da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds if (starget->starget_sdev_user) 3481da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds goto out; 3491da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds list_for_each_entry_safe(sdev, tmp, &starget->devices, 3501da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds same_target_siblings) { 3511da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds if (sdev == current_sdev) 3521da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds continue; 3531da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds if (scsi_device_get(sdev)) 3541da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds continue; 3551da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 3561da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds spin_unlock_irqrestore(shost->host_lock, flags); 3571da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds blk_run_queue(sdev->request_queue); 3581da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds spin_lock_irqsave(shost->host_lock, flags); 3591da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 3601da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds scsi_device_put(sdev); 3611da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds } 3621da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds out: 3631da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds spin_unlock_irqrestore(shost->host_lock, flags); 3641da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds} 3651da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 3669d11251709f31d49c8167a619d4475fdf6cd7f73Kiyoshi Uedastatic inline int scsi_device_is_busy(struct scsi_device *sdev) 3679d11251709f31d49c8167a619d4475fdf6cd7f73Kiyoshi Ueda{ 3689d11251709f31d49c8167a619d4475fdf6cd7f73Kiyoshi Ueda if (sdev->device_busy >= sdev->queue_depth || sdev->device_blocked) 3699d11251709f31d49c8167a619d4475fdf6cd7f73Kiyoshi Ueda return 1; 3709d11251709f31d49c8167a619d4475fdf6cd7f73Kiyoshi Ueda 3719d11251709f31d49c8167a619d4475fdf6cd7f73Kiyoshi Ueda return 0; 3729d11251709f31d49c8167a619d4475fdf6cd7f73Kiyoshi Ueda} 3739d11251709f31d49c8167a619d4475fdf6cd7f73Kiyoshi Ueda 374f0c0a376d0fcd4c5579ecf5e95f88387cba85211Mike Christiestatic inline int scsi_target_is_busy(struct scsi_target *starget) 375f0c0a376d0fcd4c5579ecf5e95f88387cba85211Mike Christie{ 376f0c0a376d0fcd4c5579ecf5e95f88387cba85211Mike Christie return ((starget->can_queue > 0 && 377f0c0a376d0fcd4c5579ecf5e95f88387cba85211Mike Christie starget->target_busy >= starget->can_queue) || 378f0c0a376d0fcd4c5579ecf5e95f88387cba85211Mike Christie starget->target_blocked); 379f0c0a376d0fcd4c5579ecf5e95f88387cba85211Mike Christie} 380f0c0a376d0fcd4c5579ecf5e95f88387cba85211Mike Christie 3819d11251709f31d49c8167a619d4475fdf6cd7f73Kiyoshi Uedastatic inline int scsi_host_is_busy(struct Scsi_Host *shost) 3829d11251709f31d49c8167a619d4475fdf6cd7f73Kiyoshi Ueda{ 3839d11251709f31d49c8167a619d4475fdf6cd7f73Kiyoshi Ueda if ((shost->can_queue > 0 && shost->host_busy >= shost->can_queue) || 3849d11251709f31d49c8167a619d4475fdf6cd7f73Kiyoshi Ueda shost->host_blocked || shost->host_self_blocked) 3859d11251709f31d49c8167a619d4475fdf6cd7f73Kiyoshi Ueda return 1; 3869d11251709f31d49c8167a619d4475fdf6cd7f73Kiyoshi Ueda 3879d11251709f31d49c8167a619d4475fdf6cd7f73Kiyoshi Ueda return 0; 3889d11251709f31d49c8167a619d4475fdf6cd7f73Kiyoshi Ueda} 3899d11251709f31d49c8167a619d4475fdf6cd7f73Kiyoshi Ueda 3901da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds/* 3911da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Function: scsi_run_queue() 3921da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * 3931da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Purpose: Select a proper request queue to serve next 3941da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * 3951da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Arguments: q - last request's queue 3961da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * 3971da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Returns: Nothing 3981da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * 3991da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Notes: The previous command was completely finished, start 4001da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * a new one if possible. 4011da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds */ 4021da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldsstatic void scsi_run_queue(struct request_queue *q) 4031da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds{ 4042a3a59e5c977654d3aad5bc11cc0aca2303a7f44Mike Christie struct scsi_device *sdev = q->queuedata; 405c055f5b2614b4f758ae6cc86733f31fa4c2c5844James Bottomley struct Scsi_Host *shost; 4062a3a59e5c977654d3aad5bc11cc0aca2303a7f44Mike Christie LIST_HEAD(starved_list); 4071da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds unsigned long flags; 4081da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 409c055f5b2614b4f758ae6cc86733f31fa4c2c5844James Bottomley /* if the device is dead, sdev will be NULL, so no queue to run */ 410c055f5b2614b4f758ae6cc86733f31fa4c2c5844James Bottomley if (!sdev) 411c055f5b2614b4f758ae6cc86733f31fa4c2c5844James Bottomley return; 412c055f5b2614b4f758ae6cc86733f31fa4c2c5844James Bottomley 413c055f5b2614b4f758ae6cc86733f31fa4c2c5844James Bottomley shost = sdev->host; 41425d7c363f2663fe399e623c9bd819258c9760bdcTony Battersby if (scsi_target(sdev)->single_lun) 4151da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds scsi_single_lun_run(sdev); 4161da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 4171da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds spin_lock_irqsave(shost->host_lock, flags); 4182a3a59e5c977654d3aad5bc11cc0aca2303a7f44Mike Christie list_splice_init(&shost->starved_list, &starved_list); 4192a3a59e5c977654d3aad5bc11cc0aca2303a7f44Mike Christie 4202a3a59e5c977654d3aad5bc11cc0aca2303a7f44Mike Christie while (!list_empty(&starved_list)) { 4211da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds /* 4221da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * As long as shost is accepting commands and we have 4231da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * starved queues, call blk_run_queue. scsi_request_fn 4241da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * drops the queue_lock and can add us back to the 4251da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * starved_list. 4261da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * 4271da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * host_lock protects the starved_list and starved_entry. 4281da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * scsi_request_fn must get the host_lock before checking 4291da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * or modifying starved_list or starved_entry. 4301da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds */ 4312a3a59e5c977654d3aad5bc11cc0aca2303a7f44Mike Christie if (scsi_host_is_busy(shost)) 432f0c0a376d0fcd4c5579ecf5e95f88387cba85211Mike Christie break; 433f0c0a376d0fcd4c5579ecf5e95f88387cba85211Mike Christie 4342a3a59e5c977654d3aad5bc11cc0aca2303a7f44Mike Christie sdev = list_entry(starved_list.next, 4352a3a59e5c977654d3aad5bc11cc0aca2303a7f44Mike Christie struct scsi_device, starved_entry); 4362a3a59e5c977654d3aad5bc11cc0aca2303a7f44Mike Christie list_del_init(&sdev->starved_entry); 437f0c0a376d0fcd4c5579ecf5e95f88387cba85211Mike Christie if (scsi_target_is_busy(scsi_target(sdev))) { 438f0c0a376d0fcd4c5579ecf5e95f88387cba85211Mike Christie list_move_tail(&sdev->starved_entry, 439f0c0a376d0fcd4c5579ecf5e95f88387cba85211Mike Christie &shost->starved_list); 440f0c0a376d0fcd4c5579ecf5e95f88387cba85211Mike Christie continue; 441f0c0a376d0fcd4c5579ecf5e95f88387cba85211Mike Christie } 442f0c0a376d0fcd4c5579ecf5e95f88387cba85211Mike Christie 4439937a5e2f32892db0dbeefc2b3bc74b3ae3ea9c7Jens Axboe spin_unlock(shost->host_lock); 4449937a5e2f32892db0dbeefc2b3bc74b3ae3ea9c7Jens Axboe spin_lock(sdev->request_queue->queue_lock); 4459937a5e2f32892db0dbeefc2b3bc74b3ae3ea9c7Jens Axboe __blk_run_queue(sdev->request_queue); 4469937a5e2f32892db0dbeefc2b3bc74b3ae3ea9c7Jens Axboe spin_unlock(sdev->request_queue->queue_lock); 4479937a5e2f32892db0dbeefc2b3bc74b3ae3ea9c7Jens Axboe spin_lock(shost->host_lock); 4481da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds } 4492a3a59e5c977654d3aad5bc11cc0aca2303a7f44Mike Christie /* put any unprocessed entries back */ 4502a3a59e5c977654d3aad5bc11cc0aca2303a7f44Mike Christie list_splice(&starved_list, &shost->starved_list); 4511da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds spin_unlock_irqrestore(shost->host_lock, flags); 4521da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 4531da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds blk_run_queue(q); 4541da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds} 4551da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 4569937a5e2f32892db0dbeefc2b3bc74b3ae3ea9c7Jens Axboevoid scsi_requeue_run_queue(struct work_struct *work) 4579937a5e2f32892db0dbeefc2b3bc74b3ae3ea9c7Jens Axboe{ 4589937a5e2f32892db0dbeefc2b3bc74b3ae3ea9c7Jens Axboe struct scsi_device *sdev; 4599937a5e2f32892db0dbeefc2b3bc74b3ae3ea9c7Jens Axboe struct request_queue *q; 4609937a5e2f32892db0dbeefc2b3bc74b3ae3ea9c7Jens Axboe 4619937a5e2f32892db0dbeefc2b3bc74b3ae3ea9c7Jens Axboe sdev = container_of(work, struct scsi_device, requeue_work); 4629937a5e2f32892db0dbeefc2b3bc74b3ae3ea9c7Jens Axboe q = sdev->request_queue; 4639937a5e2f32892db0dbeefc2b3bc74b3ae3ea9c7Jens Axboe scsi_run_queue(q); 4649937a5e2f32892db0dbeefc2b3bc74b3ae3ea9c7Jens Axboe} 4659937a5e2f32892db0dbeefc2b3bc74b3ae3ea9c7Jens Axboe 4661da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds/* 4671da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Function: scsi_requeue_command() 4681da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * 4691da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Purpose: Handle post-processing of completed commands. 4701da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * 4711da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Arguments: q - queue to operate on 4721da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * cmd - command that may need to be requeued. 4731da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * 4741da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Returns: Nothing 4751da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * 4761da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Notes: After command completion, there may be blocks left 4771da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * over which weren't finished by the previous command 4781da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * this can be for a number of reasons - the main one is 4791da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * I/O errors in the middle of the request, in which case 4801da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * we need to request the blocks that come after the bad 4811da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * sector. 482e91442b635be776ea205fba233bdd5bc74b62bc3James Bottomley * Notes: Upon return, cmd is a stale pointer. 4831da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds */ 4841da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldsstatic void scsi_requeue_command(struct request_queue *q, struct scsi_cmnd *cmd) 4851da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds{ 486e91442b635be776ea205fba233bdd5bc74b62bc3James Bottomley struct request *req = cmd->request; 487283369ccc26705bd9585a0e533c92bd7364c28d1Tejun Heo unsigned long flags; 488283369ccc26705bd9585a0e533c92bd7364c28d1Tejun Heo 489283369ccc26705bd9585a0e533c92bd7364c28d1Tejun Heo spin_lock_irqsave(q->queue_lock, flags); 49002bd3499a3be984f1e88821c3ed252c8c49c498eJames Bottomley scsi_unprep_request(req); 491e91442b635be776ea205fba233bdd5bc74b62bc3James Bottomley blk_requeue_request(q, req); 492283369ccc26705bd9585a0e533c92bd7364c28d1Tejun Heo spin_unlock_irqrestore(q->queue_lock, flags); 4931da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 4941da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds scsi_run_queue(q); 4951da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds} 4961da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 4971da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldsvoid scsi_next_command(struct scsi_cmnd *cmd) 4981da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds{ 49949d7bc64283970ee83d2c954d04ba00d04e5943dLinus Torvalds struct scsi_device *sdev = cmd->device; 50049d7bc64283970ee83d2c954d04ba00d04e5943dLinus Torvalds struct request_queue *q = sdev->request_queue; 50149d7bc64283970ee83d2c954d04ba00d04e5943dLinus Torvalds 50249d7bc64283970ee83d2c954d04ba00d04e5943dLinus Torvalds /* need to hold a reference on the device before we let go of the cmd */ 50349d7bc64283970ee83d2c954d04ba00d04e5943dLinus Torvalds get_device(&sdev->sdev_gendev); 5041da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 5051da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds scsi_put_command(cmd); 5061da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds scsi_run_queue(q); 50749d7bc64283970ee83d2c954d04ba00d04e5943dLinus Torvalds 50849d7bc64283970ee83d2c954d04ba00d04e5943dLinus Torvalds /* ok to remove device now */ 50949d7bc64283970ee83d2c954d04ba00d04e5943dLinus Torvalds put_device(&sdev->sdev_gendev); 5101da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds} 5111da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 5121da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldsvoid scsi_run_host_queues(struct Scsi_Host *shost) 5131da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds{ 5141da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds struct scsi_device *sdev; 5151da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 5161da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds shost_for_each_device(sdev, shost) 5171da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds scsi_run_queue(sdev->request_queue); 5181da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds} 5191da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 52079ed24297236b7430d6ce0a1511ff70cf5b6015aJames Bottomleystatic void __scsi_release_buffers(struct scsi_cmnd *, int); 52179ed24297236b7430d6ce0a1511ff70cf5b6015aJames Bottomley 5221da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds/* 5231da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Function: scsi_end_request() 5241da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * 5251da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Purpose: Post-processing of completed commands (usually invoked at end 5261da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * of upper level post-processing and scsi_io_completion). 5271da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * 5281da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Arguments: cmd - command that is complete. 529610d8b0c972e3b75493efef8e96175518fd736d3Kiyoshi Ueda * error - 0 if I/O indicates success, < 0 for I/O error. 5301da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * bytes - number of bytes of completed I/O 5311da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * requeue - indicates whether we should requeue leftovers. 5321da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * 5331da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Lock status: Assumed that lock is not held upon entry. 5341da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * 535e91442b635be776ea205fba233bdd5bc74b62bc3James Bottomley * Returns: cmd if requeue required, NULL otherwise. 5361da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * 5371da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Notes: This is called for block device requests in order to 5381da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * mark some number of sectors as complete. 5391da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * 5401da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * We are guaranteeing that the request queue will be goosed 5411da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * at some point during this call. 542e91442b635be776ea205fba233bdd5bc74b62bc3James Bottomley * Notes: If cmd was requeued, upon return it will be a stale pointer. 5431da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds */ 544610d8b0c972e3b75493efef8e96175518fd736d3Kiyoshi Uedastatic struct scsi_cmnd *scsi_end_request(struct scsi_cmnd *cmd, int error, 5451da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds int bytes, int requeue) 5461da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds{ 547165125e1e480f9510a5ffcfbfee4e3ee38c05f23Jens Axboe struct request_queue *q = cmd->device->request_queue; 5481da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds struct request *req = cmd->request; 5491da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 5501da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds /* 5511da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * If there are blocks left over at the end, set up the command 5521da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * to queue the remainder of them. 5531da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds */ 554610d8b0c972e3b75493efef8e96175518fd736d3Kiyoshi Ueda if (blk_end_request(req, error, bytes)) { 5551da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds /* kill remainder if no retrys */ 5564a27446f3e39b06c28d1c8e31d33a5340826ed5cMike Christie if (error && scsi_noretry_cmd(cmd)) 557e458824f9d32e9bf7700d1eb0d201749af48eee0Tejun Heo blk_end_request_all(req, error); 5581da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds else { 559e91442b635be776ea205fba233bdd5bc74b62bc3James Bottomley if (requeue) { 5601da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds /* 5611da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Bleah. Leftovers again. Stick the 5621da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * leftovers in the front of the 5631da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * queue, and goose the queue again. 5641da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds */ 56579ed24297236b7430d6ce0a1511ff70cf5b6015aJames Bottomley scsi_release_buffers(cmd); 5661da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds scsi_requeue_command(q, cmd); 567e91442b635be776ea205fba233bdd5bc74b62bc3James Bottomley cmd = NULL; 568e91442b635be776ea205fba233bdd5bc74b62bc3James Bottomley } 5691da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds return cmd; 5701da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds } 5711da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds } 5721da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 5731da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds /* 5741da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * This will goose the queue request function at the end, so we don't 5751da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * need to worry about launching another command. 5761da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds */ 57779ed24297236b7430d6ce0a1511ff70cf5b6015aJames Bottomley __scsi_release_buffers(cmd, 0); 5781da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds scsi_next_command(cmd); 5791da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds return NULL; 5801da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds} 5811da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 582a8474ce23a73185dd2bae4c884b1716474032d31Jens Axboestatic inline unsigned int scsi_sgtable_index(unsigned short nents) 583a8474ce23a73185dd2bae4c884b1716474032d31Jens Axboe{ 584a8474ce23a73185dd2bae4c884b1716474032d31Jens Axboe unsigned int index; 585a8474ce23a73185dd2bae4c884b1716474032d31Jens Axboe 586d3f46f39b7092594b498abc12f0c73b0b9913bdeJames Bottomley BUG_ON(nents > SCSI_MAX_SG_SEGMENTS); 587d3f46f39b7092594b498abc12f0c73b0b9913bdeJames Bottomley 588d3f46f39b7092594b498abc12f0c73b0b9913bdeJames Bottomley if (nents <= 8) 589a8474ce23a73185dd2bae4c884b1716474032d31Jens Axboe index = 0; 590d3f46f39b7092594b498abc12f0c73b0b9913bdeJames Bottomley else 591d3f46f39b7092594b498abc12f0c73b0b9913bdeJames Bottomley index = get_count_order(nents) - 3; 5921da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 593a8474ce23a73185dd2bae4c884b1716474032d31Jens Axboe return index; 594a8474ce23a73185dd2bae4c884b1716474032d31Jens Axboe} 595a8474ce23a73185dd2bae4c884b1716474032d31Jens Axboe 5965ed7959ede0936c55e50421a53f153b17080e876Jens Axboestatic void scsi_sg_free(struct scatterlist *sgl, unsigned int nents) 597a8474ce23a73185dd2bae4c884b1716474032d31Jens Axboe{ 598a8474ce23a73185dd2bae4c884b1716474032d31Jens Axboe struct scsi_host_sg_pool *sgp; 599a8474ce23a73185dd2bae4c884b1716474032d31Jens Axboe 6005ed7959ede0936c55e50421a53f153b17080e876Jens Axboe sgp = scsi_sg_pools + scsi_sgtable_index(nents); 6015ed7959ede0936c55e50421a53f153b17080e876Jens Axboe mempool_free(sgl, sgp->pool); 6025ed7959ede0936c55e50421a53f153b17080e876Jens Axboe} 603a8474ce23a73185dd2bae4c884b1716474032d31Jens Axboe 6045ed7959ede0936c55e50421a53f153b17080e876Jens Axboestatic struct scatterlist *scsi_sg_alloc(unsigned int nents, gfp_t gfp_mask) 6055ed7959ede0936c55e50421a53f153b17080e876Jens Axboe{ 6065ed7959ede0936c55e50421a53f153b17080e876Jens Axboe struct scsi_host_sg_pool *sgp; 607a8474ce23a73185dd2bae4c884b1716474032d31Jens Axboe 6085ed7959ede0936c55e50421a53f153b17080e876Jens Axboe sgp = scsi_sg_pools + scsi_sgtable_index(nents); 6095ed7959ede0936c55e50421a53f153b17080e876Jens Axboe return mempool_alloc(sgp->pool, gfp_mask); 6105ed7959ede0936c55e50421a53f153b17080e876Jens Axboe} 611a3bec5c5aea0da263111c4d8f8eabc1f8560d7bfJens Axboe 61230b0c37b27485a9cb897bfe3824f6f517b8c80d6Boaz Harroshstatic int scsi_alloc_sgtable(struct scsi_data_buffer *sdb, int nents, 61330b0c37b27485a9cb897bfe3824f6f517b8c80d6Boaz Harrosh gfp_t gfp_mask) 6145ed7959ede0936c55e50421a53f153b17080e876Jens Axboe{ 6155ed7959ede0936c55e50421a53f153b17080e876Jens Axboe int ret; 616a8474ce23a73185dd2bae4c884b1716474032d31Jens Axboe 61730b0c37b27485a9cb897bfe3824f6f517b8c80d6Boaz Harrosh BUG_ON(!nents); 618a8474ce23a73185dd2bae4c884b1716474032d31Jens Axboe 61930b0c37b27485a9cb897bfe3824f6f517b8c80d6Boaz Harrosh ret = __sg_alloc_table(&sdb->table, nents, SCSI_MAX_SG_SEGMENTS, 62030b0c37b27485a9cb897bfe3824f6f517b8c80d6Boaz Harrosh gfp_mask, scsi_sg_alloc); 6215ed7959ede0936c55e50421a53f153b17080e876Jens Axboe if (unlikely(ret)) 62230b0c37b27485a9cb897bfe3824f6f517b8c80d6Boaz Harrosh __sg_free_table(&sdb->table, SCSI_MAX_SG_SEGMENTS, 6237cedb1f17fb7f4374d11501f61656ae9d3ba47e9James Bottomley scsi_sg_free); 62445711f1af6eff1a6d010703b4862e0d2b9afd056Jens Axboe 625a8474ce23a73185dd2bae4c884b1716474032d31Jens Axboe return ret; 6261da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds} 6271da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 62830b0c37b27485a9cb897bfe3824f6f517b8c80d6Boaz Harroshstatic void scsi_free_sgtable(struct scsi_data_buffer *sdb) 6291da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds{ 63030b0c37b27485a9cb897bfe3824f6f517b8c80d6Boaz Harrosh __sg_free_table(&sdb->table, SCSI_MAX_SG_SEGMENTS, scsi_sg_free); 6311da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds} 6321da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 63379ed24297236b7430d6ce0a1511ff70cf5b6015aJames Bottomleystatic void __scsi_release_buffers(struct scsi_cmnd *cmd, int do_bidi_check) 63479ed24297236b7430d6ce0a1511ff70cf5b6015aJames Bottomley{ 63579ed24297236b7430d6ce0a1511ff70cf5b6015aJames Bottomley 63679ed24297236b7430d6ce0a1511ff70cf5b6015aJames Bottomley if (cmd->sdb.table.nents) 63779ed24297236b7430d6ce0a1511ff70cf5b6015aJames Bottomley scsi_free_sgtable(&cmd->sdb); 63879ed24297236b7430d6ce0a1511ff70cf5b6015aJames Bottomley 63979ed24297236b7430d6ce0a1511ff70cf5b6015aJames Bottomley memset(&cmd->sdb, 0, sizeof(cmd->sdb)); 64079ed24297236b7430d6ce0a1511ff70cf5b6015aJames Bottomley 64179ed24297236b7430d6ce0a1511ff70cf5b6015aJames Bottomley if (do_bidi_check && scsi_bidi_cmnd(cmd)) { 64279ed24297236b7430d6ce0a1511ff70cf5b6015aJames Bottomley struct scsi_data_buffer *bidi_sdb = 64379ed24297236b7430d6ce0a1511ff70cf5b6015aJames Bottomley cmd->request->next_rq->special; 64479ed24297236b7430d6ce0a1511ff70cf5b6015aJames Bottomley scsi_free_sgtable(bidi_sdb); 64579ed24297236b7430d6ce0a1511ff70cf5b6015aJames Bottomley kmem_cache_free(scsi_sdb_cache, bidi_sdb); 64679ed24297236b7430d6ce0a1511ff70cf5b6015aJames Bottomley cmd->request->next_rq->special = NULL; 64779ed24297236b7430d6ce0a1511ff70cf5b6015aJames Bottomley } 64879ed24297236b7430d6ce0a1511ff70cf5b6015aJames Bottomley 64979ed24297236b7430d6ce0a1511ff70cf5b6015aJames Bottomley if (scsi_prot_sg_count(cmd)) 65079ed24297236b7430d6ce0a1511ff70cf5b6015aJames Bottomley scsi_free_sgtable(cmd->prot_sdb); 65179ed24297236b7430d6ce0a1511ff70cf5b6015aJames Bottomley} 65279ed24297236b7430d6ce0a1511ff70cf5b6015aJames Bottomley 6531da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds/* 6541da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Function: scsi_release_buffers() 6551da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * 6561da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Purpose: Completion processing for block device I/O requests. 6571da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * 6581da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Arguments: cmd - command that we are bailing. 6591da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * 6601da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Lock status: Assumed that no lock is held upon entry. 6611da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * 6621da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Returns: Nothing 6631da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * 6641da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Notes: In the event that an upper level driver rejects a 6651da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * command, we must release resources allocated during 6661da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * the __init_io() function. Primarily this would involve 6671da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * the scatter-gather table, and potentially any bounce 6681da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * buffers. 6691da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds */ 670bb52d82f45df3a2661d88befba7c79a7db8be496Boaz Harroshvoid scsi_release_buffers(struct scsi_cmnd *cmd) 6711da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds{ 67279ed24297236b7430d6ce0a1511ff70cf5b6015aJames Bottomley __scsi_release_buffers(cmd, 1); 6731da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds} 674bb52d82f45df3a2661d88befba7c79a7db8be496Boaz HarroshEXPORT_SYMBOL(scsi_release_buffers); 6751da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 67663583cca745f440167bf27877182dc13e19d4bcfHannes Reineckestatic int __scsi_error_from_host_byte(struct scsi_cmnd *cmd, int result) 67763583cca745f440167bf27877182dc13e19d4bcfHannes Reinecke{ 67863583cca745f440167bf27877182dc13e19d4bcfHannes Reinecke int error = 0; 67963583cca745f440167bf27877182dc13e19d4bcfHannes Reinecke 68063583cca745f440167bf27877182dc13e19d4bcfHannes Reinecke switch(host_byte(result)) { 68163583cca745f440167bf27877182dc13e19d4bcfHannes Reinecke case DID_TRANSPORT_FAILFAST: 68263583cca745f440167bf27877182dc13e19d4bcfHannes Reinecke error = -ENOLINK; 68363583cca745f440167bf27877182dc13e19d4bcfHannes Reinecke break; 68463583cca745f440167bf27877182dc13e19d4bcfHannes Reinecke case DID_TARGET_FAILURE: 68563583cca745f440167bf27877182dc13e19d4bcfHannes Reinecke cmd->result |= (DID_OK << 16); 68663583cca745f440167bf27877182dc13e19d4bcfHannes Reinecke error = -EREMOTEIO; 68763583cca745f440167bf27877182dc13e19d4bcfHannes Reinecke break; 68863583cca745f440167bf27877182dc13e19d4bcfHannes Reinecke case DID_NEXUS_FAILURE: 68963583cca745f440167bf27877182dc13e19d4bcfHannes Reinecke cmd->result |= (DID_OK << 16); 69063583cca745f440167bf27877182dc13e19d4bcfHannes Reinecke error = -EBADE; 69163583cca745f440167bf27877182dc13e19d4bcfHannes Reinecke break; 69263583cca745f440167bf27877182dc13e19d4bcfHannes Reinecke default: 69363583cca745f440167bf27877182dc13e19d4bcfHannes Reinecke error = -EIO; 69463583cca745f440167bf27877182dc13e19d4bcfHannes Reinecke break; 69563583cca745f440167bf27877182dc13e19d4bcfHannes Reinecke } 69663583cca745f440167bf27877182dc13e19d4bcfHannes Reinecke 69763583cca745f440167bf27877182dc13e19d4bcfHannes Reinecke return error; 69863583cca745f440167bf27877182dc13e19d4bcfHannes Reinecke} 69963583cca745f440167bf27877182dc13e19d4bcfHannes Reinecke 7001da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds/* 7011da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Function: scsi_io_completion() 7021da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * 7031da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Purpose: Completion processing for block device I/O requests. 7041da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * 7051da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Arguments: cmd - command that is finished. 7061da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * 7071da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Lock status: Assumed that no lock is held upon entry. 7081da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * 7091da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Returns: Nothing 7101da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * 7111da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Notes: This function is matched in terms of capabilities to 7121da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * the function that created the scatter-gather list. 7131da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * In other words, if there are no bounce buffers 7141da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * (the normal case for most drivers), we don't need 7151da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * the logic to deal with cleaning up afterwards. 7161da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * 717b60af5b0adf0da24c673598c8d3fb4d4189a15ceAlan Stern * We must call scsi_end_request(). This will finish off 718b60af5b0adf0da24c673598c8d3fb4d4189a15ceAlan Stern * the specified number of sectors. If we are done, the 719b60af5b0adf0da24c673598c8d3fb4d4189a15ceAlan Stern * command block will be released and the queue function 720b60af5b0adf0da24c673598c8d3fb4d4189a15ceAlan Stern * will be goosed. If we are not done then we have to 721b60af5b0adf0da24c673598c8d3fb4d4189a15ceAlan Stern * figure out what to do next: 7221da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * 723b60af5b0adf0da24c673598c8d3fb4d4189a15ceAlan Stern * a) We can call scsi_requeue_command(). The request 724b60af5b0adf0da24c673598c8d3fb4d4189a15ceAlan Stern * will be unprepared and put back on the queue. Then 725b60af5b0adf0da24c673598c8d3fb4d4189a15ceAlan Stern * a new command will be created for it. This should 726b60af5b0adf0da24c673598c8d3fb4d4189a15ceAlan Stern * be used if we made forward progress, or if we want 727b60af5b0adf0da24c673598c8d3fb4d4189a15ceAlan Stern * to switch from READ(10) to READ(6) for example. 7281da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * 729b60af5b0adf0da24c673598c8d3fb4d4189a15ceAlan Stern * b) We can call scsi_queue_insert(). The request will 730b60af5b0adf0da24c673598c8d3fb4d4189a15ceAlan Stern * be put back on the queue and retried using the same 731b60af5b0adf0da24c673598c8d3fb4d4189a15ceAlan Stern * command as before, possibly after a delay. 732b60af5b0adf0da24c673598c8d3fb4d4189a15ceAlan Stern * 733b60af5b0adf0da24c673598c8d3fb4d4189a15ceAlan Stern * c) We can call blk_end_request() with -EIO to fail 734b60af5b0adf0da24c673598c8d3fb4d4189a15ceAlan Stern * the remainder of the request. 7351da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds */ 73603aba2f79594ca94d159c8bab454de9bcc385b76Luben Tuikovvoid scsi_io_completion(struct scsi_cmnd *cmd, unsigned int good_bytes) 7371da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds{ 7381da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds int result = cmd->result; 739165125e1e480f9510a5ffcfbfee4e3ee38c05f23Jens Axboe struct request_queue *q = cmd->device->request_queue; 7401da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds struct request *req = cmd->request; 741fa8e36c39b00a219d2c37250e493c3421e0e67e9James Bottomley int error = 0; 7421da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds struct scsi_sense_hdr sshdr; 7431da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds int sense_valid = 0; 7441da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds int sense_deferred = 0; 745b60af5b0adf0da24c673598c8d3fb4d4189a15ceAlan Stern enum {ACTION_FAIL, ACTION_REPREP, ACTION_RETRY, 746b60af5b0adf0da24c673598c8d3fb4d4189a15ceAlan Stern ACTION_DELAYED_RETRY} action; 747b60af5b0adf0da24c673598c8d3fb4d4189a15ceAlan Stern char *description = NULL; 7481da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 7491da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds if (result) { 7501da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds sense_valid = scsi_command_normalize_sense(cmd, &sshdr); 7511da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds if (sense_valid) 7521da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds sense_deferred = scsi_sense_is_deferred(&sshdr); 7531da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds } 754631c228cd09bd5b93090fa60bd9803ec14aa0586Christoph Hellwig 75533659ebbae262228eef4e0fe990f393d1f0ed941Christoph Hellwig if (req->cmd_type == REQ_TYPE_BLOCK_PC) { /* SG_IO ioctl from block level */ 7561da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds req->errors = result; 7571da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds if (result) { 7581da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds if (sense_valid && req->sense) { 7591da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds /* 7601da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * SG_IO wants current and deferred errors 7611da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds */ 7621da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds int len = 8 + cmd->sense_buffer[7]; 7631da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 7641da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds if (len > SCSI_SENSE_BUFFERSIZE) 7651da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds len = SCSI_SENSE_BUFFERSIZE; 7661da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds memcpy(req->sense, cmd->sense_buffer, len); 7671da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds req->sense_len = len; 7681da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds } 769fa8e36c39b00a219d2c37250e493c3421e0e67e9James Bottomley if (!sense_deferred) 77063583cca745f440167bf27877182dc13e19d4bcfHannes Reinecke error = __scsi_error_from_host_byte(cmd, result); 771b22f687dd28a7a8886b918294b4d558ef175c07dPete Wyckoff } 772e6bb7a96c2c36f20c05ef648f15bd3c2b1834c78FUJITA Tomonori 773e6bb7a96c2c36f20c05ef648f15bd3c2b1834c78FUJITA Tomonori req->resid_len = scsi_get_resid(cmd); 774e6bb7a96c2c36f20c05ef648f15bd3c2b1834c78FUJITA Tomonori 7756f9a35e2dafa0f855ab051c11bdbf739745ff6f5Boaz Harrosh if (scsi_bidi_cmnd(cmd)) { 776e6bb7a96c2c36f20c05ef648f15bd3c2b1834c78FUJITA Tomonori /* 777e6bb7a96c2c36f20c05ef648f15bd3c2b1834c78FUJITA Tomonori * Bidi commands Must be complete as a whole, 778e6bb7a96c2c36f20c05ef648f15bd3c2b1834c78FUJITA Tomonori * both sides at once. 779e6bb7a96c2c36f20c05ef648f15bd3c2b1834c78FUJITA Tomonori */ 780e6bb7a96c2c36f20c05ef648f15bd3c2b1834c78FUJITA Tomonori req->next_rq->resid_len = scsi_in(cmd)->resid; 781e6bb7a96c2c36f20c05ef648f15bd3c2b1834c78FUJITA Tomonori 78263c43b0ec1765b74c734d465ba6345ef4f434df8Boaz Harrosh scsi_release_buffers(cmd); 783e6bb7a96c2c36f20c05ef648f15bd3c2b1834c78FUJITA Tomonori blk_end_request_all(req, 0); 784e6bb7a96c2c36f20c05ef648f15bd3c2b1834c78FUJITA Tomonori 785e6bb7a96c2c36f20c05ef648f15bd3c2b1834c78FUJITA Tomonori scsi_next_command(cmd); 7866f9a35e2dafa0f855ab051c11bdbf739745ff6f5Boaz Harrosh return; 7876f9a35e2dafa0f855ab051c11bdbf739745ff6f5Boaz Harrosh } 7881da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds } 7891da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 79033659ebbae262228eef4e0fe990f393d1f0ed941Christoph Hellwig /* no bidi support for !REQ_TYPE_BLOCK_PC yet */ 79133659ebbae262228eef4e0fe990f393d1f0ed941Christoph Hellwig BUG_ON(blk_bidi_rq(req)); 79230b0c37b27485a9cb897bfe3824f6f517b8c80d6Boaz Harrosh 7931da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds /* 7941da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Next deal with any sectors which we were able to correctly 7951da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * handle. 7961da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds */ 79783096ebf1263b2c1ee5e653ba37d993d02e3eb7bTejun Heo SCSI_LOG_HLCOMPLETE(1, printk("%u sectors total, " 798d6b0c53723753fc0cfda63f56735b225c43e1e9aJames Bottomley "%d bytes done.\n", 79983096ebf1263b2c1ee5e653ba37d993d02e3eb7bTejun Heo blk_rq_sectors(req), good_bytes)); 800d6b0c53723753fc0cfda63f56735b225c43e1e9aJames Bottomley 801a9bddd74630b2a1f2dedc537417c372b2d9edc76James Bottomley /* 802a9bddd74630b2a1f2dedc537417c372b2d9edc76James Bottomley * Recovered errors need reporting, but they're always treated 803a9bddd74630b2a1f2dedc537417c372b2d9edc76James Bottomley * as success, so fiddle the result code here. For BLOCK_PC 804a9bddd74630b2a1f2dedc537417c372b2d9edc76James Bottomley * we already took a copy of the original into rq->errors which 805a9bddd74630b2a1f2dedc537417c372b2d9edc76James Bottomley * is what gets returned to the user 806a9bddd74630b2a1f2dedc537417c372b2d9edc76James Bottomley */ 807e7efe5932b1d3916c79326a4221693ea90a900e2Douglas Gilbert if (sense_valid && (sshdr.sense_key == RECOVERED_ERROR)) { 808e7efe5932b1d3916c79326a4221693ea90a900e2Douglas Gilbert /* if ATA PASS-THROUGH INFORMATION AVAILABLE skip 809e7efe5932b1d3916c79326a4221693ea90a900e2Douglas Gilbert * print since caller wants ATA registers. Only occurs on 810e7efe5932b1d3916c79326a4221693ea90a900e2Douglas Gilbert * SCSI ATA PASS_THROUGH commands when CK_COND=1 811e7efe5932b1d3916c79326a4221693ea90a900e2Douglas Gilbert */ 812e7efe5932b1d3916c79326a4221693ea90a900e2Douglas Gilbert if ((sshdr.asc == 0x0) && (sshdr.ascq == 0x1d)) 813e7efe5932b1d3916c79326a4221693ea90a900e2Douglas Gilbert ; 814e7efe5932b1d3916c79326a4221693ea90a900e2Douglas Gilbert else if (!(req->cmd_flags & REQ_QUIET)) 815a9bddd74630b2a1f2dedc537417c372b2d9edc76James Bottomley scsi_print_sense("", cmd); 816a9bddd74630b2a1f2dedc537417c372b2d9edc76James Bottomley result = 0; 817a9bddd74630b2a1f2dedc537417c372b2d9edc76James Bottomley /* BLOCK_PC may have set error */ 818a9bddd74630b2a1f2dedc537417c372b2d9edc76James Bottomley error = 0; 819a9bddd74630b2a1f2dedc537417c372b2d9edc76James Bottomley } 820a9bddd74630b2a1f2dedc537417c372b2d9edc76James Bottomley 821a9bddd74630b2a1f2dedc537417c372b2d9edc76James Bottomley /* 822a9bddd74630b2a1f2dedc537417c372b2d9edc76James Bottomley * A number of bytes were successfully read. If there 823d6b0c53723753fc0cfda63f56735b225c43e1e9aJames Bottomley * are leftovers and there is some kind of error 824d6b0c53723753fc0cfda63f56735b225c43e1e9aJames Bottomley * (result != 0), retry the rest. 825d6b0c53723753fc0cfda63f56735b225c43e1e9aJames Bottomley */ 826fa8e36c39b00a219d2c37250e493c3421e0e67e9James Bottomley if (scsi_end_request(cmd, error, good_bytes, result == 0) == NULL) 827d6b0c53723753fc0cfda63f56735b225c43e1e9aJames Bottomley return; 82803aba2f79594ca94d159c8bab454de9bcc385b76Luben Tuikov 82963583cca745f440167bf27877182dc13e19d4bcfHannes Reinecke error = __scsi_error_from_host_byte(cmd, result); 8303e695f89c5debb735e4ff051e9e58d8fb4e95110Martin K. Petersen 831b60af5b0adf0da24c673598c8d3fb4d4189a15ceAlan Stern if (host_byte(result) == DID_RESET) { 832b60af5b0adf0da24c673598c8d3fb4d4189a15ceAlan Stern /* Third party bus reset or reset for error recovery 833b60af5b0adf0da24c673598c8d3fb4d4189a15ceAlan Stern * reasons. Just retry the command and see what 834b60af5b0adf0da24c673598c8d3fb4d4189a15ceAlan Stern * happens. 835b60af5b0adf0da24c673598c8d3fb4d4189a15ceAlan Stern */ 836b60af5b0adf0da24c673598c8d3fb4d4189a15ceAlan Stern action = ACTION_RETRY; 837b60af5b0adf0da24c673598c8d3fb4d4189a15ceAlan Stern } else if (sense_valid && !sense_deferred) { 8381da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds switch (sshdr.sense_key) { 8391da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds case UNIT_ATTENTION: 8401da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds if (cmd->device->removable) { 84103aba2f79594ca94d159c8bab454de9bcc385b76Luben Tuikov /* Detected disc change. Set a bit 8421da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * and quietly refuse further access. 8431da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds */ 8441da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds cmd->device->changed = 1; 845b60af5b0adf0da24c673598c8d3fb4d4189a15ceAlan Stern description = "Media Changed"; 846b60af5b0adf0da24c673598c8d3fb4d4189a15ceAlan Stern action = ACTION_FAIL; 8471da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds } else { 84803aba2f79594ca94d159c8bab454de9bcc385b76Luben Tuikov /* Must have been a power glitch, or a 84903aba2f79594ca94d159c8bab454de9bcc385b76Luben Tuikov * bus reset. Could not have been a 85003aba2f79594ca94d159c8bab454de9bcc385b76Luben Tuikov * media change, so we just retry the 851b60af5b0adf0da24c673598c8d3fb4d4189a15ceAlan Stern * command and see what happens. 85203aba2f79594ca94d159c8bab454de9bcc385b76Luben Tuikov */ 853b60af5b0adf0da24c673598c8d3fb4d4189a15ceAlan Stern action = ACTION_RETRY; 8541da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds } 8551da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds break; 8561da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds case ILLEGAL_REQUEST: 85703aba2f79594ca94d159c8bab454de9bcc385b76Luben Tuikov /* If we had an ILLEGAL REQUEST returned, then 85803aba2f79594ca94d159c8bab454de9bcc385b76Luben Tuikov * we may have performed an unsupported 85903aba2f79594ca94d159c8bab454de9bcc385b76Luben Tuikov * command. The only thing this should be 86003aba2f79594ca94d159c8bab454de9bcc385b76Luben Tuikov * would be a ten byte read where only a six 86103aba2f79594ca94d159c8bab454de9bcc385b76Luben Tuikov * byte read was supported. Also, on a system 86203aba2f79594ca94d159c8bab454de9bcc385b76Luben Tuikov * where READ CAPACITY failed, we may have 86303aba2f79594ca94d159c8bab454de9bcc385b76Luben Tuikov * read past the end of the disk. 86403aba2f79594ca94d159c8bab454de9bcc385b76Luben Tuikov */ 86526a68019c86e1d1782984a7a5babff762cde1501Jens Axboe if ((cmd->device->use_10_for_rw && 86626a68019c86e1d1782984a7a5babff762cde1501Jens Axboe sshdr.asc == 0x20 && sshdr.ascq == 0x00) && 8671da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds (cmd->cmnd[0] == READ_10 || 8681da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds cmd->cmnd[0] == WRITE_10)) { 869b60af5b0adf0da24c673598c8d3fb4d4189a15ceAlan Stern /* This will issue a new 6-byte command. */ 8701da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds cmd->device->use_10_for_rw = 0; 871b60af5b0adf0da24c673598c8d3fb4d4189a15ceAlan Stern action = ACTION_REPREP; 8723e695f89c5debb735e4ff051e9e58d8fb4e95110Martin K. Petersen } else if (sshdr.asc == 0x10) /* DIX */ { 8733e695f89c5debb735e4ff051e9e58d8fb4e95110Martin K. Petersen description = "Host Data Integrity Failure"; 8743e695f89c5debb735e4ff051e9e58d8fb4e95110Martin K. Petersen action = ACTION_FAIL; 8753e695f89c5debb735e4ff051e9e58d8fb4e95110Martin K. Petersen error = -EILSEQ; 876c98a0eb0e90d1caa8a92913cd45462102cbd5eafMartin K. Petersen /* INVALID COMMAND OPCODE or INVALID FIELD IN CDB */ 877c98a0eb0e90d1caa8a92913cd45462102cbd5eafMartin K. Petersen } else if ((sshdr.asc == 0x20 || sshdr.asc == 0x24) && 878c98a0eb0e90d1caa8a92913cd45462102cbd5eafMartin K. Petersen (cmd->cmnd[0] == UNMAP || 879c98a0eb0e90d1caa8a92913cd45462102cbd5eafMartin K. Petersen cmd->cmnd[0] == WRITE_SAME_16 || 880c98a0eb0e90d1caa8a92913cd45462102cbd5eafMartin K. Petersen cmd->cmnd[0] == WRITE_SAME)) { 881c98a0eb0e90d1caa8a92913cd45462102cbd5eafMartin K. Petersen description = "Discard failure"; 882c98a0eb0e90d1caa8a92913cd45462102cbd5eafMartin K. Petersen action = ACTION_FAIL; 883b60af5b0adf0da24c673598c8d3fb4d4189a15ceAlan Stern } else 884b60af5b0adf0da24c673598c8d3fb4d4189a15ceAlan Stern action = ACTION_FAIL; 885b60af5b0adf0da24c673598c8d3fb4d4189a15ceAlan Stern break; 886511e44f42e3239a4df77b8e0e46d294d98a768adMartin K. Petersen case ABORTED_COMMAND: 887126c098296c8f96cf7f6ca0fdb47265ac7994f00James Bottomley action = ACTION_FAIL; 888511e44f42e3239a4df77b8e0e46d294d98a768adMartin K. Petersen if (sshdr.asc == 0x10) { /* DIF */ 8893e695f89c5debb735e4ff051e9e58d8fb4e95110Martin K. Petersen description = "Target Data Integrity Failure"; 8903e695f89c5debb735e4ff051e9e58d8fb4e95110Martin K. Petersen error = -EILSEQ; 891126c098296c8f96cf7f6ca0fdb47265ac7994f00James Bottomley } 8921da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds break; 8931da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds case NOT_READY: 89403aba2f79594ca94d159c8bab454de9bcc385b76Luben Tuikov /* If the device is in the process of becoming 895f3e93f735321ea75108b41cb654c16f92d3f264cJames Bottomley * ready, or has a temporary blockage, retry. 8961da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds */ 897f3e93f735321ea75108b41cb654c16f92d3f264cJames Bottomley if (sshdr.asc == 0x04) { 898f3e93f735321ea75108b41cb654c16f92d3f264cJames Bottomley switch (sshdr.ascq) { 899f3e93f735321ea75108b41cb654c16f92d3f264cJames Bottomley case 0x01: /* becoming ready */ 900f3e93f735321ea75108b41cb654c16f92d3f264cJames Bottomley case 0x04: /* format in progress */ 901f3e93f735321ea75108b41cb654c16f92d3f264cJames Bottomley case 0x05: /* rebuild in progress */ 902f3e93f735321ea75108b41cb654c16f92d3f264cJames Bottomley case 0x06: /* recalculation in progress */ 903f3e93f735321ea75108b41cb654c16f92d3f264cJames Bottomley case 0x07: /* operation in progress */ 904f3e93f735321ea75108b41cb654c16f92d3f264cJames Bottomley case 0x08: /* Long write in progress */ 905f3e93f735321ea75108b41cb654c16f92d3f264cJames Bottomley case 0x09: /* self test in progress */ 906d8705f11d89cfabf4a9f0ea234d4809b22abb33eMartin K. Petersen case 0x14: /* space allocation in progress */ 907b60af5b0adf0da24c673598c8d3fb4d4189a15ceAlan Stern action = ACTION_DELAYED_RETRY; 908f3e93f735321ea75108b41cb654c16f92d3f264cJames Bottomley break; 9093dbf6a54046052d79743822c9206af191e582ab0Alan Stern default: 9103dbf6a54046052d79743822c9206af191e582ab0Alan Stern description = "Device not ready"; 9113dbf6a54046052d79743822c9206af191e582ab0Alan Stern action = ACTION_FAIL; 9123dbf6a54046052d79743822c9206af191e582ab0Alan Stern break; 913f3e93f735321ea75108b41cb654c16f92d3f264cJames Bottomley } 914b60af5b0adf0da24c673598c8d3fb4d4189a15ceAlan Stern } else { 915b60af5b0adf0da24c673598c8d3fb4d4189a15ceAlan Stern description = "Device not ready"; 916b60af5b0adf0da24c673598c8d3fb4d4189a15ceAlan Stern action = ACTION_FAIL; 9171da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds } 918b60af5b0adf0da24c673598c8d3fb4d4189a15ceAlan Stern break; 9191da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds case VOLUME_OVERFLOW: 92003aba2f79594ca94d159c8bab454de9bcc385b76Luben Tuikov /* See SSC3rXX or current. */ 921b60af5b0adf0da24c673598c8d3fb4d4189a15ceAlan Stern action = ACTION_FAIL; 922b60af5b0adf0da24c673598c8d3fb4d4189a15ceAlan Stern break; 9231da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds default: 924b60af5b0adf0da24c673598c8d3fb4d4189a15ceAlan Stern description = "Unhandled sense code"; 925b60af5b0adf0da24c673598c8d3fb4d4189a15ceAlan Stern action = ACTION_FAIL; 9261da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds break; 9271da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds } 928b60af5b0adf0da24c673598c8d3fb4d4189a15ceAlan Stern } else { 929b60af5b0adf0da24c673598c8d3fb4d4189a15ceAlan Stern description = "Unhandled error code"; 930b60af5b0adf0da24c673598c8d3fb4d4189a15ceAlan Stern action = ACTION_FAIL; 93103aba2f79594ca94d159c8bab454de9bcc385b76Luben Tuikov } 932b60af5b0adf0da24c673598c8d3fb4d4189a15ceAlan Stern 933b60af5b0adf0da24c673598c8d3fb4d4189a15ceAlan Stern switch (action) { 934b60af5b0adf0da24c673598c8d3fb4d4189a15ceAlan Stern case ACTION_FAIL: 935b60af5b0adf0da24c673598c8d3fb4d4189a15ceAlan Stern /* Give up and fail the remainder of the request */ 93679ed24297236b7430d6ce0a1511ff70cf5b6015aJames Bottomley scsi_release_buffers(cmd); 9374aff5e2333c9a1609662f2091f55c3f6fffdad36Jens Axboe if (!(req->cmd_flags & REQ_QUIET)) { 938b60af5b0adf0da24c673598c8d3fb4d4189a15ceAlan Stern if (description) 9393dbf6a54046052d79743822c9206af191e582ab0Alan Stern scmd_printk(KERN_INFO, cmd, "%s\n", 940b60af5b0adf0da24c673598c8d3fb4d4189a15ceAlan Stern description); 941a4d04a4cd9881e89fdc62107b6b57053438f2b30Martin K. Petersen scsi_print_result(cmd); 9423173d8c342971a03857d8af749a3f57da7d06b57James Bottomley if (driver_byte(result) & DRIVER_SENSE) 9433173d8c342971a03857d8af749a3f57da7d06b57James Bottomley scsi_print_sense("", cmd); 944002b1eb2c03ccec36bf6e7b719cccedf57d83402Martin K. Petersen scsi_print_command(cmd); 9453173d8c342971a03857d8af749a3f57da7d06b57James Bottomley } 946ad63082626f99651d261ccd8698ce4e997362f7eMike Christie if (blk_end_request_err(req, error)) 947da6c5c720c52cc717124f8f0830b710ea6a092fdTejun Heo scsi_requeue_command(q, cmd); 948da6c5c720c52cc717124f8f0830b710ea6a092fdTejun Heo else 949da6c5c720c52cc717124f8f0830b710ea6a092fdTejun Heo scsi_next_command(cmd); 950b60af5b0adf0da24c673598c8d3fb4d4189a15ceAlan Stern break; 951b60af5b0adf0da24c673598c8d3fb4d4189a15ceAlan Stern case ACTION_REPREP: 952b60af5b0adf0da24c673598c8d3fb4d4189a15ceAlan Stern /* Unprep the request and put it back at the head of the queue. 953b60af5b0adf0da24c673598c8d3fb4d4189a15ceAlan Stern * A new command will be prepared and issued. 954b60af5b0adf0da24c673598c8d3fb4d4189a15ceAlan Stern */ 95579ed24297236b7430d6ce0a1511ff70cf5b6015aJames Bottomley scsi_release_buffers(cmd); 956b60af5b0adf0da24c673598c8d3fb4d4189a15ceAlan Stern scsi_requeue_command(q, cmd); 957b60af5b0adf0da24c673598c8d3fb4d4189a15ceAlan Stern break; 958b60af5b0adf0da24c673598c8d3fb4d4189a15ceAlan Stern case ACTION_RETRY: 959b60af5b0adf0da24c673598c8d3fb4d4189a15ceAlan Stern /* Retry the same command immediately */ 9604f5299ac4e3a03d5c596c00d726fa932c600609dJames Bottomley __scsi_queue_insert(cmd, SCSI_MLQUEUE_EH_RETRY, 0); 961b60af5b0adf0da24c673598c8d3fb4d4189a15ceAlan Stern break; 962b60af5b0adf0da24c673598c8d3fb4d4189a15ceAlan Stern case ACTION_DELAYED_RETRY: 963b60af5b0adf0da24c673598c8d3fb4d4189a15ceAlan Stern /* Retry the same command after a delay */ 9644f5299ac4e3a03d5c596c00d726fa932c600609dJames Bottomley __scsi_queue_insert(cmd, SCSI_MLQUEUE_DEVICE_BUSY, 0); 965b60af5b0adf0da24c673598c8d3fb4d4189a15ceAlan Stern break; 9661da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds } 9671da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds} 9681da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 9696f9a35e2dafa0f855ab051c11bdbf739745ff6f5Boaz Harroshstatic int scsi_init_sgtable(struct request *req, struct scsi_data_buffer *sdb, 9706f9a35e2dafa0f855ab051c11bdbf739745ff6f5Boaz Harrosh gfp_t gfp_mask) 9711da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds{ 9726f9a35e2dafa0f855ab051c11bdbf739745ff6f5Boaz Harrosh int count; 9731da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 9741da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds /* 9753b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig * If sg table allocation fails, requeue request later. 9761da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds */ 97730b0c37b27485a9cb897bfe3824f6f517b8c80d6Boaz Harrosh if (unlikely(scsi_alloc_sgtable(sdb, req->nr_phys_segments, 97830b0c37b27485a9cb897bfe3824f6f517b8c80d6Boaz Harrosh gfp_mask))) { 9791da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds return BLKPREP_DEFER; 9807c72ce81870ded9365f4bc5caa98ef1591dd18ddAlan Stern } 9811da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 9823b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig req->buffer = NULL; 9831da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 9841da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds /* 9851da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Next, walk the list, and fill in the addresses and sizes of 9861da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * each segment. 9871da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds */ 98830b0c37b27485a9cb897bfe3824f6f517b8c80d6Boaz Harrosh count = blk_rq_map_sg(req->q, req, sdb->table.sgl); 98930b0c37b27485a9cb897bfe3824f6f517b8c80d6Boaz Harrosh BUG_ON(count > sdb->table.nents); 99030b0c37b27485a9cb897bfe3824f6f517b8c80d6Boaz Harrosh sdb->table.nents = count; 9911011c1b9f2e45ce7c6e38888d2b83936aec38771Tejun Heo sdb->length = blk_rq_bytes(req); 9924a03d90e35bc5273d27301fa669d4b2103196f94Rusty Russell return BLKPREP_OK; 9931da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds} 9946f9a35e2dafa0f855ab051c11bdbf739745ff6f5Boaz Harrosh 9956f9a35e2dafa0f855ab051c11bdbf739745ff6f5Boaz Harrosh/* 9966f9a35e2dafa0f855ab051c11bdbf739745ff6f5Boaz Harrosh * Function: scsi_init_io() 9976f9a35e2dafa0f855ab051c11bdbf739745ff6f5Boaz Harrosh * 9986f9a35e2dafa0f855ab051c11bdbf739745ff6f5Boaz Harrosh * Purpose: SCSI I/O initialize function. 9996f9a35e2dafa0f855ab051c11bdbf739745ff6f5Boaz Harrosh * 10006f9a35e2dafa0f855ab051c11bdbf739745ff6f5Boaz Harrosh * Arguments: cmd - Command descriptor we wish to initialize 10016f9a35e2dafa0f855ab051c11bdbf739745ff6f5Boaz Harrosh * 10026f9a35e2dafa0f855ab051c11bdbf739745ff6f5Boaz Harrosh * Returns: 0 on success 10036f9a35e2dafa0f855ab051c11bdbf739745ff6f5Boaz Harrosh * BLKPREP_DEFER if the failure is retryable 10046f9a35e2dafa0f855ab051c11bdbf739745ff6f5Boaz Harrosh * BLKPREP_KILL if the failure is fatal 10056f9a35e2dafa0f855ab051c11bdbf739745ff6f5Boaz Harrosh */ 10066f9a35e2dafa0f855ab051c11bdbf739745ff6f5Boaz Harroshint scsi_init_io(struct scsi_cmnd *cmd, gfp_t gfp_mask) 10076f9a35e2dafa0f855ab051c11bdbf739745ff6f5Boaz Harrosh{ 100813f05c8d8e98bbdce89158bfdb2e380940695a88Martin K. Petersen struct request *rq = cmd->request; 100913f05c8d8e98bbdce89158bfdb2e380940695a88Martin K. Petersen 101013f05c8d8e98bbdce89158bfdb2e380940695a88Martin K. Petersen int error = scsi_init_sgtable(rq, &cmd->sdb, gfp_mask); 10116f9a35e2dafa0f855ab051c11bdbf739745ff6f5Boaz Harrosh if (error) 10126f9a35e2dafa0f855ab051c11bdbf739745ff6f5Boaz Harrosh goto err_exit; 10136f9a35e2dafa0f855ab051c11bdbf739745ff6f5Boaz Harrosh 101413f05c8d8e98bbdce89158bfdb2e380940695a88Martin K. Petersen if (blk_bidi_rq(rq)) { 10156f9a35e2dafa0f855ab051c11bdbf739745ff6f5Boaz Harrosh struct scsi_data_buffer *bidi_sdb = kmem_cache_zalloc( 10166362abd3e00d3161affad996fa53cc69a01fc6d1Martin K. Petersen scsi_sdb_cache, GFP_ATOMIC); 10176f9a35e2dafa0f855ab051c11bdbf739745ff6f5Boaz Harrosh if (!bidi_sdb) { 10186f9a35e2dafa0f855ab051c11bdbf739745ff6f5Boaz Harrosh error = BLKPREP_DEFER; 10196f9a35e2dafa0f855ab051c11bdbf739745ff6f5Boaz Harrosh goto err_exit; 10206f9a35e2dafa0f855ab051c11bdbf739745ff6f5Boaz Harrosh } 10216f9a35e2dafa0f855ab051c11bdbf739745ff6f5Boaz Harrosh 102213f05c8d8e98bbdce89158bfdb2e380940695a88Martin K. Petersen rq->next_rq->special = bidi_sdb; 102313f05c8d8e98bbdce89158bfdb2e380940695a88Martin K. Petersen error = scsi_init_sgtable(rq->next_rq, bidi_sdb, GFP_ATOMIC); 10246f9a35e2dafa0f855ab051c11bdbf739745ff6f5Boaz Harrosh if (error) 10256f9a35e2dafa0f855ab051c11bdbf739745ff6f5Boaz Harrosh goto err_exit; 10266f9a35e2dafa0f855ab051c11bdbf739745ff6f5Boaz Harrosh } 10276f9a35e2dafa0f855ab051c11bdbf739745ff6f5Boaz Harrosh 102813f05c8d8e98bbdce89158bfdb2e380940695a88Martin K. Petersen if (blk_integrity_rq(rq)) { 10297027ad72a689797475973c6feb5f0b673382f779Martin K. Petersen struct scsi_data_buffer *prot_sdb = cmd->prot_sdb; 10307027ad72a689797475973c6feb5f0b673382f779Martin K. Petersen int ivecs, count; 10317027ad72a689797475973c6feb5f0b673382f779Martin K. Petersen 10327027ad72a689797475973c6feb5f0b673382f779Martin K. Petersen BUG_ON(prot_sdb == NULL); 103313f05c8d8e98bbdce89158bfdb2e380940695a88Martin K. Petersen ivecs = blk_rq_count_integrity_sg(rq->q, rq->bio); 10347027ad72a689797475973c6feb5f0b673382f779Martin K. Petersen 10357027ad72a689797475973c6feb5f0b673382f779Martin K. Petersen if (scsi_alloc_sgtable(prot_sdb, ivecs, gfp_mask)) { 10367027ad72a689797475973c6feb5f0b673382f779Martin K. Petersen error = BLKPREP_DEFER; 10377027ad72a689797475973c6feb5f0b673382f779Martin K. Petersen goto err_exit; 10387027ad72a689797475973c6feb5f0b673382f779Martin K. Petersen } 10397027ad72a689797475973c6feb5f0b673382f779Martin K. Petersen 104013f05c8d8e98bbdce89158bfdb2e380940695a88Martin K. Petersen count = blk_rq_map_integrity_sg(rq->q, rq->bio, 10417027ad72a689797475973c6feb5f0b673382f779Martin K. Petersen prot_sdb->table.sgl); 10427027ad72a689797475973c6feb5f0b673382f779Martin K. Petersen BUG_ON(unlikely(count > ivecs)); 104313f05c8d8e98bbdce89158bfdb2e380940695a88Martin K. Petersen BUG_ON(unlikely(count > queue_max_integrity_segments(rq->q))); 10447027ad72a689797475973c6feb5f0b673382f779Martin K. Petersen 10457027ad72a689797475973c6feb5f0b673382f779Martin K. Petersen cmd->prot_sdb = prot_sdb; 10467027ad72a689797475973c6feb5f0b673382f779Martin K. Petersen cmd->prot_sdb->table.nents = count; 10477027ad72a689797475973c6feb5f0b673382f779Martin K. Petersen } 10487027ad72a689797475973c6feb5f0b673382f779Martin K. Petersen 10496f9a35e2dafa0f855ab051c11bdbf739745ff6f5Boaz Harrosh return BLKPREP_OK ; 10506f9a35e2dafa0f855ab051c11bdbf739745ff6f5Boaz Harrosh 10516f9a35e2dafa0f855ab051c11bdbf739745ff6f5Boaz Harrosherr_exit: 10526f9a35e2dafa0f855ab051c11bdbf739745ff6f5Boaz Harrosh scsi_release_buffers(cmd); 1053610a63498f7f366031a6327eaaa9963ffa110b2bFUJITA Tomonori cmd->request->special = NULL; 10543a5c19c23db65a554f2e4f5df5f307c668277056James Bottomley scsi_put_command(cmd); 10556f9a35e2dafa0f855ab051c11bdbf739745ff6f5Boaz Harrosh return error; 10566f9a35e2dafa0f855ab051c11bdbf739745ff6f5Boaz Harrosh} 1057bb52d82f45df3a2661d88befba7c79a7db8be496Boaz HarroshEXPORT_SYMBOL(scsi_init_io); 10581da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 10593b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwigstatic struct scsi_cmnd *scsi_get_cmd_from_req(struct scsi_device *sdev, 10603b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig struct request *req) 10613b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig{ 10623b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig struct scsi_cmnd *cmd; 10633b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig 10643b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig if (!req->special) { 10653b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig cmd = scsi_get_command(sdev, GFP_ATOMIC); 10663b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig if (unlikely(!cmd)) 10673b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig return NULL; 10683b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig req->special = cmd; 10693b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig } else { 10703b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig cmd = req->special; 10713b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig } 10723b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig 10733b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig /* pull a tag out of the request if we have one */ 10743b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig cmd->tag = req->tag; 10753b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig cmd->request = req; 10763b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig 107764a87b244b9297667ca80264aab849a36f494884Boaz Harrosh cmd->cmnd = req->cmd; 107872f7d322fd60ce1a0579136dec7b26b0801ded4bMartin K. Petersen cmd->prot_op = SCSI_PROT_NORMAL; 107964a87b244b9297667ca80264aab849a36f494884Boaz Harrosh 10803b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig return cmd; 10813b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig} 10823b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig 10837f9a6bc4e9d59e7fcf03ed23f60cd81ca5d80b65James Bottomleyint scsi_setup_blk_pc_cmnd(struct scsi_device *sdev, struct request *req) 10847b16318dea8d9840dac567a2ae8c50ecdea36aeaJames Bottomley{ 10853b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig struct scsi_cmnd *cmd; 10867f9a6bc4e9d59e7fcf03ed23f60cd81ca5d80b65James Bottomley int ret = scsi_prep_state_check(sdev, req); 10877f9a6bc4e9d59e7fcf03ed23f60cd81ca5d80b65James Bottomley 10887f9a6bc4e9d59e7fcf03ed23f60cd81ca5d80b65James Bottomley if (ret != BLKPREP_OK) 10897f9a6bc4e9d59e7fcf03ed23f60cd81ca5d80b65James Bottomley return ret; 10903b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig 10913b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig cmd = scsi_get_cmd_from_req(sdev, req); 10923b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig if (unlikely(!cmd)) 10933b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig return BLKPREP_DEFER; 10943b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig 10953b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig /* 10963b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig * BLOCK_PC requests may transfer data, in which case they must 10973b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig * a bio attached to them. Or they might contain a SCSI command 10983b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig * that does not transfer data, in which case they may optionally 10993b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig * submit a request without an attached bio. 11003b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig */ 11013b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig if (req->bio) { 11023b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig int ret; 11033b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig 11043b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig BUG_ON(!req->nr_phys_segments); 11053b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig 1106bb52d82f45df3a2661d88befba7c79a7db8be496Boaz Harrosh ret = scsi_init_io(cmd, GFP_ATOMIC); 11073b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig if (unlikely(ret)) 11083b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig return ret; 11093b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig } else { 1110b0790410300abaaf4f25f702803beff701baebf1Tejun Heo BUG_ON(blk_rq_bytes(req)); 11113b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig 111230b0c37b27485a9cb897bfe3824f6f517b8c80d6Boaz Harrosh memset(&cmd->sdb, 0, sizeof(cmd->sdb)); 11133b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig req->buffer = NULL; 11143b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig } 11157b16318dea8d9840dac567a2ae8c50ecdea36aeaJames Bottomley 11167b16318dea8d9840dac567a2ae8c50ecdea36aeaJames Bottomley cmd->cmd_len = req->cmd_len; 1117b0790410300abaaf4f25f702803beff701baebf1Tejun Heo if (!blk_rq_bytes(req)) 11187b16318dea8d9840dac567a2ae8c50ecdea36aeaJames Bottomley cmd->sc_data_direction = DMA_NONE; 11197b16318dea8d9840dac567a2ae8c50ecdea36aeaJames Bottomley else if (rq_data_dir(req) == WRITE) 11207b16318dea8d9840dac567a2ae8c50ecdea36aeaJames Bottomley cmd->sc_data_direction = DMA_TO_DEVICE; 11217b16318dea8d9840dac567a2ae8c50ecdea36aeaJames Bottomley else 11227b16318dea8d9840dac567a2ae8c50ecdea36aeaJames Bottomley cmd->sc_data_direction = DMA_FROM_DEVICE; 11237b16318dea8d9840dac567a2ae8c50ecdea36aeaJames Bottomley 1124b0790410300abaaf4f25f702803beff701baebf1Tejun Heo cmd->transfersize = blk_rq_bytes(req); 11257b16318dea8d9840dac567a2ae8c50ecdea36aeaJames Bottomley cmd->allowed = req->retries; 11263b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig return BLKPREP_OK; 11277b16318dea8d9840dac567a2ae8c50ecdea36aeaJames Bottomley} 11287f9a6bc4e9d59e7fcf03ed23f60cd81ca5d80b65James BottomleyEXPORT_SYMBOL(scsi_setup_blk_pc_cmnd); 11297b16318dea8d9840dac567a2ae8c50ecdea36aeaJames Bottomley 11303b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig/* 11313b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig * Setup a REQ_TYPE_FS command. These are simple read/write request 11323b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig * from filesystems that still need to be translated to SCSI CDBs from 11333b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig * the ULD. 11343b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig */ 11357f9a6bc4e9d59e7fcf03ed23f60cd81ca5d80b65James Bottomleyint scsi_setup_fs_cmnd(struct scsi_device *sdev, struct request *req) 11361da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds{ 11371da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds struct scsi_cmnd *cmd; 11387f9a6bc4e9d59e7fcf03ed23f60cd81ca5d80b65James Bottomley int ret = scsi_prep_state_check(sdev, req); 11391da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 11407f9a6bc4e9d59e7fcf03ed23f60cd81ca5d80b65James Bottomley if (ret != BLKPREP_OK) 11417f9a6bc4e9d59e7fcf03ed23f60cd81ca5d80b65James Bottomley return ret; 1142a6a8d9f87eb8510a8f53672ea87703f62185d75fChandra Seetharaman 1143a6a8d9f87eb8510a8f53672ea87703f62185d75fChandra Seetharaman if (unlikely(sdev->scsi_dh_data && sdev->scsi_dh_data->scsi_dh 1144a6a8d9f87eb8510a8f53672ea87703f62185d75fChandra Seetharaman && sdev->scsi_dh_data->scsi_dh->prep_fn)) { 1145a6a8d9f87eb8510a8f53672ea87703f62185d75fChandra Seetharaman ret = sdev->scsi_dh_data->scsi_dh->prep_fn(sdev, req); 1146a6a8d9f87eb8510a8f53672ea87703f62185d75fChandra Seetharaman if (ret != BLKPREP_OK) 1147a6a8d9f87eb8510a8f53672ea87703f62185d75fChandra Seetharaman return ret; 1148a6a8d9f87eb8510a8f53672ea87703f62185d75fChandra Seetharaman } 1149a6a8d9f87eb8510a8f53672ea87703f62185d75fChandra Seetharaman 11501da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds /* 11513b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig * Filesystem requests must transfer data. 11521da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds */ 11533b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig BUG_ON(!req->nr_phys_segments); 11543b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig 11553b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig cmd = scsi_get_cmd_from_req(sdev, req); 11563b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig if (unlikely(!cmd)) 11573b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig return BLKPREP_DEFER; 11583b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig 115964a87b244b9297667ca80264aab849a36f494884Boaz Harrosh memset(cmd->cmnd, 0, BLK_MAX_CDB); 1160bb52d82f45df3a2661d88befba7c79a7db8be496Boaz Harrosh return scsi_init_io(cmd, GFP_ATOMIC); 11613b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig} 11627f9a6bc4e9d59e7fcf03ed23f60cd81ca5d80b65James BottomleyEXPORT_SYMBOL(scsi_setup_fs_cmnd); 11633b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig 11647f9a6bc4e9d59e7fcf03ed23f60cd81ca5d80b65James Bottomleyint scsi_prep_state_check(struct scsi_device *sdev, struct request *req) 11653b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig{ 11663b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig int ret = BLKPREP_OK; 11673b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig 11681da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds /* 11693b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig * If the device is not in running state we will reject some 11703b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig * or all commands. 11711da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds */ 11723b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig if (unlikely(sdev->sdev_state != SDEV_RUNNING)) { 11733b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig switch (sdev->sdev_state) { 11743b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig case SDEV_OFFLINE: 11753b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig /* 11763b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig * If the device is offline we refuse to process any 11773b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig * commands. The device must be brought online 11783b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig * before trying any recovery commands. 11793b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig */ 11803b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig sdev_printk(KERN_ERR, sdev, 11813b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig "rejecting I/O to offline device\n"); 11823b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig ret = BLKPREP_KILL; 11833b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig break; 11843b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig case SDEV_DEL: 11853b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig /* 11863b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig * If the device is fully deleted, we refuse to 11873b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig * process any commands as well. 11883b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig */ 11899ccfc756a70d454dfa82f48897e2883560c01a0eJames Bottomley sdev_printk(KERN_ERR, sdev, 11903b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig "rejecting I/O to dead device\n"); 11913b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig ret = BLKPREP_KILL; 11923b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig break; 11933b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig case SDEV_QUIESCE: 11943b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig case SDEV_BLOCK: 11956f4267e3bd1211b3d09130e626b0b3d885077610James Bottomley case SDEV_CREATED_BLOCK: 11963b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig /* 11973b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig * If the devices is blocked we defer normal commands. 11983b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig */ 11993b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig if (!(req->cmd_flags & REQ_PREEMPT)) 12003b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig ret = BLKPREP_DEFER; 12013b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig break; 12023b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig default: 12033b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig /* 12043b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig * For any other not fully online state we only allow 12053b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig * special commands. In particular any user initiated 12063b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig * command is not allowed. 12073b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig */ 12083b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig if (!(req->cmd_flags & REQ_PREEMPT)) 12093b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig ret = BLKPREP_KILL; 12103b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig break; 12111da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds } 12121da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds } 12137f9a6bc4e9d59e7fcf03ed23f60cd81ca5d80b65James Bottomley return ret; 12147f9a6bc4e9d59e7fcf03ed23f60cd81ca5d80b65James Bottomley} 12157f9a6bc4e9d59e7fcf03ed23f60cd81ca5d80b65James BottomleyEXPORT_SYMBOL(scsi_prep_state_check); 12161da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 12177f9a6bc4e9d59e7fcf03ed23f60cd81ca5d80b65James Bottomleyint scsi_prep_return(struct request_queue *q, struct request *req, int ret) 12187f9a6bc4e9d59e7fcf03ed23f60cd81ca5d80b65James Bottomley{ 12197f9a6bc4e9d59e7fcf03ed23f60cd81ca5d80b65James Bottomley struct scsi_device *sdev = q->queuedata; 12201da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 12213b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig switch (ret) { 12223b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig case BLKPREP_KILL: 12233b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig req->errors = DID_NO_CONNECT << 16; 12247f9a6bc4e9d59e7fcf03ed23f60cd81ca5d80b65James Bottomley /* release the command and kill it */ 12257f9a6bc4e9d59e7fcf03ed23f60cd81ca5d80b65James Bottomley if (req->special) { 12267f9a6bc4e9d59e7fcf03ed23f60cd81ca5d80b65James Bottomley struct scsi_cmnd *cmd = req->special; 12277f9a6bc4e9d59e7fcf03ed23f60cd81ca5d80b65James Bottomley scsi_release_buffers(cmd); 12287f9a6bc4e9d59e7fcf03ed23f60cd81ca5d80b65James Bottomley scsi_put_command(cmd); 12297f9a6bc4e9d59e7fcf03ed23f60cd81ca5d80b65James Bottomley req->special = NULL; 12307f9a6bc4e9d59e7fcf03ed23f60cd81ca5d80b65James Bottomley } 12313b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig break; 12323b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig case BLKPREP_DEFER: 12331da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds /* 12349934c8c04561413609d2bc38c6b9f268cba774a4Tejun Heo * If we defer, the blk_peek_request() returns NULL, but the 1235a488e74976bf0a9bccecdd094378394942dacef1Jens Axboe * queue must be restarted, so we schedule a callback to happen 1236a488e74976bf0a9bccecdd094378394942dacef1Jens Axboe * shortly. 12371da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds */ 12383b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig if (sdev->device_busy == 0) 1239a488e74976bf0a9bccecdd094378394942dacef1Jens Axboe blk_delay_queue(q, SCSI_QUEUE_DELAY); 12403b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig break; 12413b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig default: 12423b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig req->cmd_flags |= REQ_DONTPREP; 12431da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds } 12441da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 12453b00315799d78f76531b71435fbc2643cd71ae4cChristoph Hellwig return ret; 12461da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds} 12477f9a6bc4e9d59e7fcf03ed23f60cd81ca5d80b65James BottomleyEXPORT_SYMBOL(scsi_prep_return); 12487f9a6bc4e9d59e7fcf03ed23f60cd81ca5d80b65James Bottomley 1249751bf4d7865e4ced406be93b04c7436d866d3684James Bottomleyint scsi_prep_fn(struct request_queue *q, struct request *req) 12507f9a6bc4e9d59e7fcf03ed23f60cd81ca5d80b65James Bottomley{ 12517f9a6bc4e9d59e7fcf03ed23f60cd81ca5d80b65James Bottomley struct scsi_device *sdev = q->queuedata; 12527f9a6bc4e9d59e7fcf03ed23f60cd81ca5d80b65James Bottomley int ret = BLKPREP_KILL; 12537f9a6bc4e9d59e7fcf03ed23f60cd81ca5d80b65James Bottomley 12547f9a6bc4e9d59e7fcf03ed23f60cd81ca5d80b65James Bottomley if (req->cmd_type == REQ_TYPE_BLOCK_PC) 12557f9a6bc4e9d59e7fcf03ed23f60cd81ca5d80b65James Bottomley ret = scsi_setup_blk_pc_cmnd(sdev, req); 12567f9a6bc4e9d59e7fcf03ed23f60cd81ca5d80b65James Bottomley return scsi_prep_return(q, req, ret); 12577f9a6bc4e9d59e7fcf03ed23f60cd81ca5d80b65James Bottomley} 1258b391277a56b9eaaff4474339c703e574ed7fab5bHannes ReineckeEXPORT_SYMBOL(scsi_prep_fn); 12591da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 12601da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds/* 12611da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * scsi_dev_queue_ready: if we can send requests to sdev, return 1 else 12621da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * return 0. 12631da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * 12641da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Called with the queue_lock held. 12651da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds */ 12661da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldsstatic inline int scsi_dev_queue_ready(struct request_queue *q, 12671da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds struct scsi_device *sdev) 12681da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds{ 12691da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds if (sdev->device_busy == 0 && sdev->device_blocked) { 12701da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds /* 12711da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * unblock after device_blocked iterates to zero 12721da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds */ 12731da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds if (--sdev->device_blocked == 0) { 12741da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds SCSI_LOG_MLQUEUE(3, 12759ccfc756a70d454dfa82f48897e2883560c01a0eJames Bottomley sdev_printk(KERN_INFO, sdev, 12769ccfc756a70d454dfa82f48897e2883560c01a0eJames Bottomley "unblocking device at zero depth\n")); 12771da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds } else { 1278a488e74976bf0a9bccecdd094378394942dacef1Jens Axboe blk_delay_queue(q, SCSI_QUEUE_DELAY); 12791da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds return 0; 12801da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds } 12811da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds } 12829d11251709f31d49c8167a619d4475fdf6cd7f73Kiyoshi Ueda if (scsi_device_is_busy(sdev)) 12831da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds return 0; 12841da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 12851da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds return 1; 12861da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds} 12871da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 1288f0c0a376d0fcd4c5579ecf5e95f88387cba85211Mike Christie 1289f0c0a376d0fcd4c5579ecf5e95f88387cba85211Mike Christie/* 1290f0c0a376d0fcd4c5579ecf5e95f88387cba85211Mike Christie * scsi_target_queue_ready: checks if there we can send commands to target 1291f0c0a376d0fcd4c5579ecf5e95f88387cba85211Mike Christie * @sdev: scsi device on starget to check. 1292f0c0a376d0fcd4c5579ecf5e95f88387cba85211Mike Christie * 1293f0c0a376d0fcd4c5579ecf5e95f88387cba85211Mike Christie * Called with the host lock held. 1294f0c0a376d0fcd4c5579ecf5e95f88387cba85211Mike Christie */ 1295f0c0a376d0fcd4c5579ecf5e95f88387cba85211Mike Christiestatic inline int scsi_target_queue_ready(struct Scsi_Host *shost, 1296f0c0a376d0fcd4c5579ecf5e95f88387cba85211Mike Christie struct scsi_device *sdev) 1297f0c0a376d0fcd4c5579ecf5e95f88387cba85211Mike Christie{ 1298f0c0a376d0fcd4c5579ecf5e95f88387cba85211Mike Christie struct scsi_target *starget = scsi_target(sdev); 1299f0c0a376d0fcd4c5579ecf5e95f88387cba85211Mike Christie 1300f0c0a376d0fcd4c5579ecf5e95f88387cba85211Mike Christie if (starget->single_lun) { 1301f0c0a376d0fcd4c5579ecf5e95f88387cba85211Mike Christie if (starget->starget_sdev_user && 1302f0c0a376d0fcd4c5579ecf5e95f88387cba85211Mike Christie starget->starget_sdev_user != sdev) 1303f0c0a376d0fcd4c5579ecf5e95f88387cba85211Mike Christie return 0; 1304f0c0a376d0fcd4c5579ecf5e95f88387cba85211Mike Christie starget->starget_sdev_user = sdev; 1305f0c0a376d0fcd4c5579ecf5e95f88387cba85211Mike Christie } 1306f0c0a376d0fcd4c5579ecf5e95f88387cba85211Mike Christie 1307f0c0a376d0fcd4c5579ecf5e95f88387cba85211Mike Christie if (starget->target_busy == 0 && starget->target_blocked) { 1308f0c0a376d0fcd4c5579ecf5e95f88387cba85211Mike Christie /* 1309f0c0a376d0fcd4c5579ecf5e95f88387cba85211Mike Christie * unblock after target_blocked iterates to zero 1310f0c0a376d0fcd4c5579ecf5e95f88387cba85211Mike Christie */ 1311f0c0a376d0fcd4c5579ecf5e95f88387cba85211Mike Christie if (--starget->target_blocked == 0) { 1312f0c0a376d0fcd4c5579ecf5e95f88387cba85211Mike Christie SCSI_LOG_MLQUEUE(3, starget_printk(KERN_INFO, starget, 1313f0c0a376d0fcd4c5579ecf5e95f88387cba85211Mike Christie "unblocking target at zero depth\n")); 1314b4efdd586bc08cdf5977cad0a90091f44546a930Mike Christie } else 1315f0c0a376d0fcd4c5579ecf5e95f88387cba85211Mike Christie return 0; 1316f0c0a376d0fcd4c5579ecf5e95f88387cba85211Mike Christie } 1317f0c0a376d0fcd4c5579ecf5e95f88387cba85211Mike Christie 1318f0c0a376d0fcd4c5579ecf5e95f88387cba85211Mike Christie if (scsi_target_is_busy(starget)) { 1319466c08c71a7dc19528e9b336c5bfa5ec41730c7cShaohua Li list_move_tail(&sdev->starved_entry, &shost->starved_list); 1320fd01a6632da253210c3dbc7814bc6eceda96623dHillf Danton return 0; 1321f0c0a376d0fcd4c5579ecf5e95f88387cba85211Mike Christie } 1322f0c0a376d0fcd4c5579ecf5e95f88387cba85211Mike Christie 1323f0c0a376d0fcd4c5579ecf5e95f88387cba85211Mike Christie return 1; 1324f0c0a376d0fcd4c5579ecf5e95f88387cba85211Mike Christie} 1325f0c0a376d0fcd4c5579ecf5e95f88387cba85211Mike Christie 13261da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds/* 13271da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * scsi_host_queue_ready: if we can send requests to shost, return 1 else 13281da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * return 0. We must end up running the queue again whenever 0 is 13291da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * returned, else IO can hang. 13301da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * 13311da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Called with host_lock held. 13321da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds */ 13331da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldsstatic inline int scsi_host_queue_ready(struct request_queue *q, 13341da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds struct Scsi_Host *shost, 13351da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds struct scsi_device *sdev) 13361da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds{ 1337939647ee308e0ad924e776657704c7bedd498664James Bottomley if (scsi_host_in_recovery(shost)) 13381da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds return 0; 13391da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds if (shost->host_busy == 0 && shost->host_blocked) { 13401da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds /* 13411da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * unblock after host_blocked iterates to zero 13421da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds */ 13431da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds if (--shost->host_blocked == 0) { 13441da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds SCSI_LOG_MLQUEUE(3, 13451da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds printk("scsi%d unblocking host at zero depth\n", 13461da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds shost->host_no)); 13471da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds } else { 13481da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds return 0; 13491da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds } 13501da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds } 13519d11251709f31d49c8167a619d4475fdf6cd7f73Kiyoshi Ueda if (scsi_host_is_busy(shost)) { 13521da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds if (list_empty(&sdev->starved_entry)) 13531da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds list_add_tail(&sdev->starved_entry, &shost->starved_list); 13541da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds return 0; 13551da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds } 13561da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 13571da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds /* We're OK to process the command, so we can't be starved */ 13581da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds if (!list_empty(&sdev->starved_entry)) 13591da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds list_del_init(&sdev->starved_entry); 13601da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 13611da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds return 1; 13621da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds} 13631da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 13641da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds/* 13656c5121b78ba5c70a9990e2af6cb4d6bbffe0d4d8Kiyoshi Ueda * Busy state exporting function for request stacking drivers. 13666c5121b78ba5c70a9990e2af6cb4d6bbffe0d4d8Kiyoshi Ueda * 13676c5121b78ba5c70a9990e2af6cb4d6bbffe0d4d8Kiyoshi Ueda * For efficiency, no lock is taken to check the busy state of 13686c5121b78ba5c70a9990e2af6cb4d6bbffe0d4d8Kiyoshi Ueda * shost/starget/sdev, since the returned value is not guaranteed and 13696c5121b78ba5c70a9990e2af6cb4d6bbffe0d4d8Kiyoshi Ueda * may be changed after request stacking drivers call the function, 13706c5121b78ba5c70a9990e2af6cb4d6bbffe0d4d8Kiyoshi Ueda * regardless of taking lock or not. 13716c5121b78ba5c70a9990e2af6cb4d6bbffe0d4d8Kiyoshi Ueda * 13726c5121b78ba5c70a9990e2af6cb4d6bbffe0d4d8Kiyoshi Ueda * When scsi can't dispatch I/Os anymore and needs to kill I/Os 13736c5121b78ba5c70a9990e2af6cb4d6bbffe0d4d8Kiyoshi Ueda * (e.g. !sdev), scsi needs to return 'not busy'. 13746c5121b78ba5c70a9990e2af6cb4d6bbffe0d4d8Kiyoshi Ueda * Otherwise, request stacking drivers may hold requests forever. 13756c5121b78ba5c70a9990e2af6cb4d6bbffe0d4d8Kiyoshi Ueda */ 13766c5121b78ba5c70a9990e2af6cb4d6bbffe0d4d8Kiyoshi Uedastatic int scsi_lld_busy(struct request_queue *q) 13776c5121b78ba5c70a9990e2af6cb4d6bbffe0d4d8Kiyoshi Ueda{ 13786c5121b78ba5c70a9990e2af6cb4d6bbffe0d4d8Kiyoshi Ueda struct scsi_device *sdev = q->queuedata; 13796c5121b78ba5c70a9990e2af6cb4d6bbffe0d4d8Kiyoshi Ueda struct Scsi_Host *shost; 13806c5121b78ba5c70a9990e2af6cb4d6bbffe0d4d8Kiyoshi Ueda struct scsi_target *starget; 13816c5121b78ba5c70a9990e2af6cb4d6bbffe0d4d8Kiyoshi Ueda 13826c5121b78ba5c70a9990e2af6cb4d6bbffe0d4d8Kiyoshi Ueda if (!sdev) 13836c5121b78ba5c70a9990e2af6cb4d6bbffe0d4d8Kiyoshi Ueda return 0; 13846c5121b78ba5c70a9990e2af6cb4d6bbffe0d4d8Kiyoshi Ueda 13856c5121b78ba5c70a9990e2af6cb4d6bbffe0d4d8Kiyoshi Ueda shost = sdev->host; 13866c5121b78ba5c70a9990e2af6cb4d6bbffe0d4d8Kiyoshi Ueda starget = scsi_target(sdev); 13876c5121b78ba5c70a9990e2af6cb4d6bbffe0d4d8Kiyoshi Ueda 13886c5121b78ba5c70a9990e2af6cb4d6bbffe0d4d8Kiyoshi Ueda if (scsi_host_in_recovery(shost) || scsi_host_is_busy(shost) || 13896c5121b78ba5c70a9990e2af6cb4d6bbffe0d4d8Kiyoshi Ueda scsi_target_is_busy(starget) || scsi_device_is_busy(sdev)) 13906c5121b78ba5c70a9990e2af6cb4d6bbffe0d4d8Kiyoshi Ueda return 1; 13916c5121b78ba5c70a9990e2af6cb4d6bbffe0d4d8Kiyoshi Ueda 13926c5121b78ba5c70a9990e2af6cb4d6bbffe0d4d8Kiyoshi Ueda return 0; 13936c5121b78ba5c70a9990e2af6cb4d6bbffe0d4d8Kiyoshi Ueda} 13946c5121b78ba5c70a9990e2af6cb4d6bbffe0d4d8Kiyoshi Ueda 13956c5121b78ba5c70a9990e2af6cb4d6bbffe0d4d8Kiyoshi Ueda/* 1396e91442b635be776ea205fba233bdd5bc74b62bc3James Bottomley * Kill a request for a dead device 13971da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds */ 1398165125e1e480f9510a5ffcfbfee4e3ee38c05f23Jens Axboestatic void scsi_kill_request(struct request *req, struct request_queue *q) 13991da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds{ 1400e91442b635be776ea205fba233bdd5bc74b62bc3James Bottomley struct scsi_cmnd *cmd = req->special; 140103b147083a2f9a2a3fbbd2505fa88ffa3c6ab194Jiri Slaby struct scsi_device *sdev; 140203b147083a2f9a2a3fbbd2505fa88ffa3c6ab194Jiri Slaby struct scsi_target *starget; 140303b147083a2f9a2a3fbbd2505fa88ffa3c6ab194Jiri Slaby struct Scsi_Host *shost; 14041da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 14059934c8c04561413609d2bc38c6b9f268cba774a4Tejun Heo blk_start_request(req); 1406788ce43aa1ad7158f894b6bb3df8ba2f63794c20James Bottomley 1407745718132c3c7cac98a622b610e239dcd5217f71Hannes Reinecke scmd_printk(KERN_INFO, cmd, "killing request\n"); 1408745718132c3c7cac98a622b610e239dcd5217f71Hannes Reinecke 140903b147083a2f9a2a3fbbd2505fa88ffa3c6ab194Jiri Slaby sdev = cmd->device; 141003b147083a2f9a2a3fbbd2505fa88ffa3c6ab194Jiri Slaby starget = scsi_target(sdev); 141103b147083a2f9a2a3fbbd2505fa88ffa3c6ab194Jiri Slaby shost = sdev->host; 1412e91442b635be776ea205fba233bdd5bc74b62bc3James Bottomley scsi_init_cmd_errh(cmd); 1413e91442b635be776ea205fba233bdd5bc74b62bc3James Bottomley cmd->result = DID_NO_CONNECT << 16; 1414e91442b635be776ea205fba233bdd5bc74b62bc3James Bottomley atomic_inc(&cmd->device->iorequest_cnt); 1415e36e0c80137af8f012528938dab2970c26d5ec4cTejun Heo 1416e36e0c80137af8f012528938dab2970c26d5ec4cTejun Heo /* 1417e36e0c80137af8f012528938dab2970c26d5ec4cTejun Heo * SCSI request completion path will do scsi_device_unbusy(), 1418e36e0c80137af8f012528938dab2970c26d5ec4cTejun Heo * bump busy counts. To bump the counters, we need to dance 1419e36e0c80137af8f012528938dab2970c26d5ec4cTejun Heo * with the locks as normal issue path does. 1420e36e0c80137af8f012528938dab2970c26d5ec4cTejun Heo */ 1421e36e0c80137af8f012528938dab2970c26d5ec4cTejun Heo sdev->device_busy++; 1422e36e0c80137af8f012528938dab2970c26d5ec4cTejun Heo spin_unlock(sdev->request_queue->queue_lock); 1423e36e0c80137af8f012528938dab2970c26d5ec4cTejun Heo spin_lock(shost->host_lock); 1424e36e0c80137af8f012528938dab2970c26d5ec4cTejun Heo shost->host_busy++; 1425f0c0a376d0fcd4c5579ecf5e95f88387cba85211Mike Christie starget->target_busy++; 1426e36e0c80137af8f012528938dab2970c26d5ec4cTejun Heo spin_unlock(shost->host_lock); 1427e36e0c80137af8f012528938dab2970c26d5ec4cTejun Heo spin_lock(sdev->request_queue->queue_lock); 1428e36e0c80137af8f012528938dab2970c26d5ec4cTejun Heo 1429242f9dcb8ba6f68fcd217a119a7648a4f69290e9Jens Axboe blk_complete_request(req); 14301da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds} 14311da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 14321aea6434eebd25e532d2e5ddabf2733af4e1ff0bJens Axboestatic void scsi_softirq_done(struct request *rq) 14331aea6434eebd25e532d2e5ddabf2733af4e1ff0bJens Axboe{ 1434242f9dcb8ba6f68fcd217a119a7648a4f69290e9Jens Axboe struct scsi_cmnd *cmd = rq->special; 1435242f9dcb8ba6f68fcd217a119a7648a4f69290e9Jens Axboe unsigned long wait_for = (cmd->allowed + 1) * rq->timeout; 14361aea6434eebd25e532d2e5ddabf2733af4e1ff0bJens Axboe int disposition; 14371aea6434eebd25e532d2e5ddabf2733af4e1ff0bJens Axboe 14381aea6434eebd25e532d2e5ddabf2733af4e1ff0bJens Axboe INIT_LIST_HEAD(&cmd->eh_entry); 14391aea6434eebd25e532d2e5ddabf2733af4e1ff0bJens Axboe 1440242f9dcb8ba6f68fcd217a119a7648a4f69290e9Jens Axboe atomic_inc(&cmd->device->iodone_cnt); 1441242f9dcb8ba6f68fcd217a119a7648a4f69290e9Jens Axboe if (cmd->result) 1442242f9dcb8ba6f68fcd217a119a7648a4f69290e9Jens Axboe atomic_inc(&cmd->device->ioerr_cnt); 1443242f9dcb8ba6f68fcd217a119a7648a4f69290e9Jens Axboe 14441aea6434eebd25e532d2e5ddabf2733af4e1ff0bJens Axboe disposition = scsi_decide_disposition(cmd); 14451aea6434eebd25e532d2e5ddabf2733af4e1ff0bJens Axboe if (disposition != SUCCESS && 14461aea6434eebd25e532d2e5ddabf2733af4e1ff0bJens Axboe time_before(cmd->jiffies_at_alloc + wait_for, jiffies)) { 14471aea6434eebd25e532d2e5ddabf2733af4e1ff0bJens Axboe sdev_printk(KERN_ERR, cmd->device, 14481aea6434eebd25e532d2e5ddabf2733af4e1ff0bJens Axboe "timing out command, waited %lus\n", 14491aea6434eebd25e532d2e5ddabf2733af4e1ff0bJens Axboe wait_for/HZ); 14501aea6434eebd25e532d2e5ddabf2733af4e1ff0bJens Axboe disposition = SUCCESS; 14511aea6434eebd25e532d2e5ddabf2733af4e1ff0bJens Axboe } 14521aea6434eebd25e532d2e5ddabf2733af4e1ff0bJens Axboe 14531aea6434eebd25e532d2e5ddabf2733af4e1ff0bJens Axboe scsi_log_completion(cmd, disposition); 14541aea6434eebd25e532d2e5ddabf2733af4e1ff0bJens Axboe 14551aea6434eebd25e532d2e5ddabf2733af4e1ff0bJens Axboe switch (disposition) { 14561aea6434eebd25e532d2e5ddabf2733af4e1ff0bJens Axboe case SUCCESS: 14571aea6434eebd25e532d2e5ddabf2733af4e1ff0bJens Axboe scsi_finish_command(cmd); 14581aea6434eebd25e532d2e5ddabf2733af4e1ff0bJens Axboe break; 14591aea6434eebd25e532d2e5ddabf2733af4e1ff0bJens Axboe case NEEDS_RETRY: 1460596f482a90ae27ea1b3da6a12ee42909045fbfd0Christoph Hellwig scsi_queue_insert(cmd, SCSI_MLQUEUE_EH_RETRY); 14611aea6434eebd25e532d2e5ddabf2733af4e1ff0bJens Axboe break; 14621aea6434eebd25e532d2e5ddabf2733af4e1ff0bJens Axboe case ADD_TO_MLQUEUE: 14631aea6434eebd25e532d2e5ddabf2733af4e1ff0bJens Axboe scsi_queue_insert(cmd, SCSI_MLQUEUE_DEVICE_BUSY); 14641aea6434eebd25e532d2e5ddabf2733af4e1ff0bJens Axboe break; 14651aea6434eebd25e532d2e5ddabf2733af4e1ff0bJens Axboe default: 14661aea6434eebd25e532d2e5ddabf2733af4e1ff0bJens Axboe if (!scsi_eh_scmd_add(cmd, 0)) 14671aea6434eebd25e532d2e5ddabf2733af4e1ff0bJens Axboe scsi_finish_command(cmd); 14681aea6434eebd25e532d2e5ddabf2733af4e1ff0bJens Axboe } 14691aea6434eebd25e532d2e5ddabf2733af4e1ff0bJens Axboe} 14701aea6434eebd25e532d2e5ddabf2733af4e1ff0bJens Axboe 14711da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds/* 14721da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Function: scsi_request_fn() 14731da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * 14741da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Purpose: Main strategy routine for SCSI. 14751da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * 14761da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Arguments: q - Pointer to actual queue. 14771da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * 14781da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Returns: Nothing 14791da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * 14801da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Lock status: IO request lock assumed to be held when called. 14811da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds */ 14821da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldsstatic void scsi_request_fn(struct request_queue *q) 14831da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds{ 14841da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds struct scsi_device *sdev = q->queuedata; 14851da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds struct Scsi_Host *shost; 14861da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds struct scsi_cmnd *cmd; 14871da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds struct request *req; 14881da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 14891da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds if (!sdev) { 14909934c8c04561413609d2bc38c6b9f268cba774a4Tejun Heo while ((req = blk_peek_request(q)) != NULL) 1491e91442b635be776ea205fba233bdd5bc74b62bc3James Bottomley scsi_kill_request(req, q); 14921da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds return; 14931da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds } 14941da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 14951da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds if(!get_device(&sdev->sdev_gendev)) 14961da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds /* We must be tearing the block queue down already */ 14971da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds return; 14981da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 14991da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds /* 15001da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * To start with, we keep looping until the queue is empty, or until 15011da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * the host is no longer able to accept any more requests. 15021da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds */ 15031da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds shost = sdev->host; 1504a488e74976bf0a9bccecdd094378394942dacef1Jens Axboe for (;;) { 15051da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds int rtn; 15061da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds /* 15071da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * get next queueable request. We do this early to make sure 15081da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * that the request is fully prepared even if we cannot 15091da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * accept it. 15101da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds */ 15119934c8c04561413609d2bc38c6b9f268cba774a4Tejun Heo req = blk_peek_request(q); 15121da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds if (!req || !scsi_dev_queue_ready(q, sdev)) 15131da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds break; 15141da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 15151da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds if (unlikely(!scsi_device_online(sdev))) { 15169ccfc756a70d454dfa82f48897e2883560c01a0eJames Bottomley sdev_printk(KERN_ERR, sdev, 15179ccfc756a70d454dfa82f48897e2883560c01a0eJames Bottomley "rejecting I/O to offline device\n"); 1518e91442b635be776ea205fba233bdd5bc74b62bc3James Bottomley scsi_kill_request(req, q); 15191da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds continue; 15201da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds } 15211da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 15221da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 15231da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds /* 15241da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Remove the request from the request list. 15251da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds */ 15261da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds if (!(blk_queue_tagged(q) && !blk_queue_start_tag(q, req))) 15279934c8c04561413609d2bc38c6b9f268cba774a4Tejun Heo blk_start_request(req); 15281da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds sdev->device_busy++; 15291da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 15301da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds spin_unlock(q->queue_lock); 1531e91442b635be776ea205fba233bdd5bc74b62bc3James Bottomley cmd = req->special; 1532e91442b635be776ea205fba233bdd5bc74b62bc3James Bottomley if (unlikely(cmd == NULL)) { 1533e91442b635be776ea205fba233bdd5bc74b62bc3James Bottomley printk(KERN_CRIT "impossible request in %s.\n" 1534e91442b635be776ea205fba233bdd5bc74b62bc3James Bottomley "please mail a stack trace to " 15354aff5e2333c9a1609662f2091f55c3f6fffdad36Jens Axboe "linux-scsi@vger.kernel.org\n", 1536cadbd4a5e36dde7e6c49b587b2c419103c0b7218Harvey Harrison __func__); 15374aff5e2333c9a1609662f2091f55c3f6fffdad36Jens Axboe blk_dump_rq_flags(req, "foo"); 1538e91442b635be776ea205fba233bdd5bc74b62bc3James Bottomley BUG(); 1539e91442b635be776ea205fba233bdd5bc74b62bc3James Bottomley } 15401da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds spin_lock(shost->host_lock); 15411da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 1542ecefe8a97577d6c1a68d14ab6fb19bce99448af2Mike Christie /* 1543ecefe8a97577d6c1a68d14ab6fb19bce99448af2Mike Christie * We hit this when the driver is using a host wide 1544ecefe8a97577d6c1a68d14ab6fb19bce99448af2Mike Christie * tag map. For device level tag maps the queue_depth check 1545ecefe8a97577d6c1a68d14ab6fb19bce99448af2Mike Christie * in the device ready fn would prevent us from trying 1546ecefe8a97577d6c1a68d14ab6fb19bce99448af2Mike Christie * to allocate a tag. Since the map is a shared host resource 1547ecefe8a97577d6c1a68d14ab6fb19bce99448af2Mike Christie * we add the dev to the starved list so it eventually gets 1548ecefe8a97577d6c1a68d14ab6fb19bce99448af2Mike Christie * a run when a tag is freed. 1549ecefe8a97577d6c1a68d14ab6fb19bce99448af2Mike Christie */ 15506bd522f6a226f435508433d24e0de4619e016a9dMike Christie if (blk_queue_tagged(q) && !blk_rq_tagged(req)) { 1551ecefe8a97577d6c1a68d14ab6fb19bce99448af2Mike Christie if (list_empty(&sdev->starved_entry)) 1552ecefe8a97577d6c1a68d14ab6fb19bce99448af2Mike Christie list_add_tail(&sdev->starved_entry, 1553ecefe8a97577d6c1a68d14ab6fb19bce99448af2Mike Christie &shost->starved_list); 1554ecefe8a97577d6c1a68d14ab6fb19bce99448af2Mike Christie goto not_ready; 1555ecefe8a97577d6c1a68d14ab6fb19bce99448af2Mike Christie } 1556ecefe8a97577d6c1a68d14ab6fb19bce99448af2Mike Christie 1557f0c0a376d0fcd4c5579ecf5e95f88387cba85211Mike Christie if (!scsi_target_queue_ready(shost, sdev)) 1558f0c0a376d0fcd4c5579ecf5e95f88387cba85211Mike Christie goto not_ready; 1559f0c0a376d0fcd4c5579ecf5e95f88387cba85211Mike Christie 15601da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds if (!scsi_host_queue_ready(q, shost, sdev)) 15611da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds goto not_ready; 1562f0c0a376d0fcd4c5579ecf5e95f88387cba85211Mike Christie 1563f0c0a376d0fcd4c5579ecf5e95f88387cba85211Mike Christie scsi_target(sdev)->target_busy++; 15641da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds shost->host_busy++; 15651da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 15661da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds /* 15671da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * XXX(hch): This is rather suboptimal, scsi_dispatch_cmd will 15681da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * take the lock again. 15691da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds */ 15701da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds spin_unlock_irq(shost->host_lock); 15711da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 15721da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds /* 15731da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Finally, initialize any error handling parameters, and set up 15741da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * the timers for timeouts. 15751da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds */ 15761da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds scsi_init_cmd_errh(cmd); 15771da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 15781da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds /* 15791da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Dispatch the command to the low-level driver. 15801da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds */ 15811da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds rtn = scsi_dispatch_cmd(cmd); 15821da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds spin_lock_irq(q->queue_lock); 1583a488e74976bf0a9bccecdd094378394942dacef1Jens Axboe if (rtn) 1584a488e74976bf0a9bccecdd094378394942dacef1Jens Axboe goto out_delay; 15851da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds } 15861da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 15871da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds goto out; 15881da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 15891da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds not_ready: 15901da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds spin_unlock_irq(shost->host_lock); 15911da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 15921da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds /* 15931da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * lock q, handle tag, requeue req, and decrement device_busy. We 15941da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * must return with queue_lock held. 15951da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * 15961da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Decrementing device_busy without checking it is OK, as all such 15971da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * cases (host limits or settings) should run the queue at some 15981da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * later time. 15991da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds */ 16001da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds spin_lock_irq(q->queue_lock); 16011da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds blk_requeue_request(q, req); 16021da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds sdev->device_busy--; 1603a488e74976bf0a9bccecdd094378394942dacef1Jens Axboeout_delay: 1604a488e74976bf0a9bccecdd094378394942dacef1Jens Axboe if (sdev->device_busy == 0) 1605a488e74976bf0a9bccecdd094378394942dacef1Jens Axboe blk_delay_queue(q, SCSI_QUEUE_DELAY); 1606a488e74976bf0a9bccecdd094378394942dacef1Jens Axboeout: 16071da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds /* must be careful here...if we trigger the ->remove() function 16081da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * we cannot be holding the q lock */ 16091da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds spin_unlock_irq(q->queue_lock); 16101da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds put_device(&sdev->sdev_gendev); 16111da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds spin_lock_irq(q->queue_lock); 16121da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds} 16131da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 16141da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldsu64 scsi_calculate_bounce_limit(struct Scsi_Host *shost) 16151da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds{ 16161da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds struct device *host_dev; 16171da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds u64 bounce_limit = 0xffffffff; 16181da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 16191da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds if (shost->unchecked_isa_dma) 16201da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds return BLK_BOUNCE_ISA; 16211da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds /* 16221da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Platforms with virtual-DMA translation 16231da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * hardware have no practical limit. 16241da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds */ 16251da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds if (!PCI_DMA_BUS_IS_PHYS) 16261da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds return BLK_BOUNCE_ANY; 16271da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 16281da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds host_dev = scsi_get_device(shost); 16291da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds if (host_dev && host_dev->dma_mask) 16301da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds bounce_limit = *host_dev->dma_mask; 16311da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 16321da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds return bounce_limit; 16331da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds} 16341da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus TorvaldsEXPORT_SYMBOL(scsi_calculate_bounce_limit); 16351da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 1636b58d91547fb17c65ad621f3f98b1f2c228c812a5FUJITA Tomonoristruct request_queue *__scsi_alloc_queue(struct Scsi_Host *shost, 1637b58d91547fb17c65ad621f3f98b1f2c228c812a5FUJITA Tomonori request_fn_proc *request_fn) 16381da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds{ 16391da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds struct request_queue *q; 1640860ac568e825b623b0b335ca277dd47d1d7fd5d0FUJITA Tomonori struct device *dev = shost->shost_gendev.parent; 16411da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 1642b58d91547fb17c65ad621f3f98b1f2c228c812a5FUJITA Tomonori q = blk_init_queue(request_fn, NULL); 16431da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds if (!q) 16441da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds return NULL; 16451da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 1646a8474ce23a73185dd2bae4c884b1716474032d31Jens Axboe /* 1647a8474ce23a73185dd2bae4c884b1716474032d31Jens Axboe * this limit is imposed by hardware restrictions 1648a8474ce23a73185dd2bae4c884b1716474032d31Jens Axboe */ 16498a78362c4eefc1deddbefe2c7f38aabbc2429d6bMartin K. Petersen blk_queue_max_segments(q, min_t(unsigned short, shost->sg_tablesize, 16508a78362c4eefc1deddbefe2c7f38aabbc2429d6bMartin K. Petersen SCSI_MAX_SG_CHAIN_SEGMENTS)); 1651a8474ce23a73185dd2bae4c884b1716474032d31Jens Axboe 165213f05c8d8e98bbdce89158bfdb2e380940695a88Martin K. Petersen if (scsi_host_prot_dma(shost)) { 165313f05c8d8e98bbdce89158bfdb2e380940695a88Martin K. Petersen shost->sg_prot_tablesize = 165413f05c8d8e98bbdce89158bfdb2e380940695a88Martin K. Petersen min_not_zero(shost->sg_prot_tablesize, 165513f05c8d8e98bbdce89158bfdb2e380940695a88Martin K. Petersen (unsigned short)SCSI_MAX_PROT_SG_SEGMENTS); 165613f05c8d8e98bbdce89158bfdb2e380940695a88Martin K. Petersen BUG_ON(shost->sg_prot_tablesize < shost->sg_tablesize); 165713f05c8d8e98bbdce89158bfdb2e380940695a88Martin K. Petersen blk_queue_max_integrity_segments(q, shost->sg_prot_tablesize); 165813f05c8d8e98bbdce89158bfdb2e380940695a88Martin K. Petersen } 165913f05c8d8e98bbdce89158bfdb2e380940695a88Martin K. Petersen 1660086fa5ff0854c676ec333760f4c0154b3b242616Martin K. Petersen blk_queue_max_hw_sectors(q, shost->max_sectors); 16611da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds blk_queue_bounce_limit(q, scsi_calculate_bounce_limit(shost)); 16621da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds blk_queue_segment_boundary(q, shost->dma_boundary); 166399c84dbdc73d158a1ab955a4a5f74c18074796a3FUJITA Tomonori dma_set_seg_boundary(dev, shost->dma_boundary); 16641da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 1665860ac568e825b623b0b335ca277dd47d1d7fd5d0FUJITA Tomonori blk_queue_max_segment_size(q, dma_get_max_seg_size(dev)); 1666860ac568e825b623b0b335ca277dd47d1d7fd5d0FUJITA Tomonori 16671da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds if (!shost->use_clustering) 1668e692cb668fdd5a712c6ed2a2d6f2a36ee83997b4Martin K. Petersen q->limits.cluster = 0; 1669465ff3185e0cb76d46137335a4d21d0d9d3ac8a2James Bottomley 1670465ff3185e0cb76d46137335a4d21d0d9d3ac8a2James Bottomley /* 1671465ff3185e0cb76d46137335a4d21d0d9d3ac8a2James Bottomley * set a reasonable default alignment on word boundaries: the 1672465ff3185e0cb76d46137335a4d21d0d9d3ac8a2James Bottomley * host and device may alter it using 1673465ff3185e0cb76d46137335a4d21d0d9d3ac8a2James Bottomley * blk_queue_update_dma_alignment() later. 1674465ff3185e0cb76d46137335a4d21d0d9d3ac8a2James Bottomley */ 1675465ff3185e0cb76d46137335a4d21d0d9d3ac8a2James Bottomley blk_queue_dma_alignment(q, 0x03); 1676465ff3185e0cb76d46137335a4d21d0d9d3ac8a2James Bottomley 16771da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds return q; 16781da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds} 1679b58d91547fb17c65ad621f3f98b1f2c228c812a5FUJITA TomonoriEXPORT_SYMBOL(__scsi_alloc_queue); 1680b58d91547fb17c65ad621f3f98b1f2c228c812a5FUJITA Tomonori 1681b58d91547fb17c65ad621f3f98b1f2c228c812a5FUJITA Tomonoristruct request_queue *scsi_alloc_queue(struct scsi_device *sdev) 1682b58d91547fb17c65ad621f3f98b1f2c228c812a5FUJITA Tomonori{ 1683b58d91547fb17c65ad621f3f98b1f2c228c812a5FUJITA Tomonori struct request_queue *q; 1684b58d91547fb17c65ad621f3f98b1f2c228c812a5FUJITA Tomonori 1685b58d91547fb17c65ad621f3f98b1f2c228c812a5FUJITA Tomonori q = __scsi_alloc_queue(sdev->host, scsi_request_fn); 1686b58d91547fb17c65ad621f3f98b1f2c228c812a5FUJITA Tomonori if (!q) 1687b58d91547fb17c65ad621f3f98b1f2c228c812a5FUJITA Tomonori return NULL; 1688b58d91547fb17c65ad621f3f98b1f2c228c812a5FUJITA Tomonori 1689b58d91547fb17c65ad621f3f98b1f2c228c812a5FUJITA Tomonori blk_queue_prep_rq(q, scsi_prep_fn); 1690b58d91547fb17c65ad621f3f98b1f2c228c812a5FUJITA Tomonori blk_queue_softirq_done(q, scsi_softirq_done); 1691242f9dcb8ba6f68fcd217a119a7648a4f69290e9Jens Axboe blk_queue_rq_timed_out(q, scsi_times_out); 16926c5121b78ba5c70a9990e2af6cb4d6bbffe0d4d8Kiyoshi Ueda blk_queue_lld_busy(q, scsi_lld_busy); 1693b58d91547fb17c65ad621f3f98b1f2c228c812a5FUJITA Tomonori return q; 1694b58d91547fb17c65ad621f3f98b1f2c228c812a5FUJITA Tomonori} 16951da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 16961da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldsvoid scsi_free_queue(struct request_queue *q) 16971da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds{ 16983308511c93e6ad0d3c58984ecd6e5e57f96b12c8Bart Van Assche unsigned long flags; 16993308511c93e6ad0d3c58984ecd6e5e57f96b12c8Bart Van Assche 17003308511c93e6ad0d3c58984ecd6e5e57f96b12c8Bart Van Assche WARN_ON(q->queuedata); 17013308511c93e6ad0d3c58984ecd6e5e57f96b12c8Bart Van Assche 17023308511c93e6ad0d3c58984ecd6e5e57f96b12c8Bart Van Assche /* cause scsi_request_fn() to kill all non-finished requests */ 17033308511c93e6ad0d3c58984ecd6e5e57f96b12c8Bart Van Assche spin_lock_irqsave(q->queue_lock, flags); 17043308511c93e6ad0d3c58984ecd6e5e57f96b12c8Bart Van Assche q->request_fn(q); 17053308511c93e6ad0d3c58984ecd6e5e57f96b12c8Bart Van Assche spin_unlock_irqrestore(q->queue_lock, flags); 17063308511c93e6ad0d3c58984ecd6e5e57f96b12c8Bart Van Assche 17071da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds blk_cleanup_queue(q); 17081da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds} 17091da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 17101da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds/* 17111da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Function: scsi_block_requests() 17121da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * 17131da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Purpose: Utility function used by low-level drivers to prevent further 17141da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * commands from being queued to the device. 17151da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * 17161da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Arguments: shost - Host in question 17171da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * 17181da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Returns: Nothing 17191da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * 17201da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Lock status: No locks are assumed held. 17211da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * 17221da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Notes: There is no timer nor any other means by which the requests 17231da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * get unblocked other than the low-level driver calling 17241da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * scsi_unblock_requests(). 17251da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds */ 17261da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldsvoid scsi_block_requests(struct Scsi_Host *shost) 17271da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds{ 17281da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds shost->host_self_blocked = 1; 17291da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds} 17301da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus TorvaldsEXPORT_SYMBOL(scsi_block_requests); 17311da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 17321da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds/* 17331da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Function: scsi_unblock_requests() 17341da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * 17351da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Purpose: Utility function used by low-level drivers to allow further 17361da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * commands from being queued to the device. 17371da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * 17381da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Arguments: shost - Host in question 17391da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * 17401da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Returns: Nothing 17411da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * 17421da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Lock status: No locks are assumed held. 17431da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * 17441da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Notes: There is no timer nor any other means by which the requests 17451da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * get unblocked other than the low-level driver calling 17461da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * scsi_unblock_requests(). 17471da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * 17481da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * This is done as an API function so that changes to the 17491da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * internals of the scsi mid-layer won't require wholesale 17501da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * changes to drivers that use this feature. 17511da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds */ 17521da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldsvoid scsi_unblock_requests(struct Scsi_Host *shost) 17531da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds{ 17541da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds shost->host_self_blocked = 0; 17551da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds scsi_run_host_queues(shost); 17561da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds} 17571da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus TorvaldsEXPORT_SYMBOL(scsi_unblock_requests); 17581da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 17591da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldsint __init scsi_init_queue(void) 17601da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds{ 17611da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds int i; 17621da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 17636362abd3e00d3161affad996fa53cc69a01fc6d1Martin K. Petersen scsi_sdb_cache = kmem_cache_create("scsi_data_buffer", 17646362abd3e00d3161affad996fa53cc69a01fc6d1Martin K. Petersen sizeof(struct scsi_data_buffer), 17656362abd3e00d3161affad996fa53cc69a01fc6d1Martin K. Petersen 0, 0, NULL); 17666362abd3e00d3161affad996fa53cc69a01fc6d1Martin K. Petersen if (!scsi_sdb_cache) { 17676362abd3e00d3161affad996fa53cc69a01fc6d1Martin K. Petersen printk(KERN_ERR "SCSI: can't init scsi sdb cache\n"); 1768f078727b250c2653fc9a564f15547c17ebac3f99FUJITA Tomonori return -ENOMEM; 17696f9a35e2dafa0f855ab051c11bdbf739745ff6f5Boaz Harrosh } 17706f9a35e2dafa0f855ab051c11bdbf739745ff6f5Boaz Harrosh 17711da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds for (i = 0; i < SG_MEMPOOL_NR; i++) { 17721da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds struct scsi_host_sg_pool *sgp = scsi_sg_pools + i; 17731da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds int size = sgp->size * sizeof(struct scatterlist); 17741da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 17751da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds sgp->slab = kmem_cache_create(sgp->name, size, 0, 177620c2df83d25c6a95affe6157a4c9cac4cf5ffaacPaul Mundt SLAB_HWCACHE_ALIGN, NULL); 17771da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds if (!sgp->slab) { 17781da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds printk(KERN_ERR "SCSI: can't init sg slab %s\n", 17791da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds sgp->name); 17806362abd3e00d3161affad996fa53cc69a01fc6d1Martin K. Petersen goto cleanup_sdb; 17811da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds } 17821da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 178393d2341c750cda0df48a6cc67b35fe25f1ec47dfMatthew Dobson sgp->pool = mempool_create_slab_pool(SG_MEMPOOL_SIZE, 178493d2341c750cda0df48a6cc67b35fe25f1ec47dfMatthew Dobson sgp->slab); 17851da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds if (!sgp->pool) { 17861da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds printk(KERN_ERR "SCSI: can't init sg mempool %s\n", 17871da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds sgp->name); 17886362abd3e00d3161affad996fa53cc69a01fc6d1Martin K. Petersen goto cleanup_sdb; 17891da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds } 17901da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds } 17911da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 17921da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds return 0; 17933d9dd6eef888658d26ebea0cc24d15d2a93ab015FUJITA Tomonori 17946362abd3e00d3161affad996fa53cc69a01fc6d1Martin K. Petersencleanup_sdb: 17953d9dd6eef888658d26ebea0cc24d15d2a93ab015FUJITA Tomonori for (i = 0; i < SG_MEMPOOL_NR; i++) { 17963d9dd6eef888658d26ebea0cc24d15d2a93ab015FUJITA Tomonori struct scsi_host_sg_pool *sgp = scsi_sg_pools + i; 17973d9dd6eef888658d26ebea0cc24d15d2a93ab015FUJITA Tomonori if (sgp->pool) 17983d9dd6eef888658d26ebea0cc24d15d2a93ab015FUJITA Tomonori mempool_destroy(sgp->pool); 17993d9dd6eef888658d26ebea0cc24d15d2a93ab015FUJITA Tomonori if (sgp->slab) 18003d9dd6eef888658d26ebea0cc24d15d2a93ab015FUJITA Tomonori kmem_cache_destroy(sgp->slab); 18013d9dd6eef888658d26ebea0cc24d15d2a93ab015FUJITA Tomonori } 18026362abd3e00d3161affad996fa53cc69a01fc6d1Martin K. Petersen kmem_cache_destroy(scsi_sdb_cache); 18033d9dd6eef888658d26ebea0cc24d15d2a93ab015FUJITA Tomonori 18043d9dd6eef888658d26ebea0cc24d15d2a93ab015FUJITA Tomonori return -ENOMEM; 18051da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds} 18061da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 18071da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldsvoid scsi_exit_queue(void) 18081da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds{ 18091da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds int i; 18101da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 18116362abd3e00d3161affad996fa53cc69a01fc6d1Martin K. Petersen kmem_cache_destroy(scsi_sdb_cache); 1812aa7b5cd750c766f66a92c9f78ba176bc77512b7eMike Christie 18131da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds for (i = 0; i < SG_MEMPOOL_NR; i++) { 18141da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds struct scsi_host_sg_pool *sgp = scsi_sg_pools + i; 18151da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds mempool_destroy(sgp->pool); 18161da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds kmem_cache_destroy(sgp->slab); 18171da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds } 18181da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds} 18195baba830e93732e802dc7e0a362eb730e1917f58James Bottomley 18205baba830e93732e802dc7e0a362eb730e1917f58James Bottomley/** 18215baba830e93732e802dc7e0a362eb730e1917f58James Bottomley * scsi_mode_select - issue a mode select 18225baba830e93732e802dc7e0a362eb730e1917f58James Bottomley * @sdev: SCSI device to be queried 18235baba830e93732e802dc7e0a362eb730e1917f58James Bottomley * @pf: Page format bit (1 == standard, 0 == vendor specific) 18245baba830e93732e802dc7e0a362eb730e1917f58James Bottomley * @sp: Save page bit (0 == don't save, 1 == save) 18255baba830e93732e802dc7e0a362eb730e1917f58James Bottomley * @modepage: mode page being requested 18265baba830e93732e802dc7e0a362eb730e1917f58James Bottomley * @buffer: request buffer (may not be smaller than eight bytes) 18275baba830e93732e802dc7e0a362eb730e1917f58James Bottomley * @len: length of request buffer. 18285baba830e93732e802dc7e0a362eb730e1917f58James Bottomley * @timeout: command timeout 18295baba830e93732e802dc7e0a362eb730e1917f58James Bottomley * @retries: number of retries before failing 18305baba830e93732e802dc7e0a362eb730e1917f58James Bottomley * @data: returns a structure abstracting the mode header data 1831eb44820c28bc9a042e1157b41c677018a8fdfc74Rob Landley * @sshdr: place to put sense data (or NULL if no sense to be collected). 18325baba830e93732e802dc7e0a362eb730e1917f58James Bottomley * must be SCSI_SENSE_BUFFERSIZE big. 18335baba830e93732e802dc7e0a362eb730e1917f58James Bottomley * 18345baba830e93732e802dc7e0a362eb730e1917f58James Bottomley * Returns zero if successful; negative error number or scsi 18355baba830e93732e802dc7e0a362eb730e1917f58James Bottomley * status on error 18365baba830e93732e802dc7e0a362eb730e1917f58James Bottomley * 18375baba830e93732e802dc7e0a362eb730e1917f58James Bottomley */ 18385baba830e93732e802dc7e0a362eb730e1917f58James Bottomleyint 18395baba830e93732e802dc7e0a362eb730e1917f58James Bottomleyscsi_mode_select(struct scsi_device *sdev, int pf, int sp, int modepage, 18405baba830e93732e802dc7e0a362eb730e1917f58James Bottomley unsigned char *buffer, int len, int timeout, int retries, 18415baba830e93732e802dc7e0a362eb730e1917f58James Bottomley struct scsi_mode_data *data, struct scsi_sense_hdr *sshdr) 18425baba830e93732e802dc7e0a362eb730e1917f58James Bottomley{ 18435baba830e93732e802dc7e0a362eb730e1917f58James Bottomley unsigned char cmd[10]; 18445baba830e93732e802dc7e0a362eb730e1917f58James Bottomley unsigned char *real_buffer; 18455baba830e93732e802dc7e0a362eb730e1917f58James Bottomley int ret; 18465baba830e93732e802dc7e0a362eb730e1917f58James Bottomley 18475baba830e93732e802dc7e0a362eb730e1917f58James Bottomley memset(cmd, 0, sizeof(cmd)); 18485baba830e93732e802dc7e0a362eb730e1917f58James Bottomley cmd[1] = (pf ? 0x10 : 0) | (sp ? 0x01 : 0); 18495baba830e93732e802dc7e0a362eb730e1917f58James Bottomley 18505baba830e93732e802dc7e0a362eb730e1917f58James Bottomley if (sdev->use_10_for_ms) { 18515baba830e93732e802dc7e0a362eb730e1917f58James Bottomley if (len > 65535) 18525baba830e93732e802dc7e0a362eb730e1917f58James Bottomley return -EINVAL; 18535baba830e93732e802dc7e0a362eb730e1917f58James Bottomley real_buffer = kmalloc(8 + len, GFP_KERNEL); 18545baba830e93732e802dc7e0a362eb730e1917f58James Bottomley if (!real_buffer) 18555baba830e93732e802dc7e0a362eb730e1917f58James Bottomley return -ENOMEM; 18565baba830e93732e802dc7e0a362eb730e1917f58James Bottomley memcpy(real_buffer + 8, buffer, len); 18575baba830e93732e802dc7e0a362eb730e1917f58James Bottomley len += 8; 18585baba830e93732e802dc7e0a362eb730e1917f58James Bottomley real_buffer[0] = 0; 18595baba830e93732e802dc7e0a362eb730e1917f58James Bottomley real_buffer[1] = 0; 18605baba830e93732e802dc7e0a362eb730e1917f58James Bottomley real_buffer[2] = data->medium_type; 18615baba830e93732e802dc7e0a362eb730e1917f58James Bottomley real_buffer[3] = data->device_specific; 18625baba830e93732e802dc7e0a362eb730e1917f58James Bottomley real_buffer[4] = data->longlba ? 0x01 : 0; 18635baba830e93732e802dc7e0a362eb730e1917f58James Bottomley real_buffer[5] = 0; 18645baba830e93732e802dc7e0a362eb730e1917f58James Bottomley real_buffer[6] = data->block_descriptor_length >> 8; 18655baba830e93732e802dc7e0a362eb730e1917f58James Bottomley real_buffer[7] = data->block_descriptor_length; 18665baba830e93732e802dc7e0a362eb730e1917f58James Bottomley 18675baba830e93732e802dc7e0a362eb730e1917f58James Bottomley cmd[0] = MODE_SELECT_10; 18685baba830e93732e802dc7e0a362eb730e1917f58James Bottomley cmd[7] = len >> 8; 18695baba830e93732e802dc7e0a362eb730e1917f58James Bottomley cmd[8] = len; 18705baba830e93732e802dc7e0a362eb730e1917f58James Bottomley } else { 18715baba830e93732e802dc7e0a362eb730e1917f58James Bottomley if (len > 255 || data->block_descriptor_length > 255 || 18725baba830e93732e802dc7e0a362eb730e1917f58James Bottomley data->longlba) 18735baba830e93732e802dc7e0a362eb730e1917f58James Bottomley return -EINVAL; 18745baba830e93732e802dc7e0a362eb730e1917f58James Bottomley 18755baba830e93732e802dc7e0a362eb730e1917f58James Bottomley real_buffer = kmalloc(4 + len, GFP_KERNEL); 18765baba830e93732e802dc7e0a362eb730e1917f58James Bottomley if (!real_buffer) 18775baba830e93732e802dc7e0a362eb730e1917f58James Bottomley return -ENOMEM; 18785baba830e93732e802dc7e0a362eb730e1917f58James Bottomley memcpy(real_buffer + 4, buffer, len); 18795baba830e93732e802dc7e0a362eb730e1917f58James Bottomley len += 4; 18805baba830e93732e802dc7e0a362eb730e1917f58James Bottomley real_buffer[0] = 0; 18815baba830e93732e802dc7e0a362eb730e1917f58James Bottomley real_buffer[1] = data->medium_type; 18825baba830e93732e802dc7e0a362eb730e1917f58James Bottomley real_buffer[2] = data->device_specific; 18835baba830e93732e802dc7e0a362eb730e1917f58James Bottomley real_buffer[3] = data->block_descriptor_length; 18845baba830e93732e802dc7e0a362eb730e1917f58James Bottomley 18855baba830e93732e802dc7e0a362eb730e1917f58James Bottomley 18865baba830e93732e802dc7e0a362eb730e1917f58James Bottomley cmd[0] = MODE_SELECT; 18875baba830e93732e802dc7e0a362eb730e1917f58James Bottomley cmd[4] = len; 18885baba830e93732e802dc7e0a362eb730e1917f58James Bottomley } 18895baba830e93732e802dc7e0a362eb730e1917f58James Bottomley 18905baba830e93732e802dc7e0a362eb730e1917f58James Bottomley ret = scsi_execute_req(sdev, cmd, DMA_TO_DEVICE, real_buffer, len, 1891f4f4e47e4af6b02dd1c425b931c65d0165356e33FUJITA Tomonori sshdr, timeout, retries, NULL); 18925baba830e93732e802dc7e0a362eb730e1917f58James Bottomley kfree(real_buffer); 18935baba830e93732e802dc7e0a362eb730e1917f58James Bottomley return ret; 18945baba830e93732e802dc7e0a362eb730e1917f58James Bottomley} 18955baba830e93732e802dc7e0a362eb730e1917f58James BottomleyEXPORT_SYMBOL_GPL(scsi_mode_select); 18965baba830e93732e802dc7e0a362eb730e1917f58James Bottomley 18971da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds/** 1898eb44820c28bc9a042e1157b41c677018a8fdfc74Rob Landley * scsi_mode_sense - issue a mode sense, falling back from 10 to six bytes if necessary. 18991cf72699c1530c3e4ac3d58344f6a6a40a2f46d3James Bottomley * @sdev: SCSI device to be queried 19001da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * @dbd: set if mode sense will allow block descriptors to be returned 19011da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * @modepage: mode page being requested 19021da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * @buffer: request buffer (may not be smaller than eight bytes) 19031da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * @len: length of request buffer. 19041da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * @timeout: command timeout 19051da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * @retries: number of retries before failing 19061da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * @data: returns a structure abstracting the mode header data 1907eb44820c28bc9a042e1157b41c677018a8fdfc74Rob Landley * @sshdr: place to put sense data (or NULL if no sense to be collected). 19081cf72699c1530c3e4ac3d58344f6a6a40a2f46d3James Bottomley * must be SCSI_SENSE_BUFFERSIZE big. 19091da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * 19101da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Returns zero if unsuccessful, or the header offset (either 4 19111da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * or 8 depending on whether a six or ten byte command was 19121da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * issued) if successful. 1913eb44820c28bc9a042e1157b41c677018a8fdfc74Rob Landley */ 19141da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldsint 19151cf72699c1530c3e4ac3d58344f6a6a40a2f46d3James Bottomleyscsi_mode_sense(struct scsi_device *sdev, int dbd, int modepage, 19161da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds unsigned char *buffer, int len, int timeout, int retries, 19175baba830e93732e802dc7e0a362eb730e1917f58James Bottomley struct scsi_mode_data *data, struct scsi_sense_hdr *sshdr) 19185baba830e93732e802dc7e0a362eb730e1917f58James Bottomley{ 19191da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds unsigned char cmd[12]; 19201da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds int use_10_for_ms; 19211da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds int header_length; 19221cf72699c1530c3e4ac3d58344f6a6a40a2f46d3James Bottomley int result; 1923ea73a9f23906c374b697cd5b0d64f6dceced63deJames Bottomley struct scsi_sense_hdr my_sshdr; 19241da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 19251da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds memset(data, 0, sizeof(*data)); 19261da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds memset(&cmd[0], 0, 12); 19271da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds cmd[1] = dbd & 0x18; /* allows DBD and LLBA bits */ 19281da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds cmd[2] = modepage; 19291da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 1930ea73a9f23906c374b697cd5b0d64f6dceced63deJames Bottomley /* caller might not be interested in sense, but we need it */ 1931ea73a9f23906c374b697cd5b0d64f6dceced63deJames Bottomley if (!sshdr) 1932ea73a9f23906c374b697cd5b0d64f6dceced63deJames Bottomley sshdr = &my_sshdr; 1933ea73a9f23906c374b697cd5b0d64f6dceced63deJames Bottomley 19341da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds retry: 19351cf72699c1530c3e4ac3d58344f6a6a40a2f46d3James Bottomley use_10_for_ms = sdev->use_10_for_ms; 19361da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 19371da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds if (use_10_for_ms) { 19381da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds if (len < 8) 19391da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds len = 8; 19401da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 19411da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds cmd[0] = MODE_SENSE_10; 19421da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds cmd[8] = len; 19431da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds header_length = 8; 19441da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds } else { 19451da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds if (len < 4) 19461da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds len = 4; 19471da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 19481da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds cmd[0] = MODE_SENSE; 19491da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds cmd[4] = len; 19501da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds header_length = 4; 19511da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds } 19521da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 19531da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds memset(buffer, 0, len); 19541da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 19551cf72699c1530c3e4ac3d58344f6a6a40a2f46d3James Bottomley result = scsi_execute_req(sdev, cmd, DMA_FROM_DEVICE, buffer, len, 1956f4f4e47e4af6b02dd1c425b931c65d0165356e33FUJITA Tomonori sshdr, timeout, retries, NULL); 19571da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 19581da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds /* This code looks awful: what it's doing is making sure an 19591da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * ILLEGAL REQUEST sense return identifies the actual command 19601da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * byte as the problem. MODE_SENSE commands can return 19611da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * ILLEGAL REQUEST if the code page isn't supported */ 19621da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 19631cf72699c1530c3e4ac3d58344f6a6a40a2f46d3James Bottomley if (use_10_for_ms && !scsi_status_is_good(result) && 19641cf72699c1530c3e4ac3d58344f6a6a40a2f46d3James Bottomley (driver_byte(result) & DRIVER_SENSE)) { 1965ea73a9f23906c374b697cd5b0d64f6dceced63deJames Bottomley if (scsi_sense_valid(sshdr)) { 1966ea73a9f23906c374b697cd5b0d64f6dceced63deJames Bottomley if ((sshdr->sense_key == ILLEGAL_REQUEST) && 1967ea73a9f23906c374b697cd5b0d64f6dceced63deJames Bottomley (sshdr->asc == 0x20) && (sshdr->ascq == 0)) { 19681da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds /* 19691da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Invalid command operation code 19701da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds */ 19711cf72699c1530c3e4ac3d58344f6a6a40a2f46d3James Bottomley sdev->use_10_for_ms = 0; 19721da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds goto retry; 19731da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds } 19741da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds } 19751da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds } 19761da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 19771cf72699c1530c3e4ac3d58344f6a6a40a2f46d3James Bottomley if(scsi_status_is_good(result)) { 19786d73c8514da241c6b1b8d710a6294786604d7142Al Viro if (unlikely(buffer[0] == 0x86 && buffer[1] == 0x0b && 19796d73c8514da241c6b1b8d710a6294786604d7142Al Viro (modepage == 6 || modepage == 8))) { 19806d73c8514da241c6b1b8d710a6294786604d7142Al Viro /* Initio breakage? */ 19816d73c8514da241c6b1b8d710a6294786604d7142Al Viro header_length = 0; 19826d73c8514da241c6b1b8d710a6294786604d7142Al Viro data->length = 13; 19836d73c8514da241c6b1b8d710a6294786604d7142Al Viro data->medium_type = 0; 19846d73c8514da241c6b1b8d710a6294786604d7142Al Viro data->device_specific = 0; 19856d73c8514da241c6b1b8d710a6294786604d7142Al Viro data->longlba = 0; 19866d73c8514da241c6b1b8d710a6294786604d7142Al Viro data->block_descriptor_length = 0; 19876d73c8514da241c6b1b8d710a6294786604d7142Al Viro } else if(use_10_for_ms) { 19881da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds data->length = buffer[0]*256 + buffer[1] + 2; 19891da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds data->medium_type = buffer[2]; 19901da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds data->device_specific = buffer[3]; 19911da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds data->longlba = buffer[4] & 0x01; 19921da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds data->block_descriptor_length = buffer[6]*256 19931da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds + buffer[7]; 19941da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds } else { 19951da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds data->length = buffer[0] + 1; 19961da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds data->medium_type = buffer[1]; 19971da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds data->device_specific = buffer[2]; 19981da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds data->block_descriptor_length = buffer[3]; 19991da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds } 20006d73c8514da241c6b1b8d710a6294786604d7142Al Viro data->header_length = header_length; 20011da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds } 20021da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 20031cf72699c1530c3e4ac3d58344f6a6a40a2f46d3James Bottomley return result; 20041da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds} 20051da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus TorvaldsEXPORT_SYMBOL(scsi_mode_sense); 20061da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 2007001aac257cf8adbe90cdcba6e07f8d12dfc8fa6bJames Bottomley/** 2008001aac257cf8adbe90cdcba6e07f8d12dfc8fa6bJames Bottomley * scsi_test_unit_ready - test if unit is ready 2009001aac257cf8adbe90cdcba6e07f8d12dfc8fa6bJames Bottomley * @sdev: scsi device to change the state of. 2010001aac257cf8adbe90cdcba6e07f8d12dfc8fa6bJames Bottomley * @timeout: command timeout 2011001aac257cf8adbe90cdcba6e07f8d12dfc8fa6bJames Bottomley * @retries: number of retries before failing 2012001aac257cf8adbe90cdcba6e07f8d12dfc8fa6bJames Bottomley * @sshdr_external: Optional pointer to struct scsi_sense_hdr for 2013001aac257cf8adbe90cdcba6e07f8d12dfc8fa6bJames Bottomley * returning sense. Make sure that this is cleared before passing 2014001aac257cf8adbe90cdcba6e07f8d12dfc8fa6bJames Bottomley * in. 2015001aac257cf8adbe90cdcba6e07f8d12dfc8fa6bJames Bottomley * 2016001aac257cf8adbe90cdcba6e07f8d12dfc8fa6bJames Bottomley * Returns zero if unsuccessful or an error if TUR failed. For 20179f8a2c23c6c1140f515f601265c4dff7522110b7Tejun Heo * removable media, UNIT_ATTENTION sets ->changed flag. 2018001aac257cf8adbe90cdcba6e07f8d12dfc8fa6bJames Bottomley **/ 20191da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldsint 2020001aac257cf8adbe90cdcba6e07f8d12dfc8fa6bJames Bottomleyscsi_test_unit_ready(struct scsi_device *sdev, int timeout, int retries, 2021001aac257cf8adbe90cdcba6e07f8d12dfc8fa6bJames Bottomley struct scsi_sense_hdr *sshdr_external) 20221da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds{ 20231da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds char cmd[] = { 20241da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds TEST_UNIT_READY, 0, 0, 0, 0, 0, 20251da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds }; 2026001aac257cf8adbe90cdcba6e07f8d12dfc8fa6bJames Bottomley struct scsi_sense_hdr *sshdr; 20271da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds int result; 2028001aac257cf8adbe90cdcba6e07f8d12dfc8fa6bJames Bottomley 2029001aac257cf8adbe90cdcba6e07f8d12dfc8fa6bJames Bottomley if (!sshdr_external) 2030001aac257cf8adbe90cdcba6e07f8d12dfc8fa6bJames Bottomley sshdr = kzalloc(sizeof(*sshdr), GFP_KERNEL); 2031001aac257cf8adbe90cdcba6e07f8d12dfc8fa6bJames Bottomley else 2032001aac257cf8adbe90cdcba6e07f8d12dfc8fa6bJames Bottomley sshdr = sshdr_external; 2033001aac257cf8adbe90cdcba6e07f8d12dfc8fa6bJames Bottomley 2034001aac257cf8adbe90cdcba6e07f8d12dfc8fa6bJames Bottomley /* try to eat the UNIT_ATTENTION if there are enough retries */ 2035001aac257cf8adbe90cdcba6e07f8d12dfc8fa6bJames Bottomley do { 2036001aac257cf8adbe90cdcba6e07f8d12dfc8fa6bJames Bottomley result = scsi_execute_req(sdev, cmd, DMA_NONE, NULL, 0, sshdr, 2037f4f4e47e4af6b02dd1c425b931c65d0165356e33FUJITA Tomonori timeout, retries, NULL); 203832c356d76d7e13dcd0675189d8e9c64ef66aa561James Bottomley if (sdev->removable && scsi_sense_valid(sshdr) && 203932c356d76d7e13dcd0675189d8e9c64ef66aa561James Bottomley sshdr->sense_key == UNIT_ATTENTION) 204032c356d76d7e13dcd0675189d8e9c64ef66aa561James Bottomley sdev->changed = 1; 204132c356d76d7e13dcd0675189d8e9c64ef66aa561James Bottomley } while (scsi_sense_valid(sshdr) && 204232c356d76d7e13dcd0675189d8e9c64ef66aa561James Bottomley sshdr->sense_key == UNIT_ATTENTION && --retries); 2043001aac257cf8adbe90cdcba6e07f8d12dfc8fa6bJames Bottomley 2044001aac257cf8adbe90cdcba6e07f8d12dfc8fa6bJames Bottomley if (!sshdr_external) 2045001aac257cf8adbe90cdcba6e07f8d12dfc8fa6bJames Bottomley kfree(sshdr); 20461da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds return result; 20471da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds} 20481da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus TorvaldsEXPORT_SYMBOL(scsi_test_unit_ready); 20491da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 20501da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds/** 2051eb44820c28bc9a042e1157b41c677018a8fdfc74Rob Landley * scsi_device_set_state - Take the given device through the device state model. 20521da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * @sdev: scsi device to change the state of. 20531da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * @state: state to change to. 20541da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * 20551da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Returns zero if unsuccessful or an error if the requested 20561da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * transition is illegal. 2057eb44820c28bc9a042e1157b41c677018a8fdfc74Rob Landley */ 20581da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldsint 20591da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldsscsi_device_set_state(struct scsi_device *sdev, enum scsi_device_state state) 20601da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds{ 20611da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds enum scsi_device_state oldstate = sdev->sdev_state; 20621da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 20631da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds if (state == oldstate) 20641da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds return 0; 20651da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 20661da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds switch (state) { 20671da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds case SDEV_CREATED: 20686f4267e3bd1211b3d09130e626b0b3d885077610James Bottomley switch (oldstate) { 20696f4267e3bd1211b3d09130e626b0b3d885077610James Bottomley case SDEV_CREATED_BLOCK: 20706f4267e3bd1211b3d09130e626b0b3d885077610James Bottomley break; 20716f4267e3bd1211b3d09130e626b0b3d885077610James Bottomley default: 20726f4267e3bd1211b3d09130e626b0b3d885077610James Bottomley goto illegal; 20736f4267e3bd1211b3d09130e626b0b3d885077610James Bottomley } 20746f4267e3bd1211b3d09130e626b0b3d885077610James Bottomley break; 20751da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 20761da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds case SDEV_RUNNING: 20771da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds switch (oldstate) { 20781da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds case SDEV_CREATED: 20791da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds case SDEV_OFFLINE: 20801da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds case SDEV_QUIESCE: 20811da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds case SDEV_BLOCK: 20821da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds break; 20831da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds default: 20841da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds goto illegal; 20851da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds } 20861da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds break; 20871da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 20881da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds case SDEV_QUIESCE: 20891da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds switch (oldstate) { 20901da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds case SDEV_RUNNING: 20911da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds case SDEV_OFFLINE: 20921da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds break; 20931da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds default: 20941da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds goto illegal; 20951da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds } 20961da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds break; 20971da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 20981da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds case SDEV_OFFLINE: 20991da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds switch (oldstate) { 21001da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds case SDEV_CREATED: 21011da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds case SDEV_RUNNING: 21021da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds case SDEV_QUIESCE: 21031da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds case SDEV_BLOCK: 21041da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds break; 21051da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds default: 21061da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds goto illegal; 21071da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds } 21081da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds break; 21091da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 21101da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds case SDEV_BLOCK: 21111da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds switch (oldstate) { 21121da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds case SDEV_RUNNING: 21136f4267e3bd1211b3d09130e626b0b3d885077610James Bottomley case SDEV_CREATED_BLOCK: 21146f4267e3bd1211b3d09130e626b0b3d885077610James Bottomley break; 21156f4267e3bd1211b3d09130e626b0b3d885077610James Bottomley default: 21166f4267e3bd1211b3d09130e626b0b3d885077610James Bottomley goto illegal; 21176f4267e3bd1211b3d09130e626b0b3d885077610James Bottomley } 21186f4267e3bd1211b3d09130e626b0b3d885077610James Bottomley break; 21196f4267e3bd1211b3d09130e626b0b3d885077610James Bottomley 21206f4267e3bd1211b3d09130e626b0b3d885077610James Bottomley case SDEV_CREATED_BLOCK: 21216f4267e3bd1211b3d09130e626b0b3d885077610James Bottomley switch (oldstate) { 21226f4267e3bd1211b3d09130e626b0b3d885077610James Bottomley case SDEV_CREATED: 21231da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds break; 21241da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds default: 21251da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds goto illegal; 21261da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds } 21271da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds break; 21281da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 21291da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds case SDEV_CANCEL: 21301da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds switch (oldstate) { 21311da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds case SDEV_CREATED: 21321da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds case SDEV_RUNNING: 21339ea7290902abcf22f796e9aeae4dc2e71d3f7e67Alan Stern case SDEV_QUIESCE: 21341da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds case SDEV_OFFLINE: 21351da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds case SDEV_BLOCK: 21361da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds break; 21371da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds default: 21381da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds goto illegal; 21391da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds } 21401da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds break; 21411da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 21421da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds case SDEV_DEL: 21431da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds switch (oldstate) { 2144309bd271211caa5a04a8137649cebd7691376351Brian King case SDEV_CREATED: 2145309bd271211caa5a04a8137649cebd7691376351Brian King case SDEV_RUNNING: 2146309bd271211caa5a04a8137649cebd7691376351Brian King case SDEV_OFFLINE: 21471da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds case SDEV_CANCEL: 21481da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds break; 21491da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds default: 21501da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds goto illegal; 21511da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds } 21521da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds break; 21531da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 21541da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds } 21551da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds sdev->sdev_state = state; 21561da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds return 0; 21571da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 21581da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds illegal: 21591da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds SCSI_LOG_ERROR_RECOVERY(1, 21609ccfc756a70d454dfa82f48897e2883560c01a0eJames Bottomley sdev_printk(KERN_ERR, sdev, 21619ccfc756a70d454dfa82f48897e2883560c01a0eJames Bottomley "Illegal state transition %s->%s\n", 21629ccfc756a70d454dfa82f48897e2883560c01a0eJames Bottomley scsi_device_state_name(oldstate), 21639ccfc756a70d454dfa82f48897e2883560c01a0eJames Bottomley scsi_device_state_name(state)) 21641da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds ); 21651da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds return -EINVAL; 21661da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds} 21671da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus TorvaldsEXPORT_SYMBOL(scsi_device_set_state); 21681da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 21691da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds/** 2170a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik * sdev_evt_emit - emit a single SCSI device uevent 2171a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik * @sdev: associated SCSI device 2172a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik * @evt: event to emit 2173a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik * 2174a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik * Send a single uevent (scsi_event) to the associated scsi_device. 2175a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik */ 2176a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzikstatic void scsi_evt_emit(struct scsi_device *sdev, struct scsi_event *evt) 2177a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik{ 2178a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik int idx = 0; 2179a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik char *envp[3]; 2180a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik 2181a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik switch (evt->evt_type) { 2182a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik case SDEV_EVT_MEDIA_CHANGE: 2183a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik envp[idx++] = "SDEV_MEDIA_CHANGE=1"; 2184a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik break; 2185a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik 2186a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik default: 2187a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik /* do nothing */ 2188a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik break; 2189a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik } 2190a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik 2191a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik envp[idx++] = NULL; 2192a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik 2193a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik kobject_uevent_env(&sdev->sdev_gendev.kobj, KOBJ_CHANGE, envp); 2194a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik} 2195a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik 2196a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik/** 2197a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik * sdev_evt_thread - send a uevent for each scsi event 2198a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik * @work: work struct for scsi_device 2199a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik * 2200a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik * Dispatch queued events to their associated scsi_device kobjects 2201a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik * as uevents. 2202a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik */ 2203a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzikvoid scsi_evt_thread(struct work_struct *work) 2204a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik{ 2205a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik struct scsi_device *sdev; 2206a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik LIST_HEAD(event_list); 2207a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik 2208a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik sdev = container_of(work, struct scsi_device, event_work); 2209a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik 2210a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik while (1) { 2211a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik struct scsi_event *evt; 2212a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik struct list_head *this, *tmp; 2213a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik unsigned long flags; 2214a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik 2215a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik spin_lock_irqsave(&sdev->list_lock, flags); 2216a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik list_splice_init(&sdev->event_list, &event_list); 2217a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik spin_unlock_irqrestore(&sdev->list_lock, flags); 2218a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik 2219a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik if (list_empty(&event_list)) 2220a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik break; 2221a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik 2222a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik list_for_each_safe(this, tmp, &event_list) { 2223a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik evt = list_entry(this, struct scsi_event, node); 2224a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik list_del(&evt->node); 2225a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik scsi_evt_emit(sdev, evt); 2226a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik kfree(evt); 2227a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik } 2228a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik } 2229a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik} 2230a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik 2231a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik/** 2232a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik * sdev_evt_send - send asserted event to uevent thread 2233a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik * @sdev: scsi_device event occurred on 2234a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik * @evt: event to send 2235a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik * 2236a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik * Assert scsi device event asynchronously. 2237a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik */ 2238a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzikvoid sdev_evt_send(struct scsi_device *sdev, struct scsi_event *evt) 2239a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik{ 2240a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik unsigned long flags; 2241a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik 22424d1566ed2100d074ccc654e5cf2e44cdea3a01d0Kay Sievers#if 0 22434d1566ed2100d074ccc654e5cf2e44cdea3a01d0Kay Sievers /* FIXME: currently this check eliminates all media change events 22444d1566ed2100d074ccc654e5cf2e44cdea3a01d0Kay Sievers * for polled devices. Need to update to discriminate between AN 22454d1566ed2100d074ccc654e5cf2e44cdea3a01d0Kay Sievers * and polled events */ 2246a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik if (!test_bit(evt->evt_type, sdev->supported_events)) { 2247a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik kfree(evt); 2248a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik return; 2249a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik } 22504d1566ed2100d074ccc654e5cf2e44cdea3a01d0Kay Sievers#endif 2251a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik 2252a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik spin_lock_irqsave(&sdev->list_lock, flags); 2253a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik list_add_tail(&evt->node, &sdev->event_list); 2254a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik schedule_work(&sdev->event_work); 2255a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik spin_unlock_irqrestore(&sdev->list_lock, flags); 2256a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik} 2257a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff GarzikEXPORT_SYMBOL_GPL(sdev_evt_send); 2258a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik 2259a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik/** 2260a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik * sdev_evt_alloc - allocate a new scsi event 2261a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik * @evt_type: type of event to allocate 2262a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik * @gfpflags: GFP flags for allocation 2263a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik * 2264a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik * Allocates and returns a new scsi_event. 2265a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik */ 2266a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzikstruct scsi_event *sdev_evt_alloc(enum scsi_device_event evt_type, 2267a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik gfp_t gfpflags) 2268a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik{ 2269a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik struct scsi_event *evt = kzalloc(sizeof(struct scsi_event), gfpflags); 2270a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik if (!evt) 2271a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik return NULL; 2272a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik 2273a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik evt->evt_type = evt_type; 2274a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik INIT_LIST_HEAD(&evt->node); 2275a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik 2276a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik /* evt_type-specific initialization, if any */ 2277a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik switch (evt_type) { 2278a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik case SDEV_EVT_MEDIA_CHANGE: 2279a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik default: 2280a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik /* do nothing */ 2281a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik break; 2282a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik } 2283a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik 2284a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik return evt; 2285a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik} 2286a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff GarzikEXPORT_SYMBOL_GPL(sdev_evt_alloc); 2287a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik 2288a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik/** 2289a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik * sdev_evt_send_simple - send asserted event to uevent thread 2290a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik * @sdev: scsi_device event occurred on 2291a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik * @evt_type: type of event to send 2292a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik * @gfpflags: GFP flags for allocation 2293a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik * 2294a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik * Assert scsi device event asynchronously, given an event type. 2295a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik */ 2296a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzikvoid sdev_evt_send_simple(struct scsi_device *sdev, 2297a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik enum scsi_device_event evt_type, gfp_t gfpflags) 2298a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik{ 2299a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik struct scsi_event *evt = sdev_evt_alloc(evt_type, gfpflags); 2300a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik if (!evt) { 2301a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik sdev_printk(KERN_ERR, sdev, "event %d eaten due to OOM\n", 2302a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik evt_type); 2303a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik return; 2304a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik } 2305a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik 2306a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik sdev_evt_send(sdev, evt); 2307a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik} 2308a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff GarzikEXPORT_SYMBOL_GPL(sdev_evt_send_simple); 2309a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik 2310a341cd0f6a0fde1f85fec9aa8f81f824ea4a3f92Jeff Garzik/** 23111da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * scsi_device_quiesce - Block user issued commands. 23121da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * @sdev: scsi device to quiesce. 23131da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * 23141da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * This works by trying to transition to the SDEV_QUIESCE state 23151da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * (which must be a legal transition). When the device is in this 23161da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * state, only special requests will be accepted, all others will 23171da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * be deferred. Since special requests may also be requeued requests, 23181da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * a successful return doesn't guarantee the device will be 23191da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * totally quiescent. 23201da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * 23211da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Must be called with user context, may sleep. 23221da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * 23231da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Returns zero if unsuccessful or an error if not. 2324eb44820c28bc9a042e1157b41c677018a8fdfc74Rob Landley */ 23251da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldsint 23261da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldsscsi_device_quiesce(struct scsi_device *sdev) 23271da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds{ 23281da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds int err = scsi_device_set_state(sdev, SDEV_QUIESCE); 23291da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds if (err) 23301da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds return err; 23311da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 23321da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds scsi_run_queue(sdev->request_queue); 23331da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds while (sdev->device_busy) { 23341da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds msleep_interruptible(200); 23351da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds scsi_run_queue(sdev->request_queue); 23361da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds } 23371da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds return 0; 23381da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds} 23391da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus TorvaldsEXPORT_SYMBOL(scsi_device_quiesce); 23401da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 23411da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds/** 23421da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * scsi_device_resume - Restart user issued commands to a quiesced device. 23431da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * @sdev: scsi device to resume. 23441da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * 23451da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Moves the device from quiesced back to running and restarts the 23461da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * queues. 23471da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * 23481da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Must be called with user context, may sleep. 2349eb44820c28bc9a042e1157b41c677018a8fdfc74Rob Landley */ 23501da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldsvoid 23511da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldsscsi_device_resume(struct scsi_device *sdev) 23521da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds{ 23531da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds if(scsi_device_set_state(sdev, SDEV_RUNNING)) 23541da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds return; 23551da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds scsi_run_queue(sdev->request_queue); 23561da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds} 23571da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus TorvaldsEXPORT_SYMBOL(scsi_device_resume); 23581da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 23591da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldsstatic void 23601da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldsdevice_quiesce_fn(struct scsi_device *sdev, void *data) 23611da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds{ 23621da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds scsi_device_quiesce(sdev); 23631da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds} 23641da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 23651da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldsvoid 23661da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldsscsi_target_quiesce(struct scsi_target *starget) 23671da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds{ 23681da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds starget_for_each_device(starget, NULL, device_quiesce_fn); 23691da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds} 23701da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus TorvaldsEXPORT_SYMBOL(scsi_target_quiesce); 23711da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 23721da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldsstatic void 23731da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldsdevice_resume_fn(struct scsi_device *sdev, void *data) 23741da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds{ 23751da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds scsi_device_resume(sdev); 23761da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds} 23771da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 23781da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldsvoid 23791da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldsscsi_target_resume(struct scsi_target *starget) 23801da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds{ 23811da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds starget_for_each_device(starget, NULL, device_resume_fn); 23821da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds} 23831da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus TorvaldsEXPORT_SYMBOL(scsi_target_resume); 23841da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 23851da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds/** 2386eb44820c28bc9a042e1157b41c677018a8fdfc74Rob Landley * scsi_internal_device_block - internal function to put a device temporarily into the SDEV_BLOCK state 23871da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * @sdev: device to block 23881da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * 23891da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Block request made by scsi lld's to temporarily stop all 23901da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * scsi commands on the specified device. Called from interrupt 23911da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * or normal process context. 23921da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * 23931da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Returns zero if successful or error if not 23941da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * 23951da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Notes: 23961da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * This routine transitions the device to the SDEV_BLOCK state 23971da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * (which must be a legal transition). When the device is in this 23981da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * state, all commands are deferred until the scsi lld reenables 23991da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * the device with scsi_device_unblock or device_block_tmo fires. 24001da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * This routine assumes the host_lock is held on entry. 2401eb44820c28bc9a042e1157b41c677018a8fdfc74Rob Landley */ 24021da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldsint 24031da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldsscsi_internal_device_block(struct scsi_device *sdev) 24041da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds{ 2405165125e1e480f9510a5ffcfbfee4e3ee38c05f23Jens Axboe struct request_queue *q = sdev->request_queue; 24061da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds unsigned long flags; 24071da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds int err = 0; 24081da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 24091da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds err = scsi_device_set_state(sdev, SDEV_BLOCK); 24106f4267e3bd1211b3d09130e626b0b3d885077610James Bottomley if (err) { 24116f4267e3bd1211b3d09130e626b0b3d885077610James Bottomley err = scsi_device_set_state(sdev, SDEV_CREATED_BLOCK); 24126f4267e3bd1211b3d09130e626b0b3d885077610James Bottomley 24136f4267e3bd1211b3d09130e626b0b3d885077610James Bottomley if (err) 24146f4267e3bd1211b3d09130e626b0b3d885077610James Bottomley return err; 24156f4267e3bd1211b3d09130e626b0b3d885077610James Bottomley } 24161da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 24171da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds /* 24181da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * The device has transitioned to SDEV_BLOCK. Stop the 24191da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * block layer from calling the midlayer with this device's 24201da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * request queue. 24211da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds */ 24221da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds spin_lock_irqsave(q->queue_lock, flags); 24231da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds blk_stop_queue(q); 24241da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds spin_unlock_irqrestore(q->queue_lock, flags); 24251da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 24261da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds return 0; 24271da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds} 24281da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus TorvaldsEXPORT_SYMBOL_GPL(scsi_internal_device_block); 24291da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 24301da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds/** 24311da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * scsi_internal_device_unblock - resume a device after a block request 24321da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * @sdev: device to resume 24331da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * 24341da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Called by scsi lld's or the midlayer to restart the device queue 24351da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * for the previously suspended scsi device. Called from interrupt or 24361da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * normal process context. 24371da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * 24381da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Returns zero if successful or error if not. 24391da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * 24401da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Notes: 24411da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * This routine transitions the device to the SDEV_RUNNING state 24421da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * (which must be a legal transition) allowing the midlayer to 24431da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * goose the queue for this device. This routine assumes the 24441da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * host_lock is held upon entry. 2445eb44820c28bc9a042e1157b41c677018a8fdfc74Rob Landley */ 24461da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldsint 24471da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldsscsi_internal_device_unblock(struct scsi_device *sdev) 24481da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds{ 2449165125e1e480f9510a5ffcfbfee4e3ee38c05f23Jens Axboe struct request_queue *q = sdev->request_queue; 24501da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds unsigned long flags; 24511da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 24521da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds /* 24531da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * Try to transition the scsi device to SDEV_RUNNING 24541da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds * and goose the device queue if successful. 24551da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds */ 24565c10e63c943b4c67561ddc6bf61e01d4141f881fTakahiro Yasui if (sdev->sdev_state == SDEV_BLOCK) 24575c10e63c943b4c67561ddc6bf61e01d4141f881fTakahiro Yasui sdev->sdev_state = SDEV_RUNNING; 24585c10e63c943b4c67561ddc6bf61e01d4141f881fTakahiro Yasui else if (sdev->sdev_state == SDEV_CREATED_BLOCK) 24595c10e63c943b4c67561ddc6bf61e01d4141f881fTakahiro Yasui sdev->sdev_state = SDEV_CREATED; 2460986fe6c7f50974e871b8ab5a800f5310ea25b361Mike Christie else if (sdev->sdev_state != SDEV_CANCEL && 2461986fe6c7f50974e871b8ab5a800f5310ea25b361Mike Christie sdev->sdev_state != SDEV_OFFLINE) 24625c10e63c943b4c67561ddc6bf61e01d4141f881fTakahiro Yasui return -EINVAL; 24631da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 24641da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds spin_lock_irqsave(q->queue_lock, flags); 24651da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds blk_start_queue(q); 24661da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds spin_unlock_irqrestore(q->queue_lock, flags); 24671da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 24681da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds return 0; 24691da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds} 24701da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus TorvaldsEXPORT_SYMBOL_GPL(scsi_internal_device_unblock); 24711da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 24721da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldsstatic void 24731da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldsdevice_block(struct scsi_device *sdev, void *data) 24741da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds{ 24751da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds scsi_internal_device_block(sdev); 24761da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds} 24771da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 24781da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldsstatic int 24791da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldstarget_block(struct device *dev, void *data) 24801da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds{ 24811da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds if (scsi_is_target_device(dev)) 24821da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds starget_for_each_device(to_scsi_target(dev), NULL, 24831da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds device_block); 24841da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds return 0; 24851da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds} 24861da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 24871da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldsvoid 24881da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldsscsi_target_block(struct device *dev) 24891da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds{ 24901da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds if (scsi_is_target_device(dev)) 24911da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds starget_for_each_device(to_scsi_target(dev), NULL, 24921da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds device_block); 24931da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds else 24941da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds device_for_each_child(dev, NULL, target_block); 24951da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds} 24961da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus TorvaldsEXPORT_SYMBOL_GPL(scsi_target_block); 24971da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 24981da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldsstatic void 24991da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldsdevice_unblock(struct scsi_device *sdev, void *data) 25001da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds{ 25011da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds scsi_internal_device_unblock(sdev); 25021da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds} 25031da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 25041da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldsstatic int 25051da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldstarget_unblock(struct device *dev, void *data) 25061da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds{ 25071da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds if (scsi_is_target_device(dev)) 25081da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds starget_for_each_device(to_scsi_target(dev), NULL, 25091da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds device_unblock); 25101da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds return 0; 25111da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds} 25121da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds 25131da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldsvoid 25141da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvaldsscsi_target_unblock(struct device *dev) 25151da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds{ 25161da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds if (scsi_is_target_device(dev)) 25171da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds starget_for_each_device(to_scsi_target(dev), NULL, 25181da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds device_unblock); 25191da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds else 25201da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds device_for_each_child(dev, NULL, target_unblock); 25211da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus Torvalds} 25221da177e4c3f41524e886b7f1b8a0c1fc7321cacLinus TorvaldsEXPORT_SYMBOL_GPL(scsi_target_unblock); 2523cdb8c2a6d848deb9eeefffff42974478fbb51b8cGuennadi Liakhovetski 2524cdb8c2a6d848deb9eeefffff42974478fbb51b8cGuennadi Liakhovetski/** 2525cdb8c2a6d848deb9eeefffff42974478fbb51b8cGuennadi Liakhovetski * scsi_kmap_atomic_sg - find and atomically map an sg-elemnt 2526eb44820c28bc9a042e1157b41c677018a8fdfc74Rob Landley * @sgl: scatter-gather list 2527cdb8c2a6d848deb9eeefffff42974478fbb51b8cGuennadi Liakhovetski * @sg_count: number of segments in sg 2528cdb8c2a6d848deb9eeefffff42974478fbb51b8cGuennadi Liakhovetski * @offset: offset in bytes into sg, on return offset into the mapped area 2529cdb8c2a6d848deb9eeefffff42974478fbb51b8cGuennadi Liakhovetski * @len: bytes to map, on return number of bytes mapped 2530cdb8c2a6d848deb9eeefffff42974478fbb51b8cGuennadi Liakhovetski * 2531cdb8c2a6d848deb9eeefffff42974478fbb51b8cGuennadi Liakhovetski * Returns virtual address of the start of the mapped page 2532cdb8c2a6d848deb9eeefffff42974478fbb51b8cGuennadi Liakhovetski */ 2533c6132da1704be252ee6c923f47501083d835c238Jens Axboevoid *scsi_kmap_atomic_sg(struct scatterlist *sgl, int sg_count, 2534cdb8c2a6d848deb9eeefffff42974478fbb51b8cGuennadi Liakhovetski size_t *offset, size_t *len) 2535cdb8c2a6d848deb9eeefffff42974478fbb51b8cGuennadi Liakhovetski{ 2536cdb8c2a6d848deb9eeefffff42974478fbb51b8cGuennadi Liakhovetski int i; 2537cdb8c2a6d848deb9eeefffff42974478fbb51b8cGuennadi Liakhovetski size_t sg_len = 0, len_complete = 0; 2538c6132da1704be252ee6c923f47501083d835c238Jens Axboe struct scatterlist *sg; 2539cdb8c2a6d848deb9eeefffff42974478fbb51b8cGuennadi Liakhovetski struct page *page; 2540cdb8c2a6d848deb9eeefffff42974478fbb51b8cGuennadi Liakhovetski 254122cfefb56b53103a99908ec63311e61c217eaffeAndrew Morton WARN_ON(!irqs_disabled()); 254222cfefb56b53103a99908ec63311e61c217eaffeAndrew Morton 2543c6132da1704be252ee6c923f47501083d835c238Jens Axboe for_each_sg(sgl, sg, sg_count, i) { 2544cdb8c2a6d848deb9eeefffff42974478fbb51b8cGuennadi Liakhovetski len_complete = sg_len; /* Complete sg-entries */ 2545c6132da1704be252ee6c923f47501083d835c238Jens Axboe sg_len += sg->length; 2546cdb8c2a6d848deb9eeefffff42974478fbb51b8cGuennadi Liakhovetski if (sg_len > *offset) 2547cdb8c2a6d848deb9eeefffff42974478fbb51b8cGuennadi Liakhovetski break; 2548cdb8c2a6d848deb9eeefffff42974478fbb51b8cGuennadi Liakhovetski } 2549cdb8c2a6d848deb9eeefffff42974478fbb51b8cGuennadi Liakhovetski 2550cdb8c2a6d848deb9eeefffff42974478fbb51b8cGuennadi Liakhovetski if (unlikely(i == sg_count)) { 2551169e1a2a8a789fa84254695ec6a56fc410bb19a9Andrew Morton printk(KERN_ERR "%s: Bytes in sg: %zu, requested offset %zu, " 2552169e1a2a8a789fa84254695ec6a56fc410bb19a9Andrew Morton "elements %d\n", 2553cadbd4a5e36dde7e6c49b587b2c419103c0b7218Harvey Harrison __func__, sg_len, *offset, sg_count); 2554cdb8c2a6d848deb9eeefffff42974478fbb51b8cGuennadi Liakhovetski WARN_ON(1); 2555cdb8c2a6d848deb9eeefffff42974478fbb51b8cGuennadi Liakhovetski return NULL; 2556cdb8c2a6d848deb9eeefffff42974478fbb51b8cGuennadi Liakhovetski } 2557cdb8c2a6d848deb9eeefffff42974478fbb51b8cGuennadi Liakhovetski 2558cdb8c2a6d848deb9eeefffff42974478fbb51b8cGuennadi Liakhovetski /* Offset starting from the beginning of first page in this sg-entry */ 2559c6132da1704be252ee6c923f47501083d835c238Jens Axboe *offset = *offset - len_complete + sg->offset; 2560cdb8c2a6d848deb9eeefffff42974478fbb51b8cGuennadi Liakhovetski 2561cdb8c2a6d848deb9eeefffff42974478fbb51b8cGuennadi Liakhovetski /* Assumption: contiguous pages can be accessed as "page + i" */ 256245711f1af6eff1a6d010703b4862e0d2b9afd056Jens Axboe page = nth_page(sg_page(sg), (*offset >> PAGE_SHIFT)); 2563cdb8c2a6d848deb9eeefffff42974478fbb51b8cGuennadi Liakhovetski *offset &= ~PAGE_MASK; 2564cdb8c2a6d848deb9eeefffff42974478fbb51b8cGuennadi Liakhovetski 2565cdb8c2a6d848deb9eeefffff42974478fbb51b8cGuennadi Liakhovetski /* Bytes in this sg-entry from *offset to the end of the page */ 2566cdb8c2a6d848deb9eeefffff42974478fbb51b8cGuennadi Liakhovetski sg_len = PAGE_SIZE - *offset; 2567cdb8c2a6d848deb9eeefffff42974478fbb51b8cGuennadi Liakhovetski if (*len > sg_len) 2568cdb8c2a6d848deb9eeefffff42974478fbb51b8cGuennadi Liakhovetski *len = sg_len; 2569cdb8c2a6d848deb9eeefffff42974478fbb51b8cGuennadi Liakhovetski 2570cdb8c2a6d848deb9eeefffff42974478fbb51b8cGuennadi Liakhovetski return kmap_atomic(page, KM_BIO_SRC_IRQ); 2571cdb8c2a6d848deb9eeefffff42974478fbb51b8cGuennadi Liakhovetski} 2572cdb8c2a6d848deb9eeefffff42974478fbb51b8cGuennadi LiakhovetskiEXPORT_SYMBOL(scsi_kmap_atomic_sg); 2573cdb8c2a6d848deb9eeefffff42974478fbb51b8cGuennadi Liakhovetski 2574cdb8c2a6d848deb9eeefffff42974478fbb51b8cGuennadi Liakhovetski/** 2575eb44820c28bc9a042e1157b41c677018a8fdfc74Rob Landley * scsi_kunmap_atomic_sg - atomically unmap a virtual address, previously mapped with scsi_kmap_atomic_sg 2576cdb8c2a6d848deb9eeefffff42974478fbb51b8cGuennadi Liakhovetski * @virt: virtual address to be unmapped 2577cdb8c2a6d848deb9eeefffff42974478fbb51b8cGuennadi Liakhovetski */ 2578cdb8c2a6d848deb9eeefffff42974478fbb51b8cGuennadi Liakhovetskivoid scsi_kunmap_atomic_sg(void *virt) 2579cdb8c2a6d848deb9eeefffff42974478fbb51b8cGuennadi Liakhovetski{ 2580cdb8c2a6d848deb9eeefffff42974478fbb51b8cGuennadi Liakhovetski kunmap_atomic(virt, KM_BIO_SRC_IRQ); 2581cdb8c2a6d848deb9eeefffff42974478fbb51b8cGuennadi Liakhovetski} 2582cdb8c2a6d848deb9eeefffff42974478fbb51b8cGuennadi LiakhovetskiEXPORT_SYMBOL(scsi_kunmap_atomic_sg); 2583