📄 shell.c
字号:
BOOLEAN ReinstallPermanentBp = FALSE;
DPRINT((0,"reason: %u#################################################################\n", dwReasonForBreak));
ENTER_FUNC();
// in handler
bInDebuggerShell = TRUE;
bStepping = FALSE;
// don't assume we must call original handlers yet
dwCallOldInt1Handler = dwCallOldInt3Handler = dwCallOldIntEHandler = dwCallOldGPFaultHandler = 0;
bSkipMainLoop = FALSE;
bEnterNow = FALSE;
// reset trace flag (TF) on the stack
CurrentEFL&=(~0x100);
InstallPrintkHook();
// control is not depressed
bControl=FALSE;
bIrqStateAtBreak = ((CurrentEFL&(1<<9))!=0);
DPRINT((0,"\nbInDebuggerShell %x, dwReasonForBreak: %x, bIrqStateAtBreak: %d\n", bInDebuggerShell, dwReasonForBreak, bIrqStateAtBreak));
DPRINT((0,"CurrentEIP: %x, CurrentESP: %x\n", CurrentEIP, CurrentESP));
// came in because TF flag was set
if(dwReasonForBreak == REASON_SINGLESTEP)
{
ULONG ulAddress,ulAddressCurrent;
DPRINT((0,"REASON_SINGLESTEP: bSingleStep: %u\n", bSingleStep));
if(!bSingleStep)
{
dwCallOldInt1Handler = 1;
DPRINT((0,"no single step requested: %u!\n", dwCallOldInt1Handler));
goto common_return_point;
}
ulAddress = GetLinearAddress(OldCS,OldEIP);
ulAddressCurrent = GetLinearAddress(CurrentCS,CurrentEIP);
// if we came in because we needed to skip past a permanent
// INT3 hook, we need to put the INT3 back in place and
// simply restart the system.
if(NeedToReInstallSWBreakpoints(ulAddress,TRUE) )
{
DPRINT((0,"reinstalling INT3 @ %.4X:%.8X\n",OldCS,OldEIP));
ReInstallSWBreakpoint(ulAddress);
// previous command was go i.e. we did not single-step over a location
// where a permanent breakpoint was installed (Printk() etc.) we simply restart
// else we must stop the system.
if(bPreviousCommandWasGo)
{
bPreviousCommandWasGo = FALSE;
bInDebuggerShell = FALSE;
if(bStepThroughSource)
{
// set TF flag
CurrentEFL |= 0x100;
}
LEAVE_FUNC();
DPRINT((0,"singlestep-----------------------------------------------------------------\n"));
return;
}
bPreviousCommandWasGo = FALSE;
}
if(IsSwBpAtAddressInstalled(ulAddressCurrent))
DeInstallSWBreakpoint(ulAddressCurrent);
// we came here while stepping through source code block
if(bStepThroughSource)
{
ULONG ulLineNumber;
LPSTR pSrc,pFileName;
DPRINT((0,"RealIsr(): stepping through source!\n"));
// look up the corresponding source line
// if there isn't any or the source line number has changed
// we break back into the debugger
if(bShowSrc)
pSrc = FindSourceLineForAddress(ulAddressCurrent,&ulLineNumber,NULL,NULL,&pFileName);
else pSrc = NULL;
DPRINT((0,"RealIsr(): line #%u pSrc=%x (old line #%u)\n",ulLineNumber,(ULONG)pSrc,g_ulLineNumberStart));
// if we have found a source line there
if(pSrc && ulLineNumber==g_ulLineNumberStart)
{
DPRINT((0,"RealIsr(): stepping through line #%u in file = %s!\n",ulLineNumber,pFileName));
if(bStepInto)
StepInto(NULL);
else
StepOver(NULL);
bInDebuggerShell = FALSE;
LEAVE_FUNC();
DPRINT((0,"singstep-----------------------------------------------------------------\n"));
return;
}
bStepThroughSource = FALSE;
bNotifyToExit = FALSE;
bSkipMainLoop = FALSE;
}
}
// came in because hardware register triggered a breakpoint
else if(dwReasonForBreak == REASON_HARDWARE_BP)
{
ULONG ulReason;
DPRINT((0,"REASON_HARDWARE_BP\n"));
// disable HW breakpoints
__asm__("\n\t \
movl %%dr6,%%eax\n\t \
movl %%eax,%0\n\t \
xorl %%eax,%%eax\n\t \
movl %%eax,%%dr6\n\t \
movl %%eax,%%dr7"
:"=m" (ulReason)
:
:"eax"
);
DPRINT((0,"REASON_HARDWARE_BP: %x\n",(ulReason&0xF)));
// HW breakpoint DR1 (skip: only used in init_module detection)
if(ulReason&0x2)
{
CurrentEFL |=(1<<16); // set resume flag
bSkipMainLoop = TRUE;
TryToInstallVirtualSWBreakpoints();
}
// HW breakpoint DR0
else if(ulReason&0x1)
{
ULONG ulAddressCurrent;
ulAddressCurrent = GetLinearAddress(CurrentCS,CurrentEIP);
// we came here while stepping through source code block
if(bStepThroughSource)
{
ULONG ulLineNumber;
LPSTR pSrc,pFileName;
DPRINT((0,"RealIsr(): stepping through source! [2]\n"));
// look up the corresponding source line
// if there isn't any or the source line number has changed
// we break back into the debugger
if(bShowSrc)
pSrc = FindSourceLineForAddress(ulAddressCurrent,&ulLineNumber,NULL,NULL,&pFileName);
else
pSrc = NULL;
DPRINT((0,"RealIsr(): line #%u pSrc=%x (old line #%u) [2]\n",ulLineNumber,(ULONG)pSrc,g_ulLineNumberStart));
// if we have found a source line there
if(pSrc && ulLineNumber==g_ulLineNumberStart)
{
DPRINT((0,"RealIsr(): stepping through line #%u in file = %s! [2]\n",ulLineNumber,pFileName));
if(bStepInto)
StepInto(NULL);
else
StepOver(NULL);
bInDebuggerShell = FALSE;
LEAVE_FUNC();
DPRINT((0,"rrr-----------------------------------------------------------------\n"));
return;
}
bNotifyToExit = FALSE;
bSkipMainLoop = FALSE;
bStepThroughSource = FALSE;
}
}
}
else if(dwReasonForBreak==REASON_INT3)
{
ULONG ulAddress;
DPRINT((0,"REASON_INT3\n"));
// must subtract one cause INT3s are generated after instructions execution
CurrentEIP--;
// make a flat address
ulAddress = GetLinearAddress(CurrentCS,CurrentEIP);
DPRINT((0,"INT3 @ %.8X\n",ulAddress));
// if there's a breakpoint installed at current EIP remove it
if(DeInstallSWBreakpoint(ulAddress) )
{
PSW_BP p;
DPRINT((0,"INT3 @ %.8X removed\n",ulAddress));
// if it's permanent (must be Printk() ) skip the DebuggerShell() and
// do a callback
if( (p = IsPermanentSWBreakpoint(ulAddress)) )
{
DPRINT((0,"permanent breakpoint\n"));
ReinstallPermanentBp = TRUE;
OldCS = CurrentCS;
OldEIP = CurrentEIP;
bSkipMainLoop = TRUE;
DPRINT((0,"callback at %x\n",p->Callback));
if(p->Callback)
p->Callback();
}
else
{
LPSTR pFind;
if(ScanExportsByAddress(&pFind,GetLinearAddress(CurrentCS,CurrentEIP)))
{
PICE_sprintf(tempShell,"pICE: SW Breakpoint at %s (%.4X:%.8X)\n",pFind,CurrentCS,CurrentEIP);
}
else
{
PICE_sprintf(tempShell,"pICE: SW Breakpoint at %.4X:%.8X\n",CurrentCS,CurrentEIP);
}
Print(OUTPUT_WINDOW,tempShell);
}
CurrentEFL &= ~(1<<16); // clear resume flag
}
else
{
LPSTR pFind;
PEPROCESS my_current = IoGetCurrentProcess();
DPRINT((0,"can't deinstall, somebody else's breakpoint\n"));
// if no other debugger is running on this process and the address is
// above TASK_SIZE we assume this to be a hard embedded INT3
/*
#if REAL_LINUX_VERSION_CODE < 0x020400
if(ulAddress<TASK_SIZE && !(my_current->flags & PF_PTRACED) )
#else
if(ulAddress<TASK_SIZE && !(my_current->ptrace & PT_PTRACED) )
#endif
*/
if( ulAddress )
{
if(ScanExportsByAddress(&pFind,GetLinearAddress(CurrentCS,CurrentEIP)))
{
PICE_sprintf(tempShell,"pICE: break due to embedded INT 3 at %s (%.4X:%.8X)\n",pFind,CurrentCS,CurrentEIP);
}
else
{
PICE_sprintf(tempShell,"pICE: break due to embedded INT 3 at user-mode address %.4X:%.8X\n",CurrentCS,CurrentEIP);
}
Print(OUTPUT_WINDOW,tempShell);
CurrentEFL &= ~(1<<16); // clear resume flag
}
// well someone is already debugging this, we must pass the INT3 on to old handler
// but only when it's a user-mode address
/*
else
{
if(ulAddress<TASK_SIZE || !bInt3Here)
{
DPRINT((0,"SW Breakpoint but debugged by other process at %.4X:%.8X\n",CurrentCS,CurrentEIP));
// call the old handler on return from RealIsr()
dwCallOldInt3Handler = 1;
// and skip DebuggerShell()
bSkipMainLoop = TRUE;
}
else
{
if(ScanExportsByAddress(&pFind,GetLinearAddress(CurrentCS,CurrentEIP)))
{
PICE_sprintf(tempShell,"pICE: break due to embedded INT 3 at (%s) %.4X:%.8X\n",
pFind,CurrentCS,CurrentEIP);
}
else
{
PICE_sprintf(tempShell,"pICE: break due to embedded INT 3 at kernel-mode address %.4X:%.8X\n",
CurrentCS,CurrentEIP);
}
Print(OUTPUT_WINDOW,tempShell);
CurrentEFL &= ~(1<<16); // clear resume flag
}
}
*/
// skip INT3
CurrentEIP++;
}
}
else if(dwReasonForBreak == REASON_PAGEFAULT)
{
LPSTR pSymbolName;
DPRINT((0,"REASON_PAGEFAULT\n"));
if( ScanExportsByAddress(&pSymbolName,GetLinearAddress(CurrentCS,CurrentEIP)) )
{
PICE_sprintf(tempShell,"pICE: Breakpoint due to page fault at %.4X:%.8X (%s)\n",CurrentCS,CurrentEIP,pSymbolName);
}
else
{
PICE_sprintf(tempShell,"pICE: Breakpoint due to page fault at %.4X:%.8X\n",CurrentCS,CurrentEIP);
}
Print(OUTPUT_WINDOW,tempShell);
PICE_sprintf(tempShell,"pICE: memory referenced %x\n",CurrentCR2);
Print(OUTPUT_WINDOW,tempShell);
dwCallOldIntEHandler = 1;
}
else if(dwReasonForBreak == REASON_GP_FAULT)
{
LPSTR pSymbolName;
DPRINT((0,"REASON_GPFAULT\n"));
if( ScanExportsByAddress(&pSymbolName,GetLinearAddress(CurrentCS,CurrentEIP)) )
{
PICE_sprintf(tempShell,"pICE: Breakpoint due to general protection fault at %.4X:%.8X (%s)\n",CurrentCS,CurrentEIP,pSymbolName);
}
else
{
PICE_sprintf(tempShell,"pICE: Breakpoint due to general protection fault at %.4X:%.8X\n",CurrentCS,CurrentEIP);
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -