Author: dgorbachev
Date: Mon Jun 22 15:32:25 2009
New Revision: 41533
URL:
http://svn.reactos.org/svn/reactos?rev=41533&view=rev
Log:
Change GDB stub.
Modified:
trunk/reactos/ntoskrnl/kd/wrappers/gdbstub.c
Modified: trunk/reactos/ntoskrnl/kd/wrappers/gdbstub.c
URL:
http://svn.reactos.org/svn/reactos/trunk/reactos/ntoskrnl/kd/wrappers/gdbst…
==============================================================================
--- trunk/reactos/ntoskrnl/kd/wrappers/gdbstub.c [iso-8859-1] (original)
+++ trunk/reactos/ntoskrnl/kd/wrappers/gdbstub.c [iso-8859-1] Mon Jun 22 15:32:25 2009
@@ -11,76 +11,17 @@
OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
****************************************************************************/
-
/****************************************************************************
- * Header: remcom.c,v 1.34 91/03/09 12:29:49 glenne Exp $
- *
- * Module name: remcom.c $
- * Revision: 1.34 $
- * Date: 91/03/09 12:29:49 $
* Contributor: Lake Stevens Instrument Division$
*
* Description: low level support for gdb debugger. $
*
- * Considerations: only works on target hardware $
- *
* Written by: Glenn Engel $
* ModuleState: Experimental $
- *
- * NOTES: See Below $
*
* Modified for 386 by Jim Kingdon, Cygnus Support.
* Modified for ReactOS by Casper S. Hornstrup <chorns(a)users.sourceforge.net>
*
- * To enable debugger support, two things need to happen. One, setting
- * up a routine so that it is in the exception path, is necessary in order
- * to allow any breakpoints or error conditions to be properly intercepted
- * and reported to gdb.
- * Two, a breakpoint needs to be generated to begin communication.
- *
- * Because gdb will sometimes write to the stack area to execute function
- * calls, this program cannot rely on using the supervisor stack so it
- * uses it's own stack area.
- *
- *************
- *
- * The following gdb commands are supported:
- *
- * command function Return value
- *
- * g return the value of the CPU Registers hex data or ENN
- * G set the value of the CPU Registers OK or ENN
- *
- * mAA..AA,LLLL Read LLLL bytes at address AA..AA hex data or ENN
- * MAA..AA,LLLL: Write LLLL bytes at address AA.AA OK or ENN
- *
- * c Resume at current address SNN ( signal NN)
- * cAA..AA Continue at address AA..AA SNN
- *
- * s Step one instruction SNN
- * sAA..AA Step one instruction from AA..AA SNN
- *
- * k kill
- *
- * ? What was the last sigval ? SNN (signal NN)
- *
- * All commands and responses are sent with a packet which includes a
- * Checksum. A packet consists of
- *
- * $<packet info>#<Checksum>.
- *
- * where
- * <packet info> :: <characters representing the command or response>
- * <Checksum> :: < two hex digits computed as modulo 256 sum of
<packetinfo>>
- *
- * When a packet is received, it is first acknowledged with either '+' or
'-'.
- * '+' indicates a successful transfer. '-' indicates a failed
transfer.
- *
- * Example:
- *
- * Host: Reply:
- * $m0,10#2a +$00010203040506070809101112131415#42
- *
****************************************************************************/
#include <ntoskrnl.h>
@@ -88,12 +29,8 @@
#include <debug.h>
/************************************************************************/
-/* BUFMAX defines the maximum number of characters in inbound/outbound buffers*/
-/* at least NUMREGBYTES*2 are needed for register packets */
-#define BUFMAX 1000
static BOOLEAN GspInitialized;
-
static BOOLEAN GspRemoteDebug;
static CONST CHAR HexChars[]="0123456789abcdef";
@@ -105,7 +42,12 @@
static FAST_MUTEX GspLock;
extern LIST_ENTRY PsActiveProcessHead;
-KD_PORT_INFORMATION GdbPortInfo = { 2, 115200, 0 }; /* FIXME hardcoded for COM2, 115200
baud */
+
+/* FIXME hardcoded for COM2, 115200 baud */
+KD_PORT_INFORMATION GdbPortInfo = { 2, 115200, 0 };
+
+static CHAR GspInBuffer[1000];
+static CHAR GspOutBuffer[1000];
/* Number of Registers. */
#define NUMREGS 16
@@ -178,8 +120,6 @@
return -1;
}
-static CHAR GspInBuffer[BUFMAX];
-static CHAR GspOutBuffer[BUFMAX];
VOID
GdbPutChar(UCHAR Value)
@@ -199,7 +139,6 @@
}
/* scan for the sequence $<data>#<Checksum> */
-
PCHAR
GspGetPacket()
{
@@ -221,7 +160,7 @@
Count = 0;
/* now, read until a # or end of Buffer is found */
- while (Count < BUFMAX)
+ while (Count < sizeof(GspInBuffer) - 1)
{
ch = GdbGetChar();
if (ch == '$')
@@ -260,7 +199,6 @@
}
/* send the packet in Buffer. */
-
VOID
GspPutPacket(PCHAR Buffer)
{
@@ -314,17 +252,23 @@
GdbPutChar(HexChars[Checksum & 0xf]);
}
-/* Indicate to caller of GspMem2Hex or GspHex2Mem that there has been an
- error. */
+/* Indicate to caller of GspMem2Hex or GspHex2Mem that there has been an error. */
static volatile BOOLEAN GspMemoryError = FALSE;
-static volatile void *GspAccessLocation = NULL;
static CHAR
GspReadMemSafe(PCHAR Address)
{
- CHAR ch;
- KdpSafeReadMemory((ULONG_PTR)Address, 1, &ch);
+ CHAR ch = 0;
+ if (!KdpSafeReadMemory((ULONG_PTR)Address, 1, &ch))
+ GspMemoryError = TRUE;
return ch;
+}
+
+static void
+GspWriteMemSafe(PCHAR Address, CHAR Ch)
+{
+ if (!KdpSafeWriteMemory((ULONG_PTR)Address, 1, Ch))
+ GspMemoryError = TRUE;
}
/* Convert the memory pointed to by Address into hex, placing result in Buffer */
@@ -375,7 +319,6 @@
ULONG CountInPage;
ULONG i;
CHAR ch;
- ULONG OldProt = 0;
Current = Address;
while (Current < Address + Count)
@@ -391,30 +334,24 @@
/* Flows into next page, handle only current page in this iteration */
CountInPage = PAGE_SIZE - (Address - Page);
}
+
+ for (i = 0; i < CountInPage && ! GspMemoryError; i++)
+ {
+ ch = (*GetContent)(Context, Current - Address);
+
+ if (MayFault)
+ {
+ GspWriteMemSafe(Current, ch);
+ }
+ else
+ {
+ *Current = ch;
+ }
+
+ Current++;
+ }
if (MayFault)
{
- OldProt = MmGetPageProtect(NULL, Address);
- MmSetPageProtect(NULL, Address, PAGE_EXECUTE_READWRITE);
- }
-
- for (i = 0; i < CountInPage && ! GspMemoryError; i++)
- {
- ch = (*GetContent)(Context, Current - Address);
-
- if (MayFault)
- {
- GspAccessLocation = Current;
- }
- *Current = ch;
- if (MayFault)
- {
- GspAccessLocation = NULL;
- }
- Current++;
- }
- if (MayFault)
- {
- MmSetPageProtect(NULL, Page, OldProt);
if (GspMemoryError)
{
return Current - Address;
@@ -432,8 +369,8 @@
HexValue(*((PCHAR) Context + 2 * Offset + 1)));
}
-/* Convert the hex array pointed to by Buffer into binary to be placed at Address */
-/* Return a pointer to the character AFTER the last byte read from Buffer */
+/* Convert the hex array pointed to by Buffer into binary to be placed at Address
+ * Return a pointer to the character AFTER the last byte read from Buffer */
static PCHAR
GspHex2Mem(PCHAR Buffer,
PCHAR Address,
@@ -444,49 +381,6 @@
return Buffer + 2 * Count;
}
-
-static void
-GspWriteMemSafe(PCHAR Address,
- CHAR Ch)
-{
- KdpSafeWriteMemory((ULONG_PTR)Address, 1, Ch);
-}
-
-
-/* This function takes the 386 exception vector and attempts to
- translate this number into a unix compatible signal value */
-ULONG
-GspComputeSignal(NTSTATUS ExceptionCode)
-{
- ULONG SigVal;
-
- switch (ExceptionCode)
- {
- case STATUS_INTEGER_DIVIDE_BY_ZERO:
- SigVal = 8; /* divide by zero */
- break;
- case STATUS_SINGLE_STEP:
- case STATUS_BREAKPOINT:
- SigVal = 5; /* breakpoint */
- break;
- case STATUS_INTEGER_OVERFLOW:
- case STATUS_ARRAY_BOUNDS_EXCEEDED:
- SigVal = 16; /* bound instruction */
- break;
- case STATUS_ILLEGAL_INSTRUCTION:
- SigVal = 4; /* Invalid opcode */
- break;
- case STATUS_STACK_OVERFLOW:
- case STATUS_DATATYPE_MISALIGNMENT:
- case STATUS_ACCESS_VIOLATION:
- SigVal = 11; /* access violation */
- break;
- default:
- SigVal = 7; /* "software generated" */
- }
- return SigVal;
-}
-
/**********************************************/
/* WHILE WE FIND NICE HEX CHARS, BUILD A LONG */
@@ -932,6 +826,15 @@
GspMem2Hex(Buffer, &GspOutBuffer[0], strlen(Buffer), FALSE);
}
}
+ else if (strncmp(Request, "Supported", 9) == 0)
+ {
+ /* tell maximum incoming packet size */
+ sprintf(GspOutBuffer, "PacketSize=%u", sizeof(GspInBuffer) - 1);
+ }
+ else if (strncmp(Request, "Rcmd,", 5) == 0)
+ {
+ ;
+ }
}
VOID
@@ -954,6 +857,8 @@
GspOutBuffer[1] = '\0';
}
}
+
+#define DR6_BS 0x00004000 /* Single step */
#define DR7_L0 0x00000001 /* Local breakpoint 0 enable */
#define DR7_G0 0x00000002 /* Global breakpoint 0 enable */
@@ -1011,7 +916,6 @@
#define MAX_SW_BREAKPOINTS 64
static unsigned GspSwBreakpointCount = 0;
static GSPSWBREAKPOINT GspSwBreakpoints[MAX_SW_BREAKPOINTS];
-static CHAR GspSwBreakpointsInstructions[MAX_SW_BREAKPOINTS];
static void
GspSetHwBreakpoint(ULONG Type, ULONG_PTR Address, ULONG Length)
@@ -1085,6 +989,21 @@
strcpy(GspOutBuffer, "E22");
}
+static BOOLEAN
+GspFindSwBreakpoint(ULONG_PTR Address, PULONG PIndex)
+{
+ ULONG Index;
+
+ for (Index = 0; Index < GspSwBreakpointCount; Index++)
+ if (GspSwBreakpoints[Index].Address == Address)
+ {
+ if (PIndex) *PIndex = Index;
+ return TRUE;
+ }
+
+ return FALSE;
+}
+
static void
GspSetSwBreakpoint(ULONG_PTR Address)
{
@@ -1094,61 +1013,44 @@
{
DPRINT1("Trying to set too many software breakpoints\n");
strcpy(GspOutBuffer, "E22");
- }
- else
- {
- unsigned Index;
-
- for (Index = 0; Index < GspSwBreakpointCount; Index++)
- {
- if (GspSwBreakpoints[Index].Address == Address)
- {
- strcpy(GspOutBuffer, "E22");
- return;
- }
- }
-
- DPRINT("Stored at index %u\n", GspSwBreakpointCount);
- GspSwBreakpoints[GspSwBreakpointCount].Address = Address;
- GspSwBreakpoints[GspSwBreakpointCount].Active = FALSE;
- GspSwBreakpointsInstructions[GspSwBreakpointCount] =
- GspReadMemSafe((PCHAR )Address);
- GspWriteMemSafe((PCHAR )Address, 0xCC);
- GspSwBreakpointCount++;
- strcpy(GspOutBuffer, "OK");
- }
+ return;
+ }
+
+ if (GspFindSwBreakpoint(Address, NULL))
+ {
+ strcpy(GspOutBuffer, "E22");
+ return;
+ }
+
+ DPRINT("Stored at index %u\n", GspSwBreakpointCount);
+ GspSwBreakpoints[GspSwBreakpointCount].Address = Address;
+ GspSwBreakpoints[GspSwBreakpointCount].Active = FALSE;
+ GspSwBreakpointCount++;
+ strcpy(GspOutBuffer, "OK");
}
static void
GspRemoveSwBreakpoint(ULONG_PTR Address)
{
- unsigned Index;
+ ULONG Index;
DPRINT("GspRemoveSwBreakpoint(0x%p)\n", Address);
- for (Index = 0; Index < GspSwBreakpointCount; Index++)
- {
- if (GspSwBreakpoints[Index].Address == Address)
- {
- DPRINT("Found match at index %u\n", Index);
- ASSERT(! GspSwBreakpoints[Index].Active);
-
- GspWriteMemSafe((PCHAR )Address,
- GspSwBreakpointsInstructions[Index]);
-
- if (Index + 1 < GspSwBreakpointCount)
- {
- memmove(GspSwBreakpoints + Index,
- GspSwBreakpoints + (Index + 1),
- (GspSwBreakpointCount - Index - 1) *
- sizeof(GSPSWBREAKPOINT));
- memmove(GspSwBreakpointsInstructions + Index,
- GspSwBreakpointsInstructions + (Index + 1),
- (GspSwBreakpointCount - Index - 1) * sizeof(CHAR));
- }
- GspSwBreakpointCount--;
- strcpy(GspOutBuffer, "OK");
- return;
- }
+
+ if (GspFindSwBreakpoint(Address, &Index))
+ {
+ DPRINT("Found match at index %u\n", Index);
+ ASSERT(! GspSwBreakpoints[Index].Active);
+
+ if (Index + 1 < GspSwBreakpointCount)
+ {
+ memmove(GspSwBreakpoints + Index,
+ GspSwBreakpoints + (Index + 1),
+ (GspSwBreakpointCount - Index - 1) *
+ sizeof(GSPSWBREAKPOINT));
+ }
+ GspSwBreakpointCount--;
+ strcpy(GspOutBuffer, "OK");
+ return;
}
DPRINT1("Not found\n");
@@ -1195,6 +1097,28 @@
}
static void
+GspLoadSwBreakpoint(ULONG Index)
+{
+ GspMemoryError = FALSE;
+ GspSwBreakpoints[Index].PrevContent = GspReadMemSafe((PCHAR)
GspSwBreakpoints[Index].Address);
+ if (! GspMemoryError)
+ {
+ GspWriteMemSafe((PCHAR) GspSwBreakpoints[Index].Address, I386_OPCODE_INT3);
+ }
+ GspSwBreakpoints[Index].Active = ! GspMemoryError;
+ if (GspMemoryError)
+ {
+ DPRINT1("Failed to set software breakpoint at 0x%p\n",
+ GspSwBreakpoints[Index].Address);
+ }
+ else
+ {
+ DPRINT("Successfully set software breakpoint at 0x%p\n",
+ GspSwBreakpoints[Index].Address);
+ }
+}
+
+static void
GspLoadBreakpoints(PKTRAP_FRAME TrapFrame)
{
unsigned Index;
@@ -1202,6 +1126,7 @@
DPRINT("GspLoadBreakpoints\n");
DPRINT("DR7 on entry: 0x%08x\n", TrapFrame->Dr7);
+
/* Remove all breakpoints */
TrapFrame->Dr7 &= ~(DR7_L0 | DR7_L1 | DR7_L2 | DR7_L3 |
DR7_G0 | DR7_G1 | DR7_G2 | DR7_G3 |
@@ -1235,47 +1160,22 @@
for (Index = 0; Index < GspSwBreakpointCount; Index++)
{
- if (GspHwBreakpointCount + Index < MAX_HW_BREAKPOINTS)
- {
- DPRINT("Implementing software interrupt using hardware register\n");
- GspLoadHwBreakpoint(TrapFrame, GspHwBreakpointCount + Index,
- GspSwBreakpoints[Index].Address, 0,
- I386_BP_TYPE_EXECUTE);
- GspSwBreakpoints[Index].Active = FALSE;
- }
- else
- {
- DPRINT("Using real software breakpoint\n");
- GspMemoryError = FALSE;
- GspSwBreakpoints[Index].PrevContent = GspReadMemSafe((PCHAR)
GspSwBreakpoints[Index].Address);
- if (! GspMemoryError)
- {
- GspWriteMemSafe((PCHAR) GspSwBreakpoints[Index].Address,
I386_OPCODE_INT3);
- }
- GspSwBreakpoints[Index].Active = ! GspMemoryError;
- if (GspMemoryError)
- {
- DPRINT1("Failed to set software breakpoint at 0x%p\n",
- GspSwBreakpoints[Index].Address);
- }
- else
- {
- DPRINT("Successfully set software breakpoint at 0x%p\n",
- GspSwBreakpoints[Index].Address);
- DPRINT1("Successfully set software breakpoint at 0x%p\n",
GspSwBreakpoints[Index].Address);
- }
- }
+ DPRINT("Using real software breakpoint\n");
+ GspLoadSwBreakpoint(Index);
}
DPRINT("Final DR7 value 0x%08x\n", TrapFrame->Dr7);
}
static void
-GspUnloadBreakpoints(PKTRAP_FRAME TrapFrame)
+GspUnloadBreakpoints(void)
{
unsigned Index;
- DPRINT("GspUnloadHwBreakpoints\n");
+ DPRINT("GspUnloadBreakpoints\n");
+
+ /* Disable hardware debugging while we are inside the stub */
+ Ke386SetDr7(0);
for (Index = 0; Index < GspSwBreakpointCount; Index++)
{
@@ -1299,9 +1199,67 @@
}
}
-static BOOLEAN gdb_attached_yet = FALSE;
+static void
+GspStopReply(NTSTATUS ExceptionCode, PKTRAP_FRAME TrapFrame)
+{
+ PCHAR ptr = GspOutBuffer;
+ ULONG SigVal;
+ LONG Esp;
+
+ switch (ExceptionCode)
+ {
+ case STATUS_INTEGER_DIVIDE_BY_ZERO:
+ SigVal = 8; /* divide by zero */
+ break;
+ case STATUS_SINGLE_STEP:
+ case STATUS_BREAKPOINT:
+ SigVal = 5; /* breakpoint */
+ break;
+ case STATUS_INTEGER_OVERFLOW:
+ case STATUS_ARRAY_BOUNDS_EXCEEDED:
+ SigVal = 16; /* bound instruction */
+ break;
+ case STATUS_ILLEGAL_INSTRUCTION:
+ SigVal = 4; /* Invalid opcode */
+ break;
+ case STATUS_STACK_OVERFLOW:
+ case STATUS_DATATYPE_MISALIGNMENT:
+ case STATUS_ACCESS_VIOLATION:
+ SigVal = 11; /* access violation */
+ break;
+ default:
+ SigVal = 7; /* "software generated" */
+ }
+
+ ptr = GspOutBuffer;
+
+ *ptr++ = 'T'; /* notify gdb with signo, PC, FP and SP */
+ *ptr++ = HexChars[(SigVal >> 4) & 0xf];
+ *ptr++ = HexChars[SigVal & 0xf];
+
+ *ptr++ = HexChars[ESP];
+ *ptr++ = ':';
+
+ Esp = GspGetEspFromTrapFrame(TrapFrame); /* SP */
+ ptr = GspMem2Hex((PCHAR) &Esp, ptr, 4, 0);
+ *ptr++ = ';';
+
+ *ptr++ = HexChars[EBP];
+ *ptr++ = ':';
+ ptr = GspMem2Hex((PCHAR) &TrapFrame->Ebp, ptr, 4, 0); /* FP */
+ *ptr++ = ';';
+
+ *ptr++ = HexChars[PC];
+ *ptr++ = ':';
+ ptr = GspMem2Hex((PCHAR) &TrapFrame->Eip, ptr, 4, 0); /* PC */
+ *ptr++ = ';';
+
+ *ptr = '\0';
+}
+
+
/*
- * This function does all command procesing for interfacing to gdb.
+ * This function does all command procesing for interfacing to GDB.
*/
KD_CONTINUE_TYPE
NTAPI
@@ -1309,34 +1267,23 @@
PCONTEXT Context,
PKTRAP_FRAME TrapFrame)
{
- BOOLEAN Stepping;
- LONG Address;
- LONG Length;
- LONG SigVal = 0;
- LONG NewPC;
- PCHAR ptr;
-
- /* FIXME: Stop on other CPUs too */
-
- if (STATUS_ACCESS_VIOLATION == (NTSTATUS) ExceptionRecord->ExceptionCode &&
- NULL != GspAccessLocation &&
- (ULONG_PTR) GspAccessLocation ==
- (ULONG_PTR) ExceptionRecord->ExceptionInformation[1])
- {
- GspAccessLocation = NULL;
- GspMemoryError = TRUE;
- Context->Eip += 3;
- }
- else
- {
- DPRINT("Thread %p entering stub\n", PsGetCurrentThread());
+ static BOOLEAN GdbAttached = FALSE;
+ BOOLEAN Stepping = FALSE;
+ NTSTATUS ExceptionCode;
+ LONG Address;
+ LONG Length;
+ PCHAR ptr;
+
+ /* FIXME: Stop on other CPUs too */
+
+ DPRINT("Thread %p entering stub\n", PsGetCurrentThread());
+ ExceptionCode = (NTSTATUS) ExceptionRecord->ExceptionCode;
+
/* Can only debug 1 thread at a time... */
ExAcquireFastMutex(&GspLock);
DPRINT("Thread %p acquired mutex\n", PsGetCurrentThread());
- /* Disable hardware debugging while we are inside the stub */
- Ke386SetDr7(0);
- GspUnloadBreakpoints(TrapFrame);
+ GspUnloadBreakpoints();
/* Make sure we're debugging the current thread. */
if (NULL != GspDbgThread)
@@ -1346,67 +1293,29 @@
GspDbgThread = NULL;
}
- /* ugly hack to avoid attempting to send status at the very
- * beginning, right when GDB is trying to query the stub */
- if (gdb_attached_yet)
- {
- LONG Esp;
-
- stop_reply:
- /* reply to host that an exception has occurred */
- SigVal = GspComputeSignal(ExceptionRecord->ExceptionCode);
-
- ptr = GspOutBuffer;
-
- *ptr++ = 'T'; /* notify gdb with signo, PC, FP and SP */
- *ptr++ = HexChars[(SigVal >> 4) & 0xf];
- *ptr++ = HexChars[SigVal & 0xf];
-
- *ptr++ = HexChars[ESP];
- *ptr++ = ':';
-
- Esp = GspGetEspFromTrapFrame(TrapFrame); /* SP */
- ptr = GspMem2Hex((PCHAR) &Esp, ptr, 4, 0);
- *ptr++ = ';';
-
- *ptr++ = HexChars[EBP];
- *ptr++ = ':';
- ptr = GspMem2Hex((PCHAR) &TrapFrame->Ebp, ptr, 4, 0); /* FP */
- *ptr++ = ';';
-
- *ptr++ = HexChars[PC];
- *ptr++ = ':';
- ptr = GspMem2Hex((PCHAR) &TrapFrame->Eip, ptr, 4, 0); /* PC */
- *ptr++ = ';';
-
- *ptr = '\0';
-
- GspPutPacket(&GspOutBuffer[0]);
- /* DPRINT("------- replied status: (%s) -------\n", GspOutBuffer);
*/
+ if (GdbAttached)
+ {
+ GspStopReply(ExceptionCode, TrapFrame);
+ GspPutPacket(GspOutBuffer);
+ // DbgPrint(">>> (%s) >>>\n", GspOutBuffer);
}
else
{
- gdb_attached_yet = 1;
- }
-
- Stepping = FALSE;
+ GdbAttached = TRUE;
+ }
while (TRUE)
{
/* Zero the buffer now so we don't have to worry about the terminating zero
character */
- memset(GspOutBuffer, 0, sizeof(GspInBuffer));
+ memset(GspOutBuffer, 0, sizeof(GspOutBuffer));
ptr = GspGetPacket();
- /* DPRINT("------- Get (%s) command -------\n", ptr); */
+ // DbgPrint("<<< (%s) <<<\n", ptr);
switch(*ptr++)
{
case '?':
/* a little hack to send more complete status information */
- goto stop_reply;
- GspOutBuffer[0] = 'S';
- GspOutBuffer[1] = HexChars[SigVal >> 4];
- GspOutBuffer[2] = HexChars[SigVal % 16];
- GspOutBuffer[3] = 0;
+ GspStopReply(ExceptionCode, TrapFrame);
break;
case 'd':
GspRemoteDebug = !GspRemoteDebug; /* toggle debug flag */
@@ -1478,7 +1387,7 @@
if (GspMemoryError)
{
strcpy(GspOutBuffer, "E03");
- DPRINT("Fault during memory read\n");
+ DPRINT1("Fault during memory read\n");
}
}
@@ -1514,7 +1423,7 @@
if (GspMemoryError)
{
strcpy(GspOutBuffer, "E03");
- DPRINT("Fault during memory write\n");
+ DPRINT1("Fault during memory write\n");
}
else
{
@@ -1537,55 +1446,49 @@
case 'c':
{
ULONG BreakpointNumber;
- ULONG dr6_;
-
- /* try to read optional parameter, pc unchanged if no parm */
+ ULONG Dr6;
+
+ /* try to read optional parameter, pc changed if param */
if (GspHex2Long (&ptr, &Address))
{
Context->Eip = Address;
}
-
- NewPC = Context->Eip;
+ else if (ExceptionCode == STATUS_BREAKPOINT)
+ {
+ if (GspReadMemSafe((PCHAR) Context->Eip) == (CHAR)
I386_OPCODE_INT3)
+ {
+ Context->Eip++;
+ }
+ }
/* clear the trace bit */
- Context->EFlags &= 0xfffffeff;
+ Context->EFlags &= ~EFLAGS_TF;
/* set the trace bit if we're Stepping */
if (Stepping)
{
- Context->EFlags |= 0x100;
+ Context->EFlags |= EFLAGS_TF;
}
-#if defined(__GNUC__)
- asm volatile ("movl %%db6, %0\n" : "=r" (dr6_) : );
-#elif defined(_MSC_VER)
- __asm mov eax, dr6 __asm mov dr6_, eax;
-#else
-#error Unknown compiler for inline assembler
-#endif
- if (!(dr6_ & 0x4000))
+ Dr6 = Ke386GetDr6();
+ if (!(Dr6 & DR6_BS))
{
- for (BreakpointNumber = 0; BreakpointNumber < 4;
++BreakpointNumber)
+ for (BreakpointNumber = 0; BreakpointNumber < MAX_HW_BREAKPOINTS;
++BreakpointNumber)
{
- if (dr6_ & (1 << BreakpointNumber))
+ if (Dr6 & (1 << BreakpointNumber))
{
- if (GspHwBreakpoints[BreakpointNumber].Type == 0)
+ if (GspHwBreakpoints[BreakpointNumber].Type ==
I386_BP_TYPE_EXECUTE)
{
/* Set restore flag */
- Context->EFlags |= 0x10000;
+ Context->EFlags |= EFLAGS_RF;
break;
}
}
}
}
+
GspLoadBreakpoints(TrapFrame);
-#if defined(__GNUC__)
- asm volatile ("movl %0, %%db6\n" : : "r" (0));
-#elif defined(_MSC_VER)
- __asm mov eax, 0 __asm mov dr6, eax;
-#else
-#error Unknown compiler for inline assembler
-#endif
+ Ke386SetDr6(0);
if (NULL != GspDbgThread)
{
@@ -1596,14 +1499,19 @@
DPRINT("Thread %p releasing mutex\n", PsGetCurrentThread());
ExReleaseFastMutex(&GspLock);
DPRINT("Thread %p leaving stub\n", PsGetCurrentThread());
- return kdContinue;
- break;
+
+ if (ExceptionCode == STATUS_BREAKPOINT ||
+ ExceptionCode == STATUS_SINGLE_STEP)
+ {
+ return kdContinue;
+ }
+
+ return kdHandleException;
}
case 'k': /* kill the program */
strcpy(GspOutBuffer, "OK");
break;
- /* kill the program */
case 'H': /* Set thread */
GspSetThread(ptr);
@@ -1630,11 +1538,11 @@
GspHex2Long(&ptr, &Length);
if (0 == Type)
{
- GspSetSwBreakpoint((ULONG_PTR) Address);
+ GspSetSwBreakpoint((ULONG_PTR) Address);
}
else
{
- GspSetHwBreakpoint(Type, (ULONG_PTR) Address, Length);
+ GspSetHwBreakpoint(Type, (ULONG_PTR) Address, Length);
}
break;
}
@@ -1652,11 +1560,11 @@
GspHex2Long(&ptr, &Length);
if (0 == Type)
{
- GspRemoveSwBreakpoint((ULONG_PTR) Address);
+ GspRemoveSwBreakpoint((ULONG_PTR) Address);
}
else
{
- GspRemoveHwBreakpoint(Type, (ULONG_PTR) Address, Length);
+ GspRemoveHwBreakpoint(Type, (ULONG_PTR) Address, Length);
}
break;
}
@@ -1667,20 +1575,8 @@
/* reply to the request */
GspPutPacket(GspOutBuffer);
- /* DPRINT("------- reply command (%s) -------\n", GspOutBuffer); */
- }
-
- /* not reached */
- ASSERT(0);
- }
-
- if (NULL != GspDbgThread)
- {
- ObDereferenceObject(GspDbgThread);
- GspDbgThread = NULL;
- }
-
- return kdContinue;
+ // DbgPrint(">>> (%s) >>>\n", GspOutBuffer);
+ }
}
@@ -1754,8 +1650,6 @@
/* Initialize the Port */
KdPortInitializeEx(&GdbPortInfo, 0, 0);
-
- KdpPort = GdbPortInfo.ComPort;
}
else if (BootPhase == 1)
{