Remove/Modify an inherited ACE in an ACL (Windows)

acl, c++, windows

Solution

To remove inherited ACEs, call SetNamedSecurityInfo and pass `DACL_SECURITY_INFORMATION | PROTECTED_DACL_SECURITY_INFORMATION` for the SecurityInfo parameter.

The `PROTECTED_DACL_SECURITY_INFORMATION` flag prevents inheritable ACEs from the parent from being added to the ACL you specify.

If you don't need to copy other inherited permissions, but can just specify a particular ACL to use, that would be simpler. If you do need to copy other inherited permissions, you'll need to keep the read-compare-add loop in your existing code, but you should also be clearing the INHERITED_ACE flag since these are now explicit permissions.

Problem

I'm trying to modify the existing ACL on a directory (and its sub-directories) to remove write access for the built-in Users group. The directory is inheriting this particular right from its parent directory. I've tried using AtlSetDacl() to set a new ACL but this doesn't clear out the inherited write permission. Fragment: ``` ATL::CDacl dacl; ATL::AtlGetDacl(directoryName.c_str(), SE_FILE_OBJECT, &dacl); UINT aceCount = dacl.GetAceCount(); ATL::CDacl newDacl; for (UINT i = 0; i < aceCount; ++i) { ATL::CSid sid; ACCESS_MASK mask = 0; BYTE flags = 0; dacl.GetAclEntry(i, &sid, &mask, (BYTE*) 0, &flags); if (sid != Sids::Users()) newDacl.AddAllowedAce(sid, mask, flags); } newDacl.AddAllowedAce(Sids::Users(),FILE_LIST_DIRECTORY | FILE_READ_EA | FILE_EXECUTE | FILE_READ_ATTRIBUTES, CONTAINER_INHERIT_ACE | OBJECT_INHERIT_ACE); AtlSetDacl(directoryName.c_str(), SE_FILE_OBJECT, newDacl); ``` I've also tried SetNamedSecurityInfo() and related APIs to wipe the existing ACL and create a new one, but no luck here either. Doesn't seem like this should be that hard. Using cacls.exe this is a piece of cake (unfortunately not an option for me). Any ideas on how to do this?

Original source