summaryrefslogtreecommitdiffstats
path: root/source3
diff options
context:
space:
mode:
authorDavid Disseldorp <ddiss@samba.org>2015-02-09 18:21:59 +0100
committerJeremy Allison <jra@samba.org>2015-03-09 21:27:07 +0100
commit12c0b6bf4055b0466d0a2962d5ac34ac60357de3 (patch)
treec9a8bed2fc463020192cd9191ea7cf615a9e0ebd /source3
parent3787119eb8d85d122badb22b3bcc15ed5c32765d (diff)
downloadsamba-12c0b6bf4055b0466d0a2962d5ac34ac60357de3.tar.gz
samba-12c0b6bf4055b0466d0a2962d5ac34ac60357de3.tar.xz
samba-12c0b6bf4055b0466d0a2962d5ac34ac60357de3.zip
s3/vfs: change fallocate mode flags from enum->uint32_t
The Linux fallocate syscall offers a mode parameter which can take the following flags: FALLOC_FL_KEEP_SIZE FALLOC_FL_PUNCH_HOLE (since 2.6.38) FALLOC_FL_COLLAPSE_RANGE (since 3.15) FALLOC_FL_ZERO_RANGE (since 3.14) The flags are not exclusive, e.g. FALLOC_FL_PUNCH_HOLE must be specified alongside FALLOC_FL_KEEP_SIZE. Samba currently takes a vfs_fallocate_mode enum parameter for the VFS fallocate hook, taking either an EXTEND_SIZE or KEEP_SIZE value. This commit changes the fallocate hook such that it accepts a uint32_t flags parameter, in preparation for PUNCH_HOLE and ZERO_RANGE support. Signed-off-by: David Disseldorp <ddiss@samba.org> Reviewed-by: Jeremy Allison <jra@samba.org>
Diffstat (limited to 'source3')
-rw-r--r--source3/include/proto.h2
-rw-r--r--source3/include/vfs.h16
-rw-r--r--source3/lib/system.c21
-rw-r--r--source3/modules/vfs_ceph.c3
-rw-r--r--source3/modules/vfs_default.c13
-rw-r--r--source3/modules/vfs_fruit.c2
-rw-r--r--source3/modules/vfs_full_audit.c2
-rw-r--r--source3/modules/vfs_glusterfs.c3
-rw-r--r--source3/modules/vfs_gpfs.c7
-rw-r--r--source3/modules/vfs_streams_xattr.c2
-rw-r--r--source3/modules/vfs_time_audit.c2
-rw-r--r--source3/smbd/vfs.c14
12 files changed, 43 insertions, 44 deletions
diff --git a/source3/include/proto.h b/source3/include/proto.h
index 64bce03d72..c66283b906 100644
--- a/source3/include/proto.h
+++ b/source3/include/proto.h
@@ -255,7 +255,7 @@ int sys_fstat(int fd, SMB_STRUCT_STAT *sbuf,
int sys_lstat(const char *fname,SMB_STRUCT_STAT *sbuf,
bool fake_dir_create_times);
int sys_posix_fallocate(int fd, off_t offset, off_t len);
-int sys_fallocate(int fd, enum vfs_fallocate_mode mode, off_t offset, off_t len);
+int sys_fallocate(int fd, uint32_t mode, off_t offset, off_t len);
void kernel_flock(int fd, uint32 share_mode, uint32 access_mask);
DIR *sys_fdopendir(int fd);
int sys_mknod(const char *path, mode_t mode, SMB_DEV_T dev);
diff --git a/source3/include/vfs.h b/source3/include/vfs.h
index 13143c2e8d..3d0b82b508 100644
--- a/source3/include/vfs.h
+++ b/source3/include/vfs.h
@@ -163,6 +163,7 @@
/* Version 32 - Add in and out create context blobs to create_file */
/* Version 32 - Remove unnecessary SMB_VFS_DISK_FREE() small_query parameter */
/* Bump to version 33 - Samba 4.3 will ship with that. */
+/* Version 33 - change fallocate mode flags param from enum->uint32_t */
#define SMB_VFS_INTERFACE_VERSION 33
@@ -487,9 +488,8 @@ enum vfs_translate_direction {
vfs_translate_to_windows
};
-enum vfs_fallocate_mode {
- VFS_FALLOCATE_EXTEND_SIZE = 0,
- VFS_FALLOCATE_KEEP_SIZE = 1
+enum vfs_fallocate_flags {
+ VFS_FALLOCATE_FL_KEEP_SIZE = 0x0001,
};
/*
@@ -609,7 +609,7 @@ struct vfs_fn_pointers {
int (*ftruncate_fn)(struct vfs_handle_struct *handle, struct files_struct *fsp, off_t offset);
int (*fallocate_fn)(struct vfs_handle_struct *handle,
struct files_struct *fsp,
- enum vfs_fallocate_mode mode,
+ uint32_t mode,
off_t offset,
off_t len);
bool (*lock_fn)(struct vfs_handle_struct *handle, struct files_struct *fsp, int op, off_t offset, off_t count, int type);
@@ -1050,10 +1050,10 @@ int smb_vfs_call_ntimes(struct vfs_handle_struct *handle,
int smb_vfs_call_ftruncate(struct vfs_handle_struct *handle,
struct files_struct *fsp, off_t offset);
int smb_vfs_call_fallocate(struct vfs_handle_struct *handle,
- struct files_struct *fsp,
- enum vfs_fallocate_mode mode,
- off_t offset,
- off_t len);
+ struct files_struct *fsp,
+ uint32_t mode,
+ off_t offset,
+ off_t len);
bool smb_vfs_call_lock(struct vfs_handle_struct *handle,
struct files_struct *fsp, int op, off_t offset,
off_t count, int type);
diff --git a/source3/lib/system.c b/source3/lib/system.c
index 4f3e214a54..fca5855ec3 100644
--- a/source3/lib/system.c
+++ b/source3/lib/system.c
@@ -478,18 +478,19 @@ int sys_posix_fallocate(int fd, off_t offset, off_t len)
#include <linux/falloc.h>
#endif
-int sys_fallocate(int fd, enum vfs_fallocate_mode mode, off_t offset, off_t len)
+int sys_fallocate(int fd, uint32_t mode, off_t offset, off_t len)
{
#if defined(HAVE_LINUX_FALLOCATE)
- int lmode;
- switch (mode) {
- case VFS_FALLOCATE_EXTEND_SIZE:
- lmode = 0;
- break;
- case VFS_FALLOCATE_KEEP_SIZE:
- lmode = FALLOC_FL_KEEP_SIZE;
- break;
- default:
+ int lmode = 0;
+
+ if (mode & VFS_FALLOCATE_FL_KEEP_SIZE) {
+ lmode |= FALLOC_FL_KEEP_SIZE;
+ mode &= ~VFS_FALLOCATE_FL_KEEP_SIZE;
+ }
+
+ if (mode != 0) {
+ DEBUG(2, ("unmapped fallocate flags: %lx\n",
+ (unsigned long)mode));
errno = EINVAL;
return -1;
}
diff --git a/source3/modules/vfs_ceph.c b/source3/modules/vfs_ceph.c
index 096742863c..d53a2de338 100644
--- a/source3/modules/vfs_ceph.c
+++ b/source3/modules/vfs_ceph.c
@@ -796,8 +796,7 @@ static int strict_allocate_ftruncate(struct vfs_handle_struct *handle, files_str
emulation is being done by the libc (like on AIX with JFS1). In that
case we do our own emulation. fallocate implementations can
return ENOTSUP or EINVAL in cases like that. */
- ret = SMB_VFS_FALLOCATE(fsp, VFS_FALLOCATE_EXTEND_SIZE,
- pst->st_ex_size, space_to_write);
+ ret = SMB_VFS_FALLOCATE(fsp, 0, pst->st_ex_size, space_to_write);
if (ret == -1 && errno == ENOSPC) {
return -1;
}
diff --git a/source3/modules/vfs_default.c b/source3/modules/vfs_default.c
index 31648f69fe..fdb90e4109 100644
--- a/source3/modules/vfs_default.c
+++ b/source3/modules/vfs_default.c
@@ -1861,8 +1861,7 @@ static int strict_allocate_ftruncate(vfs_handle_struct *handle, files_struct *fs
emulation is being done by the libc (like on AIX with JFS1). In that
case we do our own emulation. fallocate implementations can
return ENOTSUP or EINVAL in cases like that. */
- ret = SMB_VFS_FALLOCATE(fsp, VFS_FALLOCATE_EXTEND_SIZE,
- pst->st_ex_size, space_to_write);
+ ret = SMB_VFS_FALLOCATE(fsp, 0, pst->st_ex_size, space_to_write);
if (ret == -1 && errno == ENOSPC) {
return -1;
}
@@ -1962,14 +1961,14 @@ static int vfswrap_ftruncate(vfs_handle_struct *handle, files_struct *fsp, off_t
static int vfswrap_fallocate(vfs_handle_struct *handle,
files_struct *fsp,
- enum vfs_fallocate_mode mode,
+ uint32_t mode,
off_t offset,
off_t len)
{
int result;
START_PROFILE(syscall_fallocate);
- if (mode == VFS_FALLOCATE_EXTEND_SIZE) {
+ if (mode == 0) {
result = sys_posix_fallocate(fsp->fh->fd, offset, len);
/*
* posix_fallocate returns 0 on success, errno on error
@@ -1980,11 +1979,9 @@ static int vfswrap_fallocate(vfs_handle_struct *handle,
errno = result;
result = -1;
}
- } else if (mode == VFS_FALLOCATE_KEEP_SIZE) {
- result = sys_fallocate(fsp->fh->fd, mode, offset, len);
} else {
- errno = EINVAL;
- result = -1;
+ /* sys_fallocate handles filtering of unsupported mode flags */
+ result = sys_fallocate(fsp->fh->fd, mode, offset, len);
}
END_PROFILE(syscall_fallocate);
return result;
diff --git a/source3/modules/vfs_fruit.c b/source3/modules/vfs_fruit.c
index 0445e04cf0..fbee3217a8 100644
--- a/source3/modules/vfs_fruit.c
+++ b/source3/modules/vfs_fruit.c
@@ -3039,7 +3039,7 @@ exit:
static int fruit_fallocate(struct vfs_handle_struct *handle,
struct files_struct *fsp,
- enum vfs_fallocate_mode mode,
+ uint32_t mode,
off_t offset,
off_t len)
{
diff --git a/source3/modules/vfs_full_audit.c b/source3/modules/vfs_full_audit.c
index b7a4eeeeb4..87a2f9c3bc 100644
--- a/source3/modules/vfs_full_audit.c
+++ b/source3/modules/vfs_full_audit.c
@@ -1452,7 +1452,7 @@ static int smb_full_audit_ftruncate(vfs_handle_struct *handle, files_struct *fsp
}
static int smb_full_audit_fallocate(vfs_handle_struct *handle, files_struct *fsp,
- enum vfs_fallocate_mode mode,
+ uint32_t mode,
off_t offset,
off_t len)
{
diff --git a/source3/modules/vfs_glusterfs.c b/source3/modules/vfs_glusterfs.c
index 09c789c790..2c7266e27b 100644
--- a/source3/modules/vfs_glusterfs.c
+++ b/source3/modules/vfs_glusterfs.c
@@ -927,9 +927,10 @@ static int vfs_gluster_ftruncate(struct vfs_handle_struct *handle,
static int vfs_gluster_fallocate(struct vfs_handle_struct *handle,
struct files_struct *fsp,
- enum vfs_fallocate_mode mode,
+ uint32_t mode,
off_t offset, off_t len)
{
+ /* TODO: add support using glfs_fallocate() and glfs_zerofill() */
errno = ENOTSUP;
return -1;
}
diff --git a/source3/modules/vfs_gpfs.c b/source3/modules/vfs_gpfs.c
index 21707c5f6c..999e83b16a 100644
--- a/source3/modules/vfs_gpfs.c
+++ b/source3/modules/vfs_gpfs.c
@@ -1843,7 +1843,7 @@ static int vfs_gpfs_ntimes(struct vfs_handle_struct *handle,
}
static int vfs_gpfs_fallocate(struct vfs_handle_struct *handle,
- struct files_struct *fsp, enum vfs_fallocate_mode mode,
+ struct files_struct *fsp, uint32_t mode,
off_t offset, off_t len)
{
int ret;
@@ -1859,8 +1859,9 @@ static int vfs_gpfs_fallocate(struct vfs_handle_struct *handle,
return -1;
}
- if (mode == VFS_FALLOCATE_KEEP_SIZE) {
- DEBUG(10, ("Unsupported VFS_FALLOCATE_KEEP_SIZE\n"));
+ if (mode != 0) {
+ DEBUG(10, ("unmapped fallocate flags: %lx\n",
+ (unsigned long)mode));
errno = ENOTSUP;
return -1;
}
diff --git a/source3/modules/vfs_streams_xattr.c b/source3/modules/vfs_streams_xattr.c
index b3c1df15c3..52a9059d80 100644
--- a/source3/modules/vfs_streams_xattr.c
+++ b/source3/modules/vfs_streams_xattr.c
@@ -1093,7 +1093,7 @@ static int streams_xattr_ftruncate(struct vfs_handle_struct *handle,
static int streams_xattr_fallocate(struct vfs_handle_struct *handle,
struct files_struct *fsp,
- enum vfs_fallocate_mode mode,
+ uint32_t mode,
off_t offset,
off_t len)
{
diff --git a/source3/modules/vfs_time_audit.c b/source3/modules/vfs_time_audit.c
index 04552ec9d0..45e30acfd1 100644
--- a/source3/modules/vfs_time_audit.c
+++ b/source3/modules/vfs_time_audit.c
@@ -1209,7 +1209,7 @@ static int smb_time_audit_ftruncate(vfs_handle_struct *handle,
static int smb_time_audit_fallocate(vfs_handle_struct *handle,
files_struct *fsp,
- enum vfs_fallocate_mode mode,
+ uint32_t mode,
off_t offset,
off_t len)
{
diff --git a/source3/smbd/vfs.c b/source3/smbd/vfs.c
index 381bb8d2af..1e20963da1 100644
--- a/source3/smbd/vfs.c
+++ b/source3/smbd/vfs.c
@@ -573,7 +573,8 @@ int vfs_allocate_file_space(files_struct *fsp, uint64_t len)
if (lp_strict_allocate(SNUM(fsp->conn))) {
/* See if we have a syscall that will allocate beyond
end-of-file without changing EOF. */
- ret = SMB_VFS_FALLOCATE(fsp, VFS_FALLOCATE_KEEP_SIZE, 0, len);
+ ret = SMB_VFS_FALLOCATE(fsp, VFS_FALLOCATE_FL_KEEP_SIZE,
+ 0, len);
} else {
ret = 0;
}
@@ -728,8 +729,7 @@ int vfs_fill_sparse(files_struct *fsp, off_t len)
* emulation is being done by the libc (like on AIX with JFS1). In that
* case we do our own emulation. fallocate implementations can
* return ENOTSUP or EINVAL in cases like that. */
- ret = SMB_VFS_FALLOCATE(fsp, VFS_FALLOCATE_EXTEND_SIZE,
- offset, num_to_write);
+ ret = SMB_VFS_FALLOCATE(fsp, 0, offset, num_to_write);
if (ret == -1 && errno == ENOSPC) {
goto out;
}
@@ -2023,10 +2023,10 @@ int smb_vfs_call_ftruncate(struct vfs_handle_struct *handle,
}
int smb_vfs_call_fallocate(struct vfs_handle_struct *handle,
- struct files_struct *fsp,
- enum vfs_fallocate_mode mode,
- off_t offset,
- off_t len)
+ struct files_struct *fsp,
+ uint32_t mode,
+ off_t offset,
+ off_t len)
{
VFS_FIND(fallocate);
return handle->fns->fallocate_fn(handle, fsp, mode, offset, len);