From 3cb0e521e1bdddde972b6fd08fb86f7fe73da8d5 Mon Sep 17 00:00:00 2001 From: Tim Prouty Date: Thu, 2 Jul 2009 13:39:20 -0700 Subject: s3: Plumb smb_filename through SMB_VFS_NTIMES --- source3/modules/onefs_streams.c | 37 ++++++++++++++++++++++++--------- source3/modules/vfs_cap.c | 26 ++++++++++++++++++++--- source3/modules/vfs_default.c | 20 ++++++++++++------ source3/modules/vfs_full_audit.c | 8 ++++--- source3/modules/vfs_onefs.c | 5 +++-- source3/modules/vfs_onefs_shadow_copy.c | 9 ++++---- source3/modules/vfs_recycle.c | 11 ++-------- source3/modules/vfs_shadow_copy2.c | 14 +++++++++++-- 8 files changed, 91 insertions(+), 39 deletions(-) (limited to 'source3/modules') diff --git a/source3/modules/onefs_streams.c b/source3/modules/onefs_streams.c index 2a31036862..2be490f52d 100644 --- a/source3/modules/onefs_streams.c +++ b/source3/modules/onefs_streams.c @@ -508,15 +508,15 @@ int onefs_unlink(vfs_handle_struct *handle, return ret; } -int onefs_vtimes_streams(vfs_handle_struct *handle, const char *fname, +int onefs_vtimes_streams(vfs_handle_struct *handle, + const struct smb_filename *smb_fname, int flags, struct timespec times[3]) { + struct smb_filename *smb_fname_onefs = NULL; int ret; - bool is_stream; - char *base; - char *stream; int dirfd; int saved_errno; + NTSTATUS status; START_PROFILE(syscall_ntimes); @@ -524,23 +524,40 @@ int onefs_vtimes_streams(vfs_handle_struct *handle, const char *fname, if (ret) return ret; - if (!is_stream) { - ret = vtimes(fname, times, flags); + if (!is_ntfs_stream_smb_fname(smb_fname)) { + ret = vtimes(smb_fname->base_name, times, flags); return ret; } - dirfd = get_stream_dir_fd(handle->conn, base, NULL); - if (dirfd < -1) { + status = onefs_stream_prep_smb_fname(talloc_tos(), smb_fname, + &smb_fname_onefs); + if (!NT_STATUS_IS_OK(status)) { + errno = map_errno_from_nt_status(status); return -1; } - ret = enc_vtimesat(dirfd, stream, ENC_DEFAULT, times, flags); + /* Default stream (the ::$DATA was just stripped off). */ + if (!is_ntfs_stream_smb_fname(smb_fname_onefs)) { + ret = vtimes(smb_fname_onefs->base_name, times, flags); + goto out; + } + + dirfd = get_stream_dir_fd(handle->conn, smb_fname->base_name, NULL); + if (dirfd < -1) { + ret = -1; + goto out; + } - END_PROFILE(syscall_ntimes); + ret = enc_vtimesat(dirfd, smb_fname_onefs->stream_name, ENC_DEFAULT, + times, flags); saved_errno = errno; close(dirfd); errno = saved_errno; + + out: + END_PROFILE(syscall_ntimes); + TALLOC_FREE(smb_fname_onefs); return ret; } diff --git a/source3/modules/vfs_cap.c b/source3/modules/vfs_cap.c index 9348ab9554..7e363b6be7 100644 --- a/source3/modules/vfs_cap.c +++ b/source3/modules/vfs_cap.c @@ -301,16 +301,36 @@ static int cap_chdir(vfs_handle_struct *handle, const char *path) return SMB_VFS_NEXT_CHDIR(handle, cappath); } -static int cap_ntimes(vfs_handle_struct *handle, const char *path, +static int cap_ntimes(vfs_handle_struct *handle, + const struct smb_filename *smb_fname, struct smb_file_time *ft) { - char *cappath = capencode(talloc_tos(), path); + struct smb_filename *smb_fname_tmp = NULL; + char *cappath = NULL; + NTSTATUS status; + int ret; + + cappath = capencode(talloc_tos(), smb_fname->base_name); if (!cappath) { errno = ENOMEM; return -1; } - return SMB_VFS_NEXT_NTIMES(handle, cappath, ft); + + /* Setup temporary smb_filename structs. */ + status = copy_smb_filename(talloc_tos(), smb_fname, + &smb_fname_tmp); + if (!NT_STATUS_IS_OK(status)) { + errno = map_errno_from_nt_status(status); + return -1; + } + + smb_fname_tmp->base_name = cappath; + + ret = SMB_VFS_NEXT_NTIMES(handle, smb_fname_tmp, ft); + + TALLOC_FREE(smb_fname_tmp); + return ret; } diff --git a/source3/modules/vfs_default.c b/source3/modules/vfs_default.c index c95c68fe0f..7565e7bb65 100644 --- a/source3/modules/vfs_default.c +++ b/source3/modules/vfs_default.c @@ -789,34 +789,42 @@ static char *vfswrap_getwd(vfs_handle_struct *handle, char *path) system will support. **********************************************************************/ -static int vfswrap_ntimes(vfs_handle_struct *handle, const char *path, +static int vfswrap_ntimes(vfs_handle_struct *handle, + const struct smb_filename *smb_fname, struct smb_file_time *ft) { - int result; + int result = -1; START_PROFILE(syscall_ntimes); + + if (smb_fname->stream_name) { + errno = ENOENT; + goto out; + } + #if defined(HAVE_UTIMES) if (ft != NULL) { struct timeval tv[2]; tv[0] = convert_timespec_to_timeval(ft->atime); tv[1] = convert_timespec_to_timeval(ft->mtime); - result = utimes(path, tv); + result = utimes(smb_fname->base_name, tv); } else { - result = utimes(path, NULL); + result = utimes(smb_fname->base_name, NULL); } #elif defined(HAVE_UTIME) if (ft != NULL) { struct utimbuf times; times.actime = convert_timespec_to_time_t(ft->atime); times.modtime = convert_timespec_to_time_t(ft->mtime); - result = utime(path, ×); + result = utime(smb_fname->base_name, ×); } else { - result = utime(path, NULL); + result = utime(smb_fname->base_name, NULL); } #else errno = ENOSYS; result = -1; #endif + out: END_PROFILE(syscall_ntimes); return result; } diff --git a/source3/modules/vfs_full_audit.c b/source3/modules/vfs_full_audit.c index 1f5e8333b9..e8702aa2c8 100644 --- a/source3/modules/vfs_full_audit.c +++ b/source3/modules/vfs_full_audit.c @@ -1011,13 +1011,15 @@ static char *smb_full_audit_getwd(vfs_handle_struct *handle, } static int smb_full_audit_ntimes(vfs_handle_struct *handle, - const char *path, struct smb_file_time *ft) + const struct smb_filename *smb_fname, + struct smb_file_time *ft) { int result; - result = SMB_VFS_NEXT_NTIMES(handle, path, ft); + result = SMB_VFS_NEXT_NTIMES(handle, smb_fname, ft); - do_log(SMB_VFS_OP_NTIMES, (result >= 0), handle, "%s", path); + do_log(SMB_VFS_OP_NTIMES, (result >= 0), handle, "%s", + smb_fname_str_do_log(smb_fname)); return result; } diff --git a/source3/modules/vfs_onefs.c b/source3/modules/vfs_onefs.c index 8ca3795e27..1a37622bea 100644 --- a/source3/modules/vfs_onefs.c +++ b/source3/modules/vfs_onefs.c @@ -200,7 +200,8 @@ done: return result; } -static int onefs_ntimes(vfs_handle_struct *handle, const char *fname, +static int onefs_ntimes(vfs_handle_struct *handle, + const struct smb_filename *smb_fname, struct smb_file_time *ft) { int flags = 0; @@ -230,7 +231,7 @@ static int onefs_ntimes(vfs_handle_struct *handle, const char *fname, ft->create_time.tv_nsec)); } - return onefs_vtimes_streams(handle, fname, flags, times); + return onefs_vtimes_streams(handle, smb_fname, flags, times); } static uint32_t onefs_fs_capabilities(struct vfs_handle_struct *handle) diff --git a/source3/modules/vfs_onefs_shadow_copy.c b/source3/modules/vfs_onefs_shadow_copy.c index 1a43e0671a..651e20a875 100644 --- a/source3/modules/vfs_onefs_shadow_copy.c +++ b/source3/modules/vfs_onefs_shadow_copy.c @@ -394,12 +394,13 @@ onefs_shadow_copy_chdir(vfs_handle_struct *handle, const char *path) } static int -onefs_shadow_copy_ntimes(vfs_handle_struct *handle, const char *path, +onefs_shadow_copy_ntimes(vfs_handle_struct *handle, + const struct smb_filename *smb_fname, struct smb_file_time *ft) { - SHADOW_NEXT(NTIMES, - (handle, cpath ?: path, ft), - int); + SHADOW_NEXT_SMB_FNAME_CONST(NTIMES, + (handle, smb_fname_tmp, ft), + int); } diff --git a/source3/modules/vfs_recycle.c b/source3/modules/vfs_recycle.c index 24166d1266..771189ca73 100644 --- a/source3/modules/vfs_recycle.c +++ b/source3/modules/vfs_recycle.c @@ -417,7 +417,6 @@ static void recycle_do_touch(vfs_handle_struct *handle, { struct smb_filename *smb_fname_tmp = NULL; struct smb_file_time ft; - char *fname = NULL; NTSTATUS status; int ret, err; @@ -438,22 +437,16 @@ static void recycle_do_touch(vfs_handle_struct *handle, /* mtime */ ft.mtime = touch_mtime ? ft.atime : smb_fname_tmp->st.st_ex_mtime; - status = get_full_smb_filename(talloc_tos(), smb_fname_tmp, &fname); - if (!NT_STATUS_IS_OK(status)) { - goto out; - } - become_root(); - ret = SMB_VFS_NEXT_NTIMES(handle, fname, &ft); + ret = SMB_VFS_NEXT_NTIMES(handle, smb_fname_tmp, &ft); err = errno; unbecome_root(); if (ret == -1 ) { DEBUG(0, ("recycle: touching %s failed, reason = %s\n", smb_fname_str_dbg(smb_fname_tmp), strerror(err))); } - out: - TALLOC_FREE(fname); + TALLOC_FREE(smb_fname_tmp); } /** diff --git a/source3/modules/vfs_shadow_copy2.c b/source3/modules/vfs_shadow_copy2.c index 05a8b67f71..1f300a055c 100644 --- a/source3/modules/vfs_shadow_copy2.c +++ b/source3/modules/vfs_shadow_copy2.c @@ -446,9 +446,19 @@ static int shadow_copy2_chdir(vfs_handle_struct *handle, } static int shadow_copy2_ntimes(vfs_handle_struct *handle, - const char *fname, struct smb_file_time *ft) + const struct smb_filename *smb_fname_in, + struct smb_file_time *ft) { - SHADOW2_NEXT(NTIMES, (handle, name, ft), int, -1); + struct smb_filename *smb_fname = NULL; + NTSTATUS status; + + status = copy_smb_filename(talloc_tos(), smb_fname_in, &smb_fname); + if (!NT_STATUS_IS_OK(status)) { + errno = map_errno_from_nt_status(status); + return -1; + } + + SHADOW2_NEXT_SMB_FNAME(NTIMES, (handle, smb_fname, ft), int, -1); } static int shadow_copy2_readlink(vfs_handle_struct *handle, -- cgit