The branch, master has been updated
       via  e454681 Linux-specific optimization in aio_open code.
       via  a7c63ac Set fsp->initial_allocation_size before calling 
open_file_ntcreate().
       via  775014b Make sure we reset fsp->initial_allocation_size to zero if 
we didn't create the file.
       via  cb40594 Add an optimization to pthread aio writes to also do fsync 
if requested.
      from  622eb59 s3: Make us survive base-delaywrite with aio enabled

http://gitweb.samba.org/?p=samba.git;a=shortlog;h=master


- Log -----------------------------------------------------------------
commit e454681276ffa34984dda56e74d2fda05a24636c
Author: Jeremy Allison <[email protected]>
Date:   Thu Jul 12 10:10:32 2012 -0700

    Linux-specific optimization in aio_open code.
    
    Use initial_allocation_size to allocate on disk if sent. Ignore
    failures (upper level will cope).
    
    Autobuild-User(master): Jeremy Allison <[email protected]>
    Autobuild-Date(master): Fri Jul 13 00:35:48 CEST 2012 on sn-devel-104

commit a7c63ac1b7bc3f9c9a0e8786046644194e270f10
Author: Jeremy Allison <[email protected]>
Date:   Thu Jul 12 10:09:37 2012 -0700

    Set fsp->initial_allocation_size before calling open_file_ntcreate().
    
    Allows an SMB_VFS_OPEN() vfs module to do something interesting with
    the request.

commit 775014bd9cc8717ad5bb2651ca1078833d149610
Author: Jeremy Allison <[email protected]>
Date:   Wed Jul 11 16:35:32 2012 -0700

    Make sure we reset fsp->initial_allocation_size to zero if we didn't create 
the file.
    
    This will become important as we set fsp->initial_allocation_size before
    create.

commit cb405947caa9f4bdb962483860a9093a364ecbf2
Author: Jeremy Allison <[email protected]>
Date:   Thu Jul 12 10:57:47 2012 -0700

    Add an optimization to pthread aio writes to also do fsync if requested.
    
    Should help by ensuring complete writes done in sub-thread, not in
    the main thread.

-----------------------------------------------------------------------

Summary of changes:
 source3/modules/vfs_aio_pthread.c |   37 +++++++++++++++++++++++++++++++++++++
 source3/smbd/aio.c                |    9 +++++++++
 source3/smbd/open.c               |    7 +++++++
 source3/smbd/proto.h              |    1 +
 4 files changed, 54 insertions(+), 0 deletions(-)


Changeset truncated at 500 lines:

diff --git a/source3/modules/vfs_aio_pthread.c 
b/source3/modules/vfs_aio_pthread.c
index d62af57..2c6121d 100644
--- a/source3/modules/vfs_aio_pthread.c
+++ b/source3/modules/vfs_aio_pthread.c
@@ -27,6 +27,9 @@
 #include "smbd/smbd.h"
 #include "smbd/globals.h"
 #include "lib/pthreadpool/pthreadpool.h"
+#ifdef HAVE_LINUX_FALLOC_H
+#include <linux/falloc.h>
+#endif
 
 struct aio_extra;
 static struct pthreadpool *pool;
@@ -40,6 +43,7 @@ struct aio_private_data {
        int ret_errno;
        bool cancelled;
        bool write_command;
+       bool flush_write;
 };
 
 /* List of outstanding requests we have. */
@@ -115,6 +119,14 @@ static void aio_worker(void *private_data)
                                        (const void *)pd->aiocb->aio_buf,
                                        pd->aiocb->aio_nbytes);
                }
+               if (pd->ret_size != -1 && pd->flush_write) {
+                       /*
+                        * Optimization - flush if requested.
+                        * Ignore error as upper layer will
+                        * also do this.
+                        */
+                       (void)fsync(pd->aiocb->aio_fildes);
+               }
        } else {
                pd->ret_size = sys_pread(pd->aiocb->aio_fildes,
                                (void *)pd->aiocb->aio_buf,
@@ -229,6 +241,12 @@ static int aio_pthread_write(struct vfs_handle_struct 
*handle,
        }
 
        pd->write_command = true;
+       if (lp_strict_sync(SNUM(fsp->conn)) &&
+                       (lp_syncalways(SNUM(fsp->conn)) ||
+                               aio_write_through_requested(aio_ex))) {
+               pd->flush_write = true;
+       }
+
 
        ret = pthreadpool_add_job(pool, pd->jobid, aio_worker, (void *)pd);
        if (ret) {
@@ -620,6 +638,7 @@ struct aio_open_private_data {
        char *dname;
        struct smbd_server_connection *sconn;
        const struct security_unix_token *ux_tok;
+       uint64_t initial_allocation_size;
        /* Returns. */
        int ret_fd;
        int ret_errno;
@@ -754,6 +773,23 @@ static void aio_open_worker(void *private_data)
        } else {
                /* Create was successful. */
                opd->ret_errno = 0;
+
+#if defined(HAVE_LINUX_FALLOCATE)
+               /*
+                * See if we can set the initial
+                * allocation size. We don't record
+                * the return for this as it's an
+                * optimization - the upper layer
+                * will also do this for us once
+                * the open returns.
+                */
+               if (opd->initial_allocation_size) {
+                       (void)fallocate(opd->ret_fd,
+                                       FALLOC_FL_KEEP_SIZE,
+                                       0,
+                                       (off_t)opd->initial_allocation_size);
+               }
+#endif
        }
 }
 
@@ -795,6 +831,7 @@ static struct aio_open_private_data 
*create_private_open_data(const files_struct
        opd->mid = fsp->mid;
        opd->in_progress = true;
        opd->sconn = fsp->conn->sconn;
+       opd->initial_allocation_size = fsp->initial_allocation_size;
 
        /* Copy our current credentials. */
        opd->ux_tok = copy_unix_token(opd, get_current_utok(fsp->conn));
diff --git a/source3/smbd/aio.c b/source3/smbd/aio.c
index 0ea5274..569741c 100644
--- a/source3/smbd/aio.c
+++ b/source3/smbd/aio.c
@@ -53,6 +53,15 @@ struct aio_extra {
 };
 
 /****************************************************************************
+ Accessor function to return write_through state.
+*****************************************************************************/
+
+bool aio_write_through_requested(struct aio_extra *aio_ex)
+{
+       return aio_ex->write_through;
+}
+
+/****************************************************************************
  Initialize the signal handler for aio read/write.
 *****************************************************************************/
 
diff --git a/source3/smbd/open.c b/source3/smbd/open.c
index 0f4a588..a445524 100644
--- a/source3/smbd/open.c
+++ b/source3/smbd/open.c
@@ -3643,6 +3643,11 @@ static NTSTATUS create_file_unixpath(connection_struct 
*conn,
                        fsp->base_fsp = base_fsp;
                }
 
+               if (allocation_size) {
+                       fsp->initial_allocation_size = smb_roundup(fsp->conn,
+                                                       allocation_size);
+               }
+
                status = open_file_ntcreate(conn,
                                            req,
                                            access_mask,
@@ -3727,6 +3732,8 @@ static NTSTATUS create_file_unixpath(connection_struct 
*conn,
                        fsp->initial_allocation_size = smb_roundup(
                                fsp->conn, 
(uint64_t)fsp->fsp_name->st.st_ex_size);
                }
+       } else {
+               fsp->initial_allocation_size = 0;
        }
 
        if ((info == FILE_WAS_CREATED) && lp_nt_acl_support(SNUM(conn)) &&
diff --git a/source3/smbd/proto.h b/source3/smbd/proto.h
index 9aaa00a..26d6432 100644
--- a/source3/smbd/proto.h
+++ b/source3/smbd/proto.h
@@ -64,6 +64,7 @@ void srv_set_signing(struct smbd_server_connection *conn,
 
 /* The following definitions come from smbd/aio.c  */
 
+bool aio_write_through_requested(struct aio_extra *aio_ex);
 bool initialize_async_io_handler(void);
 NTSTATUS schedule_aio_read_and_X(connection_struct *conn,
                             struct smb_request *req,


-- 
Samba Shared Repository

Reply via email to