mirror of
https://github.com/SCST-project/scst.git
synced 2026-05-14 01:01:27 +00:00
Custom parse improvements
git-svn-id: http://svn.code.sf.net/p/scst/svn/trunk@3281 d57e44dd-8a1f-0410-8b47-8ef2f437770f
This commit is contained in:
@@ -850,6 +850,7 @@ struct scst_user_scsi_cmd_reply_parse
|
||||
uint32_t op_flags;
|
||||
int32_t data_len;
|
||||
int32_t bufflen;
|
||||
int32_t out_bufflen;
|
||||
},
|
||||
|
||||
where:
|
||||
@@ -857,7 +858,7 @@ where:
|
||||
- queue_type - SCSI task attribute (queue type). NOTE! In current
|
||||
implementation setting changing this field from the provided value
|
||||
affects commands execution only when then produced by iSCSI-SCST
|
||||
target. With al other target drivers, this field is ignored. This is
|
||||
target. With all other target drivers, this field is ignored. This is
|
||||
because for them commands queueing is set before parse() called.
|
||||
|
||||
- data_direction - command's data flow direction, one of SCST_DATA_*
|
||||
@@ -866,11 +867,17 @@ where:
|
||||
- cdb_len - length of CDB
|
||||
|
||||
- op_flags - commands flags, one or more scst_cdb_flags bits, see above.
|
||||
At least SCST_INFO_VALID must be set for correct processing.
|
||||
SCST_IMPLICIT_HQ not implemented (yet) for single stage init target
|
||||
drivers (all, except iSCSI), because custom parse can reorder
|
||||
commands due to multithreaded processing.
|
||||
|
||||
- data_len - command's data length
|
||||
|
||||
- bufflen - command's buffer length
|
||||
|
||||
- out_bufflen - command's out buffer length (for bidirectional commands)
|
||||
|
||||
|
||||
struct scst_user_scsi_cmd_reply_alloc_mem
|
||||
{
|
||||
|
||||
@@ -227,6 +227,7 @@ struct scst_user_scsi_cmd_reply_parse {
|
||||
uint32_t op_flags;
|
||||
int32_t data_len;
|
||||
int32_t bufflen;
|
||||
int32_t out_bufflen;
|
||||
};
|
||||
struct {
|
||||
uint8_t sense_len;
|
||||
|
||||
@@ -1272,12 +1272,16 @@ static int dev_user_process_reply_parse(struct scst_user_cmd *ucmd,
|
||||
(preply->bufflen == 0)))
|
||||
goto out_inval;
|
||||
|
||||
if (unlikely((preply->bufflen < 0) || (preply->data_len < 0)))
|
||||
if (unlikely((preply->bufflen < 0) || (preply->out_bufflen < 0) ||
|
||||
(preply->data_len < 0)))
|
||||
goto out_inval;
|
||||
|
||||
if (unlikely(preply->cdb_len > cmd->cdb_len))
|
||||
goto out_inval;
|
||||
|
||||
if (!(preply->op_flags & SCST_INFO_VALID))
|
||||
goto out_inval;
|
||||
|
||||
TRACE_DBG("ucmd %p, queue_type %x, data_direction, %x, bufflen %d, "
|
||||
"data_len %d, pbuf %llx, cdb_len %d, op_flags %x", ucmd,
|
||||
preply->queue_type, preply->data_direction, preply->bufflen,
|
||||
@@ -1287,11 +1291,11 @@ static int dev_user_process_reply_parse(struct scst_user_cmd *ucmd,
|
||||
cmd->queue_type = preply->queue_type;
|
||||
cmd->data_direction = preply->data_direction;
|
||||
cmd->bufflen = preply->bufflen;
|
||||
cmd->out_bufflen = preply->out_bufflen;
|
||||
cmd->data_len = preply->data_len;
|
||||
if (preply->cdb_len > 0)
|
||||
cmd->cdb_len = preply->cdb_len;
|
||||
if (preply->op_flags & SCST_INFO_VALID)
|
||||
cmd->op_flags = preply->op_flags;
|
||||
cmd->op_flags = preply->op_flags;
|
||||
|
||||
out_process:
|
||||
scst_post_parse(cmd);
|
||||
|
||||
@@ -3845,8 +3845,15 @@ static int __scst_init_cmd(struct scst_cmd *cmd)
|
||||
if (unlikely(failure))
|
||||
goto out_busy;
|
||||
|
||||
if (unlikely(scst_pre_parse(cmd) != 0))
|
||||
goto out;
|
||||
/*
|
||||
* SCST_IMPLICIT_HQ for unknown commands not implemented for
|
||||
* case when set_sn_on_restart_cmd not set, because custom parse
|
||||
* can reorder commands due to multithreaded processing. To
|
||||
* implement it we need to implement all unknown commands as
|
||||
* ORDERED in the beginning and post parse reprocess of
|
||||
* queue_type to change it if needed. ToDo.
|
||||
*/
|
||||
scst_pre_parse(cmd);
|
||||
|
||||
if (!cmd->set_sn_on_restart_cmd)
|
||||
scst_cmd_set_sn(cmd);
|
||||
|
||||
@@ -192,8 +192,18 @@ static int do_parse(struct vdisk_cmd *vcmd)
|
||||
reply->data_direction = cmd->expected_data_direction;
|
||||
reply->data_len = cmd->expected_transfer_len;
|
||||
reply->bufflen = cmd->expected_transfer_len;
|
||||
reply->out_bufflen = cmd->expected_out_transfer_len;
|
||||
reply->cdb_len = cmd->cdb_len;
|
||||
reply->op_flags = reply->op_flags;
|
||||
|
||||
if (cmd->op_flags & SCST_INFO_VALID)
|
||||
reply->op_flags = cmd->op_flags;
|
||||
else {
|
||||
TRACE_DBG_SPECIAL("Extra parse (op %x)", cmd->cdb[0]);
|
||||
|
||||
if (reply->data_direction & SCST_DATA_WRITE)
|
||||
reply->op_flags |= SCST_WRITE_MEDIUM;
|
||||
reply->op_flags |= SCST_INFO_VALID;
|
||||
}
|
||||
|
||||
out:
|
||||
TRACE_EXIT_RES(res);
|
||||
|
||||
Reference in New Issue
Block a user