ReactOS  0.4.15-dev-1392-g3014417
kdb.c File Reference
#include <ntoskrnl.h>
#include <debug.h>
Include dependency graph for kdb.c:

Go to the source code of this file.

Macros

#define NDEBUG
 
#define KDB_STACK_SIZE   (4096*3)
 
#define KDB_MAXIMUM_BREAKPOINT_COUNT   256
 
#define KDB_MAXIMUM_HW_BREAKPOINT_COUNT   4
 
#define KDB_MAXIMUM_SW_BREAKPOINT_COUNT   256
 
#define __STRING(x)   #x
 
#define _STRING(x)   __STRING(x)
 
#define CONST_STR_LEN(x)   (sizeof(x)/sizeof(x[0]) - 1)
 

Functions

static VOID KdbpKdbTrapFrameFromKernelStack (PVOID KernelStack, PKDB_KTRAP_FRAME KdbTrapFrame)
 
static NTSTATUS KdbpOverwriteInstruction (IN PEPROCESS Process, IN ULONG_PTR Address, IN UCHAR NewInst, OUT PUCHAR OldInst OPTIONAL)
 Overwrites the instruction at Address with NewInst and stores the old instruction in *OldInst. More...
 
BOOLEAN KdbpShouldStepOverInstruction (ULONG_PTR Eip)
 Checks whether the given instruction can be single stepped or has to be stepped over using a temporary breakpoint. More...
 
BOOLEAN KdbpStepOverInstruction (ULONG_PTR Eip)
 Steps over an instruction. More...
 
BOOLEAN KdbpStepIntoInstruction (ULONG_PTR Eip)
 Steps into an instruction (interrupts) More...
 
LONG KdbpGetNextBreakPointNr (IN ULONG Start OPTIONAL)
 Gets the number of the next breakpoint >= Start. More...
 
BOOLEAN KdbpGetBreakPointInfo (IN ULONG BreakPointNr, OUT ULONG_PTR *Address OPTIONAL, OUT KDB_BREAKPOINT_TYPE *Type OPTIONAL, OUT UCHAR *Size OPTIONAL, OUT KDB_ACCESS_TYPE *AccessType OPTIONAL, OUT UCHAR *DebugReg OPTIONAL, OUT BOOLEAN *Enabled OPTIONAL, OUT BOOLEAN *Global OPTIONAL, OUT PEPROCESS *Process OPTIONAL, OUT PCHAR *ConditionExpression OPTIONAL)
 Returns information of the specified breakpoint. More...
 
NTSTATUS KdbpInsertBreakPoint (IN ULONG_PTR Address, IN KDB_BREAKPOINT_TYPE Type, IN UCHAR Size OPTIONAL, IN KDB_ACCESS_TYPE AccessType OPTIONAL, IN PCHAR ConditionExpression OPTIONAL, IN BOOLEAN Global, OUT PLONG BreakPointNr OPTIONAL)
 Inserts a breakpoint into the breakpoint array. More...
 
BOOLEAN KdbpDeleteBreakPoint (IN LONG BreakPointNr OPTIONAL, IN OUT PKDB_BREAKPOINT BreakPoint OPTIONAL)
 Deletes a breakpoint. More...
 
static LONG KdbpIsBreakPointOurs (IN NTSTATUS ExceptionCode, IN PCONTEXT Context)
 Checks if the breakpoint was set by the debugger. More...
 
BOOLEAN KdbpEnableBreakPoint (IN LONG BreakPointNr OPTIONAL, IN OUT PKDB_BREAKPOINT BreakPoint OPTIONAL)
 Enables a breakpoint. More...
 
BOOLEAN KdbpDisableBreakPoint (IN LONG BreakPointNr OPTIONAL, IN OUT PKDB_BREAKPOINT BreakPoint OPTIONAL)
 Disables a breakpoint. More...
 
BOOLEAN KdbpGetEnterCondition (IN LONG ExceptionNr, IN BOOLEAN FirstChance, OUT KDB_ENTER_CONDITION *Condition)
 Gets the first or last chance enter-condition for exception nr. ExceptionNr. More...
 
BOOLEAN KdbpSetEnterCondition (IN LONG ExceptionNr, IN BOOLEAN FirstChance, IN KDB_ENTER_CONDITION Condition)
 Sets the first or last chance enter-condition for exception nr. ExceptionNr. More...
 
BOOLEAN KdbpAttachToThread (PVOID ThreadId)
 Switches to another thread context. More...
 
BOOLEAN KdbpAttachToProcess (PVOID ProcessId)
 Switches to another process/thread context. More...
 
static VOID KdbpCallMainLoop (VOID)
 Calls the main loop ... More...
 
static VOID KdbpInternalEnter (VOID)
 Internal function to enter KDB. More...
 
static ULONG KdbpGetExceptionNumberFromStatus (IN NTSTATUS ExceptionCode)
 
KD_CONTINUE_TYPE KdbEnterDebuggerException (IN PEXCEPTION_RECORD64 ExceptionRecord, IN KPROCESSOR_MODE PreviousMode, IN PCONTEXT Context, IN BOOLEAN FirstChance)
 KDB Exception filter. More...
 
KD_CONTINUE_TYPE KdbEnterDebuggerFirstChanceException (IN OUT PKTRAP_FRAME TrapFrame)
 
VOID NTAPI KdbpGetCommandLineSettings (PCHAR p1)
 
NTSTATUS KdbpSafeReadMemory (OUT PVOID Dest, IN PVOID Src, IN ULONG Bytes)
 
NTSTATUS KdbpSafeWriteMemory (OUT PVOID Dest, IN PVOID Src, IN ULONG Bytes)
 

Variables

static LONG KdbEntryCount = 0
 
static CHAR KdbStack [KDB_STACK_SIZE]
 
static ULONG KdbBreakPointCount = 0
 
static KDB_BREAKPOINT KdbBreakPoints [KDB_MAXIMUM_BREAKPOINT_COUNT] = {{0}}
 
static ULONG KdbSwBreakPointCount = 0
 
static ULONG KdbHwBreakPointCount = 0
 
static PKDB_BREAKPOINT KdbSwBreakPoints [KDB_MAXIMUM_SW_BREAKPOINT_COUNT]
 
static PKDB_BREAKPOINT KdbHwBreakPoints [KDB_MAXIMUM_HW_BREAKPOINT_COUNT]
 
static PKDB_BREAKPOINT KdbBreakPointToReenable = NULL
 
static BOOLEAN KdbpEvenThoughWeHaveABreakPointToReenableWeAlsoHaveARealSingleStep
 
LONG KdbLastBreakPointNr = -1
 
ULONG KdbNumSingleSteps = 0
 
BOOLEAN KdbSingleStepOver = FALSE
 
ULONG KdbDebugState = 0
 
static BOOLEAN KdbEnteredOnSingleStep = FALSE
 
PEPROCESS KdbCurrentProcess = NULL
 
PEPROCESS KdbOriginalProcess = NULL
 
PETHREAD KdbCurrentThread = NULL
 
PETHREAD KdbOriginalThread = NULL
 
PKDB_KTRAP_FRAME KdbCurrentTrapFrame = NULL
 
static KDB_KTRAP_FRAME KdbTrapFrame = { 0 }
 
static KDB_KTRAP_FRAME KdbThreadTrapFrame = { 0 }
 
static KAPC_STATE KdbApcState
 
BOOLEAN KdbpBugCheckRequested
 
static KDB_ENTER_CONDITION KdbEnterConditions [][2]
 
static const CHARExceptionNrToString []
 

Macro Definition Documentation

◆ __STRING

#define __STRING (   x)    #x

Definition at line 25 of file kdb.c.

◆ _STRING

#define _STRING (   x)    __STRING(x)

Definition at line 26 of file kdb.c.

◆ CONST_STR_LEN

#define CONST_STR_LEN (   x)    (sizeof(x)/sizeof(x[0]) - 1)

◆ KDB_MAXIMUM_BREAKPOINT_COUNT

#define KDB_MAXIMUM_BREAKPOINT_COUNT   256

Definition at line 21 of file kdb.c.

◆ KDB_MAXIMUM_HW_BREAKPOINT_COUNT

#define KDB_MAXIMUM_HW_BREAKPOINT_COUNT   4

Definition at line 22 of file kdb.c.

◆ KDB_MAXIMUM_SW_BREAKPOINT_COUNT

#define KDB_MAXIMUM_SW_BREAKPOINT_COUNT   256

Definition at line 23 of file kdb.c.

◆ KDB_STACK_SIZE

#define KDB_STACK_SIZE   (4096*3)

Definition at line 20 of file kdb.c.

◆ NDEBUG

#define NDEBUG

Definition at line 13 of file kdb.c.

Function Documentation

◆ KdbEnterDebuggerException()

KD_CONTINUE_TYPE KdbEnterDebuggerException ( IN PEXCEPTION_RECORD64  ExceptionRecord,
IN KPROCESSOR_MODE  PreviousMode,
IN PCONTEXT  Context,
IN BOOLEAN  FirstChance 
)

KDB Exception filter.

Called by the exception dispatcher.

Parameters
ExceptionRecordUnused.
PreviousModeUserMode if the exception was raised from umode, otherwise KernelMode.
ContextContext, IN/OUT parameter.
TrapFrameException TrapFrame.
FirstChanceTRUE when called before exception frames were serached, FALSE for the second call.
Returns
KD_CONTINUE_TYPE

Definition at line 1258 of file kdb.c.

1263 {
1264  KDB_ENTER_CONDITION EnterCondition;
1265  KD_CONTINUE_TYPE ContinueType = kdHandleException;
1266  PKDB_BREAKPOINT BreakPoint;
1267  ULONG ExpNr;
1268  ULONGLONG ull;
1269  BOOLEAN Resume = FALSE;
1270  BOOLEAN EnterConditionMet = TRUE;
1271  ULONG OldEflags;
1272  KIRQL OldIrql;
1274 
1275  ExceptionCode = (ExceptionRecord ? ExceptionRecord->ExceptionCode : STATUS_BREAKPOINT);
1276 
1278 
1279  /* Set continue type to kdContinue for single steps and breakpoints */
1283  {
1284  ContinueType = kdContinue;
1285  }
1286 
1287  /* Check if we should handle the exception. */
1288  /* FIXME - won't get all exceptions here :( */
1290  EnterCondition = KdbEnterConditions[ExpNr][FirstChance ? 0 : 1];
1291  if (EnterCondition == KdbDoNotEnter ||
1292  (EnterCondition == KdbEnterFromUmode && PreviousMode == KernelMode) ||
1293  (EnterCondition == KdbEnterFromKmode && PreviousMode != KernelMode))
1294  {
1295  EnterConditionMet = FALSE;
1296  }
1297 
1298  /* If we stopped on one of our breakpoints then let the user know */
1299  KdbLastBreakPointNr = -1;
1301 
1302  if (FirstChance && (ExceptionCode == STATUS_SINGLE_STEP || ExceptionCode == STATUS_BREAKPOINT) &&
1304  {
1305  BreakPoint = KdbBreakPoints + KdbLastBreakPointNr;
1306 
1308  {
1309  /* ... and restore the original instruction */
1311  BreakPoint->Data.SavedInstruction, NULL)))
1312  {
1313  KdbpPrint("Couldn't restore original instruction after INT3! Cannot continue execution.\n");
1314  KeBugCheck(0); // FIXME: Proper bugcode!
1315  }
1316 
1317  /* Also since we are past the int3 now, decrement EIP in the
1318  TrapFrame. This is only needed because KDBG insists on working
1319  with the TrapFrame instead of with the Context, as it is supposed
1320  to do. The context has already EIP point to the int3, since
1321  KiDispatchException accounts for that. Whatever we do here with
1322  the TrapFrame does not matter anyway, since KiDispatchException
1323  will overwrite it with the values from the Context! */
1324  Context->Eip--;
1325  }
1326 
1327  if ((BreakPoint->Type == KdbBreakPointHardware) &&
1328  (BreakPoint->Data.Hw.AccessType == KdbAccessExec))
1329  {
1330  Resume = TRUE; /* Set the resume flag when continuing execution */
1331  }
1332 
1333  /*
1334  * When a temporary breakpoint is hit we have to make sure that we are
1335  * in the same context in which it was set, otherwise it could happen
1336  * that another process/thread hits it before and it gets deleted.
1337  */
1338  else if (BreakPoint->Type == KdbBreakPointTemporary &&
1339  BreakPoint->Process == KdbCurrentProcess)
1340  {
1341  ASSERT((Context->EFlags & EFLAGS_TF) == 0);
1342 
1343  /* Delete the temporary breakpoint which was used to step over or into the instruction */
1344  KdbpDeleteBreakPoint(-1, BreakPoint);
1345 
1346  if (--KdbNumSingleSteps > 0)
1347  {
1350  {
1351  Context->EFlags |= EFLAGS_TF;
1352  }
1353 
1354  goto continue_execution; /* return */
1355  }
1356 
1358  }
1359 
1360  /*
1361  * If we hit a breakpoint set by the debugger we set the single step flag,
1362  * ignore the next single step and reenable the breakpoint.
1363  */
1364  else if (BreakPoint->Type == KdbBreakPointSoftware ||
1365  BreakPoint->Type == KdbBreakPointTemporary)
1366  {
1368  Context->EFlags |= EFLAGS_TF;
1369  KdbBreakPointToReenable = BreakPoint;
1370  }
1371 
1372  /* Make sure that the breakpoint should be triggered in this context */
1373  if (!BreakPoint->Global && BreakPoint->Process != KdbCurrentProcess)
1374  {
1375  goto continue_execution; /* return */
1376  }
1377 
1378  /* Check if the condition for the breakpoint is met. */
1379  if (BreakPoint->Condition)
1380  {
1381  /* Setup the KDB trap frame */
1382  KdbTrapFrame = *Context;
1383 
1384  ull = 0;
1385  if (!KdbpRpnEvaluateParsedExpression(BreakPoint->Condition, &KdbTrapFrame, &ull, NULL, NULL))
1386  {
1387  /* FIXME: Print warning? */
1388  }
1389  else if (ull == 0) /* condition is not met */
1390  {
1391  goto continue_execution; /* return */
1392  }
1393  }
1394 
1395  if (BreakPoint->Type == KdbBreakPointSoftware)
1396  {
1397  KdbpPrint("\nEntered debugger on breakpoint #%d: EXEC 0x%04x:0x%08x\n",
1398  KdbLastBreakPointNr, Context->SegCs & 0xffff, Context->Eip);
1399  }
1400  else if (BreakPoint->Type == KdbBreakPointHardware)
1401  {
1402  KdbpPrint("\nEntered debugger on breakpoint #%d: %s 0x%08x\n",
1404  (BreakPoint->Data.Hw.AccessType == KdbAccessRead) ? "READ" :
1405  ((BreakPoint->Data.Hw.AccessType == KdbAccessWrite) ? "WRITE" :
1406  ((BreakPoint->Data.Hw.AccessType == KdbAccessReadWrite) ? "RDWR" : "EXEC")),
1407  BreakPoint->Address);
1408  }
1409  }
1410  else if (ExceptionCode == STATUS_SINGLE_STEP)
1411  {
1412  /* Silently ignore a debugger initiated single step. */
1413  if ((Context->Dr6 & 0xf) == 0 && KdbBreakPointToReenable)
1414  {
1415  /* FIXME: Make sure that the breakpoint was really hit (check bp->Address vs. tf->Eip) */
1416  BreakPoint = KdbBreakPointToReenable;
1418  ASSERT(BreakPoint->Type == KdbBreakPointSoftware ||
1419  BreakPoint->Type == KdbBreakPointTemporary);
1420 
1421  /*
1422  * Reenable the breakpoint we disabled to execute the breakpointed
1423  * instruction.
1424  */
1426  &BreakPoint->Data.SavedInstruction)))
1427  {
1428  KdbpPrint("Warning: Couldn't reenable breakpoint %d\n",
1429  BreakPoint - KdbBreakPoints);
1430  }
1431 
1432  /* Unset TF if we are no longer single stepping. */
1433  if (KdbNumSingleSteps == 0)
1434  Context->EFlags &= ~EFLAGS_TF;
1435 
1437  {
1438  goto continue_execution; /* return */
1439  }
1440  }
1441 
1442  /* Quoth the raven, 'Nevermore!' */
1444 
1445  /* Check if we expect a single step */
1446  if ((Context->Dr6 & 0xf) == 0 && KdbNumSingleSteps > 0)
1447  {
1448  /*ASSERT((Context->Eflags & EFLAGS_TF) != 0);*/
1449  if (--KdbNumSingleSteps > 0)
1450  {
1453  {
1454  Context->EFlags &= ~EFLAGS_TF;
1455  }
1456  else
1457  {
1458  Context->EFlags |= EFLAGS_TF;
1459  }
1460 
1461  goto continue_execution; /* return */
1462  }
1463  else
1464  {
1465  Context->EFlags &= ~EFLAGS_TF;
1467  }
1468  }
1469  else
1470  {
1471  if (!EnterConditionMet)
1472  {
1473  return kdHandleException;
1474  }
1475 
1476  KdbpPrint("\nEntered debugger on unexpected debug trap!\n");
1477  }
1478  }
1479  else if (ExceptionCode == STATUS_BREAKPOINT)
1480  {
1481  if (KdbInitFileBuffer)
1482  {
1484  EnterConditionMet = FALSE;
1485  }
1486  if (!EnterConditionMet)
1487  {
1488  return kdHandleException;
1489  }
1490 
1491  KdbpPrint("\nEntered debugger on embedded INT3 at 0x%04x:0x%08x.\n",
1492  Context->SegCs & 0xffff, Context->Eip - 1);
1493  }
1494  else
1495  {
1496  const CHAR *ExceptionString = (ExpNr < RTL_NUMBER_OF(ExceptionNrToString)) ?
1497  (ExceptionNrToString[ExpNr]) :
1498  ("Unknown/User defined exception");
1499 
1500  if (!EnterConditionMet)
1501  {
1502  return ContinueType;
1503  }
1504 
1505  KdbpPrint("\nEntered debugger on %s-chance exception (Exception Code: 0x%x) (%s)\n",
1506  FirstChance ? "first" : "last", ExceptionCode, ExceptionString);
1507 
1509  ExceptionRecord && ExceptionRecord->NumberParameters != 0)
1510  {
1511  ULONG_PTR TrapCr2;
1512 
1513  TrapCr2 = __readcr2();
1514 
1515  KdbpPrint("Memory at 0x%p could not be accessed\n", TrapCr2);
1516  }
1517  }
1518 
1519  /* Once we enter the debugger we do not expect any more single steps to happen */
1520  KdbNumSingleSteps = 0;
1521 
1522  /* Update the current process pointer */
1526 
1527  /* Setup the KDB trap frame */
1528  KdbTrapFrame = *Context;
1529 
1530  /* Enter critical section */
1531  OldEflags = __readeflags();
1532  _disable();
1533 
1534  /* HACK: Save the current IRQL and pretend we are at passive level,
1535  * although interrupts are off. Needed because KDBG calls pageable code. */
1538 
1539  /* Exception inside the debugger? Game over. */
1541  {
1542  __writeeflags(OldEflags);
1543  return kdHandleException;
1544  }
1545 
1546  /* Call the main loop */
1548 
1549  /* Check if we should single step */
1550  if (KdbNumSingleSteps > 0)
1551  {
1552  /* Variable explains itself! */
1554 
1557  {
1559  /*KdbCurrentTrapFrame->EFlags &= ~EFLAGS_TF;*/
1560  }
1561  else
1562  {
1564  }
1565  }
1566 
1567  /* We can't update the current thread's trapframe 'cause it might not have one */
1568 
1569  /* Detach from attached process */
1571  {
1573  }
1574 
1575  /* Update the exception Context */
1576  *Context = KdbTrapFrame;
1577 
1578  /* Decrement the entry count */
1580 
1581  /* HACK: Raise back to old IRQL */
1583 
1584  /* Leave critical section */
1585  __writeeflags(OldEflags);
1586 
1587  /* Check if user requested a bugcheck */
1589  {
1590  /* Clear the flag and bugcheck the system */
1592  KeBugCheck(MANUALLY_INITIATED_CRASH);
1593  }
1594 
1595 continue_execution:
1596  /* Clear debug status */
1597  if (ExceptionCode == STATUS_BREAKPOINT) /* FIXME: Why clear DR6 on INT3? */
1598  {
1599  /* Set the RF flag so we don't trigger the same breakpoint again. */
1600  if (Resume)
1601  {
1602  Context->EFlags |= EFLAGS_RF;
1603  }
1604 
1605  /* Clear dr6 status flags. */
1606  Context->Dr6 &= ~0x0000e00f;
1607 
1609  {
1610  /* Skip the current instruction */
1611  Context->Eip++;
1612  }
1613  }
1614 
1615  return ContinueType;
1616 }
#define KeGetCurrentIrql()
Definition: env_spec_w32.h:706
BOOLEAN KdbpDeleteBreakPoint(IN LONG BreakPointNr OPTIONAL, IN OUT PKDB_BREAKPOINT BreakPoint OPTIONAL)
Deletes a breakpoint.
Definition: kdb.c:594
_Inout_ PIRP _In_ NTSTATUS ExceptionCode
Definition: cdprocs.h:1772
#define KeRaiseIrql(irql, oldIrql)
Definition: env_spec_w32.h:597
union _KDB_BREAKPOINT::@1799 Data
#define KeLowerIrql(oldIrql)
Definition: env_spec_w32.h:602
static PKDB_BREAKPOINT KdbBreakPointToReenable
Definition: kdb.c:39
__INTRIN_INLINE unsigned long __readcr2(void)
Definition: intrin_x86.h:1740
ULONG Eip
Definition: nt_native.h:1476
struct _KDB_BREAKPOINT::@1799::@1800 Hw
#define PsGetCurrentThread()
Definition: env_spec_w32.h:81
BOOLEAN Global
Definition: kdb.h:36
static VOID KdbpInternalEnter(VOID)
Internal function to enter KDB.
Definition: kdb.c:1153
BOOLEAN KdbpStepIntoInstruction(ULONG_PTR Eip)
Steps into an instruction (interrupts)
Definition: kdb.c:295
#define TRUE
Definition: types.h:120
PETHREAD KdbOriginalThread
Definition: kdb.c:50
PEPROCESS KdbCurrentProcess
Definition: kdb.c:47
char CHAR
Definition: xmlstorage.h:175
LONG NTSTATUS
Definition: precomp.h:26
#define STATUS_SINGLE_STEP
Definition: ntstatus.h:185
BOOLEAN KdbpStepOverInstruction(ULONG_PTR Eip)
Steps over an instruction.
Definition: kdb.c:267
VOID KdbpCliInterpretInitFile(VOID)
This function is called by KdbEnterDebuggerException...
Definition: kdb_cli.c:3686
PEPROCESS KdbOriginalProcess
Definition: kdb.c:48
uint32_t ULONG_PTR
Definition: typedefs.h:65
static ULONG KdbpGetExceptionNumberFromStatus(IN NTSTATUS ExceptionCode)
Definition: kdb.c:1192
UCHAR KIRQL
Definition: env_spec_w32.h:591
static LONG KdbEntryCount
Definition: kdb.c:30
__INTRIN_INLINE uintptr_t __readeflags(void)
Definition: intrin_x86.h:1603
#define FALSE
Definition: types.h:117
DECLSPEC_NORETURN VOID NTAPI KeBugCheck(ULONG BugCheckCode)
Definition: bug.c:1427
static KDB_ENTER_CONDITION KdbEnterConditions[][2]
Definition: kdb.c:58
static const CHAR * ExceptionNrToString[]
Definition: kdb.c:86
static NTSTATUS KdbpOverwriteInstruction(IN PEPROCESS Process, IN ULONG_PTR Address, IN UCHAR NewInst, OUT PUCHAR OldInst OPTIONAL)
Overwrites the instruction at Address with NewInst and stores the old instruction in *OldInst.
Definition: kdb.c:150
static BOOLEAN KdbpEvenThoughWeHaveABreakPointToReenableWeAlsoHaveARealSingleStep
Definition: kdb.c:41
#define PsGetCurrentProcess
Definition: psfuncs.h:17
unsigned char BOOLEAN
#define STATUS_BREAKPOINT
Definition: ntstatus.h:184
ULONG_PTR Address
Definition: kdb.h:35
PVOID Condition
Definition: kdb.h:39
ULONG EFlags
Definition: nt_native.h:1478
PKDB_KTRAP_FRAME KdbCurrentTrapFrame
Definition: kdb.c:51
#define STATUS_ASSERTION_FAILURE
Definition: ntstatus.h:960
_In_ KPROCESSOR_MODE PreviousMode
Definition: sefuncs.h:103
#define ASSERT(a)
Definition: mode.c:45
#define NT_SUCCESS(StatCode)
Definition: apphelp.c:32
uint64_t ULONGLONG
Definition: typedefs.h:67
VOID KdbpPrint(IN PCHAR Format, IN ... OPTIONAL)
Prints the given string with printf-like formatting.
Definition: kdb_cli.c:2618
ULONG KdbNumSingleSteps
Definition: kdb.c:43
#define InterlockedDecrement
Definition: armddk.h:52
enum _KDB_ENTER_CONDITION KDB_ENTER_CONDITION
_Requires_lock_held_ Interrupt _Releases_lock_ Interrupt _In_ _IRQL_restores_ KIRQL OldIrql
Definition: kefuncs.h:790
__INTRIN_INLINE void __writeeflags(uintptr_t Value)
Definition: intrin_x86.h:1598
#define EFLAGS_RF
Definition: cpu.c:19
BOOLEAN KdbSingleStepOver
Definition: kdb.c:44
#define EFLAGS_TF
Definition: ketypes.h:125
BOOLEAN KdbpBugCheckRequested
Definition: kdb_cli.c:132
#define PASSIVE_LEVEL
Definition: env_spec_w32.h:693
BOOLEAN KdbpRpnEvaluateParsedExpression(IN PVOID Expression, IN PKDB_KTRAP_FRAME TrapFrame, OUT PULONGLONG Result, OUT PLONG ErrOffset OPTIONAL, OUT PCHAR ErrMsg OPTIONAL)
Evaluates the given expression and returns the result.
Definition: kdb_expr.c:1181
PEPROCESS Process
Definition: kdb.h:37
UCHAR SavedInstruction
Definition: kdb.h:42
#define InterlockedIncrement
Definition: armddk.h:53
#define STATUS_ACCESS_VIOLATION
Definition: ntstatus.h:242
#define RTL_NUMBER_OF(x)
Definition: RtlRegistry.c:12
LONG KdbLastBreakPointNr
Definition: kdb.c:42
VOID NTAPI KeUnstackDetachProcess(IN PRKAPC_STATE ApcState)
Definition: procobj.c:753
static KAPC_STATE KdbApcState
Definition: kdb.c:54
#define NULL
Definition: types.h:112
static KDB_KTRAP_FRAME KdbTrapFrame
Definition: kdb.c:52
PETHREAD KdbCurrentThread
Definition: kdb.c:49
struct tagContext Context
Definition: acpixf.h:1034
void __cdecl _disable(void)
Definition: intrin_arm.h:365
unsigned int ULONG
Definition: retypes.h:1
static LONG KdbpIsBreakPointOurs(IN NTSTATUS ExceptionCode, IN PCONTEXT Context)
Checks if the breakpoint was set by the debugger.
Definition: kdb.c:644
static KDB_BREAKPOINT KdbBreakPoints[KDB_MAXIMUM_BREAKPOINT_COUNT]
Definition: kdb.c:34
KDB_BREAKPOINT_TYPE Type
Definition: kdb.h:33
static BOOLEAN KdbEnteredOnSingleStep
Definition: kdb.c:46
PCHAR KdbInitFileBuffer
Definition: kdb_cli.c:131

Referenced by KdbEnterDebuggerFirstChanceException(), and KdSendPacket().

◆ KdbEnterDebuggerFirstChanceException()

KD_CONTINUE_TYPE KdbEnterDebuggerFirstChanceException ( IN OUT PKTRAP_FRAME  TrapFrame)

Definition at line 1619 of file kdb.c.

1621 {
1622  EXCEPTION_RECORD64 ExceptionRecord;
1623  KD_CONTINUE_TYPE Return;
1624  CONTEXT Context;
1625 
1626  /* Copy TrapFrame to Context */
1627  RtlZeroMemory(&Context, sizeof(CONTEXT));
1629  KeTrapFrameToContext(TrapFrame, NULL, &Context);
1630 
1631  /* Create ExceptionRecord (assume breakpoint) */
1632  RtlZeroMemory(&ExceptionRecord, sizeof(EXCEPTION_RECORD64));
1633  ExceptionRecord.ExceptionCode = STATUS_BREAKPOINT;
1634 
1635  /* Call real function */
1636  Return = KdbEnterDebuggerException(&ExceptionRecord,
1637  KernelMode,
1638  &Context,
1639  TRUE);
1640 
1641  /* Copy back Context to TrapFrame */
1642  KeContextToTrapFrame(&Context, NULL, TrapFrame, Context.ContextFlags, KernelMode);
1643 
1644  return Return;
1645 }
VOID NTAPI KeContextToTrapFrame(PCONTEXT Context, PKEXCEPTION_FRAME ExeptionFrame, PKTRAP_FRAME TrapFrame, ULONG ContextFlags, KPROCESSOR_MODE PreviousMode)
#define CONTEXT_CONTROL
Definition: nt_native.h:1369
#define CONTEXT_EXTENDED_REGISTERS
#define TRUE
Definition: types.h:120
#define CONTEXT_FLOATING_POINT
Definition: nt_native.h:1372
NTSTATUS ExceptionCode
Definition: rtltypes.h:190
#define CONTEXT_SEGMENTS
Definition: nt_native.h:1371
#define STATUS_BREAKPOINT
Definition: ntstatus.h:184
VOID NTAPI KeTrapFrameToContext(IN PKTRAP_FRAME TrapFrame, IN PKEXCEPTION_FRAME ExceptionFrame, IN OUT PCONTEXT Context)
Definition: context.c:169
#define CONTEXT_DEBUG_REGISTERS
Definition: nt_native.h:1373
#define NULL
Definition: types.h:112
struct tagContext Context
Definition: acpixf.h:1034
#define RtlZeroMemory(Destination, Length)
Definition: typedefs.h:262
#define CONTEXT_INTEGER
Definition: nt_native.h:1370
KD_CONTINUE_TYPE KdbEnterDebuggerException(IN PEXCEPTION_RECORD64 ExceptionRecord, IN KPROCESSOR_MODE PreviousMode, IN PCONTEXT Context, IN BOOLEAN FirstChance)
KDB Exception filter.
Definition: kdb.c:1258

◆ KdbpAttachToProcess()

BOOLEAN KdbpAttachToProcess ( PVOID  ProcessId)

Switches to another process/thread context.

This function switches to the first thread in the specified process.

Parameters
ProcessIdId of the process to switch to.
Return values
TRUESuccess.
FALSEFailure (i.e. invalid process id)

Definition at line 1113 of file kdb.c.

1115 {
1117  PETHREAD Thread;
1119 
1120  /* Get a pointer to the process */
1122  {
1123  KdbpPrint("Invalid process id: 0x%08x\n", (ULONG_PTR)ProcessId);
1124  return FALSE;
1125  }
1126 
1127  Entry = Process->ThreadListHead.Flink;
1130  {
1131  KdbpPrint("No threads in process 0x%p, cannot attach to process!\n", ProcessId);
1132  return FALSE;
1133  }
1134 
1135  Thread = CONTAINING_RECORD(Entry, ETHREAD, ThreadListEntry);
1136 
1138 }
IN PLARGE_INTEGER IN PLARGE_INTEGER PEPROCESS ProcessId
Definition: fatprocs.h:2706
struct _Entry Entry
Definition: kefuncs.h:627
BOOLEAN KdbpAttachToThread(PVOID ThreadId)
Switches to another thread context.
Definition: kdb.c:1032
PEPROCESS KdbCurrentProcess
Definition: kdb.c:47
uint32_t ULONG_PTR
Definition: typedefs.h:65
#define FALSE
Definition: types.h:117
LIST_ENTRY ThreadListHead
Definition: pstypes.h:1271
PFLT_MESSAGE_WAITER_QUEUE CONTAINING_RECORD(Csq, DEVICE_EXTENSION, IrpQueue)) -> WaiterQ.mLock) _IRQL_raises_(DISPATCH_LEVEL) VOID NTAPI FltpAcquireMessageWaiterLock(_In_ PIO_CSQ Csq, _Out_ PKIRQL Irql)
Definition: Messaging.c:560
#define NT_SUCCESS(StatCode)
Definition: apphelp.c:32
CLIENT_ID Cid
Definition: pstypes.h:1070
#define ObDereferenceObject
Definition: obfuncs.h:203
VOID KdbpPrint(IN PCHAR Format, IN ... OPTIONAL)
Prints the given string with printf-like formatting.
Definition: kdb_cli.c:2618
_In_opt_ PFILE_OBJECT _In_opt_ PETHREAD Thread
Definition: fltkernel.h:2653
HANDLE UniqueThread
Definition: compat.h:685
NTSTATUS NTAPI PsLookupProcessByProcessId(IN HANDLE ProcessId, OUT PEPROCESS *Process)
Definition: process.c:919
Definition: typedefs.h:119
#define NULL
Definition: types.h:112
_Must_inspect_result_ _In_ PLARGE_INTEGER _In_ PLARGE_INTEGER _In_ ULONG _In_ PFILE_OBJECT _In_ PVOID Process
Definition: fsrtlfuncs.h:219
base of all file and directory entries
Definition: entries.h:82

Referenced by KdbpCmdProc().

◆ KdbpAttachToThread()

BOOLEAN KdbpAttachToThread ( PVOID  ThreadId)

Switches to another thread context.

Parameters
ThreadIdId of the thread to switch to.
Return values
TRUESuccess.
FALSEFailure (i.e. invalid thread id)

Definition at line 1032 of file kdb.c.

1034 {
1035  PETHREAD Thread = NULL;
1037 
1038  /* Get a pointer to the thread */
1039  if (!NT_SUCCESS(PsLookupThreadByThreadId(ThreadId, &Thread)))
1040  {
1041  KdbpPrint("Invalid thread id: 0x%08x\n", (ULONG_PTR)ThreadId);
1042  return FALSE;
1043  }
1044  Process = Thread->ThreadsProcess;
1045 
1047  {
1048  KdbpPrint("Cannot attach to thread within another process while executing a DPC.\n");
1050  return FALSE;
1051  }
1052 
1053  /* Save the current thread's context (if we previously attached to a thread) */
1055  {
1057  /* Actually, we can't save the context, there's no guarantee that there was a trap frame */
1058  }
1059  else
1060  {
1062  }
1063 
1064  /* Switch to the thread's context */
1065  if (Thread != KdbOriginalThread)
1066  {
1067  /* The thread we're attaching to isn't the thread on which we entered
1068  * kdb and so the thread we're attaching to is not running. There
1069  * is no guarantee that it actually has a trap frame. So we have to
1070  * peek directly at the registers which were saved on the stack when the
1071  * thread was preempted in the scheduler */
1075  }
1076  else /* Switching back to original thread */
1077  {
1079  }
1081 
1082  /* Attach to the thread's process */
1084  if (KdbCurrentProcess != Process)
1085  {
1086  if (KdbCurrentProcess != KdbOriginalProcess) /* detach from previously attached process */
1087  {
1089  }
1090 
1091  if (KdbOriginalProcess != Process)
1092  {
1094  }
1095 
1097  }
1098 
1100  return TRUE;
1101 }
#define TRUE
Definition: types.h:120
PETHREAD KdbOriginalThread
Definition: kdb.c:50
PEPROCESS KdbCurrentProcess
Definition: kdb.c:47
NTSTATUS NTAPI PsLookupThreadByThreadId(IN HANDLE ThreadId, OUT PETHREAD *Thread)
Definition: thread.c:643
KTHREAD Tcb
Definition: pstypes.h:1045
static VOID KdbpKdbTrapFrameFromKernelStack(PVOID KernelStack, PKDB_KTRAP_FRAME KdbTrapFrame)
Definition: kdb.c:114
BOOLEAN NTAPI KeIsExecutingDpc(VOID)
Definition: dpc.c:946
static KDB_KTRAP_FRAME KdbThreadTrapFrame
Definition: kdb.c:53
PEPROCESS KdbOriginalProcess
Definition: kdb.c:48
uint32_t ULONG_PTR
Definition: typedefs.h:65
#define FALSE
Definition: types.h:117
VOID NTAPI KeStackAttachProcess(IN PKPROCESS Process, OUT PRKAPC_STATE ApcState)
Definition: procobj.c:701
#define PsGetCurrentProcess
Definition: psfuncs.h:17
PVOID KernelStack
Definition: ketypes.h:1607
PKDB_KTRAP_FRAME KdbCurrentTrapFrame
Definition: kdb.c:51
#define ASSERT(a)
Definition: mode.c:45
#define NT_SUCCESS(StatCode)
Definition: apphelp.c:32
#define ObDereferenceObject
Definition: obfuncs.h:203
VOID KdbpPrint(IN PCHAR Format, IN ... OPTIONAL)
Prints the given string with printf-like formatting.
Definition: kdb_cli.c:2618
_In_opt_ PFILE_OBJECT _In_opt_ PETHREAD Thread
Definition: fltkernel.h:2653
VOID NTAPI KeUnstackDetachProcess(IN PRKAPC_STATE ApcState)
Definition: procobj.c:753
static KAPC_STATE KdbApcState
Definition: kdb.c:54
#define NULL
Definition: types.h:112
static KDB_KTRAP_FRAME KdbTrapFrame
Definition: kdb.c:52
_Must_inspect_result_ _In_ PLARGE_INTEGER _In_ PLARGE_INTEGER _In_ ULONG _In_ PFILE_OBJECT _In_ PVOID Process
Definition: fsrtlfuncs.h:219
PETHREAD KdbCurrentThread
Definition: kdb.c:49

Referenced by KdbpAttachToProcess(), and KdbpCmdThread().

◆ KdbpCallMainLoop()

static VOID KdbpCallMainLoop ( VOID  )
static

Calls the main loop ...

Definition at line 1143 of file kdb.c.

1144 {
1146 }
VOID KdbpCliMainLoop(IN BOOLEAN EnteredOnSingleStep)
KDB Main Loop.
Definition: kdb_cli.c:3608
static BOOLEAN KdbEnteredOnSingleStep
Definition: kdb.c:46

Referenced by KdbpInternalEnter().

◆ KdbpDeleteBreakPoint()

BOOLEAN KdbpDeleteBreakPoint ( IN LONG BreakPointNr  OPTIONAL,
IN OUT PKDB_BREAKPOINT BreakPoint  OPTIONAL 
)

Deletes a breakpoint.

Parameters
BreakPointNrNumber of the breakpoint to delete. Can be -1
BreakPointBreakpoint to delete. Can be NULL.
Return values
TRUESuccess.
FALSEFailure (invalid breakpoint number)

Definition at line 594 of file kdb.c.

597 {
598  if (BreakPointNr < 0)
599  {
600  ASSERT(BreakPoint);
601  BreakPointNr = BreakPoint - KdbBreakPoints;
602  }
603 
604  if (BreakPointNr < 0 || BreakPointNr >= KDB_MAXIMUM_BREAKPOINT_COUNT)
605  {
606  KdbpPrint("Invalid breakpoint: %d\n", BreakPointNr);
607  return FALSE;
608  }
609 
610  if (!BreakPoint)
611  {
612  BreakPoint = KdbBreakPoints + BreakPointNr;
613  }
614 
615  if (BreakPoint->Type == KdbBreakPointNone)
616  {
617  KdbpPrint("Invalid breakpoint: %d\n", BreakPointNr);
618  return FALSE;
619  }
620 
621  if (BreakPoint->Enabled && !KdbpDisableBreakPoint(-1, BreakPoint))
622  return FALSE;
623 
624  if (BreakPoint->Type != KdbBreakPointTemporary)
625  KdbpPrint("Breakpoint %d deleted.\n", BreakPointNr);
626 
627  BreakPoint->Type = KdbBreakPointNone;
629 
630  return TRUE;
631 }
static ULONG KdbBreakPointCount
Definition: kdb.c:33
#define KDB_MAXIMUM_BREAKPOINT_COUNT
Definition: kdb.c:21
#define TRUE
Definition: types.h:120
BOOLEAN KdbpDisableBreakPoint(IN LONG BreakPointNr OPTIONAL, IN OUT PKDB_BREAKPOINT BreakPoint OPTIONAL)
Disables a breakpoint.
Definition: kdb.c:864
#define FALSE
Definition: types.h:117
#define ASSERT(a)
Definition: mode.c:45
VOID KdbpPrint(IN PCHAR Format, IN ... OPTIONAL)
Prints the given string with printf-like formatting.
Definition: kdb_cli.c:2618
static KDB_BREAKPOINT KdbBreakPoints[KDB_MAXIMUM_BREAKPOINT_COUNT]
Definition: kdb.c:34

Referenced by KdbEnterDebuggerException(), and KdbpCmdEnableDisableClearBreakPoint().

◆ KdbpDisableBreakPoint()

BOOLEAN KdbpDisableBreakPoint ( IN LONG BreakPointNr  OPTIONAL,
IN OUT PKDB_BREAKPOINT BreakPoint  OPTIONAL 
)

Disables a breakpoint.

Parameters
BreakPointNrNumber of the breakpoint to disable. Can be -1
BreakPointBreakpoint to disable. Can be NULL.
Return values
TRUESuccess.
FALSEFailure.
See also
KdbpEnableBreakPoint

Definition at line 864 of file kdb.c.

867 {
868  ULONG i;
870 
871  if (BreakPointNr < 0)
872  {
873  ASSERT(BreakPoint);
874  BreakPointNr = BreakPoint - KdbBreakPoints;
875  }
876 
877  if (BreakPointNr < 0 || BreakPointNr >= KDB_MAXIMUM_BREAKPOINT_COUNT)
878  {
879  KdbpPrint("Invalid breakpoint: %d\n", BreakPointNr);
880  return FALSE;
881  }
882 
883  if (!BreakPoint)
884  {
885  BreakPoint = KdbBreakPoints + BreakPointNr;
886  }
887 
888  if (BreakPoint->Type == KdbBreakPointNone)
889  {
890  KdbpPrint("Invalid breakpoint: %d\n", BreakPointNr);
891  return FALSE;
892  }
893 
894  if (BreakPoint->Enabled == FALSE)
895  {
896  KdbpPrint("Breakpoint %d is not enabled.\n", BreakPointNr);
897  return TRUE;
898  }
899 
900  if (BreakPoint->Type == KdbBreakPointSoftware ||
901  BreakPoint->Type == KdbBreakPointTemporary)
902  {
904  Status = KdbpOverwriteInstruction(BreakPoint->Process, BreakPoint->Address,
905  BreakPoint->Data.SavedInstruction, NULL);
906 
907  if (!NT_SUCCESS(Status))
908  {
909  KdbpPrint("Couldn't restore original instruction.\n");
910  return FALSE;
911  }
912 
913  for (i = 0; i < KdbSwBreakPointCount; i++)
914  {
915  if (KdbSwBreakPoints[i] == BreakPoint)
916  {
918  i = -1; /* if the last breakpoint is disabled dont break with i >= KdbSwBreakPointCount */
919  break;
920  }
921  }
922 
923  if (i != MAXULONG) /* not found */
924  ASSERT(0);
925  }
926  else
927  {
928  ASSERT(BreakPoint->Type == KdbBreakPointHardware);
929 
930  /* Clear the breakpoint. */
931  KdbTrapFrame.Dr7 &= ~(0x3 << (BreakPoint->Data.Hw.DebugReg * 2));
932  if ((KdbTrapFrame.Dr7 & 0xFF) == 0)
933  {
934  /* If no breakpoints are enabled then clear the exact match flags. */
935  KdbTrapFrame.Dr7 &= 0xFFFFFCFF;
936  }
937 
938  for (i = 0; i < KdbHwBreakPointCount; i++)
939  {
940  if (KdbHwBreakPoints[i] == BreakPoint)
941  {
943  i = -1; /* if the last breakpoint is disabled dont break with i >= KdbHwBreakPointCount */
944  break;
945  }
946  }
947 
948  if (i != MAXULONG) /* not found */
949  ASSERT(0);
950  }
951 
952  BreakPoint->Enabled = FALSE;
953  if (BreakPoint->Type != KdbBreakPointTemporary)
954  KdbpPrint("Breakpoint %d disabled.\n", BreakPointNr);
955 
956  return TRUE;
957 }
#define KDB_MAXIMUM_BREAKPOINT_COUNT
Definition: kdb.c:21
#define TRUE
Definition: types.h:120
static ULONG KdbSwBreakPointCount
Definition: kdb.c:35
LONG NTSTATUS
Definition: precomp.h:26
ULONG Dr7
Definition: nt_native.h:1439
static PKDB_BREAKPOINT KdbHwBreakPoints[KDB_MAXIMUM_HW_BREAKPOINT_COUNT]
Definition: kdb.c:38
#define FALSE
Definition: types.h:117
static NTSTATUS KdbpOverwriteInstruction(IN PEPROCESS Process, IN ULONG_PTR Address, IN UCHAR NewInst, OUT PUCHAR OldInst OPTIONAL)
Overwrites the instruction at Address with NewInst and stores the old instruction in *OldInst.
Definition: kdb.c:150
Status
Definition: gdiplustypes.h:24
#define ASSERT(a)
Definition: mode.c:45
#define NT_SUCCESS(StatCode)
Definition: apphelp.c:32
static PKDB_BREAKPOINT KdbSwBreakPoints[KDB_MAXIMUM_SW_BREAKPOINT_COUNT]
Definition: kdb.c:37
VOID KdbpPrint(IN PCHAR Format, IN ... OPTIONAL)
Prints the given string with printf-like formatting.
Definition: kdb_cli.c:2618
#define MAXULONG
Definition: typedefs.h:251
GLsizei GLenum const GLvoid GLsizei GLenum GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLint GLint GLint GLshort GLshort GLshort GLubyte GLubyte GLubyte GLuint GLuint GLuint GLushort GLushort GLushort GLbyte GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLfloat GLint GLint GLint GLint GLshort GLshort GLshort GLshort GLubyte GLubyte GLubyte GLubyte GLuint GLuint GLuint GLuint GLushort GLushort GLushort GLushort GLboolean const GLdouble const GLfloat const GLint const GLshort const GLbyte const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLdouble const GLfloat const GLfloat const GLint const GLint const GLshort const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort GLenum GLenum GLenum GLfloat GLenum GLint GLenum GLenum GLenum GLfloat GLenum GLenum GLint GLenum GLfloat GLenum GLint GLint GLushort GLenum GLenum GLfloat GLenum GLenum GLint GLfloat const GLubyte GLenum GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLint GLint GLsizei GLsizei GLint GLenum GLenum const GLvoid GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLenum const GLdouble GLenum GLenum const GLfloat GLenum GLenum const GLint GLsizei GLuint GLfloat GLuint GLbitfield GLfloat GLint GLuint GLboolean GLenum GLfloat GLenum GLbitfield GLenum GLfloat GLfloat GLint GLint const GLfloat GLenum GLfloat GLfloat GLint GLint GLfloat GLfloat GLint GLint const GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat const GLdouble const GLfloat const GLdouble const GLfloat GLint i
Definition: glfuncs.h:248
#define NULL
Definition: types.h:112
static KDB_KTRAP_FRAME KdbTrapFrame
Definition: kdb.c:52
unsigned int ULONG
Definition: retypes.h:1
static KDB_BREAKPOINT KdbBreakPoints[KDB_MAXIMUM_BREAKPOINT_COUNT]
Definition: kdb.c:34
static ULONG KdbHwBreakPointCount
Definition: kdb.c:36

Referenced by KdbpCmdEnableDisableClearBreakPoint(), and KdbpDeleteBreakPoint().

◆ KdbpEnableBreakPoint()

BOOLEAN KdbpEnableBreakPoint ( IN LONG BreakPointNr  OPTIONAL,
IN OUT PKDB_BREAKPOINT BreakPoint  OPTIONAL 
)

Enables a breakpoint.

Parameters
BreakPointNrNumber of the breakpoint to enable Can be -1.
BreakPointBreakpoint to enable. Can be NULL.
Return values
TRUESuccess.
FALSEFailure.
See also
KdbpDisableBreakPoint

Definition at line 697 of file kdb.c.

700 {
702  INT i;
703  ULONG ul;
704 
705  if (BreakPointNr < 0)
706  {
707  ASSERT(BreakPoint);
708  BreakPointNr = BreakPoint - KdbBreakPoints;
709  }
710 
711  if (BreakPointNr < 0 || BreakPointNr >= KDB_MAXIMUM_BREAKPOINT_COUNT)
712  {
713  KdbpPrint("Invalid breakpoint: %d\n", BreakPointNr);
714  return FALSE;
715  }
716 
717  if (!BreakPoint)
718  {
719  BreakPoint = KdbBreakPoints + BreakPointNr;
720  }
721 
722  if (BreakPoint->Type == KdbBreakPointNone)
723  {
724  KdbpPrint("Invalid breakpoint: %d\n", BreakPointNr);
725  return FALSE;
726  }
727 
728  if (BreakPoint->Enabled)
729  {
730  KdbpPrint("Breakpoint %d is already enabled.\n", BreakPointNr);
731  return TRUE;
732  }
733 
734  if (BreakPoint->Type == KdbBreakPointSoftware ||
735  BreakPoint->Type == KdbBreakPointTemporary)
736  {
738  {
739  KdbpPrint("Maximum number of SW breakpoints (%d) used. "
740  "Disable another breakpoint in order to enable this one.\n",
742  return FALSE;
743  }
744 
745  Status = KdbpOverwriteInstruction(BreakPoint->Process, BreakPoint->Address,
746  0xCC, &BreakPoint->Data.SavedInstruction);
747  if (!NT_SUCCESS(Status))
748  {
749  KdbpPrint("Couldn't access memory at 0x%p\n", BreakPoint->Address);
750  return FALSE;
751  }
752 
753  KdbSwBreakPoints[KdbSwBreakPointCount++] = BreakPoint;
754  }
755  else
756  {
757  if (BreakPoint->Data.Hw.AccessType == KdbAccessExec)
758  ASSERT(BreakPoint->Data.Hw.Size == 1);
759 
760  ASSERT((BreakPoint->Address % BreakPoint->Data.Hw.Size) == 0);
761 
763  {
764  KdbpPrint("Maximum number of HW breakpoints (%d) already used. "
765  "Disable another breakpoint in order to enable this one.\n",
767 
768  return FALSE;
769  }
770 
771  /* Find unused hw breakpoint */
773  for (i = 0; i < KDB_MAXIMUM_HW_BREAKPOINT_COUNT; i++)
774  {
775  if ((KdbTrapFrame.Dr7 & (0x3 << (i * 2))) == 0)
776  break;
777  }
778 
780 
781  /* Set the breakpoint address. */
782  switch (i)
783  {
784  case 0:
785  KdbTrapFrame.Dr0 = BreakPoint->Address;
786  break;
787  case 1:
788  KdbTrapFrame.Dr1 = BreakPoint->Address;
789  break;
790  case 2:
791  KdbTrapFrame.Dr2 = BreakPoint->Address;
792  break;
793  case 3:
794  KdbTrapFrame.Dr3 = BreakPoint->Address;
795  break;
796  }
797 
798  /* Enable the global breakpoint */
799  KdbTrapFrame.Dr7 |= (0x2 << (i * 2));
800 
801  /* Enable the exact match bits. */
802  KdbTrapFrame.Dr7 |= 0x00000300;
803 
804  /* Clear existing state. */
805  KdbTrapFrame.Dr7 &= ~(0xF << (16 + (i * 4)));
806 
807  /* Set the breakpoint type. */
808  switch (BreakPoint->Data.Hw.AccessType)
809  {
810  case KdbAccessExec:
811  ul = 0;
812  break;
813  case KdbAccessWrite:
814  ul = 1;
815  break;
816  case KdbAccessRead:
817  case KdbAccessReadWrite:
818  ul = 3;
819  break;
820  default:
821  ASSERT(0);
822  return TRUE;
823  break;
824  }
825 
826  KdbTrapFrame.Dr7 |= (ul << (16 + (i * 4)));
827 
828  /* Set the breakpoint length. */
829  KdbTrapFrame.Dr7 |= ((BreakPoint->Data.Hw.Size - 1) << (18 + (i * 4)));
830 
831  /* Update KdbCurrentTrapFrame - values are taken from there by the CLI */
833  {
840  }
841 
842  BreakPoint->Data.Hw.DebugReg = i;
843  KdbHwBreakPoints[KdbHwBreakPointCount++] = BreakPoint;
844  }
845 
846  BreakPoint->Enabled = TRUE;
847  if (BreakPoint->Type != KdbBreakPointTemporary)
848  KdbpPrint("Breakpoint %d enabled.\n", BreakPointNr);
849 
850  return TRUE;
851 }
#define KDB_MAXIMUM_SW_BREAKPOINT_COUNT
Definition: kdb.c:23
#define KDB_MAXIMUM_BREAKPOINT_COUNT
Definition: kdb.c:21
#define TRUE
Definition: types.h:120
static ULONG KdbSwBreakPointCount
Definition: kdb.c:35
LONG NTSTATUS
Definition: precomp.h:26
int32_t INT
Definition: typedefs.h:58
ULONG Dr7
Definition: nt_native.h:1439
ULONG Dr3
Definition: nt_native.h:1437
static PKDB_BREAKPOINT KdbHwBreakPoints[KDB_MAXIMUM_HW_BREAKPOINT_COUNT]
Definition: kdb.c:38
#define FALSE
Definition: types.h:117
static NTSTATUS KdbpOverwriteInstruction(IN PEPROCESS Process, IN ULONG_PTR Address, IN UCHAR NewInst, OUT PUCHAR OldInst OPTIONAL)
Overwrites the instruction at Address with NewInst and stores the old instruction in *OldInst.
Definition: kdb.c:150
ULONG Dr1
Definition: nt_native.h:1435
ULONG Dr2
Definition: nt_native.h:1436
PKDB_KTRAP_FRAME KdbCurrentTrapFrame
Definition: kdb.c:51
Status
Definition: gdiplustypes.h:24
#define ASSERT(a)
Definition: mode.c:45
#define NT_SUCCESS(StatCode)
Definition: apphelp.c:32
static PKDB_BREAKPOINT KdbSwBreakPoints[KDB_MAXIMUM_SW_BREAKPOINT_COUNT]
Definition: kdb.c:37
VOID KdbpPrint(IN PCHAR Format, IN ... OPTIONAL)
Prints the given string with printf-like formatting.
Definition: kdb_cli.c:2618
#define KDB_MAXIMUM_HW_BREAKPOINT_COUNT
Definition: kdb.c:22
GLsizei GLenum const GLvoid GLsizei GLenum GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLint GLint GLint GLshort GLshort GLshort GLubyte GLubyte GLubyte GLuint GLuint GLuint GLushort GLushort GLushort GLbyte GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLfloat GLint GLint GLint GLint GLshort GLshort GLshort GLshort GLubyte GLubyte GLubyte GLubyte GLuint GLuint GLuint GLuint GLushort GLushort GLushort GLushort GLboolean const GLdouble const GLfloat const GLint const GLshort const GLbyte const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLdouble const GLfloat const GLfloat const GLint const GLint const GLshort const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort GLenum GLenum GLenum GLfloat GLenum GLint GLenum GLenum GLenum GLfloat GLenum GLenum GLint GLenum GLfloat GLenum GLint GLint GLushort GLenum GLenum GLfloat GLenum GLenum GLint GLfloat const GLubyte GLenum GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLint GLint GLsizei GLsizei GLint GLenum GLenum const GLvoid GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLenum const GLdouble GLenum GLenum const GLfloat GLenum GLenum const GLint GLsizei GLuint GLfloat GLuint GLbitfield GLfloat GLint GLuint GLboolean GLenum GLfloat GLenum GLbitfield GLenum GLfloat GLfloat GLint GLint const GLfloat GLenum GLfloat GLfloat GLint GLint GLfloat GLfloat GLint GLint const GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat const GLdouble const GLfloat const GLdouble const GLfloat GLint i
Definition: glfuncs.h:248
ULONG Dr6
Definition: nt_native.h:1438
static KDB_KTRAP_FRAME KdbTrapFrame
Definition: kdb.c:52
ULONG Dr0
Definition: nt_native.h:1434
unsigned int ULONG
Definition: retypes.h:1
BOOLEAN Enabled
Definition: kdb.h:34
static KDB_BREAKPOINT KdbBreakPoints[KDB_MAXIMUM_BREAKPOINT_COUNT]
Definition: kdb.c:34
static ULONG KdbHwBreakPointCount
Definition: kdb.c:36

Referenced by KdbpCmdEnableDisableClearBreakPoint(), and KdbpInsertBreakPoint().

◆ KdbpGetBreakPointInfo()

BOOLEAN KdbpGetBreakPointInfo ( IN ULONG  BreakPointNr,
OUT ULONG_PTR *Address  OPTIONAL,
OUT KDB_BREAKPOINT_TYPE *Type  OPTIONAL,
OUT UCHAR *Size  OPTIONAL,
OUT KDB_ACCESS_TYPE *AccessType  OPTIONAL,
OUT UCHAR *DebugReg  OPTIONAL,
OUT BOOLEAN *Enabled  OPTIONAL,
OUT BOOLEAN *Global  OPTIONAL,
OUT PEPROCESS *Process  OPTIONAL,
OUT PCHAR *ConditionExpression  OPTIONAL 
)

Returns information of the specified breakpoint.

Parameters
BreakPointNrNumber of the breakpoint to return information of.
AddressReceives the address of the breakpoint.
TypeReceives the type of the breakpoint (hardware or software)
SizeSize - for memory breakpoints.
AccessTypeAccess type - for hardware breakpoints.
DebugRegDebug register - for enabled hardware breakpoints.
EnabledWhether the breakpoint is enabled or not.
ProcessThe owning process of the breakpoint.
ConditionExpressionThe expression which was given as condition for the bp.
Returns
NULL on failure, pointer to a KDB_BREAKPOINT struct on success.

Definition at line 404 of file kdb.c.

415 {
416  PKDB_BREAKPOINT bp;
417 
418  if (BreakPointNr >= RTL_NUMBER_OF(KdbBreakPoints) ||
419  KdbBreakPoints[BreakPointNr].Type == KdbBreakPointNone)
420  {
421  return FALSE;
422  }
423 
424  bp = KdbBreakPoints + BreakPointNr;
425  if (Address)
426  *Address = bp->Address;
427 
428  if (Type)
429  *Type = bp->Type;
430 
431  if (bp->Type == KdbBreakPointHardware)
432  {
433  if (Size)
434  *Size = bp->Data.Hw.Size;
435 
436  if (AccessType)
437  *AccessType = bp->Data.Hw.AccessType;
438 
439  if (DebugReg && bp->Enabled)
440  *DebugReg = bp->Data.Hw.DebugReg;
441  }
442 
443  if (Enabled)
444  *Enabled = bp->Enabled;
445 
446  if (Global)
447  *Global = bp->Global;
448 
449  if (Process)
450  *Process = bp->Process;
451 
452  if (ConditionExpression)
453  *ConditionExpression = bp->ConditionExpression;
454 
455  return TRUE;
456 }
union _KDB_BREAKPOINT::@1799 Data
struct _KDB_BREAKPOINT::@1799::@1800 Hw
BOOLEAN Global
Definition: kdb.h:36
#define TRUE
Definition: types.h:120
PCHAR ConditionExpression
Definition: kdb.h:38
IN PVOID IN PVOID IN USHORT IN USHORT Size
Definition: pci.h:361
UNICODE_STRING Global
Definition: symlink.c:37
#define FALSE
Definition: types.h:117
static WCHAR Address[46]
Definition: ping.c:68
ULONG_PTR Address
Definition: kdb.h:35
Type
Definition: Type.h:6
PEPROCESS Process
Definition: kdb.h:37
#define RTL_NUMBER_OF(x)
Definition: RtlRegistry.c:12
_Must_inspect_result_ _In_ PLARGE_INTEGER _In_ PLARGE_INTEGER _In_ ULONG _In_ PFILE_OBJECT _In_ PVOID Process
Definition: fsrtlfuncs.h:219
BOOLEAN Enabled
Definition: kdb.h:34
static KDB_BREAKPOINT KdbBreakPoints[KDB_MAXIMUM_BREAKPOINT_COUNT]
Definition: kdb.c:34
KDB_BREAKPOINT_TYPE Type
Definition: kdb.h:33

Referenced by KdbpCmdBreakPointList().

◆ KdbpGetCommandLineSettings()

VOID NTAPI KdbpGetCommandLineSettings ( PCHAR  p1)

Definition at line 1649 of file kdb.c.

1651 {
1652 #define CONST_STR_LEN(x) (sizeof(x)/sizeof(x[0]) - 1)
1653 
1654  while (p1 && (p1 = strchr(p1, ' ')))
1655  {
1656  /* Skip other spaces */
1657  while (*p1 == ' ') ++p1;
1658 
1659  if (!_strnicmp(p1, "KDSERIAL", CONST_STR_LEN("KDSERIAL")))
1660  {
1661  p1 += CONST_STR_LEN("KDSERIAL");
1663  KdpDebugMode.Serial = TRUE;
1664  }
1665  else if (!_strnicmp(p1, "KDNOECHO", CONST_STR_LEN("KDNOECHO")))
1666  {
1667  p1 += CONST_STR_LEN("KDNOECHO");
1669  }
1670  else if (!_strnicmp(p1, "FIRSTCHANCE", CONST_STR_LEN("FIRSTCHANCE")))
1671  {
1672  p1 += CONST_STR_LEN("FIRSTCHANCE");
1674  }
1675  }
1676 }
BOOLEAN KdbpSetEnterCondition(IN LONG ExceptionNr, IN BOOLEAN FirstChance, IN KDB_ENTER_CONDITION Condition)
Sets the first or last chance enter-condition for exception nr. ExceptionNr.
Definition: kdb.c:991
ULONG KdbDebugState
Definition: kdb.c:45
#define TRUE
Definition: types.h:120
KDP_DEBUG_MODE KdpDebugMode
Definition: kdio.c:46
#define CONST_STR_LEN(x)
#define _strnicmp(_String1, _String2, _MaxCount)
Definition: compat.h:23
char * strchr(const char *String, int ch)
Definition: utclib.c:501

Referenced by KdDebuggerInitialize0().

◆ KdbpGetEnterCondition()

BOOLEAN KdbpGetEnterCondition ( IN LONG  ExceptionNr,
IN BOOLEAN  FirstChance,
OUT KDB_ENTER_CONDITION Condition 
)

Gets the first or last chance enter-condition for exception nr. ExceptionNr.

Parameters
ExceptionNrNumber of the exception to get condition of.
FirstChanceWhether to get first or last chance condition.
ConditionReceives the condition setting.
Return values
TRUESuccess.
FALSEFailure (invalid exception nr)

Definition at line 969 of file kdb.c.

973 {
974  if (ExceptionNr >= (LONG)RTL_NUMBER_OF(KdbEnterConditions))
975  return FALSE;
976 
977  *Condition = KdbEnterConditions[ExceptionNr][FirstChance ? 0 : 1];
978  return TRUE;
979 }
#define TRUE
Definition: types.h:120
#define FALSE
Definition: types.h:117
static KDB_ENTER_CONDITION KdbEnterConditions[][2]
Definition: kdb.c:58
long LONG
Definition: pedump.c:60
IN ULONG IN UCHAR Condition
#define RTL_NUMBER_OF(x)
Definition: RtlRegistry.c:12

Referenced by KdbpCmdSet().

◆ KdbpGetExceptionNumberFromStatus()

static ULONG KdbpGetExceptionNumberFromStatus ( IN NTSTATUS  ExceptionCode)
static

Definition at line 1192 of file kdb.c.

1194 {
1195  ULONG Ret;
1196 
1197  switch (ExceptionCode)
1198  {
1200  Ret = 0;
1201  break;
1202  case STATUS_SINGLE_STEP:
1203  Ret = 1;
1204  break;
1205  case STATUS_BREAKPOINT:
1206  Ret = 3;
1207  break;
1209  Ret = 4;
1210  break;
1212  Ret = 5;
1213  break;
1215  Ret = 6;
1216  break;
1218  Ret = 7;
1219  break;
1220  case STATUS_STACK_OVERFLOW:
1221  Ret = 12;
1222  break;
1224  Ret = 14;
1225  break;
1227  Ret = 17;
1228  break;
1230  Ret = 18;
1231  break;
1233  Ret = 20;
1234  break;
1235 
1236  default:
1237  Ret = RTL_NUMBER_OF(KdbEnterConditions) - 1;
1238  break;
1239  }
1240 
1241  return Ret;
1242 }
_Inout_ PIRP _In_ NTSTATUS ExceptionCode
Definition: cdprocs.h:1772
#define STATUS_ILLEGAL_INSTRUCTION
Definition: ntstatus.h:266
#define STATUS_SINGLE_STEP
Definition: ntstatus.h:185
#define STATUS_INTEGER_OVERFLOW
Definition: ntstatus.h:385
static KDB_ENTER_CONDITION KdbEnterConditions[][2]
Definition: kdb.c:58
#define STATUS_INTEGER_DIVIDE_BY_ZERO
Definition: ntstatus.h:384
#define STATUS_BREAKPOINT
Definition: ntstatus.h:184
#define STATUS_ASSERTION_FAILURE
Definition: ntstatus.h:960
#define STATUS_FLOAT_MULTIPLE_TRAPS
Definition: ntstatus.h:808
#define STATUS_ACCESS_VIOLATION
Definition: ntstatus.h:242
#define RTL_NUMBER_OF(x)
Definition: RtlRegistry.c:12
#define STATUS_STACK_OVERFLOW
Definition: ntstatus.h:489
#define STATUS_DATATYPE_MISALIGNMENT
Definition: ntstatus.h:183
unsigned int ULONG
Definition: retypes.h:1
#define STATUS_FLOAT_INVALID_OPERATION
Definition: ntstatus.h:380
#define STATUS_ARRAY_BOUNDS_EXCEEDED
Definition: ntstatus.h:376

Referenced by KdbEnterDebuggerException().

◆ KdbpGetNextBreakPointNr()

LONG KdbpGetNextBreakPointNr ( IN ULONG Start  OPTIONAL)

Gets the number of the next breakpoint >= Start.

Parameters
StartBreakpoint number to start searching at. -1 if no more breakpoints are found.
Returns
Breakpoint number (-1 if no more breakpoints are found)

Definition at line 377 of file kdb.c.

379 {
381  {
383  return Start;
384  }
385 
386  return -1;
387 }
Type
Definition: Type.h:6
Definition: partlist.h:33
#define RTL_NUMBER_OF(x)
Definition: RtlRegistry.c:12
static KDB_BREAKPOINT KdbBreakPoints[KDB_MAXIMUM_BREAKPOINT_COUNT]
Definition: kdb.c:34

Referenced by KdbpCmdBreakPointList().

◆ KdbpInsertBreakPoint()

NTSTATUS KdbpInsertBreakPoint ( IN ULONG_PTR  Address,
IN KDB_BREAKPOINT_TYPE  Type,
IN UCHAR Size  OPTIONAL,
IN KDB_ACCESS_TYPE AccessType  OPTIONAL,
IN PCHAR ConditionExpression  OPTIONAL,
IN BOOLEAN  Global,
OUT PLONG BreakPointNr  OPTIONAL 
)

Inserts a breakpoint into the breakpoint array.

The Process of the breakpoint is set to KdbCurrentProcess

Parameters
AddressAddress at which to set the breakpoint.
TypeType of breakpoint (hardware or software)
SizeSize of breakpoint (for hardware/memory breakpoints)
AccessTypeAccess type (for hardware breakpoins)
ConditionExpressionExpression which must evaluate to true for conditional breakpoints.
GlobalWether the breakpoint is global or local to a process.
BreakPointNumberReceives the breakpoint number on success
Returns
NTSTATUS

Definition at line 473 of file kdb.c.

481 {
482  LONG i;
484  PCHAR ConditionExpressionDup;
485  LONG ErrOffset;
486  CHAR ErrMsg[128];
487 
489 
491  {
492  if ((Address % Size) != 0)
493  {
494  KdbpPrint("Address (0x%p) must be aligned to a multiple of the size (%d)\n", Address, Size);
495  return STATUS_UNSUCCESSFUL;
496  }
497 
498  if (AccessType == KdbAccessExec && Size != 1)
499  {
500  KdbpPrint("Size must be 1 for execution breakpoints.\n");
501  return STATUS_UNSUCCESSFUL;
502  }
503  }
504 
506  {
507  return STATUS_UNSUCCESSFUL;
508  }
509 
510  /* Parse conditon expression string and duplicate it */
511  if (ConditionExpression)
512  {
513  Condition = KdbpRpnParseExpression(ConditionExpression, &ErrOffset, ErrMsg);
514  if (!Condition)
515  {
516  if (ErrOffset >= 0)
517  KdbpPrint("Couldn't parse expression: %s at character %d\n", ErrMsg, ErrOffset);
518  else
519  KdbpPrint("Couldn't parse expression: %s", ErrMsg);
520 
521  return STATUS_UNSUCCESSFUL;
522  }
523 
524  i = strlen(ConditionExpression) + 1;
525  ConditionExpressionDup = ExAllocatePoolWithTag(NonPagedPool, i, TAG_KDBG);
526  RtlCopyMemory(ConditionExpressionDup, ConditionExpression, i);
527  }
528  else
529  {
530  Condition = NULL;
531  ConditionExpressionDup = NULL;
532  }
533 
534  /* Find unused breakpoint */
536  {
537  for (i = RTL_NUMBER_OF(KdbBreakPoints) - 1; i >= 0; i--)
538  {
540  break;
541  }
542  }
543  else
544  {
545  for (i = 0; i < (LONG)RTL_NUMBER_OF(KdbBreakPoints); i++)
546  {
548  break;
549  }
550  }
551 
553 
554  /* Set the breakpoint */
561  KdbBreakPoints[i].ConditionExpression = ConditionExpressionDup;
563 
565  {
566  KdbBreakPoints[i].Data.Hw.Size = Size;
567  KdbBreakPoints[i].Data.Hw.AccessType = AccessType;
568  }
569 
571 
573  KdbpPrint("Breakpoint %d inserted.\n", i);
574 
575  /* Try to enable the breakpoint */
577 
578  /* Return the breakpoint number */
579  if (BreakPointNr)
580  *BreakPointNr = i;
581 
582  return STATUS_SUCCESS;
583 }
#define TAG_KDBG
Definition: kdb.h:8
signed char * PCHAR
Definition: retypes.h:7
union _KDB_BREAKPOINT::@1799 Data
PVOID KdbpRpnParseExpression(IN PCHAR Expression, OUT PLONG ErrOffset OPTIONAL, OUT PCHAR ErrMsg OPTIONAL)
Parses the given expression and returns a "handle" to it.
Definition: kdb_expr.c:1127
struct _KDB_BREAKPOINT::@1799::@1800 Hw
BOOLEAN Global
Definition: kdb.h:36
static ULONG KdbBreakPointCount
Definition: kdb.c:33
ACPI_SIZE strlen(const char *String)
Definition: utclib.c:269
#define KDB_MAXIMUM_BREAKPOINT_COUNT
Definition: kdb.c:21
PEPROCESS KdbCurrentProcess
Definition: kdb.c:47
char CHAR
Definition: xmlstorage.h:175
PCHAR ConditionExpression
Definition: kdb.h:38
IN PVOID IN PVOID IN USHORT IN USHORT Size
Definition: pci.h:361
UNICODE_STRING Global
Definition: symlink.c:37
#define FALSE
Definition: types.h:117
long LONG
Definition: pedump.c:60
static WCHAR Address[46]
Definition: ping.c:68
ULONG_PTR Address
Definition: kdb.h:35
PVOID Condition
Definition: kdb.h:39
IN ULONG IN UCHAR Condition
BOOLEAN KdbpEnableBreakPoint(IN LONG BreakPointNr OPTIONAL, IN OUT PKDB_BREAKPOINT BreakPoint OPTIONAL)
Enables a breakpoint.
Definition: kdb.c:697
#define ASSERT(a)
Definition: mode.c:45
VOID KdbpPrint(IN PCHAR Format, IN ... OPTIONAL)
Prints the given string with printf-like formatting.
Definition: kdb_cli.c:2618
Type
Definition: Type.h:6
#define STATUS_UNSUCCESSFUL
Definition: udferr_usr.h:132
#define ExAllocatePoolWithTag(hernya, size, tag)
Definition: env_spec_w32.h:350
PEPROCESS Process
Definition: kdb.h:37
GLsizei GLenum const GLvoid GLsizei GLenum GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLint GLint GLint GLshort GLshort GLshort GLubyte GLubyte GLubyte GLuint GLuint GLuint GLushort GLushort GLushort GLbyte GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLfloat GLint GLint GLint GLint GLshort GLshort GLshort GLshort GLubyte GLubyte GLubyte GLubyte GLuint GLuint GLuint GLuint GLushort GLushort GLushort GLushort GLboolean const GLdouble const GLfloat const GLint const GLshort const GLbyte const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLdouble const GLfloat const GLfloat const GLint const GLint const GLshort const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort GLenum GLenum GLenum GLfloat GLenum GLint GLenum GLenum GLenum GLfloat GLenum GLenum GLint GLenum GLfloat GLenum GLint GLint GLushort GLenum GLenum GLfloat GLenum GLenum GLint GLfloat const GLubyte GLenum GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLint GLint GLsizei GLsizei GLint GLenum GLenum const GLvoid GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLenum const GLdouble GLenum GLenum const GLfloat GLenum GLenum const GLint GLsizei GLuint GLfloat GLuint GLbitfield GLfloat GLint GLuint GLboolean GLenum GLfloat GLenum GLbitfield GLenum GLfloat GLfloat GLint GLint const GLfloat GLenum GLfloat GLfloat GLint GLint GLfloat GLfloat GLint GLint const GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat const GLdouble const GLfloat const GLdouble const GLfloat GLint i
Definition: glfuncs.h:248
#define RTL_NUMBER_OF(x)
Definition: RtlRegistry.c:12
#define NULL
Definition: types.h:112
#define RtlCopyMemory(Destination, Source, Length)
Definition: typedefs.h:263
BOOLEAN Enabled
Definition: kdb.h:34
#define STATUS_SUCCESS
Definition: shellext.h:65
static KDB_BREAKPOINT KdbBreakPoints[KDB_MAXIMUM_BREAKPOINT_COUNT]
Definition: kdb.c:34
KDB_BREAKPOINT_TYPE Type
Definition: kdb.h:33

Referenced by KdbpCmdBreakPoint(), KdbpStepIntoInstruction(), and KdbpStepOverInstruction().

◆ KdbpInternalEnter()

static VOID KdbpInternalEnter ( VOID  )
static

Internal function to enter KDB.

Disables interrupts, releases display ownership, ...

Definition at line 1153 of file kdb.c.

1154 {
1155  PETHREAD Thread;
1156  PVOID SavedInitialStack, SavedStackBase, SavedKernelStack;
1157  ULONG SavedStackLimit;
1158 
1159  KbdDisableMouse();
1160 
1161  /* Take control of the display */
1162  if (KdpDebugMode.Screen)
1163  KdpScreenAcquire();
1164 
1165  /* Call the interface's main loop on a different stack */
1167  SavedInitialStack = Thread->Tcb.InitialStack;
1168  SavedStackBase = Thread->Tcb.StackBase;
1169  SavedStackLimit = Thread->Tcb.StackLimit;
1170  SavedKernelStack = Thread->Tcb.KernelStack;
1174 
1175  // KdbpPrint("Switching to KDB stack 0x%08x-0x%08x (Current Stack is 0x%08x)\n", Thread->Tcb.StackLimit, Thread->Tcb.StackBase, Esp);
1176 
1178 
1179  Thread->Tcb.InitialStack = SavedInitialStack;
1180  Thread->Tcb.StackBase = SavedStackBase;
1181  Thread->Tcb.StackLimit = SavedStackLimit;
1182  Thread->Tcb.KernelStack = SavedKernelStack;
1183 
1184  /* Release the display */
1185  if (KdpDebugMode.Screen)
1186  KdpScreenRelease();
1187 
1188  KbdEnableMouse();
1189 }
#define PsGetCurrentThread()
Definition: env_spec_w32.h:81
KTHREAD Tcb
Definition: pstypes.h:1045
static CHAR KdbStack[KDB_STACK_SIZE]
Definition: kdb.c:31
KDP_DEBUG_MODE KdpDebugMode
Definition: kdio.c:46
VOID NTAPI KdbpStackSwitchAndCall(IN PVOID NewStack, IN VOID(*Function)(VOID))
VOID KdpScreenRelease(VOID)
Definition: kdio.c:369
VOID KbdEnableMouse(VOID)
PVOID KernelStack
Definition: ketypes.h:1607
VOID KdpScreenAcquire(VOID)
Definition: kdio.c:350
#define KDB_STACK_SIZE
Definition: kdb.c:20
volatile VOID * StackLimit
Definition: ketypes.h:1597
VOID KbdDisableMouse(VOID)
static VOID KdbpCallMainLoop(VOID)
Calls the main loop ...
Definition: kdb.c:1143
_In_opt_ PFILE_OBJECT _In_opt_ PETHREAD Thread
Definition: fltkernel.h:2653
PVOID StackBase
Definition: ketypes.h:1598
unsigned int ULONG
Definition: retypes.h:1
#define ULONG_PTR
Definition: config.h:101
PVOID InitialStack
Definition: ketypes.h:1596

Referenced by KdbEnterDebuggerException().

◆ KdbpIsBreakPointOurs()

static LONG KdbpIsBreakPointOurs ( IN NTSTATUS  ExceptionCode,
IN PCONTEXT  Context 
)
static

Checks if the breakpoint was set by the debugger.

Tries to find a breakpoint in the breakpoint array which caused the debug exception to happen.

Parameters
ExpNrException Number (1 or 3)
TrapFrameException trapframe
Returns
Breakpoint number, -1 on error.

Definition at line 644 of file kdb.c.

647 {
648  ULONG i;
650 
651  if (ExceptionCode == STATUS_BREAKPOINT) /* Software interrupt */
652  {
653  ULONG_PTR BpEip = (ULONG_PTR)Context->Eip - 1; /* Get EIP of INT3 instruction */
654  for (i = 0; i < KdbSwBreakPointCount; i++)
655  {
659 
660  if (KdbSwBreakPoints[i]->Address == BpEip)
661  {
663  }
664  }
665  }
666  else if (ExceptionCode == STATUS_SINGLE_STEP) /* Hardware interrupt */
667  {
668  UCHAR DebugReg;
669 
670  for (i = 0; i < KdbHwBreakPointCount; i++)
671  {
674  DebugReg = KdbHwBreakPoints[i]->Data.Hw.DebugReg;
675 
676  if ((Context->Dr6 & (1 << DebugReg)) != 0)
677  {
679  }
680  }
681  }
682 
683  return -1;
684 }
_Inout_ PIRP _In_ NTSTATUS ExceptionCode
Definition: cdprocs.h:1772
union _KDB_BREAKPOINT::@1799 Data
struct _KDB_BREAKPOINT::@1799::@1800 Hw
static ULONG KdbSwBreakPointCount
Definition: kdb.c:35
#define STATUS_SINGLE_STEP
Definition: ntstatus.h:185
uint32_t ULONG_PTR
Definition: typedefs.h:65
static PKDB_BREAKPOINT KdbHwBreakPoints[KDB_MAXIMUM_HW_BREAKPOINT_COUNT]
Definition: kdb.c:38
static WCHAR Address[46]
Definition: ping.c:68
#define STATUS_BREAKPOINT
Definition: ntstatus.h:184
#define ASSERT(a)
Definition: mode.c:45
static PKDB_BREAKPOINT KdbSwBreakPoints[KDB_MAXIMUM_SW_BREAKPOINT_COUNT]
Definition: kdb.c:37
Type
Definition: Type.h:6
#define for
Definition: utility.h:88
unsigned char UCHAR
Definition: xmlstorage.h:181
GLsizei GLenum const GLvoid GLsizei GLenum GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLint GLint GLint GLshort GLshort GLshort GLubyte GLubyte GLubyte GLuint GLuint GLuint GLushort GLushort GLushort GLbyte GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLfloat GLint GLint GLint GLint GLshort GLshort GLshort GLshort GLubyte GLubyte GLubyte GLubyte GLuint GLuint GLuint GLuint GLushort GLushort GLushort GLushort GLboolean const GLdouble const GLfloat const GLint const GLshort const GLbyte const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLdouble const GLfloat const GLfloat const GLint const GLint const GLshort const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort GLenum GLenum GLenum GLfloat GLenum GLint GLenum GLenum GLenum GLfloat GLenum GLenum GLint GLenum GLfloat GLenum GLint GLint GLushort GLenum GLenum GLfloat GLenum GLenum GLint GLfloat const GLubyte GLenum GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLint GLint GLsizei GLsizei GLint GLenum GLenum const GLvoid GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLenum const GLdouble GLenum GLenum const GLfloat GLenum GLenum const GLint GLsizei GLuint GLfloat GLuint GLbitfield GLfloat GLint GLuint GLboolean GLenum GLfloat GLenum GLbitfield GLenum GLfloat GLfloat GLint GLint const GLfloat GLenum GLfloat GLfloat GLint GLint GLfloat GLfloat GLint GLint const GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat const GLdouble const GLfloat const GLdouble const GLfloat GLint i
Definition: glfuncs.h:248
unsigned int ULONG
Definition: retypes.h:1
#define ULONG_PTR
Definition: config.h:101
static KDB_BREAKPOINT KdbBreakPoints[KDB_MAXIMUM_BREAKPOINT_COUNT]
Definition: kdb.c:34
static ULONG KdbHwBreakPointCount
Definition: kdb.c:36

Referenced by KdbEnterDebuggerException().

◆ KdbpKdbTrapFrameFromKernelStack()

static VOID KdbpKdbTrapFrameFromKernelStack ( PVOID  KernelStack,
PKDB_KTRAP_FRAME  KdbTrapFrame 
)
static

Definition at line 114 of file kdb.c.

117 {
118  ULONG_PTR *StackPtr;
119 
121  StackPtr = (ULONG_PTR *) KernelStack;
122 #ifdef _M_IX86
123  KdbTrapFrame->Ebp = StackPtr[3];
124  KdbTrapFrame->Edi = StackPtr[4];
125  KdbTrapFrame->Esi = StackPtr[5];
126  KdbTrapFrame->Ebx = StackPtr[6];
127  KdbTrapFrame->Eip = StackPtr[7];
128  KdbTrapFrame->Esp = (ULONG) (StackPtr + 8);
134 #endif
135 
136  /* FIXME: what about the other registers??? */
137 }
ULONG Esp
Definition: nt_native.h:1479
ULONG Eip
Definition: nt_native.h:1476
#define KGDT_R0_CODE
Definition: ketypes.h:75
ULONG SegGs
Definition: nt_native.h:1453
ULONG SegDs
Definition: nt_native.h:1456
uint32_t ULONG_PTR
Definition: typedefs.h:65
ULONG SegEs
Definition: nt_native.h:1455
ULONG Esi
Definition: nt_native.h:1464
ULONG SegCs
Definition: nt_native.h:1477
ULONG Ebx
Definition: nt_native.h:1465
#define KGDT_R0_DATA
Definition: ketypes.h:76
ULONG SegSs
Definition: nt_native.h:1480
static KDB_KTRAP_FRAME KdbTrapFrame
Definition: kdb.c:52
unsigned int ULONG
Definition: retypes.h:1
#define RtlZeroMemory(Destination, Length)
Definition: typedefs.h:262
ULONG Ebp
Definition: nt_native.h:1475
ULONG Edi
Definition: nt_native.h:1463

Referenced by KdbpAttachToThread().

◆ KdbpOverwriteInstruction()

static NTSTATUS KdbpOverwriteInstruction ( IN PEPROCESS  Process,
IN ULONG_PTR  Address,
IN UCHAR  NewInst,
OUT PUCHAR OldInst  OPTIONAL 
)
static

Overwrites the instruction at Address with NewInst and stores the old instruction in *OldInst.

Parameters
ProcessProcess in which's context to overwrite the instruction.
AddressAddress at which to overwrite the instruction.
NewInstNew instruction (written to Address)
OldInstOld instruction (read from Address)
Returns
NTSTATUS

Definition at line 150 of file kdb.c.

155 {
157  ULONG Protect;
160 
161  /* Get the protection for the address. */
163 
164  /* Return if that page isn't present. */
165  if (Protect & PAGE_NOACCESS)
166  {
168  }
169 
170  /* Attach to the process */
171  if (CurrentProcess != Process)
172  {
174  }
175 
176  /* Make the page writeable if it is read only. */
178  {
181  }
182 
183  /* Copy the old instruction back to the caller. */
184  if (OldInst)
185  {
186  Status = KdbpSafeReadMemory(OldInst, (PUCHAR)Address, 1);
187  if (!NT_SUCCESS(Status))
188  {
190  {
192  }
193 
194  /* Detach from process */
195  if (CurrentProcess != Process)
196  {
197  KeDetachProcess();
198  }
199 
200  return Status;
201  }
202  }
203 
204  /* Copy the new instruction in its place. */
205  Status = KdbpSafeWriteMemory((PUCHAR)Address, &NewInst, 1);
206 
207  /* Restore the page protection. */
209  {
211  }
212 
213  /* Detach from process */
214  if (CurrentProcess != Process)
215  {
217  }
218 
219  return Status;
220 }
KAPC_STATE
Definition: ketypes.h:1280
_In_ HANDLE _Outptr_result_bytebuffer_ ViewSize PVOID _In_ ULONG_PTR _In_ SIZE_T _Inout_opt_ PLARGE_INTEGER _Inout_ PSIZE_T _In_ SECTION_INHERIT _In_ ULONG _In_ ULONG Protect
Definition: zwfuncs.h:214
ULONG NTAPI MmGetPageProtect(struct _EPROCESS *Process, PVOID Address)
unsigned char * PUCHAR
Definition: retypes.h:3
LONG NTSTATUS
Definition: precomp.h:26
#define PAGE_ROUND_DOWN(x)
Definition: mmtypes.h:36
VOID NTAPI KeStackAttachProcess(IN PKPROCESS Process, OUT PRKAPC_STATE ApcState)
Definition: procobj.c:701
#define PsGetCurrentProcess
Definition: psfuncs.h:17
#define PAGE_NOACCESS
Definition: nt_native.h:1302
static WCHAR Address[46]
Definition: ping.c:68
#define PAGE_EXECUTE
Definition: nt_native.h:1306
Status
Definition: gdiplustypes.h:24
ULONG CurrentProcess
Definition: shell.c:125
#define NT_SUCCESS(StatCode)
Definition: apphelp.c:32
NTSTATUS KdbpSafeWriteMemory(OUT PVOID Dest, IN PVOID Src, IN ULONG Bytes)
Definition: kdb.c:1693
VOID NTAPI MmSetPageProtect(struct _EPROCESS *Process, PVOID Address, ULONG flProtect)
VOID NTAPI KeDetachProcess(VOID)
Definition: procobj.c:618
NTSTATUS KdbpSafeReadMemory(OUT PVOID Dest, IN PVOID Src, IN ULONG Bytes)
Definition: kdb.c:1679
#define STATUS_MEMORY_NOT_ALLOCATED
Definition: ntstatus.h:396
VOID NTAPI KeUnstackDetachProcess(IN PRKAPC_STATE ApcState)
Definition: procobj.c:753
_Out_ PKAPC_STATE ApcState
Definition: mm.h:1484
#define PAGE_READONLY
Definition: compat.h:138
_Must_inspect_result_ _In_ PLARGE_INTEGER _In_ PLARGE_INTEGER _In_ ULONG _In_ PFILE_OBJECT _In_ PVOID Process
Definition: fsrtlfuncs.h:219
unsigned int ULONG
Definition: retypes.h:1
#define PAGE_EXECUTE_READ
Definition: nt_native.h:1307
#define PAGE_READWRITE
Definition: nt_native.h:1304

Referenced by KdbEnterDebuggerException(), KdbpDisableBreakPoint(), and KdbpEnableBreakPoint().

◆ KdbpSafeReadMemory()

NTSTATUS KdbpSafeReadMemory ( OUT PVOID  Dest,
IN PVOID  Src,
IN ULONG  Bytes 
)

Definition at line 1679 of file kdb.c.

1683 {
1684  return KdpCopyMemoryChunks((ULONG64)(ULONG_PTR)Src,
1685  Dest,
1686  Bytes,
1687  0,
1689  NULL);
1690 }
NTSTATUS NTAPI KdpCopyMemoryChunks(_In_ ULONG64 Address, _In_ PVOID Buffer, _In_ ULONG TotalSize, _In_ ULONG ChunkSize, _In_ ULONG Flags, _Out_opt_ PULONG ActualSize)
Definition: kdapi.c:50
_In_ UINT Bytes
Definition: mmcopy.h:9
uint32_t ULONG_PTR
Definition: typedefs.h:65
unsigned __int64 ULONG64
Definition: imports.h:198
#define MMDBG_COPY_UNSAFE
Definition: mm.h:55
#define NULL
Definition: types.h:112

Referenced by KdbpCmdBackTrace(), KdbpCmdDisassembleX(), KdbpCmdGdtLdtIdt(), KdbpCmdThread(), KdbpContextFromPrevTss(), KdbpIsNestedTss(), KdbpOverwriteInstruction(), KdbpReadMemory(), KdbpRetrieveTss(), KdbpShouldStepOverInstruction(), KdbpStepIntoInstruction(), and RpnpEvaluateStack().

◆ KdbpSafeWriteMemory()

NTSTATUS KdbpSafeWriteMemory ( OUT PVOID  Dest,
IN PVOID  Src,
IN ULONG  Bytes 
)

Definition at line 1693 of file kdb.c.

1697 {
1698  return KdpCopyMemoryChunks((ULONG64)(ULONG_PTR)Dest,
1699  Src,
1700  Bytes,
1701  0,
1703  NULL);
1704 }
NTSTATUS NTAPI KdpCopyMemoryChunks(_In_ ULONG64 Address, _In_ PVOID Buffer, _In_ ULONG TotalSize, _In_ ULONG ChunkSize, _In_ ULONG Flags, _Out_opt_ PULONG ActualSize)
Definition: kdapi.c:50
_In_ UINT Bytes
Definition: mmcopy.h:9
uint32_t ULONG_PTR
Definition: typedefs.h:65
#define MMDBG_COPY_WRITE
Definition: mm.h:53
unsigned __int64 ULONG64
Definition: imports.h:198
#define MMDBG_COPY_UNSAFE
Definition: mm.h:55
#define NULL
Definition: types.h:112

Referenced by KdbpOverwriteInstruction().

◆ KdbpSetEnterCondition()

BOOLEAN KdbpSetEnterCondition ( IN LONG  ExceptionNr,
IN BOOLEAN  FirstChance,
IN KDB_ENTER_CONDITION  Condition 
)

Sets the first or last chance enter-condition for exception nr. ExceptionNr.

Parameters
ExceptionNrNumber of the exception to set condition of (-1 for all)
FirstChanceWhether to set first or last chance condition.
ConditionThe new condition setting.
Return values
TRUESuccess.
FALSEFailure (invalid exception nr)

Definition at line 991 of file kdb.c.

995 {
996  if (ExceptionNr < 0)
997  {
998  for (ExceptionNr = 0; ExceptionNr < (LONG)RTL_NUMBER_OF(KdbEnterConditions); ExceptionNr++)
999  {
1000  if (ExceptionNr == 1 || ExceptionNr == 8 ||
1001  ExceptionNr == 9 || ExceptionNr == 15) /* Reserved exceptions */
1002  {
1003  continue;
1004  }
1005 
1006  KdbEnterConditions[ExceptionNr][FirstChance ? 0 : 1] = Condition;
1007  }
1008  }
1009  else
1010  {
1011  if (ExceptionNr >= (LONG)RTL_NUMBER_OF(KdbEnterConditions) ||
1012  ExceptionNr == 1 || ExceptionNr == 8 || /* Do not allow changing of the debug */
1013  ExceptionNr == 9 || ExceptionNr == 15) /* trap or reserved exceptions */
1014  {
1015  return FALSE;
1016  }
1017 
1018  KdbEnterConditions[ExceptionNr][FirstChance ? 0 : 1] = Condition;
1019  }
1020 
1021  return TRUE;
1022 }
#define TRUE
Definition: types.h:120
#define FALSE
Definition: types.h:117
static KDB_ENTER_CONDITION KdbEnterConditions[][2]
Definition: kdb.c:58
long LONG
Definition: pedump.c:60
IN ULONG IN UCHAR Condition
#define RTL_NUMBER_OF(x)
Definition: RtlRegistry.c:12

Referenced by KdbpCmdSet(), and KdbpGetCommandLineSettings().

◆ KdbpShouldStepOverInstruction()

BOOLEAN KdbpShouldStepOverInstruction ( ULONG_PTR  Eip)

Checks whether the given instruction can be single stepped or has to be stepped over using a temporary breakpoint.

Return values
TRUEInstruction is a call.
FALSEInstruction is not a call.

Definition at line 229 of file kdb.c.

231 {
232  UCHAR Mem[3];
233  ULONG i = 0;
234 
235  if (!NT_SUCCESS(KdbpSafeReadMemory(Mem, (PVOID)Eip, sizeof (Mem))))
236  {
237  KdbpPrint("Couldn't access memory at 0x%p\n", Eip);
238  return FALSE;
239  }
240 
241  /* Check if the current instruction is a call. */
242  while ((i < sizeof (Mem)) && (Mem[i] == 0x66 || Mem[i] == 0x67))
243  i++;
244 
245  if (i == sizeof (Mem))
246  return FALSE;
247 
248  if (Mem[i] == 0xE8 || Mem[i] == 0x9A || Mem[i] == 0xF2 || Mem[i] == 0xF3 ||
249  (((i + 1) < sizeof (Mem)) && Mem[i] == 0xFF && (Mem[i+1] & 0x38) == 0x10))
250  {
251  return TRUE;
252  }
253 
254  return FALSE;
255 }
#define TRUE
Definition: types.h:120
#define FALSE
Definition: types.h:117
#define NT_SUCCESS(StatCode)
Definition: apphelp.c:32
VOID KdbpPrint(IN PCHAR Format, IN ... OPTIONAL)
Prints the given string with printf-like formatting.
Definition: kdb_cli.c:2618
unsigned char UCHAR
Definition: xmlstorage.h:181
NTSTATUS KdbpSafeReadMemory(OUT PVOID Dest, IN PVOID Src, IN ULONG Bytes)
Definition: kdb.c:1679
GLsizei GLenum const GLvoid GLsizei GLenum GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLint GLint GLint GLshort GLshort GLshort GLubyte GLubyte GLubyte GLuint GLuint GLuint GLushort GLushort GLushort GLbyte GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLfloat GLint GLint GLint GLint GLshort GLshort GLshort GLshort GLubyte GLubyte GLubyte GLubyte GLuint GLuint GLuint GLuint GLushort GLushort GLushort GLushort GLboolean const GLdouble const GLfloat const GLint const GLshort const GLbyte const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLdouble const GLfloat const GLfloat const GLint const GLint const GLshort const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort GLenum GLenum GLenum GLfloat GLenum GLint GLenum GLenum GLenum GLfloat GLenum GLenum GLint GLenum GLfloat GLenum GLint GLint GLushort GLenum GLenum GLfloat GLenum GLenum GLint GLfloat const GLubyte GLenum GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLint GLint GLsizei GLsizei GLint GLenum GLenum const GLvoid GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLenum const GLdouble GLenum GLenum const GLfloat GLenum GLenum const GLint GLsizei GLuint GLfloat GLuint GLbitfield GLfloat GLint GLuint GLboolean GLenum GLfloat GLenum GLbitfield GLenum GLfloat GLfloat GLint GLint const GLfloat GLenum GLfloat GLfloat GLint GLint GLfloat GLfloat GLint GLint const GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat const GLdouble const GLfloat const GLdouble const GLfloat GLint i
Definition: glfuncs.h:248
unsigned int ULONG
Definition: retypes.h:1

Referenced by KdbpStepOverInstruction().

◆ KdbpStepIntoInstruction()

BOOLEAN KdbpStepIntoInstruction ( ULONG_PTR  Eip)

Steps into an instruction (interrupts)

If the given instruction should be stepped into, this function inserts a temporary breakpoint at the target instruction and returns TRUE, otherwise it returns FALSE.

Return values
TRUETemporary breakpoint set at target instruction.
FALSENo breakpoint was set.

Definition at line 295 of file kdb.c.

297 {
298  KDESCRIPTOR Idtr = {0};
299  UCHAR Mem[2];
300  INT IntVect;
301  ULONG IntDesc[2];
302  ULONG_PTR TargetEip;
303 
304  /* Read memory */
305  if (!NT_SUCCESS(KdbpSafeReadMemory(Mem, (PVOID)Eip, sizeof (Mem))))
306  {
307  /*KdbpPrint("Couldn't access memory at 0x%p\n", Eip);*/
308  return FALSE;
309  }
310 
311  /* Check for INT instruction */
312  /* FIXME: Check for iret */
313  if (Mem[0] == 0xcc)
314  IntVect = 3;
315  else if (Mem[0] == 0xcd)
316  IntVect = Mem[1];
317  else if (Mem[0] == 0xce && KdbCurrentTrapFrame->EFlags & (1<<11)) /* 1 << 11 is the overflow flag */
318  IntVect = 4;
319  else
320  return FALSE;
321 
322  if (IntVect < 32) /* We should be informed about interrupts < 32 by the kernel, no need to breakpoint them */
323  {
324  return FALSE;
325  }
326 
327  /* Read the interrupt descriptor table register */
328  __sidt(&Idtr.Limit);
329  if (IntVect >= (Idtr.Limit + 1) / 8)
330  {
331  /*KdbpPrint("IDT does not contain interrupt vector %d.\n", IntVect);*/
332  return TRUE;
333  }
334 
335  /* Get the interrupt descriptor */
336  if (!NT_SUCCESS(KdbpSafeReadMemory(IntDesc, (PVOID)(ULONG_PTR)(Idtr.Base + (IntVect * 8)), sizeof (IntDesc))))
337  {
338  /*KdbpPrint("Couldn't access memory at 0x%p\n", (ULONG_PTR)Idtr.Base + (IntVect * 8));*/
339  return FALSE;
340  }
341 
342  /* Check descriptor and get target eip (16 bit interrupt/trap gates not supported) */
343  if ((IntDesc[1] & (1 << 15)) == 0) /* not present */
344  {
345  return FALSE;
346  }
347  if ((IntDesc[1] & 0x1f00) == 0x0500) /* Task gate */
348  {
349  /* FIXME: Task gates not supported */
350  return FALSE;
351  }
352  else if (((IntDesc[1] & 0x1fe0) == 0x0e00) || /* 32 bit Interrupt gate */
353  ((IntDesc[1] & 0x1fe0) == 0x0f00)) /* 32 bit Trap gate */
354  {
355  /* FIXME: Should the segment selector of the interrupt gate be checked? */
356  TargetEip = (IntDesc[1] & 0xffff0000) | (IntDesc[0] & 0x0000ffff);
357  }
358  else
359  {
360  return FALSE;
361  }
362 
363  /* Insert breakpoint */
365  return FALSE;
366 
367  return TRUE;
368 }
ActualNumberDriverObjects * sizeof(PDRIVER_OBJECT)) PDRIVER_OBJECT *DriverObjectList
#define TRUE
Definition: types.h:120
NTSTATUS KdbpInsertBreakPoint(IN ULONG_PTR Address, IN KDB_BREAKPOINT_TYPE Type, IN UCHAR Size OPTIONAL, IN KDB_ACCESS_TYPE AccessType OPTIONAL, IN PCHAR ConditionExpression OPTIONAL, IN BOOLEAN Global, OUT PLONG BreakPointNr OPTIONAL)
Inserts a breakpoint into the breakpoint array.
Definition: kdb.c:473
int32_t INT
Definition: typedefs.h:58
PVOID Base
Definition: ketypes.h:486
USHORT Limit
Definition: ketypes.h:485
uint32_t ULONG_PTR
Definition: typedefs.h:65
#define FALSE
Definition: types.h:117
__INTRIN_INLINE void __sidt(void *Destination)
Definition: intrin_x86.h:1952
ULONG EFlags
Definition: nt_native.h:1478
PKDB_KTRAP_FRAME KdbCurrentTrapFrame
Definition: kdb.c:51
#define NT_SUCCESS(StatCode)
Definition: apphelp.c:32
unsigned char UCHAR
Definition: xmlstorage.h:181
NTSTATUS KdbpSafeReadMemory(OUT PVOID Dest, IN PVOID Src, IN ULONG Bytes)
Definition: kdb.c:1679
#define NULL
Definition: types.h:112
unsigned int ULONG
Definition: retypes.h:1

Referenced by KdbEnterDebuggerException().

◆ KdbpStepOverInstruction()

BOOLEAN KdbpStepOverInstruction ( ULONG_PTR  Eip)

Steps over an instruction.

If the given instruction should be stepped over, this function inserts a temporary breakpoint after the instruction and returns TRUE, otherwise it returns FALSE.

Return values
TRUETemporary breakpoint set after instruction.
FALSENo breakpoint was set.

Definition at line 267 of file kdb.c.

269 {
270  LONG InstLen;
271 
273  return FALSE;
274 
275  InstLen = KdbpGetInstLength(Eip);
276  if (InstLen < 1)
277  return FALSE;
278 
279  if (!NT_SUCCESS(KdbpInsertBreakPoint(Eip + InstLen, KdbBreakPointTemporary, 0, 0, NULL, FALSE, NULL)))
280  return FALSE;
281 
282  return TRUE;
283 }
#define TRUE
Definition: types.h:120
NTSTATUS KdbpInsertBreakPoint(IN ULONG_PTR Address, IN KDB_BREAKPOINT_TYPE Type, IN UCHAR Size OPTIONAL, IN KDB_ACCESS_TYPE AccessType OPTIONAL, IN PCHAR ConditionExpression OPTIONAL, IN BOOLEAN Global, OUT PLONG BreakPointNr OPTIONAL)
Inserts a breakpoint into the breakpoint array.
Definition: kdb.c:473
#define FALSE
Definition: types.h:117
long LONG
Definition: pedump.c:60
#define NT_SUCCESS(StatCode)
Definition: apphelp.c:32
LONG KdbpGetInstLength(IN ULONG Address)
Definition: i386-dis.c:95
#define NULL
Definition: types.h:112
BOOLEAN KdbpShouldStepOverInstruction(ULONG_PTR Eip)
Checks whether the given instruction can be single stepped or has to be stepped over using a temporar...
Definition: kdb.c:229

Referenced by KdbEnterDebuggerException().

Variable Documentation

◆ ExceptionNrToString

const CHAR* ExceptionNrToString[]
static
Initial value:
=
{
"Divide Error",
"Debug Trap",
"NMI",
"Breakpoint",
"Overflow",
"BOUND range exceeded",
"Invalid Opcode",
"No Math Coprocessor",
"Double Fault",
"Unknown(9)",
"Invalid TSS",
"Segment Not Present",
"Stack Segment Fault",
"General Protection",
"Page Fault",
"Reserved(15)",
"Math Fault",
"Alignment Check",
"Machine Check",
"SIMD Fault",
"Assertion Failure"
}

Definition at line 86 of file kdb.c.

Referenced by KdbEnterDebuggerException().

◆ KdbApcState

KAPC_STATE KdbApcState
static

Definition at line 54 of file kdb.c.

Referenced by KdbEnterDebuggerException(), and KdbpAttachToThread().

◆ KdbBreakPointCount

ULONG KdbBreakPointCount = 0
static

Definition at line 33 of file kdb.c.

Referenced by KdbpDeleteBreakPoint(), and KdbpInsertBreakPoint().

◆ KdbBreakPoints

◆ KdbBreakPointToReenable

PKDB_BREAKPOINT KdbBreakPointToReenable = NULL
static

Definition at line 39 of file kdb.c.

Referenced by KdbEnterDebuggerException().

◆ KdbCurrentProcess

◆ KdbCurrentThread

PETHREAD KdbCurrentThread = NULL

Definition at line 49 of file kdb.c.

Referenced by KdbEnterDebuggerException(), KdbpAttachToThread(), KdbpCmdProc(), and KdbpCmdThread().

◆ KdbCurrentTrapFrame

◆ KdbDebugState

ULONG KdbDebugState = 0

◆ KdbEnterConditions

◆ KdbEnteredOnSingleStep

BOOLEAN KdbEnteredOnSingleStep = FALSE
static

Definition at line 46 of file kdb.c.

Referenced by KdbEnterDebuggerException(), and KdbpCallMainLoop().

◆ KdbEntryCount

LONG KdbEntryCount = 0
static

Definition at line 30 of file kdb.c.

Referenced by KdbEnterDebuggerException().

◆ KdbHwBreakPointCount

ULONG KdbHwBreakPointCount = 0
static

Definition at line 36 of file kdb.c.

Referenced by KdbpDisableBreakPoint(), KdbpEnableBreakPoint(), and KdbpIsBreakPointOurs().

◆ KdbHwBreakPoints

Definition at line 38 of file kdb.c.

Referenced by KdbpDisableBreakPoint(), KdbpEnableBreakPoint(), and KdbpIsBreakPointOurs().

◆ KdbLastBreakPointNr

LONG KdbLastBreakPointNr = -1

Definition at line 42 of file kdb.c.

Referenced by KdbEnterDebuggerException(), and KdbpCmdBreakPointList().

◆ KdbNumSingleSteps

ULONG KdbNumSingleSteps = 0

Definition at line 43 of file kdb.c.

Referenced by KdbEnterDebuggerException(), and KdbpCmdStep().

◆ KdbOriginalProcess

PEPROCESS KdbOriginalProcess = NULL

Definition at line 48 of file kdb.c.

Referenced by KdbEnterDebuggerException(), and KdbpAttachToThread().

◆ KdbOriginalThread

PETHREAD KdbOriginalThread = NULL

Definition at line 50 of file kdb.c.

Referenced by KdbEnterDebuggerException(), and KdbpAttachToThread().

◆ KdbpBugCheckRequested

BOOLEAN KdbpBugCheckRequested

Definition at line 132 of file kdb_cli.c.

Referenced by KdbEnterDebuggerException(), and KdbpCmdBugCheck().

◆ KdbpEvenThoughWeHaveABreakPointToReenableWeAlsoHaveARealSingleStep

BOOLEAN KdbpEvenThoughWeHaveABreakPointToReenableWeAlsoHaveARealSingleStep
static

Definition at line 41 of file kdb.c.

Referenced by KdbEnterDebuggerException().

◆ KdbSingleStepOver

BOOLEAN KdbSingleStepOver = FALSE

Definition at line 44 of file kdb.c.

Referenced by KdbEnterDebuggerException(), and KdbpCmdStep().

◆ KdbStack

CHAR KdbStack[KDB_STACK_SIZE]
static

Definition at line 31 of file kdb.c.

Referenced by KdbpInternalEnter().

◆ KdbSwBreakPointCount

ULONG KdbSwBreakPointCount = 0
static

Definition at line 35 of file kdb.c.

Referenced by KdbpDisableBreakPoint(), KdbpEnableBreakPoint(), and KdbpIsBreakPointOurs().

◆ KdbSwBreakPoints

Definition at line 37 of file kdb.c.

Referenced by KdbpDisableBreakPoint(), KdbpEnableBreakPoint(), and KdbpIsBreakPointOurs().

◆ KdbThreadTrapFrame

KDB_KTRAP_FRAME KdbThreadTrapFrame = { 0 }
static

Definition at line 53 of file kdb.c.

Referenced by KdbpAttachToThread().

◆ KdbTrapFrame