From: Stefan Metzmacher Date: Wed, 30 Sep 2020 12:01:25 +0000 (+0200) Subject: smb2_server: split out smbd_smb2_advance_send_queue() out of smbd_smb2_flush_send_queue() X-Git-Tag: tevent-0.16.0~715 X-Git-Url: http://git.ipfire.org/cgi-bin/gitweb.cgi?a=commitdiff_plain;h=0ca825c4bc25a7843b8200ea0126fc3320f8724a;p=thirdparty%2Fsamba.git smb2_server: split out smbd_smb2_advance_send_queue() out of smbd_smb2_flush_send_queue() The logic in smbd_smb2_advance_send_queue() will be reused for io_uring. Signed-off-by: Stefan Metzmacher Reviewed-by: Jeremy Allison --- diff --git a/source3/smbd/smb2_server.c b/source3/smbd/smb2_server.c index 767cbbb405b..fa81082aacf 100644 --- a/source3/smbd/smb2_server.c +++ b/source3/smbd/smb2_server.c @@ -4732,6 +4732,39 @@ static int socket_error_from_errno(int ret, return sys_errno; } +static NTSTATUS smbd_smb2_advance_send_queue(struct smbXsrv_connection *xconn, + struct smbd_smb2_send_queue **_e, + size_t n) +{ + struct smbd_smb2_send_queue *e = *_e; + bool ok; + + xconn->ack.unacked_bytes += n; + + ok = iov_advance(&e->vector, &e->count, n); + if (!ok) { + return NT_STATUS_INTERNAL_ERROR; + } + + if (e->count > 0) { + return NT_STATUS_RETRY; + } + + xconn->smb2.send_queue_len--; + DLIST_REMOVE(xconn->smb2.send_queue, e); + + if (e->ack.req == NULL) { + *_e = NULL; + talloc_free(e->mem_ctx); + return NT_STATUS_OK; + } + + e->ack.required_acked_bytes = xconn->ack.unacked_bytes; + DLIST_ADD_END(xconn->ack.queue, e); + + return NT_STATUS_OK; +} + static NTSTATUS smbd_smb2_flush_send_queue(struct smbXsrv_connection *xconn) { int ret; @@ -4747,7 +4780,6 @@ static NTSTATUS smbd_smb2_flush_send_queue(struct smbXsrv_connection *xconn) while (xconn->smb2.send_queue != NULL) { struct smbd_smb2_send_queue *e = xconn->smb2.send_queue; unsigned sendmsg_flags = 0; - bool ok; struct msghdr msg; if (!NT_STATUS_IS_OK(xconn->transport.status)) { @@ -4845,29 +4877,17 @@ static NTSTATUS smbd_smb2_flush_send_queue(struct smbXsrv_connection *xconn) return status; } - xconn->ack.unacked_bytes += ret; - - ok = iov_advance(&e->vector, &e->count, ret); - if (!ok) { - return NT_STATUS_INTERNAL_ERROR; - } - - if (e->count > 0) { - /* we have more to write */ + status = smbd_smb2_advance_send_queue(xconn, &e, ret); + if (NT_STATUS_EQUAL(status, NT_STATUS_RETRY)) { + /* retry later */ TEVENT_FD_WRITEABLE(xconn->transport.fde); return NT_STATUS_OK; } - - xconn->smb2.send_queue_len--; - DLIST_REMOVE(xconn->smb2.send_queue, e); - - if (e->ack.req == NULL) { - talloc_free(e->mem_ctx); - continue; + if (!NT_STATUS_IS_OK(status)) { + smbXsrv_connection_disconnect_transport(xconn, + status); + return status; } - - e->ack.required_acked_bytes = xconn->ack.unacked_bytes; - DLIST_ADD_END(xconn->ack.queue, e); } /*