Win32 File API GetNamedSecurityInfo function

Download EaseFilter Monitor, Control and Encryption Filter Driver SDK Setup File
Download EaseFilter Monitor, Control and Encryption Filter Driver SDK Zip File

The GetNamedSecurityInfo function retrieves a copy of the security descriptor for an object specified by name.

Syntax

DWORD GetNamedSecurityInfoW(
  LPCWSTR              pObjectName,
  SE_OBJECT_TYPE       ObjectType,
  SECURITY_INFORMATION SecurityInfo,
  PSID                 *ppsidOwner,
  PSID                 *ppsidGroup,
  PACL                 *ppDacl,
  PACL                 *ppSacl,
  PSECURITY_DESCRIPTOR *ppSecurityDescriptor
);

Parameters

pObjectName

A pointer to a null-terminated string that specifies the name of the object from which to retrieve security information. For descriptions of the string formats for the different object types, see SE_OBJECT_TYPE.

ObjectType

Specifies a value from the SE_OBJECT_TYPE enumeration that indicates the type of object named by the pObjectName parameter.

SecurityInfo

A set of bit flags that indicate the type of security information to retrieve. This parameter can be a combination of theSECURITY_INFORMATION bit flags.

ppsidOwner

A pointer to a variable that receives a pointer to the owner SID in the security descriptor returned in ppSecurityDescriptor or NULL if the security descriptor has no owner SID. The returned pointer is valid only if you set the OWNER_SECURITY_INFORMATION flag. Also, this parameter can be NULL if you do not need the owner SID.

ppsidGroup

A pointer to a variable that receives a pointer to the primary group SID in the returned security descriptor or NULL if the security descriptor has no group SID. The returned pointer is valid only if you set the GROUP_SECURITY_INFORMATION flag. Also, this parameter can be NULL if you do not need the group SID.

ppDacl

A pointer to a variable that receives a pointer to the DACL in the returned security descriptor or NULL if the security descriptor has no DACL. The returned pointer is valid only if you set the DACL_SECURITY_INFORMATION flag. Also, this parameter can be NULL if you do not need the DACL.

ppSacl

A pointer to a variable that receives a pointer to the SACL in the returned security descriptor or NULL if the security descriptor has no SACL. The returned pointer is valid only if you set the SACL_SECURITY_INFORMATION flag. Also, this parameter can be NULL if you do not need the SACL.

ppSecurityDescriptor

A pointer to a variable that receives a pointer to the security descriptor of the object. When you have finished using the pointer, free the returned buffer by calling the LocalFree function.

This parameter is required if any one of the ppsidOwnerppsidGroupppDacl, or ppSacl parameters is not NULL.

Return Value

If the function succeeds, the return value is ERROR_SUCCESS.

If the function fails, the return value is a nonzero error code defined in WinError.h.

Remarks

If any of the ppsidOwnerppsidGroupppDacl, or ppSacl parameters are non-NULL, and the SecurityInfo parameter specifies that they be retrieved from the object, those parameters will point to the corresponding parameters in the security descriptor returned in ppSecurityDescriptor. If the security descriptor does not contain the requested information, the corresponding parameter will be set to NULL.

To read the owner, group, or DACL from the object's security descriptor, the object's DACL must grant READ_CONTROL access to the caller, or the caller must be the owner of the object.

To read the system access control list of the object, the SE_SECURITY_NAME privilege must be enabled for the calling process. For information about the security implications of enabling privileges, see Running with Special Privileges.

You can use the GetNamedSecurityInfo function with the following types of objects:

  • Local or remote files or directories on an NTFS file system
  • Local or remote printers
  • Local or remote Windows services
  • Network shares
  • Registry keys
  • Semaphores, events, mutexes, and waitable timers
  • File-mapping objects
  • Directory service objects
This function does not handle race conditions. If your thread calls this function at the approximate time that another thread changes the object's security descriptor, then this function could fail.

This function transfers information in plaintext. The information transferred by this function is signed unless signing has been turned off for the system, but no encryption is performed.

For more information about controlling access to objects through user accounts, group accounts, or logon sessions, see How DACLs Control Access to an Object.

Examples

The following example adds an access control entry (ACE) to the discretionary access control list (DACL) of an object.

The AccessMode parameter determines the type of new ACE and how the new ACE is combined with any existing ACEs for the specified trustee. Use the GRANT_ACCESS, SET_ACCESS, DENY_ACCESS, or REVOKE_ACCESS flags in the AccessMode parameter. For information about these flags, see ACCESS_MODE.

Similar code can be used to work with a system access control list (SACL). Specify SACL_SECURITY_INFORMATION in the GetNamedSecurityInfo and SetNamedSecurityInfo functions to get and set the SACL for the object. Use the SET_AUDIT_SUCCESS, SET_AUDIT_FAILURE, and REVOKE_ACCESS flags in the AccessMode parameter. For information about these flags, see ACCESS_MODE.

Use this code to add an object-specific ACE to the DACL of a directory service object. To specify the GUIDs in an object-specific ACE, set the TrusteeForm parameter to TRUSTEE_IS_OBJECTS_AND_NAME or TRUSTEE_IS_OBJECTS_AND_SID and set the pszTrusteeparameter to be a pointer to an OBJECTS_AND_NAME or OBJECTS_AND_SID structure.

This example uses the GetNamedSecurityInfo function to get the existing DACL. Then it fills an EXPLICIT_ACCESS structure with information about an ACE and uses the SetEntriesInAcl function to merge the new ACE with any existing ACEs in the DACL. Finally, the example calls the SetNamedSecurityInfo function to attach the new DACL to the security descriptor of the object.

#include <windows.h>  
#include <stdio.h>

DWORD AddAceToObjectsSecurityDescriptor (
    LPTSTR pszObjName,          // name of object
    SE_OBJECT_TYPE ObjectType,  // type of object
    LPTSTR pszTrustee,          // trustee for new ACE
    TRUSTEE_FORM TrusteeForm,   // format of trustee structure
    DWORD dwAccessRights,       // access mask for new ACE
    ACCESS_MODE AccessMode,     // type of ACE
    DWORD dwInheritance         // inheritance flags for new ACE
) 
{
    DWORD dwRes = 0;
    PACL pOldDACL = NULL, pNewDACL = NULL;
    PSECURITY_DESCRIPTOR pSD = NULL;
    EXPLICIT_ACCESS ea;

    if (NULL == pszObjName) 
        return ERROR_INVALID_PARAMETER;

    // Get a pointer to the existing DACL.

    dwRes = GetNamedSecurityInfo(pszObjName, ObjectType, 
          DACL_SECURITY_INFORMATION,
          NULL, NULL, &pOldDACL, NULL, &pSD);
    if (ERROR_SUCCESS != dwRes) {
        printf( "GetNamedSecurityInfo Error %u\n", dwRes );
        goto Cleanup; 
    }  

    // Initialize an EXPLICIT_ACCESS structure for the new ACE. 

    ZeroMemory(&ea, sizeof(EXPLICIT_ACCESS));
    ea.grfAccessPermissions = dwAccessRights;
    ea.grfAccessMode = AccessMode;
    ea.grfInheritance= dwInheritance;
    ea.Trustee.TrusteeForm = TrusteeForm;
    ea.Trustee.ptstrName = pszTrustee;

    // Create a new ACL that merges the new ACE
    // into the existing DACL.

    dwRes = SetEntriesInAcl(1, &ea, pOldDACL, &pNewDACL);
    if (ERROR_SUCCESS != dwRes)  {
        printf( "SetEntriesInAcl Error %u\n", dwRes );
        goto Cleanup; 
    }  

    // Attach the new ACL as the object's DACL.

    dwRes = SetNamedSecurityInfo(pszObjName, ObjectType, 
          DACL_SECURITY_INFORMATION,
          NULL, NULL, pNewDACL, NULL);
    if (ERROR_SUCCESS != dwRes)  {
        printf( "SetNamedSecurityInfo Error %u\n", dwRes );
        goto Cleanup; 
    }  

    Cleanup:

        if(pSD != NULL) 
            LocalFree((HLOCAL) pSD); 
        if(pNewDACL != NULL) 
            LocalFree((HLOCAL) pNewDACL); 

        return dwRes;
}