Commit fbc514b4e262bc0596faae8640ebc0b9142a1cdd
Committed by
James Bottomley
1 parent
3e5c28ad03
Exists in
master
and in
7 other branches
[SCSI] iscsi_tcp: convert iscsi_tcp to support merged tasks
Convert iscsi_tcp to support merged tasks. Signed-off-by: Mike Christie <michaelc@cs.wisc.edu> Signed-off-by: James Bottomley <James.Bottomley@HansenPartnership.com>
Showing 2 changed files with 54 additions and 81 deletions Side-by-side Diff
drivers/scsi/iscsi_tcp.c
... | ... | @@ -498,11 +498,15 @@ |
498 | 498 | * must be called with session lock |
499 | 499 | */ |
500 | 500 | static void |
501 | -iscsi_tcp_cleanup_ctask(struct iscsi_conn *conn, struct iscsi_cmd_task *ctask) | |
501 | +iscsi_tcp_cleanup_task(struct iscsi_conn *conn, struct iscsi_cmd_task *ctask) | |
502 | 502 | { |
503 | 503 | struct iscsi_tcp_cmd_task *tcp_ctask = ctask->dd_data; |
504 | 504 | struct iscsi_r2t_info *r2t; |
505 | 505 | |
506 | + /* nothing to do for mgmt ctasks */ | |
507 | + if (!ctask->sc) | |
508 | + return; | |
509 | + | |
506 | 510 | /* flush ctask's r2t queues */ |
507 | 511 | while (__kfifo_get(tcp_ctask->r2tqueue, (void*)&r2t, sizeof(void*))) { |
508 | 512 | __kfifo_put(tcp_ctask->r2tpool.queue, (void*)&r2t, |
... | ... | @@ -521,7 +525,7 @@ |
521 | 525 | /** |
522 | 526 | * iscsi_data_rsp - SCSI Data-In Response processing |
523 | 527 | * @conn: iscsi connection |
524 | - * @ctask: scsi command task | |
528 | + * @ctask: scsi command ctask | |
525 | 529 | **/ |
526 | 530 | static int |
527 | 531 | iscsi_data_rsp(struct iscsi_conn *conn, struct iscsi_cmd_task *ctask) |
... | ... | @@ -578,7 +582,7 @@ |
578 | 582 | /** |
579 | 583 | * iscsi_solicit_data_init - initialize first Data-Out |
580 | 584 | * @conn: iscsi connection |
581 | - * @ctask: scsi command task | |
585 | + * @ctask: scsi command ctask | |
582 | 586 | * @r2t: R2T info |
583 | 587 | * |
584 | 588 | * Notes: |
... | ... | @@ -620,7 +624,7 @@ |
620 | 624 | /** |
621 | 625 | * iscsi_r2t_rsp - iSCSI R2T Response processing |
622 | 626 | * @conn: iscsi connection |
623 | - * @ctask: scsi command task | |
627 | + * @ctask: scsi command ctask | |
624 | 628 | **/ |
625 | 629 | static int |
626 | 630 | iscsi_r2t_rsp(struct iscsi_conn *conn, struct iscsi_cmd_task *ctask) |
... | ... | @@ -646,7 +650,7 @@ |
646 | 650 | return ISCSI_ERR_R2TSN; |
647 | 651 | } |
648 | 652 | |
649 | - /* fill-in new R2T associated with the task */ | |
653 | + /* fill-in new R2T associated with the ctask */ | |
650 | 654 | iscsi_update_cmdsn(session, (struct iscsi_nopin*)rhdr); |
651 | 655 | |
652 | 656 | if (!ctask->sc || session->state != ISCSI_STATE_LOGGED_IN) { |
... | ... | @@ -769,6 +773,8 @@ |
769 | 773 | ctask = iscsi_itt_to_ctask(conn, hdr->itt); |
770 | 774 | if (!ctask) |
771 | 775 | return ISCSI_ERR_BAD_ITT; |
776 | + if (!ctask->sc) | |
777 | + return ISCSI_ERR_NO_SCSI_CMD; | |
772 | 778 | |
773 | 779 | spin_lock(&conn->session->lock); |
774 | 780 | rc = iscsi_data_rsp(conn, ctask); |
... | ... | @@ -815,6 +821,8 @@ |
815 | 821 | ctask = iscsi_itt_to_ctask(conn, hdr->itt); |
816 | 822 | if (!ctask) |
817 | 823 | return ISCSI_ERR_BAD_ITT; |
824 | + if (!ctask->sc) | |
825 | + return ISCSI_ERR_NO_SCSI_CMD; | |
818 | 826 | |
819 | 827 | if (ahslen) |
820 | 828 | rc = ISCSI_ERR_AHSLEN; |
... | ... | @@ -1194,7 +1202,7 @@ |
1194 | 1202 | |
1195 | 1203 | /* If header digest is enabled, compute the CRC and |
1196 | 1204 | * place the digest into the same buffer. We make |
1197 | - * sure that both iscsi_tcp_ctask and mtask have | |
1205 | + * sure that both iscsi_tcp_cmd_task and mctask have | |
1198 | 1206 | * sufficient room. |
1199 | 1207 | */ |
1200 | 1208 | if (conn->hdrdgst_en) { |
... | ... | @@ -1269,7 +1277,7 @@ |
1269 | 1277 | /** |
1270 | 1278 | * iscsi_solicit_data_cont - initialize next Data-Out |
1271 | 1279 | * @conn: iscsi connection |
1272 | - * @ctask: scsi command task | |
1280 | + * @ctask: scsi command ctask | |
1273 | 1281 | * @r2t: R2T info |
1274 | 1282 | * @left: bytes left to transfer |
1275 | 1283 | * |
1276 | 1284 | |
1277 | 1285 | |
1278 | 1286 | |
... | ... | @@ -1316,19 +1324,37 @@ |
1316 | 1324 | } |
1317 | 1325 | |
1318 | 1326 | /** |
1319 | - * iscsi_tcp_ctask - Initialize iSCSI SCSI_READ or SCSI_WRITE commands | |
1327 | + * iscsi_tcp_task - Initialize iSCSI SCSI_READ or SCSI_WRITE commands | |
1320 | 1328 | * @conn: iscsi connection |
1321 | - * @ctask: scsi command task | |
1329 | + * @ctask: scsi command ctask | |
1322 | 1330 | * @sc: scsi command |
1323 | 1331 | **/ |
1324 | 1332 | static int |
1325 | -iscsi_tcp_ctask_init(struct iscsi_cmd_task *ctask) | |
1333 | +iscsi_tcp_task_init(struct iscsi_cmd_task *ctask) | |
1326 | 1334 | { |
1327 | 1335 | struct iscsi_tcp_cmd_task *tcp_ctask = ctask->dd_data; |
1328 | 1336 | struct iscsi_conn *conn = ctask->conn; |
1329 | 1337 | struct scsi_cmnd *sc = ctask->sc; |
1330 | 1338 | int err; |
1331 | 1339 | |
1340 | + if (!sc) { | |
1341 | + /* | |
1342 | + * mgmt ctasks do not have a scatterlist since they come | |
1343 | + * in from the iscsi interface. | |
1344 | + */ | |
1345 | + debug_scsi("mctask deq [cid %d itt 0x%x]\n", conn->id, | |
1346 | + ctask->itt); | |
1347 | + | |
1348 | + /* Prepare PDU, optionally w/ immediate data */ | |
1349 | + iscsi_tcp_send_hdr_prep(conn, ctask->hdr, sizeof(*ctask->hdr)); | |
1350 | + | |
1351 | + /* If we have immediate data, attach a payload */ | |
1352 | + if (ctask->data_count) | |
1353 | + iscsi_tcp_send_linear_data_prepare(conn, ctask->data, | |
1354 | + ctask->data_count); | |
1355 | + return 0; | |
1356 | + } | |
1357 | + | |
1332 | 1358 | BUG_ON(__kfifo_len(tcp_ctask->r2tqueue)); |
1333 | 1359 | tcp_ctask->sent = 0; |
1334 | 1360 | tcp_ctask->exp_datasn = 0; |
1335 | 1361 | |
1336 | 1362 | |
1337 | 1363 | |
1338 | 1364 | |
... | ... | @@ -1353,52 +1379,21 @@ |
1353 | 1379 | return 0; |
1354 | 1380 | } |
1355 | 1381 | |
1356 | -/** | |
1357 | - * iscsi_tcp_mtask_xmit - xmit management(immediate) task | |
1358 | - * @conn: iscsi connection | |
1359 | - * @mtask: task management task | |
1360 | - * | |
1361 | - * Notes: | |
1362 | - * The function can return -EAGAIN in which case caller must | |
1363 | - * call it again later, or recover. '0' return code means successful | |
1364 | - * xmit. | |
1365 | - **/ | |
1366 | -static int | |
1367 | -iscsi_tcp_mtask_xmit(struct iscsi_conn *conn, struct iscsi_mgmt_task *mtask) | |
1368 | -{ | |
1369 | - int rc; | |
1370 | - | |
1371 | - /* Flush any pending data first. */ | |
1372 | - rc = iscsi_tcp_flush(conn); | |
1373 | - if (rc < 0) | |
1374 | - return rc; | |
1375 | - | |
1376 | - if (mtask->hdr->itt == RESERVED_ITT) { | |
1377 | - struct iscsi_session *session = conn->session; | |
1378 | - | |
1379 | - spin_lock_bh(&session->lock); | |
1380 | - iscsi_free_mgmt_task(conn, mtask); | |
1381 | - spin_unlock_bh(&session->lock); | |
1382 | - } | |
1383 | - | |
1384 | - return 0; | |
1385 | -} | |
1386 | - | |
1387 | 1382 | /* |
1388 | - * iscsi_tcp_ctask_xmit - xmit normal PDU task | |
1389 | - * @conn: iscsi connection | |
1390 | - * @ctask: iscsi command task | |
1383 | + * iscsi_tcp_task_xmit - xmit normal PDU ctask | |
1384 | + * @ctask: iscsi command ctask | |
1391 | 1385 | * |
1392 | 1386 | * We're expected to return 0 when everything was transmitted succesfully, |
1393 | 1387 | * -EAGAIN if there's still data in the queue, or != 0 for any other kind |
1394 | 1388 | * of error. |
1395 | 1389 | */ |
1396 | 1390 | static int |
1397 | -iscsi_tcp_ctask_xmit(struct iscsi_conn *conn, struct iscsi_cmd_task *ctask) | |
1391 | +iscsi_tcp_task_xmit(struct iscsi_cmd_task *ctask) | |
1398 | 1392 | { |
1393 | + struct iscsi_conn *conn = ctask->conn; | |
1399 | 1394 | struct iscsi_tcp_cmd_task *tcp_ctask = ctask->dd_data; |
1400 | 1395 | struct scsi_cmnd *sc = ctask->sc; |
1401 | - struct scsi_data_buffer *sdb = scsi_out(sc); | |
1396 | + struct scsi_data_buffer *sdb; | |
1402 | 1397 | int rc = 0; |
1403 | 1398 | |
1404 | 1399 | flush: |
1405 | 1400 | |
... | ... | @@ -1407,10 +1402,18 @@ |
1407 | 1402 | if (rc < 0) |
1408 | 1403 | return rc; |
1409 | 1404 | |
1405 | + /* mgmt command */ | |
1406 | + if (!sc) { | |
1407 | + if (ctask->hdr->itt == RESERVED_ITT) | |
1408 | + iscsi_put_ctask(ctask); | |
1409 | + return 0; | |
1410 | + } | |
1411 | + | |
1410 | 1412 | /* Are we done already? */ |
1411 | 1413 | if (sc->sc_data_direction != DMA_TO_DEVICE) |
1412 | 1414 | return 0; |
1413 | 1415 | |
1416 | + sdb = scsi_out(sc); | |
1414 | 1417 | if (ctask->unsol_count != 0) { |
1415 | 1418 | struct iscsi_data *hdr = &tcp_ctask->unsol_dtask.hdr; |
1416 | 1419 | |
... | ... | @@ -1688,21 +1691,6 @@ |
1688 | 1691 | return err; |
1689 | 1692 | } |
1690 | 1693 | |
1691 | -/* called with host lock */ | |
1692 | -static void | |
1693 | -iscsi_tcp_mtask_init(struct iscsi_conn *conn, struct iscsi_mgmt_task *mtask) | |
1694 | -{ | |
1695 | - debug_scsi("mtask deq [cid %d itt 0x%x]\n", conn->id, mtask->itt); | |
1696 | - | |
1697 | - /* Prepare PDU, optionally w/ immediate data */ | |
1698 | - iscsi_tcp_send_hdr_prep(conn, mtask->hdr, sizeof(*mtask->hdr)); | |
1699 | - | |
1700 | - /* If we have immediate data, attach a payload */ | |
1701 | - if (mtask->data_count) | |
1702 | - iscsi_tcp_send_linear_data_prepare(conn, mtask->data, | |
1703 | - mtask->data_count); | |
1704 | -} | |
1705 | - | |
1706 | 1694 | static int |
1707 | 1695 | iscsi_r2tpool_alloc(struct iscsi_session *session) |
1708 | 1696 | { |
... | ... | @@ -1710,7 +1698,7 @@ |
1710 | 1698 | int cmd_i; |
1711 | 1699 | |
1712 | 1700 | /* |
1713 | - * initialize per-task: R2T pool and xmit queue | |
1701 | + * initialize per-ctask: R2T pool and xmit queue | |
1714 | 1702 | */ |
1715 | 1703 | for (cmd_i = 0; cmd_i < session->cmds_max; cmd_i++) { |
1716 | 1704 | struct iscsi_cmd_task *ctask = session->cmds[cmd_i]; |
1717 | 1705 | |
... | ... | @@ -1880,13 +1868,12 @@ |
1880 | 1868 | |
1881 | 1869 | cls_session = iscsi_session_setup(&iscsi_tcp_transport, shost, cmds_max, |
1882 | 1870 | sizeof(struct iscsi_tcp_cmd_task), |
1883 | - sizeof(struct iscsi_tcp_mgmt_task), | |
1884 | 1871 | initial_cmdsn); |
1885 | 1872 | if (!cls_session) |
1886 | 1873 | goto remove_host; |
1887 | 1874 | session = cls_session->dd_data; |
1888 | 1875 | |
1889 | - shost->can_queue = session->cmds_max; | |
1876 | + shost->can_queue = session->scsi_cmds_max; | |
1890 | 1877 | for (cmd_i = 0; cmd_i < session->cmds_max; cmd_i++) { |
1891 | 1878 | struct iscsi_cmd_task *ctask = session->cmds[cmd_i]; |
1892 | 1879 | struct iscsi_tcp_cmd_task *tcp_ctask = ctask->dd_data; |
... | ... | @@ -1895,13 +1882,6 @@ |
1895 | 1882 | ctask->hdr_max = sizeof(tcp_ctask->hdr) - ISCSI_DIGEST_SIZE; |
1896 | 1883 | } |
1897 | 1884 | |
1898 | - for (cmd_i = 0; cmd_i < session->mgmtpool_max; cmd_i++) { | |
1899 | - struct iscsi_mgmt_task *mtask = session->mgmt_cmds[cmd_i]; | |
1900 | - struct iscsi_tcp_mgmt_task *tcp_mtask = mtask->dd_data; | |
1901 | - | |
1902 | - mtask->hdr = (struct iscsi_hdr *) &tcp_mtask->hdr; | |
1903 | - } | |
1904 | - | |
1905 | 1885 | if (iscsi_r2tpool_alloc(session)) |
1906 | 1886 | goto remove_session; |
1907 | 1887 | return cls_session; |
... | ... | @@ -1999,11 +1979,9 @@ |
1999 | 1979 | /* IO */ |
2000 | 1980 | .send_pdu = iscsi_conn_send_pdu, |
2001 | 1981 | .get_stats = iscsi_conn_get_stats, |
2002 | - .init_cmd_task = iscsi_tcp_ctask_init, | |
2003 | - .init_mgmt_task = iscsi_tcp_mtask_init, | |
2004 | - .xmit_cmd_task = iscsi_tcp_ctask_xmit, | |
2005 | - .xmit_mgmt_task = iscsi_tcp_mtask_xmit, | |
2006 | - .cleanup_cmd_task = iscsi_tcp_cleanup_ctask, | |
1982 | + .init_task = iscsi_tcp_task_init, | |
1983 | + .xmit_task = iscsi_tcp_task_xmit, | |
1984 | + .cleanup_task = iscsi_tcp_cleanup_task, | |
2007 | 1985 | /* recovery */ |
2008 | 1986 | .session_recovery_timedout = iscsi_session_recovery_timedout, |
2009 | 1987 | }; |
drivers/scsi/iscsi_tcp.h
... | ... | @@ -103,11 +103,6 @@ |
103 | 103 | char hdrext[ISCSI_DIGEST_SIZE];/* Header-Digest */ |
104 | 104 | }; |
105 | 105 | |
106 | -struct iscsi_tcp_mgmt_task { | |
107 | - struct iscsi_hdr hdr; | |
108 | - char hdrext[ISCSI_DIGEST_SIZE]; /* Header-Digest */ | |
109 | -}; | |
110 | - | |
111 | 106 | struct iscsi_r2t_info { |
112 | 107 | __be32 ttt; /* copied from R2T */ |
113 | 108 | __be32 exp_statsn; /* copied from R2T */ |