[stgt] [PATCH 1/3] SBC: Add basic WRITE_SAME(10) support (no UNMAP support yet)
Ronnie Sahlberg
ronniesahlberg at gmail.com
Wed Apr 18 11:30:40 CEST 2012
Signed-off-by: Ronnie Sahlberg <ronniesahlberg at gmail.com>
---
usr/bs_rdwr.c | 24 ++++++++++++++++++++++++
usr/sbc.c | 17 ++++++++++++++++-
usr/scsi.c | 2 ++
3 files changed, 42 insertions(+), 1 deletions(-)
diff --git a/usr/bs_rdwr.c b/usr/bs_rdwr.c
index fbc9a2c..e4456fc 100644
--- a/usr/bs_rdwr.c
+++ b/usr/bs_rdwr.c
@@ -65,6 +65,7 @@ static void bs_rdwr_request(struct scsi_cmd *cmd)
uint8_t key;
uint16_t asc;
char *tmpbuf;
+ size_t blocksize;
ret = length = 0;
key = asc = 0;
@@ -109,6 +110,29 @@ static void bs_rdwr_request(struct scsi_cmd *cmd)
POSIX_FADV_NOREUSE);
break;
+ case WRITE_SAME:
+ while (cmd->tl > 0) {
+ blocksize = 1 << cmd->dev->blk_shift;
+ tmpbuf = scsi_get_out_buffer(cmd);
+
+ switch(cmd->scb[1] & 0x06) {
+ case 0x02: /* PBDATA==0 LBDATA==1 */
+ put_unaligned_be32(cmd->offset, tmpbuf);
+ break;
+ case 0x04: /* PBDATA==1 LBDATA==0 */
+ /* physical sector format */
+ put_unaligned_be64(cmd->offset, tmpbuf);
+ break;
+ }
+
+ ret = pwrite64(fd, tmpbuf, blocksize, cmd->offset);
+ if (ret != blocksize)
+ set_medium_error(&result, &key, &asc);
+
+ cmd->offset += blocksize;
+ cmd->tl -= blocksize;
+ }
+ break;
case READ_6:
case READ_10:
case READ_12:
diff --git a/usr/sbc.c b/usr/sbc.c
index 55145cf..cf72e65 100644
--- a/usr/sbc.c
+++ b/usr/sbc.c
@@ -228,6 +228,20 @@ static int sbc_rw(int host_no, struct scsi_cmd *cmd)
goto sense;
}
break;
+ case WRITE_SAME:
+ /* We only support protection information type 0 */
+ if (cmd->scb[1] & 0xe0) {
+ key = ILLEGAL_REQUEST;
+ asc = ASC_INVALID_FIELD_IN_CDB;
+ goto sense;
+ }
+ /* LBDATA and PBDATA can not both be set */
+ if ((cmd->scb[1] & 0x06) == 0x06) {
+ key = ILLEGAL_REQUEST;
+ asc = ASC_INVALID_FIELD_IN_CDB;
+ goto sense;
+ }
+ break;
}
if (lu->attrs.readonly) {
@@ -236,6 +250,7 @@ static int sbc_rw(int host_no, struct scsi_cmd *cmd)
case WRITE_10:
case WRITE_12:
case WRITE_16:
+ case WRITE_SAME:
case PRE_FETCH_10:
case PRE_FETCH_16:
key = DATA_PROTECT;
@@ -607,7 +622,7 @@ static struct device_type_template sbc_template = {
/* 0x40 */
{spc_illegal_op,},
- {spc_illegal_op,},
+ {sbc_rw,}, /* WRITE_SAME10 */
{sbc_unmap,},
{spc_illegal_op,},
{spc_illegal_op,},
diff --git a/usr/scsi.c b/usr/scsi.c
index 7802ba1..c46753e 100644
--- a/usr/scsi.c
+++ b/usr/scsi.c
@@ -119,6 +119,7 @@ uint64_t scsi_rw_offset(uint8_t *scb)
case WRITE_10:
case VERIFY_10:
case WRITE_VERIFY:
+ case WRITE_SAME:
case SYNCHRONIZE_CACHE:
case READ_12:
case WRITE_12:
@@ -162,6 +163,7 @@ uint32_t scsi_rw_count(uint8_t *scb)
case WRITE_10:
case VERIFY_10:
case WRITE_VERIFY:
+ case WRITE_SAME:
case SYNCHRONIZE_CACHE:
cnt = (uint16_t)scb[7] << 8 | (uint16_t)scb[8];
break;
--
1.7.3.1
--
To unsubscribe from this list: send the line "unsubscribe stgt" in
the body of a message to majordomo at vger.kernel.org
More majordomo info at http://vger.kernel.org/majordomo-info.html
More information about the stgt
mailing list