]> git.ipfire.org Git - thirdparty/samba.git/commitdiff
smb2_server: use sendmsg/recvmsg instead of writev/readv
authorStefan Metzmacher <metze@samba.org>
Mon, 27 Aug 2018 11:02:50 +0000 (13:02 +0200)
committerStefan Metzmacher <metze@samba.org>
Thu, 6 Feb 2020 14:57:42 +0000 (14:57 +0000)
This avoids a few function calls inside the kernel
in order to reach sock_sendmsg() quicker:

    entry_SYSCALL_64_after_hwframe
       do_syscall_64
          __x64_sys_writev
             do_writev
                vfs_writev
                   do_iter_write
                      do_iter_readv_writev
                         sock_write_iter
                            sock_sendmsg

    entry_SYSCALL_64_after_hwframe
       do_syscall_64
          __x64_sys_sendmsg
             __sys_sendmsg
                ___sys_sendmsg
                   sock_sendmsg

As a side effect it will be useful for SMB-Direct invalidation
messages via msg->msg_control and CMSG_*.

Signed-off-by: Stefan Metzmacher <metze@samba.org>
Reviewed-by: Andreas Schneider <asn@samba.org>
source3/smbd/smb2_server.c

index 8c66d74c8de0ca2f5256747897e45bd9fad6c9d3..a4372bf114576d561457ef9efae4ea37c7de3b44 100644 (file)
@@ -3758,6 +3758,7 @@ 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;
                bool ok;
+               struct msghdr msg;
 
                if (e->sendfile_header != NULL) {
                        size_t size = 0;
@@ -3806,7 +3807,12 @@ static NTSTATUS smbd_smb2_flush_send_queue(struct smbXsrv_connection *xconn)
                        continue;
                }
 
-               ret = writev(xconn->transport.sock, e->vector, e->count);
+               msg = (struct msghdr) {
+                       .msg_iov = e->vector,
+                       .msg_iovlen = e->count,
+               };
+
+               ret = sendmsg(xconn->transport.sock, &msg, 0);
                if (ret == 0) {
                        /* propagate end of file */
                        return NT_STATUS_INTERNAL_ERROR;
@@ -3862,6 +3868,7 @@ static NTSTATUS smbd_smb2_io_handler(struct smbXsrv_connection *xconn,
        bool retry;
        NTSTATUS status;
        NTTIME now;
+       struct msghdr msg;
 
        if (!NT_STATUS_IS_OK(xconn->transport.status)) {
                /*
@@ -3896,7 +3903,12 @@ again:
                state->vector.iov_len = NBT_HDR_SIZE;
        }
 
-       ret = readv(xconn->transport.sock, &state->vector, 1);
+       msg = (struct msghdr) {
+               .msg_iov = &state->vector,
+               .msg_iovlen = 1,
+       };
+
+       ret = recvmsg(xconn->transport.sock, &msg, 0);
        if (ret == 0) {
                /* propagate end of file */
                return NT_STATUS_END_OF_FILE;