diff options
author | Jeremy Allison <jra@samba.org> | 2011-10-19 16:56:00 -0700 |
---|---|---|
committer | Jeremy Allison <jra@samba.org> | 2011-10-20 09:07:46 -0700 |
commit | ff8fa5aa2b7665cd38bd589870f52ac58f38c66f (patch) | |
tree | db7d0cc08b7db97a68cfc3a9308687b4ddf2a076 | |
parent | 3ae478be0fca9a095ac81fa55debcbc51303e6fa (diff) | |
download | samba-ff8fa5aa2b7665cd38bd589870f52ac58f38c66f.tar.gz samba-ff8fa5aa2b7665cd38bd589870f52ac58f38c66f.tar.bz2 samba-ff8fa5aa2b7665cd38bd589870f52ac58f38c66f.zip |
Make mkdir_internal() check the parent ACL for SEC_DIR_ADD_SUBDIR rights.
-rw-r--r-- | source3/smbd/open.c | 35 |
1 files changed, 33 insertions, 2 deletions
diff --git a/source3/smbd/open.c b/source3/smbd/open.c index a56dd6bfa1..a03e41da3e 100644 --- a/source3/smbd/open.c +++ b/source3/smbd/open.c @@ -2441,9 +2441,12 @@ static NTSTATUS mkdir_internal(connection_struct *conn, NTSTATUS status; bool posix_open = false; bool need_re_stat = false; + struct security_descriptor *parent_sd = NULL; + uint32_t access_mask = SEC_DIR_ADD_SUBDIR; + uint32_t access_granted = 0; - if(!CAN_WRITE(conn)) { - DEBUG(5,("mkdir_internal: failing create on read-only share " + if(access_mask & ~(conn->share_access)) { + DEBUG(5,("mkdir_internal: failing share access " "%s\n", lp_servicename(SNUM(conn)))); return NT_STATUS_ACCESS_DENIED; } @@ -2465,6 +2468,34 @@ static NTSTATUS mkdir_internal(connection_struct *conn, mode = unix_mode(conn, FILE_ATTRIBUTE_DIRECTORY, smb_dname, parent_dir); } + status = SMB_VFS_GET_NT_ACL(conn, + parent_dir, + SECINFO_DACL, + &parent_sd); + if (!NT_STATUS_IS_OK(status)) { + DEBUG(5,("mkdir_internal: SMB_VFS_GET_NT_ACL failed for " + "%s with error %s\n", + parent_dir, + nt_errstr(status))); + return status; + } + + status = smb1_file_se_access_check(conn, + parent_sd, + get_current_nttok(conn), + access_mask, + &access_granted); + if(!NT_STATUS_IS_OK(status)) { + DEBUG(5,("mkdir_internal: access check " + "on directory %s for " + "path %s for mask 0x%x returned %s\n", + parent_dir, + smb_dname->base_name, + access_mask, + nt_errstr(status) )); + return status; + } + if (SMB_VFS_MKDIR(conn, smb_dname->base_name, mode) != 0) { return map_nt_error_from_unix(errno); } |