summaryrefslogtreecommitdiffstats
path: root/drivers/scsi/libiscsi.c
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/scsi/libiscsi.c')
-rw-r--r--drivers/scsi/libiscsi.c26
1 files changed, 25 insertions, 1 deletions
diff --git a/drivers/scsi/libiscsi.c b/drivers/scsi/libiscsi.c
index 07c08ce68d70..894b1e3ebd56 100644
--- a/drivers/scsi/libiscsi.c
+++ b/drivers/scsi/libiscsi.c
@@ -561,8 +561,12 @@ static void iscsi_complete_task(struct iscsi_task *task, int state)
561 WARN_ON_ONCE(task->state == ISCSI_TASK_FREE); 561 WARN_ON_ONCE(task->state == ISCSI_TASK_FREE);
562 task->state = state; 562 task->state = state;
563 563
564 if (!list_empty(&task->running)) 564 spin_lock_bh(&conn->taskqueuelock);
565 if (!list_empty(&task->running)) {
566 pr_debug_once("%s while task on list", __func__);
565 list_del_init(&task->running); 567 list_del_init(&task->running);
568 }
569 spin_unlock_bh(&conn->taskqueuelock);
566 570
567 if (conn->task == task) 571 if (conn->task == task)
568 conn->task = NULL; 572 conn->task = NULL;
@@ -784,7 +788,9 @@ __iscsi_conn_send_pdu(struct iscsi_conn *conn, struct iscsi_hdr *hdr,
784 if (session->tt->xmit_task(task)) 788 if (session->tt->xmit_task(task))
785 goto free_task; 789 goto free_task;
786 } else { 790 } else {
791 spin_lock_bh(&conn->taskqueuelock);
787 list_add_tail(&task->running, &conn->mgmtqueue); 792 list_add_tail(&task->running, &conn->mgmtqueue);
793 spin_unlock_bh(&conn->taskqueuelock);
788 iscsi_conn_queue_work(conn); 794 iscsi_conn_queue_work(conn);
789 } 795 }
790 796
@@ -1475,8 +1481,10 @@ void iscsi_requeue_task(struct iscsi_task *task)
1475 * this may be on the requeue list already if the xmit_task callout 1481 * this may be on the requeue list already if the xmit_task callout
1476 * is handling the r2ts while we are adding new ones 1482 * is handling the r2ts while we are adding new ones
1477 */ 1483 */
1484 spin_lock_bh(&conn->taskqueuelock);
1478 if (list_empty(&task->running)) 1485 if (list_empty(&task->running))
1479 list_add_tail(&task->running, &conn->requeue); 1486 list_add_tail(&task->running, &conn->requeue);
1487 spin_unlock_bh(&conn->taskqueuelock);
1480 iscsi_conn_queue_work(conn); 1488 iscsi_conn_queue_work(conn);
1481} 1489}
1482EXPORT_SYMBOL_GPL(iscsi_requeue_task); 1490EXPORT_SYMBOL_GPL(iscsi_requeue_task);
@@ -1513,22 +1521,26 @@ static int iscsi_data_xmit(struct iscsi_conn *conn)
1513 * only have one nop-out as a ping from us and targets should not 1521 * only have one nop-out as a ping from us and targets should not
1514 * overflow us with nop-ins 1522 * overflow us with nop-ins
1515 */ 1523 */
1524 spin_lock_bh(&conn->taskqueuelock);
1516check_mgmt: 1525check_mgmt:
1517 while (!list_empty(&conn->mgmtqueue)) { 1526 while (!list_empty(&conn->mgmtqueue)) {
1518 conn->task = list_entry(conn->mgmtqueue.next, 1527 conn->task = list_entry(conn->mgmtqueue.next,
1519 struct iscsi_task, running); 1528 struct iscsi_task, running);
1520 list_del_init(&conn->task->running); 1529 list_del_init(&conn->task->running);
1530 spin_unlock_bh(&conn->taskqueuelock);
1521 if (iscsi_prep_mgmt_task(conn, conn->task)) { 1531 if (iscsi_prep_mgmt_task(conn, conn->task)) {
1522 /* regular RX path uses back_lock */ 1532 /* regular RX path uses back_lock */
1523 spin_lock_bh(&conn->session->back_lock); 1533 spin_lock_bh(&conn->session->back_lock);
1524 __iscsi_put_task(conn->task); 1534 __iscsi_put_task(conn->task);
1525 spin_unlock_bh(&conn->session->back_lock); 1535 spin_unlock_bh(&conn->session->back_lock);
1526 conn->task = NULL; 1536 conn->task = NULL;
1537 spin_lock_bh(&conn->taskqueuelock);
1527 continue; 1538 continue;
1528 } 1539 }
1529 rc = iscsi_xmit_task(conn); 1540 rc = iscsi_xmit_task(conn);
1530 if (rc) 1541 if (rc)
1531 goto done; 1542 goto done;
1543 spin_lock_bh(&conn->taskqueuelock);
1532 } 1544 }
1533 1545
1534 /* process pending command queue */ 1546 /* process pending command queue */
@@ -1536,19 +1548,24 @@ check_mgmt:
1536 conn->task = list_entry(conn->cmdqueue.next, struct iscsi_task, 1548 conn->task = list_entry(conn->cmdqueue.next, struct iscsi_task,
1537 running); 1549 running);
1538 list_del_init(&conn->task->running); 1550 list_del_init(&conn->task->running);
1551 spin_unlock_bh(&conn->taskqueuelock);
1539 if (conn->session->state == ISCSI_STATE_LOGGING_OUT) { 1552 if (conn->session->state == ISCSI_STATE_LOGGING_OUT) {
1540 fail_scsi_task(conn->task, DID_IMM_RETRY); 1553 fail_scsi_task(conn->task, DID_IMM_RETRY);
1554 spin_lock_bh(&conn->taskqueuelock);
1541 continue; 1555 continue;
1542 } 1556 }
1543 rc = iscsi_prep_scsi_cmd_pdu(conn->task); 1557 rc = iscsi_prep_scsi_cmd_pdu(conn->task);
1544 if (rc) { 1558 if (rc) {
1545 if (rc == -ENOMEM || rc == -EACCES) { 1559 if (rc == -ENOMEM || rc == -EACCES) {
1560 spin_lock_bh(&conn->taskqueuelock);
1546 list_add_tail(&conn->task->running, 1561 list_add_tail(&conn->task->running,
1547 &conn->cmdqueue); 1562 &conn->cmdqueue);
1548 conn->task = NULL; 1563 conn->task = NULL;
1564 spin_unlock_bh(&conn->taskqueuelock);
1549 goto done; 1565 goto done;
1550 } else 1566 } else
1551 fail_scsi_task(conn->task, DID_ABORT); 1567 fail_scsi_task(conn->task, DID_ABORT);
1568 spin_lock_bh(&conn->taskqueuelock);
1552 continue; 1569 continue;
1553 } 1570 }
1554 rc = iscsi_xmit_task(conn); 1571 rc = iscsi_xmit_task(conn);
@@ -1559,6 +1576,7 @@ check_mgmt:
1559 * we need to check the mgmt queue for nops that need to 1576 * we need to check the mgmt queue for nops that need to
1560 * be sent to aviod starvation 1577 * be sent to aviod starvation
1561 */ 1578 */
1579 spin_lock_bh(&conn->taskqueuelock);
1562 if (!list_empty(&conn->mgmtqueue)) 1580 if (!list_empty(&conn->mgmtqueue))
1563 goto check_mgmt; 1581 goto check_mgmt;
1564 } 1582 }
@@ -1578,12 +1596,15 @@ check_mgmt:
1578 conn->task = task; 1596 conn->task = task;
1579 list_del_init(&conn->task->running); 1597 list_del_init(&conn->task->running);
1580 conn->task->state = ISCSI_TASK_RUNNING; 1598 conn->task->state = ISCSI_TASK_RUNNING;
1599 spin_unlock_bh(&conn->taskqueuelock);
1581 rc = iscsi_xmit_task(conn); 1600 rc = iscsi_xmit_task(conn);
1582 if (rc) 1601 if (rc)
1583 goto done; 1602 goto done;
1603 spin_lock_bh(&conn->taskqueuelock);
1584 if (!list_empty(&conn->mgmtqueue)) 1604 if (!list_empty(&conn->mgmtqueue))
1585 goto check_mgmt; 1605 goto check_mgmt;
1586 } 1606 }
1607 spin_unlock_bh(&conn->taskqueuelock);
1587 spin_unlock_bh(&conn->session->frwd_lock); 1608 spin_unlock_bh(&conn->session->frwd_lock);
1588 return -ENODATA; 1609 return -ENODATA;
1589 1610
@@ -1739,7 +1760,9 @@ int iscsi_queuecommand(struct Scsi_Host *host, struct scsi_cmnd *sc)
1739 goto prepd_reject; 1760 goto prepd_reject;
1740 } 1761 }
1741 } else { 1762 } else {
1763 spin_lock_bh(&conn->taskqueuelock);
1742 list_add_tail(&task->running, &conn->cmdqueue); 1764 list_add_tail(&task->running, &conn->cmdqueue);
1765 spin_unlock_bh(&conn->taskqueuelock);
1743 iscsi_conn_queue_work(conn); 1766 iscsi_conn_queue_work(conn);
1744 } 1767 }
1745 1768
@@ -2897,6 +2920,7 @@ iscsi_conn_setup(struct iscsi_cls_session *cls_session, int dd_size,
2897 INIT_LIST_HEAD(&conn->mgmtqueue); 2920 INIT_LIST_HEAD(&conn->mgmtqueue);
2898 INIT_LIST_HEAD(&conn->cmdqueue); 2921 INIT_LIST_HEAD(&conn->cmdqueue);
2899 INIT_LIST_HEAD(&conn->requeue); 2922 INIT_LIST_HEAD(&conn->requeue);
2923 spin_lock_init(&conn->taskqueuelock);
2900 INIT_WORK(&conn->xmitwork, iscsi_xmitworker); 2924 INIT_WORK(&conn->xmitwork, iscsi_xmitworker);
2901 2925
2902 /* allocate login_task used for the login/text sequences */ 2926 /* allocate login_task used for the login/text sequences */