Tuesday 2 August 2011

How to programmatically set access rights on a file (Windows)

Object access control is part of Windows security. Each securable object has its name, type (file, directory, process, event, semaphore, mutex, timer, registry key,...) and security descriptor which contains information about its:
  • owner
  • group
  • ACLs (Access Control Lists) - one instance of each type of ACLs:
    • DACL (Discretionary Access Control List) - specifies the access particular users or groups can have to the object
    • SACL (System Access Control List) - controls the logging of attempts to access the object
ACL is a set of Access Control Entries (ACEs). ACE contains set of structures that specify access rights for  trustee where trustee (user or group) is identified by its Security IDentifier (SID).

If we want to change access right for particular user on some object we need to:
  1. identify object for which we want to set permission (by its name and type)
  2. get object's current DACL (use GetNamedSecurityInfo)
  3. identify user (by its name or SID); identify rights
  4. create new ACE, stating user and its rights (instantiate EXPLICIT_ACCESS structure)
  5. merge new ACE to existing DACL in order to get a new DACL (use SetEntriesInAcl)
  6. attach new DACL to the object (use SetNamedSecurityInfo)
MSDN article "Modifying the ACLs of an Object in C++" shows implementation of these steps within function  AddAceToObjectsSecurityDescriptor. For example, if we want to set read and execute rights for IUSR user on some file which path is in pszPath, we can call this function with following paramethers:

DWORD dwRes = AddAceToObjectsSecurityDescriptor(
pszPath,
SE_FILE_OBJECT,
"IUSR",
TRUSTEE_IS_NAME,
STANDARD_RIGHTS_READ | STANDARD_RIGHTS_EXECUTE,
GRANT_ACCESS,
NO_INHERITANCE);

No comments: