From 39771ce57e3efa8e708fcdedc43459756686759b Mon Sep 17 00:00:00 2001 From: Vishnu Itta Date: Thu, 21 Feb 2019 21:25:18 +0530 Subject: [PATCH] fixes(istgt): leaving recvlowat as 1 to read data at earliest (#231) - log for op_text response - reading immediate flag from correct bit - commented out unused code - Not closing the connection on logout request which will be closed only when client triggers it Signed-off-by: Vitta --- src/istgt_iscsi.c | 63 +++++++++++++++++++++++------------------------ 1 file changed, 31 insertions(+), 32 deletions(-) diff --git a/src/istgt_iscsi.c b/src/istgt_iscsi.c index a516093d..2dd3bf46 100644 --- a/src/istgt_iscsi.c +++ b/src/istgt_iscsi.c @@ -279,11 +279,12 @@ istgt_iscsi_read_pdu(CONN_Ptr conn, ISCSI_PDU_Ptr pdu) iovec[0].iov_len = 4 * pdu->total_ahs_len; /* Header Digest */ - iovec[1].iov_base = pdu->header_digest; if (conn->header_digest) { + iovec[1].iov_base = pdu->header_digest; iovec[1].iov_len = ISCSI_DIGEST_LEN; total += ISCSI_DIGEST_LEN; } else { + iovec[1].iov_base = NULL; iovec[1].iov_len = 0; } @@ -313,11 +314,12 @@ istgt_iscsi_read_pdu(CONN_Ptr conn, ISCSI_PDU_Ptr pdu) iovec[2].iov_len = ISCSI_ALIGN(pdu->data_segment_len); /* Data Digest */ - iovec[3].iov_base = pdu->data_digest; if (conn->data_digest && data_len != 0) { + iovec[3].iov_base = pdu->data_digest; iovec[3].iov_len = ISCSI_DIGEST_LEN; total += ISCSI_DIGEST_LEN; } else { + iovec[3].iov_base = NULL; iovec[3].iov_len = 0; } @@ -349,7 +351,7 @@ istgt_iscsi_read_pdu(CONN_Ptr conn, ISCSI_PDU_Ptr pdu) for (i = 0; i < 4; i++) { if (iovec[i].iov_len != 0 && iovec[i].iov_len > (size_t)rc) { iovec[i].iov_base - = (void *) (((uintptr_t)iovec[i].iov_base) + rc); + = (void *) (((char *)iovec[i].iov_base) + rc); iovec[i].iov_len -= rc; break; } else { @@ -680,8 +682,8 @@ istgt_iscsi_write_pdu_internal(CONN_Ptr conn, ISCSI_PDU_Ptr pdu, ISTGT_LU_CMD_Pt rc = writev(conn->sock, &iovec[0], 5); if (rc < 0) { now = time(NULL); - ISTGT_ERRLOG("writev() failed (errno=%d,%s,time=%f) for opcode:0x%2.2x CSN:0x%x\n", - errno, conn->initiator_name, difftime(now, start), lu_cmd->cdb0, lu_cmd->CmdSN); + ISTGT_ERRLOG("writev() failed (errno=%d,%s,time=%f) for opcode:%d cdb:0x%2.2x CSN:0x%x\n", + errno, conn->initiator_name, difftime(now, start), opcode, lu_cmd->cdb0, lu_cmd->CmdSN); return (-1); } nbytes -= rc; @@ -2508,6 +2510,8 @@ istgt_iscsi_op_text(CONN_Ptr conn, ISCSI_PDU_Ptr pdu) uint32_t sMaxCmdSN = 0; uint32_t cStatSN = 0; int step = 0; + int8_t sendtargets_discovery = 0; + if (!conn->full_feature) { ISTGT_ERRLOG("before Full Feature\n"); return (-1); @@ -2519,7 +2523,7 @@ istgt_iscsi_op_text(CONN_Ptr conn, ISCSI_PDU_Ptr pdu) memset(data, 0, alloc_len); cp = (uint8_t *) &pdu->bhs; - I_bit = BGET8(&cp[0], 7); + I_bit = BGET8(&cp[0], 6); F_bit = BGET8(&cp[1], 7); C_bit = BGET8(&cp[1], 6); @@ -2623,6 +2627,7 @@ istgt_iscsi_op_text(CONN_Ptr conn, ISCSI_PDU_Ptr pdu) conn->initiator_name, conn->initiator_addr, val, data, alloc_len, data_len); + sendtargets_discovery = 1; SESS_MTX_LOCK(conn); } else { if (strcasecmp(val, "ALL") == 0) { @@ -2635,6 +2640,7 @@ istgt_iscsi_op_text(CONN_Ptr conn, ISCSI_PDU_Ptr pdu) conn->initiator_name, conn->initiator_addr, val, data, alloc_len, data_len); + sendtargets_discovery = 2; SESS_MTX_LOCK(conn); } } @@ -2689,6 +2695,8 @@ istgt_iscsi_op_text(CONN_Ptr conn, ISCSI_PDU_Ptr pdu) return (-1); } + ISTGT_NOTICELOG("queued op_text response: %s", (sendtargets_discovery == 1) ? "sendtargets_discovery" : + ((sendtargets_discovery == 2) ? "sendtargets_nondiscovery" : "")); /* update internal variables */ istgt_iscsi_copy_param2var(conn); /* check value */ @@ -5343,7 +5351,7 @@ wait_all_task(CONN_Ptr conn) conn->id, conn->running_tasks); } - +#if 0 static void snd_cleanup(void *arg) { @@ -5428,6 +5436,7 @@ worker_cleanup(void *arg) MTX_UNLOCK(&g_conns_mutex); ISTGT_TRACELOG(ISTGT_TRACE_DEBUG, "cancel cleanup UNLOCK\n"); } +#endif const char lu_task_typ[4][12] = { "RESPONSE", @@ -5724,7 +5733,7 @@ sender(void *arg) pthread_set_name_np(slf, tinfo); #endif - pthread_cleanup_push(snd_cleanup, (void *)conn); +// pthread_cleanup_push(snd_cleanup, (void *)conn); memset(&abstime, 0, sizeof (abstime)); /* handle DATA-IN/SCSI status */ ISTGT_TRACELOG(ISTGT_TRACE_DEBUG, "sender loop start (%d)\n", conn->id); @@ -5882,7 +5891,7 @@ sender(void *arg) // MTX_UNLOCK(&conn->wpdu_mutex); } // MTX_UNLOCK(&conn->sender_mutex); - pthread_cleanup_pop(0); +// pthread_cleanup_pop(0); ISTGT_NOTICELOG("sender loop ended (%d:%d:%d)\n", conn->id, conn->epfd, ntohs(conn->iport)); return (NULL); } @@ -5929,22 +5938,21 @@ worker(void *arg) // #endif events.data.fd = conn->sock; - events.events = EPOLLIN; - rc = epoll_ctl(epfd, EPOLL_CTL_ADD, conn->sock, &events); - if (rc == -1) { + events.events = EPOLLIN; + rc = epoll_ctl(epfd, EPOLL_CTL_ADD, conn->sock, &events); + if (rc == -1) { ISTGT_ERRLOG("epoll_ctl() failed\n"); close(epfd); return (NULL); - } + } events.data.fd = conn->task_pipe[0]; - events.events = EPOLLIN; - rc = epoll_ctl(epfd, EPOLL_CTL_ADD, conn->task_pipe[0], &events); - if (rc == -1) { + events.events = EPOLLIN; + rc = epoll_ctl(epfd, EPOLL_CTL_ADD, conn->task_pipe[0], &events); + if (rc == -1) { ISTGT_ERRLOG("epoll_ctl() failed\n"); close(epfd); return (NULL); - } - + } // TODO // if (!conn->istgt->daemon) { @@ -6019,7 +6027,7 @@ worker(void *arg) conn->exec_lu_task = NULL; lu_task = NULL; - pthread_cleanup_push(worker_cleanup, conn); +// pthread_cleanup_push(worker_cleanup, conn); pthread_setcancelstate(PTHREAD_CANCEL_ENABLE, NULL); /* create sender thread */ @@ -6097,13 +6105,14 @@ worker(void *arg) if ((events.events & EPOLLERR) || (events.events & EPOLLHUP) || (!(events.events & EPOLLIN))) { - ISTGT_ERRLOG("close conn %d\n", errno); + ISTGT_ERRLOG("close conn events %d\n", events.events); break; } rc = istgt_iscsi_read_pdu(conn, &conn->pdu); if (rc < 0) { if (errno == EAGAIN) { + ISTGT_ERRLOG("close conn %d %d\n", errno, events.events); break; } if (conn->state != CONN_STATE_EXITING) { @@ -6111,8 +6120,8 @@ worker(void *arg) } if (conn->state != CONN_STATE_RUNNING) { if (errno == EINPROGRESS) { - sleep(1); - continue; + ISTGT_ERRLOG("iscsi_read_pdu shouldn't get EINPROGRESS"); + break; } if (errno == ECONNRESET || errno == ETIMEDOUT) { @@ -6139,7 +6148,6 @@ worker(void *arg) break; } else if (rc == 1) { // means successful logout ISCSI_OP_LOGOUT ISTGT_TRACELOG(ISTGT_TRACE_ISCSI, "logout received\n"); - break; } if (conn->pdu.ahs != NULL) { @@ -6273,7 +6281,6 @@ worker(void *arg) cleanup_exit: ; - pthread_cleanup_pop(0); conn->state = CONN_STATE_EXITING; if (conn->sess != NULL) { lu = conn->sess->lu; @@ -6480,14 +6487,6 @@ istgt_create_conn(ISTGT_Ptr istgt, PORTAL_Ptr portal, int sock, struct sockaddr ISTGT_ERRLOG("istgt_set_sendtimeo() failed\n"); goto error_return; } -#if defined(ISTGT_USE_IOVEC) - /* set low water mark */ - rc = istgt_set_recvlowat(conn->sock, ISCSI_BHS_LEN); - if (rc != 0) { - ISTGT_ERRLOG("istgt_set_recvlowat() failed\n"); - goto error_return; - } -#endif rc = pipe(conn->task_pipe); if (rc != 0) {