From: mengcong Date: Thu, 17 May 2012 03:14:46 +0000 (+0800) Subject: target: Handle ATA_16 passthrough for pSCSI backend devices X-Git-Url: http://drtracing.org/?a=commitdiff_plain;h=8da10935bc8358f03c9d90ed2e4a3bbaa19940ab;p=deliverable%2Flinux.git 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 Signed-off-by: Nicholas Bellinger --- 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( size = (cdb[7] << 8) | cdb[8]; cmd->se_cmd_flags |= SCF_SCSI_CONTROL_SG_IO_CDB; break; + case ATA_16: + /* Only support ATA passthrough to pSCSI backends.. */ + if (!passthrough) + goto out_unsupported_cdb; + + /* T_LENGTH */ + switch (cdb[2] & 0x3) { + case 0x0: + sectors = 0; + break; + case 0x1: + sectors = (((cdb[1] & 0x1) ? cdb[3] : 0) << 8) | cdb[4]; + break; + case 0x2: + sectors = (((cdb[1] & 0x1) ? cdb[5] : 0) << 8) | cdb[6]; + break; + case 0x3: + pr_err("T_LENGTH=0x3 not supported for ATA_16\n"); + goto out_invalid_cdb_field; + } + + /* BYTE_BLOCK */ + if (cdb[2] & 0x4) { + /* BLOCK T_TYPE: 512 or sector */ + size = sectors * ((cdb[2] & 0x10) ? + dev->se_sub_dev->se_dev_attrib.block_size : 512); + } else { + /* BYTE */ + size = sectors; + } + cmd->se_cmd_flags |= SCF_SCSI_CONTROL_SG_IO_CDB; + break; default: pr_warn("TARGET_CORE[%s]: Unsupported SCSI Opcode" " 0x%02x, sending CHECK_CONDITION.\n",