aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/target
diff options
context:
space:
mode:
authormengcong <mc@linux.vnet.ibm.com>2012-05-16 23:14:46 -0400
committerNicholas Bellinger <nab@linux-iscsi.org>2012-05-17 03:45:58 -0400
commit8da10935bc8358f03c9d90ed2e4a3bbaa19940ab (patch)
tree700e56db8e6515a0616460020686ed56f5f4bd48 /drivers/target
parent5b9a4d7280e160982a8ea37bc03619f53b5c98b7 (diff)
target: Handle ATA_16 passthrough for pSCSI backend devices
The cdrecord uses ATA_PASS_THROUGH_16 command while burning CDs with a SATA CD-ROM. This patch adds support to it so that PSCSI CD-ROM passthrough works with the cdrecord. (nab: Add !passthrough check to prevent non pSCSI backends from ATA_16) Signed-off-by: Cong Meng <mc@linux.vnet.ibm.com> Signed-off-by: Nicholas Bellinger <nab@linux-iscsi.org>
Diffstat (limited to 'drivers/target')
-rw-r--r--drivers/target/target_core_transport.c32
1 files changed, 32 insertions, 0 deletions
diff --git a/drivers/target/target_core_transport.c b/drivers/target/target_core_transport.c
index f95a74da4d40..b05fdc0c05d3 100644
--- a/drivers/target/target_core_transport.c
+++ b/drivers/target/target_core_transport.c
@@ -2927,6 +2927,38 @@ static int transport_generic_cmd_sequencer(
2927 size = (cdb[7] << 8) | cdb[8]; 2927 size = (cdb[7] << 8) | cdb[8];
2928 cmd->se_cmd_flags |= SCF_SCSI_CONTROL_SG_IO_CDB; 2928 cmd->se_cmd_flags |= SCF_SCSI_CONTROL_SG_IO_CDB;
2929 break; 2929 break;
2930 case ATA_16:
2931 /* Only support ATA passthrough to pSCSI backends.. */
2932 if (!passthrough)
2933 goto out_unsupported_cdb;
2934
2935 /* T_LENGTH */
2936 switch (cdb[2] & 0x3) {
2937 case 0x0:
2938 sectors = 0;
2939 break;
2940 case 0x1:
2941 sectors = (((cdb[1] & 0x1) ? cdb[3] : 0) << 8) | cdb[4];
2942 break;
2943 case 0x2:
2944 sectors = (((cdb[1] & 0x1) ? cdb[5] : 0) << 8) | cdb[6];
2945 break;
2946 case 0x3:
2947 pr_err("T_LENGTH=0x3 not supported for ATA_16\n");
2948 goto out_invalid_cdb_field;
2949 }
2950
2951 /* BYTE_BLOCK */
2952 if (cdb[2] & 0x4) {
2953 /* BLOCK T_TYPE: 512 or sector */
2954 size = sectors * ((cdb[2] & 0x10) ?
2955 dev->se_sub_dev->se_dev_attrib.block_size : 512);
2956 } else {
2957 /* BYTE */
2958 size = sectors;
2959 }
2960 cmd->se_cmd_flags |= SCF_SCSI_CONTROL_SG_IO_CDB;
2961 break;
2930 default: 2962 default:
2931 pr_warn("TARGET_CORE[%s]: Unsupported SCSI Opcode" 2963 pr_warn("TARGET_CORE[%s]: Unsupported SCSI Opcode"
2932 " 0x%02x, sending CHECK_CONDITION.\n", 2964 " 0x%02x, sending CHECK_CONDITION.\n",