Author: sginsberg
Date: Mon Sep 28 14:08:54 2015
New Revision: 69400
URL:
http://svn.reactos.org/svn/reactos?rev=69400&view=rev
Log:
[NTOS] Implement the KD Get/SetContextEx functionality (copying part of a CONTEXT via
Offset + Byte Count instead of copying a whole context), and stub out
KdpWriteCustomBreakpoint. Newer WinDbg uses the GetContextEx functionality regardless of
whether we report it as supported or not, and didn't seem to fall back on the regular
GetContext functionality when it was missing, so whatever it was using it for should work
awesome now. This had no impact on the broken Registers window though. Also small fix to
use the _M_XXX checks consistently.
Modified:
trunk/reactos/include/reactos/windbgkd.h
trunk/reactos/ntoskrnl/kd64/kdapi.c
trunk/reactos/ntoskrnl/kd64/kddata.c
Modified: trunk/reactos/include/reactos/windbgkd.h
URL:
http://svn.reactos.org/svn/reactos/trunk/reactos/include/reactos/windbgkd.h…
==============================================================================
--- trunk/reactos/include/reactos/windbgkd.h [iso-8859-1] (original)
+++ trunk/reactos/include/reactos/windbgkd.h [iso-8859-1] Mon Sep 28 14:08:54 2015
@@ -111,16 +111,10 @@
#define DbgKdFillMemoryApi 0x0000315B
#define DbgKdQueryMemoryApi 0x0000315C
#define DbgKdSwitchPartition 0x0000315D
-#define DbgKdMaximumManipulate 0x0000315E
-
-/*
- * Three possible new API messages as well as the new Max
- * if these were to be added. Be careful about implementing these.
- */
-//#define DbgKdWriteCustomBreakpointApi 0x0000315E
-//#define DbgKdGetContextExApi 0x0000315F
-//#define DbgKdSetContextExApi 0x00003160
-//#define DbgKdMaximumManipulate 0x00003161
+#define DbgKdWriteCustomBreakpointApi 0x0000315E
+#define DbgKdGetContextExApi 0x0000315F
+#define DbgKdSetContextExApi 0x00003160
+#define DbgKdMaximumManipulate 0x00003161
//
// Debug I/O Types
@@ -713,6 +707,22 @@
{
ULONG Partition;
} DBGKD_SWITCH_PARTITION;
+
+typedef struct _DBGKD_CONTEXT_EX
+{
+ ULONG Offset;
+ ULONG ByteCount;
+ ULONG BytesCopied;
+} DBGKD_CONTEXT_EX, *PDBGKD_CONTEXT_EX;
+
+typedef struct _DBGKD_WRITE_CUSTOM_BREAKPOINT
+{
+ ULONG64 BreakPointAddress;
+ ULONG64 BreakPointInstruction;
+ ULONG BreakPointHandle;
+ UCHAR BreakPointInstructionSize;
+ UCHAR BreakPointInstructionAlignment;
+} DBGKD_WRITE_CUSTOM_BREAKPOINT, *PDBGKD_WRITE_CUSTOM_BREAKPOINT;
//
// DBGKD Structure for Manipulate
@@ -782,6 +792,8 @@
DBGKD_FILL_MEMORY FillMemory;
DBGKD_QUERY_MEMORY QueryMemory;
DBGKD_SWITCH_PARTITION SwitchPartition;
+ DBGKD_WRITE_CUSTOM_BREAKPOINT WriteCustomBreakpoint;
+ DBGKD_CONTEXT_EX ContextEx;
} u;
} DBGKD_MANIPULATE_STATE64, *PDBGKD_MANIPULATE_STATE64;
@@ -878,22 +890,6 @@
} u;
} DBGKD_TRACE_IO, *PDBGKD_TRACE_IO;
-typedef struct _DBGKD_WRITE_CUSTOM_BREAKPOINT
-{
- ULONG64 BreakPointAddress;
- ULONG64 BreakPointInstruction;
- ULONG BreakPointHandle;
- UCHAR BreakPointInstructionSize;
- UCHAR BreakPointInstructionAlignment;
-} DBGKD_WRITE_CUSTOM_BREAKPOINT, *PDBGKD_WRITE_CUSTOM_BREAKPOINT;
-
-typedef struct _DBGKD_CONTEXT_EX
-{
- ULONG Offset;
- ULONG ByteCount;
- ULONG BytesCopied;
-} DBGKD_CONTEXT_EX, *PDBGKD_CONTEXT_EX;
-
static
__inline
VOID
Modified: trunk/reactos/ntoskrnl/kd64/kdapi.c
URL:
http://svn.reactos.org/svn/reactos/trunk/reactos/ntoskrnl/kd64/kdapi.c?rev=…
==============================================================================
--- trunk/reactos/ntoskrnl/kd64/kdapi.c [iso-8859-1] (original)
+++ trunk/reactos/ntoskrnl/kd64/kdapi.c [iso-8859-1] Mon Sep 28 14:08:54 2015
@@ -315,6 +315,28 @@
VOID
NTAPI
+KdpWriteCustomBreakpoint(IN PDBGKD_MANIPULATE_STATE64 State,
+ IN PSTRING Data,
+ IN PCONTEXT Context)
+{
+ //PDBGKD_WRITE_CUSTOM_BREAKPOINT = &State->u.WriteCustomBreakpoint;
+ STRING Header;
+
+ /* Not supported */
+ KdpDprintf("Custom Breakpoint Write is unimplemented\n");
+
+ /* Send a failure packet */
+ State->ReturnStatus = STATUS_UNSUCCESSFUL;
+ Header.Length = sizeof(DBGKD_MANIPULATE_STATE64);
+ Header.Buffer = (PCHAR)State;
+ KdSendPacket(PACKET_TYPE_KD_STATE_MANIPULATE,
+ &Header,
+ NULL,
+ &KdpContext);
+}
+
+VOID
+NTAPI
DumpTraceData(IN PSTRING TraceData)
{
/* Update the buffer */
@@ -726,7 +748,8 @@
ASSERT(Data->Length == sizeof(CONTEXT));
/* Make sure that this is a valid request */
- if ((State->Processor < KeNumberProcessors) && (KdpContextSent !=
FALSE))
+ if ((State->Processor < KeNumberProcessors) &&
+ (KdpContextSent))
{
/* Check if the request is for this CPU */
if (State->Processor == KeGetCurrentPrcb()->Number)
@@ -750,6 +773,130 @@
else
{
/* Invalid request */
+ State->ReturnStatus = STATUS_UNSUCCESSFUL;
+ }
+
+ /* Send the reply */
+ KdSendPacket(PACKET_TYPE_KD_STATE_MANIPULATE,
+ &Header,
+ NULL,
+ &KdpContext);
+}
+
+VOID
+NTAPI
+KdpGetContextEx(IN PDBGKD_MANIPULATE_STATE64 State,
+ IN PSTRING Data,
+ IN PCONTEXT Context)
+{
+ STRING Header;
+ PDBGKD_CONTEXT_EX ContextEx;
+ PCONTEXT TargetContext;
+ ASSERT(Data->Length == 0);
+
+ /* Get our struct */
+ ContextEx = &State->u.ContextEx;
+
+ /* Set up the header */
+ Header.Length = sizeof(DBGKD_MANIPULATE_STATE64);
+ Header.Buffer = (PCHAR)State;
+
+ /* Make sure that this is a valid request */
+ if ((State->Processor < KeNumberProcessors) &&
+ (ContextEx->Offset + ContextEx->ByteCount) <= sizeof(CONTEXT))
+ {
+ /* Check if the request is for this CPU */
+ if (State->Processor == KeGetCurrentPrcb()->Number)
+ {
+ /* We're just copying our own context */
+ TargetContext = Context;
+ }
+ else
+ {
+ /* Get the context from the PRCB array */
+ TargetContext = &KiProcessorBlock[State->Processor]->
+ ProcessorState.ContextFrame;
+ }
+
+ /* Copy what is requested */
+ RtlCopyMemory(Data->Buffer,
+ (PVOID)((ULONG_PTR)TargetContext + ContextEx->Offset),
+ ContextEx->ByteCount);
+
+ /* KD copies all */
+ Data->Length = ContextEx->BytesCopied = ContextEx->ByteCount;
+
+ /* Let the debugger set the context now */
+ KdpContextSent = TRUE;
+
+ /* Finish up */
+ State->ReturnStatus = STATUS_SUCCESS;
+ }
+ else
+ {
+ /* Invalid request */
+ ContextEx->BytesCopied = 0;
+ State->ReturnStatus = STATUS_UNSUCCESSFUL;
+ }
+
+ /* Send the reply */
+ KdSendPacket(PACKET_TYPE_KD_STATE_MANIPULATE,
+ &Header,
+ Data,
+ &KdpContext);
+}
+
+VOID
+NTAPI
+KdpSetContextEx(IN PDBGKD_MANIPULATE_STATE64 State,
+ IN PSTRING Data,
+ IN PCONTEXT Context)
+{
+ STRING Header;
+ PDBGKD_CONTEXT_EX ContextEx;
+ PCONTEXT TargetContext;
+
+ /* Get our struct */
+ ContextEx = &State->u.ContextEx;
+ ASSERT(Data->Length == ContextEx->ByteCount);
+
+ /* Set up the header */
+ Header.Length = sizeof(DBGKD_MANIPULATE_STATE64);
+ Header.Buffer = (PCHAR)State;
+
+ /* Make sure that this is a valid request */
+ if ((State->Processor < KeNumberProcessors) &&
+ ((ContextEx->Offset + ContextEx->ByteCount) <= sizeof(CONTEXT))
&&
+ (KdpContextSent))
+ {
+ /* Check if the request is for this CPU */
+ if (State->Processor == KeGetCurrentPrcb()->Number)
+ {
+ /* We're just copying our own context */
+ TargetContext = Context;
+ }
+ else
+ {
+ /* Get the context from the PRCB array */
+ TargetContext = &KiProcessorBlock[State->Processor]->
+ ProcessorState.ContextFrame;
+ }
+
+ /* Copy what is requested */
+ RtlCopyMemory((PVOID)((ULONG_PTR)TargetContext + ContextEx->Offset),
+ Data->Buffer,
+ ContextEx->ByteCount);
+
+ /* KD copies all */
+ ContextEx->BytesCopied = ContextEx->ByteCount;
+
+ /* Finish up */
+ State->ReturnStatus = STATUS_SUCCESS;
+ }
+ else
+ {
+ /* Invalid request */
+ ContextEx->BytesCopied = 0;
State->ReturnStatus = STATUS_UNSUCCESSFUL;
}
@@ -1359,27 +1506,29 @@
KdpNotSupported(&ManipulateState);
break;
+ case DbgKdWriteCustomBreakpointApi:
+
+ /* Write the customized breakpoint */
+ KdpWriteCustomBreakpoint(&ManipulateState, &Data, Context);
+ break;
+
+ case DbgKdGetContextExApi:
+
+ /* Extended Context Get */
+ KdpGetContextEx(&ManipulateState, &Data, Context);
+ break;
+
+ case DbgKdSetContextExApi:
+
+ /* Extended Context Set */
+ KdpSetContextEx(&ManipulateState, &Data, Context);
+ break;
+
/* Unsupported Messages */
default:
/* Send warning */
- KdpDprintf("Received Unhandled API %lx\n",
ManipulateState.ApiNumber);
-
- /*
- * These 3 messages are unimplemented by us, but one (DbgKdGetContextExApi)
- * is sent by WinDbg as of late during kernel debugging for some reason even
though
- * our MaxManipulate in the version block does not report it as being
available.
- *
- * Any of these being sent to begin with is most likely a bug in WinDbg, so
these
- * are ignored and do not print a warning message to not spam the debug
output.
- * So far, WinDbg seems perfectly fine with this.
- *
- * DbgKdSetContextExApi complements the Get and
DbgKdWriteCustomBreakpointApi
- * fills the gap after DbgKdSwitchPartition (0x315D).
- */
- case 0x315E: // DbgKdWriteCustomBreakpointApi
- case 0x315F: // DbgKdGetContextExApi
- case 0x3160: // DbgKdSetContextExApi
+ KdpDprintf("Received Unrecognized API 0x%lx\n",
ManipulateState.ApiNumber);
/* Setup an empty message, with failure */
Data.Length = 0;
Modified: trunk/reactos/ntoskrnl/kd64/kddata.c
URL:
http://svn.reactos.org/svn/reactos/trunk/reactos/ntoskrnl/kd64/kddata.c?rev…
==============================================================================
--- trunk/reactos/ntoskrnl/kd64/kddata.c [iso-8859-1] (original)
+++ trunk/reactos/ntoskrnl/kd64/kddata.c [iso-8859-1] Mon Sep 28 14:08:54 2015
@@ -19,11 +19,11 @@
//
// Apply the KIPCR WDK workaround for x86 and AMD64
//
-#if defined(_X86_) || defined(_AMD64_)
+#if defined(_M_IX86) || defined(_M_AMD64)
#define KPCR KIPCR
#endif
-#if defined(_X86_)
+#if defined(_M_IX86)
#define KPCR_SELF_PCR_OFFSET FIELD_OFFSET(KPCR, Self)
#define KPCR_CURRENT_PRCB_OFFSET FIELD_OFFSET(KPCR, Prcb)
@@ -33,7 +33,7 @@
#define KPRCB_PCR_PAGE_OFFSET 0
#define CBSTACK_FRAME_POINTER Ebp
-#elif defined(_AMD64_)
+#elif defined(_M_AMD64)
#define KPCR_SELF_PCR_OFFSET FIELD_OFFSET(KPCR, Self)
#define KPCR_CURRENT_PRCB_OFFSET FIELD_OFFSET(KPCR, CurrentPrcb)
@@ -43,7 +43,7 @@
#define KPRCB_PCR_PAGE_OFFSET 0
#define CBSTACK_FRAME_POINTER Rbp
-#elif defined(_ARM_)
+#elif defined(_M_ARM)
#define KPCR_SELF_PCR_OFFSET 0
#define KPCR_CURRENT_PRCB_OFFSET FIELD_OFFSET(KIPCR, Prcb)
@@ -374,7 +374,7 @@
0,
DBGKD_64BIT_PROTOCOL_VERSION2,
CURRENT_KD_SECONDARY_VERSION,
-#if defined(_WIN64)
+#if defined(_M_AMD64) || defined(_M_ARM64)
DBGKD_VERS_FLAG_DATA | DBGKD_VERS_FLAG_PTR64,
#else
DBGKD_VERS_FLAG_DATA,
@@ -521,7 +521,7 @@
KPRCB_PCR_PAGE_OFFSET,
#endif
FIELD_OFFSET(KPRCB, ProcessorState.SpecialRegisters),
-#if defined(_X86_)
+#if defined(_M_IX86)
//
// x86 GDT/LDT/TSS constants
//
@@ -535,7 +535,7 @@
KGDT_TSS,
0,
0,
-#elif defined(_AMD64_)
+#elif defined(_M_AMD64)
//
// AMD64 GDT/LDT/TSS constants
//