]> git.ipfire.org Git - thirdparty/samba.git/commitdiff
vfs_gpfs: add sys_proc_fd_path() fallback to vfs_gpfs_fset_dos_attributes()
authorRalph Boehme <slow@samba.org>
Thu, 1 Jul 2021 14:08:02 +0000 (16:08 +0200)
committerRalph Boehme <slow@samba.org>
Thu, 26 Aug 2021 19:18:31 +0000 (19:18 +0000)
gpfs_set_winattrs() is a modifying operation, my expectation thus is that it is
not allowed on pathref (O_PATH) handles even though a recent Linux kernel commit
44a3b87444058b2cb055092cdebc63858707bf66 allowed calling utimensat() on pathref
handles.

BUG: https://bugzilla.samba.org/show_bug.cgi?id=14771
RN: Some VFS operations on pathref (O_PATH) handles fail on GPFS

Signed-off-by: Ralph Boehme <slow@samba.org>
Reviewed-by: Christof Schmitt <cs@samba.org>
source3/modules/vfs_gpfs.c

index 94d0258b38d4a776e659c909cdd8184971a78930..cc653c2271237140cfe14d505dd3857cfbe03287 100644 (file)
@@ -1585,11 +1585,47 @@ static NTSTATUS vfs_gpfs_fset_dos_attributes(struct vfs_handle_struct *handle,
 
        attrs.winAttrs = vfs_gpfs_dosmode_to_winattrs(dosmode);
 
-       ret = gpfswrap_set_winattrs(fsp_get_io_fd(fsp),
-                                   GPFS_WINATTR_SET_ATTRS, &attrs);
+       if (!fsp->fsp_flags.is_pathref) {
+               ret = gpfswrap_set_winattrs(fsp_get_io_fd(fsp),
+                                           GPFS_WINATTR_SET_ATTRS, &attrs);
+               if (ret == -1) {
+                       DBG_WARNING("Setting winattrs failed for %s: %s\n",
+                                   fsp_str_dbg(fsp), strerror(errno));
+                       return map_nt_error_from_unix(errno);
+               }
+               return NT_STATUS_OK;
+       }
+
+       if (fsp->fsp_flags.have_proc_fds) {
+               int fd = fsp_get_pathref_fd(fsp);
+               const char *p = NULL;
+               char buf[PATH_MAX];
+
+               p = sys_proc_fd_path(fd, buf, sizeof(buf));
+               if (p == NULL) {
+                       return NT_STATUS_NO_MEMORY;
+               }
+
+               ret = gpfswrap_set_winattrs_path(p,
+                                                GPFS_WINATTR_SET_ATTRS,
+                                                &attrs);
+               if (ret == -1) {
+                       DBG_WARNING("Setting winattrs failed for [%s][%s]: %s\n",
+                                   p, fsp_str_dbg(fsp), strerror(errno));
+                       return map_nt_error_from_unix(errno);
+               }
+               return NT_STATUS_OK;
+       }
+
+       /*
+        * This is no longer a handle based call.
+        */
+       ret = gpfswrap_set_winattrs_path(fsp->fsp_name->base_name,
+                                        GPFS_WINATTR_SET_ATTRS,
+                                        &attrs);
        if (ret == -1) {
-               DBG_WARNING("Setting winattrs failed for %s: %s\n",
-                           fsp->fsp_name->base_name, strerror(errno));
+               DBG_WARNING("Setting winattrs failed for [%s]: %s\n",
+                           fsp_str_dbg(fsp), strerror(errno));
                return map_nt_error_from_unix(errno);
        }