summaryrefslogtreecommitdiffstats
path: root/include/scsi
diff options
context:
space:
mode:
authorBoaz Harrosh <bharrosh@panasas.com>2008-04-30 11:27:26 +0300
committerJames Bottomley <James.Bottomley@HansenPartnership.com>2008-05-02 11:33:25 -0500
commitdb4742dd8f0aa9125b74f9b2516336a75f3d9106 (patch)
tree6820b74e8fbfb13c4eee4c8ef8b59a9132320799 /include/scsi
parent64a87b244b9297667ca80264aab849a36f494884 (diff)
downloadlinux-db4742dd8f0aa9125b74f9b2516336a75f3d9106.tar.bz2
[SCSI] add support for variable length extended commands
Add support for variable-length, extended, and vendor specific CDBs to scsi-ml. It is now possible for initiators and ULD's to issue these types of commands. LLDs need not change much. All they need is to raise the .max_cmd_len to the longest command they support (see iscsi patch). - clean-up some code paths that did not expect commands to be larger than 16, and change cmd_len members' type to short as char is not enough. Signed-off-by: Boaz Harrosh <bharrosh@panasas.com> Signed-off-by: Benny Halevy <bhalevy@panasas.com> Signed-off-by: James Bottomley <James.Bottomley@HansenPartnership.com>
Diffstat (limited to 'include/scsi')
-rw-r--r--include/scsi/scsi.h40
-rw-r--r--include/scsi/scsi_cmnd.h2
-rw-r--r--include/scsi/scsi_host.h8
3 files changed, 37 insertions, 13 deletions
diff --git a/include/scsi/scsi.h b/include/scsi/scsi.h
index 1f74bcd603fe..32742c4563de 100644
--- a/include/scsi/scsi.h
+++ b/include/scsi/scsi.h
@@ -30,13 +30,6 @@
#endif
/*
- * SCSI command lengths
- */
-
-extern const unsigned char scsi_command_size[8];
-#define COMMAND_SIZE(opcode) scsi_command_size[((opcode) >> 5) & 7]
-
-/*
* Special value for scanning to specify scanning or rescanning of all
* possible channels, (target) ids, or luns on a given shost.
*/
@@ -109,6 +102,7 @@ extern const unsigned char scsi_command_size[8];
#define MODE_SENSE_10 0x5a
#define PERSISTENT_RESERVE_IN 0x5e
#define PERSISTENT_RESERVE_OUT 0x5f
+#define VARIABLE_LENGTH_CMD 0x7f
#define REPORT_LUNS 0xa0
#define MAINTENANCE_IN 0xa3
#define MOVE_MEDIUM 0xa5
@@ -136,6 +130,38 @@ extern const unsigned char scsi_command_size[8];
#define ATA_12 0xa1 /* 12-byte pass-thru */
/*
+ * SCSI command lengths
+ */
+
+#define SCSI_MAX_VARLEN_CDB_SIZE 260
+
+/* defined in T10 SCSI Primary Commands-2 (SPC2) */
+struct scsi_varlen_cdb_hdr {
+ u8 opcode; /* opcode always == VARIABLE_LENGTH_CMD */
+ u8 control;
+ u8 misc[5];
+ u8 additional_cdb_length; /* total cdb length - 8 */
+ __be16 service_action;
+ /* service specific data follows */
+};
+
+static inline unsigned
+scsi_varlen_cdb_length(const void *hdr)
+{
+ return ((struct scsi_varlen_cdb_hdr *)hdr)->additional_cdb_length + 8;
+}
+
+extern const unsigned char scsi_command_size_tbl[8];
+#define COMMAND_SIZE(opcode) scsi_command_size_tbl[((opcode) >> 5) & 7]
+
+static inline unsigned
+scsi_command_size(const unsigned char *cmnd)
+{
+ return (cmnd[0] == VARIABLE_LENGTH_CMD) ?
+ scsi_varlen_cdb_length(cmnd) : COMMAND_SIZE(cmnd[0]);
+}
+
+/*
* SCSI Architecture Model (SAM) Status codes. Taken from SAM-3 draft
* T10/1561-D Revision 4 Draft dated 7th November 2002.
*/
diff --git a/include/scsi/scsi_cmnd.h b/include/scsi/scsi_cmnd.h
index 7ed883c8e48a..3e46dfae8194 100644
--- a/include/scsi/scsi_cmnd.h
+++ b/include/scsi/scsi_cmnd.h
@@ -78,7 +78,7 @@ struct scsi_cmnd {
int allowed;
int timeout_per_command;
- unsigned char cmd_len;
+ unsigned short cmd_len;
enum dma_data_direction sc_data_direction;
/* These elements define the operation we are about to perform */
diff --git a/include/scsi/scsi_host.h b/include/scsi/scsi_host.h
index d967d6dc7a28..1834fdfe82a7 100644
--- a/include/scsi/scsi_host.h
+++ b/include/scsi/scsi_host.h
@@ -573,13 +573,11 @@ struct Scsi_Host {
/*
* The maximum length of SCSI commands that this host can accept.
* Probably 12 for most host adapters, but could be 16 for others.
+ * or 260 if the driver supports variable length cdbs.
* For drivers that don't set this field, a value of 12 is
- * assumed. I am leaving this as a number rather than a bit
- * because you never know what subsequent SCSI standards might do
- * (i.e. could there be a 20 byte or a 24-byte command a few years
- * down the road?).
+ * assumed.
*/
- unsigned char max_cmd_len;
+ unsigned short max_cmd_len;
int this_id;
int can_queue;