The branch, master has been updated
       via  2b0ff09 Replace lseek()/write()/lseek() triple with pwrite call. We 
already emulate this inside pwrite under the covers.
       via  24ca7bc posix_fallocate() returns an errno, not -1 on error.
       via  b8d7de3 Merge the two conflicting allocation codes into one 
function, vfs_slow_fallocate() and use that from both the truncate and 
fill_sparse functions.
      from  1f1491d Oops. Missed adding vfswrap_posix_fallocate to 
vfs_default_fns table.

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


- Log -----------------------------------------------------------------
commit 2b0ff09982bcf961b830dc44e5a658e1cf31bfc1
Author: Jeremy Allison <[email protected]>
Date:   Thu Dec 2 17:52:11 2010 -0800

    Replace lseek()/write()/lseek() triple with pwrite call. We already emulate 
this
    inside pwrite under the covers.
    
    Jeremy.
    
    Autobuild-User: Jeremy Allison <[email protected]>
    Autobuild-Date: Fri Dec  3 03:39:42 CET 2010 on sn-devel-104

commit 24ca7bcb604a1a5de6a074fd3ad1dfab4e58b34d
Author: Jeremy Allison <[email protected]>
Date:   Thu Dec 2 17:46:30 2010 -0800

    posix_fallocate() returns an errno, not -1 on error.

commit b8d7de319980f9efade92dd0721ed02efcb7e48d
Author: Jeremy Allison <[email protected]>
Date:   Thu Dec 2 17:26:00 2010 -0800

    Merge the two conflicting allocation codes into one function, 
vfs_slow_fallocate()
    and use that from both the truncate and fill_sparse functions.
    
    Jeremy.

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

Summary of changes:
 source3/include/proto.h             |    1 +
 source3/modules/vfs_default.c       |   40 +++---------------
 source3/modules/vfs_streams_xattr.c |    2 +-
 source3/smbd/vfs.c                  |   79 ++++++++++++++++++++---------------
 4 files changed, 53 insertions(+), 69 deletions(-)


Changeset truncated at 500 lines:

diff --git a/source3/include/proto.h b/source3/include/proto.h
index 85a7294..19c693b 100644
--- a/source3/include/proto.h
+++ b/source3/include/proto.h
@@ -5562,6 +5562,7 @@ ssize_t vfs_pwrite_data(struct smb_request *req,
                        SMB_OFF_T offset);
 int vfs_allocate_file_space(files_struct *fsp, uint64_t len);
 int vfs_set_filelen(files_struct *fsp, SMB_OFF_T len);
+int vfs_slow_fallocate(files_struct *fsp, SMB_OFF_T offset, SMB_OFF_T len);
 int vfs_fill_sparse(files_struct *fsp, SMB_OFF_T len);
 SMB_OFF_T vfs_transfer_file(files_struct *in, files_struct *out, SMB_OFF_T n);
 const char *vfs_readdirname(connection_struct *conn, void *p,
diff --git a/source3/modules/vfs_default.c b/source3/modules/vfs_default.c
index 0ec5b66..648aa34 100644
--- a/source3/modules/vfs_default.c
+++ b/source3/modules/vfs_default.c
@@ -822,16 +822,11 @@ static int vfswrap_ntimes(vfs_handle_struct *handle,
 static int strict_allocate_ftruncate(vfs_handle_struct *handle, files_struct 
*fsp, SMB_OFF_T len)
 {
        SMB_STRUCT_STAT st;
-       SMB_OFF_T currpos = SMB_VFS_LSEEK(fsp, 0, SEEK_CUR);
-       unsigned char zero_space[4096];
        SMB_OFF_T space_to_write;
        uint64_t space_avail;
        uint64_t bsize,dfree,dsize;
        int ret;
 
-       if (currpos == -1)
-               return -1;
-
        if (SMB_VFS_FSTAT(fsp, &st) == -1)
                return -1;
 
@@ -877,25 +872,12 @@ static int strict_allocate_ftruncate(vfs_handle_struct 
*handle, files_struct *fs
        }
 
        /* Write out the real space on disk. */
-       if (SMB_VFS_LSEEK(fsp, st.st_ex_size, SEEK_SET) != st.st_ex_size)
-               return -1;
-
-       memset(zero_space, '\0', sizeof(zero_space));
-       while ( space_to_write > 0) {
-               SMB_OFF_T retlen;
-               SMB_OFF_T current_len_to_write = 
MIN(sizeof(zero_space),space_to_write);
-
-               retlen = SMB_VFS_WRITE(fsp,(char 
*)zero_space,current_len_to_write);
-               if (retlen <= 0)
-                       return -1;
-
-               space_to_write -= retlen;
+       ret = vfs_slow_fallocate(fsp, st.st_ex_size, space_to_write);
+       if (ret != 0) {
+               errno = ret;
+               ret = -1;
        }
 
-       /* Seek to where we were */
-       if (SMB_VFS_LSEEK(fsp, currpos, SEEK_SET) != currpos)
-               return -1;
-
        return 0;
 }
 
@@ -904,7 +886,6 @@ static int vfswrap_ftruncate(vfs_handle_struct *handle, 
files_struct *fsp, SMB_O
        int result = -1;
        SMB_STRUCT_STAT st;
        char c = 0;
-       SMB_OFF_T currpos;
 
        START_PROFILE(syscall_ftruncate);
 
@@ -927,10 +908,6 @@ static int vfswrap_ftruncate(vfs_handle_struct *handle, 
files_struct *fsp, SMB_O
        /* According to W. R. Stevens advanced UNIX prog. Pure 4.3 BSD cannot
           extend a file with ftruncate. Provide alternate implementation
           for this */
-       currpos = SMB_VFS_LSEEK(fsp, 0, SEEK_CUR);
-       if (currpos == -1) {
-               goto done;
-       }
 
        /* Do an fstat to see if the file is longer than the requested
           size in which case the ftruncate above should have
@@ -957,15 +934,10 @@ static int vfswrap_ftruncate(vfs_handle_struct *handle, 
files_struct *fsp, SMB_O
                goto done;
        }
 
-       if (SMB_VFS_LSEEK(fsp, len-1, SEEK_SET) != len -1)
-               goto done;
-
-       if (SMB_VFS_WRITE(fsp, &c, 1)!=1)
+       if (SMB_VFS_PWRITE(fsp, &c, 1, len-1)!=1) {
                goto done;
+       }
 
-       /* Seek to where we were */
-       if (SMB_VFS_LSEEK(fsp, currpos, SEEK_SET) != currpos)
-               goto done;
        result = 0;
 
   done:
diff --git a/source3/modules/vfs_streams_xattr.c 
b/source3/modules/vfs_streams_xattr.c
index 8870c6e..819f33d 100644
--- a/source3/modules/vfs_streams_xattr.c
+++ b/source3/modules/vfs_streams_xattr.c
@@ -1040,7 +1040,7 @@ static int streams_xattr_posix_fallocate(struct 
vfs_handle_struct *handle,
        }
 
        if (!streams_xattr_recheck(sio)) {
-               return -1;
+               return errno;
        }
 
        /* Let the pwrite code path handle it. */
diff --git a/source3/smbd/vfs.c b/source3/smbd/vfs.c
index 1829e3a..a35142e 100644
--- a/source3/smbd/vfs.c
+++ b/source3/smbd/vfs.c
@@ -558,22 +558,56 @@ int vfs_set_filelen(files_struct *fsp, SMB_OFF_T len)
 }
 
 /****************************************************************************
+ A slow version of posix_fallocate. Fallback code if SMB_VFS_POSIX_FALLOCATE
+ fails. Needs to be outside of the default version of SMB_VFS_POSIX_FALLOCATE
+ as this is also called from the default SMB_VFS_FTRUNCATE code.
+ Returns 0 on success, errno on failure.
+****************************************************************************/
+
+#define SPARSE_BUF_WRITE_SIZE (32*1024)
+
+int vfs_slow_fallocate(files_struct *fsp, SMB_OFF_T offset, SMB_OFF_T len)
+{
+       ssize_t pwrite_ret;
+       size_t total = 0;
+
+       if (!sparse_buf) {
+               sparse_buf = SMB_CALLOC_ARRAY(char, SPARSE_BUF_WRITE_SIZE);
+               if (!sparse_buf) {
+                       errno = ENOMEM;
+                       return ENOMEM;
+               }
+       }
+
+       while (total < len) {
+               size_t curr_write_size = MIN(SPARSE_BUF_WRITE_SIZE, (len - 
total));
+
+               pwrite_ret = SMB_VFS_PWRITE(fsp, sparse_buf, curr_write_size, 
offset + total);
+               if (pwrite_ret == -1) {
+                       DEBUG(10,("vfs_slow_fallocate: SMB_VFS_PWRITE for file "
+                                 "%s failed with error %s\n",
+                                 fsp_str_dbg(fsp), strerror(errno)));
+                       return errno;
+               }
+               total += pwrite_ret;
+       }
+
+       return 0;
+}
+
+/****************************************************************************
  A vfs fill sparse call.
  Writes zeros from the end of file to len, if len is greater than EOF.
  Used only by strict_sync.
  Returns 0 on success, -1 on failure.
 ****************************************************************************/
 
-#define SPARSE_BUF_WRITE_SIZE (32*1024)
-
 int vfs_fill_sparse(files_struct *fsp, SMB_OFF_T len)
 {
        int ret;
        SMB_STRUCT_STAT st;
        SMB_OFF_T offset;
-       size_t total;
        size_t num_to_write;
-       ssize_t pwrite_ret;
 
        ret = SMB_VFS_FSTAT(fsp, &st);
        if (ret == -1) {
@@ -616,47 +650,24 @@ int vfs_fill_sparse(files_struct *fsp, SMB_OFF_T len)
                        goto out;
                }
                if (ret == 0) {
-                       set_filelen_write_cache(fsp, len);
                        goto out;
                }
                DEBUG(10,("vfs_fill_sparse: SMB_VFS_POSIX_FALLOCATE failed with 
"
                        "error %d. Falling back to slow manual allocation\n", 
ret));
        }
 
-       if (!sparse_buf) {
-               sparse_buf = SMB_CALLOC_ARRAY(char, SPARSE_BUF_WRITE_SIZE);
-               if (!sparse_buf) {
-                       errno = ENOMEM;
-                       ret = -1;
-                       goto out;
-               }
+       ret = vfs_slow_fallocate(fsp, offset, num_to_write);
+       if (ret != 0) {
+               errno = ret;
+               ret = -1;
        }
 
-       total = 0;
-
-       while (total < num_to_write) {
-               size_t curr_write_size = MIN(SPARSE_BUF_WRITE_SIZE, 
(num_to_write - total));
-
-               pwrite_ret = SMB_VFS_PWRITE(fsp, sparse_buf, curr_write_size, 
offset + total);
-               if (pwrite_ret == -1) {
-                       DEBUG(10,("vfs_fill_sparse: SMB_VFS_PWRITE for file "
-                                 "%s failed with error %s\n",
-                                 fsp_str_dbg(fsp), strerror(errno)));
-                       ret = -1;
-                       goto out;
-               }
-               if (pwrite_ret == 0) {
-                       ret = 0;
-                       goto out;
-               }
+ out:
 
-               total += pwrite_ret;
+       if (ret == 0) {
+               set_filelen_write_cache(fsp, len);
        }
 
-       set_filelen_write_cache(fsp, len);
-
-       ret = 0;
- out:
        contend_level2_oplocks_end(fsp, LEVEL2_CONTEND_FILL_SPARSE);
        return ret;
 }


-- 
Samba Shared Repository

Reply via email to