]> git.ipfire.org Git - thirdparty/samba.git/commitdiff
smbd: open a pathref fsp on the parent directory
authorRalph Boehme <slow@samba.org>
Wed, 16 Dec 2020 14:20:47 +0000 (15:20 +0100)
committerJeremy Allison <jra@samba.org>
Thu, 17 Dec 2020 18:56:29 +0000 (18:56 +0000)
Prepares for calling SMB_VFS_MKDIRAT() below with a real dirfsp/atname. As
parent_dir_fname now has a pathref fsp in parent_dir_fname->fsp, make sure to
talloc_free() the parent_dir_fname before leaving the function, so the pathref
fsp is closed right there and not left around until the talloc tos is
destroyed (parent_dir_fname is a child of talloc-tos).

Signed-off-by: Ralph Boehme <slow@samba.org>
Reviewed-by: Jeremy Allison <jra@samba.org>
source3/smbd/open.c

index 35949f4b17c0aefca84c4943a066bbabe9a79bd7..d6dcf41183fcdf01984f5002d4f0b9a0dc054d1e 100644 (file)
@@ -4320,6 +4320,7 @@ static NTSTATUS mkdir_internal(connection_struct *conn,
                loadparm_s3_global_substitution();
        mode_t mode;
        struct smb_filename *parent_dir_fname = NULL;
+       struct smb_filename *base_name = NULL;
        NTSTATUS status;
        bool posix_open = false;
        bool need_re_stat = false;
@@ -4336,11 +4337,16 @@ static NTSTATUS mkdir_internal(connection_struct *conn,
        ok = parent_smb_fname(talloc_tos(),
                              smb_dname,
                              &parent_dir_fname,
-                             NULL);
+                             &base_name);
        if (!ok) {
                return NT_STATUS_NO_MEMORY;
        }
 
+       status = openat_pathref_fsp(conn->cwd_fsp, parent_dir_fname);
+       if (!NT_STATUS_IS_OK(status)) {
+               return status;
+       }
+
        if (file_attributes & FILE_FLAG_POSIX_SEMANTICS) {
                posix_open = true;
                mode = (mode_t)(file_attributes & ~FILE_FLAG_POSIX_SEMANTICS);
@@ -4361,6 +4367,7 @@ static NTSTATUS mkdir_internal(connection_struct *conn,
                        smb_fname_str_dbg(parent_dir_fname),
                        smb_dname->base_name,
                        nt_errstr(status) ));
+               TALLOC_FREE(parent_dir_fname);
                return status;
        }
 
@@ -4377,6 +4384,7 @@ static NTSTATUS mkdir_internal(connection_struct *conn,
                              smb_dname,
                              mode);
        if (ret != 0) {
+               TALLOC_FREE(parent_dir_fname);
                return map_nt_error_from_unix(errno);
        }
 
@@ -4386,12 +4394,14 @@ static NTSTATUS mkdir_internal(connection_struct *conn,
        if (SMB_VFS_LSTAT(conn, smb_dname) == -1) {
                DEBUG(2, ("Could not stat directory '%s' just created: %s\n",
                          smb_fname_str_dbg(smb_dname), strerror(errno)));
+               TALLOC_FREE(parent_dir_fname);
                return map_nt_error_from_unix(errno);
        }
 
        if (!S_ISDIR(smb_dname->st.st_ex_mode)) {
                DEBUG(0, ("Directory '%s' just created is not a directory !\n",
                          smb_fname_str_dbg(smb_dname)));
+               TALLOC_FREE(parent_dir_fname);
                return NT_STATUS_NOT_A_DIRECTORY;
        }
 
@@ -4443,6 +4453,8 @@ static NTSTATUS mkdir_internal(connection_struct *conn,
                need_re_stat = true;
        }
 
+       TALLOC_FREE(parent_dir_fname);
+
        if (need_re_stat) {
                if (SMB_VFS_LSTAT(conn, smb_dname) == -1) {
                        DEBUG(2, ("Could not stat directory '%s' just created: %s\n",