/// <summary> /// Do an access check between a security descriptor and a token to determine the allowed access. /// </summary> /// <param name="sd">The security descriptor</param> /// <param name="token">The access token.</param> /// <param name="access_rights">The set of access rights to check against</param> /// <param name="generic_mapping">The type specific generic mapping (get from corresponding NtType entry).</param> /// <returns>The allowed access mask as a unsigned integer.</returns> /// <exception cref="NtException">Thrown if an error occurred in the access check.</exception> public static uint GetAllowedAccess(SecurityDescriptor sd, NtToken token, GenericAccessRights access_rights, GenericMapping generic_mapping) { if (sd == null) { throw new ArgumentNullException("sd"); } if (token == null) { throw new ArgumentNullException("token"); } using (var sd_buffer = sd.ToSafeBuffer()) { using (NtToken imp_token = token.DuplicateToken(SecurityImpersonationLevel.Identification)) { uint granted_access; NtStatus result_status; using (var privs = new SafePrivilegeSetBuffer()) { int buffer_length = privs.Length; NtSystemCalls.NtAccessCheck(sd_buffer, imp_token.Handle, (uint)access_rights, ref generic_mapping, privs, ref buffer_length, out granted_access, out result_status).ToNtException(); if (result_status.IsSuccess()) { return(granted_access); } return(0); } } } }
public static extern NtStatus NtAccessCheck( SafeBuffer SecurityDescriptor, SafeKernelObjectHandle ClientToken, AccessMask DesiredAccess, ref GenericMapping GenericMapping, SafePrivilegeSetBuffer RequiredPrivilegesBuffer, ref int BufferLength, out AccessMask GrantedAccess, out NtStatus AccessStatus);
internal PrivilegeCheckResult(SafePrivilegeSetBuffer privileges, bool all_privileges_held) { var result = privileges.Result; LuidAndAttributes[] luids = new LuidAndAttributes[result.PrivilegeCount]; privileges.Data.ReadArray(0, luids, 0, luids.Length); Privileges = luids.Select(l => new TokenPrivilege(l.Luid, l.Attributes)).ToList().AsReadOnly(); AllPrivilegesHeld = all_privileges_held; }
public static extern NtStatus NtAccessCheckByType( SafeBuffer SecurityDescriptor, SafeHandle PrincipalSelfSid, SafeKernelObjectHandle ClientToken, AccessMask DesiredAccess, [In] ObjectTypeList[] ObjectTypeList, int ObjectTypeListLength, ref GenericMapping GenericMapping, SafePrivilegeSetBuffer RequiredPrivilegesBuffer, ref int BufferLength, out AccessMask GrantedAccess, out NtStatus AccessStatus);
/// <summary> /// Do an access check between a security descriptor and a token to determine the allowed access. /// </summary> /// <param name="sd">The security descriptor</param> /// <param name="token">The access token.</param> /// <param name="access_rights">The set of access rights to check against</param> /// <param name="principal">An optional principal SID used to replace the SELF SID in a security descriptor.</param> /// <param name="generic_mapping">The type specific generic mapping (get from corresponding NtType entry).</param> /// <returns>The allowed access mask as a unsigned integer.</returns> /// <exception cref="NtException">Thrown if an error occurred in the access check.</exception> public static AccessMask GetAllowedAccess(SecurityDescriptor sd, NtToken token, AccessMask access_rights, Sid principal, GenericMapping generic_mapping) { if (sd == null) { throw new ArgumentNullException("sd"); } if (token == null) { throw new ArgumentNullException("token"); } if (access_rights.IsEmpty) { return(AccessMask.Empty); } using (SafeBuffer sd_buffer = sd.ToSafeBuffer()) { using (NtToken imp_token = DuplicateForAccessCheck(token)) { using (var privs = new SafePrivilegeSetBuffer()) { int buffer_length = privs.Length; using (var self_sid = principal != null ? principal.ToSafeBuffer() : SafeSidBufferHandle.Null) { NtSystemCalls.NtAccessCheckByType(sd_buffer, self_sid, imp_token.Handle, access_rights, SafeHGlobalBuffer.Null, 0, ref generic_mapping, privs, ref buffer_length, out AccessMask granted_access, out NtStatus result_status).ToNtException(); if (result_status.IsSuccess()) { return(granted_access); } return(AccessMask.Empty); } } } } }
public static extern NtStatus NtPrivilegeCheck( SafeKernelObjectHandle ClientToken, SafePrivilegeSetBuffer RequiredPrivileges, [MarshalAs(UnmanagedType.U1)] out bool Result);
internal AccessCheckResult(NtStatus status, AccessMask granted_access, SafePrivilegeSetBuffer privilege_set) { Status = status; GrantedAccess = granted_access; PrivilegesRequired = privilege_set?.GetPrivileges() ?? new TokenPrivilege[0]; }