NtAlpcQueryInformation
Fragt Metadaten eines ALPC-Ports ab — Besitzer-Prozess, Message-Statistiken, Server-SID, Port-Attribute.
Prototyp
NTSTATUS NtAlpcQueryInformation( HANDLE PortHandle, ALPC_PORT_INFORMATION_CLASS PortInformationClass, PVOID PortInformation, ULONG Length, PULONG ReturnLength );
Argumente
| Name | Type | Dir | Description |
|---|---|---|---|
| PortHandle | HANDLE | in | Handle auf einen ALPC-Connection-, Communication- oder Server-Port. NULL für AlpcBasicInformation-Abfragen gegen die Port-Tabelle des aufrufenden Prozesses. |
| PortInformationClass | ALPC_PORT_INFORMATION_CLASS | in | AlpcBasicInformation (0), AlpcPortInformation (1), AlpcAssociateCompletionPortInformation (2), AlpcConnectedSIDInformation (3), AlpcServerInformation (4), AlpcMessageZoneInformation (5), AlpcRegisterCompletionListInformation (6), AlpcUnregisterCompletionListInformation (7), AlpcAdjustCompletionListConcurrencyCount (8), AlpcRegisterCallbackInformation (9), AlpcCompletionListRundownInformation (10), AlpcWaitForPortReferences (11). |
| PortInformation | PVOID | in/out | Puffer für die infoklasse-spezifische Struktur (z. B. ALPC_BASIC_INFORMATION, ALPC_SERVER_INFORMATION). |
| Length | ULONG | in | Größe von PortInformation in Bytes. |
| ReturnLength | PULONG | out | Empfängt die Anzahl geschriebener Bytes; bei STATUS_INFO_LENGTH_MISMATCH die benötigte Größe. |
Syscall-IDs pro Windows-Version
| Windows-Version | Syscall-ID | Build |
|---|---|---|
| Win10 1507 | 0x85 | win10-1507 |
| Win10 1607 | 0x85 | win10-1607 |
| Win10 1703 | 0x86 | win10-1703 |
| Win10 1709 | 0x86 | win10-1709 |
| Win10 1803 | 0x87 | win10-1803 |
| Win10 1809 | 0x87 | win10-1809 |
| Win10 1903 | 0x87 | win10-1903 |
| Win10 1909 | 0x87 | win10-1909 |
| Win10 2004 | 0x89 | win10-2004 |
| Win10 20H2 | 0x89 | win10-20h2 |
| Win10 21H1 | 0x89 | win10-21h1 |
| Win10 21H2 | 0x89 | win10-21h2 |
| Win10 22H2 | 0x89 | win10-22h2 |
| Win11 21H2 | 0x89 | win11-21h2 |
| Win11 22H2 | 0x89 | win11-22h2 |
| Win11 23H2 | 0x89 | win11-23h2 |
| Win11 24H2 | 0x8B | win11-24h2 |
| Server 2016 | 0x85 | winserver-2016 |
| Server 2019 | 0x87 | winserver-2019 |
| Server 2022 | 0x89 | winserver-2022 |
| Server 2025 | 0x8B | winserver-2025 |
Kernel-Modul
Verwandte APIs
Syscall-Stub
4C 8B D1 mov r10, rcx B8 8B 00 00 00 mov eax, 0x8B 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
Undokumentierte Hinweise
Das Introspektions-Pendant zu `NtAlpcSetInformation`. Am häufigsten genutzte Klassen: `AlpcBasicInformation` (Port-Flags, Attribute, Ref-Counts), `AlpcServerInformation` (löst ein Port-Handle in den *Server*-Prozess auf — aus einem Client-Port liefert sie die PID des den Connection-Port hostenden Prozesses) und `AlpcConnectedSIDInformation` (liefert die SID auf der Gegenseite). `AlpcServerInformation` ist insofern besonders, als es eine `ProcessId` als Eingabe akzeptiert und Server-Port-Infos zurückgibt — historisch ein Fingerprinting-/Enumerationstrick. Kein öffentlicher Win32-Wrapper; SystemInformer und ProcessHacker rufen es direkt zum Füllen ihrer ALPC-Port-Listen.
Häufige Malware-Nutzung
Wird von ALPC-aware-Recon-Tools verwendet: aus einem `ncalrpc`-Endpoint löst `AlpcServerInformation` die hostende PID auf — nützlich, um zu verifizieren, dass man tatsächlich mit (z. B.) `services.exe` spricht und nicht mit einem Fake-Endpoint, oder umgekehrt, um vor einem LPE-Versuch zu identifizieren, welcher Prozess einen hochwertigen LRPC-Port besitzt. Anti-Sandbox-Checks enumerieren gelegentlich ALPC-Ports, um Cuckoo- / Joe-Sandbox-Agent-Endpoints zu erkennen (ältere Versionen zeigten identifizierbare LRPC-Namen). Ansonsten ein passiver Query-Syscall mit minimalem Direkt-Missbrauchssignal.
Erkennungsmöglichkeiten
Geringer Wert als primäre Detektion. ALPC-Introspektion betreibt die Hälfte der mit Windows ausgelieferten Diagnose-Tools (`tasklist /svc`, `wmic`, die neuen `Get-Process`-PowerShell-Cmdlets, die `sysinternals`-Suite). Der ETW-Provider `Microsoft-Windows-Kernel-ALPC` emittiert zwar Query-Events, ist aber extrem laut. Die Blue-Team-Taktik: diesen Syscall ignorieren und stattdessen auf das nachfolgende alerten — ein `NtAlpcConnectPort` aus einem Nicht-System-Binary auf einen hochwertigen LRPC-Port, dessen Besitzer gerade abgefragt wurde.
Direkte Syscall-Beispiele
asmx64 direct stub (Win11 24H2)
; Direct syscall stub for NtAlpcQueryInformation (SSN 0x8B on Win11 24H2)
NtAlpcQueryInformation PROC
mov r10, rcx ; PortHandle
mov eax, 8Bh ; SSN — drifts per build
syscall
ret
NtAlpcQueryInformation ENDPcResolve an ALPC client port to its server PID
// AlpcServerInformation (class 4) accepts a ProcessId in the IN side of the
// ALPC_SERVER_INFORMATION struct and returns the server-port name & flags.
#include <windows.h>
#include <winternl.h>
typedef enum _ALPC_PORT_INFORMATION_CLASS {
AlpcBasicInformation = 0,
AlpcServerInformation = 4,
AlpcConnectedSIDInformation = 3,
} ALPC_PORT_INFORMATION_CLASS;
typedef struct _ALPC_SERVER_INFORMATION_IN {
HANDLE ProcessId;
} ALPC_SERVER_INFORMATION_IN;
typedef struct _ALPC_SERVER_INFORMATION_OUT {
BOOLEAN ThreadBlocked;
HANDLE ConnectedProcessId;
UNICODE_STRING ConnectionPortName;
} ALPC_SERVER_INFORMATION_OUT;
typedef union _ALPC_SERVER_INFORMATION {
ALPC_SERVER_INFORMATION_IN In;
ALPC_SERVER_INFORMATION_OUT Out;
} ALPC_SERVER_INFORMATION;
typedef NTSTATUS (NTAPI *pNtAlpcQueryInformation)(
HANDLE, ALPC_PORT_INFORMATION_CLASS, PVOID, ULONG, PULONG);
NTSTATUS WhoOwnsPort(HANDLE hClientPort, ALPC_SERVER_INFORMATION_OUT *out) {
ALPC_SERVER_INFORMATION info = {0};
ULONG ret = 0;
pNtAlpcQueryInformation fn = (pNtAlpcQueryInformation)GetProcAddress(
GetModuleHandleA("ntdll.dll"), "NtAlpcQueryInformation");
NTSTATUS st = fn(hClientPort, AlpcServerInformation,
&info, sizeof(info), &ret);
if (NT_SUCCESS(st)) *out = info.Out;
return st;
}MITRE ATT&CK-Mappings
Last verified: 2026-05-20