Sup, hope OP is still interested in the answer. Here is the working code adding ACEs to ACLs, it may be used to add ACEs to registry or filesystem DACLs. I haven't tried it with anything else yet. As you may notice, no nasty RegGetKeySecurity
or manual ACL composing needed. There's even no need to RegOpenKeyEx
. For more info, check this MS doc.
UPD Of course it will need admin rights for execution.
// sk - alloced string / path to needed key
// common look: MACHINE\\Software\\... where MACHINE == HKEY_LOCAL_MACHINE
// google for more address abbrevations
PSECURITY_DESCRIPTOR pSD = 0;
EXPLICIT_ACCESS ea;
PACL pOldDACL = 0, pNewDACL = 0;
if (ERROR_SUCCESS == GetNamedSecurityInfo(sk, SE_REGISTRY_KEY, DACL_SECURITY_INFORMATION, 0, 0, &pOldDACL, 0, &pSD)) {
memset(&ea, 0, sizeof(EXPLICIT_ACCESS));
ea.grfAccessPermissions = KEY_ALL_ACCESS;
ea.grfAccessMode = GRANT_ACCESS;
ea.grfInheritance = NO_INHERITANCE;
ea.Trustee.TrusteeForm = TRUSTEE_IS_NAME;
ea.Trustee.ptstrName = <USERNAME HERE>; //DOMAIN\\USERNAME
if (ERROR_SUCCESS == SetEntriesInAcl(1, &ea, pOldDACL, &pNewDACL)) {
if (ERROR_SUCCESS == SetNamedSecurityInfo(sk, SE_REGISTRY_KEY, DACL_SECURITY_INFORMATION, 0, 0, pNewDACL, 0)) {
if (pSD != 0) LocalFree((HLOCAL)pSD);
if (pNewDACL != 0) LocalFree((HLOCAL)pNewDACL);
SAFE_FREE(sk);
// WE'RE GOOD!
return ... ;
} else {
if (pSD) LocalFree((HLOCAL)pSD);
if (pNewDACL) LocalFree((HLOCAL)pNewDACL);
SAFE_FREE(sk);
// SetNamedSecurityInfo failed
return ... ;
}
} else {
if (pSD) LocalFree((HLOCAL)pSD);
if (pNewDACL) LocalFree((HLOCAL)pNewDACL);
SAFE_FREE(sk);
// SetEntriesInAcl failed
return ... ;
}
} else {
if (pSD) LocalFree((HLOCAL)pSD);
SAFE_FREE(sk);
// GetNamedSecurityInfo failed
return ... ;
}