[SCSI] iscsi_tcp: hold lock during data rsp processing
iscsi_data_rsp needs to hold the sesison lock when it calls iscsi_update_cmdsn. Signed-off-by: Mike Christie <michaelc@cs.wisc.edu> Signed-off-by: James Bottomley <James.Bottomley@HansenPartnership.com>
This commit is contained in:
parent
66bbe0ce11
commit
4545a88fc1
1 changed files with 6 additions and 8 deletions
|
@ -641,13 +641,11 @@ iscsi_r2t_rsp(struct iscsi_conn *conn, struct iscsi_cmd_task *ctask)
|
||||||
}
|
}
|
||||||
|
|
||||||
/* fill-in new R2T associated with the task */
|
/* fill-in new R2T associated with the task */
|
||||||
spin_lock(&session->lock);
|
|
||||||
iscsi_update_cmdsn(session, (struct iscsi_nopin*)rhdr);
|
iscsi_update_cmdsn(session, (struct iscsi_nopin*)rhdr);
|
||||||
|
|
||||||
if (!ctask->sc || session->state != ISCSI_STATE_LOGGED_IN) {
|
if (!ctask->sc || session->state != ISCSI_STATE_LOGGED_IN) {
|
||||||
printk(KERN_INFO "iscsi_tcp: dropping R2T itt %d in "
|
printk(KERN_INFO "iscsi_tcp: dropping R2T itt %d in "
|
||||||
"recovery...\n", ctask->itt);
|
"recovery...\n", ctask->itt);
|
||||||
spin_unlock(&session->lock);
|
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -660,7 +658,6 @@ iscsi_r2t_rsp(struct iscsi_conn *conn, struct iscsi_cmd_task *ctask)
|
||||||
printk(KERN_ERR "iscsi_tcp: invalid R2T with zero data len\n");
|
printk(KERN_ERR "iscsi_tcp: invalid R2T with zero data len\n");
|
||||||
__kfifo_put(tcp_ctask->r2tpool.queue, (void*)&r2t,
|
__kfifo_put(tcp_ctask->r2tpool.queue, (void*)&r2t,
|
||||||
sizeof(void*));
|
sizeof(void*));
|
||||||
spin_unlock(&session->lock);
|
|
||||||
return ISCSI_ERR_DATALEN;
|
return ISCSI_ERR_DATALEN;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -676,7 +673,6 @@ iscsi_r2t_rsp(struct iscsi_conn *conn, struct iscsi_cmd_task *ctask)
|
||||||
r2t->data_offset, scsi_bufflen(ctask->sc));
|
r2t->data_offset, scsi_bufflen(ctask->sc));
|
||||||
__kfifo_put(tcp_ctask->r2tpool.queue, (void*)&r2t,
|
__kfifo_put(tcp_ctask->r2tpool.queue, (void*)&r2t,
|
||||||
sizeof(void*));
|
sizeof(void*));
|
||||||
spin_unlock(&session->lock);
|
|
||||||
return ISCSI_ERR_DATALEN;
|
return ISCSI_ERR_DATALEN;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -690,8 +686,6 @@ iscsi_r2t_rsp(struct iscsi_conn *conn, struct iscsi_cmd_task *ctask)
|
||||||
conn->r2t_pdus_cnt++;
|
conn->r2t_pdus_cnt++;
|
||||||
|
|
||||||
iscsi_requeue_ctask(ctask);
|
iscsi_requeue_ctask(ctask);
|
||||||
spin_unlock(&session->lock);
|
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -764,7 +758,9 @@ iscsi_tcp_hdr_dissect(struct iscsi_conn *conn, struct iscsi_hdr *hdr)
|
||||||
switch(opcode) {
|
switch(opcode) {
|
||||||
case ISCSI_OP_SCSI_DATA_IN:
|
case ISCSI_OP_SCSI_DATA_IN:
|
||||||
ctask = session->cmds[itt];
|
ctask = session->cmds[itt];
|
||||||
|
spin_lock(&conn->session->lock);
|
||||||
rc = iscsi_data_rsp(conn, ctask);
|
rc = iscsi_data_rsp(conn, ctask);
|
||||||
|
spin_unlock(&conn->session->lock);
|
||||||
if (rc)
|
if (rc)
|
||||||
return rc;
|
return rc;
|
||||||
if (tcp_conn->in.datalen) {
|
if (tcp_conn->in.datalen) {
|
||||||
|
@ -806,9 +802,11 @@ iscsi_tcp_hdr_dissect(struct iscsi_conn *conn, struct iscsi_hdr *hdr)
|
||||||
ctask = session->cmds[itt];
|
ctask = session->cmds[itt];
|
||||||
if (ahslen)
|
if (ahslen)
|
||||||
rc = ISCSI_ERR_AHSLEN;
|
rc = ISCSI_ERR_AHSLEN;
|
||||||
else if (ctask->sc->sc_data_direction == DMA_TO_DEVICE)
|
else if (ctask->sc->sc_data_direction == DMA_TO_DEVICE) {
|
||||||
|
spin_lock(&session->lock);
|
||||||
rc = iscsi_r2t_rsp(conn, ctask);
|
rc = iscsi_r2t_rsp(conn, ctask);
|
||||||
else
|
spin_unlock(&session->lock);
|
||||||
|
} else
|
||||||
rc = ISCSI_ERR_PROTO;
|
rc = ISCSI_ERR_PROTO;
|
||||||
break;
|
break;
|
||||||
case ISCSI_OP_LOGIN_RSP:
|
case ISCSI_OP_LOGIN_RSP:
|
||||||
|
|
Loading…
Reference in a new issue