summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorRalph Boehme <slow@samba.org>2016-08-25 07:45:34 +0200
committerKarolin Seeger <kseeger@samba.org>2016-09-16 12:05:34 +0200
commit20728fe694d7280277e0b639c5929155e58b839d (patch)
treefcd7749cb05c32ed5599e95e1b1f114cd10618c5
parent63d0f968eb72ec2d9074570d1bc14cf9013263ca (diff)
downloadsamba-20728fe694d7280277e0b639c5929155e58b839d.tar.gz
vfs_acl_common: Windows style default ACL
Reintroduce Windows style default ACL, but this time as an optional feature, not changing default behaviour. Original bugreport that got reverted because it changed the default behaviour: https://bugzilla.samba.org/show_bug.cgi?id=12028 Bug: https://bugzilla.samba.org/show_bug.cgi?id=12177 Signed-off-by: Ralph Boehme <slow@samba.org> Reviewed-by: Jeremy Allison <jra@samba.org> (cherry picked from commit 0730cb7e1ce33dbc5fc48a7363204c1220400c68)
-rw-r--r--source3/modules/vfs_acl_common.c76
1 files changed, 76 insertions, 0 deletions
diff --git a/source3/modules/vfs_acl_common.c b/source3/modules/vfs_acl_common.c
index e8eaa4fcd2c..44fef12a377 100644
--- a/source3/modules/vfs_acl_common.c
+++ b/source3/modules/vfs_acl_common.c
@@ -507,6 +507,78 @@ static NTSTATUS make_default_acl_posix(TALLOC_CTX *ctx,
return NT_STATUS_OK;
}
+static NTSTATUS make_default_acl_windows(TALLOC_CTX *ctx,
+ const char *name,
+ SMB_STRUCT_STAT *psbuf,
+ struct security_descriptor **ppdesc)
+{
+ struct dom_sid owner_sid, group_sid;
+ size_t size = 0;
+ struct security_ace aces[4];
+ uint32_t access_mask = 0;
+ mode_t mode = psbuf->st_ex_mode;
+ struct security_acl *new_dacl = NULL;
+ int idx = 0;
+
+ DBG_DEBUG("file [%s] mode [0%o]\n", name, (int)mode);
+
+ uid_to_sid(&owner_sid, psbuf->st_ex_uid);
+ gid_to_sid(&group_sid, psbuf->st_ex_gid);
+
+ /*
+ * We provide 2 ACEs:
+ * - Owner
+ * - NT System
+ */
+
+ if (mode & S_IRUSR) {
+ if (mode & S_IWUSR) {
+ access_mask |= SEC_RIGHTS_FILE_ALL;
+ } else {
+ access_mask |= SEC_RIGHTS_FILE_READ | SEC_FILE_EXECUTE;
+ }
+ }
+ if (mode & S_IWUSR) {
+ access_mask |= SEC_RIGHTS_FILE_WRITE | SEC_STD_DELETE;
+ }
+
+ init_sec_ace(&aces[idx],
+ &owner_sid,
+ SEC_ACE_TYPE_ACCESS_ALLOWED,
+ access_mask,
+ 0);
+ idx++;
+
+ init_sec_ace(&aces[idx],
+ &global_sid_System,
+ SEC_ACE_TYPE_ACCESS_ALLOWED,
+ SEC_RIGHTS_FILE_ALL,
+ 0);
+ idx++;
+
+ new_dacl = make_sec_acl(ctx,
+ NT4_ACL_REVISION,
+ idx,
+ aces);
+
+ if (!new_dacl) {
+ return NT_STATUS_NO_MEMORY;
+ }
+
+ *ppdesc = make_sec_desc(ctx,
+ SECURITY_DESCRIPTOR_REVISION_1,
+ SEC_DESC_SELF_RELATIVE|SEC_DESC_DACL_PRESENT,
+ &owner_sid,
+ &group_sid,
+ NULL,
+ new_dacl,
+ &size);
+ if (!*ppdesc) {
+ return NT_STATUS_NO_MEMORY;
+ }
+ return NT_STATUS_OK;
+}
+
static NTSTATUS make_default_filesystem_acl(TALLOC_CTX *ctx,
struct acl_common_config *config,
const char *name,
@@ -521,6 +593,10 @@ static NTSTATUS make_default_filesystem_acl(TALLOC_CTX *ctx,
status = make_default_acl_posix(ctx, name, psbuf, ppdesc);
break;
+ case DEFAULT_ACL_WINDOWS:
+ status = make_default_acl_windows(ctx, name, psbuf, ppdesc);
+ break;
+
default:
DBG_ERR("unknown acl style %d", config->default_acl_style);
status = NT_STATUS_INTERNAL_ERROR;