* [PATCH 1/3] scsi_debug: add get_data_transfer_info helper function
@ 2008-01-22 16:31 FUJITA Tomonori
2008-01-22 16:32 ` [PATCH 2/3] scsi_debug: add bidi data transfer support FUJITA Tomonori
` (2 more replies)
0 siblings, 3 replies; 6+ messages in thread
From: FUJITA Tomonori @ 2008-01-22 16:31 UTC (permalink / raw)
To: James.Bottomley, dougg; +Cc: bharrosh, fujita.tomonori, linux-scsi, Jens.Axboe
This adds get_data_transfer_info helper function that get lha and
sectors for READ_* and WRITE_* commands (and XDWRITEREAD_10 later).
Signed-off-by: FUJITA Tomonori <fujita.tomonori@lab.ntt.co.jp>
---
drivers/scsi/scsi_debug.c | 83 ++++++++++++++++++++------------------------
1 files changed, 38 insertions(+), 45 deletions(-)
diff --git a/drivers/scsi/scsi_debug.c b/drivers/scsi/scsi_debug.c
index 82c06f0..31f7378 100644
--- a/drivers/scsi/scsi_debug.c
+++ b/drivers/scsi/scsi_debug.c
@@ -311,12 +311,47 @@ static void sdebug_max_tgts_luns(void);
static struct device pseudo_primary;
static struct bus_type pseudo_lld_bus;
+static void get_data_transfer_info(unsigned char *cmd,
+ unsigned long long *lba, unsigned int *num)
+{
+ int i;
+
+ switch (*cmd) {
+ case WRITE_16:
+ case READ_16:
+ for (*lba = 0, i = 0; i < 8; ++i) {
+ if (i > 0)
+ *lba <<= 8;
+ *lba += cmd[2 + i];
+ }
+ *num = cmd[13] + (cmd[12] << 8) +
+ (cmd[11] << 16) + (cmd[10] << 24);
+ break;
+ case WRITE_12:
+ case READ_12:
+ *lba = cmd[5] + (cmd[4] << 8) + (cmd[3] << 16) + (cmd[2] << 24);
+ *num = cmd[9] + (cmd[8] << 8) + (cmd[7] << 16) + (cmd[6] << 24);
+ break;
+ case WRITE_10:
+ case READ_10:
+ *lba = cmd[5] + (cmd[4] << 8) + (cmd[3] << 16) + (cmd[2] << 24);
+ *num = cmd[8] + (cmd[7] << 8);
+ break;
+ case WRITE_6:
+ case READ_6:
+ *lba = cmd[3] + (cmd[2] << 8) + ((cmd[1] & 0x1f) << 16);
+ *num = (0 == cmd[4]) ? 256 : cmd[4];
+ break;
+ default:
+ break;
+ }
+}
static
int scsi_debug_queuecommand(struct scsi_cmnd * SCpnt, done_funct_t done)
{
unsigned char *cmd = (unsigned char *) SCpnt->cmnd;
- int len, k, j;
+ int len, k;
unsigned int num;
unsigned long long lba;
int errsts = 0;
@@ -452,28 +487,7 @@ int scsi_debug_queuecommand(struct scsi_cmnd * SCpnt, done_funct_t done)
break;
if (scsi_debug_fake_rw)
break;
- if ((*cmd) == READ_16) {
- for (lba = 0, j = 0; j < 8; ++j) {
- if (j > 0)
- lba <<= 8;
- lba += cmd[2 + j];
- }
- num = cmd[13] + (cmd[12] << 8) +
- (cmd[11] << 16) + (cmd[10] << 24);
- } else if ((*cmd) == READ_12) {
- lba = cmd[5] + (cmd[4] << 8) +
- (cmd[3] << 16) + (cmd[2] << 24);
- num = cmd[9] + (cmd[8] << 8) +
- (cmd[7] << 16) + (cmd[6] << 24);
- } else if ((*cmd) == READ_10) {
- lba = cmd[5] + (cmd[4] << 8) +
- (cmd[3] << 16) + (cmd[2] << 24);
- num = cmd[8] + (cmd[7] << 8);
- } else { /* READ (6) */
- lba = cmd[3] + (cmd[2] << 8) +
- ((cmd[1] & 0x1f) << 16);
- num = (0 == cmd[4]) ? 256 : cmd[4];
- }
+ get_data_transfer_info(cmd, &lba, &num);
errsts = resp_read(SCpnt, lba, num, devip);
if (inj_recovered && (0 == errsts)) {
mk_sense_buffer(devip, RECOVERED_ERROR,
@@ -500,28 +514,7 @@ int scsi_debug_queuecommand(struct scsi_cmnd * SCpnt, done_funct_t done)
break;
if (scsi_debug_fake_rw)
break;
- if ((*cmd) == WRITE_16) {
- for (lba = 0, j = 0; j < 8; ++j) {
- if (j > 0)
- lba <<= 8;
- lba += cmd[2 + j];
- }
- num = cmd[13] + (cmd[12] << 8) +
- (cmd[11] << 16) + (cmd[10] << 24);
- } else if ((*cmd) == WRITE_12) {
- lba = cmd[5] + (cmd[4] << 8) +
- (cmd[3] << 16) + (cmd[2] << 24);
- num = cmd[9] + (cmd[8] << 8) +
- (cmd[7] << 16) + (cmd[6] << 24);
- } else if ((*cmd) == WRITE_10) {
- lba = cmd[5] + (cmd[4] << 8) +
- (cmd[3] << 16) + (cmd[2] << 24);
- num = cmd[8] + (cmd[7] << 8);
- } else { /* WRITE (6) */
- lba = cmd[3] + (cmd[2] << 8) +
- ((cmd[1] & 0x1f) << 16);
- num = (0 == cmd[4]) ? 256 : cmd[4];
- }
+ get_data_transfer_info(cmd, &lba, &num);
errsts = resp_write(SCpnt, lba, num, devip);
if (inj_recovered && (0 == errsts)) {
mk_sense_buffer(devip, RECOVERED_ERROR,
--
1.5.3.4
^ permalink raw reply related [flat|nested] 6+ messages in thread* [PATCH 2/3] scsi_debug: add bidi data transfer support 2008-01-22 16:31 [PATCH 1/3] scsi_debug: add get_data_transfer_info helper function FUJITA Tomonori @ 2008-01-22 16:32 ` FUJITA Tomonori 2008-01-22 23:11 ` Douglas Gilbert 2008-01-22 16:32 ` [PATCH 3/3] scsi_debug: add XDWRITEREAD_10 support FUJITA Tomonori 2008-01-22 23:10 ` [PATCH 1/3] scsi_debug: add get_data_transfer_info helper function Douglas Gilbert 2 siblings, 1 reply; 6+ messages in thread From: FUJITA Tomonori @ 2008-01-22 16:32 UTC (permalink / raw) To: James.Bottomley, dougg; +Cc: bharrosh, fujita.tomonori, linux-scsi, Jens.Axboe This enables fill_from_dev_buffer and fetch_to_dev_buffer to handle bidi commands. Signed-off-by: FUJITA Tomonori <fujita.tomonori@lab.ntt.co.jp> --- drivers/scsi/scsi_debug.c | 21 ++++++++++----------- 1 files changed, 10 insertions(+), 11 deletions(-) diff --git a/drivers/scsi/scsi_debug.c b/drivers/scsi/scsi_debug.c index 31f7378..d810aa7 100644 --- a/drivers/scsi/scsi_debug.c +++ b/drivers/scsi/scsi_debug.c @@ -594,18 +594,18 @@ static int fill_from_dev_buffer(struct scsi_cmnd * scp, unsigned char * arr, int k, req_len, act_len, len, active; void * kaddr; void * kaddr_off; - struct scatterlist * sg; + struct scatterlist *sg; + struct scsi_data_buffer *sdb = scsi_in(scp); - if (0 == scsi_bufflen(scp)) + if (!sdb->length) return 0; - if (NULL == scsi_sglist(scp)) + if (!sdb->table.sgl) return (DID_ERROR << 16); - if (! ((scp->sc_data_direction == DMA_BIDIRECTIONAL) || - (scp->sc_data_direction == DMA_FROM_DEVICE))) + if (!(scsi_bidi_cmnd(scp) || scp->sc_data_direction == DMA_FROM_DEVICE)) return (DID_ERROR << 16); active = 1; req_len = act_len = 0; - scsi_for_each_sg(scp, sg, scsi_sg_count(scp), k) { + for_each_sg(sdb->table.sgl, sg, sdb->table.nents, k) { if (active) { kaddr = (unsigned char *) kmap_atomic(sg_page(sg), KM_USER0); @@ -623,10 +623,10 @@ static int fill_from_dev_buffer(struct scsi_cmnd * scp, unsigned char * arr, } req_len += sg->length; } - if (scsi_get_resid(scp)) - scsi_set_resid(scp, scsi_get_resid(scp) - act_len); + if (sdb->resid) + sdb->resid -= act_len; else - scsi_set_resid(scp, req_len - act_len); + sdb->resid = req_len - act_len; return 0; } @@ -643,8 +643,7 @@ static int fetch_to_dev_buffer(struct scsi_cmnd * scp, unsigned char * arr, return 0; if (NULL == scsi_sglist(scp)) return -1; - if (! ((scp->sc_data_direction == DMA_BIDIRECTIONAL) || - (scp->sc_data_direction == DMA_TO_DEVICE))) + if (!(scsi_bidi_cmnd(scp) || scp->sc_data_direction == DMA_TO_DEVICE)) return -1; req_len = fin = 0; scsi_for_each_sg(scp, sg, scsi_sg_count(scp), k) { -- 1.5.3.4 ^ permalink raw reply related [flat|nested] 6+ messages in thread
* Re: [PATCH 2/3] scsi_debug: add bidi data transfer support 2008-01-22 16:32 ` [PATCH 2/3] scsi_debug: add bidi data transfer support FUJITA Tomonori @ 2008-01-22 23:11 ` Douglas Gilbert 0 siblings, 0 replies; 6+ messages in thread From: Douglas Gilbert @ 2008-01-22 23:11 UTC (permalink / raw) To: FUJITA Tomonori Cc: James.Bottomley, bharrosh, fujita.tomonori, linux-scsi, Jens.Axboe FUJITA Tomonori wrote: > This enables fill_from_dev_buffer and fetch_to_dev_buffer to handle > bidi commands. > > Signed-off-by: FUJITA Tomonori <fujita.tomonori@lab.ntt.co.jp> > --- > drivers/scsi/scsi_debug.c | 21 ++++++++++----------- > 1 files changed, 10 insertions(+), 11 deletions(-) > > diff --git a/drivers/scsi/scsi_debug.c b/drivers/scsi/scsi_debug.c > index 31f7378..d810aa7 100644 > --- a/drivers/scsi/scsi_debug.c > +++ b/drivers/scsi/scsi_debug.c > @@ -594,18 +594,18 @@ static int fill_from_dev_buffer(struct scsi_cmnd * scp, unsigned char * arr, > int k, req_len, act_len, len, active; > void * kaddr; > void * kaddr_off; > - struct scatterlist * sg; > + struct scatterlist *sg; > + struct scsi_data_buffer *sdb = scsi_in(scp); > > - if (0 == scsi_bufflen(scp)) > + if (!sdb->length) > return 0; > - if (NULL == scsi_sglist(scp)) > + if (!sdb->table.sgl) > return (DID_ERROR << 16); > - if (! ((scp->sc_data_direction == DMA_BIDIRECTIONAL) || > - (scp->sc_data_direction == DMA_FROM_DEVICE))) > + if (!(scsi_bidi_cmnd(scp) || scp->sc_data_direction == DMA_FROM_DEVICE)) > return (DID_ERROR << 16); > active = 1; > req_len = act_len = 0; > - scsi_for_each_sg(scp, sg, scsi_sg_count(scp), k) { > + for_each_sg(sdb->table.sgl, sg, sdb->table.nents, k) { > if (active) { > kaddr = (unsigned char *) > kmap_atomic(sg_page(sg), KM_USER0); > @@ -623,10 +623,10 @@ static int fill_from_dev_buffer(struct scsi_cmnd * scp, unsigned char * arr, > } > req_len += sg->length; > } > - if (scsi_get_resid(scp)) > - scsi_set_resid(scp, scsi_get_resid(scp) - act_len); > + if (sdb->resid) > + sdb->resid -= act_len; > else > - scsi_set_resid(scp, req_len - act_len); > + sdb->resid = req_len - act_len; > return 0; > } > > @@ -643,8 +643,7 @@ static int fetch_to_dev_buffer(struct scsi_cmnd * scp, unsigned char * arr, > return 0; > if (NULL == scsi_sglist(scp)) > return -1; > - if (! ((scp->sc_data_direction == DMA_BIDIRECTIONAL) || > - (scp->sc_data_direction == DMA_TO_DEVICE))) > + if (!(scsi_bidi_cmnd(scp) || scp->sc_data_direction == DMA_TO_DEVICE)) > return -1; > req_len = fin = 0; > scsi_for_each_sg(scp, sg, scsi_sg_count(scp), k) { Signed-off-by: Douglas Gilbert <dougg@torque.net> ^ permalink raw reply [flat|nested] 6+ messages in thread
* [PATCH 3/3] scsi_debug: add XDWRITEREAD_10 support 2008-01-22 16:31 [PATCH 1/3] scsi_debug: add get_data_transfer_info helper function FUJITA Tomonori 2008-01-22 16:32 ` [PATCH 2/3] scsi_debug: add bidi data transfer support FUJITA Tomonori @ 2008-01-22 16:32 ` FUJITA Tomonori 2008-01-22 23:11 ` Douglas Gilbert 2008-01-22 23:10 ` [PATCH 1/3] scsi_debug: add get_data_transfer_info helper function Douglas Gilbert 2 siblings, 1 reply; 6+ messages in thread From: FUJITA Tomonori @ 2008-01-22 16:32 UTC (permalink / raw) To: James.Bottomley, dougg; +Cc: bharrosh, fujita.tomonori, linux-scsi, Jens.Axboe Signed-off-by: FUJITA Tomonori <fujita.tomonori@lab.ntt.co.jp> --- drivers/scsi/scsi_debug.c | 70 +++++++++++++++++++++++++++++++++++++++++++++ include/scsi/scsi.h | 1 + 2 files changed, 71 insertions(+), 0 deletions(-) diff --git a/drivers/scsi/scsi_debug.c b/drivers/scsi/scsi_debug.c index d810aa7..1541c17 100644 --- a/drivers/scsi/scsi_debug.c +++ b/drivers/scsi/scsi_debug.c @@ -280,6 +280,8 @@ static int resp_write(struct scsi_cmnd * SCpnt, unsigned long long lba, unsigned int num, struct sdebug_dev_info * devip); static int resp_report_luns(struct scsi_cmnd * SCpnt, struct sdebug_dev_info * devip); +static int resp_xdwriteread(struct scsi_cmnd *scp, unsigned long long lba, + unsigned int num, struct sdebug_dev_info *devip); static int fill_from_dev_buffer(struct scsi_cmnd * scp, unsigned char * arr, int arr_len); static int fetch_to_dev_buffer(struct scsi_cmnd * scp, unsigned char * arr, @@ -334,6 +336,7 @@ static void get_data_transfer_info(unsigned char *cmd, break; case WRITE_10: case READ_10: + case XDWRITEREAD_10: *lba = cmd[5] + (cmd[4] << 8) + (cmd[3] << 16) + (cmd[2] << 24); *num = cmd[8] + (cmd[7] << 8); break; @@ -542,6 +545,28 @@ int scsi_debug_queuecommand(struct scsi_cmnd * SCpnt, done_funct_t done) case WRITE_BUFFER: errsts = check_readiness(SCpnt, 1, devip); break; + case XDWRITEREAD_10: + if (!scsi_bidi_cmnd(SCpnt)) { + mk_sense_buffer(devip, ILLEGAL_REQUEST, + INVALID_FIELD_IN_CDB, 0); + errsts = check_condition_result; + break; + } + + errsts = check_readiness(SCpnt, 0, devip); + if (errsts) + break; + if (scsi_debug_fake_rw) + break; + get_data_transfer_info(cmd, &lba, &num); + errsts = resp_read(SCpnt, lba, num, devip); + if (errsts) + break; + errsts = resp_write(SCpnt, lba, num, devip); + if (errsts) + break; + errsts = resp_xdwriteread(SCpnt, lba, num, devip); + break; default: if (SCSI_DEBUG_OPT_NOISE & scsi_debug_opts) printk(KERN_INFO "scsi_debug: Opcode: 0x%x not " @@ -1948,6 +1973,50 @@ static int resp_report_luns(struct scsi_cmnd * scp, min((int)alloc_len, SDEBUG_RLUN_ARR_SZ)); } +static int resp_xdwriteread(struct scsi_cmnd *scp, unsigned long long lba, + unsigned int num, struct sdebug_dev_info *devip) +{ + int i, j, ret = -1; + unsigned char *kaddr, *buf; + unsigned int offset; + struct scatterlist *sg; + struct scsi_data_buffer *sdb = scsi_in(scp); + + /* better not to use temporary buffer. */ + buf = kmalloc(scsi_bufflen(scp), GFP_ATOMIC); + if (!buf) + return ret; + + offset = 0; + scsi_for_each_sg(scp, sg, scsi_sg_count(scp), i) { + kaddr = (unsigned char *)kmap_atomic(sg_page(sg), KM_USER0); + if (!kaddr) + goto out; + + memcpy(buf + offset, kaddr + sg->offset, sg->length); + offset += sg->length; + kunmap_atomic(kaddr, KM_USER0); + } + + offset = 0; + for_each_sg(sdb->table.sgl, sg, sdb->table.nents, i) { + kaddr = (unsigned char *)kmap_atomic(sg_page(sg), KM_USER0); + if (!kaddr) + goto out; + + for (j = 0; j < sg->length; j++) + *(kaddr + sg->offset + j) ^= *(buf + offset + j); + + offset += sg->length; + kunmap_atomic(kaddr, KM_USER0); + } + ret = 0; +out: + kfree(buf); + + return ret; +} + /* When timer goes off this function is called. */ static void timer_intr_handler(unsigned long indx) { @@ -1981,6 +2050,7 @@ static int scsi_debug_slave_alloc(struct scsi_device * sdp) if (SCSI_DEBUG_OPT_NOISE & scsi_debug_opts) printk(KERN_INFO "scsi_debug: slave_alloc <%u %u %u %u>\n", sdp->host->host_no, sdp->channel, sdp->id, sdp->lun); + set_bit(QUEUE_FLAG_BIDI, &sdp->request_queue->queue_flags); return 0; } diff --git a/include/scsi/scsi.h b/include/scsi/scsi.h index 056c5af..19ca9e9 100644 --- a/include/scsi/scsi.h +++ b/include/scsi/scsi.h @@ -102,6 +102,7 @@ extern const unsigned char scsi_command_size[8]; #define READ_TOC 0x43 #define LOG_SELECT 0x4c #define LOG_SENSE 0x4d +#define XDWRITEREAD_10 0x53 #define MODE_SELECT_10 0x55 #define RESERVE_10 0x56 #define RELEASE_10 0x57 -- 1.5.3.4 ^ permalink raw reply related [flat|nested] 6+ messages in thread
* Re: [PATCH 3/3] scsi_debug: add XDWRITEREAD_10 support 2008-01-22 16:32 ` [PATCH 3/3] scsi_debug: add XDWRITEREAD_10 support FUJITA Tomonori @ 2008-01-22 23:11 ` Douglas Gilbert 0 siblings, 0 replies; 6+ messages in thread From: Douglas Gilbert @ 2008-01-22 23:11 UTC (permalink / raw) To: FUJITA Tomonori Cc: James.Bottomley, bharrosh, fujita.tomonori, linux-scsi, Jens.Axboe FUJITA Tomonori wrote: > Signed-off-by: FUJITA Tomonori <fujita.tomonori@lab.ntt.co.jp> > --- > drivers/scsi/scsi_debug.c | 70 +++++++++++++++++++++++++++++++++++++++++++++ > include/scsi/scsi.h | 1 + > 2 files changed, 71 insertions(+), 0 deletions(-) > > diff --git a/drivers/scsi/scsi_debug.c b/drivers/scsi/scsi_debug.c > index d810aa7..1541c17 100644 > --- a/drivers/scsi/scsi_debug.c > +++ b/drivers/scsi/scsi_debug.c > @@ -280,6 +280,8 @@ static int resp_write(struct scsi_cmnd * SCpnt, unsigned long long lba, > unsigned int num, struct sdebug_dev_info * devip); > static int resp_report_luns(struct scsi_cmnd * SCpnt, > struct sdebug_dev_info * devip); > +static int resp_xdwriteread(struct scsi_cmnd *scp, unsigned long long lba, > + unsigned int num, struct sdebug_dev_info *devip); > static int fill_from_dev_buffer(struct scsi_cmnd * scp, unsigned char * arr, > int arr_len); > static int fetch_to_dev_buffer(struct scsi_cmnd * scp, unsigned char * arr, > @@ -334,6 +336,7 @@ static void get_data_transfer_info(unsigned char *cmd, > break; > case WRITE_10: > case READ_10: > + case XDWRITEREAD_10: > *lba = cmd[5] + (cmd[4] << 8) + (cmd[3] << 16) + (cmd[2] << 24); > *num = cmd[8] + (cmd[7] << 8); > break; > @@ -542,6 +545,28 @@ int scsi_debug_queuecommand(struct scsi_cmnd * SCpnt, done_funct_t done) > case WRITE_BUFFER: > errsts = check_readiness(SCpnt, 1, devip); > break; > + case XDWRITEREAD_10: > + if (!scsi_bidi_cmnd(SCpnt)) { > + mk_sense_buffer(devip, ILLEGAL_REQUEST, > + INVALID_FIELD_IN_CDB, 0); > + errsts = check_condition_result; > + break; > + } > + > + errsts = check_readiness(SCpnt, 0, devip); > + if (errsts) > + break; > + if (scsi_debug_fake_rw) > + break; > + get_data_transfer_info(cmd, &lba, &num); > + errsts = resp_read(SCpnt, lba, num, devip); > + if (errsts) > + break; > + errsts = resp_write(SCpnt, lba, num, devip); > + if (errsts) > + break; > + errsts = resp_xdwriteread(SCpnt, lba, num, devip); > + break; > default: > if (SCSI_DEBUG_OPT_NOISE & scsi_debug_opts) > printk(KERN_INFO "scsi_debug: Opcode: 0x%x not " > @@ -1948,6 +1973,50 @@ static int resp_report_luns(struct scsi_cmnd * scp, > min((int)alloc_len, SDEBUG_RLUN_ARR_SZ)); > } > > +static int resp_xdwriteread(struct scsi_cmnd *scp, unsigned long long lba, > + unsigned int num, struct sdebug_dev_info *devip) > +{ > + int i, j, ret = -1; > + unsigned char *kaddr, *buf; > + unsigned int offset; > + struct scatterlist *sg; > + struct scsi_data_buffer *sdb = scsi_in(scp); > + > + /* better not to use temporary buffer. */ > + buf = kmalloc(scsi_bufflen(scp), GFP_ATOMIC); > + if (!buf) > + return ret; > + > + offset = 0; > + scsi_for_each_sg(scp, sg, scsi_sg_count(scp), i) { > + kaddr = (unsigned char *)kmap_atomic(sg_page(sg), KM_USER0); > + if (!kaddr) > + goto out; > + > + memcpy(buf + offset, kaddr + sg->offset, sg->length); > + offset += sg->length; > + kunmap_atomic(kaddr, KM_USER0); > + } > + > + offset = 0; > + for_each_sg(sdb->table.sgl, sg, sdb->table.nents, i) { > + kaddr = (unsigned char *)kmap_atomic(sg_page(sg), KM_USER0); > + if (!kaddr) > + goto out; > + > + for (j = 0; j < sg->length; j++) > + *(kaddr + sg->offset + j) ^= *(buf + offset + j); > + > + offset += sg->length; > + kunmap_atomic(kaddr, KM_USER0); > + } > + ret = 0; > +out: > + kfree(buf); > + > + return ret; > +} > + > /* When timer goes off this function is called. */ > static void timer_intr_handler(unsigned long indx) > { > @@ -1981,6 +2050,7 @@ static int scsi_debug_slave_alloc(struct scsi_device * sdp) > if (SCSI_DEBUG_OPT_NOISE & scsi_debug_opts) > printk(KERN_INFO "scsi_debug: slave_alloc <%u %u %u %u>\n", > sdp->host->host_no, sdp->channel, sdp->id, sdp->lun); > + set_bit(QUEUE_FLAG_BIDI, &sdp->request_queue->queue_flags); > return 0; > } > > diff --git a/include/scsi/scsi.h b/include/scsi/scsi.h > index 056c5af..19ca9e9 100644 > --- a/include/scsi/scsi.h > +++ b/include/scsi/scsi.h > @@ -102,6 +102,7 @@ extern const unsigned char scsi_command_size[8]; > #define READ_TOC 0x43 > #define LOG_SELECT 0x4c > #define LOG_SENSE 0x4d > +#define XDWRITEREAD_10 0x53 > #define MODE_SELECT_10 0x55 > #define RESERVE_10 0x56 > #define RELEASE_10 0x57 Signed-off-by: Douglas Gilbert <dougg@torque.net> ^ permalink raw reply [flat|nested] 6+ messages in thread
* Re: [PATCH 1/3] scsi_debug: add get_data_transfer_info helper function 2008-01-22 16:31 [PATCH 1/3] scsi_debug: add get_data_transfer_info helper function FUJITA Tomonori 2008-01-22 16:32 ` [PATCH 2/3] scsi_debug: add bidi data transfer support FUJITA Tomonori 2008-01-22 16:32 ` [PATCH 3/3] scsi_debug: add XDWRITEREAD_10 support FUJITA Tomonori @ 2008-01-22 23:10 ` Douglas Gilbert 2 siblings, 0 replies; 6+ messages in thread From: Douglas Gilbert @ 2008-01-22 23:10 UTC (permalink / raw) To: FUJITA Tomonori Cc: James.Bottomley, bharrosh, fujita.tomonori, linux-scsi, Jens.Axboe FUJITA Tomonori wrote: > This adds get_data_transfer_info helper function that get lha and > sectors for READ_* and WRITE_* commands (and XDWRITEREAD_10 later). > > Signed-off-by: FUJITA Tomonori <fujita.tomonori@lab.ntt.co.jp> > --- > drivers/scsi/scsi_debug.c | 83 ++++++++++++++++++++------------------------ > 1 files changed, 38 insertions(+), 45 deletions(-) > > diff --git a/drivers/scsi/scsi_debug.c b/drivers/scsi/scsi_debug.c > index 82c06f0..31f7378 100644 > --- a/drivers/scsi/scsi_debug.c > +++ b/drivers/scsi/scsi_debug.c > @@ -311,12 +311,47 @@ static void sdebug_max_tgts_luns(void); > static struct device pseudo_primary; > static struct bus_type pseudo_lld_bus; > > +static void get_data_transfer_info(unsigned char *cmd, > + unsigned long long *lba, unsigned int *num) > +{ > + int i; > + > + switch (*cmd) { > + case WRITE_16: > + case READ_16: > + for (*lba = 0, i = 0; i < 8; ++i) { > + if (i > 0) > + *lba <<= 8; > + *lba += cmd[2 + i]; > + } > + *num = cmd[13] + (cmd[12] << 8) + > + (cmd[11] << 16) + (cmd[10] << 24); > + break; > + case WRITE_12: > + case READ_12: > + *lba = cmd[5] + (cmd[4] << 8) + (cmd[3] << 16) + (cmd[2] << 24); > + *num = cmd[9] + (cmd[8] << 8) + (cmd[7] << 16) + (cmd[6] << 24); > + break; > + case WRITE_10: > + case READ_10: > + *lba = cmd[5] + (cmd[4] << 8) + (cmd[3] << 16) + (cmd[2] << 24); > + *num = cmd[8] + (cmd[7] << 8); > + break; > + case WRITE_6: > + case READ_6: > + *lba = cmd[3] + (cmd[2] << 8) + ((cmd[1] & 0x1f) << 16); > + *num = (0 == cmd[4]) ? 256 : cmd[4]; > + break; > + default: > + break; > + } > +} > > static > int scsi_debug_queuecommand(struct scsi_cmnd * SCpnt, done_funct_t done) > { > unsigned char *cmd = (unsigned char *) SCpnt->cmnd; > - int len, k, j; > + int len, k; > unsigned int num; > unsigned long long lba; > int errsts = 0; > @@ -452,28 +487,7 @@ int scsi_debug_queuecommand(struct scsi_cmnd * SCpnt, done_funct_t done) > break; > if (scsi_debug_fake_rw) > break; > - if ((*cmd) == READ_16) { > - for (lba = 0, j = 0; j < 8; ++j) { > - if (j > 0) > - lba <<= 8; > - lba += cmd[2 + j]; > - } > - num = cmd[13] + (cmd[12] << 8) + > - (cmd[11] << 16) + (cmd[10] << 24); > - } else if ((*cmd) == READ_12) { > - lba = cmd[5] + (cmd[4] << 8) + > - (cmd[3] << 16) + (cmd[2] << 24); > - num = cmd[9] + (cmd[8] << 8) + > - (cmd[7] << 16) + (cmd[6] << 24); > - } else if ((*cmd) == READ_10) { > - lba = cmd[5] + (cmd[4] << 8) + > - (cmd[3] << 16) + (cmd[2] << 24); > - num = cmd[8] + (cmd[7] << 8); > - } else { /* READ (6) */ > - lba = cmd[3] + (cmd[2] << 8) + > - ((cmd[1] & 0x1f) << 16); > - num = (0 == cmd[4]) ? 256 : cmd[4]; > - } > + get_data_transfer_info(cmd, &lba, &num); > errsts = resp_read(SCpnt, lba, num, devip); > if (inj_recovered && (0 == errsts)) { > mk_sense_buffer(devip, RECOVERED_ERROR, > @@ -500,28 +514,7 @@ int scsi_debug_queuecommand(struct scsi_cmnd * SCpnt, done_funct_t done) > break; > if (scsi_debug_fake_rw) > break; > - if ((*cmd) == WRITE_16) { > - for (lba = 0, j = 0; j < 8; ++j) { > - if (j > 0) > - lba <<= 8; > - lba += cmd[2 + j]; > - } > - num = cmd[13] + (cmd[12] << 8) + > - (cmd[11] << 16) + (cmd[10] << 24); > - } else if ((*cmd) == WRITE_12) { > - lba = cmd[5] + (cmd[4] << 8) + > - (cmd[3] << 16) + (cmd[2] << 24); > - num = cmd[9] + (cmd[8] << 8) + > - (cmd[7] << 16) + (cmd[6] << 24); > - } else if ((*cmd) == WRITE_10) { > - lba = cmd[5] + (cmd[4] << 8) + > - (cmd[3] << 16) + (cmd[2] << 24); > - num = cmd[8] + (cmd[7] << 8); > - } else { /* WRITE (6) */ > - lba = cmd[3] + (cmd[2] << 8) + > - ((cmd[1] & 0x1f) << 16); > - num = (0 == cmd[4]) ? 256 : cmd[4]; > - } > + get_data_transfer_info(cmd, &lba, &num); > errsts = resp_write(SCpnt, lba, num, devip); > if (inj_recovered && (0 == errsts)) { > mk_sense_buffer(devip, RECOVERED_ERROR, Tomo, Thanks. Signed-off-by: Douglas Gilbert <dougg@torque.net> ^ permalink raw reply [flat|nested] 6+ messages in thread
end of thread, other threads:[~2008-01-22 23:12 UTC | newest] Thread overview: 6+ messages (download: mbox.gz follow: Atom feed -- links below jump to the message on this page -- 2008-01-22 16:31 [PATCH 1/3] scsi_debug: add get_data_transfer_info helper function FUJITA Tomonori 2008-01-22 16:32 ` [PATCH 2/3] scsi_debug: add bidi data transfer support FUJITA Tomonori 2008-01-22 23:11 ` Douglas Gilbert 2008-01-22 16:32 ` [PATCH 3/3] scsi_debug: add XDWRITEREAD_10 support FUJITA Tomonori 2008-01-22 23:11 ` Douglas Gilbert 2008-01-22 23:10 ` [PATCH 1/3] scsi_debug: add get_data_transfer_info helper function Douglas Gilbert
This is a public inbox, see mirroring instructions for how to clone and mirror all data and code used for this inbox; as well as URLs for NNTP newsgroup(s).