> Windows Syscalls
ntoskrnl.exeT1562.002T1106

NtAccessCheckByTypeResultListAndAuditAlarm

Typed access check returning a per-type result list, while writing audit-alarm entries to the Security event log.

Prototype

NTSTATUS NtAccessCheckByTypeResultListAndAuditAlarm(
  PUNICODE_STRING       SubsystemName,
  PVOID                 HandleId,
  PUNICODE_STRING       ObjectTypeName,
  PUNICODE_STRING       ObjectName,
  PSECURITY_DESCRIPTOR  SecurityDescriptor,
  PSID                  PrincipalSelfSid,
  ACCESS_MASK           DesiredAccess,
  AUDIT_EVENT_TYPE      AuditType,
  ULONG                 Flags,
  POBJECT_TYPE_LIST     ObjectTypeList,
  ULONG                 ObjectTypeListLength,
  PGENERIC_MAPPING      GenericMapping,
  BOOLEAN               ObjectCreation,
  PACCESS_MASK          GrantedAccessList,
  PNTSTATUS             AccessStatusList,
  PBOOLEAN              GenerateOnClose
);

Arguments

NameTypeDirDescription
SubsystemNamePUNICODE_STRINGinSubsystem identifier, e.g. L"Security". Stored in every emitted audit event.
HandleIdPVOIDinOpaque correlation handle ID surfaced in the audit event.
ObjectTypeNamePUNICODE_STRINGinTop-level object type name, e.g. L"DS-Object", L"File".
ObjectNamePUNICODE_STRINGinObject instance name (DN, path, kernel-object name) recorded in the audit event.
SecurityDescriptorPSECURITY_DESCRIPTORinSecurity descriptor with DACL + SACL — both are consulted (DACL for access, SACL for audit).
PrincipalSelfSidPSIDinOptional SID substituted for PRINCIPAL_SELF placeholders in the DACL/SACL.
DesiredAccessACCESS_MASKinAccess rights to evaluate per object-type-list entry.
AuditTypeAUDIT_EVENT_TYPEinAuditEventObjectAccess or AuditEventDirectoryServiceAccess — picks the audit category.
FlagsULONGinReserved / behavior modifiers (e.g. AUDIT_ALLOW_NO_PRIVILEGE).
ObjectTypeListPOBJECT_TYPE_LISTinHierarchy-flattened list of types (object + property sets + properties).
ObjectTypeListLengthULONGinNumber of ObjectTypeList entries; sizes the two output arrays.
GenericMappingPGENERIC_MAPPINGinPer-type GENERIC_* -> specific-rights mapping.
ObjectCreationBOOLEANinTRUE for object creation (logged as create), FALSE for opening an existing object.
GrantedAccessListPACCESS_MASKoutPer-entry granted access masks.
AccessStatusListPNTSTATUSoutPer-entry NTSTATUS (STATUS_SUCCESS / STATUS_ACCESS_DENIED).
GenerateOnClosePBOOLEANoutTRUE if the caller must later invoke NtCloseObjectAuditAlarm to emit the matching close event.

Syscall IDs by Windows version

Windows versionSyscall IDBuild
Win10 15070x65win10-1507
Win10 16070x65win10-1607
Win10 17030x65win10-1703
Win10 17090x65win10-1709
Win10 18030x65win10-1803
Win10 18090x65win10-1809
Win10 19030x65win10-1903
Win10 19090x65win10-1909
Win10 20040x65win10-2004
Win10 20H20x65win10-20h2
Win10 21H10x65win10-21h1
Win10 21H20x65win10-21h2
Win10 22H20x65win10-22h2
Win11 21H20x65win11-21h2
Win11 22H20x65win11-22h2
Win11 23H20x65win11-23h2
Win11 24H20x65win11-24h2
Server 20160x65winserver-2016
Server 20190x65winserver-2019
Server 20220x65winserver-2022
Server 20250x65winserver-2025

Kernel module

ntoskrnl.exeNtAccessCheckByTypeResultListAndAuditAlarm

Related APIs

AccessCheckByTypeResultListAndAuditAlarmWAccessCheckByTypeResultListAndAuditAlarmByHandleWNtAccessCheckByTypeResultListNtAccessCheckByTypeAndAuditAlarmNtCloseObjectAuditAlarm

Syscall stub

4C 8B D1            mov r10, rcx
B8 65 00 00 00      mov eax, 0x65
F6 04 25 08 03 FE 7F 01   test byte ptr [0x7FFE0308], 1
75 03               jne short +3
0F 05               syscall
C3                  ret
CD 2E               int 2Eh
C3                  ret

Undocumented notes

Among the longest-prototype syscalls in the Native API — 15 arguments, owing to the combination of typed access checking (object + property-set hierarchy) with audit-alarm emission. It is the union of NtAccessCheckByTypeResultList (result vector) and NtAccessCheckByTypeAndAuditAlarm (audit emission). Used almost exclusively by ntdsa.dll inside lsass.exe to evaluate Active Directory object reads/writes where the result must be both per-property-set AND logged. The SACL of the AD object drives whether any Security event 4662 ("An operation was performed on an object") is emitted; the per-entry decision drives whether the operation is rejected. SSN `0x65` has been stable since Windows 10 1507.

Common malware usage

Essentially zero. The function is too specialized — caller must marshal a valid OBJECT_TYPE_LIST, hold SeAuditPrivilege, and every successful call generates a 4662 in the Security log. Commodity malware does the opposite: it either bypasses access checks entirely (token theft via NtImpersonateThread + SeDebugPrivilege) or, on a DC, abuses Replication Get-Changes-All via legitimate RPC paths (DCSync) so the SACL evaluation happens on ntdsa's behalf with logs going to the *defenders*. No in-the-wild malware family is known to invoke this syscall directly.

Detection opportunities

This syscall is the engine behind Active Directory object-access auditing (Event 4662, 4663, 4690). Defenders should ensure Advanced Audit Policy `Audit Directory Service Access` and `Audit Directory Service Changes` are enabled on every domain controller, with SACLs configured on sensitive containers (Domain NC head, AdminSDHolder, Krbtgt account). A sudden drop in 4662 volume on a DC, especially during otherwise-busy hours, is a strong signal of audit subsystem tampering (T1562.002) — possibly via NtFlushKey on the Eventlog hive, registry edits to SACL, or driver-based SRM hooks.

Direct syscall examples

asmx64 direct stub

; Direct syscall stub for NtAccessCheckByTypeResultListAndAuditAlarm (SSN 0x65)
NtAccessCheckByTypeResultListAndAuditAlarm PROC
    mov  r10, rcx          ; syscall convention
    mov  eax, 65h          ; SSN
    syscall
    ret
NtAccessCheckByTypeResultListAndAuditAlarm ENDP

cWin32 wrapper (advapi32)

// AccessCheckByTypeResultListAndAuditAlarmW marshals OBJECT_TYPE_LIST_W and
// dispatches to the Nt-level entry point.
UNICODE_STRING sub  = RTL_CONSTANT_STRING(L"Security");
UNICODE_STRING tname= RTL_CONSTANT_STRING(L"DS-Object");
UNICODE_STRING oname= RTL_CONSTANT_STRING(L"CN=krbtgt,CN=Users,DC=contoso,DC=com");
ACCESS_MASK granted[2] = {0};
NTSTATUS    statuses[2] = {STATUS_ACCESS_DENIED, STATUS_ACCESS_DENIED};
BOOLEAN     gen_on_close = FALSE;

NTSTATUS rc = NtAccessCheckByTypeResultListAndAuditAlarm(
    &sub,
    (PVOID)0xABCD1234,
    &tname, &oname,
    pSd, NULL,
    READ_CONTROL | ADS_RIGHT_DS_READ_PROP,
    AuditEventDirectoryServiceAccess,
    0,
    pObjectTypeList, 2,
    &g_DsGenericMapping,
    FALSE,
    granted, statuses,
    &gen_on_close);

// Each successful entry emits a 4662 carrying the object DN and the GUID
// of the property set evaluated.

rustwindows-sys Win32 advapi32 wrapper

// AccessCheckByTypeResultListAndAuditAlarmW in windows-sys::Win32::Security::Authorization.
use windows_sys::Win32::Security::Authorization::*;
use windows_sys::Win32::Security::*;

unsafe {
    let mut granted = [0u32; 2];
    let mut status  = [0i32; 2];
    let mut gen_on_close: i32 = 0;

    let rc = AccessCheckByTypeResultListAndAuditAlarmW(
        windows_sys::w!("Security"),
        handle_id as *mut _,
        windows_sys::w!("DS-Object"),
        windows_sys::w!("CN=krbtgt,CN=Users,DC=contoso,DC=com"),
        sd_ptr, std::ptr::null_mut(),
        ADS_RIGHT_DS_READ_PROP.0 as u32 | READ_CONTROL,
        otl.as_ptr(), otl.len() as u32,
        0, // ObjectCreation == FALSE
        granted.as_mut_ptr(), status.as_mut_ptr(),
        &mut gen_on_close,
    );
}

MITRE ATT&CK mappings

Last verified: 2026-05-20