mirror of
https://github.com/reactos/reactos.git
synced 2024-12-27 09:34:43 +00:00
Little KDB update ;-) If you have any problems and/or questions let me know. I hope it was tested enough and works well enough for everybody.
svn path=/trunk/; revision=13841
This commit is contained in:
parent
ef8c905431
commit
f3cea5b1a2
24 changed files with 5621 additions and 1814 deletions
|
@ -216,6 +216,8 @@ bootcd_install_before:
|
|||
$(CP) media/nls/l_intl.nls $(BOOTCD_DIR)/reactos/l_intl.nls
|
||||
$(HALFVERBOSEECHO) [COPY] media/drivers/etc/services to $(BOOTCD_DIR)/reactos/services
|
||||
$(CP) media/drivers/etc/services $(BOOTCD_DIR)/reactos/services
|
||||
$(HALFVERBOSEECHO) [COPY] media/drivers/etc/KDB.init to $(BOOTCD_DIR)/reactos/KDB.init
|
||||
$(CP) media/drivers/etc/KDB.init $(BOOTCD_DIR)/reactos/KDB.init
|
||||
|
||||
bootcd_basic: bootcd_directory_layout bootcd_bootstrap_files bootcd_install_before
|
||||
|
||||
|
@ -1043,6 +1045,8 @@ install_before:
|
|||
$(CP) media/nls/l_intl.nls $(INSTALL_DIR)/system32/casemap.nls
|
||||
$(HALFVERBOSEECHO) [INSTALL] media/drivers/etc/services to $(INSTALL_DIR)/system32/drivers/etc/services
|
||||
$(CP) media/drivers/etc/services $(INSTALL_DIR)/system32/drivers/etc/services
|
||||
$(HALFVERBOSEECHO) [INSTALL] media/drivers/etc/KDB.init to $(INSTALL_DIR)/system32/drivers/etc/KDB.init
|
||||
$(CP) media/drivers/etc/KDB.init $(INSTALL_DIR)/system32/drivers/etc/KDB.init
|
||||
|
||||
.PHONY: install_clean install_dirs install_before
|
||||
|
||||
|
|
|
@ -38,6 +38,7 @@ static BYTE capsDown,numDown,scrollDown;
|
|||
static DWORD ctrlKeyState;
|
||||
static PKINTERRUPT KbdInterrupt;
|
||||
static KDPC KbdDpc;
|
||||
static PIO_WORKITEM KbdWorkItem = NULL;
|
||||
static BOOLEAN AlreadyOpened = FALSE;
|
||||
|
||||
/*
|
||||
|
@ -407,6 +408,24 @@ static WORD ScanToVirtual(BYTE scanCode)
|
|||
}
|
||||
|
||||
|
||||
/*
|
||||
* Debug request handler
|
||||
*/
|
||||
|
||||
static VOID STDCALL
|
||||
KbdWorkItemRoutine(IN PDEVICE_OBJECT DeviceObject,
|
||||
IN PVOID Context)
|
||||
{
|
||||
LONG Debug;
|
||||
|
||||
Debug = InterlockedExchange(&DoSystemDebug, -1);
|
||||
if (Debug != -1)
|
||||
{
|
||||
KdSystemDebugControl(Debug);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
* Keyboard IRQ handler
|
||||
*/
|
||||
|
@ -419,14 +438,21 @@ KbdDpcRoutine(PKDPC Dpc,
|
|||
{
|
||||
PIRP Irp = (PIRP)SystemArgument2;
|
||||
PDEVICE_OBJECT DeviceObject = (PDEVICE_OBJECT)SystemArgument1;
|
||||
|
||||
|
||||
if (SystemArgument1 == NULL && DoSystemDebug != -1)
|
||||
{
|
||||
KdSystemDebugControl(DoSystemDebug);
|
||||
DoSystemDebug = -1;
|
||||
if (KbdWorkItem != NULL)
|
||||
{
|
||||
IoQueueWorkItem(KbdWorkItem, (PIO_WORKITEM_ROUTINE)KbdWorkItemRoutine, DelayedWorkQueue, NULL);
|
||||
}
|
||||
else
|
||||
{
|
||||
KdSystemDebugControl(DoSystemDebug);
|
||||
DoSystemDebug = -1;
|
||||
}
|
||||
return;
|
||||
}
|
||||
|
||||
|
||||
CHECKPOINT;
|
||||
DPRINT("KbdDpcRoutine(DeviceObject %x, Irp %x)\n",
|
||||
DeviceObject,Irp);
|
||||
|
@ -436,6 +462,7 @@ KbdDpcRoutine(PKDPC Dpc,
|
|||
IoStartNextPacket(DeviceObject,FALSE);
|
||||
}
|
||||
|
||||
|
||||
static BOOLEAN STDCALL
|
||||
KeyboardHandler(PKINTERRUPT Interrupt,
|
||||
PVOID Context)
|
||||
|
@ -538,7 +565,7 @@ KeyboardHandler(PKINTERRUPT Interrupt,
|
|||
else if (InSysRq == TRUE && ScanToVirtual(thisKey) >= VK_A &&
|
||||
ScanToVirtual(thisKey) <= VK_Z && isDown)
|
||||
{
|
||||
DoSystemDebug = ScanToVirtual(thisKey) - VK_A;
|
||||
InterlockedExchange(&DoSystemDebug, ScanToVirtual(thisKey) - VK_A);
|
||||
KeInsertQueueDpc(&KbdDpc, NULL, NULL);
|
||||
return(TRUE);
|
||||
}
|
||||
|
@ -659,6 +686,11 @@ static int InitializeKeyboard(PDEVICE_OBJECT DeviceObject)
|
|||
KbdClearInput();
|
||||
KeyboardConnectInterrupt(DeviceObject);
|
||||
KeInitializeDpc(&KbdDpc,KbdDpcRoutine,NULL);
|
||||
KbdWorkItem = IoAllocateWorkItem(DeviceObject);
|
||||
if (KbdWorkItem == NULL)
|
||||
{
|
||||
DPRINT("Warning: Couldn't allocate work item!\n");
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
|
15
reactos/media/drivers/etc/KDB.init
Normal file
15
reactos/media/drivers/etc/KDB.init
Normal file
|
@ -0,0 +1,15 @@
|
|||
# Example KDB.init file
|
||||
#
|
||||
# The disassembly flavor is set to "intel" (default is "at&t") and the
|
||||
#
|
||||
|
||||
# Set the disassembly flavor to "intel" (default is "at&t")
|
||||
set syntax intel
|
||||
|
||||
# Change the condition to enter KDB on INT3 to "always" (default is "kmode")
|
||||
set condition INT3 first always
|
||||
|
||||
# This is a special command available only in the KDB.init file - it breaks into
|
||||
# KDB when it is interpreting the init file at startup.
|
||||
#break
|
||||
|
|
@ -25,14 +25,10 @@ LINKER_SCRIPT := ntoskrnl.lnk
|
|||
STRIP_FLAGS := -Wl,-s
|
||||
|
||||
ifeq ($(KDBG), 1)
|
||||
OBJECTS_KDBG := dbg/kdb.o dbg/kdb_serial.o dbg/kdb_keyboard.o dbg/rdebug.o \
|
||||
dbg/i386/kdb_help.o \
|
||||
../dk/w32/lib/libkjs.a dbg/i386/i386-dis.o
|
||||
CFLAGS_KDBG := -I../lib/kjs/include
|
||||
OBJECTS_KDBG := dbg/kdb.o dbg/kdb_cli.o dbg/kdb_expr.o dbg/kdb_keyboard.o \
|
||||
dbg/kdb_serial.o dbg/kdb_string.o dbg/rdebug.o dbg/i386/kdb_help.o \
|
||||
dbg/i386/i386-dis.o dbg/i386/longjmp.o dbg/i386/setjmp.o
|
||||
preall: all
|
||||
|
||||
../dk/w32/lib/libkjs.a:
|
||||
$(MAKE) -C ../lib/kjs
|
||||
else
|
||||
OBJECTS_KDBG :=
|
||||
endif
|
||||
|
|
|
@ -1,4 +1,4 @@
|
|||
/* $Id:$
|
||||
/* $Id$
|
||||
*
|
||||
* COPYRIGHT: See COPYING in the top level directory
|
||||
* PROJECT: ReactOS kernel
|
||||
|
@ -52,10 +52,10 @@ extern long MmSafeCopyFromUser(void *Dest, void *Src, unsigned long NumberOfByte
|
|||
|
||||
|
||||
int
|
||||
print_insn_i386_att (bfd_vma pc, struct disassemble_info *info);
|
||||
print_insn_i386 (bfd_vma pc, struct disassemble_info *info);
|
||||
|
||||
int
|
||||
KdbPrintDisasm(void* Ignored, const char* fmt, ...)
|
||||
KdbpPrintDisasm(void* Ignored, const char* fmt, ...)
|
||||
{
|
||||
va_list ap;
|
||||
static char buffer[256];
|
||||
|
@ -69,46 +69,46 @@ KdbPrintDisasm(void* Ignored, const char* fmt, ...)
|
|||
}
|
||||
|
||||
int
|
||||
KdbNopPrintDisasm(void* Ignored, const char* fmt, ...)
|
||||
KdbpNopPrintDisasm(void* Ignored, const char* fmt, ...)
|
||||
{
|
||||
return(0);
|
||||
}
|
||||
|
||||
int static
|
||||
KdbReadMemory(unsigned int Addr, unsigned char* Data, unsigned int Length,
|
||||
struct disassemble_info * Ignored)
|
||||
KdbpReadMemory(unsigned int Addr, unsigned char* Data, unsigned int Length,
|
||||
struct disassemble_info * Ignored)
|
||||
{
|
||||
return KdbpSafeReadMemory(Data, (void *)Addr, Length); /* 0 means no error */
|
||||
}
|
||||
|
||||
void static
|
||||
KdbMemoryError(int Status, unsigned int Addr,
|
||||
struct disassemble_info * Ignored)
|
||||
KdbpMemoryError(int Status, unsigned int Addr,
|
||||
struct disassemble_info * Ignored)
|
||||
{
|
||||
}
|
||||
|
||||
void static
|
||||
KdbPrintAddressInCode(unsigned int Addr, struct disassemble_info * Ignored)
|
||||
KdbpPrintAddressInCode(unsigned int Addr, struct disassemble_info * Ignored)
|
||||
{
|
||||
if (!KdbSymPrintAddress((void*)Addr))
|
||||
{
|
||||
DbgPrint("<0x%X>", Addr);
|
||||
DbgPrint("<%08x>", Addr);
|
||||
}
|
||||
}
|
||||
|
||||
void static
|
||||
KdbNopPrintAddress(unsigned int Addr, struct disassemble_info * Ignored)
|
||||
KdbpNopPrintAddress(unsigned int Addr, struct disassemble_info * Ignored)
|
||||
{
|
||||
}
|
||||
|
||||
#include "dis-asm.h"
|
||||
|
||||
long
|
||||
KdbGetInstLength(unsigned int Address)
|
||||
KdbpGetInstLength(unsigned int Address)
|
||||
{
|
||||
disassemble_info info;
|
||||
|
||||
info.fprintf_func = KdbNopPrintDisasm;
|
||||
info.fprintf_func = KdbpNopPrintDisasm;
|
||||
info.stream = NULL;
|
||||
info.application_data = NULL;
|
||||
info.flavour = bfd_target_unknown_flavour;
|
||||
|
@ -116,9 +116,9 @@ KdbGetInstLength(unsigned int Address)
|
|||
info.mach = bfd_mach_i386_i386;
|
||||
info.insn_sets = 0;
|
||||
info.flags = 0;
|
||||
info.read_memory_func = KdbReadMemory;
|
||||
info.memory_error_func = KdbMemoryError;
|
||||
info.print_address_func = KdbNopPrintAddress;
|
||||
info.read_memory_func = KdbpReadMemory;
|
||||
info.memory_error_func = KdbpMemoryError;
|
||||
info.print_address_func = KdbpNopPrintAddress;
|
||||
info.symbol_at_address_func = NULL;
|
||||
info.buffer = NULL;
|
||||
info.buffer_vma = info.buffer_length = 0;
|
||||
|
@ -126,25 +126,25 @@ KdbGetInstLength(unsigned int Address)
|
|||
info.display_endian = BIG_ENDIAN_LITTLE;
|
||||
info.disassembler_options = NULL;
|
||||
|
||||
return(print_insn_i386_att(Address, &info));
|
||||
return(print_insn_i386(Address, &info));
|
||||
}
|
||||
|
||||
long
|
||||
KdbDisassemble(unsigned int Address)
|
||||
KdbpDisassemble(unsigned int Address, unsigned long IntelSyntax)
|
||||
{
|
||||
disassemble_info info;
|
||||
|
||||
info.fprintf_func = KdbPrintDisasm;
|
||||
info.fprintf_func = KdbpPrintDisasm;
|
||||
info.stream = NULL;
|
||||
info.application_data = NULL;
|
||||
info.flavour = bfd_target_unknown_flavour;
|
||||
info.arch = bfd_arch_i386;
|
||||
info.mach = bfd_mach_i386_i386;
|
||||
info.mach = IntelSyntax ? bfd_mach_i386_i386_intel_syntax : bfd_mach_i386_i386;
|
||||
info.insn_sets = 0;
|
||||
info.flags = 0;
|
||||
info.read_memory_func = KdbReadMemory;
|
||||
info.memory_error_func = KdbMemoryError;
|
||||
info.print_address_func = KdbPrintAddressInCode;
|
||||
info.read_memory_func = KdbpReadMemory;
|
||||
info.memory_error_func = KdbpMemoryError;
|
||||
info.print_address_func = KdbpPrintAddressInCode;
|
||||
info.symbol_at_address_func = NULL;
|
||||
info.buffer = NULL;
|
||||
info.buffer_vma = info.buffer_length = 0;
|
||||
|
@ -152,7 +152,7 @@ KdbDisassemble(unsigned int Address)
|
|||
info.display_endian = BIG_ENDIAN_LITTLE;
|
||||
info.disassembler_options = NULL;
|
||||
|
||||
return(print_insn_i386_att(Address, &info));
|
||||
return(print_insn_i386(Address, &info));
|
||||
}
|
||||
|
||||
/* Print i386 instructions for GDB, the GNU debugger.
|
||||
|
@ -2113,7 +2113,7 @@ print_insn (pc, info)
|
|||
#else
|
||||
mode_64bit = 0;
|
||||
priv.orig_sizeflag = AFLAG | DFLAG;
|
||||
intel_syntax = 0;
|
||||
/*intel_syntax = 0;*/
|
||||
#endif
|
||||
|
||||
if (intel_syntax)
|
||||
|
|
|
@ -1,29 +1,19 @@
|
|||
#include <internal/ke.h>
|
||||
#include <internal/i386/segment.h>
|
||||
|
||||
.data
|
||||
_KdbEipTemp:
|
||||
.int 0
|
||||
.text
|
||||
|
||||
.text
|
||||
.globl _KdbEnter
|
||||
.globl _KdbEnter
|
||||
_KdbEnter:
|
||||
/*
|
||||
* Record when we are inside the debugger.
|
||||
*/
|
||||
incl _KdbEntryCount
|
||||
|
||||
/*
|
||||
* Save the callers eip.
|
||||
*/
|
||||
popl _KdbEipTemp
|
||||
|
||||
/*
|
||||
* Set up a trap frame
|
||||
*/
|
||||
/* Ss - space already reserved by return EIP */
|
||||
pushl %esp /* Esp */
|
||||
pushfl /* Eflags */
|
||||
pushl %cs /* Cs */
|
||||
pushl _KdbEipTemp /* Eip */
|
||||
pushl 12(%esp) /* Eip */
|
||||
movl %ss, 16(%esp) /* Save Ss */
|
||||
pushl $0 /* ErrorCode */
|
||||
pushl %ebp /* Ebp */
|
||||
pushl %ebx /* Ebx */
|
||||
|
@ -56,34 +46,35 @@ _KdbEnter:
|
|||
pushl $0 /* TempEip */
|
||||
pushl $0 /* TempCs */
|
||||
pushl $0 /* DebugPointer */
|
||||
pushl $0 /* DebugArgMark */
|
||||
pushl _KdbEipTemp /* DebugEip */
|
||||
pushl $3 /* DebugArgMark (Exception number) */
|
||||
pushl 0x60(%esp) /* DebugEip */
|
||||
pushl %ebp /* DebugEbp */
|
||||
|
||||
/*
|
||||
* Push a pointer to the trap frame
|
||||
*/
|
||||
pushl %esp
|
||||
|
||||
/*
|
||||
* Call KDB
|
||||
*/
|
||||
call _KdbInternalEnter
|
||||
movl %esp, %eax
|
||||
pushl $1 /* FirstChance */
|
||||
pushl %eax /* Push a pointer to the trap frame */
|
||||
pushl $0 /* Context */
|
||||
pushl $0 /* PreviousMode (KernelMode) */
|
||||
pushl $0 /* ExceptionRecord */
|
||||
call _KdbEnterDebuggerException
|
||||
|
||||
/*
|
||||
* Pop the argument
|
||||
* Pop the arguments and unused portions of the trap frame:
|
||||
* DebugEbp
|
||||
* DebugEip
|
||||
* DebugArgMark
|
||||
* DebugPointer
|
||||
* TempCs
|
||||
* TempEip
|
||||
*/
|
||||
popl %eax
|
||||
addl $(11*4), %esp
|
||||
|
||||
/*
|
||||
* Ignore unused portions of the trap frame.
|
||||
* Restore/update debugging registers.
|
||||
*/
|
||||
popl %eax /* DebugEbp */
|
||||
popl %eax /* DebugEip */
|
||||
popl %eax /* DebugArgMark */
|
||||
popl %eax /* DebugPointer */
|
||||
popl %eax /* TempCs */
|
||||
popl %eax /* TempEip */
|
||||
popl %eax /* Dr0 */
|
||||
movl %eax, %dr0
|
||||
popl %eax /* Dr1 */
|
||||
|
@ -113,13 +104,17 @@ _KdbEnter:
|
|||
popl %edi /* Edi */
|
||||
popl %esi /* Esi */
|
||||
popl %ebx /* Ebx */
|
||||
popl %ebp /* Ebp */
|
||||
addl $4, %esp /* ErrorCode */
|
||||
|
||||
/*
|
||||
* Record when we are in the debugger.
|
||||
*/
|
||||
decl _KdbEntryCount
|
||||
/* Remove SS:ESP from the stack */
|
||||
movl 16(%esp), %ebp
|
||||
movl %ebp, 24(%esp)
|
||||
movl 12(%esp), %ebp
|
||||
movl %ebp, 20(%esp)
|
||||
movl 8(%esp), %ebp
|
||||
movl %ebp, 16(%esp)
|
||||
|
||||
popl %ebp /* Ebp */
|
||||
addl $12, %esp /* ErrorCode and SS:ESP */
|
||||
|
||||
/*
|
||||
* Return to the caller.
|
||||
|
@ -127,5 +122,26 @@ _KdbEnter:
|
|||
iret
|
||||
|
||||
|
||||
.globl _KdbpStackSwitchAndCall@8
|
||||
_KdbpStackSwitchAndCall@8:
|
||||
pushl %ebp
|
||||
movl %esp, %ebp
|
||||
|
||||
movl 0x8(%esp), %eax /* New stack */
|
||||
movl 0xC(%esp), %ecx /* Function to call */
|
||||
movl %esp, %edx /* Old stack */
|
||||
|
||||
/* Switch stack */
|
||||
movl %eax, %esp
|
||||
pushl %edx
|
||||
|
||||
/* Call function */
|
||||
call *%ecx
|
||||
|
||||
/* Switch back to old stack */
|
||||
popl %esp
|
||||
|
||||
/* Return */
|
||||
popl %ebp
|
||||
ret $8
|
||||
|
||||
|
||||
|
|
70
reactos/ntoskrnl/dbg/i386/longjmp.S
Normal file
70
reactos/ntoskrnl/dbg/i386/longjmp.S
Normal file
|
@ -0,0 +1,70 @@
|
|||
.file "longjmp.S"
|
||||
/*
|
||||
* Copyright (C) 1998, 1999, Jonathan S. Shapiro.
|
||||
*
|
||||
* This file is part of the EROS Operating System.
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or
|
||||
* modify it under the terms of the GNU General Public License
|
||||
* as published by the Free Software Foundation; either version 2,
|
||||
* or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software
|
||||
* Foundation, 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
|
||||
*/
|
||||
|
||||
/*
|
||||
* typedef struct {
|
||||
* unsigned long ebx, esi, edi;
|
||||
* unsigned long ebp;
|
||||
* unsigned long sp;
|
||||
* unsigned long pc;
|
||||
* } jmp_buf[1];
|
||||
*/
|
||||
|
||||
/*
|
||||
* On entry, the stack to longjmp looks like:
|
||||
*
|
||||
* value
|
||||
* ptr to jmp_buf
|
||||
* return PC
|
||||
*/
|
||||
|
||||
.globl _longjmp
|
||||
_longjmp:
|
||||
pushl %ebp
|
||||
movl %esp,%ebp
|
||||
|
||||
movl 8(%ebp),%ecx /* address of jmp_buf to ecx */
|
||||
movl 12(%ebp),%eax /* return value to %eax */
|
||||
testl %eax,%eax
|
||||
jne 1f
|
||||
incl %eax /* return 1 if handed 0 */
|
||||
|
||||
1:
|
||||
movl (%ecx),%ebx /* restore %ebx */
|
||||
movl 4(%ecx),%esi /* restore %esi */
|
||||
movl 8(%ecx),%edi /* restore %edi */
|
||||
|
||||
/*
|
||||
* From this instant on we are not running in a valid frame
|
||||
*/
|
||||
|
||||
movl 12(%ecx),%ebp /* restore %ebp */
|
||||
movl 16(%ecx),%esp /* restore %esp */
|
||||
/* movl 20(%ecx),%eax return PC */
|
||||
|
||||
/*
|
||||
* Since we are abandoning the stack in any case,
|
||||
* there isn't much point in doing the usual return
|
||||
* discipline.
|
||||
*/
|
||||
|
||||
jmpl *20(%ecx)
|
||||
|
59
reactos/ntoskrnl/dbg/i386/setjmp.S
Normal file
59
reactos/ntoskrnl/dbg/i386/setjmp.S
Normal file
|
@ -0,0 +1,59 @@
|
|||
.file "setjmp.S"
|
||||
/*
|
||||
* Copyright (C) 1998, 1999, Jonathan S. Shapiro.
|
||||
*
|
||||
* This file is part of the EROS Operating System.
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or
|
||||
* modify it under the terms of the GNU General Public License
|
||||
* as published by the Free Software Foundation; either version 2,
|
||||
* or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software
|
||||
* Foundation, 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
|
||||
*/
|
||||
|
||||
/* #include <eros/i486/asm.h> */
|
||||
|
||||
|
||||
/*
|
||||
* typedef struct {
|
||||
* unsigned long ebx, esi, edi;
|
||||
* unsigned long ebp;
|
||||
* unsigned long sp;
|
||||
* unsigned long pc;
|
||||
* } jmp_buf[1];
|
||||
*/
|
||||
|
||||
/*
|
||||
* On entry, the stack to setjmp looks like:
|
||||
*
|
||||
* ptr to jmp_buf
|
||||
* return PC
|
||||
*/
|
||||
.globl _setjmp
|
||||
_setjmp:
|
||||
pushl %ebp
|
||||
movl %esp,%ebp
|
||||
|
||||
movl 0x8(%ebp),%eax /* address of jmp_buf to eax */
|
||||
movl %ebx,(%eax) /* save %ebx */
|
||||
movl %esi,4(%eax) /* save %esi */
|
||||
movl %edi,8(%eax) /* save %edi */
|
||||
leal 8(%ebp),%edx /* calling proc's esp, not ours! */
|
||||
movl %edx,16(%eax)
|
||||
movl 4(%ebp), %edx /* save return PC */
|
||||
movl %edx,20(%eax)
|
||||
movl 0(%ebp),%edx /* calling proc's ebp, not ours! */
|
||||
movl %edx,12(%eax)
|
||||
|
||||
xorl %eax,%eax /* return 0 the first time */
|
||||
leave
|
||||
ret $4
|
||||
|
File diff suppressed because it is too large
Load diff
|
@ -1,6 +1,82 @@
|
|||
#ifndef NTOSKRNL_KDB_H
|
||||
#define NTOSKRNL_KDB_H
|
||||
|
||||
/* INCLUDES ******************************************************************/
|
||||
|
||||
#define NTOS_MODE_KERNEL
|
||||
#include <ntos.h>
|
||||
|
||||
#include <internal/ke.h>
|
||||
|
||||
/* DEFINES *******************************************************************/
|
||||
|
||||
#define TAG_KDBG (('K' << 24) | ('D' << 16) | ('B' << 8) | 'G')
|
||||
|
||||
#ifndef RTL_NUMBER_OF
|
||||
# define RTL_NUMBER_OF(x) (sizeof(x) / sizeof((x)[0]))
|
||||
#endif
|
||||
|
||||
|
||||
/* TYPES *********************************************************************/
|
||||
|
||||
/* from kdb.c */
|
||||
typedef struct _KDB_KTRAP_FRAME
|
||||
{
|
||||
KTRAP_FRAME Tf;
|
||||
ULONG Cr0;
|
||||
ULONG Cr1; /* reserved/unused */
|
||||
ULONG Cr2;
|
||||
ULONG Cr3;
|
||||
ULONG Cr4;
|
||||
} KDB_KTRAP_FRAME, *PKDB_KTRAP_FRAME;
|
||||
|
||||
typedef enum _KDB_BREAKPOINT_TYPE
|
||||
{
|
||||
KdbBreakPointNone = 0,
|
||||
KdbBreakPointSoftware,
|
||||
KdbBreakPointHardware,
|
||||
KdbBreakPointTemporary
|
||||
} KDB_BREAKPOINT_TYPE;
|
||||
|
||||
typedef enum _KDB_ACCESS_TYPE
|
||||
{
|
||||
KdbAccessRead,
|
||||
KdbAccessWrite,
|
||||
KdbAccessReadWrite,
|
||||
KdbAccessExec
|
||||
} KDB_ACCESS_TYPE;
|
||||
|
||||
typedef struct _KDB_BREAKPOINT
|
||||
{
|
||||
KDB_BREAKPOINT_TYPE Type; /* Type of breakpoint */
|
||||
BOOLEAN Enabled; /* Whether the bp is enabled */
|
||||
ULONG_PTR Address; /* Address of the breakpoint */
|
||||
BOOLEAN Global; /* Whether the breakpoint is global or local to a process */
|
||||
PEPROCESS Process; /* Owning process */
|
||||
PCHAR ConditionExpression;
|
||||
PVOID Condition;
|
||||
union {
|
||||
/* KdbBreakPointSoftware */
|
||||
UCHAR SavedInstruction;
|
||||
/* KdbBreakPointHardware */
|
||||
struct {
|
||||
UCHAR DebugReg : 2;
|
||||
UCHAR Size : 3;
|
||||
KDB_ACCESS_TYPE AccessType;
|
||||
} Hw;
|
||||
} Data;
|
||||
} KDB_BREAKPOINT, *PKDB_BREAKPOINT;
|
||||
|
||||
typedef enum _KDB_ENTER_CONDITION
|
||||
{
|
||||
KdbDoNotEnter,
|
||||
KdbEnterAlways,
|
||||
KdbEnterFromKmode,
|
||||
KdbEnterFromUmode
|
||||
} KDB_ENTER_CONDITION;
|
||||
|
||||
|
||||
/* from kdb_symbols.c */
|
||||
typedef struct _KDB_MODULE_INFO
|
||||
{
|
||||
WCHAR Name[256];
|
||||
|
@ -9,6 +85,74 @@ typedef struct _KDB_MODULE_INFO
|
|||
PROSSYM_INFO RosSymInfo;
|
||||
} KDB_MODULE_INFO, *PKDB_MODULE_INFO;
|
||||
|
||||
|
||||
/* FUNCTIONS *****************************************************************/
|
||||
|
||||
/* from i386/i386-dis.c */
|
||||
|
||||
LONG
|
||||
KdbpDisassemble(
|
||||
IN ULONG Address,
|
||||
IN ULONG IntelSyntax);
|
||||
|
||||
LONG
|
||||
KdbpGetInstLength(
|
||||
IN ULONG Address);
|
||||
|
||||
/* from i386/kdb_help.S */
|
||||
|
||||
STDCALL VOID
|
||||
KdbpStackSwitchAndCall(
|
||||
IN PVOID NewStack,
|
||||
IN VOID (*Function)(VOID));
|
||||
|
||||
/* from kdb_cli.c */
|
||||
|
||||
extern PCHAR KdbInitFileBuffer;
|
||||
|
||||
VOID
|
||||
KdbpCliInit();
|
||||
|
||||
VOID
|
||||
KdbpCliMainLoop(
|
||||
IN BOOLEAN EnteredOnSingleStep);
|
||||
|
||||
VOID
|
||||
KdbpCliModuleLoaded(
|
||||
IN PUNICODE_STRING Name);
|
||||
|
||||
VOID
|
||||
KdbpCliInterpretInitFile();
|
||||
|
||||
VOID
|
||||
KdbpPrint(
|
||||
IN PCHAR Format,
|
||||
IN ... OPTIONAL);
|
||||
|
||||
/* from kdb_expr.c */
|
||||
|
||||
BOOLEAN
|
||||
KdbpRpnEvaluateExpression(
|
||||
IN PCHAR Expression,
|
||||
IN PKDB_KTRAP_FRAME TrapFrame,
|
||||
OUT PULONGLONG Result,
|
||||
OUT PLONG ErrOffset OPTIONAL,
|
||||
OUT PCHAR ErrMsg OPTIONAL);
|
||||
|
||||
PVOID
|
||||
KdbpRpnParseExpression(
|
||||
IN PCHAR Expression,
|
||||
OUT PLONG ErrOffset OPTIONAL,
|
||||
OUT PCHAR ErrMsg OPTIONAL);
|
||||
|
||||
BOOLEAN
|
||||
KdbpRpnEvaluateParsedExpression(
|
||||
IN PVOID Expression,
|
||||
IN PKDB_KTRAP_FRAME TrapFrame,
|
||||
OUT PULONGLONG Result,
|
||||
OUT PLONG ErrOffset OPTIONAL,
|
||||
OUT PCHAR ErrMsg OPTIONAL);
|
||||
|
||||
/* from kdb_symbols.c */
|
||||
|
||||
BOOLEAN
|
||||
|
@ -33,23 +177,86 @@ KdbSymGetAddressInformation(IN PROSSYM_INFO RosSymInfo,
|
|||
OUT PCH FileName OPTIONAL,
|
||||
OUT PCH FunctionName OPTIONAL);
|
||||
|
||||
/* other functions */
|
||||
#define KdbpSafeReadMemory(dst, src, size) MmSafeCopyFromUser(dst, src, size)
|
||||
#define KdbpSafeWriteMemory(dst, src, size) MmSafeCopyToUser(dst, src, size)
|
||||
CHAR
|
||||
KdbTryGetCharKeyboard(PULONG ScanCode);
|
||||
ULONG
|
||||
KdbTryGetCharSerial(VOID);
|
||||
/* from kdb.c */
|
||||
|
||||
extern PEPROCESS KdbCurrentProcess;
|
||||
extern PETHREAD KdbCurrentThread;
|
||||
extern LONG KdbLastBreakPointNr;
|
||||
extern ULONG KdbNumSingleSteps;
|
||||
extern BOOLEAN KdbSingleStepOver;
|
||||
extern PKDB_KTRAP_FRAME KdbCurrentTrapFrame;
|
||||
|
||||
VOID
|
||||
KdbEnter(VOID);
|
||||
KdbInit();
|
||||
|
||||
VOID
|
||||
DbgRDebugInit(VOID);
|
||||
VOID
|
||||
DbgShowFiles(VOID);
|
||||
VOID
|
||||
DbgEnableFile(PCH Filename);
|
||||
VOID
|
||||
DbgDisableFile(PCH Filename);
|
||||
KdbModuleLoaded(
|
||||
IN PUNICODE_STRING Name);
|
||||
|
||||
LONG
|
||||
KdbpGetNextBreakPointNr(
|
||||
IN ULONG Start OPTIONAL);
|
||||
|
||||
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);
|
||||
|
||||
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 PULONG BreakPointNumber OPTIONAL);
|
||||
|
||||
BOOLEAN
|
||||
KdbpDeleteBreakPoint(
|
||||
IN LONG BreakPointNr OPTIONAL,
|
||||
IN OUT PKDB_BREAKPOINT BreakPoint OPTIONAL);
|
||||
|
||||
BOOLEAN
|
||||
KdbpEnableBreakPoint(
|
||||
IN LONG BreakPointNr OPTIONAL,
|
||||
IN OUT PKDB_BREAKPOINT BreakPoint OPTIONAL);
|
||||
|
||||
BOOLEAN
|
||||
KdbpDisableBreakPoint(
|
||||
IN LONG BreakPointNr OPTIONAL,
|
||||
IN OUT PKDB_BREAKPOINT BreakPoint OPTIONAL);
|
||||
|
||||
BOOLEAN
|
||||
KdbpGetEnterCondition(
|
||||
IN LONG ExceptionNr,
|
||||
IN BOOLEAN FirstChance,
|
||||
OUT KDB_ENTER_CONDITION *Condition);
|
||||
|
||||
BOOLEAN
|
||||
KdbpSetEnterCondition(
|
||||
IN LONG ExceptionNr,
|
||||
IN BOOLEAN FirstChance,
|
||||
IN KDB_ENTER_CONDITION Condition);
|
||||
|
||||
BOOLEAN
|
||||
KdbpAttachToThread(
|
||||
PVOID ThreadId);
|
||||
|
||||
BOOLEAN
|
||||
KdbpAttachToProcess(
|
||||
PVOID ProcessId);
|
||||
|
||||
/* from profile.c */
|
||||
|
||||
VOID
|
||||
KdbInitProfiling();
|
||||
VOID
|
||||
|
@ -61,13 +268,25 @@ KdbEnableProfiling();
|
|||
VOID
|
||||
KdbProfileInterrupt(ULONG_PTR Eip);
|
||||
|
||||
/* other functions */
|
||||
|
||||
#define KdbpSafeReadMemory(dst, src, size) MmSafeCopyFromUser(dst, src, size)
|
||||
#define KdbpSafeWriteMemory(dst, src, size) MmSafeCopyToUser(dst, src, size)
|
||||
CHAR
|
||||
KdbpTryGetCharKeyboard(PULONG ScanCode);
|
||||
ULONG
|
||||
KdbpTryGetCharSerial(VOID);
|
||||
VOID
|
||||
KdbModuleLoaded(IN PUNICODE_STRING Name);
|
||||
KdbEnter(VOID);
|
||||
VOID
|
||||
DbgRDebugInit(VOID);
|
||||
VOID
|
||||
DbgShowFiles(VOID);
|
||||
VOID
|
||||
DbgEnableFile(PCH Filename);
|
||||
VOID
|
||||
DbgDisableFile(PCH Filename);
|
||||
|
||||
|
||||
struct KDB_BPINFO {
|
||||
DWORD Addr;
|
||||
DWORD Type;
|
||||
DWORD Size;
|
||||
DWORD Enabled;
|
||||
};
|
||||
#endif /* NTOSKRNL_KDB_H */
|
||||
|
||||
|
|
2307
reactos/ntoskrnl/dbg/kdb_cli.c
Normal file
2307
reactos/ntoskrnl/dbg/kdb_cli.c
Normal file
File diff suppressed because it is too large
Load diff
1081
reactos/ntoskrnl/dbg/kdb_expr.c
Normal file
1081
reactos/ntoskrnl/dbg/kdb_expr.c
Normal file
File diff suppressed because it is too large
Load diff
|
@ -1,4 +1,4 @@
|
|||
/* $Id:$
|
||||
/* $Id$
|
||||
*
|
||||
* COPYRIGHT: See COPYING in the top level directory
|
||||
* PROJECT: ReactOS kernel
|
||||
|
@ -62,7 +62,7 @@ VOID KbdDisableMouse()
|
|||
}
|
||||
|
||||
CHAR
|
||||
KdbTryGetCharKeyboard(PULONG ScanCode)
|
||||
KdbpTryGetCharKeyboard(PULONG ScanCode)
|
||||
{
|
||||
static byte_t last_key = 0;
|
||||
static byte_t shift = 0;
|
||||
|
@ -305,7 +305,7 @@ static char keymap[128][2] = {
|
|||
* Yes, this is horrible.
|
||||
*/
|
||||
ULONG
|
||||
KdbTryGetCharKeyboard(VOID)
|
||||
KdbpTryGetCharKeyboard(VOID)
|
||||
{
|
||||
static unsigned shift_state, ctrl_state, meta_state;
|
||||
unsigned scan_code, ch;
|
||||
|
|
|
@ -1,4 +1,4 @@
|
|||
/* $Id:$
|
||||
/* $Id$
|
||||
*
|
||||
* COPYRIGHT: See COPYING in the top level directory
|
||||
* PROJECT: ReactOS kernel
|
||||
|
@ -20,7 +20,7 @@ extern KD_PORT_INFORMATION LogPortInfo;
|
|||
|
||||
|
||||
CHAR
|
||||
KdbTryGetCharSerial()
|
||||
KdbpTryGetCharSerial()
|
||||
{
|
||||
UCHAR Result;
|
||||
|
||||
|
|
123
reactos/ntoskrnl/dbg/kdb_string.c
Normal file
123
reactos/ntoskrnl/dbg/kdb_string.c
Normal file
|
@ -0,0 +1,123 @@
|
|||
/*
|
||||
* ReactOS kernel
|
||||
* Copyright (C) 2005 ReactOS Team
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation; either version 2 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program; if not, write to the Free Software
|
||||
* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
|
||||
*/
|
||||
/* $Id$
|
||||
*
|
||||
* PROJECT: ReactOS kernel
|
||||
* FILE: ntoskrnl/dbg/kdb_string.c
|
||||
* PURPOSE: Kernel debugger string functions
|
||||
* PROGRAMMER: Gregor Anich (blight@blight.eu.org)
|
||||
* UPDATE HISTORY:
|
||||
* Created 17/01/2005
|
||||
*/
|
||||
|
||||
/* INCLUDES ******************************************************************/
|
||||
#include <ntoskrnl.h>
|
||||
|
||||
/* FUNCTIONS *****************************************************************/
|
||||
|
||||
#if 0
|
||||
int
|
||||
_stricmp(
|
||||
const char *s1,
|
||||
const char *s2)
|
||||
{
|
||||
char c1, c2;
|
||||
for (;;)
|
||||
{
|
||||
c1 = tolower(*s1++);
|
||||
c2 = tolower(*s2++);
|
||||
if (c1 < c2)
|
||||
return -1;
|
||||
else if (c1 > c2)
|
||||
return 1;
|
||||
if (c1 == '\0')
|
||||
break;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
#endif /* unused */
|
||||
|
||||
/*
|
||||
* Convert a string to an unsigned long integer.
|
||||
*
|
||||
* Ignores `locale' stuff. Assumes that the upper and lower case
|
||||
* alphabets and digits are each contiguous.
|
||||
*/
|
||||
unsigned long
|
||||
strtoul(const char *nptr, char **endptr, int base)
|
||||
{
|
||||
const char *s = nptr;
|
||||
unsigned long acc;
|
||||
int c;
|
||||
unsigned long cutoff;
|
||||
int neg = 0, any, cutlim;
|
||||
|
||||
/*
|
||||
* See strtol for comments as to the logic used.
|
||||
*/
|
||||
do {
|
||||
c = *s++;
|
||||
} while (isspace(c));
|
||||
if (c == '-')
|
||||
{
|
||||
neg = 1;
|
||||
c = *s++;
|
||||
}
|
||||
else if (c == '+')
|
||||
c = *s++;
|
||||
if ((base == 0 || base == 16) &&
|
||||
c == '0' && (*s == 'x' || *s == 'X'))
|
||||
{
|
||||
c = s[1];
|
||||
s += 2;
|
||||
base = 16;
|
||||
}
|
||||
if (base == 0)
|
||||
base = c == '0' ? 8 : 10;
|
||||
cutoff = (unsigned long)ULONG_MAX / (unsigned long)base;
|
||||
cutlim = (unsigned long)ULONG_MAX % (unsigned long)base;
|
||||
for (acc = 0, any = 0;; c = *s++)
|
||||
{
|
||||
if (isdigit(c))
|
||||
c -= '0';
|
||||
else if (isalpha(c))
|
||||
c -= isupper(c) ? 'A' - 10 : 'a' - 10;
|
||||
else
|
||||
break;
|
||||
if (c >= base)
|
||||
break;
|
||||
if (any < 0 || acc > cutoff || (acc == cutoff && c > cutlim))
|
||||
any = -1;
|
||||
else {
|
||||
any = 1;
|
||||
acc *= base;
|
||||
acc += c;
|
||||
}
|
||||
}
|
||||
if (any < 0)
|
||||
{
|
||||
acc = ULONG_MAX;
|
||||
}
|
||||
else if (neg)
|
||||
acc = -acc;
|
||||
if (endptr != 0)
|
||||
*endptr = any ? (char *)s - 1 : (char *)nptr;
|
||||
return acc;
|
||||
}
|
||||
|
|
@ -243,12 +243,12 @@ KdbSymPrintAddress(IN PVOID Address)
|
|||
FunctionName);
|
||||
if (NT_SUCCESS(Status))
|
||||
{
|
||||
DbgPrint("<%ws: %x (%s:%d (%s))>",
|
||||
DbgPrint("<%ws:%x (%s:%d (%s))>",
|
||||
Info.Name, RelativeAddress, FileName, LineNumber, FunctionName);
|
||||
}
|
||||
else
|
||||
{
|
||||
DbgPrint("<%ws: %x>", Info.Name, RelativeAddress);
|
||||
DbgPrint("<%ws:%x>", Info.Name, RelativeAddress);
|
||||
}
|
||||
|
||||
return TRUE;
|
||||
|
@ -541,7 +541,7 @@ KdbSymFreeProcessSymbols(IN PEPROCESS Process)
|
|||
CurrentProcess = PsGetCurrentProcess();
|
||||
if (CurrentProcess != Process)
|
||||
{
|
||||
KeAttachProcess(&Process->Pcb);
|
||||
KeAttachProcess(EPROCESS_TO_KPROCESS(Process));
|
||||
}
|
||||
Peb = Process->Peb;
|
||||
ASSERT(Peb);
|
||||
|
|
|
@ -69,9 +69,11 @@
|
|||
#define KTRAP_FRAME_RESERVED9 (0x8A)
|
||||
#define KTRAP_FRAME_SIZE (0x8C)
|
||||
|
||||
#define X86_EFLAGS_TF 0x00000100 /* Trap flag */
|
||||
#define X86_EFLAGS_IF 0x00000200 /* Interrupt Enable flag */
|
||||
#define X86_EFLAGS_IOPL 0x00003000 /* I/O Privilege Level bits */
|
||||
#define X86_EFLAGS_NT 0x00004000 /* Nested Task flag */
|
||||
#define X86_EFLAGS_RF 0x00010000 /* Resume flag */
|
||||
#define X86_EFLAGS_VM 0x00020000 /* Virtual Mode */
|
||||
#define X86_EFLAGS_ID 0x00200000 /* CPUID detection flag */
|
||||
|
||||
|
|
|
@ -98,9 +98,6 @@ KdGdbDebugPrint (LPSTR Message);
|
|||
VOID
|
||||
KdDebugPrint (LPSTR Message);
|
||||
|
||||
VOID
|
||||
KdbCreateThreadHook(PCONTEXT Context);
|
||||
|
||||
KD_CONTINUE_TYPE
|
||||
KdEnterDebuggerException(PEXCEPTION_RECORD ExceptionRecord,
|
||||
PCONTEXT Context,
|
||||
|
@ -118,7 +115,7 @@ VOID KdPrintMda(PCH pch);
|
|||
# define KDB_CREATE_THREAD_HOOK(CONTEXT) do { } while (0)
|
||||
#else
|
||||
# define KDB_LOADUSERMODULE_HOOK(LDRMOD) KdbSymLoadUserModuleSymbols(LDRMOD)
|
||||
# define KDB_DELETEPROCESS_HOOK(PROCESS) KdbSymFreeProcessSymbols(PROCESS)
|
||||
# define KDB_DELETEPROCESS_HOOK(PROCESS) KdbDeleteProcessHook(PROCESS)
|
||||
# define KDB_LOADDRIVER_HOOK(FILENAME, MODULE) KdbSymLoadDriverSymbols(FILENAME, MODULE)
|
||||
# define KDB_UNLOADDRIVER_HOOK(MODULE) KdbSymUnloadDriverSymbols(MODULE)
|
||||
# define KDB_LOADERINIT_HOOK(NTOS, HAL) KdbSymInit(NTOS, HAL)
|
||||
|
@ -126,6 +123,9 @@ VOID KdPrintMda(PCH pch);
|
|||
/*#define KDB_CREATE_THREAD_HOOK(CONTEXT) \
|
||||
KdbCreateThreadHook(CONTEXT)
|
||||
*/
|
||||
VOID
|
||||
KdbDeleteProcessHook(IN PEPROCESS Process);
|
||||
|
||||
VOID
|
||||
KdbSymLoadUserModuleSymbols(IN PLDR_MODULE LdrModule);
|
||||
|
||||
|
@ -155,7 +155,7 @@ KdbEnterDebuggerException(PEXCEPTION_RECORD ExceptionRecord,
|
|||
KPROCESSOR_MODE PreviousMode,
|
||||
PCONTEXT Context,
|
||||
PKTRAP_FRAME TrapFrame,
|
||||
BOOLEAN HandleAlways);
|
||||
BOOLEAN FirstChance);
|
||||
|
||||
#endif /* KDBG || DBG */
|
||||
|
||||
|
|
|
@ -81,7 +81,7 @@ KiDispatchException(PEXCEPTION_RECORD ExceptionRecord,
|
|||
|
||||
#ifdef KDBG
|
||||
Action = KdbEnterDebuggerException (ExceptionRecord, PreviousMode,
|
||||
Context, Tf, FALSE);
|
||||
Context, Tf, TRUE);
|
||||
if (Action == kdContinue)
|
||||
{
|
||||
return;
|
||||
|
@ -131,7 +131,7 @@ KiDispatchException(PEXCEPTION_RECORD ExceptionRecord,
|
|||
|
||||
#ifdef KDBG
|
||||
Action = KdbEnterDebuggerException (ExceptionRecord, PreviousMode,
|
||||
Context, Tf, TRUE);
|
||||
Context, Tf, FALSE);
|
||||
if (Action == kdContinue)
|
||||
{
|
||||
return;
|
||||
|
@ -147,7 +147,7 @@ KiDispatchException(PEXCEPTION_RECORD ExceptionRecord,
|
|||
/* PreviousMode == KernelMode */
|
||||
#ifdef KDBG
|
||||
Action = KdbEnterDebuggerException (ExceptionRecord, PreviousMode,
|
||||
Context, Tf, FALSE);
|
||||
Context, Tf, TRUE);
|
||||
if (Action == kdContinue)
|
||||
{
|
||||
return;
|
||||
|
@ -168,7 +168,7 @@ KiDispatchException(PEXCEPTION_RECORD ExceptionRecord,
|
|||
ExceptionRecord->ExceptionAddress );
|
||||
#ifdef KDBG
|
||||
Action = KdbEnterDebuggerException (ExceptionRecord, PreviousMode,
|
||||
Context, Tf, TRUE);
|
||||
Context, Tf, FALSE);
|
||||
if (Action == kdContinue)
|
||||
{
|
||||
return;
|
||||
|
|
|
@ -26,7 +26,9 @@
|
|||
|
||||
/* INCLUDES ******************************************************************/
|
||||
|
||||
#include <roscfg.h>
|
||||
#include <ddk/status.h>
|
||||
#include <internal/i386/ke.h>
|
||||
#include <internal/i386/segment.h>
|
||||
#include <internal/ps.h>
|
||||
#include <ddk/defines.h>
|
||||
|
@ -74,6 +76,29 @@ _KiTrapRet:
|
|||
popl %edi
|
||||
popl %esi
|
||||
popl %ebx
|
||||
|
||||
#ifdef DBG
|
||||
/*
|
||||
* Cleanup the stack which was used to setup a trapframe with SS:ESP when called
|
||||
* from kmode.
|
||||
*/
|
||||
movw 0xC(%esp), %bp /* Get CS from trapframe */
|
||||
cmpw $KERNEL_CS, %bp
|
||||
jne 0f
|
||||
|
||||
/* Copy EBP, CS:EIP and EFLAGS from the trapframe back onto the top of our stack. */
|
||||
movl 0x00(%esp), %ebp /* EBP */
|
||||
movl %ebp, 0x24(%esp)
|
||||
movl 0x08(%esp), %ebp /* EIP */
|
||||
movl %ebp, 0x2C(%esp)
|
||||
movl 0x0C(%esp), %ebp /* CS */
|
||||
movl %ebp, 0x30(%esp)
|
||||
movl 0x10(%esp), %ebp /* EFLAGS */
|
||||
movl %ebp, 0x34(%esp)
|
||||
|
||||
addl $0x24, %esp
|
||||
0:
|
||||
#endif /* DBG */
|
||||
popl %ebp
|
||||
addl $0x4, %esp /* Ignore error code */
|
||||
|
||||
|
@ -81,10 +106,32 @@ _KiTrapRet:
|
|||
|
||||
.globl _KiTrapProlog
|
||||
_KiTrapProlog:
|
||||
#ifdef DBG
|
||||
/*
|
||||
* If we were called from kmode we start setting up a new trapframe (with SS:ESP at the end)
|
||||
*/
|
||||
movw 0x14(%esp), %bx /* Get old CS */
|
||||
cmpw $KERNEL_CS, %bx
|
||||
|
||||
jne 0f
|
||||
|
||||
leal 0x1C(%esp), %ebp
|
||||
pushl %ss /* Old SS */
|
||||
pushl %ebp /* Old ESP */
|
||||
pushl 0x20(%esp) /* Old EFLAGS */
|
||||
pushl 0x20(%esp) /* Old CS */
|
||||
pushl 0x20(%esp) /* Old EIP */
|
||||
pushl 0x20(%esp) /* ErrorCode */
|
||||
pushl 0x20(%esp) /* Ebp */
|
||||
pushl 0x20(%esp) /* Ebx */
|
||||
pushl 0x20(%esp) /* Esi */
|
||||
0:
|
||||
#endif /* DBG */
|
||||
|
||||
pushl %edi
|
||||
pushl %fs
|
||||
|
||||
/*
|
||||
/*
|
||||
* Check that the PCR exists, very early in the boot process it may
|
||||
* not
|
||||
*/
|
||||
|
|
|
@ -45,6 +45,10 @@ _Ki386ContextSwitch:
|
|||
* Thread = Thread to switch to
|
||||
* OldThread = Thread to switch from
|
||||
*/
|
||||
#ifdef KDBG
|
||||
jmp SaveTrapFrameForKDB
|
||||
SaveTrapFrameForKDB_Return:
|
||||
#endif
|
||||
pushl %ebp
|
||||
movl %esp, %ebp
|
||||
|
||||
|
@ -218,3 +222,128 @@ _Ki386ContextSwitch:
|
|||
ret
|
||||
.endfunc
|
||||
|
||||
|
||||
|
||||
#ifdef KDBG
|
||||
|
||||
SaveTrapFrameForKDB:
|
||||
/*
|
||||
* Set up a trap frame.
|
||||
*/
|
||||
/* Ss - space already reserved by return EIP */
|
||||
pushl %esp /* Esp */
|
||||
pushfl /* Eflags */
|
||||
pushl %cs /* Cs */
|
||||
pushl 12(%esp) /* Eip */
|
||||
movl %ss, 16(%esp) /* Save Ss */
|
||||
pushl $0 /* ErrorCode */
|
||||
pushl %ebp /* Ebp */
|
||||
pushl %ebx /* Ebx */
|
||||
pushl %esi /* Esi */
|
||||
pushl %edi /* Edi */
|
||||
pushl %fs /* Fs */
|
||||
pushl $0 /* ExceptionList */
|
||||
pushl $0 /* PreviousMode */
|
||||
pushl %eax /* Eax */
|
||||
pushl %ecx /* Ecx */
|
||||
pushl %edx /* Edx */
|
||||
pushl %ds /* Ds */
|
||||
pushl %es /* Es */
|
||||
pushl %gs /* Gs */
|
||||
movl %dr7, %eax
|
||||
pushl %eax /* Dr7 */
|
||||
/* Clear breakpoint enables in dr7. */
|
||||
andl $~0xffff, %eax
|
||||
movl %eax, %dr7
|
||||
movl %dr6, %eax
|
||||
pushl %eax /* Dr6 */
|
||||
movl %dr3, %eax
|
||||
pushl %eax /* Dr3 */
|
||||
movl %dr2, %eax
|
||||
pushl %eax /* Dr2 */
|
||||
movl %dr1, %eax
|
||||
pushl %eax /* Dr1 */
|
||||
movl %dr0, %eax
|
||||
pushl %eax /* Dr0 */
|
||||
pushl $0 /* TempEip */
|
||||
pushl $0 /* TempCs */
|
||||
pushl $0 /* DebugPointer */
|
||||
pushl $0xffffffff /* DebugArgMark (Exception number) */
|
||||
pushl 0x60(%esp) /* DebugEip */
|
||||
pushl %ebp /* DebugEbp */
|
||||
|
||||
movl %esp, %ebp /* Save pointer to new TrapFrame */
|
||||
|
||||
/* Save the old trapframe and set pointer to the new one */
|
||||
movl 0x80(%esp), %ebx /* Get pointer to OldThread */
|
||||
pushl KTHREAD_TRAP_FRAME(%ebx)
|
||||
movl %ebp, KTHREAD_TRAP_FRAME(%ebx)
|
||||
|
||||
/* Copy the arguments which were passed to Ki386ContextSwitch */
|
||||
pushl 0x80(%ebp) /* OldThread */
|
||||
pushl 0x7c(%ebp) /* NewThread */
|
||||
pushl $RestoreTrapFrameForKDB /* Return address */
|
||||
|
||||
/* Restore clobbered registers */
|
||||
movl KTRAP_FRAME_EBX(%ebp), %ebx
|
||||
movl KTRAP_FRAME_EBP(%ebp), %ebp
|
||||
|
||||
/* Return */
|
||||
jmp SaveTrapFrameForKDB_Return
|
||||
|
||||
|
||||
RestoreTrapFrameForKDB:
|
||||
addl $8, %esp /* Remove NewThread and OldThread arguments from the stack */
|
||||
movl 0x84(%esp), %ebx /* Get pointer to OldThread */
|
||||
|
||||
/* Restore the old trapframe */
|
||||
popl KTHREAD_TRAP_FRAME(%ebx)
|
||||
|
||||
/*
|
||||
* Pop unused portions of the trap frame:
|
||||
* DebugEbp
|
||||
* DebugEip
|
||||
* DebugArgMark
|
||||
* DebugPointer
|
||||
* TempCs
|
||||
* TempEip
|
||||
* Dr0-3
|
||||
* Dr6-7
|
||||
*/
|
||||
addl $(12*4), %esp
|
||||
|
||||
/*
|
||||
* Restore registers including any that might have been changed
|
||||
* inside the debugger.
|
||||
*/
|
||||
popl %gs /* Gs */
|
||||
popl %es /* Es */
|
||||
popl %ds /* Ds */
|
||||
popl %edx /* Edx */
|
||||
popl %ecx /* Ecx */
|
||||
popl %eax /* Eax */
|
||||
addl $4, %esp /* PreviousMode */
|
||||
addl $4, %esp /* ExceptionList */
|
||||
popl %fs /* Fs */
|
||||
popl %edi /* Edi */
|
||||
popl %esi /* Esi */
|
||||
popl %ebx /* Ebx */
|
||||
|
||||
/* Remove SS:ESP from the stack */
|
||||
movl 16(%esp), %ebp
|
||||
movl %ebp, 24(%esp)
|
||||
movl 12(%esp), %ebp
|
||||
movl %ebp, 20(%esp)
|
||||
movl 8(%esp), %ebp
|
||||
movl %ebp, 16(%esp)
|
||||
|
||||
popl %ebp /* Ebp */
|
||||
addl $12, %esp /* ErrorCode and SS:ESP */
|
||||
|
||||
/*
|
||||
* Return to the caller.
|
||||
*/
|
||||
iret
|
||||
|
||||
#endif /* KDBG */
|
||||
|
||||
|
|
|
@ -236,10 +236,7 @@ KeInitializeThread(PKPROCESS Process, PKTHREAD Thread, BOOLEAN First)
|
|||
Thread->Alerted[0] = 0;
|
||||
Thread->Alerted[1] = 0;
|
||||
Thread->Iopl = 0;
|
||||
/*
|
||||
* FIXME: Think how this might work
|
||||
*/
|
||||
Thread->NpxState = 0;
|
||||
Thread->NpxState = NPX_STATE_INVALID;
|
||||
|
||||
Thread->Saturation = 0;
|
||||
Thread->Priority = Process->BasePriority;
|
||||
|
@ -262,7 +259,7 @@ KeInitializeThread(PKPROCESS Process, PKTHREAD Thread, BOOLEAN First)
|
|||
Thread->DecrementCount = 0;
|
||||
Thread->PriorityDecrement = 0;
|
||||
Thread->Quantum = Process->ThreadQuantum;
|
||||
memset(Thread->WaitBlock, 0, sizeof(KWAIT_BLOCK)*4);
|
||||
RtlZeroMemory(Thread->WaitBlock, sizeof(KWAIT_BLOCK)*4);
|
||||
Thread->LegoData = 0;
|
||||
Thread->UserAffinity = Process->Affinity;
|
||||
Thread->SystemAffinityActive = 0;
|
||||
|
@ -271,7 +268,7 @@ KeInitializeThread(PKPROCESS Process, PKTHREAD Thread, BOOLEAN First)
|
|||
Thread->ServiceTable = KeServiceDescriptorTable;
|
||||
Thread->Queue = NULL;
|
||||
KeInitializeSpinLock(&Thread->ApcQueueLock);
|
||||
memset(&Thread->Timer, 0, sizeof(KTIMER));
|
||||
RtlZeroMemory(&Thread->Timer, sizeof(KTIMER));
|
||||
KeInitializeTimer(&Thread->Timer);
|
||||
Thread->QueueListEntry.Flink = NULL;
|
||||
Thread->QueueListEntry.Blink = NULL;
|
||||
|
@ -291,7 +288,7 @@ KeInitializeThread(PKPROCESS Process, PKTHREAD Thread, BOOLEAN First)
|
|||
Thread->PreviousMode = KernelMode;
|
||||
Thread->KernelTime = 0;
|
||||
Thread->UserTime = 0;
|
||||
memset(&Thread->SavedApcState, 0, sizeof(KAPC_STATE));
|
||||
RtlZeroMemory(&Thread->SavedApcState, sizeof(KAPC_STATE));
|
||||
|
||||
Thread->ApcStateIndex = OriginalApcEnvironment;
|
||||
Thread->ApcQueueable = TRUE;
|
||||
|
|
|
@ -697,6 +697,7 @@ ExpInitializeExecutive(VOID)
|
|||
}
|
||||
|
||||
#if defined(KDBG) || defined(DBG)
|
||||
KdbInit();
|
||||
KdbInitProfiling2();
|
||||
#endif /* KDBG */
|
||||
|
||||
|
|
|
@ -120,7 +120,7 @@ NtCallbackReturn (PVOID Result,
|
|||
else
|
||||
{
|
||||
*CallerResultLength = min(ResultLength, *CallerResultLength);
|
||||
memcpy(*CallerResult, Result, *CallerResultLength);
|
||||
RtlCopyMemory(*CallerResult, Result, *CallerResultLength);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -131,9 +131,9 @@ NtCallbackReturn (PVOID Result,
|
|||
if ((Thread->Tcb.NpxState & NPX_STATE_VALID) &&
|
||||
ETHREAD_TO_KTHREAD(Thread) != KeGetCurrentKPCR()->PrcbData.NpxThread)
|
||||
{
|
||||
memcpy((char*)InitialStack - sizeof(FX_SAVE_AREA),
|
||||
(char*)Thread->Tcb.InitialStack - sizeof(FX_SAVE_AREA),
|
||||
sizeof(FX_SAVE_AREA));
|
||||
RtlCopyMemory((char*)InitialStack - sizeof(FX_SAVE_AREA),
|
||||
(char*)Thread->Tcb.InitialStack - sizeof(FX_SAVE_AREA),
|
||||
sizeof(FX_SAVE_AREA));
|
||||
}
|
||||
Thread->Tcb.InitialStack = InitialStack;
|
||||
Thread->Tcb.StackBase = StackBase;
|
||||
|
@ -289,11 +289,11 @@ NtW32Call (IN ULONG RoutineIndex,
|
|||
AssignedStack = CONTAINING_RECORD(StackEntry, NTW32CALL_CALLBACK_STACK,
|
||||
ListEntry);
|
||||
NewStack = AssignedStack->BaseAddress;
|
||||
memset(NewStack, 0, StackSize);
|
||||
RtlZeroMemory(NewStack, StackSize);
|
||||
}
|
||||
/* FIXME: Need to check whether we were interrupted from v86 mode. */
|
||||
memcpy((char*)NewStack + StackSize - sizeof(KTRAP_FRAME) - sizeof(FX_SAVE_AREA),
|
||||
Thread->Tcb.TrapFrame, sizeof(KTRAP_FRAME) - (4 * sizeof(DWORD)));
|
||||
RtlCopyMemory((char*)NewStack + StackSize - sizeof(KTRAP_FRAME) - sizeof(FX_SAVE_AREA),
|
||||
Thread->Tcb.TrapFrame, sizeof(KTRAP_FRAME) - (4 * sizeof(DWORD)));
|
||||
NewFrame = (PKTRAP_FRAME)((char*)NewStack + StackSize - sizeof(KTRAP_FRAME) - sizeof(FX_SAVE_AREA));
|
||||
/* We need the stack pointer to remain 4-byte aligned */
|
||||
NewFrame->Esp -= (((ArgumentLength + 3) & (~ 0x3)) + (4 * sizeof(ULONG)));
|
||||
|
@ -303,7 +303,7 @@ NtW32Call (IN ULONG RoutineIndex,
|
|||
UserEsp[1] = RoutineIndex;
|
||||
UserEsp[2] = (ULONG)&UserEsp[4];
|
||||
UserEsp[3] = ArgumentLength;
|
||||
memcpy((PVOID)&UserEsp[4], Argument, ArgumentLength);
|
||||
RtlCopyMemory((PVOID)&UserEsp[4], Argument, ArgumentLength);
|
||||
|
||||
/* Switch to the new environment and return to user-mode. */
|
||||
KeRaiseIrql(HIGH_LEVEL, &oldIrql);
|
||||
|
@ -319,9 +319,9 @@ NtW32Call (IN ULONG RoutineIndex,
|
|||
if ((Thread->Tcb.NpxState & NPX_STATE_VALID) &&
|
||||
ETHREAD_TO_KTHREAD(Thread) != KeGetCurrentKPCR()->PrcbData.NpxThread)
|
||||
{
|
||||
memcpy((char*)NewStack + StackSize - sizeof(FX_SAVE_AREA),
|
||||
(char*)SavedState.SavedInitialStack - sizeof(FX_SAVE_AREA),
|
||||
sizeof(FX_SAVE_AREA));
|
||||
RtlCopyMemory((char*)NewStack + StackSize - sizeof(FX_SAVE_AREA),
|
||||
(char*)SavedState.SavedInitialStack - sizeof(FX_SAVE_AREA),
|
||||
sizeof(FX_SAVE_AREA));
|
||||
}
|
||||
Thread->Tcb.InitialStack = Thread->Tcb.StackBase = (char*)NewStack + StackSize;
|
||||
Thread->Tcb.StackLimit = (ULONG)NewStack;
|
||||
|
|
Loading…
Reference in a new issue