diff options
Diffstat (limited to 'source4/ntvfs')
-rw-r--r-- | source4/ntvfs/ntvfs_generic.c | 2 | ||||
-rw-r--r-- | source4/ntvfs/posix/pvfs_acl.c | 31 | ||||
-rw-r--r-- | source4/ntvfs/posix/pvfs_open.c | 15 | ||||
-rw-r--r-- | source4/ntvfs/simple/vfs_simple.c | 6 | ||||
-rw-r--r-- | source4/ntvfs/unixuid/vfs_unixuid.c | 5 |
5 files changed, 45 insertions, 14 deletions
diff --git a/source4/ntvfs/ntvfs_generic.c b/source4/ntvfs/ntvfs_generic.c index 5838178d9e..6e2e075f1e 100644 --- a/source4/ntvfs/ntvfs_generic.c +++ b/source4/ntvfs/ntvfs_generic.c @@ -515,7 +515,7 @@ NTSTATUS ntvfs_map_open(struct ntvfs_module_context *ntvfs, io2->generic.in.flags = 0; break; } - io2->generic.in.root_fid = 0; + io2->generic.in.root_fid.fnum = 0; io2->generic.in.access_mask = io->smb2.in.desired_access; io2->generic.in.alloc_size = io->smb2.in.alloc_size; io2->generic.in.file_attr = io->smb2.in.file_attributes; diff --git a/source4/ntvfs/posix/pvfs_acl.c b/source4/ntvfs/posix/pvfs_acl.c index ad7ac5a749..26515cfe1a 100644 --- a/source4/ntvfs/posix/pvfs_acl.c +++ b/source4/ntvfs/posix/pvfs_acl.c @@ -384,6 +384,9 @@ NTSTATUS pvfs_acl_set(struct pvfs_state *pvfs, } else { ret = fchown(fd, new_uid, new_gid); } + if (errno == EPERM && uwrap_enabled()) { + ret = 0; + } if (ret == -1) { return pvfs_map_errno(pvfs, errno); } @@ -490,16 +493,16 @@ NTSTATUS pvfs_access_check_unix(struct pvfs_state *pvfs, { uid_t uid = geteuid(); uint32_t max_bits = SEC_RIGHTS_FILE_READ | SEC_FILE_ALL; + struct security_token *token = req->session_info->security_token; if (pvfs_read_only(pvfs, *access_mask)) { return NT_STATUS_ACCESS_DENIED; } - /* owner and root get extra permissions */ - if (uid == 0) { - max_bits |= SEC_STD_ALL | SEC_FLAG_SYSTEM_SECURITY; - } else if (uid == name->st.st_uid) { + if (uid == name->st.st_uid) { max_bits |= SEC_STD_ALL; + } else if (security_token_has_privilege(token, SEC_PRIV_RESTORE)) { + max_bits |= SEC_STD_DELETE; } if ((name->st.st_mode & S_IWOTH) || @@ -516,13 +519,23 @@ NTSTATUS pvfs_access_check_unix(struct pvfs_state *pvfs, max_bits |= SEC_STD_ALL; } - if (*access_mask == SEC_FLAG_MAXIMUM_ALLOWED) { - *access_mask = max_bits; - return NT_STATUS_OK; + if (*access_mask & SEC_FLAG_MAXIMUM_ALLOWED) { + *access_mask |= max_bits; + *access_mask &= ~SEC_FLAG_MAXIMUM_ALLOWED; } - if (uid != 0 && (*access_mask & SEC_FLAG_SYSTEM_SECURITY)) { - return NT_STATUS_ACCESS_DENIED; + if ((*access_mask & SEC_FLAG_SYSTEM_SECURITY) && + security_token_has_privilege(token, SEC_PRIV_SECURITY)) { + max_bits |= SEC_FLAG_SYSTEM_SECURITY; + } + + if (((*access_mask & ~max_bits) & SEC_RIGHTS_PRIV_RESTORE) && + security_token_has_privilege(token, SEC_PRIV_RESTORE)) { + max_bits |= ~(SEC_RIGHTS_PRIV_RESTORE); + } + if (((*access_mask & ~max_bits) & SEC_RIGHTS_PRIV_BACKUP) && + security_token_has_privilege(token, SEC_PRIV_BACKUP)) { + max_bits |= ~(SEC_RIGHTS_PRIV_BACKUP); } if (*access_mask & ~max_bits) { diff --git a/source4/ntvfs/posix/pvfs_open.c b/source4/ntvfs/posix/pvfs_open.c index 46e39a00dd..e8f1c0c4c8 100644 --- a/source4/ntvfs/posix/pvfs_open.c +++ b/source4/ntvfs/posix/pvfs_open.c @@ -1272,6 +1272,21 @@ NTSTATUS pvfs_open(struct ntvfs_module_context *ntvfs, return NT_STATUS_ACCESS_DENIED; } + /* cope with non-zero root_fid */ + if (io->ntcreatex.in.root_fid.ntvfs != NULL) { + f = pvfs_find_fd(pvfs, req, io->ntcreatex.in.root_fid.ntvfs); + if (f == NULL) { + return NT_STATUS_INVALID_HANDLE; + } + if (f->handle->fd != -1) { + return NT_STATUS_INVALID_DEVICE_REQUEST; + } + io->ntcreatex.in.fname = talloc_asprintf(req, "%s\\%s", + f->handle->name->original_name, + io->ntcreatex.in.fname); + NT_STATUS_HAVE_NO_MEMORY(io->ntcreatex.in.fname); + } + if (io->ntcreatex.in.file_attr & (FILE_ATTRIBUTE_DEVICE| FILE_ATTRIBUTE_VOLUME| (~FILE_ATTRIBUTE_ALL_MASK))) { diff --git a/source4/ntvfs/simple/vfs_simple.c b/source4/ntvfs/simple/vfs_simple.c index aabaa3c47f..9577e8673a 100644 --- a/source4/ntvfs/simple/vfs_simple.c +++ b/source4/ntvfs/simple/vfs_simple.c @@ -70,9 +70,9 @@ static NTSTATUS svfs_connect(struct ntvfs_module_context *ntvfs, } if (strncmp(sharename, "\\\\", 2) == 0) { - char *p = strchr(sharename+2, '\\'); - if (p) { - sharename = p + 1; + char *p2 = strchr(sharename+2, '\\'); + if (p2) { + sharename = p2 + 1; } } diff --git a/source4/ntvfs/unixuid/vfs_unixuid.c b/source4/ntvfs/unixuid/vfs_unixuid.c index 97c306f7c3..70ad6ee253 100644 --- a/source4/ntvfs/unixuid/vfs_unixuid.c +++ b/source4/ntvfs/unixuid/vfs_unixuid.c @@ -235,7 +235,10 @@ static NTSTATUS unixuid_setup_security(struct ntvfs_module_context *ntvfs, struct unix_sec_ctx *newsec; NTSTATUS status; - if (req->session_info == NULL) { + /* If we are asked to set up, but have not had a successful + * session setup or tree connect, then these may not be filled + * in. ACCESS_DENIED is the right error code here */ + if (req->session_info == NULL || priv == NULL) { return NT_STATUS_ACCESS_DENIED; } |