HyperDbg Debugger
Loading...
Searching...
No Matches
Kd.c File Reference

Routines related to kernel mode debugging. More...

#include "pch.h"

Functions

VOID KdInitializeKernelDebugger ()
 initialize kernel debugger
 
VOID KdUninitializeKernelDebugger ()
 uninitialize kernel debugger
 
BOOLEAN KdCheckImmediateMessagingMechanism (UINT32 OperationCode)
 Checks whether the immediate messaging mechism is needed or not.
 
VOID KdInitializeInstantEventPools ()
 Initialize the required pools for instant events.
 
VOID KdDummyDPC (PKDPC Dpc, PVOID DeferredContext, PVOID SystemArgument1, PVOID SystemArgument2)
 A test function for DPC.
 
VOID KdFireDpc (PVOID Routine, PVOID Parameter)
 Add a DPC to dpc queue.
 
BOOLEAN KdQueryDebuggerQueryThreadOrProcessTracingDetailsByCoreId (UINT32 CoreId, DEBUGGER_THREAD_PROCESS_TRACING TracingType)
 Query for process/thread interception status.
 
_Use_decl_annotations_ BYTE KdComputeDataChecksum (PVOID Buffer, UINT32 Length)
 calculate the checksum of received buffer from debugger
 
_Use_decl_annotations_ BOOLEAN KdResponsePacketToDebugger (DEBUGGER_REMOTE_PACKET_TYPE PacketType, DEBUGGER_REMOTE_PACKET_REQUESTED_ACTION Response, CHAR *OptionalBuffer, UINT32 OptionalBufferLength)
 Sends a HyperDbg response packet to the debugger.
 
_Use_decl_annotations_ BOOLEAN KdLoggingResponsePacketToDebugger (CHAR *OptionalBuffer, UINT32 OptionalBufferLength, UINT32 OperationCode)
 Sends a HyperDbg logging response packet to the debugger.
 
VOID KdHandleDebugEventsWhenKernelDebuggerIsAttached (PROCESSOR_DEBUGGING_STATE *DbgState, BOOLEAN TrapSetByDebugger)
 Handles debug events when kernel-debugger is attached.
 
VOID KdApplyTasksPreHaltCore (PROCESSOR_DEBUGGING_STATE *DbgState)
 before halting any core, all the tasks will be applied to all cores including the main core
 
VOID KdApplyTasksPostContinueCore (PROCESSOR_DEBUGGING_STATE *DbgState)
 before continue any core, all the tasks will be applied to all cores including the main core
 
_Use_decl_annotations_ VOID KdContinueDebuggee (PROCESSOR_DEBUGGING_STATE *DbgState, BOOLEAN PauseBreaksUntilSpecialMessageSent, DEBUGGER_REMOTE_PACKET_REQUESTED_ACTION SpeialEventResponse)
 continue the debuggee, this function guarantees that all other cores are continued (except current core)
 
VOID KdContinueDebuggeeJustCurrentCore (PROCESSOR_DEBUGGING_STATE *DbgState)
 continue the debuggee, just the current operating core
 
_Use_decl_annotations_ BOOLEAN KdReadRegisters (PROCESSOR_DEBUGGING_STATE *DbgState, PDEBUGGEE_REGISTER_READ_DESCRIPTION ReadRegisterRequest)
 read registers
 
_Use_decl_annotations_ BOOLEAN KdReadMemory (PGUEST_REGS Regs, PDEBUGGEE_REGISTER_READ_DESCRIPTION ReadRegisterRequest)
 read registers
 
BOOLEAN KdSwitchCore (PROCESSOR_DEBUGGING_STATE *DbgState, DEBUGGEE_CHANGE_CORE_PACKET *ChangeCorePacket)
 change the current operating core to new core
 
VOID KdCheckUserModePriorityBuffers ()
 Check the user-mode priority buffer.
 
VOID KdCloseConnectionAndUnloadDebuggee ()
 Notify user-mode to unload the debuggee and close the connections.
 
_Use_decl_annotations_ VOID KdReloadSymbolDetailsInDebuggee (PDEBUGGEE_SYMBOL_REQUEST_PACKET SymPacket)
 Notify user-mode to re-send (reload) the symbol packets.
 
VOID KdNotifyDebuggeeForUserInput (DEBUGGEE_USER_INPUT_PACKET *Descriptor, UINT32 Len)
 Notify user-mode to about new user-input buffer.
 
VOID KdSendFormatsFunctionResult (UINT64 Value)
 Notify user-mode to unload the debuggee and close the connections.
 
VOID KdSendCommandFinishedSignal (UINT32 CoreId)
 Notify debugger that the execution of command finished.
 
_Use_decl_annotations_ VOID KdHandleHaltsWhenNmiReceivedFromVmxRoot (PROCESSOR_DEBUGGING_STATE *DbgState)
 Tries to get the lock and won't return until successfully get the lock.
 
VOID KdCustomDebuggerBreakSpinlockLock (PROCESSOR_DEBUGGING_STATE *DbgState, volatile LONG *Lock)
 Tries to get the lock and won't return until successfully get the lock.
 
VOID KdHandleNmiBroadcastDebugBreaks (UINT32 CoreId, BOOLEAN IsOnVmxNmiHandler)
 Handle broadcast NMIs for halting cores in vmx-root mode.
 
_Use_decl_annotations_ VOID KdHandleBreakpointAndDebugBreakpointsCallback (UINT32 CoreId, DEBUGGEE_PAUSING_REASON Reason, PDEBUGGER_TRIGGERED_EVENT_DETAILS EventDetails)
 Handle #DBs and #BPs for kernel debugger.
 
_Use_decl_annotations_ VOID KdHandleRegisteredMtfCallback (UINT32 CoreId)
 Handle #DBs and #BPs for kernel debugger.
 
_Use_decl_annotations_ VOID KdHandleBreakpointAndDebugBreakpoints (PROCESSOR_DEBUGGING_STATE *DbgState, DEBUGGEE_PAUSING_REASON Reason, PDEBUGGER_TRIGGERED_EVENT_DETAILS EventDetails)
 Handle #DBs and #BPs for kernel debugger.
 
_Use_decl_annotations_ BOOLEAN KdCheckAndHandleNmiCallback (UINT32 CoreId)
 Handle NMI vm-exits.
 
_Use_decl_annotations_ VOID KdHandleNmi (PROCESSOR_DEBUGGING_STATE *DbgState)
 Handle NMI Vm-exits.
 
VOID KdGuaranteedStepInstruction (PROCESSOR_DEBUGGING_STATE *DbgState)
 apply a guaranteed step one instruction to the debuggee
 
BOOLEAN KdCheckGuestOperatingModeChanges (UINT16 PreviousCsSelector, UINT16 CurrentCsSelector)
 Check if the execution mode (kernel-mode to user-mode or user-mode to kernel-mode) changed.
 
VOID KdRegularStepInInstruction (PROCESSOR_DEBUGGING_STATE *DbgState)
 Regular step-in | step one instruction to the debuggee.
 
VOID KdRegularStepOver (PROCESSOR_DEBUGGING_STATE *DbgState, BOOLEAN IsNextInstructionACall, UINT32 CallLength)
 Regular step-over | step one instruction to the debuggee if there is a call then it jumps the call.
 
BOOLEAN KdPerformRegisterEvent (PDEBUGGEE_EVENT_AND_ACTION_HEADER_FOR_REMOTE_PACKET EventDetailHeader, DEBUGGER_EVENT_AND_ACTION_RESULT *DebuggerEventAndActionResult)
 Send event registration buffer to user-mode to register the event.
 
BOOLEAN KdPerformAddActionToEvent (PDEBUGGEE_EVENT_AND_ACTION_HEADER_FOR_REMOTE_PACKET ActionDetailHeader, DEBUGGER_EVENT_AND_ACTION_RESULT *DebuggerEventAndActionResult)
 Send action buffer to user-mode to be added to the event.
 
VOID KdQueryRflagTrapState ()
 Query state of the RFLAG's traps.
 
BOOLEAN KdCheckAllCoresAreLocked ()
 Check whether all cores are locked or not.
 
BOOLEAN KdCheckTargetCoreIsLocked (UINT32 CoreNumber)
 Check whether a specific target core is locked or not.
 
VOID KdQuerySystemState ()
 Query state of the system.
 
VOID KdUnlockTheHaltedCore (PROCESSOR_DEBUGGING_STATE *DbgState)
 unlock the target core
 
BOOLEAN KdCheckTheHaltedCore (PROCESSOR_DEBUGGING_STATE *DbgState)
 check the lock state of the target core
 
BOOLEAN KdBringPagein (PROCESSOR_DEBUGGING_STATE *DbgState, PDEBUGGER_PAGE_IN_REQUEST PageinRequest)
 routines to break page-in
 
VOID KdPerformTheTestPacketOperation (PROCESSOR_DEBUGGING_STATE *DbgState, DEBUGGER_DEBUGGER_TEST_QUERY_BUFFER *TestQueryPacket)
 Perform the test packet's operation.
 
VOID KdPerformSettingTheStateOfShortCircuiting (PROCESSOR_DEBUGGING_STATE *DbgState, PDEBUGGER_SHORT_CIRCUITING_EVENT ShortCircuitingEvent)
 Perform modify the state of short-circuiting.
 
BOOLEAN KdPerformEventQueryAndModification (PDEBUGGER_MODIFY_EVENTS ModifyAndQueryEvent)
 Perform modify and query events.
 
VOID KdDispatchAndPerformCommandsFromDebugger (PROCESSOR_DEBUGGING_STATE *DbgState)
 This function applies commands from the debugger to the debuggee.
 
BOOLEAN KdIsGuestOnUsermode32Bit ()
 determines if the guest was in 32-bit user-mode or 64-bit (long mode)
 
VOID KdManageSystemHaltOnVmxRoot (PROCESSOR_DEBUGGING_STATE *DbgState, PDEBUGGER_TRIGGERED_EVENT_DETAILS EventDetails)
 manage system halt on vmx-root mode
 
VOID KdBroadcastHaltOnAllCores ()
 routines for broadcast system halt
 
VOID KdHaltSystem (PDEBUGGER_PAUSE_PACKET_RECEIVED PausePacket)
 Halt the system.
 

Detailed Description

Routines related to kernel mode debugging.

Author
Sina Karvandi (sina@.nosp@m.hype.nosp@m.rdbg..nosp@m.org)
Alee Amini (alee@.nosp@m.hype.nosp@m.rdbg..nosp@m.org)
Version
0.1
Date
2020-12-20

Function Documentation

◆ KdApplyTasksPostContinueCore()

VOID KdApplyTasksPostContinueCore ( PROCESSOR_DEBUGGING_STATE * DbgState)

before continue any core, all the tasks will be applied to all cores including the main core

these tasks will be applied in vmx-root

Parameters
DbgStateThe state of the debugger on the current core
Returns
VOID
557{
558 //
559 // Check to apply hardware debug register breakpoints for step-over
560 //
561 if (DbgState->HardwareDebugRegisterForStepping != (UINT64)NULL)
562 {
565 FALSE,
567
569 }
570}
#define FALSE
Definition BasicTypes.h:54
unsigned __int64 UINT64
Definition BasicTypes.h:21
@ BREAK_ON_INSTRUCTION_FETCH
Definition DataTypes.h:70
BOOLEAN SetDebugRegisters(UINT32 DebugRegNum, DEBUG_REGISTER_TYPE ActionType, BOOLEAN ApplyToVmcs, UINT64 TargetAddress)
Configure hardware debug register for access, write and fetch breakpoints.
Definition DebugRegisters.c:37
#define DEBUGGER_DEBUG_REGISTER_FOR_STEP_OVER
debug register for step-over
Definition Debugger.h:21
UINT64 HardwareDebugRegisterForStepping
Definition State.h:183

◆ KdApplyTasksPreHaltCore()

VOID KdApplyTasksPreHaltCore ( PROCESSOR_DEBUGGING_STATE * DbgState)

before halting any core, all the tasks will be applied to all cores including the main core

these tasks will be applied in vmx-root

Parameters
DbgStateThe state of the debugger on the current core
Returns
VOID
518{
519 //
520 // Check to unset mov to cr3 vm-exits
521 //
523 {
524 //
525 // Disable process change detection
526 //
528 FALSE,
530 }
531
532 //
533 // Check to unset change thread alerts
534 //
536 {
537 //
538 // Disable thread change alerts
539 //
541 FALSE,
543 }
544}
#define TRUE
Definition BasicTypes.h:55
VOID ProcessEnableOrDisableThreadChangeMonitor(PROCESSOR_DEBUGGING_STATE *DbgState, BOOLEAN Enable, BOOLEAN IsSwitchByClockIntrrupt)
Enable or disable the process change monitoring detection on the running core.
Definition Process.c:220
VOID ThreadEnableOrDisableThreadChangeMonitor(PROCESSOR_DEBUGGING_STATE *DbgState, BOOLEAN Enable, BOOLEAN IsSwitchByClockIntrrupt)
Enable or disable the thread change monitoring detection on the running core.
Definition Thread.c:597
BOOLEAN InitialSetByClockInterrupt
Definition State.h:50
BOOLEAN InitialSetProcessChangeEvent
Definition State.h:47
BOOLEAN InitialSetThreadChangeEvent
Definition State.h:48
DEBUGGEE_PROCESS_OR_THREAD_TRACING_DETAILS ThreadOrProcessTracingDetails
Definition State.h:178

◆ KdBringPagein()

BOOLEAN KdBringPagein ( PROCESSOR_DEBUGGING_STATE * DbgState,
PDEBUGGER_PAGE_IN_REQUEST PageinRequest )

routines to break page-in

Parameters
DbgStateThe state of the debugger on the current core
PageinRequest
Returns
BOOLEAN
1841{
1842 //
1843 // Inject page-fault range
1844 //
1846 PageinRequest->VirtualAddressFrom,
1847 PageinRequest->VirtualAddressTo,
1848 PageinRequest->PageFaultErrorCode);
1849
1850 //
1851 // Also, set the RFLAGS.TF to intercept the process (thread) again after inject #PF
1852 //
1854
1855 //
1856 // Unset the trap flag next time that it's triggered (on current thread/process)
1857 //
1858 if (!BreakpointRestoreTheTrapFlagOnceTriggered(HANDLE_TO_UINT32(PsGetCurrentProcessId()), HANDLE_TO_UINT32(PsGetCurrentThreadId())))
1859 {
1860 //
1861 // Adjust the flags for showing there was error
1862 //
1864
1865 return FALSE;
1866 }
1867 else
1868 {
1869 //
1870 // Adjust the flags for showing the successful #PF injection
1871 //
1873
1874 return TRUE;
1875 }
1876}
BOOLEAN BreakpointRestoreTheTrapFlagOnceTriggered(UINT32 ProcessId, UINT32 ThreadId)
This function makes sure to unset the RFLAGS.TF on next trigger of #DB on the target process/thread.
Definition BreakpointCommands.c:174
#define DEBUGGER_ERROR_THE_TRAP_FLAG_LIST_IS_FULL
error, the list of threads/process trap flag is full
Definition ErrorCodes.h:411
#define DEBUGGER_OPERATION_WAS_SUCCESSFUL
General value to indicate that the operation or request was successful.
Definition ErrorCodes.h:23
VOID VmFuncSetRflagTrapFlag(BOOLEAN Set)
Set Rflag's trap flag.
Definition Export.c:110
VOID VmFuncEventInjectPageFaultRangeAddress(UINT32 CoreId, UINT64 AddressFrom, UINT64 AddressTo, UINT32 PageFaultCode)
Inject a range of page-faults.
Definition Export.c:643
#define HANDLE_TO_UINT32(_var)
Definition MetaMacros.h:39
UINT64 VirtualAddressFrom
Definition RequestStructures.h:74
UINT32 KernelStatus
Definition RequestStructures.h:78
UINT32 PageFaultErrorCode
Definition RequestStructures.h:77
UINT64 VirtualAddressTo
Definition RequestStructures.h:75
UINT32 CoreId
Definition State.h:169

◆ KdBroadcastHaltOnAllCores()

VOID KdBroadcastHaltOnAllCores ( )

routines for broadcast system halt

Returns
VOID
3362{
3363 //
3364 // Broadcast to all cores
3365 //
3366 KeGenericCallDpc(DpcRoutineVmExitAndHaltSystemAllCores, NULL);
3367}
VOID DpcRoutineVmExitAndHaltSystemAllCores(KDPC *Dpc, PVOID DeferredContext, PVOID SystemArgument1, PVOID SystemArgument2)
vm-exit and halt the system
Definition DpcRoutines.c:260

◆ KdCheckAllCoresAreLocked()

BOOLEAN KdCheckAllCoresAreLocked ( )

Check whether all cores are locked or not.

Returns
BOOLEAN
1702{
1703 ULONG ProcessorsCount;
1704
1705 ProcessorsCount = KeQueryActiveProcessorCount(0);
1706
1707 //
1708 // Query core debugging Lock info
1709 //
1710 for (size_t i = 0; i < ProcessorsCount; i++)
1711 {
1712 if (!SpinlockCheckLock(&g_DbgState[i].Lock))
1713 {
1714 //
1715 // We found one core that is not locked
1716 //
1717 return FALSE;
1718 }
1719 }
1720
1721 //
1722 // Reaching here means all cores are locked
1723 //
1724 return TRUE;
1725}
unsigned long ULONG
Definition BasicTypes.h:37
BOOLEAN SpinlockCheckLock(volatile LONG *Lock)
Check the lock without changing the state.
Definition Spinlock.c:169
PROCESSOR_DEBUGGING_STATE * g_DbgState
Save the state and variables related to debugging on each to logical core.
Definition Global.h:17

◆ KdCheckAndHandleNmiCallback()

_Use_decl_annotations_ BOOLEAN KdCheckAndHandleNmiCallback ( UINT32 CoreId)

Handle NMI vm-exits.

Parameters
CoreId

This function should be called in vmx-root mode

Returns
BOOLEAN
1323{
1324 BOOLEAN Result = FALSE;
1325 PROCESSOR_DEBUGGING_STATE * DbgState = &g_DbgState[CoreId];
1326
1327 if (DbgState->NmiState.WaitingToBeLocked)
1328 {
1329 //
1330 // The NMI wait is handled here
1331 //
1332 Result = TRUE;
1333
1334 //
1335 // Handle break of the core
1336 //
1338 {
1339 //
1340 // Handle it like an NMI is received from VMX root
1341 //
1343 }
1344 else
1345 {
1346 //
1347 // Handle halt of the current core as an NMI
1348 //
1349 KdHandleNmi(DbgState);
1350 }
1351 }
1352
1353 return Result;
1354}
UCHAR BOOLEAN
Definition BasicTypes.h:39
_Use_decl_annotations_ VOID KdHandleNmi(PROCESSOR_DEBUGGING_STATE *DbgState)
Handle NMI Vm-exits.
Definition Kd.c:1365
_Use_decl_annotations_ VOID KdHandleHaltsWhenNmiReceivedFromVmxRoot(PROCESSOR_DEBUGGING_STATE *DbgState)
Tries to get the lock and won't return until successfully get the lock.
Definition Kd.c:943
volatile BOOLEAN WaitingToBeLocked
Definition State.h:97
volatile BOOLEAN NmiCalledInVmxRootRelatedToHaltDebuggee
Definition State.h:96
Saves the debugger state.
Definition State.h:165
KD_NMI_STATE NmiState
Definition State.h:179

◆ KdCheckGuestOperatingModeChanges()

BOOLEAN KdCheckGuestOperatingModeChanges ( UINT16 PreviousCsSelector,
UINT16 CurrentCsSelector )

Check if the execution mode (kernel-mode to user-mode or user-mode to kernel-mode) changed.

Parameters
PreviousCsSelector
CurrentCsSelector
Returns
BOOLEAN
1454{
1455 PreviousCsSelector = PreviousCsSelector & ~3;
1456 CurrentCsSelector = CurrentCsSelector & ~3;
1457
1458 //
1459 // Check if the execution modes are the same or not
1460 //
1461 if (PreviousCsSelector == CurrentCsSelector)
1462 {
1463 //
1464 // Execution modes are not changed
1465 //
1466 return FALSE;
1467 }
1468
1469 if ((PreviousCsSelector == KGDT64_R3_CODE || PreviousCsSelector == KGDT64_R3_CMCODE) && CurrentCsSelector == KGDT64_R0_CODE)
1470 {
1471 //
1472 // User-mode -> Kernel-mode
1473 //
1474 LogInfo("User-mode -> Kernel-mode\n");
1475 }
1476 else if ((CurrentCsSelector == KGDT64_R3_CODE || CurrentCsSelector == KGDT64_R3_CMCODE) && PreviousCsSelector == KGDT64_R0_CODE)
1477 {
1478 //
1479 // Kernel-mode to user-mode
1480 //
1481 LogInfo("Kernel-mode -> User-mode\n");
1482 }
1483 else if (CurrentCsSelector == KGDT64_R3_CODE && PreviousCsSelector == KGDT64_R3_CMCODE)
1484 {
1485 //
1486 // A heaven's gate (User-mode 32-bit code -> User-mode 64-bit code)
1487 //
1488 LogInfo("32-bit User-mode -> 64-bit User-mode (Heaven's gate)\n");
1489 }
1490 else if (PreviousCsSelector == KGDT64_R3_CODE && CurrentCsSelector == KGDT64_R3_CMCODE)
1491 {
1492 //
1493 // A heaven's gate (User-mode 64-bit code -> User-mode 32-bit code)
1494 //
1495 LogInfo("64-bit User-mode -> 32-bit User-mode (Return from Heaven's gate)\n");
1496 }
1497 else
1498 {
1499 LogError("Err, unknown changes in cs selector during the instrumentation step-in\n");
1500 }
1501
1502 //
1503 // Execution modes are changed
1504 //
1505 return TRUE;
1506}
#define LogError(format,...)
Log in the case of error.
Definition HyperDbgHyperLogIntrinsics.h:113
#define LogInfo(format,...)
Define log variables.
Definition HyperDbgHyperLogIntrinsics.h:71
#define KGDT64_R3_CODE
Definition Common.h:127
#define KGDT64_R0_CODE
Definition Common.h:123
#define KGDT64_R3_CMCODE
Definition Common.h:125

◆ KdCheckImmediateMessagingMechanism()

BOOLEAN KdCheckImmediateMessagingMechanism ( UINT32 OperationCode)

Checks whether the immediate messaging mechism is needed or not.

Parameters
OperationCode
Returns
BOOLEAN
121{
122 return (g_KernelDebuggerState && !(OperationCode & OPERATION_MANDATORY_DEBUGGEE_BIT));
123}
#define OPERATION_MANDATORY_DEBUGGEE_BIT
If a operation use this bit in its Operation code, then it means that the operation should be perform...
Definition Constants.h:359
BOOLEAN g_KernelDebuggerState
shows whether the kernel debugger is enabled or disabled
Definition Global.h:103

◆ KdCheckTargetCoreIsLocked()

BOOLEAN KdCheckTargetCoreIsLocked ( UINT32 CoreNumber)

Check whether a specific target core is locked or not.

Parameters
CoreNumber
Returns
BOOLEAN
1735{
1736 //
1737 // Query core debugging Lock info
1738 //
1739
1740 if (!SpinlockCheckLock(&g_DbgState[CoreNumber].Lock))
1741 {
1742 //
1743 // This core is not locked
1744 //
1745 return FALSE;
1746 }
1747 else
1748 {
1749 //
1750 // Target core is locked
1751 //
1752 return TRUE;
1753 }
1754}

◆ KdCheckTheHaltedCore()

BOOLEAN KdCheckTheHaltedCore ( PROCESSOR_DEBUGGING_STATE * DbgState)

check the lock state of the target core

Parameters
DbgStateThe state of the debugger on the target core
Returns
BOOLEAN
1826{
1827 return SpinlockCheckLock(&DbgState->Lock);
1828}
volatile LONG Lock
Definition State.h:166

◆ KdCheckUserModePriorityBuffers()

VOID KdCheckUserModePriorityBuffers ( )

Check the user-mode priority buffer.

Returns
VOID
809{
810 //
811 // Check if the priority buffer is full or not
812 //
814 {
815 LogWarning("Warning, the user-mode priority buffers are full, thus the new action replaces "
816 "previously unserviced actions. As the result, some functionalities might not work correctly!\n"
817 "For more information please visit: https://docs.hyperdbg.org/tips-and-tricks/misc/instant-events\n");
818 }
819}
BOOLEAN LogCallbackCheckIfBufferIsFull(BOOLEAN Priority)
routines callback for checking if buffer is full
Definition Callback.c:100
#define LogWarning(format,...)
Log in the case of warning.
Definition HyperDbgHyperLogIntrinsics.h:99

◆ KdCloseConnectionAndUnloadDebuggee()

VOID KdCloseConnectionAndUnloadDebuggee ( )

Notify user-mode to unload the debuggee and close the connections.

Returns
VOID
828{
829 //
830 // Check if the priority buffer is full or not
831 //
833
834 //
835 // Send one byte buffer and operation codes
836 //
838 "$",
839 sizeof(CHAR),
840 TRUE);
841}
char CHAR
Definition BasicTypes.h:31
BOOLEAN LogCallbackSendBuffer(_In_ UINT32 OperationCode, _In_reads_bytes_(BufferLength) PVOID Buffer, _In_ UINT32 BufferLength, _In_ BOOLEAN Priority)
routines callback for sending buffer
Definition Callback.c:123
#define OPERATION_COMMAND_FROM_DEBUGGER_CLOSE_AND_UNLOAD_VMM
Definition Constants.h:372
VOID KdCheckUserModePriorityBuffers()
Check the user-mode priority buffer.
Definition Kd.c:808

◆ KdComputeDataChecksum()

_Use_decl_annotations_ BYTE KdComputeDataChecksum ( PVOID Buffer,
UINT32 Length )

calculate the checksum of received buffer from debugger

Parameters
Buffer
LengthReceived
Returns
BYTE
271{
272 BYTE CalculatedCheckSum = 0;
273 BYTE Temp = 0;
274 while (Length--)
275 {
276 Temp = *(BYTE *)Buffer;
277 CalculatedCheckSum = CalculatedCheckSum + Temp;
278 Buffer = (PVOID)((UINT64)Buffer + 1);
279 }
280 return CalculatedCheckSum;
281}
unsigned char BYTE
Definition BasicTypes.h:24

◆ KdContinueDebuggee()

_Use_decl_annotations_ VOID KdContinueDebuggee ( PROCESSOR_DEBUGGING_STATE * DbgState,
BOOLEAN PauseBreaksUntilSpecialMessageSent,
DEBUGGER_REMOTE_PACKET_REQUESTED_ACTION SpeialEventResponse )

continue the debuggee, this function guarantees that all other cores are continued (except current core)

Parameters
DbgStateThe state of the debugger on the current core
SpeialEventResponse
PauseBreaksUntilSpecialMessageSent
Returns
VOID
586{
587 if (PauseBreaksUntilSpecialMessageSent)
588 {
590 g_IgnoreBreaksToDebugger.SpeialEventResponse = SpeialEventResponse;
591 }
592
593 //
594 // Check if we should enable interrupts in this core or not,
595 // we have another same check in SWITCHING CORES too
596 //
598
599 //
600 // Unlock all the cores
601 //
602 ULONG ProcessorsCount = KeQueryActiveProcessorCount(0);
603 for (size_t i = 0; i < ProcessorsCount; i++)
604 {
605 SpinlockUnlock(&g_DbgState[i].Lock);
606 }
607}
VOID VmFuncCheckAndEnableExternalInterrupts(UINT32 CoreId)
Check and enable external interrupts.
Definition Export.c:505
void SpinlockUnlock(volatile LONG *Lock)
Release the lock.
Definition Spinlock.c:158
DEBUGGEE_REQUEST_TO_IGNORE_BREAKS_UNTIL_AN_EVENT g_IgnoreBreaksToDebugger
Holds the requests to pause the break of debuggee until a special event happens.
Definition Global.h:55
volatile BOOLEAN PauseBreaksUntilSpecialMessageSent
Definition Kd.h:62
DEBUGGER_REMOTE_PACKET_REQUESTED_ACTION SpeialEventResponse
Definition Kd.h:63

◆ KdContinueDebuggeeJustCurrentCore()

VOID KdContinueDebuggeeJustCurrentCore ( PROCESSOR_DEBUGGING_STATE * DbgState)

continue the debuggee, just the current operating core

Parameters
DbgStateThe state of the debugger on the current core
Returns
VOID
617{
618 //
619 // In the case of any halting event, the processor won't send NMIs
620 // to other cores if this field is set
621 //
623
624 //
625 // Unlock the current core
626 //
627 SpinlockUnlock(&DbgState->Lock);
628}
BOOLEAN DoNotNmiNotifyOtherCoresByThisCore
Definition State.h:176

◆ KdCustomDebuggerBreakSpinlockLock()

VOID KdCustomDebuggerBreakSpinlockLock ( PROCESSOR_DEBUGGING_STATE * DbgState,
volatile LONG * Lock )

Tries to get the lock and won't return until successfully get the lock.

Parameters
DbgStateThe state of the debugger on the current core
LONGLock variable
Returns
VOID
994{
995 unsigned wait = 1;
996
997 //
998 // *** Lock handling breaks ***
999 //
1000
1001 while (!SpinlockTryLock(Lock))
1002 {
1003 for (unsigned i = 0; i < wait; ++i)
1004 {
1005 _mm_pause();
1006 }
1007
1008 //
1009 // check if the core needs to be locked
1010 //
1011 if (DbgState->NmiState.WaitingToBeLocked)
1012 {
1013 //
1014 // We should ignore one MTF as we touched MTF and it's not usable anymore
1015 //
1017
1018 //
1019 // Handle break of the core
1020 //
1022 {
1023 //
1024 // Handle it like an NMI is received from VMX root
1025 //
1027 }
1028 else
1029 {
1030 //
1031 // Handle halt of the current core as an NMI
1032 //
1033 KdHandleNmi(DbgState);
1034 }
1035 }
1036
1037 //
1038 // Don't call "pause" too many times. If the wait becomes too big,
1039 // clamp it to the MaxWait.
1040 //
1041
1042 if (wait * 2 > 65536)
1043 {
1044 wait = 65536;
1045 }
1046 else
1047 {
1048 wait = wait * 2;
1049 }
1050 }
1051}
VOID VmFuncChangeIgnoreOneMtfState(UINT32 CoreId, BOOLEAN Set)
Change ignore one MTF state.
Definition Export.c:60
BOOLEAN SpinlockTryLock(volatile LONG *Lock)
Tries to get the lock otherwise returns.
Definition Spinlock.c:41

◆ KdDispatchAndPerformCommandsFromDebugger()

VOID KdDispatchAndPerformCommandsFromDebugger ( PROCESSOR_DEBUGGING_STATE * DbgState)

This function applies commands from the debugger to the debuggee.

when we reach here, we are on the first core

Parameters
DbgStateThe state of the debugger on the current core
Returns
VOID
2293{
2294 PDEBUGGEE_CHANGE_CORE_PACKET ChangeCorePacket;
2295 PDEBUGGEE_STEP_PACKET SteppingPacket;
2297 PDEBUGGER_CALLSTACK_REQUEST CallstackPacket;
2298 PDEBUGGER_SINGLE_CALLSTACK_FRAME CallstackFrameBuffer;
2300 PDEBUGGEE_REGISTER_READ_DESCRIPTION ReadRegisterPacket;
2301 PDEBUGGEE_REGISTER_WRITE_DESCRIPTION WriteRegisterPacket;
2302 PDEBUGGER_READ_MEMORY ReadMemoryPacket;
2303 PDEBUGGER_EDIT_MEMORY EditMemoryPacket;
2306 PDEBUGGEE_SCRIPT_PACKET ScriptPacket;
2307 PDEBUGGEE_USER_INPUT_PACKET UserInputPacket;
2308 PDEBUGGER_SEARCH_MEMORY SearchQueryPacket;
2309 PDEBUGGEE_BP_PACKET BpPacket;
2311 PDEBUGGER_PAGE_IN_REQUEST PageinPacket;
2312 PDEBUGGER_VA2PA_AND_PA2VA_COMMANDS Va2paPa2vaPacket;
2313 PDEBUGGEE_BP_LIST_OR_MODIFY_PACKET BpListOrModifyPacket;
2314 PDEBUGGEE_SYMBOL_REQUEST_PACKET SymReloadPacket;
2317 PDEBUGGER_MODIFY_EVENTS QueryAndModifyEventPacket;
2318 PDEBUGGER_SHORT_CIRCUITING_EVENT ShortCircuitingEventPacket;
2319 UINT32 SizeToSend = 0;
2320 BOOLEAN UnlockTheNewCore = FALSE;
2321 UINT32 ReturnSize = 0;
2322 DEBUGGEE_RESULT_OF_SEARCH_PACKET SearchPacketResult = {0};
2323 DEBUGGER_EVENT_AND_ACTION_RESULT DebuggerEventAndActionResult = {0};
2324
2325 while (TRUE)
2326 {
2327 BOOLEAN EscapeFromTheLoop = FALSE;
2328 CHAR * RecvBuffer = &DbgState->KdRecvBuffer[0];
2329 UINT32 RecvBufferLength = 0;
2330 PDEBUGGER_REMOTE_PACKET TheActualPacket = (PDEBUGGER_REMOTE_PACKET)RecvBuffer;
2331
2332 //
2333 // Zero the receiving buffer
2334 //
2335 RtlZeroMemory(RecvBuffer, MaxSerialPacketSize);
2336
2337 //
2338 // Receive the buffer in polling mode
2339 //
2340 if (!SerialConnectionRecvBuffer(RecvBuffer, &RecvBufferLength))
2341 {
2342 //
2343 // Invalid buffer
2344 //
2345 continue;
2346 }
2347
2348 if (TheActualPacket->Indicator == INDICATOR_OF_HYPERDBG_PACKET)
2349 {
2350 //
2351 // Check checksum
2352 //
2353 if (KdComputeDataChecksum((PVOID)&TheActualPacket->Indicator,
2354 RecvBufferLength - sizeof(BYTE)) != TheActualPacket->Checksum)
2355 {
2356 LogError("Err, checksum is invalid");
2357 continue;
2358 }
2359
2360 //
2361 // Check if the packet type is correct
2362 //
2364 {
2365 //
2366 // sth wrong happened, the packet is not belonging to use
2367 // nothing to do, just wait again
2368 //
2369 LogError("Err, unknown packet received from the debugger\n");
2370 continue;
2371 }
2372
2373 //
2374 // It's a HyperDbg packet
2375 //
2376 switch (TheActualPacket->RequestedActionOfThePacket)
2377 {
2379
2380 //
2381 // Unlock other cores
2382 //
2384
2385 //
2386 // No need to wait for new commands
2387 //
2388 EscapeFromTheLoop = TRUE;
2389
2390 break;
2391
2393
2394 SteppingPacket = (DEBUGGEE_STEP_PACKET *)(((CHAR *)TheActualPacket) + sizeof(DEBUGGER_REMOTE_PACKET));
2395
2396 switch (SteppingPacket->StepType)
2397 {
2400
2401 //
2402 // Guaranteed step in (i command) or used for tracking (creating call tree)
2403 //
2404
2405 //
2406 // Indicate a step
2407 //
2409
2410 //
2411 // Unlock just on core
2412 //
2414
2416 {
2417 DbgState->IgnoreDisasmInNextPacket = TRUE;
2418 }
2419
2420 //
2421 // No need to wait for new commands
2422 //
2423 EscapeFromTheLoop = TRUE;
2424
2425 break;
2426
2430
2431 //
2432 // Step-over (p command)
2433 //
2434 KdRegularStepOver(DbgState, SteppingPacket->IsCurrentInstructionACall, SteppingPacket->CallLength);
2435
2436 //
2437 // Unlock other cores
2438 //
2440
2442 {
2443 DbgState->IgnoreDisasmInNextPacket = TRUE;
2444 }
2445
2446 //
2447 // Continue to the debuggee
2448 //
2449 EscapeFromTheLoop = TRUE;
2450
2451 break;
2452
2454
2455 //
2456 // Step in (t command)
2457 //
2458
2459 //
2460 // Indicate a step
2461 //
2463
2464 //
2465 // Unlock other cores
2466 //
2468
2469 //
2470 // Continue to the debuggee
2471 //
2472 EscapeFromTheLoop = TRUE;
2473
2474 break;
2475
2476 default:
2477 break;
2478 }
2479
2480 break;
2481
2483
2484 //
2485 // Send the close buffer
2486 //
2488
2489 //
2490 // Unlock other cores
2491 //
2493
2494 //
2495 // No need to wait for new commands
2496 //
2497 EscapeFromTheLoop = TRUE;
2498
2499 break;
2500
2502
2503 ChangeCorePacket = (DEBUGGEE_CHANGE_CORE_PACKET *)(((CHAR *)TheActualPacket) + sizeof(DEBUGGER_REMOTE_PACKET));
2504
2505 //
2506 // Switch to new core
2507 //
2508 if (KdSwitchCore(DbgState, ChangeCorePacket))
2509 {
2510 //
2511 // No need to wait for new commands
2512 //
2513 EscapeFromTheLoop = TRUE;
2514
2515 //
2516 // Unlock the new core
2517 //
2518 UnlockTheNewCore = TRUE;
2519 }
2520
2521 //
2522 // Send the result of switching core back to the debuggee
2523 //
2526 (CHAR *)ChangeCorePacket,
2528
2529 //
2530 // Because we don't want two cores to send the same packets simultaneously
2531 //
2532 if (UnlockTheNewCore)
2533 {
2534 UnlockTheNewCore = FALSE;
2535 SpinlockUnlock(&g_DbgState[ChangeCorePacket->NewCore].Lock);
2536 }
2537
2538 break;
2539
2541
2542 FlushPacket = (DEBUGGER_FLUSH_LOGGING_BUFFERS *)(((CHAR *)TheActualPacket) + sizeof(DEBUGGER_REMOTE_PACKET));
2543
2544 //
2545 // Flush the buffers
2546 //
2547 DebuggerCommandFlush(FlushPacket);
2548
2549 //
2550 // Send the result of flushing back to the debuggee
2551 //
2554 (CHAR *)FlushPacket,
2556
2557 break;
2558
2560
2561 CallstackPacket = (DEBUGGER_CALLSTACK_REQUEST *)(((CHAR *)TheActualPacket) + sizeof(DEBUGGER_REMOTE_PACKET));
2562
2563 CallstackFrameBuffer = (DEBUGGER_SINGLE_CALLSTACK_FRAME *)(((CHAR *)TheActualPacket) + sizeof(DEBUGGER_REMOTE_PACKET) + sizeof(DEBUGGER_CALLSTACK_REQUEST));
2564
2565 //
2566 // If the address is null, we use the current RSP register
2567 //
2568 if (CallstackPacket->BaseAddress == (UINT64)NULL)
2569 {
2570 CallstackPacket->BaseAddress = DbgState->Regs->rsp;
2571 }
2572
2573 //
2574 // Feel the callstack frames the buffers
2575 //
2576 if (CallstackWalkthroughStack(CallstackFrameBuffer,
2577 CallstackPacket->BaseAddress,
2578 CallstackPacket->Size,
2579 CallstackPacket->Is32Bit))
2580 {
2582 }
2583 else
2584 {
2586 }
2587
2588 //
2589 // Send the result of flushing back to the debuggee
2590 //
2593 (CHAR *)CallstackPacket,
2594 (UINT32)CallstackPacket->BufferSize);
2595
2596 break;
2597
2599
2600 TestQueryPacket = (DEBUGGER_DEBUGGER_TEST_QUERY_BUFFER *)(((CHAR *)TheActualPacket) + sizeof(DEBUGGER_REMOTE_PACKET));
2601
2602 //
2603 // Perform the test packet operation
2604 //
2605 KdPerformTheTestPacketOperation(DbgState, TestQueryPacket);
2606
2607 //
2608 // Send the result of query system state to the debuggee
2609 //
2612 (CHAR *)TestQueryPacket,
2614
2615 break;
2616
2618
2619 ReadRegisterPacket = (DEBUGGEE_REGISTER_READ_DESCRIPTION *)(((CHAR *)TheActualPacket) + sizeof(DEBUGGER_REMOTE_PACKET));
2620
2621 //
2622 // Read registers
2623 //
2624 if (KdReadRegisters(DbgState, ReadRegisterPacket))
2625 {
2626 ReadRegisterPacket->KernelStatus = DEBUGGER_OPERATION_WAS_SUCCESSFUL;
2627 }
2628 else
2629 {
2631 }
2632
2633 if (ReadRegisterPacket->RegisterId == DEBUGGEE_SHOW_ALL_REGISTERS)
2634 {
2635 SizeToSend = sizeof(DEBUGGEE_REGISTER_READ_DESCRIPTION) + sizeof(GUEST_REGS) + sizeof(GUEST_EXTRA_REGISTERS);
2636 }
2637 else
2638 {
2639 SizeToSend = sizeof(DEBUGGEE_REGISTER_READ_DESCRIPTION);
2640 }
2641 //
2642 // Send the result of reading registers back to the debuggee
2643 //
2646 (CHAR *)ReadRegisterPacket,
2647 SizeToSend);
2648
2649 break;
2650
2652
2653 WriteRegisterPacket = (DEBUGGEE_REGISTER_WRITE_DESCRIPTION *)(((CHAR *)TheActualPacket) + sizeof(DEBUGGER_REMOTE_PACKET));
2654
2655 //
2656 // Write register
2657 //
2658 if (SetRegValue(DbgState->Regs, WriteRegisterPacket->RegisterId, WriteRegisterPacket->Value))
2659 {
2660 WriteRegisterPacket->KernelStatus = DEBUGGER_OPERATION_WAS_SUCCESSFUL;
2661 }
2662 else
2663 {
2665 }
2666
2667 //
2668 // Send the result of writing register back to the debuggee
2669 //
2672 (CHAR *)WriteRegisterPacket,
2674
2675 break;
2676
2678
2679 ReadMemoryPacket = (DEBUGGER_READ_MEMORY *)(((CHAR *)TheActualPacket) + sizeof(DEBUGGER_REMOTE_PACKET));
2680
2681 //
2682 // Read memory
2683 //
2684 if (DebuggerCommandReadMemoryVmxRoot(ReadMemoryPacket,
2685 (PVOID)((UINT64)ReadMemoryPacket + sizeof(DEBUGGER_READ_MEMORY)),
2686 &ReturnSize))
2687 {
2689 }
2690 else
2691 {
2692 ReadMemoryPacket->KernelStatus = DEBUGGER_ERROR_INVALID_ADDRESS;
2693 }
2694
2695 ReadMemoryPacket->ReturnLength = ReturnSize;
2696
2697 //
2698 // Send the result of reading memory back to the debuggee
2699 //
2702 (CHAR *)ReadMemoryPacket,
2703 sizeof(DEBUGGER_READ_MEMORY) + ReturnSize);
2704
2705 break;
2706
2708
2709 EditMemoryPacket = (PDEBUGGER_EDIT_MEMORY)(((CHAR *)TheActualPacket) + sizeof(DEBUGGER_REMOTE_PACKET));
2710
2711 //
2712 // Edit memory
2713 //
2714 DebuggerCommandEditMemoryVmxRoot(EditMemoryPacket);
2715
2716 //
2717 // Send the result of reading memory back to the debuggee
2718 //
2721 (CHAR *)EditMemoryPacket,
2722 sizeof(DEBUGGER_EDIT_MEMORY));
2723
2724 break;
2725
2727
2728 ChangeProcessPacket = (DEBUGGEE_DETAILS_AND_SWITCH_PROCESS_PACKET *)(((CHAR *)TheActualPacket) + sizeof(DEBUGGER_REMOTE_PACKET));
2729
2730 //
2731 // Interpret the process packet
2732 //
2733 ProcessInterpretProcess(DbgState, ChangeProcessPacket);
2734
2735 //
2736 // Send the result of switching process back to the debuggee
2737 //
2740 (CHAR *)ChangeProcessPacket,
2742
2743 break;
2744
2746
2747 ChangeThreadPacket = (DEBUGGEE_DETAILS_AND_SWITCH_THREAD_PACKET *)(((CHAR *)TheActualPacket) + sizeof(DEBUGGER_REMOTE_PACKET));
2748
2749 //
2750 // Interpret the thread packet
2751 //
2752 ThreadInterpretThread(DbgState, ChangeThreadPacket);
2753
2754 //
2755 // Send the result of switching thread back to the debuggee
2756 //
2759 (CHAR *)ChangeThreadPacket,
2761
2762 break;
2763
2765
2766 ScriptPacket = (DEBUGGEE_SCRIPT_PACKET *)(((CHAR *)TheActualPacket) + sizeof(DEBUGGER_REMOTE_PACKET));
2767
2768 //
2769 // Run the script in debuggee
2770 //
2771 if (DebuggerPerformRunScript(DbgState,
2772 NULL,
2773 ScriptPacket,
2775 {
2776 //
2777 // Set status
2778 //
2780 }
2781 else
2782 {
2783 //
2784 // Set status
2785 //
2787 }
2788
2789 //
2790 // Send the result of running script back to the debuggee
2791 //
2794 (CHAR *)ScriptPacket,
2795 sizeof(DEBUGGEE_SCRIPT_PACKET));
2796
2797 break;
2798
2800
2801 UserInputPacket = (DEBUGGEE_USER_INPUT_PACKET *)(((CHAR *)TheActualPacket) + sizeof(DEBUGGER_REMOTE_PACKET));
2802
2803 //
2804 // Send the user-input to user-mode debuggee
2805 //
2807 sizeof(DEBUGGEE_USER_INPUT_PACKET) + UserInputPacket->CommandLen);
2808
2809 //
2810 // Continue Debuggee
2811 //
2813 EscapeFromTheLoop = TRUE;
2814
2815 break;
2816
2818
2819 SearchQueryPacket = (DEBUGGER_SEARCH_MEMORY *)(((CHAR *)TheActualPacket) + sizeof(DEBUGGER_REMOTE_PACKET));
2820
2821 //
2822 // Perform the search in debuggee debuggee
2823 // Call the search wrapper
2824 //
2825
2826 if (SearchAddressWrapper(NULL,
2827 SearchQueryPacket,
2828 SearchQueryPacket->Address,
2829 SearchQueryPacket->Address + SearchQueryPacket->Length,
2830 TRUE,
2831 &SearchPacketResult.CountOfResults))
2832 {
2833 //
2834 // The search was successful
2835 //
2836 SearchPacketResult.Result = DEBUGGER_OPERATION_WAS_SUCCESSFUL;
2837 }
2838 else
2839 {
2840 //
2841 // There was an error, probably the address was not valid
2842 //
2843 SearchPacketResult.Result = DEBUGGER_ERROR_INVALID_ADDRESS;
2844 }
2845
2846 //
2847 // Send the result of the 's*' back to the debuggee
2848 //
2851 (CHAR *)&SearchPacketResult,
2853
2854 break;
2855
2857
2858 EventRegPacket = (DEBUGGEE_EVENT_AND_ACTION_HEADER_FOR_REMOTE_PACKET *)(((CHAR *)TheActualPacket) + sizeof(DEBUGGER_REMOTE_PACKET));
2859
2860 //
2861 // Parsing the event either in the VMX-root mode or pass it to the user-mode
2862 //
2863 if (KdPerformRegisterEvent(EventRegPacket, &DebuggerEventAndActionResult))
2864 {
2865 //
2866 // Continue Debuggee (Send the event buffer to user-mode debuggee)
2867 //
2869 EscapeFromTheLoop = TRUE;
2870 }
2871 else
2872 {
2873 //
2874 // Send the response of event registration to the debugger
2875 //
2878 (CHAR *)&DebuggerEventAndActionResult,
2880 }
2881
2882 break;
2883
2885
2886 AddActionPacket = (DEBUGGEE_EVENT_AND_ACTION_HEADER_FOR_REMOTE_PACKET *)(((CHAR *)TheActualPacket) + sizeof(DEBUGGER_REMOTE_PACKET));
2887
2888 //
2889 // Parsing the action either in the VMX-root mode or pass it to the user-mode
2890 //
2891 if (KdPerformAddActionToEvent(AddActionPacket, &DebuggerEventAndActionResult))
2892 {
2893 //
2894 // Continue Debuggee (Send the action buffer to user-mode debuggee)
2895 //
2897 EscapeFromTheLoop = TRUE;
2898 }
2899 else
2900 {
2901 //
2902 // Send the response of event registration to the debugger
2903 //
2906 (CHAR *)&DebuggerEventAndActionResult,
2908 }
2909
2910 break;
2911
2913
2914 QueryAndModifyEventPacket = (DEBUGGER_MODIFY_EVENTS *)(((CHAR *)TheActualPacket) + sizeof(DEBUGGER_REMOTE_PACKET));
2915
2916 //
2917 // Perform the action and check if we should continue the debuggee or not
2918 //
2919 if (KdPerformEventQueryAndModification(QueryAndModifyEventPacket))
2920 {
2921 //
2922 // Continue Debuggee
2923 //
2925 EscapeFromTheLoop = TRUE;
2926 }
2927 else
2928 {
2929 //
2930 // Send the response of event query and modification (anything other than clear)
2931 //
2934 (CHAR *)QueryAndModifyEventPacket,
2935 sizeof(DEBUGGER_MODIFY_EVENTS));
2936 }
2937
2938 break;
2939
2941
2942 ShortCircuitingEventPacket = (DEBUGGER_SHORT_CIRCUITING_EVENT *)(((CHAR *)TheActualPacket) + sizeof(DEBUGGER_REMOTE_PACKET));
2943
2944 //
2945 // Perform the action
2946 //
2947 KdPerformSettingTheStateOfShortCircuiting(DbgState, ShortCircuitingEventPacket);
2948
2949 //
2950 // Send the response of short-circuiting event
2951 //
2954 (CHAR *)ShortCircuitingEventPacket,
2956
2957 break;
2958
2960
2961 BpPacket = (DEBUGGEE_BP_PACKET *)(((CHAR *)TheActualPacket) + sizeof(DEBUGGER_REMOTE_PACKET));
2962
2963 //
2964 // Perform the action
2965 //
2966 BreakpointAddNew(BpPacket);
2967
2968 //
2969 // Send the result of the 'bp' back to the debuggee
2970 //
2973 (CHAR *)BpPacket,
2974 sizeof(DEBUGGEE_BP_PACKET));
2975
2976 break;
2977
2979
2980 PtePacket = (DEBUGGER_READ_PAGE_TABLE_ENTRIES_DETAILS *)(((CHAR *)TheActualPacket) + sizeof(DEBUGGER_REMOTE_PACKET));
2981
2982 //
2983 // Get the page table details (it's in vmx-root)
2984 //
2985 ExtensionCommandPte(PtePacket, TRUE);
2986
2987 //
2988 // Send the result of the '!pte' back to the debuggee
2989 //
2992 (CHAR *)PtePacket,
2994
2995 break;
2996
2998
2999 PageinPacket = (DEBUGGER_PAGE_IN_REQUEST *)(((CHAR *)TheActualPacket) + sizeof(DEBUGGER_REMOTE_PACKET));
3000
3001 //
3002 // Perform bringing the pages in (it's in vmx-root)
3003 //
3004 KdBringPagein(DbgState, PageinPacket);
3005
3006 //
3007 // Send the result of the '.pagein' back to the debuggee
3008 //
3011 (CHAR *)PageinPacket,
3012 sizeof(DEBUGGER_PAGE_IN_REQUEST));
3013
3014 break;
3015
3017
3018 Va2paPa2vaPacket = (DEBUGGER_VA2PA_AND_PA2VA_COMMANDS *)(((CHAR *)TheActualPacket) + sizeof(DEBUGGER_REMOTE_PACKET));
3019
3020 //
3021 // Perform the virtual to physical or physical to virtual address
3022 // conversion (it's on vmx-root mode)
3023 //
3024 ExtensionCommandVa2paAndPa2va(Va2paPa2vaPacket, TRUE);
3025
3026 //
3027 // Send the result of the '!va2pa' or '!pa2va' back to the debuggee
3028 //
3031 (CHAR *)Va2paPa2vaPacket,
3033
3034 break;
3035
3037
3038 BpListOrModifyPacket = (DEBUGGEE_BP_LIST_OR_MODIFY_PACKET *)(((CHAR *)TheActualPacket) + sizeof(DEBUGGER_REMOTE_PACKET));
3039
3040 //
3041 // Perform the action
3042 //
3043 BreakpointListOrModify(BpListOrModifyPacket);
3044
3045 //
3046 // Send the result of modify or list breakpoints to the debuggee
3047 //
3050 (CHAR *)BpListOrModifyPacket,
3052
3053 break;
3054
3056
3057 SymReloadPacket = (DEBUGGEE_SYMBOL_REQUEST_PACKET *)(((CHAR *)TheActualPacket) + sizeof(DEBUGGER_REMOTE_PACKET));
3058
3059 //
3060 // Send the reload symbol request buffer
3061 //
3062 KdReloadSymbolDetailsInDebuggee(SymReloadPacket);
3063
3064 //
3065 // Unlock other cores
3066 //
3068
3069 //
3070 // No need to wait for new commands
3071 //
3072 EscapeFromTheLoop = TRUE;
3073
3074 break;
3075
3076 default:
3077 LogError("Err, unknown packet action received from the debugger\n");
3078 break;
3079 }
3080 }
3081 else
3082 {
3083 //
3084 // It's not a HyperDbg packet, the packet is probably deformed
3085 //
3086 LogError("Err, it's not a HyperDbg packet, the packet is probably deformed\n");
3087 continue;
3088 }
3089
3090 //
3091 // If we have to leave the loop, we apply it here
3092 //
3093 if (EscapeFromTheLoop)
3094 {
3095 break;
3096 }
3097 }
3098}
unsigned int UINT32
Definition BasicTypes.h:48
struct GUEST_EXTRA_REGISTERS GUEST_EXTRA_REGISTERS
struct for extra registers
BOOLEAN BreakpointAddNew(PDEBUGGEE_BP_PACKET BpDescriptorArg)
Add new breakpoints.
Definition BreakpointCommands.c:893
BOOLEAN BreakpointListOrModify(PDEBUGGEE_BP_LIST_OR_MODIFY_PACKET ListOrModifyBreakpoints)
List of modify breakpoints.
Definition BreakpointCommands.c:1089
BOOLEAN CallstackWalkthroughStack(PDEBUGGER_SINGLE_CALLSTACK_FRAME AddressToSaveFrames, UINT64 StackBaseAddress, UINT32 Size, BOOLEAN Is32Bit)
Walkthrough the stack.
Definition Callstack.c:25
struct _DEBUGGER_REMOTE_PACKET * PDEBUGGER_REMOTE_PACKET
@ DEBUGGER_REMOTE_PACKET_TYPE_DEBUGGEE_TO_DEBUGGER
Definition Connection.h:164
@ DEBUGGER_REMOTE_PACKET_TYPE_DEBUGGER_TO_DEBUGGEE_EXECUTE_ON_VMX_ROOT
Definition Connection.h:154
@ DEBUGGER_REMOTE_PACKET_REQUESTED_ACTION_DEBUGGEE_RESULT_OF_BP
Definition Connection.h:122
@ DEBUGGER_REMOTE_PACKET_REQUESTED_ACTION_ON_VMX_ROOT_REGISTER_EVENT
Definition Connection.h:85
@ DEBUGGER_REMOTE_PACKET_REQUESTED_ACTION_DEBUGGEE_RESULT_OF_PTE
Definition Connection.h:128
@ DEBUGGER_REMOTE_PACKET_REQUESTED_ACTION_DEBUGGEE_RESULT_TEST_QUERY
Definition Connection.h:114
@ DEBUGGER_REMOTE_PACKET_REQUESTED_ACTION_ON_VMX_ROOT_SEARCH_QUERY
Definition Connection.h:84
@ DEBUGGER_REMOTE_PACKET_REQUESTED_ACTION_DEBUGGEE_RELOAD_SEARCH_QUERY
Definition Connection.h:127
@ DEBUGGER_REMOTE_PACKET_REQUESTED_ACTION_DEBUGGEE_RESULT_OF_SHORT_CIRCUITING_STATE
Definition Connection.h:123
@ DEBUGGER_REMOTE_PACKET_REQUESTED_ACTION_NO_ACTION
Definition Connection.h:103
@ DEBUGGER_REMOTE_PACKET_REQUESTED_ACTION_ON_VMX_ROOT_LIST_OR_MODIFY_BREAKPOINTS
Definition Connection.h:92
@ DEBUGGER_REMOTE_PACKET_REQUESTED_ACTION_ON_VMX_ROOT_INJECT_PAGE_FAULT
Definition Connection.h:97
@ DEBUGGER_REMOTE_PACKET_REQUESTED_ACTION_DEBUGGEE_RESULT_OF_FLUSH
Definition Connection.h:112
@ DEBUGGER_REMOTE_PACKET_REQUESTED_ACTION_ON_VMX_ROOT_EDIT_MEMORY
Definition Connection.h:90
@ DEBUGGER_REMOTE_PACKET_REQUESTED_ACTION_ON_VMX_ROOT_MODE_CONTINUE
Definition Connection.h:74
@ DEBUGGER_REMOTE_PACKET_REQUESTED_ACTION_ON_VMX_ROOT_ADD_ACTION_TO_EVENT
Definition Connection.h:86
@ DEBUGGER_REMOTE_PACKET_REQUESTED_ACTION_DEBUGGEE_RESULT_OF_ADDING_ACTION_TO_EVENT
Definition Connection.h:116
@ DEBUGGER_REMOTE_PACKET_REQUESTED_ACTION_ON_VMX_ROOT_MODE_CHANGE_CORE
Definition Connection.h:76
@ DEBUGGER_REMOTE_PACKET_REQUESTED_ACTION_DEBUGGEE_RESULT_OF_READING_REGISTERS
Definition Connection.h:119
@ DEBUGGER_REMOTE_PACKET_REQUESTED_ACTION_ON_VMX_ROOT_MODE_CHANGE_THREAD
Definition Connection.h:81
@ DEBUGGER_REMOTE_PACKET_REQUESTED_ACTION_ON_VMX_ROOT_MODE_CHANGE_PROCESS
Definition Connection.h:80
@ DEBUGGER_REMOTE_PACKET_REQUESTED_ACTION_ON_VMX_ROOT_READ_REGISTERS
Definition Connection.h:88
@ DEBUGGER_REMOTE_PACKET_REQUESTED_ACTION_DEBUGGEE_RESULT_OF_READING_MEMORY
Definition Connection.h:120
@ DEBUGGER_REMOTE_PACKET_REQUESTED_ACTION_DEBUGGEE_RESULT_OF_REGISTERING_EVENT
Definition Connection.h:115
@ DEBUGGER_REMOTE_PACKET_REQUESTED_ACTION_DEBUGGEE_RESULT_OF_WRITE_REGISTER
Definition Connection.h:131
@ DEBUGGER_REMOTE_PACKET_REQUESTED_ACTION_ON_VMX_ROOT_MODE_STEP
Definition Connection.h:73
@ DEBUGGER_REMOTE_PACKET_REQUESTED_ACTION_ON_VMX_ROOT_WRITE_REGISTER
Definition Connection.h:98
@ DEBUGGER_REMOTE_PACKET_REQUESTED_ACTION_DEBUGGEE_RESULT_OF_VA2PA_AND_PA2VA
Definition Connection.h:129
@ DEBUGGER_REMOTE_PACKET_REQUESTED_ACTION_ON_VMX_ROOT_SET_SHORT_CIRCUITING_STATE
Definition Connection.h:96
@ DEBUGGER_REMOTE_PACKET_REQUESTED_ACTION_ON_VMX_ROOT_MODE_CLOSE_AND_UNLOAD_DEBUGGEE
Definition Connection.h:75
@ DEBUGGER_REMOTE_PACKET_REQUESTED_ACTION_DEBUGGEE_RESULT_OF_EDITING_MEMORY
Definition Connection.h:121
@ DEBUGGER_REMOTE_PACKET_REQUESTED_ACTION_DEBUGGEE_RESULT_OF_CHANGING_THREAD
Definition Connection.h:109
@ DEBUGGER_REMOTE_PACKET_REQUESTED_ACTION_ON_VMX_ROOT_MODE_CALLSTACK
Definition Connection.h:78
@ DEBUGGER_REMOTE_PACKET_REQUESTED_ACTION_ON_VMX_ROOT_MODE_TEST_QUERY
Definition Connection.h:79
@ DEBUGGER_REMOTE_PACKET_REQUESTED_ACTION_ON_VMX_ROOT_QUERY_PA2VA_AND_VA2PA
Definition Connection.h:94
@ DEBUGGER_REMOTE_PACKET_REQUESTED_ACTION_DEBUGGEE_RESULT_OF_RUNNING_SCRIPT
Definition Connection.h:110
@ DEBUGGER_REMOTE_PACKET_REQUESTED_ACTION_DEBUGGEE_RESULT_OF_BRINGING_PAGES_IN
Definition Connection.h:130
@ DEBUGGER_REMOTE_PACKET_REQUESTED_ACTION_ON_VMX_ROOT_BP
Definition Connection.h:91
@ DEBUGGER_REMOTE_PACKET_REQUESTED_ACTION_ON_VMX_ROOT_READ_MEMORY
Definition Connection.h:89
@ DEBUGGER_REMOTE_PACKET_REQUESTED_ACTION_DEBUGGEE_RESULT_OF_QUERY_AND_MODIFY_EVENT
Definition Connection.h:117
@ DEBUGGER_REMOTE_PACKET_REQUESTED_ACTION_ON_VMX_ROOT_SYMBOL_QUERY_PTE
Definition Connection.h:95
@ DEBUGGER_REMOTE_PACKET_REQUESTED_ACTION_DEBUGGEE_RESULT_OF_CALLSTACK
Definition Connection.h:113
@ DEBUGGER_REMOTE_PACKET_REQUESTED_ACTION_ON_VMX_ROOT_QUERY_AND_MODIFY_EVENT
Definition Connection.h:87
@ DEBUGGER_REMOTE_PACKET_REQUESTED_ACTION_ON_VMX_ROOT_MODE_FLUSH_BUFFERS
Definition Connection.h:77
@ DEBUGGER_REMOTE_PACKET_REQUESTED_ACTION_DEBUGGEE_RESULT_OF_CHANGING_CORE
Definition Connection.h:107
@ DEBUGGER_REMOTE_PACKET_REQUESTED_ACTION_DEBUGGEE_RESULT_OF_LIST_OR_MODIFY_BREAKPOINTS
Definition Connection.h:124
@ DEBUGGER_REMOTE_PACKET_REQUESTED_ACTION_ON_VMX_ROOT_RUN_SCRIPT
Definition Connection.h:82
@ DEBUGGER_REMOTE_PACKET_REQUESTED_ACTION_ON_VMX_ROOT_SYMBOL_RELOAD
Definition Connection.h:93
@ DEBUGGER_REMOTE_PACKET_REQUESTED_ACTION_DEBUGGEE_RESULT_OF_CHANGING_PROCESS
Definition Connection.h:108
@ DEBUGGER_REMOTE_PACKET_REQUESTED_ACTION_ON_VMX_ROOT_USER_INPUT_BUFFER
Definition Connection.h:83
struct _DEBUGGER_REMOTE_PACKET DEBUGGER_REMOTE_PACKET
The structure of remote packets in HyperDbg.
#define INDICATOR_OF_HYPERDBG_PACKET
constant indicator of a HyperDbg packet
Definition Constants.h:502
#define DEBUGGEE_SHOW_ALL_REGISTERS
for reading all registers in r command.
Definition Constants.h:665
#define MaxSerialPacketSize
size of buffer for serial
Definition Constants.h:194
BOOLEAN DebuggerPerformRunScript(PROCESSOR_DEBUGGING_STATE *DbgState, DEBUGGER_EVENT_ACTION *Action, DEBUGGEE_SCRIPT_PACKET *ScriptDetails, DEBUGGER_TRIGGERED_EVENT_DETAILS *EventTriggerDetail)
Managing run script action.
Definition Debugger.c:1608
BOOLEAN DebuggerCommandEditMemoryVmxRoot(PDEBUGGER_EDIT_MEMORY EditMemRequest)
Edit physical and virtual memory on vmxroot mode.
Definition DebuggerCommands.c:555
BOOLEAN DebuggerCommandReadMemoryVmxRoot(PDEBUGGER_READ_MEMORY ReadMemRequest, UCHAR *UserBuffer, UINT32 *ReturnSize)
Read memory for different commands from vmxroot mode.
Definition DebuggerCommands.c:137
BOOLEAN SearchAddressWrapper(PUINT64 AddressToSaveResults, PDEBUGGER_SEARCH_MEMORY SearchMemRequest, UINT64 StartAddress, UINT64 EndAddress, BOOLEAN IsDebuggeePaused, PUINT32 CountOfMatchedCases)
The wrapper to check for validity of addresses and call the search routines for both physical and vir...
Definition DebuggerCommands.c:962
NTSTATUS DebuggerCommandFlush(PDEBUGGER_FLUSH_LOGGING_BUFFERS DebuggerFlushBuffersRequest)
Perform the flush requests to vmx-root and vmx non-root buffers.
Definition DebuggerCommands.c:1235
#define DEBUGGER_ERROR_INVALID_REGISTER_NUMBER
error, invalid register number
Definition ErrorCodes.h:178
#define DEBUGGER_ERROR_UNABLE_TO_GET_CALLSTACK
error, unable to get the callstack
Definition ErrorCodes.h:380
#define DEBUGGER_ERROR_INVALID_ADDRESS
error, invalid address specified for debugger
Definition ErrorCodes.h:63
#define DEBUGGER_ERROR_PREPARING_DEBUGGEE_TO_RUN_SCRIPT
error, unable to run script in remote debuggee
Definition ErrorCodes.h:172
VOID ExtensionCommandVa2paAndPa2va(PDEBUGGER_VA2PA_AND_PA2VA_COMMANDS AddressDetails, BOOLEAN OperateOnVmxRoot)
routines for !va2pa and !pa2va commands
Definition ExtensionCommands.c:23
BOOLEAN ExtensionCommandPte(PDEBUGGER_READ_PAGE_TABLE_ENTRIES_DETAILS PteDetails, BOOLEAN IsOperatingInVmxRoot)
routines for !pte command
Definition ExtensionCommands.c:170
VOID KdContinueDebuggeeJustCurrentCore(PROCESSOR_DEBUGGING_STATE *DbgState)
continue the debuggee, just the current operating core
Definition Kd.c:616
VOID KdRegularStepInInstruction(PROCESSOR_DEBUGGING_STATE *DbgState)
Regular step-in | step one instruction to the debuggee.
Definition Kd.c:1515
VOID KdPerformTheTestPacketOperation(PROCESSOR_DEBUGGING_STATE *DbgState, DEBUGGER_DEBUGGER_TEST_QUERY_BUFFER *TestQueryPacket)
Perform the test packet's operation.
Definition Kd.c:1887
_Use_decl_annotations_ VOID KdReloadSymbolDetailsInDebuggee(PDEBUGGEE_SYMBOL_REQUEST_PACKET SymPacket)
Notify user-mode to re-send (reload) the symbol packets.
Definition Kd.c:851
VOID KdNotifyDebuggeeForUserInput(DEBUGGEE_USER_INPUT_PACKET *Descriptor, UINT32 Len)
Notify user-mode to about new user-input buffer.
Definition Kd.c:876
BOOLEAN KdBringPagein(PROCESSOR_DEBUGGING_STATE *DbgState, PDEBUGGER_PAGE_IN_REQUEST PageinRequest)
routines to break page-in
Definition Kd.c:1839
VOID KdGuaranteedStepInstruction(PROCESSOR_DEBUGGING_STATE *DbgState)
apply a guaranteed step one instruction to the debuggee
Definition Kd.c:1406
BOOLEAN KdPerformEventQueryAndModification(PDEBUGGER_MODIFY_EVENTS ModifyAndQueryEvent)
Perform modify and query events.
Definition Kd.c:2084
_Use_decl_annotations_ VOID KdContinueDebuggee(PROCESSOR_DEBUGGING_STATE *DbgState, BOOLEAN PauseBreaksUntilSpecialMessageSent, DEBUGGER_REMOTE_PACKET_REQUESTED_ACTION SpeialEventResponse)
continue the debuggee, this function guarantees that all other cores are continued (except current co...
Definition Kd.c:583
_Use_decl_annotations_ BYTE KdComputeDataChecksum(PVOID Buffer, UINT32 Length)
calculate the checksum of received buffer from debugger
Definition Kd.c:270
BOOLEAN KdPerformRegisterEvent(PDEBUGGEE_EVENT_AND_ACTION_HEADER_FOR_REMOTE_PACKET EventDetailHeader, DEBUGGER_EVENT_AND_ACTION_RESULT *DebuggerEventAndActionResult)
Send event registration buffer to user-mode to register the event.
Definition Kd.c:1584
VOID KdCloseConnectionAndUnloadDebuggee()
Notify user-mode to unload the debuggee and close the connections.
Definition Kd.c:827
_Use_decl_annotations_ BOOLEAN KdReadRegisters(PROCESSOR_DEBUGGING_STATE *DbgState, PDEBUGGEE_REGISTER_READ_DESCRIPTION ReadRegisterRequest)
read registers
Definition Kd.c:639
BOOLEAN KdPerformAddActionToEvent(PDEBUGGEE_EVENT_AND_ACTION_HEADER_FOR_REMOTE_PACKET ActionDetailHeader, DEBUGGER_EVENT_AND_ACTION_RESULT *DebuggerEventAndActionResult)
Send action buffer to user-mode to be added to the event.
Definition Kd.c:1636
VOID KdPerformSettingTheStateOfShortCircuiting(PROCESSOR_DEBUGGING_STATE *DbgState, PDEBUGGER_SHORT_CIRCUITING_EVENT ShortCircuitingEvent)
Perform modify the state of short-circuiting.
Definition Kd.c:2057
BOOLEAN KdSwitchCore(PROCESSOR_DEBUGGING_STATE *DbgState, DEBUGGEE_CHANGE_CORE_PACKET *ChangeCorePacket)
change the current operating core to new core
Definition Kd.c:736
VOID KdRegularStepOver(PROCESSOR_DEBUGGING_STATE *DbgState, BOOLEAN IsNextInstructionACall, UINT32 CallLength)
Regular step-over | step one instruction to the debuggee if there is a call then it jumps the call.
Definition Kd.c:1536
_Use_decl_annotations_ BOOLEAN KdResponsePacketToDebugger(DEBUGGER_REMOTE_PACKET_TYPE PacketType, DEBUGGER_REMOTE_PACKET_REQUESTED_ACTION Response, CHAR *OptionalBuffer, UINT32 OptionalBufferLength)
Sends a HyperDbg response packet to the debugger.
Definition Kd.c:294
BOOLEAN ProcessInterpretProcess(PROCESSOR_DEBUGGING_STATE *DbgState, PDEBUGGEE_DETAILS_AND_SWITCH_PROCESS_PACKET PidRequest)
change the current process @detail ONLY TO BE USED IN KD STUFFS
Definition Process.c:525
BOOLEAN SetRegValue(PGUEST_REGS GuestRegs, UINT32 RegisterId, UINT64 Value)
Set the register value.
Definition Regs.c:963
struct _DEBUGGER_CALLSTACK_REQUEST DEBUGGER_CALLSTACK_REQUEST
request for callstack frames
@ DEBUGGER_REMOTE_STEPPING_REQUEST_INSTRUMENTATION_STEP_IN
Definition RequestStructures.h:993
@ DEBUGGER_REMOTE_STEPPING_REQUEST_INSTRUMENTATION_STEP_IN_FOR_TRACKING
Definition RequestStructures.h:994
@ DEBUGGER_REMOTE_STEPPING_REQUEST_STEP_IN
Definition RequestStructures.h:992
@ DEBUGGER_REMOTE_STEPPING_REQUEST_STEP_OVER_FOR_GU
Definition RequestStructures.h:997
@ DEBUGGER_REMOTE_STEPPING_REQUEST_STEP_OVER
Definition RequestStructures.h:996
@ DEBUGGER_REMOTE_STEPPING_REQUEST_STEP_OVER_FOR_GU_LAST_INSTRUCTION
Definition RequestStructures.h:998
struct _DEBUGGEE_REGISTER_READ_DESCRIPTION DEBUGGEE_REGISTER_READ_DESCRIPTION
Register Descriptor Structure to use in r command.
struct _DEBUGGER_EDIT_MEMORY * PDEBUGGER_EDIT_MEMORY
BOOLEAN SerialConnectionRecvBuffer(CHAR *BufferToSave, UINT32 *LengthReceived)
Receive packet from the debugger.
Definition SerialConnection.c:99
BOOLEAN ThreadInterpretThread(PROCESSOR_DEBUGGING_STATE *DbgState, PDEBUGGEE_DETAILS_AND_SWITCH_THREAD_PACKET TidRequest)
change the current thread
Definition Thread.c:325
DEBUGGER_TRIGGERED_EVENT_DETAILS g_EventTriggerDetail
Trigger event details.
Definition Global.h:133
NULL()
Definition test-case-generator.py:530
The structure of breakpoint modification requests packet in HyperDbg.
Definition RequestStructures.h:1090
The structure of bp command packet in HyperDbg.
Definition RequestStructures.h:1060
The structure of changing core packet in HyperDbg.
Definition RequestStructures.h:599
The structure of changing process and show process packet in HyperDbg.
Definition RequestStructures.h:924
The structure of changing thead and show thread packet in HyperDbg.
Definition RequestStructures.h:963
The structure of user-input packet in HyperDbg.
Definition DataTypes.h:156
Register Descriptor Structure to use in r command.
Definition RequestStructures.h:1156
UINT32 RegisterId
Definition RequestStructures.h:1157
UINT32 KernelStatus
Definition RequestStructures.h:1159
Register Descriptor Structure to write on registers.
Definition RequestStructures.h:1171
UINT64 Value
Definition RequestStructures.h:1173
UINT32 RegisterId
Definition RequestStructures.h:1172
UINT32 KernelStatus
Definition RequestStructures.h:1174
The structure of result of search packet in HyperDbg.
Definition RequestStructures.h:1142
UINT32 CountOfResults
Definition RequestStructures.h:1143
UINT32 Result
Definition RequestStructures.h:1144
The structure of script packet in HyperDbg.
Definition RequestStructures.h:1122
UINT32 Result
Definition RequestStructures.h:1126
The structure of stepping packet in HyperDbg.
Definition RequestStructures.h:1007
BOOLEAN IsCurrentInstructionACall
Definition RequestStructures.h:1014
UINT32 CallLength
Definition RequestStructures.h:1015
DEBUGGER_REMOTE_STEPPING_REQUEST StepType
Definition RequestStructures.h:1008
The structure of .sym reload packet in HyperDbg.
Definition RequestStructures.h:1047
The structure of user-input packet in HyperDbg.
Definition DataTypes.h:140
UINT32 CommandLen
Definition DataTypes.h:141
request for callstack frames
Definition RequestStructures.h:789
UINT32 Size
Definition RequestStructures.h:793
UINT32 KernelStatus
Definition RequestStructures.h:791
BOOLEAN Is32Bit
Definition RequestStructures.h:790
UINT64 BaseAddress
Definition RequestStructures.h:795
request for test query buffers
Definition RequestStructures.h:333
request for edit virtual and physical memory
Definition RequestStructures.h:482
Status of register buffers.
Definition Events.h:423
request for flushing buffers
Definition RequestStructures.h:294
request for modifying events (enable/disable/clear)
Definition Events.h:242
requests for the '.pagein' command
Definition RequestStructures.h:73
request for reading virtual and physical memory
Definition RequestStructures.h:266
UINT32 KernelStatus
Definition RequestStructures.h:275
UINT32 ReturnLength
Definition RequestStructures.h:274
request for !pte command
Definition RequestStructures.h:22
The structure of remote packets in HyperDbg.
Definition Connection.h:183
DEBUGGER_REMOTE_PACKET_REQUESTED_ACTION RequestedActionOfThePacket
Definition Connection.h:187
DEBUGGER_REMOTE_PACKET_TYPE TypeOfThePacket
Definition Connection.h:186
BYTE Checksum
Definition Connection.h:184
UINT64 Indicator
Definition Connection.h:185
request for searching memory
Definition RequestStructures.h:527
UINT64 Length
Definition RequestStructures.h:529
UINT64 Address
Definition RequestStructures.h:528
request for performing a short-circuiting event
Definition Events.h:256
The structure for saving the callstack frame of one parameter.
Definition RequestStructures.h:761
requests for !va2pa and !pa2va commands
Definition RequestStructures.h:54
GUEST_REGS * Regs
Definition State.h:168
CHAR KdRecvBuffer[MaxSerialPacketSize]
Definition State.h:188
BOOLEAN IgnoreDisasmInNextPacket
Definition State.h:171
Definition BasicTypes.h:70
UINT64 rsp
Definition BasicTypes.h:79

◆ KdDummyDPC()

VOID KdDummyDPC ( PKDPC Dpc,
PVOID DeferredContext,
PVOID SystemArgument1,
PVOID SystemArgument2 )

A test function for DPC.

Parameters
Dpc
DeferredContext
SystemArgument1
SystemArgument2
Returns
VOID
185{
186 UNREFERENCED_PARAMETER(Dpc);
187 UNREFERENCED_PARAMETER(SystemArgument1);
188 UNREFERENCED_PARAMETER(SystemArgument2);
189
190 LogInfo("I'm here %llx\n", DeferredContext);
191}

◆ KdFireDpc()

VOID KdFireDpc ( PVOID Routine,
PVOID Parameter )

Add a DPC to dpc queue.

Parameters
Routine
Parameter
ProcessorNumber
Returns
VOID
203{
204 ULONG CurrentCore = KeGetCurrentProcessorNumberEx(NULL);
205
206 KeInitializeDpc(g_DbgState[CurrentCore].KdDpcObject, (PKDEFERRED_ROUTINE)Routine, Parameter);
207
208 KeInsertQueueDpc(g_DbgState[CurrentCore].KdDpcObject, NULL, NULL);
209}

◆ KdGuaranteedStepInstruction()

VOID KdGuaranteedStepInstruction ( PROCESSOR_DEBUGGING_STATE * DbgState)

apply a guaranteed step one instruction to the debuggee

Parameters
DbgStateThe state of the debugger on the current core
Returns
VOID
1407{
1408 //
1409 // Only 16 bit is needed however, vmwrite might write on other bits
1410 // and corrupt other variables, that's why we get 64bit
1411 //
1412 UINT64 CsSel = (UINT64)NULL;
1413
1414 //
1415 // Read cs to have a trace of the execution mode of running application
1416 // in the debuggee
1417 //
1418 CsSel = VmFuncGetCsSelector();
1419
1420 DbgState->InstrumentationStepInTrace.CsSel = (UINT16)CsSel;
1421
1422 //
1423 // Set an indicator of a break in the case of an MTF
1424 //
1425 VmFuncRegisterMtfBreak(DbgState->CoreId);
1426
1427 //
1428 // Not unset MTF again
1429 //
1431
1432 //
1433 // Disable external interrupts and interrupt Window
1434 //
1436
1437 //
1438 // Set the MTF flag
1439 //
1441}
unsigned short UINT16
Definition BasicTypes.h:47
VOID VmFuncChangeMtfUnsettingState(UINT32 CoreId, BOOLEAN Set)
Suppress unsetting MTF.
Definition Export.c:47
UINT16 VmFuncGetCsSelector()
Read CS selector.
Definition Export.c:341
VOID VmFuncRegisterMtfBreak(UINT32 CoreId)
Register for break in the case of an MTF.
Definition Export.c:73
VOID VmFuncSetMonitorTrapFlag(BOOLEAN Set)
Set the monitor trap flag.
Definition Export.c:98
VOID VmFuncDisableExternalInterruptsAndInterruptWindow(UINT32 CoreId)
Disable external-interrupts and interrupt window.
Definition Export.c:518
UINT16 CsSel
Definition State.h:36
DEBUGGEE_INSTRUMENTATION_STEP_IN_TRACE InstrumentationStepInTrace
Definition State.h:175

◆ KdHaltSystem()

VOID KdHaltSystem ( PDEBUGGER_PAUSE_PACKET_RECEIVED PausePacket)

Halt the system.

Parameters
PausePacket
Returns
VOID
3377{
3378 //
3379 // Broadcast to halt everything
3380 // Instead of broadcasting we will just send one vmcall and
3381 // from that point, we halt all the other cores by NMIs, this
3382 // way we are sure that we get all the other cores at the middle
3383 // of their execution codes and not on HyperDbg routines
3384 //
3385 // KdBroadcastHaltOnAllCores();
3386 //
3387
3388 //
3389 // vm-exit and halt current core
3390 //
3392
3393 //
3394 // Set the status
3395 //
3397}
#define DEBUGGER_VMCALL_VM_EXIT_HALT_SYSTEM
VMCALL to cause vm-exit and halt the system.
Definition DebuggerVmcalls.h:22
NTSTATUS VmFuncVmxVmcall(unsigned long long VmcallNumber, unsigned long long OptionalParam1, unsigned long long OptionalParam2, unsigned long long OptionalParam3)
Export for running VMX VMCALLs.
Definition Export.c:683
UINT32 Result
Definition DataTypes.h:179

◆ KdHandleBreakpointAndDebugBreakpoints()

_Use_decl_annotations_ VOID KdHandleBreakpointAndDebugBreakpoints ( PROCESSOR_DEBUGGING_STATE * DbgState,
DEBUGGEE_PAUSING_REASON Reason,
PDEBUGGER_TRIGGERED_EVENT_DETAILS EventDetails )

Handle #DBs and #BPs for kernel debugger.

This function can be used in vmx-root

Parameters
DbgStateThe state of the debugger on the current core
Reason
EventDetails
Returns
VOID
1217{
1218 //
1219 // Lock handling breaks
1220 //
1222
1223 //
1224 // Check if we should ignore this break request or not
1225 //
1227 {
1228 //
1229 // Unlock the above core
1230 //
1232
1233 //
1234 // Not continue anymore as the break should be ignored
1235 //
1236 return;
1237 }
1238
1239 //
1240 // Set it as the main core
1241 //
1242 DbgState->MainDebuggingCore = TRUE;
1243
1244 //
1245 // Lock current core
1246 //
1247 DbgState->NmiState.WaitingToBeLocked = FALSE;
1248 SpinlockLock(&DbgState->Lock);
1249
1250 //
1251 // Set the halting reason
1252 //
1253 g_DebuggeeHaltReason = Reason;
1254
1255 //
1256 // Set the context and tag, and stage
1257 //
1258 if (EventDetails != NULL)
1259 {
1260 RtlCopyMemory(&g_EventTriggerDetail, EventDetails, sizeof(DEBUGGER_TRIGGERED_EVENT_DETAILS));
1261 }
1262
1264 {
1265 //
1266 // Unset to avoid future not notifying events
1267 //
1269 }
1270 else
1271 {
1272 //
1273 // Make sure, nobody is in the middle of sending anything
1274 //
1276
1277 //
1278 // Broadcast NMI with the intention of halting cores
1279 //
1281
1282 //
1283 // Unlock the sending response lock to perform regular debugging
1284 //
1286 }
1287
1288 //
1289 // All the cores should go and manage through the following function
1290 //
1291 KdManageSystemHaltOnVmxRoot(DbgState, EventDetails);
1292
1293 //
1294 // Clear the halting reason
1295 //
1297
1298 //
1299 // Clear the context, tag, and stage
1300 //
1302
1303 //
1304 // Unlock handling breaks
1305 //
1306 if (DbgState->MainDebuggingCore)
1307 {
1308 DbgState->MainDebuggingCore = FALSE;
1310 }
1311}
@ DEBUGGEE_PAUSING_REASON_NOT_PAUSED
Definition Connection.h:24
BOOLEAN VmFuncNmiBroadcastRequest(UINT32 CoreId)
Broadcast NMI requests.
Definition Export.c:433
VOID KdCustomDebuggerBreakSpinlockLock(PROCESSOR_DEBUGGING_STATE *DbgState, volatile LONG *Lock)
Tries to get the lock and won't return until successfully get the lock.
Definition Kd.c:993
VOID KdManageSystemHaltOnVmxRoot(PROCESSOR_DEBUGGING_STATE *DbgState, PDEBUGGER_TRIGGERED_EVENT_DETAILS EventDetails)
manage system halt on vmx-root mode
Definition Kd.c:3162
void SpinlockLock(volatile LONG *Lock)
Tries to get the lock and won't return until successfully get the lock.
Definition Spinlock.c:52
volatile LONG DebuggerHandleBreakpointLock
Vmx-root lock for handling breaks to debugger.
Definition Kd.h:28
volatile LONG DebuggerResponseLock
Vmx-root lock for sending response of debugger.
Definition Kd.h:22
DEBUGGEE_PAUSING_REASON g_DebuggeeHaltReason
Reason that the debuggee is halted.
Definition Global.h:127
The structure of detail of a triggered event in HyperDbg.
Definition DataTypes.h:192
volatile BOOLEAN MainDebuggingCore
Definition State.h:167

◆ KdHandleBreakpointAndDebugBreakpointsCallback()

_Use_decl_annotations_ VOID KdHandleBreakpointAndDebugBreakpointsCallback ( UINT32 CoreId,
DEBUGGEE_PAUSING_REASON Reason,
PDEBUGGER_TRIGGERED_EVENT_DETAILS EventDetails )

Handle #DBs and #BPs for kernel debugger.

This function can be used in vmx-root

Parameters
CoreId
Reason
EventDetails
Returns
VOID
1127{
1128 PROCESSOR_DEBUGGING_STATE * DbgState = &g_DbgState[CoreId];
1129
1130 KdHandleBreakpointAndDebugBreakpoints(DbgState, Reason, EventDetails);
1131}
_Use_decl_annotations_ VOID KdHandleBreakpointAndDebugBreakpoints(PROCESSOR_DEBUGGING_STATE *DbgState, DEBUGGEE_PAUSING_REASON Reason, PDEBUGGER_TRIGGERED_EVENT_DETAILS EventDetails)
Handle #DBs and #BPs for kernel debugger.
Definition Kd.c:1214

◆ KdHandleDebugEventsWhenKernelDebuggerIsAttached()

VOID KdHandleDebugEventsWhenKernelDebuggerIsAttached ( PROCESSOR_DEBUGGING_STATE * DbgState,
BOOLEAN TrapSetByDebugger )

Handles debug events when kernel-debugger is attached.

Parameters
DbgStateThe state of the debugger on the current core
TrapSetByDebuggerShows whether a trap set by debugger or not
Returns
VOID
427{
428 DEBUGGER_TRIGGERED_EVENT_DETAILS TargetContext = {0};
429 BOOLEAN IgnoreDebugEvent = FALSE;
430 UINT64 LastVmexitRip = VmFuncGetLastVmexitRip(DbgState->CoreId);
431
432 //
433 // It's a breakpoint and should be handled by the kernel debugger
434 //
435 TargetContext.Context = (PVOID)LastVmexitRip;
436
437 if (TrapSetByDebugger)
438 {
439 //
440 // *** Handle a regular trap flag (most of the times as a result of stepping) set by the debugger ***
441 //
442
443 //
444 // Check and handle if there is a software defined breakpoint
445 //
447 LastVmexitRip,
449 FALSE))
450 {
452 {
453 //
454 // Check if it's caused by a step-over hardware debug breakpoint or not
455 //
457 {
460 {
461 //
462 // It's a step caused by a debug register breakpoint step-over
463 //
465 }
466 else
467 {
468 //
469 // Should be ignored because it's a hardware debug register that is
470 // likely triggered by other thread
471 //
472 IgnoreDebugEvent = TRUE;
473
474 //
475 // Also, we should re-apply the hardware debug breakpoint on this thread
476 //
479 FALSE,
481 }
482 }
483 }
484
485 if (!IgnoreDebugEvent)
486 {
487 //
488 // Handle a regular step
489 //
492 &TargetContext);
493 }
494 }
495 }
496 else
497 {
498 //
499 // It's a regular debug break event
500 //
503 &TargetContext);
504 }
505}
BOOLEAN BreakpointCheckAndHandleDebuggerDefinedBreakpoints(PROCESSOR_DEBUGGING_STATE *DbgState, UINT64 GuestRip, DEBUGGEE_PAUSING_REASON Reason, BOOLEAN ChangeMtfState)
Check if the breakpoint vm-exit relates to 'bp' command or not.
Definition BreakpointCommands.c:497
@ DEBUGGEE_PAUSING_REASON_DEBUGGEE_STEPPED
Definition Connection.h:27
@ DEBUGGEE_PAUSING_REASON_DEBUGGEE_HARDWARE_DEBUG_REGISTER_HIT
Definition Connection.h:30
UINT64 VmFuncGetLastVmexitRip(UINT32 CoreId)
get the last vm-exit RIP
Definition Export.c:318
HARDWARE_DEBUG_REGISTER_DETAILS g_HardwareDebugRegisterDetailsForStepOver
Holds the state of hardware debug register for step-over.
Definition Global.h:61
PVOID Context
Definition DataTypes.h:194
store the details of a hardware debug register to ignore any trigger for other threads
Definition Kd.h:73
UINT32 ThreadId
Definition Kd.h:76
UINT64 Address
Definition Kd.h:74
UINT32 ProcessId
Definition Kd.h:75

◆ KdHandleHaltsWhenNmiReceivedFromVmxRoot()

_Use_decl_annotations_ VOID KdHandleHaltsWhenNmiReceivedFromVmxRoot ( PROCESSOR_DEBUGGING_STATE * DbgState)

Tries to get the lock and won't return until successfully get the lock.

Parameters
DbgStateThe state of the debugger on the current core
Returns
VOID
944{
945 //
946 // During the debugging of HyperDbg, we realized that whenever an
947 // event is set, one core might (and will) get the lock of the
948 // debugging and other cores that are triggering the same event
949 // go to the wait for the debugging lock
950 // As we send NMIs to all cores to notify them and halt them,
951 // a core might be in VMX-root and receive the NMI
952 // Handling the NMI and halting from the NMI handlers is not
953 // possible as the stack of the Windows' NMI handler routine
954 // is not big enough to handle HyperDbg's command dispatching
955 // routines, so if the user switches to the cores that are halted
956 // from an NMI handler then we ran out of stack and debugger crashes
957 // It is also not possible to change the stack to a bigger stack because
958 // we're not really interested in allocating other memories for the stack
959 // and also the target stack will not be a valid Windows stack as it's
960 // supposed to run with NMI handling routines.
961 //
962 // By the way, I conclude to let the NMI handler finish its normal
963 // execution and then we check for the possible pausing reasons.
964 //
965 // The pausing scenario should be checked two cases,
966 // 1. If the current core is stuck in spinlock of getting
967 // the debug lock
968 // 2. If the current core is making it self ready for the vm-entry
969 //
970 // In these two cases we should check for the possible halting of the core
971 //
972
973 //
974 // Handle halt of the current core as an NMI
975 //
976 KdHandleNmi(DbgState);
977
978 //
979 // Set the indication to false as we handled it
980 //
982}

◆ KdHandleNmi()

_Use_decl_annotations_ VOID KdHandleNmi ( PROCESSOR_DEBUGGING_STATE * DbgState)

Handle NMI Vm-exits.

Parameters
DbgStateThe state of the debugger on the current core

This function should be called in vmx-root mode

Returns
VOID
1366{
1367 //
1368 // Test
1369 //
1370 // LogInfo("NMI Arrived on : %d \n",CurrentProcessorIndex);
1371
1372 //
1373 // Not the main debugging core
1374 //
1375 DbgState->MainDebuggingCore = FALSE;
1376
1377 //
1378 // Lock current core
1379 //
1380 DbgState->NmiState.WaitingToBeLocked = FALSE;
1381 SpinlockLock(&DbgState->Lock);
1382
1383 //
1384 // All the cores should go and manage through the following function
1385 //
1386 KdManageSystemHaltOnVmxRoot(DbgState, NULL);
1387
1388 //
1389 // Unlock handling breaks
1390 //
1391 if (DbgState->MainDebuggingCore)
1392 {
1393 DbgState->MainDebuggingCore = FALSE;
1395 }
1396}

◆ KdHandleNmiBroadcastDebugBreaks()

VOID KdHandleNmiBroadcastDebugBreaks ( UINT32 CoreId,
BOOLEAN IsOnVmxNmiHandler )

Handle broadcast NMIs for halting cores in vmx-root mode.

Parameters
CoreId
IsOnVmxNmiHandler
Returns
VOID
1063{
1064 //
1065 // Get the current debugging state
1066 //
1067 PROCESSOR_DEBUGGING_STATE * DbgState = &g_DbgState[CoreId];
1068
1069 //
1070 // We use it as a global flag (for both vmx-root and vmx non-root), because
1071 // generally it doesn't have any use case in vmx-root (IsOnVmxNmiHandler == FALSE)
1072 // but in some cases, we might set the MTF but another vm-exit receives before
1073 // MTF and in that place if it tries to trigger and event, then the MTF is not
1074 // handled and the core is not locked properly, just waits to get the handle
1075 // of the "DebuggerHandleBreakpointLock", so we check this flag there
1076 //
1077 DbgState->NmiState.WaitingToBeLocked = TRUE;
1078
1079 if (IsOnVmxNmiHandler)
1080 {
1081 //
1082 // Indicate that it's called from NMI handle, and it relates to
1083 // halting the debuggee
1084 //
1086
1087 //
1088 // If the core was in the middle of spinning on the spinlock
1089 // of getting the debug lock, this mechanism is not needed,
1090 // but if the core is not spinning there or the core is processing
1091 // a random vm-exit, then we inject an immediate vm-exit after vm-entry
1092 // or inject a DPC
1093 // this is used for two reasons.
1094 //
1095 // 1. first, we will get the registers (context) to halt the core
1096 // 2. second, it guarantees that if the NMI arrives within any
1097 // instruction in vmx-root mode, then we injected an immediate
1098 // vm-exit and we won't miss any cpu cycle in the guest
1099 //
1100 // KdFireDpc(KdHaltCoreInTheCaseOfHaltedFromNmiInVmxRoot, NULL);
1102 }
1103 else
1104 {
1105 //
1106 // Handle core break
1107 //
1108 KdHandleNmi(DbgState);
1109 }
1110}

◆ KdHandleRegisteredMtfCallback()

_Use_decl_annotations_ VOID KdHandleRegisteredMtfCallback ( UINT32 CoreId)

Handle #DBs and #BPs for kernel debugger.

This function can be used in vmx-root

Parameters
CoreId
Returns
VOID
1144{
1145 PROCESSOR_DEBUGGING_STATE * DbgState = &g_DbgState[CoreId];
1146
1147 //
1148 // Check for tracing instructions
1149 //
1150 if (DbgState->TracingMode)
1151 {
1152 //
1153 // Handle callback for tracing instructions
1154 //
1155 TracingHandleMtf(DbgState);
1156 }
1157 else
1158 {
1159 //
1160 // Only 16 bit is needed however, vmwrite might write on other bits
1161 // and corrupt other variables, that's why we get 64bit
1162 //
1163 UINT64 CsSel = NULL64_ZERO;
1164 DEBUGGER_TRIGGERED_EVENT_DETAILS TargetContext = {0};
1165 UINT64 LastVmexitRip = VmFuncGetLastVmexitRip(CoreId);
1166
1167 //
1168 // Check if the cs selector changed or not, which indicates that the
1169 // execution changed from user-mode to kernel-mode or kernel-mode to
1170 // user-mode
1171 //
1172 CsSel = VmFuncGetCsSelector();
1173
1175 (UINT16)CsSel);
1176
1177 //
1178 // Unset the MTF flag and previous cs selector
1179 //
1180 DbgState->InstrumentationStepInTrace.CsSel = 0;
1181
1182 //
1183 // Check and handle if there is a software defined breakpoint
1184 //
1186 LastVmexitRip,
1188 TRUE))
1189 {
1190 //
1191 // Handle the step (if the disassembly ignored here, it means the debugger wants to use it
1192 // as a tracking mechanism, so we'll change the reason for that)
1193 //
1194 TargetContext.Context = (PVOID)LastVmexitRip;
1197 &TargetContext);
1198 }
1199 }
1200}
#define NULL64_ZERO
Definition BasicTypes.h:52
@ DEBUGGEE_PAUSING_REASON_DEBUGGEE_TRACKING_STEPPED
Definition Connection.h:28
BOOLEAN KdCheckGuestOperatingModeChanges(UINT16 PreviousCsSelector, UINT16 CurrentCsSelector)
Check if the execution mode (kernel-mode to user-mode or user-mode to kernel-mode) changed.
Definition Kd.c:1453
VOID TracingHandleMtf(PROCESSOR_DEBUGGING_STATE *DbgState)
Callback for handling VM-exits for MTF in the case of tracing instructions.
Definition Tracing.c:43
BOOLEAN TracingMode
Definition State.h:177

◆ KdInitializeInstantEventPools()

VOID KdInitializeInstantEventPools ( )

Initialize the required pools for instant events.

Returns
VOID
132{
133 //
134 // Request pages to be allocated for regular instant events
135 //
137
138 //
139 // Request pages to be allocated for regular instant events's actions
140 //
142
143#if MAXIMUM_BIG_INSTANT_EVENTS >= 1
144
145 //
146 // Request pages to be allocated for big instant events
147 //
149
150 //
151 // Request pages to be allocated for big instant events's actions
152 //
154
155#endif // MAXIMUM_BIG_INSTANT_EVENTS
156
157 //
158 // Pre-allocate pools for possible EPT hooks
159 // Because there are possible init EPT hook structures, we only allocate the
160 // maximum number of regular instant event subtracted from the initial pages
161 //
163
165 {
166 LogWarning("Warning, cannot allocate the pre-allocated pools for EPT hooks");
167
168 //
169 // BTW, won't fail the starting phase because of this
170 //
171 }
172}
VOID ConfigureEptHookReservePreallocatedPoolsForEptHooks(UINT32 Count)
Allocate (reserve) pages for storing EPT hooks page hooks.
Definition Configuration.c:239
#define MAXIMUM_NUMBER_OF_INITIAL_PREALLOCATED_EPT_HOOKS
Maximum number of initial pre-allocated EPT hooks.
Definition Constants.h:260
#define BIG_INSTANT_EVENT_ACTION_BUFFER
Pre-allocated size for a big action + custom code or script buffer.
Definition Constants.h:300
#define REGULAR_INSTANT_EVENT_ACTION_BUFFER
Pre-allocated size for a regular action + custom code or script buffer.
Definition Constants.h:294
#define MAXIMUM_BIG_INSTANT_EVENTS
Maximum number of (big) instant events that are pre-allocated.
Definition Constants.h:276
#define MAXIMUM_REGULAR_INSTANT_EVENTS
Maximum number of (regular) instant events that are pre-allocated.
Definition Constants.h:270
#define REGULAR_INSTANT_EVENT_CONDITIONAL_BUFFER
Pre-allocated size for a regular event + conditions buffer.
Definition Constants.h:282
#define BIG_INSTANT_EVENT_CONDITIONAL_BUFFER
Pre-allocated size for a big event + conditions buffer.
Definition Constants.h:288
@ INSTANT_BIG_EVENT_BUFFER
Definition DataTypes.h:52
@ INSTANT_BIG_EVENT_ACTION_BUFFER
Definition DataTypes.h:54
@ INSTANT_REGULAR_EVENT_ACTION_BUFFER
Definition DataTypes.h:53
@ INSTANT_REGULAR_EVENT_BUFFER
Definition DataTypes.h:51
BOOLEAN PoolManagerCheckAndPerformAllocationAndDeallocation()
This function performs allocations from VMX non-root based on g_RequestNewAllocation.
Definition PoolManager.c:302
BOOLEAN PoolManagerRequestAllocation(SIZE_T Size, UINT32 Count, POOL_ALLOCATION_INTENTION Intention)
Request to allocate new buffers.
Definition PoolManager.c:415

◆ KdInitializeKernelDebugger()

VOID KdInitializeKernelDebugger ( )

initialize kernel debugger

this function should be called on vmx non-root

Returns
VOID
23{
24 //
25 // Allocate DPC routine
26 //
27 // for (size_t i = 0; i < CoreCount; i++)
28 // {
29 // g_DbgState[i].KdDpcObject = PlatformMemAllocateNonPagedPool(sizeof(KDPC));
30 //
31 // if (g_DbgState[i].KdDpcObject == NULL)
32 // {
33 // LogError("Err, allocating dpc holder for debuggee");
34 // return;
35 // }
36 // }
37
38 //
39 // Request pages for breakpoint detail
40 //
44
45 //
46 // Enable vm-exit on Hardware debug exceptions and breakpoints
47 // so, intercept #DBs and #BP by changing exception bitmap (one core)
48 //
50
51 //
52 // Reset pause break requests
53 //
55
56 //
57 // Initialize list of breakpoints and breakpoint id
58 //
61
62 //
63 // Initial the needed pools for instant events
64 //
66
67 //
68 // Indicate that the kernel debugger is active
69 //
71}
VOID BroadcastEnableDbAndBpExitingAllCores()
routines to set vm-exit on all #DBs and #BP on all cores
Definition Broadcast.c:35
#define MAXIMUM_BREAKPOINTS_WITHOUT_CONTINUE
maximum number of buffers to be allocated for a single breakpoint
Definition Constants.h:398
@ BREAKPOINT_DEFINITION_STRUCTURE
Definition DataTypes.h:45
VOID KdInitializeInstantEventPools()
Initialize the required pools for instant events.
Definition Kd.c:131
FORCEINLINE VOID InitializeListHead(_Out_ PLIST_ENTRY ListHead)
Definition Windows.h:41
LIST_ENTRY g_BreakpointsListHead
List header of breakpoints for debugger-mode.
Definition Global.h:91
UINT64 g_MaximumBreakpointId
Seed for setting id of breakpoints.
Definition Global.h:97
The structure of storing breakpoints.
Definition State.h:72
request to pause and halt the system
Definition Kd.h:61

◆ KdIsGuestOnUsermode32Bit()

BOOLEAN KdIsGuestOnUsermode32Bit ( )

determines if the guest was in 32-bit user-mode or 64-bit (long mode)

this function should be called from vmx-root

Returns
BOOLEAN
3108{
3109 //
3110 // Only 16 bit is needed however, vmwrite might write on other bits
3111 // and corrupt other variables, that's why we get 64bit
3112 //
3113 UINT64 CsSel = (UINT64)NULL;
3114
3115 //
3116 // Read guest's cs selector
3117 //
3118 CsSel = VmFuncGetCsSelector();
3119
3120 if (CsSel == KGDT64_R0_CODE)
3121 {
3122 //
3123 // 64-bit kernel-mode
3124 //
3125 return FALSE;
3126 }
3127 else if ((CsSel & ~3) == KGDT64_R3_CODE)
3128 {
3129 //
3130 // 64-bit user-mode
3131 //
3132 return FALSE;
3133 }
3134 else if ((CsSel & ~3) == KGDT64_R3_CMCODE)
3135 {
3136 //
3137 // 32-bit user-mode
3138 //
3139 return TRUE;
3140 }
3141 else
3142 {
3143 LogError("Err, unknown value for cs, cannot determine wow64 mode");
3144 }
3145
3146 //
3147 // By default, 64-bit
3148 //
3149 return FALSE;
3150}

◆ KdLoggingResponsePacketToDebugger()

_Use_decl_annotations_ BOOLEAN KdLoggingResponsePacketToDebugger ( CHAR * OptionalBuffer,
UINT32 OptionalBufferLength,
UINT32 OperationCode )

Sends a HyperDbg logging response packet to the debugger.

Parameters
OptionalBuffer
OptionalBufferLength
OperationCode
Returns
BOOLEAN
376{
377 DEBUGGER_REMOTE_PACKET Packet = {0};
378 BOOLEAN Result = FALSE;
379
380 //
381 // Make the packet's structure
382 //
385
386 //
387 // Set the requested action
388 //
390
391 //
392 // Calculate checksum
393 //
394 Packet.Checksum = KdComputeDataChecksum((PVOID)((UINT64)&Packet + 1),
395 sizeof(DEBUGGER_REMOTE_PACKET) - sizeof(BYTE));
396
397 Packet.Checksum += KdComputeDataChecksum((PVOID)&OperationCode, sizeof(UINT32));
398 Packet.Checksum += KdComputeDataChecksum((PVOID)OptionalBuffer, OptionalBufferLength);
399
400 //
401 // Check if we're in Vmx-root, if it is then we use our customized HIGH_IRQL Spinlock,
402 // if not we use the windows spinlock
403 //
404
407 Result = SerialConnectionSendThreeBuffers((CHAR *)&Packet,
409 (CHAR *)&OperationCode,
410 sizeof(UINT32),
411 OptionalBuffer,
412 OptionalBufferLength));
413
414 return Result;
415}
@ DEBUGGER_REMOTE_PACKET_REQUESTED_ACTION_DEBUGGEE_LOGGING_MECHANISM
Definition Connection.h:105
BOOLEAN SerialConnectionSendThreeBuffers(CHAR *Buffer1, UINT32 Length1, CHAR *Buffer2, UINT32 Length2, CHAR *Buffer3, UINT32 Length3)
Perform sending 3 not appended buffers over serial.
Definition SerialConnection.c:242
#define ScopedSpinlock(LockObject, CodeToRun)
Definition Spinlock.h:39

◆ KdManageSystemHaltOnVmxRoot()

VOID KdManageSystemHaltOnVmxRoot ( PROCESSOR_DEBUGGING_STATE * DbgState,
PDEBUGGER_TRIGGERED_EVENT_DETAILS EventDetails )

manage system halt on vmx-root mode

This function should only be called from KdHandleBreakpointAndDebugBreakpoints

Parameters
DbgStateThe state of the debugger on the current core
EventDetails
MainCorethe core that triggered the event
Returns
VOID
3164{
3165 DEBUGGEE_KD_PAUSED_PACKET PausePacket;
3166 ULONG ExitInstructionLength = 0;
3167 RFLAGS Rflags = {0};
3168 UINT64 LastVmexitRip = 0;
3169
3170 //
3171 // Perform Pre-halt tasks
3172 //
3173 KdApplyTasksPreHaltCore(DbgState);
3174
3175StartAgain:
3176
3177 //
3178 // We check for receiving buffer (unhalting) only on the
3179 // first core and not on every cores
3180 //
3181 if (DbgState->MainDebuggingCore)
3182 {
3183 //
3184 // *** Current Operating Core ***
3185 //
3186 RtlZeroMemory(&PausePacket, sizeof(DEBUGGEE_KD_PAUSED_PACKET));
3187
3188 //
3189 // Get the last RIP for vm-exit handler
3190 //
3191 LastVmexitRip = VmFuncGetRip();
3192
3193 //
3194 // Set the halt reason
3195 //
3196 PausePacket.PausingReason = g_DebuggeeHaltReason;
3197
3198 //
3199 // Set the current core
3200 //
3201 PausePacket.CurrentCore = DbgState->CoreId;
3202
3203 //
3204 // Set the RIP and mode of execution
3205 //
3206 PausePacket.Rip = LastVmexitRip;
3208
3209 //
3210 // Set disassembly state
3211 //
3212 PausePacket.IgnoreDisassembling = DbgState->IgnoreDisasmInNextPacket;
3213 DbgState->IgnoreDisasmInNextPacket = FALSE;
3214
3215 //
3216 // Set rflags for finding the results of conditional jumps
3217 //
3218 Rflags.AsUInt = VmFuncGetRflags();
3219 PausePacket.Rflags = Rflags.AsUInt;
3220
3221 //
3222 // Set the event tag (if it's an event)
3223 //
3224 if (EventDetails != NULL)
3225 {
3226 PausePacket.EventTag = EventDetails->Tag;
3227 PausePacket.EventCallingStage = EventDetails->Stage;
3228 }
3229
3230 //
3231 // Read the instruction len hint
3232 //
3233 if (DbgState->InstructionLengthHint != 0)
3234 {
3235 ExitInstructionLength = DbgState->InstructionLengthHint;
3236 }
3237 else
3238 {
3239 //
3240 // Reading instruction length (VMCS_VMEXIT_INSTRUCTION_LENGTH) won't work for anything that is not instruction exiting,
3241 // so we won't use it anymore
3242 //
3243
3244 //
3245 // Set the length to notify debuggee
3246 //
3247 ExitInstructionLength = CheckAddressMaximumInstructionLength((PVOID)LastVmexitRip);
3248 }
3249
3250 //
3251 // Set the reading length of bytes (for instruction disassembling)
3252 //
3253 PausePacket.ReadInstructionLen = (UINT16)ExitInstructionLength;
3254
3255 //
3256 // Find the current instruction
3257 //
3259 &PausePacket.InstructionBytesOnRip,
3260 ExitInstructionLength);
3261
3262 //
3263 // Send the pause packet, along with RIP and an indication
3264 // to pause to the debugger
3265 //
3268 (CHAR *)&PausePacket,
3270
3271 //
3272 // Perform Commands from the debugger
3273 //
3275
3276 //
3277 // Check if it's a change core event or not, otherwise finish the execution
3278 // and continue debuggee
3279 //
3280 if (!DbgState->MainDebuggingCore)
3281 {
3282 //
3283 // It's a core switch, start again
3284 //
3285 goto StartAgain;
3286 }
3287 }
3288 else
3289 {
3290 //
3291 // All cores except operating core
3292 //
3293
3294 //
3295 // Lock and unlock the lock so all core can get the lock
3296 // and continue their normal execution
3297 //
3298 DbgState->NmiState.WaitingToBeLocked = FALSE;
3299
3301 DbgState->Lock,
3302
3303 //
3304 // Check if it's a change core event or not
3305 //
3306 if (DbgState->MainDebuggingCore) {
3307 //
3308 // It's a core change event
3309 //
3310 g_DebuggeeHaltReason = DEBUGGEE_PAUSING_REASON_DEBUGGEE_CORE_SWITCHED;
3311
3312 goto StartAgain;
3313 }
3314
3315 );
3316
3317 //
3318 // Check if any task needs to be executed on this core or not
3319 //
3320 if (DbgState->HaltedCoreTask.PerformHaltedTask)
3321 {
3322 //
3323 // Indicate that the halted core is no longer needed to execute a task
3324 // as the current task is executed once
3325 //
3327
3328 //
3329 // Perform the target task
3330 //
3332 DbgState->HaltedCoreTask.TargetTask,
3333 DbgState->HaltedCoreTask.Context);
3334
3335 //
3336 // Check if the core needs to be locked again
3337 //
3338 if (DbgState->HaltedCoreTask.LockAgainAfterTask)
3339 {
3340 //
3341 // Lock again
3342 //
3343 SpinlockLock(&DbgState->Lock);
3344
3345 goto StartAgain;
3346 }
3347 }
3348 }
3349
3350 //
3351 // Apply the basic task for the core before continue
3352 //
3354}
UINT32 CheckAddressMaximumInstructionLength(PVOID Address)
This function returns the maximum instruction length that can be read from this address.
Definition AddressCheck.c:306
@ DEBUGGER_REMOTE_PACKET_REQUESTED_ACTION_DEBUGGEE_PAUSED_AND_CURRENT_INSTRUCTION
Definition Connection.h:106
UINT64 VmFuncGetRflags()
Read guest's RFLAGS.
Definition Export.c:352
UINT64 VmFuncGetRip()
Read guest's RIP.
Definition Export.c:375
VOID HaltedCorePerformTargetTask(PROCESSOR_DEBUGGING_STATE *DbgState, UINT64 TargetTask, PVOID Context)
Perform the task on halted core.
Definition HaltedCore.c:45
VOID KdApplyTasksPreHaltCore(PROCESSOR_DEBUGGING_STATE *DbgState)
before halting any core, all the tasks will be applied to all cores including the main core
Definition Kd.c:517
BOOLEAN KdIsGuestOnUsermode32Bit()
determines if the guest was in 32-bit user-mode or 64-bit (long mode)
Definition Kd.c:3107
VOID KdDispatchAndPerformCommandsFromDebugger(PROCESSOR_DEBUGGING_STATE *DbgState)
This function applies commands from the debugger to the debuggee.
Definition Kd.c:2292
VOID KdApplyTasksPostContinueCore(PROCESSOR_DEBUGGING_STATE *DbgState)
before continue any core, all the tasks will be applied to all cores including the main core
Definition Kd.c:556
_Use_decl_annotations_ BOOLEAN MemoryMapperReadMemorySafeOnTargetProcess(UINT64 VaAddressToRead, PVOID BufferToSaveMemory, SIZE_T SizeToRead)
Read memory safely by mapping the buffer on the target process memory (It's a wrapper)
Definition MemoryMapper.c:1120
if(.test_var==4)
Definition script_conditional_statement_global_var.txt:5
BOOLEAN LockAgainAfterTask
Definition State.h:139
PVOID Context
Definition State.h:141
BOOLEAN PerformHaltedTask
Definition State.h:138
UINT64 TargetTask
Definition State.h:140
The structure of pausing packet in kHyperDbg.
Definition DataTypes.h:207
UINT16 ReadInstructionLen
Definition DataTypes.h:217
UINT64 Rip
Definition DataTypes.h:208
UINT64 Rflags
Definition DataTypes.h:215
BYTE InstructionBytesOnRip[MAXIMUM_INSTR_SIZE]
Definition DataTypes.h:216
BOOLEAN IsProcessorOn32BitMode
Definition DataTypes.h:209
DEBUGGEE_PAUSING_REASON PausingReason
Definition DataTypes.h:211
UINT64 EventTag
Definition DataTypes.h:213
ULONG CurrentCore
Definition DataTypes.h:212
BOOLEAN IgnoreDisassembling
Definition DataTypes.h:210
VMM_CALLBACK_EVENT_CALLING_STAGE_TYPE EventCallingStage
Definition DataTypes.h:214
UINT64 Tag
Definition DataTypes.h:193
VMM_CALLBACK_EVENT_CALLING_STAGE_TYPE Stage
Definition DataTypes.h:195
UINT16 InstructionLengthHint
Definition State.h:182
DEBUGGEE_HALTED_CORE_TASK HaltedCoreTask
Definition State.h:180

◆ KdNotifyDebuggeeForUserInput()

VOID KdNotifyDebuggeeForUserInput ( DEBUGGEE_USER_INPUT_PACKET * Descriptor,
UINT32 Len )

Notify user-mode to about new user-input buffer.

Parameters
Descriptor
Len
Returns
VOID
877{
878 //
879 // Check if the priority buffer is full or not
880 //
882
883 //
884 // Send user-input buffer along with operation code to
885 // the user-mode
886 //
888 Descriptor,
889 Len,
890 TRUE);
891}
#define OPERATION_DEBUGGEE_USER_INPUT
Definition Constants.h:374

◆ KdPerformAddActionToEvent()

BOOLEAN KdPerformAddActionToEvent ( PDEBUGGEE_EVENT_AND_ACTION_HEADER_FOR_REMOTE_PACKET ActionDetailHeader,
DEBUGGER_EVENT_AND_ACTION_RESULT * DebuggerEventAndActionResult )

Send action buffer to user-mode to be added to the event.

Parameters
ActionDetailHeader
DebuggerEventAndActionResult
Returns
BOOLEAN Shows whether the debuggee should be continued or not
1638{
1639#if EnableInstantEventMechanism
1640
1641 DEBUGGER_GENERAL_ACTION * GeneralActionDetail = NULL;
1642
1643 GeneralActionDetail = (PDEBUGGER_GENERAL_ACTION)(((CHAR *)ActionDetailHeader) +
1645
1646 //
1647 // Parse action from the VMX-root mode
1648 //
1649 DebuggerParseAction(GeneralActionDetail, DebuggerEventAndActionResult, TRUE);
1650
1651 return FALSE;
1652
1653#else
1654
1655 //
1656 // Check if the priority buffer is full or not
1657 //
1659
1661 ((CHAR *)ActionDetailHeader + sizeof(DEBUGGEE_EVENT_AND_ACTION_HEADER_FOR_REMOTE_PACKET)),
1662 ActionDetailHeader->Length,
1663 TRUE);
1664 return TRUE;
1665
1666#endif // EnableInstantEventMechanism
1667}
#define OPERATION_DEBUGGEE_ADD_ACTION_TO_EVENT
Definition Constants.h:376
struct _DEBUGGEE_EVENT_AND_ACTION_HEADER_FOR_REMOTE_PACKET DEBUGGEE_EVENT_AND_ACTION_HEADER_FOR_REMOTE_PACKET
The structure of user-input packet in HyperDbg.
BOOLEAN DebuggerParseAction(PDEBUGGER_GENERAL_ACTION ActionDetails, PDEBUGGER_EVENT_AND_ACTION_RESULT ResultsToReturn, BOOLEAN InputFromVmxRoot)
Routine for validating and parsing actions that are coming from the user-mode.
Definition Debugger.c:3260
struct _DEBUGGER_GENERAL_ACTION * PDEBUGGER_GENERAL_ACTION
Each event can have multiple actions.
Definition Events.h:406

◆ KdPerformEventQueryAndModification()

BOOLEAN KdPerformEventQueryAndModification ( PDEBUGGER_MODIFY_EVENTS ModifyAndQueryEvent)

Perform modify and query events.

Parameters
ModifyAndQueryEvent
Returns
BOOLEAN Shows whether the debuggee should be continued or not
2085{
2086 BOOLEAN IsForAllEvents = FALSE;
2087 BOOLEAN ContinueDebugger = FALSE;
2088
2089 //
2090 // Check if the tag is valid or not
2091 //
2092 if (ModifyAndQueryEvent->Tag == DEBUGGER_MODIFY_EVENTS_APPLY_TO_ALL_TAG)
2093 {
2094 IsForAllEvents = TRUE;
2095 }
2096 else if (!DebuggerIsTagValid(ModifyAndQueryEvent->Tag))
2097 {
2098 //
2099 // Tag is invalid
2100 //
2102 return FALSE;
2103 }
2104
2105 //
2106 // ***************************************************************************
2107 //
2108
2109 //
2110 // Check if it's a query state command
2111 //
2112 if (ModifyAndQueryEvent->TypeOfAction == DEBUGGER_MODIFY_EVENTS_QUERY_STATE)
2113 {
2114 //
2115 // check if tag is valid or not
2116 //
2117 if (!DebuggerIsTagValid(ModifyAndQueryEvent->Tag))
2118 {
2119 ModifyAndQueryEvent->KernelStatus = DEBUGGER_ERROR_TAG_NOT_EXISTS;
2120 }
2121 else
2122 {
2123 //
2124 // Set event state
2125 //
2126 if (DebuggerQueryStateEvent(ModifyAndQueryEvent->Tag))
2127 {
2128 ModifyAndQueryEvent->IsEnabled = TRUE;
2129 }
2130 else
2131 {
2132 ModifyAndQueryEvent->IsEnabled = FALSE;
2133 }
2134
2135 //
2136 // The function was successful
2137 //
2138 ModifyAndQueryEvent->KernelStatus = DEBUGGER_OPERATION_WAS_SUCCESSFUL;
2139 }
2140 }
2141 else if (ModifyAndQueryEvent->TypeOfAction == DEBUGGER_MODIFY_EVENTS_ENABLE)
2142 {
2143 if (IsForAllEvents)
2144 {
2145 //
2146 // Enable all events
2147 //
2149 }
2150 else
2151 {
2152 //
2153 // Enable just one event
2154 //
2155 DebuggerEnableEvent(ModifyAndQueryEvent->Tag);
2156 }
2157
2158 //
2159 // The function was successful
2160 //
2161 ModifyAndQueryEvent->KernelStatus = DEBUGGER_OPERATION_WAS_SUCCESSFUL;
2162 }
2163 else if (ModifyAndQueryEvent->TypeOfAction == DEBUGGER_MODIFY_EVENTS_DISABLE)
2164 {
2165 if (IsForAllEvents)
2166 {
2167 //
2168 // Disable all events
2169 //
2171 }
2172 else
2173 {
2174 //
2175 // Disable just one event
2176 //
2177 DebuggerDisableEvent(ModifyAndQueryEvent->Tag);
2178 }
2179
2180 //
2181 // The function was successful
2182 //
2183 ModifyAndQueryEvent->KernelStatus = DEBUGGER_OPERATION_WAS_SUCCESSFUL;
2184 }
2185 else if (ModifyAndQueryEvent->TypeOfAction == DEBUGGER_MODIFY_EVENTS_CLEAR)
2186 {
2187#if EnableInstantEventMechanism
2188
2189 //
2190 // For clearing events, we just disable them here and after that
2191 // we'll send a DPC to the user-mode to clear the event
2192 //
2193 // This is because we want to make sure that no other core is in middle
2194 // of handling anything (so the structures and the track of the debugger
2195 // might be lost)
2196 //
2197 // For example, the debugger might be (and will be) paused while other cores
2198 // are halted but in the middle of handling an EPT, and if we remove the EPT
2199 // hook directly, it might break the operation of the other cores, but when
2200 // we disable it then we're sure no other cores get a chance to trigger the
2201 // event
2202 //
2203 if (IsForAllEvents)
2204 {
2205 //
2206 // Disable all events
2207 //
2209 }
2210 else
2211 {
2212 //
2213 // Disable just one event
2214 //
2215 DebuggerDisableEvent(ModifyAndQueryEvent->Tag);
2216 }
2217
2218 //
2219 // Send the DPC to remove the event at next run
2220 //
2221
2222 //
2223 // Send one byte buffer and operation codes to the user-mode
2224 // This buffer won't notify the debugger and silently removes
2225 // the event(s)
2226 //
2228 {
2230 ModifyAndQueryEvent,
2231 sizeof(DEBUGGER_MODIFY_EVENTS),
2232 TRUE);
2233
2234 //
2235 // The function was successful
2236 //
2237 ModifyAndQueryEvent->KernelStatus = DEBUGGER_OPERATION_WAS_SUCCESSFUL;
2238 }
2239 else
2240 {
2241 //
2242 // The event is already disabled, but we cannot deliver the user-mode
2243 // to clear the buffer because the buffers are either not served or
2244 // too much buffers are added to queue
2245 //
2247 }
2248
2249#else
2250
2251 //
2252 // Check if the priority buffer is full or not
2253 //
2255
2256 //
2257 // Send one byte buffer and operation codes to the user-mode
2258 //
2260 ModifyAndQueryEvent,
2261 sizeof(DEBUGGER_MODIFY_EVENTS),
2262 TRUE);
2263
2264 ContinueDebugger = TRUE;
2265
2266#endif // EnableInstantEventMechanism
2267 }
2268 else
2269 {
2270 //
2271 // Invalid parameter specified in Action
2272 //
2274 }
2275
2276 //
2277 // In all of the cases except clearing event while instant event
2278 // mechanism is disabled, we shouldn't continue the debugger and
2279 // keep the debugger in the halt state
2280 //
2281 return ContinueDebugger;
2282}
#define DEBUGGER_MODIFY_EVENTS_APPLY_TO_ALL_TAG
Apply event modifications to all tags.
Definition Constants.h:586
#define OPERATION_DEBUGGEE_CLEAR_EVENTS_WITHOUT_NOTIFYING_DEBUGGER
Definition Constants.h:379
#define OPERATION_DEBUGGEE_CLEAR_EVENTS
Definition Constants.h:378
BOOLEAN DebuggerEnableOrDisableAllEvents(BOOLEAN IsEnable)
Enable or disable all events from all the types.
Definition Debugger.c:1901
BOOLEAN DebuggerDisableEvent(UINT64 Tag)
Disable an event by tag.
Definition Debugger.c:2363
BOOLEAN DebuggerIsTagValid(UINT64 Tag)
Detect whether the tag exists or not.
Definition Debugger.c:2471
BOOLEAN DebuggerEnableEvent(UINT64 Tag)
Enable an event by tag.
Definition Debugger.c:2302
BOOLEAN DebuggerQueryStateEvent(UINT64 Tag)
returns whether an event is enabled/disabled by tag
Definition Debugger.c:2336
#define DEBUGGER_ERROR_TAG_NOT_EXISTS
error, the tag not exist
Definition ErrorCodes.h:33
#define DEBUGGER_ERROR_MODIFY_EVENTS_INVALID_TYPE_OF_ACTION
error, type of action (enable/disable/clear) is wrong
Definition ErrorCodes.h:127
#define DEBUGGER_ERROR_MODIFY_EVENTS_INVALID_TAG
error, invalid tag for 'events' command (tag id is unknown for kernel)
Definition ErrorCodes.h:121
#define DEBUGGER_ERROR_THE_TARGET_EVENT_IS_DISABLED_BUT_CANNOT_BE_CLEARED_PRIRITY_BUFFER_IS_FULL
error, the target event(s) is/are disabled but cannot clear them because the buffer of the user-mode ...
Definition ErrorCodes.h:520
@ DEBUGGER_MODIFY_EVENTS_ENABLE
Definition Events.h:232
@ DEBUGGER_MODIFY_EVENTS_DISABLE
Definition Events.h:233
@ DEBUGGER_MODIFY_EVENTS_QUERY_STATE
Definition Events.h:231
@ DEBUGGER_MODIFY_EVENTS_CLEAR
Definition Events.h:234
DEBUGGER_MODIFY_EVENTS_TYPE TypeOfAction
Definition Events.h:246
BOOLEAN IsEnabled
Definition Events.h:247
UINT64 KernelStatus
Definition Events.h:244
UINT64 Tag
Definition Events.h:243

◆ KdPerformRegisterEvent()

BOOLEAN KdPerformRegisterEvent ( PDEBUGGEE_EVENT_AND_ACTION_HEADER_FOR_REMOTE_PACKET EventDetailHeader,
DEBUGGER_EVENT_AND_ACTION_RESULT * DebuggerEventAndActionResult )

Send event registration buffer to user-mode to register the event.

Parameters
EventDetailHeader
DebuggerEventAndActionResult
Returns
BOOLEAN Shows whether the debuggee should be continued or not
1586{
1587#if EnableInstantEventMechanism
1588
1589 DEBUGGER_GENERAL_EVENT_DETAIL * GeneralEventDetail = NULL;
1590
1591 GeneralEventDetail = (PDEBUGGER_GENERAL_EVENT_DETAIL)(((CHAR *)EventDetailHeader) +
1593
1594 //
1595 // Check to see whether all cores are halted (in instant event)
1596 //
1598 {
1599 DebuggerEventAndActionResult->IsSuccessful = FALSE;
1601 }
1602 else
1603 {
1604 //
1605 // Parse event from the VMX-root mode
1606 //
1607 DebuggerParseEvent(GeneralEventDetail, DebuggerEventAndActionResult, TRUE);
1608 }
1609
1610 return FALSE;
1611
1612#else
1613
1614 //
1615 // Check if the priority buffer is full or not
1616 //
1618
1620 ((CHAR *)EventDetailHeader + sizeof(DEBUGGEE_EVENT_AND_ACTION_HEADER_FOR_REMOTE_PACKET)),
1621 EventDetailHeader->Length,
1622 TRUE);
1623 return TRUE;
1624
1625#endif // EnableInstantEventMechanism
1626}
#define OPERATION_DEBUGGEE_REGISTER_EVENT
Definition Constants.h:375
BOOLEAN DebuggerParseEvent(PDEBUGGER_GENERAL_EVENT_DETAIL EventDetails, PDEBUGGER_EVENT_AND_ACTION_RESULT ResultsToReturn, BOOLEAN InputFromVmxRoot)
Routine for parsing events.
Definition Debugger.c:3116
#define DEBUGGER_ERROR_NOT_ALL_CORES_ARE_LOCKED_FOR_APPLYING_INSTANT_EVENT
error, not all cores are locked (probably due to a race condition in HyperDbg) in instant-event mecha...
Definition ErrorCodes.h:527
BOOLEAN KdCheckAllCoresAreLocked()
Check whether all cores are locked or not.
Definition Kd.c:1701
struct _DEBUGGER_GENERAL_EVENT_DETAIL * PDEBUGGER_GENERAL_EVENT_DETAIL
UINT32 Error
Definition Events.h:425
BOOLEAN IsSuccessful
Definition Events.h:424
Each command is like the following struct, it also used for tracing works in user mode and sending it...
Definition Events.h:350

◆ KdPerformSettingTheStateOfShortCircuiting()

VOID KdPerformSettingTheStateOfShortCircuiting ( PROCESSOR_DEBUGGING_STATE * DbgState,
PDEBUGGER_SHORT_CIRCUITING_EVENT ShortCircuitingEvent )

Perform modify the state of short-circuiting.

Parameters
DbgStateThe state of the debugger on the current core
ShortCircuitingEvent
Returns
VOID
2058{
2059 //
2060 // Perform the short-circuiting changes
2061 //
2062 if (ShortCircuitingEvent->IsShortCircuiting)
2063 {
2064 DbgState->ShortCircuitingEvent = TRUE;
2065 }
2066 else
2067 {
2068 DbgState->ShortCircuitingEvent = FALSE;
2069 }
2070
2071 //
2072 // The status was okay
2073 //
2074 ShortCircuitingEvent->KernelStatus = DEBUGGER_OPERATION_WAS_SUCCESSFUL;
2075}
BOOLEAN IsShortCircuiting
Definition Events.h:258
UINT64 KernelStatus
Definition Events.h:257
BOOLEAN ShortCircuitingEvent
Definition State.h:170

◆ KdPerformTheTestPacketOperation()

VOID KdPerformTheTestPacketOperation ( PROCESSOR_DEBUGGING_STATE * DbgState,
DEBUGGER_DEBUGGER_TEST_QUERY_BUFFER * TestQueryPacket )

Perform the test packet's operation.

Parameters
DbgStateThe state of the debugger on the current core
TestQueryPackettest packet request
Returns
VOID
1889{
1890 //
1891 // Dispatch the request
1892 //
1893 switch (TestQueryPacket->RequestType)
1894 {
1896
1897 //
1898 // Query state of the system
1899 //
1901
1903
1904 break;
1905
1907
1908 //
1909 // Query state of the trap
1910 //
1912
1914
1915 break;
1916
1918
1919 //
1920 // Query state of pre-allocated pools
1921 //
1923
1925
1926 break;
1927
1930
1931 //
1932 // Send request for the target task to the halted cores (synchronized and unsynchronized)
1933 //
1936 TRUE,
1938 (PVOID)0x55);
1939
1941
1942 break;
1943
1945
1946 //
1947 // Validate core number
1948 //
1949 if (!CommonValidateCoreNumber((UINT32)TestQueryPacket->Context))
1950 {
1951 //
1952 // Core number is invalid
1953 //
1955 }
1956 else
1957 {
1958 //
1959 // Send request for the target task to the target halted core
1960 //
1963 TRUE,
1964 (PVOID)0x85);
1965
1967 }
1968
1969 break;
1970
1972
1973 //
1974 // Turn off the breakpoint interception
1975 //
1977
1979
1980 break;
1981
1983
1984 //
1985 // Turn on the breakpoint interception
1986 //
1988
1990
1991 break;
1992
1994
1995 //
1996 // Turn off the breakpoints and events interception before executing the commands in the remote computer
1997 //
1999
2001
2002 break;
2003
2005
2006 //
2007 // Turn on the breakpoints and events interception after finishing the commands in the remote computer
2008 //
2010
2012
2013 break;
2014
2016
2017 //
2018 // Turn off the debug break interception
2019 //
2021
2023
2024 break;
2025
2027
2028 //
2029 // Turn on the debug break interception
2030 //
2032
2034
2035 break;
2036
2037 default:
2038
2039 //
2040 // Query index not found
2041 //
2043
2044 break;
2045 }
2046}
#define DEBUGGER_ERROR_INVALID_CORE_ID
error, the core id is invalid
Definition ErrorCodes.h:69
#define DEBUGGER_ERROR_UNKNOWN_TEST_QUERY_RECEIVED
error, unknown test query is received
Definition ErrorCodes.h:399
VOID HaltedCoreRunTaskOnSingleCore(UINT32 TargetCoreId, UINT64 TargetTask, BOOLEAN LockAgainAfterTask, PVOID Context)
Run the task on a single halted core.
Definition HaltedCore.c:356
BOOLEAN HaltedCoreBroadcastTaskAllCores(PROCESSOR_DEBUGGING_STATE *DbgState, UINT64 TargetTask, BOOLEAN LockAgainAfterTask, BOOLEAN Synchronize, PVOID Context)
Broadcast tasks to halted cores.
Definition HaltedCore.c:399
#define DEBUGGER_HALTED_CORE_TASK_TEST
Halted core task for testing purpose.
Definition HaltedCore.h:22
VOID KdQueryRflagTrapState()
Query state of the RFLAG's traps.
Definition Kd.c:1675
VOID KdQuerySystemState()
Query state of the system.
Definition Kd.c:1762
VOID PoolManagerShowPreAllocatedPools()
Shows list of pre-allocated pools available (used for debugging purposes)
Definition PoolManager.c:177
@ TEST_BREAKPOINT_TURN_OFF_DBS
Definition RequestStructures.h:323
@ TEST_BREAKPOINT_TURN_ON_BPS_AND_EVENTS_FOR_COMMANDS_IN_REMOTE_COMPUTER
Definition RequestStructures.h:319
@ TEST_BREAKPOINT_TURN_OFF_BPS
Definition RequestStructures.h:316
@ TEST_BREAKPOINT_TURN_ON_DBS
Definition RequestStructures.h:324
@ TEST_SETTING_TARGET_TASKS_ON_HALTED_CORES_ASYNCHRONOUS
Definition RequestStructures.h:321
@ TEST_BREAKPOINT_TURN_ON_BPS
Definition RequestStructures.h:317
@ TEST_SETTING_TARGET_TASKS_ON_HALTED_CORES_SYNCHRONOUS
Definition RequestStructures.h:320
@ TEST_QUERY_PREALLOCATED_POOL_STATE
Definition RequestStructures.h:314
@ TEST_QUERY_HALTING_CORE_STATUS
Definition RequestStructures.h:313
@ TEST_QUERY_TRAP_STATE
Definition RequestStructures.h:315
@ TEST_SETTING_TARGET_TASKS_ON_TARGET_HALTED_CORES
Definition RequestStructures.h:322
@ TEST_BREAKPOINT_TURN_OFF_BPS_AND_EVENTS_FOR_COMMANDS_IN_REMOTE_COMPUTER
Definition RequestStructures.h:318
_Use_decl_annotations_ BOOLEAN CommonValidateCoreNumber(UINT32 CoreNumber)
Validate core number.
Definition Common.c:256
BOOLEAN g_InterceptDebugBreaks
shows whether the debugger should intercept breakpoints (#DB) or not
Definition Global.h:121
BOOLEAN g_InterceptBreakpoints
shows whether the debugger should intercept breakpoints (#BP) or not
Definition Global.h:115
BOOLEAN g_InterceptBreakpointsAndEventsForCommandsInRemoteComputer
To avoid getting stuck from getting hit from the breakpoints while executing the commands in the remo...
Definition Global.h:166
UINT64 Context
Definition RequestStructures.h:335
UINT32 KernelStatus
Definition RequestStructures.h:336
DEBUGGER_TEST_QUERY_STATE RequestType
Definition RequestStructures.h:334

◆ KdQueryDebuggerQueryThreadOrProcessTracingDetailsByCoreId()

BOOLEAN KdQueryDebuggerQueryThreadOrProcessTracingDetailsByCoreId ( UINT32 CoreId,
DEBUGGER_THREAD_PROCESS_TRACING TracingType )

Query for process/thread interception status.

Parameters
CoreId
TracingType
Returns
BOOLEAN whether it's activated or not
221{
222 BOOLEAN Result = FALSE;
223 PROCESSOR_DEBUGGING_STATE * DbgState = &g_DbgState[CoreId];
224
225 switch (TracingType)
226 {
228
230
231 break;
232
234
236
237 break;
238
240
242
243 break;
244
246
248
249 break;
250
251 default:
252
253 LogError("Err, debugger encountered an unknown query type for querying process or thread interception details");
254
255 break;
256 }
257
258 return Result;
259}
@ DEBUGGER_THREAD_PROCESS_TRACING_INTERCEPT_CLOCK_INTERRUPTS_FOR_THREAD_CHANGE
Definition DataTypes.h:106
@ DEBUGGER_THREAD_PROCESS_TRACING_INTERCEPT_CLOCK_INTERRUPTS_FOR_PROCESS_CHANGE
Definition DataTypes.h:107
@ DEBUGGER_THREAD_PROCESS_TRACING_INTERCEPT_CLOCK_DEBUG_REGISTER_INTERCEPTION
Definition DataTypes.h:108
@ DEBUGGER_THREAD_PROCESS_TRACING_INTERCEPT_CLOCK_WAITING_FOR_MOV_CR3_VM_EXITS
Definition DataTypes.h:109
BOOLEAN InterceptClockInterruptsForProcessChange
Definition State.h:63
BOOLEAN DebugRegisterInterceptionState
Definition State.h:56
BOOLEAN IsWatingForMovCr3VmExits
Definition State.h:62
BOOLEAN InterceptClockInterruptsForThreadChange
Definition State.h:57

◆ KdQueryRflagTrapState()

VOID KdQueryRflagTrapState ( )

Query state of the RFLAG's traps.

Returns
VOID
1676{
1677 //
1678 // show the number of items
1679 //
1680 LogInfo("Number of valid entries: 0x%x\n"
1681 "(Please be aware that only top 0x%x items are considered valid. "
1682 "There could be other items present in the array, but they are not valid.)",
1685
1686 for (size_t i = 0; i < MAXIMUM_NUMBER_OF_THREAD_INFORMATION_FOR_TRAPS; i++)
1687 {
1688 LogInfo("g_TrapFlagState.ThreadInformation[%d].ProcessId = %x | ThreadId = %x",
1689 i,
1692 }
1693}
#define MAXIMUM_NUMBER_OF_THREAD_INFORMATION_FOR_TRAPS
maximum number of thread/process ids to be allocated for a simultaneous debugging
Definition Constants.h:407
DEBUGGER_TRAP_FLAG_STATE g_TrapFlagState
State of the trap-flag.
Definition Global.h:29
UINT32 ProcessId
Definition State.h:113
struct _DEBUGGER_PROCESS_THREAD_INFORMATION::@49::@51 Fields
UINT32 ThreadId
Definition State.h:114
DEBUGGER_PROCESS_THREAD_INFORMATION ThreadInformation[MAXIMUM_NUMBER_OF_THREAD_INFORMATION_FOR_TRAPS]
Definition State.h:128
UINT32 NumberOfItems
Definition State.h:127

◆ KdQuerySystemState()

VOID KdQuerySystemState ( )

Query state of the system.

Returns
VOID
1763{
1764 ULONG ProcessorsCount;
1765
1766 ProcessorsCount = KeQueryActiveProcessorCount(0);
1767
1768 //
1769 // Query core debugging Lock info
1770 //
1771 Log("================================================ Debugging Lock Info ================================================\n");
1772
1773 for (size_t i = 0; i < ProcessorsCount; i++)
1774 {
1775 if (SpinlockCheckLock(&g_DbgState[i].Lock))
1776 {
1777 LogInfo("Core : %d is locked", i);
1778 }
1779 else
1780 {
1781 LogInfo("Core : %d isn't locked", i);
1782 }
1783 }
1784
1785 //
1786 // Query if the core is halted (or NMI is received) when the debuggee
1787 // was in the vmx-root mode
1788 //
1789 Log("\n================================================ NMI Receiver State =======+=========================================\n");
1790
1791 for (size_t i = 0; i < ProcessorsCount; i++)
1792 {
1793 if (g_DbgState[i].NmiState.NmiCalledInVmxRootRelatedToHaltDebuggee)
1794 {
1795 LogInfo("Core : %d - called from an NMI that is called in VMX-root mode", i);
1796 }
1797 else
1798 {
1799 LogInfo("Core : %d - not called from an NMI handler (through the immediate VM-exit mechanism)", i);
1800 }
1801 }
1802}
#define Log(format,...)
Log without any prefix.
Definition HyperDbgHyperLogIntrinsics.h:129

◆ KdReadMemory()

_Use_decl_annotations_ BOOLEAN KdReadMemory ( PGUEST_REGS Regs,
PDEBUGGEE_REGISTER_READ_DESCRIPTION ReadRegisterRequest )

read registers

Parameters
Regs
ReadRegisterRequest
Returns
BOOLEAN
689{
690 GUEST_EXTRA_REGISTERS ERegs = {0};
691
692 if (ReadRegisterRequest->RegisterId == DEBUGGEE_SHOW_ALL_REGISTERS)
693 {
694 //
695 // Add General purpose registers
696 //
697 memcpy((void *)((CHAR *)ReadRegisterRequest + sizeof(DEBUGGEE_REGISTER_READ_DESCRIPTION)),
698 Regs,
699 sizeof(GUEST_REGS));
700
701 //
702 // Read Extra registers
703 //
712
713 //
714 // copy at the end of ReadRegisterRequest structure
715 //
716 memcpy((void *)((CHAR *)ReadRegisterRequest + sizeof(DEBUGGEE_REGISTER_READ_DESCRIPTION) + sizeof(GUEST_REGS)),
717 &ERegs,
718 sizeof(GUEST_EXTRA_REGISTERS));
719 }
720 else
721 {
722 ReadRegisterRequest->Value = DebuggerGetRegValueWrapper(Regs, ReadRegisterRequest->RegisterId);
723 }
724
725 return TRUE;
726}
UINT64 DebuggerGetRegValueWrapper(PGUEST_REGS GuestRegs, UINT32 RegId)
A wrapper for GetRegValue() in script-engine.
Definition Debugger.c:21
@ REGISTER_CS
Definition ScriptEngineCommonDefinitions.h:394
@ REGISTER_RIP
Definition ScriptEngineCommonDefinitions.h:416
@ REGISTER_FS
Definition ScriptEngineCommonDefinitions.h:392
@ REGISTER_SS
Definition ScriptEngineCommonDefinitions.h:395
@ REGISTER_GS
Definition ScriptEngineCommonDefinitions.h:393
@ REGISTER_ES
Definition ScriptEngineCommonDefinitions.h:391
@ REGISTER_RFLAGS
Definition ScriptEngineCommonDefinitions.h:396
@ REGISTER_DS
Definition ScriptEngineCommonDefinitions.h:390
UINT64 Value
Definition RequestStructures.h:1158
struct for extra registers
Definition BasicTypes.h:103
UINT16 FS
Definition BasicTypes.h:106
UINT16 ES
Definition BasicTypes.h:108
UINT64 RFLAGS
Definition BasicTypes.h:110
UINT64 RIP
Definition BasicTypes.h:111
UINT16 DS
Definition BasicTypes.h:105
UINT16 SS
Definition BasicTypes.h:109
UINT16 GS
Definition BasicTypes.h:107
UINT16 CS
Definition BasicTypes.h:104

◆ KdReadRegisters()

_Use_decl_annotations_ BOOLEAN KdReadRegisters ( PROCESSOR_DEBUGGING_STATE * DbgState,
PDEBUGGEE_REGISTER_READ_DESCRIPTION ReadRegisterRequest )

read registers

Parameters
DbgStateThe state of the debugger on the current core
ReadRegisterRequest
Returns
BOOLEAN
640{
641 GUEST_EXTRA_REGISTERS ERegs = {0};
642
643 if (ReadRegisterRequest->RegisterId == DEBUGGEE_SHOW_ALL_REGISTERS)
644 {
645 //
646 // Add General purpose registers
647 //
648 memcpy((void *)((CHAR *)ReadRegisterRequest + sizeof(DEBUGGEE_REGISTER_READ_DESCRIPTION)),
649 DbgState->Regs,
650 sizeof(GUEST_REGS));
651
652 //
653 // Read Extra registers
654 //
663
664 //
665 // copy at the end of ReadRegisterRequest structure
666 //
667 memcpy((void *)((CHAR *)ReadRegisterRequest + sizeof(DEBUGGEE_REGISTER_READ_DESCRIPTION) + sizeof(GUEST_REGS)),
668 &ERegs,
669 sizeof(GUEST_EXTRA_REGISTERS));
670 }
671 else
672 {
673 ReadRegisterRequest->Value = DebuggerGetRegValueWrapper(DbgState->Regs, ReadRegisterRequest->RegisterId);
674 }
675
676 return TRUE;
677}

◆ KdRegularStepInInstruction()

VOID KdRegularStepInInstruction ( PROCESSOR_DEBUGGING_STATE * DbgState)

Regular step-in | step one instruction to the debuggee.

Parameters
DbgStateThe state of the debugger on the current core
Returns
VOID
1516{
1518
1519 //
1520 // Unset the trap flag on the next VM-exit
1521 //
1522 BreakpointRestoreTheTrapFlagOnceTriggered(HANDLE_TO_UINT32(PsGetCurrentProcessId()), HANDLE_TO_UINT32(PsGetCurrentThreadId()));
1523}
VOID TracingPerformRegularStepInInstruction(PROCESSOR_DEBUGGING_STATE *DbgState)
Regular step-in | step one instruction to the debuggee.
Definition Tracing.c:113

◆ KdRegularStepOver()

VOID KdRegularStepOver ( PROCESSOR_DEBUGGING_STATE * DbgState,
BOOLEAN IsNextInstructionACall,
UINT32 CallLength )

Regular step-over | step one instruction to the debuggee if there is a call then it jumps the call.

Parameters
DbgStateThe state of the debugger on the current core
IsNextInstructionACall
CallLength
Returns
VOID
1537{
1538 UINT64 NextAddressForHardwareDebugBp = 0;
1539 ULONG ProcessorsCount;
1540
1541 if (IsNextInstructionACall)
1542 {
1543 //
1544 // It's a call, we should put a hardware debug register breakpoint
1545 // on the next instruction
1546 //
1547 NextAddressForHardwareDebugBp = VmFuncGetLastVmexitRip(DbgState->CoreId) + CallLength;
1548
1549 ProcessorsCount = KeQueryActiveProcessorCount(0);
1550
1551 //
1552 // Store the detail of the hardware debug register to avoid trigger
1553 // in other processes
1554 //
1555 g_HardwareDebugRegisterDetailsForStepOver.Address = NextAddressForHardwareDebugBp;
1558
1559 //
1560 // Add hardware debug breakpoints on all core on vm-entry
1561 //
1562 for (size_t i = 0; i < ProcessorsCount; i++)
1563 {
1564 g_DbgState[i].HardwareDebugRegisterForStepping = NextAddressForHardwareDebugBp;
1565 }
1566 }
1567 else
1568 {
1569 //
1570 // Any instruction other than call (regular step)
1571 //
1573 }
1574}

◆ KdReloadSymbolDetailsInDebuggee()

_Use_decl_annotations_ VOID KdReloadSymbolDetailsInDebuggee ( PDEBUGGEE_SYMBOL_REQUEST_PACKET SymPacket)

Notify user-mode to re-send (reload) the symbol packets.

Parameters
SymPacket
Returns
VOID
852{
853 //
854 // Check if the priority buffer is full or not
855 //
857
858 //
859 // Send one byte buffer and operation codes
860 //
862 SymPacket,
864 TRUE);
865}
#define OPERATION_COMMAND_FROM_DEBUGGER_RELOAD_SYMBOL
Definition Constants.h:384

◆ KdResponsePacketToDebugger()

_Use_decl_annotations_ BOOLEAN KdResponsePacketToDebugger ( DEBUGGER_REMOTE_PACKET_TYPE PacketType,
DEBUGGER_REMOTE_PACKET_REQUESTED_ACTION Response,
CHAR * OptionalBuffer,
UINT32 OptionalBufferLength )

Sends a HyperDbg response packet to the debugger.

Parameters
PacketType
Response
OptionalBuffer
OptionalBufferLength
Returns
BOOLEAN
299{
300 DEBUGGER_REMOTE_PACKET Packet = {0};
301 BOOLEAN Result = FALSE;
302
303 //
304 // Make the packet's structure
305 //
307 Packet.TypeOfThePacket = PacketType;
308
309 //
310 // Set the requested action
311 //
312 Packet.RequestedActionOfThePacket = Response;
313
314 //
315 // Send the serial packets to the debugger
316 //
317 if (OptionalBuffer == NULL || OptionalBufferLength == 0)
318 {
319 Packet.Checksum = KdComputeDataChecksum((PVOID)((UINT64)&Packet + 1),
320 sizeof(DEBUGGER_REMOTE_PACKET) - sizeof(BYTE));
321
322 //
323 // Check if we're in Vmx-root, if it is then we use our customized HIGH_IRQL Spinlock,
324 // if not we use the windows spinlock
325 //
328 Result = SerialConnectionSend((CHAR *)&Packet,
329 sizeof(DEBUGGER_REMOTE_PACKET)));
330 }
331 else
332 {
333 Packet.Checksum = KdComputeDataChecksum((PVOID)((UINT64)&Packet + 1),
334 sizeof(DEBUGGER_REMOTE_PACKET) - sizeof(BYTE));
335
336 Packet.Checksum += KdComputeDataChecksum((PVOID)OptionalBuffer, OptionalBufferLength);
337
338 //
339 // Check if we're in Vmx-root, if it is then we use our customized HIGH_IRQL Spinlock,
340 // if not we use the windows spinlock
341 //
342
345 Result = SerialConnectionSendTwoBuffers((CHAR *)&Packet,
347 OptionalBuffer,
348 OptionalBufferLength));
349 }
350
352 {
353 //
354 // Set it to false by zeroing it
355 //
357 }
358
359 return Result;
360}
BOOLEAN SerialConnectionSendTwoBuffers(CHAR *Buffer1, UINT32 Length1, CHAR *Buffer2, UINT32 Length2)
Perform sending 2 not appended buffers over serial.
Definition SerialConnection.c:192
BOOLEAN SerialConnectionSend(CHAR *Buffer, UINT32 Length)
Perform sending buffer over serial.
Definition SerialConnection.c:155

◆ KdSendCommandFinishedSignal()

VOID KdSendCommandFinishedSignal ( UINT32 CoreId)

Notify debugger that the execution of command finished.

Parameters
CoreId
Returns
VOID
925{
926 //
927 // Halt other cores again
928 //
931 NULL);
932}
@ DEBUGGEE_PAUSING_REASON_DEBUGGEE_COMMAND_EXECUTION_FINISHED
Definition Connection.h:34
_Use_decl_annotations_ VOID KdHandleBreakpointAndDebugBreakpointsCallback(UINT32 CoreId, DEBUGGEE_PAUSING_REASON Reason, PDEBUGGER_TRIGGERED_EVENT_DETAILS EventDetails)
Handle #DBs and #BPs for kernel debugger.
Definition Kd.c:1124

◆ KdSendFormatsFunctionResult()

VOID KdSendFormatsFunctionResult ( UINT64 Value)

Notify user-mode to unload the debuggee and close the connections.

Parameters
Value
Returns
VOID
901{
902 DEBUGGEE_FORMATS_PACKET FormatsPacket = {0};
903
905 FormatsPacket.Value = Value;
906
907 //
908 // Kernel debugger is active, we should send the bytes over serial
909 //
913 (CHAR *)&FormatsPacket,
915}
@ DEBUGGER_REMOTE_PACKET_REQUESTED_ACTION_DEBUGGEE_RESULT_OF_FORMATS
Definition Connection.h:111
RequestedActionOfThePacket Value(0x1) 00000000
The structure of .formats result packet in HyperDbg.
Definition RequestStructures.h:1033
UINT32 Result
Definition RequestStructures.h:1035
UINT64 Value
Definition RequestStructures.h:1034

◆ KdSwitchCore()

BOOLEAN KdSwitchCore ( PROCESSOR_DEBUGGING_STATE * DbgState,
DEBUGGEE_CHANGE_CORE_PACKET * ChangeCorePacket )

change the current operating core to new core

Parameters
DbgStateThe state of the debugger on the current core
ChangeCorePacket
Returns
BOOLEAN
738{
739 ULONG ProcessorsCount = KeQueryActiveProcessorCount(0);
740
741 if (DbgState->CoreId == ChangeCorePacket->NewCore)
742 {
743 //
744 // The operating core and the target core is the same, no need for further action
745 //
746 ChangeCorePacket->Result = DEBUGGER_OPERATION_WAS_SUCCESSFUL;
747 return FALSE; // Return FALSE to not unlock anything
748 }
749
750 //
751 // Check if core is valid or not
752 //
753 if (ChangeCorePacket->NewCore >= ProcessorsCount)
754 {
755 //
756 // Invalid core count
757 //
759 return FALSE;
760 }
761
762 //
763 // *** Core is valid ***
764 //
765
766 //
767 // Check to see whether this core is locked or not
768 //
769 if (!KdCheckTargetCoreIsLocked(ChangeCorePacket->NewCore))
770 {
772 return FALSE;
773 }
774
775 //
776 // Check if we should enable interrupts in this core or not
777 //
779
780 //
781 // Unset the current operating core (this is not important as if we
782 // return from the operating function then the it will be unset
783 // automatically but as we want to not have two operating cores
784 // at the same time so we unset it here too)
785 //
786 DbgState->MainDebuggingCore = FALSE;
787
788 //
789 // Set new operating core
790 //
791 g_DbgState[ChangeCorePacket->NewCore].MainDebuggingCore = TRUE;
792
793 //
794 // Unlock the new core
795 // *** We should not unlock the spinlock here as the other core might
796 // simultaneously start sending packets and corrupt our packets ***
797 //
798 ChangeCorePacket->Result = DEBUGGER_OPERATION_WAS_SUCCESSFUL;
799 return TRUE;
800}
#define DEBUGGER_ERROR_PREPARING_DEBUGGEE_INVALID_CORE_IN_REMOTE_DEBUGGE
error, invalid core selected in changing core in remote debuggee
Definition ErrorCodes.h:158
#define DEBUGGER_ERROR_TARGET_SWITCHING_CORE_IS_NOT_LOCKED
error, switching to the target core is not possible because core is not locked (probably due to a rac...
Definition ErrorCodes.h:534
BOOLEAN KdCheckTargetCoreIsLocked(UINT32 CoreNumber)
Check whether a specific target core is locked or not.
Definition Kd.c:1734
UINT32 Result
Definition RequestStructures.h:601
UINT32 NewCore
Definition RequestStructures.h:600

◆ KdUninitializeKernelDebugger()

VOID KdUninitializeKernelDebugger ( )

uninitialize kernel debugger

this function should be called on vmx non-root

Returns
VOID
82{
83 ULONG ProcessorsCount;
84
86 {
87 ProcessorsCount = KeQueryActiveProcessorCount(0);
88
89 //
90 // Indicate that the kernel debugger is not active
91 //
93
94 //
95 // Reset pause break requests
96 //
98
99 //
100 // Remove all active breakpoints
101 //
103
104 //
105 // Disable vm-exit on Hardware debug exceptions and breakpoints
106 // so, not intercept #DBs and #BP by changing exception bitmap (one core)
107 //
109 }
110}
VOID BreakpointRemoveAllBreakpoints()
Remove all the breakpoints if possible.
Definition BreakpointCommands.c:803
VOID BroadcastDisableDbAndBpExitingAllCores()
routines to unset vm-exit on all #DBs and #BP on all cores
Definition Broadcast.c:49

◆ KdUnlockTheHaltedCore()

VOID KdUnlockTheHaltedCore ( PROCESSOR_DEBUGGING_STATE * DbgState)

unlock the target core

Parameters
DbgStateThe state of the debugger on the target core
Returns
VOID
1813{
1814 SpinlockUnlock(&DbgState->Lock);
1815}