/*++ Copyright (c) 1998-2001 Klaus P. Gerlicher Module Name: parse.c Abstract: execution of debugger commands Environment: Kernel mode only Author: Klaus P. Gerlicher Revision History: 19-Aug-1998: created 15-Nov-2000: general cleanup of source files Copyright notice: This file may be distributed under the terms of the GNU Public License. --*/ //////////////////////////////////////////////////// // INCLUDES //// #include "remods.h" #include "precomp.h" #include "pci_ids.h" /////////////////////////////////////////////////// // GLOBALS ULONG ValueTrue=1,ValueFalse=0; ULONG ulLastDisassStartAddress=0,ulLastDisassEndAddress=0,ulLastInvertedAddress=0; USHORT gCurrentSelector=0; ULONG gCurrentOffset=0; LONG ulCurrentlyDisplayedLineNumber=0; USHORT usOldDisasmSegment = 0; ULONG ulOldDisasmOffset = 0; static ULONG ulCountForWaitKey = 0; extern PDEBUG_MODULE pdebug_module_head; extern PDEBUG_MODULE pdebug_module_tail; //extern unsigned long sys_call_table[]; BOOLEAN (*DisplayMemory)(PARGS) = DisplayMemoryDword; char szCurrentFile[256]=""; PDEBUG_MODULE pCurrentMod=NULL; PICE_SYMBOLFILE_HEADER* pCurrentSymbols=NULL; // suppresses passing on of function keys while stepping code BOOLEAN bStepping = FALSE; BOOLEAN bInt3Here = TRUE; BOOLEAN bInt1Here = TRUE; KEYWORDS RegKeyWords[]={ {"eax",&CurrentEAX,sizeof(ULONG)}, {"ebx",&CurrentEBX,sizeof(ULONG)}, {"ecx",&CurrentECX,sizeof(ULONG)}, {"edx",&CurrentEDX,sizeof(ULONG)}, {"edi",&CurrentEDI,sizeof(ULONG)}, {"esi",&CurrentESI,sizeof(ULONG)}, {"ebp",&CurrentEBP,sizeof(ULONG)}, {"esp",&CurrentESP,sizeof(ULONG)}, {"eip",&CurrentEIP,sizeof(ULONG)}, {NULL,0,0} }; KEYWORDS SelectorRegKeyWords[]={ {"cs",&CurrentCS,sizeof(USHORT)}, {"ds",&CurrentDS,sizeof(USHORT)}, {"es",&CurrentES,sizeof(USHORT)}, {"fs",&CurrentFS,sizeof(USHORT)}, {"gs",&CurrentGS,sizeof(USHORT)}, {"ss",&CurrentSS,sizeof(USHORT)}, {NULL,0,0} }; KEYWORDS OnOffKeyWords[]={ {"on",&ValueTrue,sizeof(ULONG)}, {"off",&ValueFalse,sizeof(ULONG)}, {NULL,0,0} }; KEYWORDS SpecialKeyWords[]={ {"process",&CurrentProcess,sizeof(ULONG)}, {NULL,0,0} }; LPSTR LocalVarRegs[]= { "EAX", "ECX", "EDX", "EBX", "ESP", "EBP", "ESI", "EDI", "EIP", "EFL", "CS", "SS", "DS", "ES", "FS", "GS" }; #define COMMAND_HAS_NO_PARAMS (0) #define COMMAND_HAS_PARAMS (1<<0) #define COMMAND_HAS_SWITCHES (1<<1) // #define PARAM_CAN_BE_SYMBOLIC (1<<0) #define PARAM_CAN_BE_SEG_OFFSET (1<<1) #define PARAM_CAN_BE_MODULE (1<<2) #define PARAM_CAN_BE_PRNAME (1<<3) #define PARAM_CAN_BE_PID (1<<4) #define PARAM_CAN_BE_SRC_FILE (1<<5) #define PARAM_CAN_BE_NUMERIC (1<<6) #define PARAM_CAN_BE_REG_KEYWORD (1<<7) #define PARAM_CAN_BE_ONOFF_KEYWORD (1<<8) #define PARAM_CAN_BE_SPECIAL_KEYWORD (1<<9) #define PARAM_CAN_BE_ASTERISK (1<<10) #define PARAM_CAN_BE_ONOFF (1<<11) #define PARAM_CAN_BE_VIRTUAL_SYMBOLIC (1<<12) #define PARAM_CAN_BE_SRCLINE (1<<13) #define PARAM_CAN_BE_PARTIAL_SYM_NAME (1<<14) #define PARAM_CAN_BE_ANY_STRING (1<<15) #define PARAM_CAN_BE_DECIMAL (1<<16) #define PARAM_CAN_BE_SIZE_DESC (1<<17) #define PARAM_CAN_BE_LETTER (1<<18) // #define COMMAND_GROUP_HELP (0) #define COMMAND_GROUP_FLOW (1) #define COMMAND_GROUP_STRUCT (2) #define COMMAND_GROUP_OS (3) #define COMMAND_GROUP_MEM (4) #define COMMAND_GROUP_BREAKPOINT (5) #define COMMAND_GROUP_WINDOW (6) #define COMMAND_GROUP_DEBUG (7) #define COMMAND_GROUP_INFO (8) #define COMMAND_GROUP_STATE (9) #define COMMAND_GROUP_HELP_ONLY (10) #define COMMAND_GROUP_LAST (11) LPSTR CommandGroups[]= { "HELP", "FLOW CONTROL", "STRUCTURES", "OS SPECIFIC", "MEMORY", "BREAKPOINTS", "WINDOW", "DEBUGGING", "INFORMATION", "STATE", "EDITOR", NULL }; // table of command handlers CMDTABLE CmdTable[]={ {"gdt",ShowGdt,"display current global descriptor table" ,0,{0,0,0,0,0},"",COMMAND_GROUP_STRUCT}, {"idt",ShowIdt,"display current interrupt descriptor table" ,0,{0,0,0,0,0},"",COMMAND_GROUP_STRUCT}, {"x",LeaveIce,"return to Reactos" ,0,{0,0,0,0,0},"",COMMAND_GROUP_FLOW}, {"t",SingleStep,"single step one instruction" ,0,{0,0,0,0,0},"",COMMAND_GROUP_FLOW}, {"vma",ShowVirtualMemory,"displays VMAs" ,0,{0,0,0,0,0},"",COMMAND_GROUP_OS}, {"h",ShowHelp,"list help on commands" ,0,{0,0,0,0,0},"",COMMAND_GROUP_HELP}, {"page",ShowPageDirs,"dump page directories" ,COMMAND_HAS_PARAMS,{PARAM_CAN_BE_NUMERIC|PARAM_CAN_BE_REG_KEYWORD,0,0,0,0},"",COMMAND_GROUP_STRUCT}, {"proc",ShowProcesses,"list all processes" ,COMMAND_HAS_PARAMS,{PARAM_CAN_BE_PRNAME|PARAM_CAN_BE_PID,0,0,0,0},"",COMMAND_GROUP_OS}, {"dd",DisplayMemoryDword,"display dword memory" ,COMMAND_HAS_PARAMS,{PARAM_CAN_BE_NUMERIC|PARAM_CAN_BE_SYMBOLIC|PARAM_CAN_BE_REG_KEYWORD,0,0,0,0},"",COMMAND_GROUP_MEM}, {"db",DisplayMemoryByte,"display byte memory " ,COMMAND_HAS_PARAMS,{PARAM_CAN_BE_NUMERIC|PARAM_CAN_BE_SYMBOLIC|PARAM_CAN_BE_REG_KEYWORD,0,0,0,0},"",COMMAND_GROUP_MEM}, {"dpd",DisplayPhysMemDword,"display dword physical memory" ,COMMAND_HAS_PARAMS,{PARAM_CAN_BE_NUMERIC,0,0,0,0},"",COMMAND_GROUP_MEM}, {"u",Unassemble,"disassemble at address" ,COMMAND_HAS_PARAMS|COMMAND_HAS_SWITCHES,{PARAM_CAN_BE_NUMERIC|PARAM_CAN_BE_SYMBOLIC|PARAM_CAN_BE_REG_KEYWORD|PARAM_CAN_BE_SRCLINE,0,0,0,0},"f",COMMAND_GROUP_MEM}, {"mod",ShowModules,"displays all modules" ,0,{0,0,0,0,0},"",COMMAND_GROUP_OS}, {"bpx",SetBreakpoint,"set code breakpoint" ,COMMAND_HAS_PARAMS,{PARAM_CAN_BE_NUMERIC|PARAM_CAN_BE_VIRTUAL_SYMBOLIC|PARAM_CAN_BE_SYMBOLIC|PARAM_CAN_BE_SRCLINE|PARAM_CAN_BE_REG_KEYWORD,0,0,0,0},"",COMMAND_GROUP_BREAKPOINT}, {"bl",ListBreakpoints,"list breakpoints" ,COMMAND_HAS_PARAMS,{PARAM_CAN_BE_NUMERIC,0,0,0,0},"",COMMAND_GROUP_BREAKPOINT}, {"bc",ClearBreakpoints,"clear breakpoints" ,COMMAND_HAS_PARAMS,{PARAM_CAN_BE_NUMERIC|PARAM_CAN_BE_ASTERISK,0,0,0,0},"",COMMAND_GROUP_BREAKPOINT}, {"ver",Ver,"display pICE version and state information" ,0,{0,0,0,0,0},"",COMMAND_GROUP_INFO}, {"hboot",Hboot,"hard boot the system" ,0,{0,0,0,0,0},"",COMMAND_GROUP_FLOW}, {"code",SetCodeDisplay,"toggle code display" ,COMMAND_HAS_PARAMS,{PARAM_CAN_BE_ONOFF,0,0,0,0},"",COMMAND_GROUP_STATE}, {"cpu",ShowCPU,"display CPU special registers" ,0,{0,0,0,0,0},"",COMMAND_GROUP_STRUCT}, {"stack",WalkStack,"display call stack" ,0,{0,0,0,0,0},"",COMMAND_GROUP_STRUCT}, {"peek",PeekMemory,"peek at physical memory" ,COMMAND_HAS_PARAMS,{PARAM_CAN_BE_SIZE_DESC,PARAM_CAN_BE_NUMERIC,0,0,0},"",COMMAND_GROUP_MEM}, {"poke",PokeMemory,"poke to physical memory" ,COMMAND_HAS_PARAMS,{PARAM_CAN_BE_SIZE_DESC,PARAM_CAN_BE_NUMERIC,PARAM_CAN_BE_NUMERIC,0,0},"",COMMAND_GROUP_MEM}, {".",UnassembleAtCurrentEip,"unassemble at current instruction" ,0,{0,0,0,0,0},"",COMMAND_GROUP_MEM}, {"p",StepOver,"single step over call" ,0,{0,0,0,0,0},"",COMMAND_GROUP_FLOW}, {"i",StepInto,"single step into call" ,0,{0,0,0,0,0},"",COMMAND_GROUP_FLOW}, {"locals",ShowLocals,"display local symbols" ,0,{0,0,0,0,0},"",COMMAND_GROUP_MEM}, {"table",SwitchTables,"display loaded symbol tables" ,COMMAND_HAS_PARAMS,{PARAM_CAN_BE_MODULE,0,0,0,0},"",COMMAND_GROUP_DEBUG}, {"file",SwitchFiles,"display source files in symbol table" ,COMMAND_HAS_PARAMS,{PARAM_CAN_BE_SRC_FILE,0,0,0,0},"",COMMAND_GROUP_DEBUG}, {"sym",ShowSymbols,"list known symbol information" ,COMMAND_HAS_PARAMS,{PARAM_CAN_BE_PARTIAL_SYM_NAME,0,0,0,0},"",COMMAND_GROUP_DEBUG}, {"?",EvaluateExpression,"evaluate an expression" ,COMMAND_HAS_PARAMS,{PARAM_CAN_BE_ANY_STRING,0,0,0,0},"",COMMAND_GROUP_DEBUG}, {"src",SetSrcDisplay,"sets disassembly mode" ,0,{0,0,0,0,0},"",COMMAND_GROUP_DEBUG}, {"wc",SizeCodeWindow,"change size of code window" ,COMMAND_HAS_PARAMS,{PARAM_CAN_BE_DECIMAL,0,0,0,0},"",COMMAND_GROUP_WINDOW}, {"wd",SizeDataWindow,"change size of data window" ,COMMAND_HAS_PARAMS,{PARAM_CAN_BE_DECIMAL,0,0,0,0},"",COMMAND_GROUP_WINDOW}, {"r",SetGetRegisters,"sets or displays registers" ,COMMAND_HAS_PARAMS,{PARAM_CAN_BE_REG_KEYWORD,PARAM_CAN_BE_NUMERIC,0,0,0},"",COMMAND_GROUP_STRUCT}, {"cls",ClearScreen,"clear output window" ,0,{0,0,0,0,0},"",COMMAND_GROUP_WINDOW}, {"phys",ShowMappings,"show all mappings for linear address" ,COMMAND_HAS_PARAMS,{PARAM_CAN_BE_NUMERIC,0,0,0,0},"",COMMAND_GROUP_MEM}, {"timers",ShowTimers,"show all active timers" ,0,{0,0,0,0,0},"",COMMAND_GROUP_OS}, {"pci",ShowPCI,"show PCI devices" ,COMMAND_HAS_PARAMS|COMMAND_HAS_SWITCHES,{PARAM_CAN_BE_DECIMAL,PARAM_CAN_BE_DECIMAL,0,0,0},"a",COMMAND_GROUP_INFO}, {"next",NextInstr,"advance EIP to next instruction" ,0,{0,0,0,0,0},""}, {"i3here",I3here,"catch INT 3s" ,COMMAND_HAS_PARAMS,{PARAM_CAN_BE_ONOFF,0,0,0,0},"",COMMAND_GROUP_FLOW}, {"layout",SetKeyboardLayout,"sets keyboard layout" ,COMMAND_HAS_PARAMS,{PARAM_CAN_BE_ANY_STRING,0,0,0,0},"",COMMAND_GROUP_FLOW}, {"syscall",ShowSysCallTable,"displays syscall (table)" ,COMMAND_HAS_PARAMS,{PARAM_CAN_BE_DECIMAL,0,0,0,0},"",COMMAND_GROUP_FLOW}, {"altkey",SetAltKey,"set alternate break key" ,COMMAND_HAS_PARAMS,{PARAM_CAN_BE_LETTER,0,0,0,0},"",COMMAND_GROUP_FLOW}, {"addr",ShowContext,"show/set address contexts" ,COMMAND_HAS_PARAMS,{PARAM_CAN_BE_PRNAME,0,0,0,0},"",COMMAND_GROUP_FLOW}, {"arrow up",NULL,"" ,0,{0,0,0,0,0},"",COMMAND_GROUP_HELP_ONLY}, {NULL,0,NULL} }; char tempCmd[1024]; char HexDigit[] = { '0', '1', '2', '3', '4', '5', '6', '7', '8', '9', 'A', 'B', 'C', 'D', 'E', 'F' }; CPUINFO CPUInfo[]={ {"DR0",&CurrentDR0}, {"DR1",&CurrentDR1}, {"DR2",&CurrentDR2}, {"DR3",&CurrentDR3}, {"DR6",&CurrentDR6}, {"DR7",&CurrentDR7}, {"EFLAGS",&CurrentEFL}, {"CR0",&CurrentCR0}, {"CR2",&CurrentCR2}, {"CR3",&CurrentCR3}, {"",NULL}, }; BP Bp[4]={ {0,0,0,FALSE,FALSE,FALSE,"",""}, {0,0,0,FALSE,FALSE,FALSE,"",""}, {0,0,0,FALSE,FALSE,FALSE,"",""}, {0,0,0,FALSE,FALSE,FALSE,"",""} }; BOOLEAN bShowSrc = TRUE; BOOLEAN bCodeOn = FALSE; BOOLEAN bNeedToFillBuffer = TRUE; char *NonSystemSegmentTypes[]= { "Data RO", "Data RO accessed", "Data RW", "Data RW accessed", "Data RO expand-dwon", "Data RO expand-down, accessed", "Data RW expand-dwon", "Data RW expand-down, accessed", "Code EO", "Code EO accessed", "Code ER", "Code ER accessed", "Code EO conforming", "Code EO conforming, accessed", "Code ER conforming", "Code ER conforming, accessed" }; char *SystemSegmentTypes[]= { "reserved0", "16-bit TSS (available)", "LDT", "16-bit TSS (busy)", "16-bit call gate", "task gate", "16-bit interrupt gate", "16-bit trap gate", "reserved1", "32-bit TSS (available)", "reserved2", "32-bit TSS (busy)", "32-bit call gate", "reserved3", "32-bit interrupt gate", "32-bit trap gate" }; //////////////////////////////////////////////////// // FUNCTIONS //// //************************************************************************* // RepaintSource() // //************************************************************************* void RepaintSource(void) { ARGS Args; ENTER_FUNC(); // disassembly from current address PICE_memset(&Args,0,sizeof(ARGS)); // make unassembler refresh all again ulLastDisassStartAddress=ulLastDisassEndAddress=0; Args.Count=0; Unassemble(&Args); LEAVE_FUNC(); } //************************************************************************* // RepaintDesktop() // //************************************************************************* void RepaintDesktop(void) { ARGS Args; ENTER_FUNC(); PrintTemplate(); DisplayRegs(); // display data window Args.Value[0]=OldSelector; Args.Value[1]=OldOffset; Args.Count=2; DisplayMemory(&Args); // disassembly from current address PICE_memset(&Args,0,sizeof(ARGS)); // make unassembler refresh all again ulLastDisassStartAddress=ulLastDisassEndAddress=0; Args.Count=0; Unassemble(&Args); PrintRingBuffer(wWindow[OUTPUT_WINDOW].cy-1); Print(OUTPUT_WINDOW,""); ShowStoppedMsg(); ShowStatusLine(); LEAVE_FUNC(); } //************************************************************************* // PutStatusText() // //************************************************************************* void PutStatusText(LPSTR p) { ENTER_FUNC(); ClrLine(wWindow[OUTPUT_WINDOW].y-1); PutChar(p,1,wWindow[OUTPUT_WINDOW].y-1); LEAVE_FUNC(); } //************************************************************************* // WaitForKey() // //************************************************************************* BOOLEAN WaitForKey(void) { BOOLEAN result=TRUE; if(ulCountForWaitKey == 0) SuspendPrintRingBuffer(TRUE); ulCountForWaitKey++; if(ulCountForWaitKey == (wWindow[OUTPUT_WINDOW].cy-1)) { SuspendPrintRingBuffer(FALSE); PrintRingBuffer(wWindow[OUTPUT_WINDOW].cy-1); ulCountForWaitKey = 0; SetBackgroundColor(WHITE); ClrLine(wWindow[OUTPUT_WINDOW].y+wWindow[OUTPUT_WINDOW].cy); PutChar(" Press any key to continue listing or press ESC to stop... ",1,wWindow[OUTPUT_WINDOW].y+wWindow[OUTPUT_WINDOW].cy); ucKeyPressedWhileIdle=0; while(!(ucKeyPressedWhileIdle=GetKeyPolled())) { PrintCursor(FALSE); } SetBackgroundColor(BLACK); // if ESCAPE then indicate retreat if(ucKeyPressedWhileIdle==SCANCODE_ESC) { result=FALSE; } ucKeyPressedWhileIdle=0; } return result; } ///////////////////////////////////////////////////////////// // command handlers ///////////////////////////////////////////////////////////// //************************************************************************* // SingleStep() // //************************************************************************* COMMAND_PROTOTYPE(SingleStep) { ULONG ulLineNumber; LPSTR pSrcStart,pSrcEnd,pFilename; ENTER_FUNC(); if(FindSourceLineForAddress(GetLinearAddress(CurrentCS,CurrentEIP),&ulLineNumber,&pSrcStart,&pSrcEnd,&pFilename)) { DPRINT((0,"SingleStep(): stepping into source\n")); StepInto(NULL); } else { // modify trace flag CurrentEFL|=0x100; // set trace flag (TF) bSingleStep=TRUE; bNotifyToExit=TRUE; } bStepping = TRUE; LEAVE_FUNC(); return TRUE; } //************************************************************************* // StepOver() // // step over calls //************************************************************************* COMMAND_PROTOTYPE(StepOver) { char tempDisasm[256]; ULONG dwBreakAddress; ULONG ulLineNumber; LPSTR pSrcStart,pSrcEnd,pFilename; ENTER_FUNC(); DPRINT((0,"StepOver():\n")); // only no arguments supplied // when we have source and current disassembly mod is SOURCE // we have to analyse the code block for the source line if(FindSourceLineForAddress(GetLinearAddress(CurrentCS,CurrentEIP),&ulLineNumber,&pSrcStart,&pSrcEnd,&pFilename)) { DPRINT((0,"StepOver(): we have source here!\n")); DPRINT((0,"StepOver(): line #%u in file = %s!\n",ulLineNumber,pFilename)); g_ulLineNumberStart = ulLineNumber; bStepThroughSource = TRUE; // deinstall the INT3 in kernel's printk() DeInstallPrintkHook(); goto proceed_as_normal; } else { DPRINT((0,"StepOver(): no source here!\n")); proceed_as_normal: // if there is some form of call instruction at EIP we need to find // the return address if(IsCallInstrAtEIP()) { // get address of next instruction dwBreakAddress=GetLinearAddress(CurrentCS,CurrentEIP); Disasm(&dwBreakAddress,tempDisasm); DPRINT((0,"address of break = %.4X:%.8X\n",CurrentCS,dwBreakAddress)); dwBreakAddress=GetLinearAddress(CurrentCS,dwBreakAddress); DPRINT((0,"linear address of break = %.8X\n",dwBreakAddress)); DPRINT((0,"setting DR0=%.8X\n",dwBreakAddress)); SetHardwareBreakPoint(dwBreakAddress,0); bSingleStep = FALSE; bNotifyToExit = TRUE; } else { DPRINT((0,"no call at breakpoint\n")); // modify trace flag CurrentEFL|=0x100; // set trace flag (TF) bSingleStep=TRUE; bNotifyToExit=TRUE; } } bStepInto = FALSE; bStepping = TRUE; LEAVE_FUNC(); return TRUE; } //************************************************************************* // StepInto() // // step into calls //************************************************************************* COMMAND_PROTOTYPE(StepInto) { ULONG ulLineNumber; LPSTR pSrcStart,pSrcEnd,pFilename; ENTER_FUNC(); // only no arguments supplied // when we have source and current disassembly mod is SOURCE // we have to analyse the code block for the source line if(FindSourceLineForAddress(GetLinearAddress(CurrentCS,CurrentEIP),&ulLineNumber,&pSrcStart,&pSrcEnd,&pFilename)) { DPRINT((0,"StepOver(): we have source here!\n")); DPRINT((0,"StepOver(): line #%u in file = %s!\n",ulLineNumber,pFilename)); g_ulLineNumberStart = ulLineNumber; bStepThroughSource = TRUE; // deinstall the INT3 in kernel's printk() DeInstallPrintkHook(); goto proceed_as_normal_into; } else { DPRINT((0,"StepInto(): no source here!\n")); proceed_as_normal_into: // modify trace flag CurrentEFL|=0x100; // set trace flag (TF) bSingleStep=TRUE; bNotifyToExit=TRUE; } bStepInto = TRUE; bStepping = TRUE; LEAVE_FUNC(); return TRUE; } //************************************************************************* // SetBreakpoint() // //************************************************************************* COMMAND_PROTOTYPE(SetBreakpoint) { ULONG addr,addrorg; USHORT segment; if(pArgs->Count<=2) { if(pArgs->bNotTranslated[0]==FALSE) { if(gCurrentSelector) { addr=pArgs->Value[0]; addrorg=gCurrentOffset; segment=gCurrentSelector; } else { addrorg=addr=pArgs->Value[0]; segment=CurrentCS; } if(InstallSWBreakpoint(GetLinearAddress(segment,addr),FALSE,NULL) ) { PICE_sprintf(tempCmd,"BP #%u set to %.4X:%.8X\n",0,segment,addr); } else { PICE_sprintf(tempCmd,"BP #%u NOT set (either page not valid OR already used)\n",0); } Print(OUTPUT_WINDOW,tempCmd); } else { if(InstallVirtualSWBreakpoint((LPSTR)pArgs->Value[0],(LPSTR)pArgs->Value[1]) ) { PICE_sprintf(tempCmd,"BP #%u virtually set to %s!%s\n",0,(LPSTR)pArgs->Value[0],(LPSTR)pArgs->Value[1]); } else { PICE_sprintf(tempCmd,"BP #%u NOT set (maybe no symbols loaded)\n",0); } Print(OUTPUT_WINDOW,tempCmd); } RepaintSource(); } return TRUE; } //************************************************************************* // ListBreakpoints() // //************************************************************************* COMMAND_PROTOTYPE(ListBreakpoints) { ULONG i; ListSWBreakpoints(); for(i=0;i<4;i++) { if(Bp[i].Used) { PICE_sprintf(tempCmd,"(%u) %s %.4X:%.8X(linear %.8X)\n",i,Bp[i].Active?"*":" ",Bp[i].Segment,Bp[i].Offset,Bp[i].LinearAddress); Print(OUTPUT_WINDOW,tempCmd); } } return TRUE; } //************************************************************************* // ClearBreakpoints() // //************************************************************************* COMMAND_PROTOTYPE(ClearBreakpoints) { if(pArgs->Count) { if(pArgs->Value[0]<4) { Bp[pArgs->Value[0]].Used=Bp[pArgs->Value[0]].Active=FALSE; } RepaintSource(); } else { ULONG i; RemoveAllSWBreakpoints(FALSE); for(i=0;i<4;i++)Bp[i].Used=Bp[i].Active=FALSE; RepaintSource(); } return TRUE; } //************************************************************************* // LeaveIce() // //************************************************************************* COMMAND_PROTOTYPE(LeaveIce) { // SetHardwareBreakPoints(); bSingleStep=FALSE; bNotifyToExit=TRUE; return TRUE; } //************************************************************************* // ShowGdt() // //************************************************************************* COMMAND_PROTOTYPE(ShowGdt) { ULONG gdtr[2]; USHORT i; PGDT pGdt; static ULONG addr=0; LPSTR pVerbose; // get GDT register __asm__ ("sgdt %0\n" :"=m" (gdtr)); // info out PICE_sprintf(tempCmd,"Address=%.8X Limit=%.4X\n",(gdtr[1]<<16)|(gdtr[0]>>16),gdtr[0]&0xFFFF); Print(OUTPUT_WINDOW,tempCmd); WaitForKey(); // make pointer to GDT pGdt=(PGDT)(((ULONG)(gdtr[1]<<16))|((ULONG)(gdtr[0]>>16))); if(pArgs->Count==1) { ULONG limit=((pGdt[addr].Limit_19_16<<16)|pGdt[addr].Limit_15_0); addr=pArgs->Value[0]; addr&=(~0x7); if(pGdt[addr>>3].Gran)limit=(limit*4096)|0xfff; if(!pGdt[addr>>3].DescType) pVerbose = SystemSegmentTypes[pGdt[addr>>3].SegType]; else pVerbose = NonSystemSegmentTypes[pGdt[addr>>3].SegType]; PICE_sprintf(tempCmd,"%.4X %.8X %.8X %s %u %s\n", addr, (pGdt[addr>>3].Base_31_24<<24)|(pGdt[addr>>3].Base_23_16<<16)|(pGdt[addr>>3].Base_15_0), limit, pGdt[addr>>3].Present?" P":"NP", pGdt[addr>>3].Dpl, pVerbose); Print(OUTPUT_WINDOW,tempCmd); } else if(pArgs->Count==0) { for(i=0;i<((gdtr[0]&0xFFFF)>>3);i++) { ULONG limit=((pGdt[i].Limit_19_16<<16)|pGdt[i].Limit_15_0); if(!pGdt[i].DescType) pVerbose = SystemSegmentTypes[pGdt[i].SegType]; else pVerbose = NonSystemSegmentTypes[pGdt[i].SegType]; if(pGdt[i].Gran)limit=(limit*4096)|0xfff; PICE_sprintf(tempCmd,"%.4X %.8X %.8X %s %u %s\n", i<<3, (pGdt[i].Base_31_24<<24)|(pGdt[i].Base_23_16<<16)|(pGdt[i].Base_15_0), limit, pGdt[i].Present?" P":"NP", pGdt[i].Dpl, pVerbose); Print(OUTPUT_WINDOW,tempCmd); if(WaitForKey()==FALSE)break; } } return TRUE; } //************************************************************************* // OutputIdtEntry() // //************************************************************************* void OutputIdtEntry(PIDT pIdt,ULONG i) { USHORT seg; ULONG offset; LPSTR pSym; seg = (USHORT)pIdt[i].Selector; offset = (pIdt[i].Offset_31_16<<16)|(pIdt[i].Offset_15_0); switch(pIdt[i].DescType) { // task gate case 0x5: PICE_sprintf(tempCmd,"(%0.4X) %0.4X:%0.8X %u [task]\n",i, seg, GetLinearAddress((USHORT)seg,0), pIdt[i].Dpl); break; // interrupt gate case 0x6: case 0xE: if(ScanExportsByAddress(&pSym,GetLinearAddress((USHORT)seg,offset))) { PICE_sprintf(tempCmd,"(%0.4X) %0.4X:%0.8X %u [int] (%s)\n",i, seg, offset, pIdt[i].Dpl, pSym); } else { PICE_sprintf(tempCmd,"(%0.4X) %0.4X:%0.8X %u [int]\n",i, seg, offset, pIdt[i].Dpl); } break; // trap gate case 0x7: case 0xF: if(ScanExportsByAddress(&pSym,GetLinearAddress((USHORT)seg,offset))) { PICE_sprintf(tempCmd,"(%0.4X) %0.4X:%0.8X %u [trap] (%s)\n",i, seg, offset, pIdt[i].Dpl, pSym); } else { PICE_sprintf(tempCmd,"(%0.4X) %0.4X:%0.8X %u [trap]\n",i, seg, offset, pIdt[i].Dpl); } break; default: PICE_sprintf(tempCmd,"(%0.4X) INVALID\n",i); break; } Print(OUTPUT_WINDOW,tempCmd); } //************************************************************************* // ShowIdt() // //************************************************************************* COMMAND_PROTOTYPE(ShowIdt) { ULONG idtr[2]; USHORT i; PIDT pIdt; ULONG addr=0; ENTER_FUNC(); // get GDT register __asm__ ("sidt %0\n" :"=m" (idtr)); // info out PICE_sprintf(tempCmd,"Address=%.8X Limit=%.4X\n",(idtr[1]<<16)|(idtr[0]>>16),idtr[0]&0xFFFF); Print(OUTPUT_WINDOW,tempCmd); WaitForKey(); // make pointer to GDT pIdt=(PIDT)(((ULONG)(idtr[1]<<16))|((ULONG)(idtr[0]>>16))); if(pArgs->Count==1) { addr=pArgs->Value[0]; addr&=(~0x7); } else if(pArgs->Count==0) { for(i=0;i<((idtr[0]&0xFFFF)>>3);i++) { OutputIdtEntry(pIdt,i); if(WaitForKey()==FALSE)break; } } LEAVE_FUNC(); return TRUE; } //************************************************************************* // ShowHelp() // //************************************************************************* COMMAND_PROTOTYPE(ShowHelp) { ULONG i,j; PutStatusText("COMMAND KEYWORD DESCRIPTION"); for(j=0;j show all page directories if(!pArgs->Count) { PutStatusText("Linear Physical Attributes"); // there are 1024 page directories each mapping 1024*4k of address space for(i=0;i<1024;i++) { ULONG ulAddress = i<<22; // from the mm_struct get pointer to page directory for this address pPGD = ADDR_TO_PDE(ulAddress); // create a structurized pointer from PGD pPageDir = (PPAGEDIR)pPGD; if(pPageDir->PTBase) { PICE_sprintf(tempCmd,"%.8X-%.8X %.8X %s %s %s\n", ulAddress, ulAddress + 0x400000, (pPageDir->PTBase<<12), pPageDir->P?"P ":"NP", pPageDir->RW?"RW":"R ", pPageDir->US?"U":"S"); Print(OUTPUT_WINDOW,tempCmd); if(WaitForKey()==FALSE)break; } } } // one arg supplied -> show individual page else if(pArgs->Count == 1) { pPGD = ADDR_TO_PDE((ULONG)pArgs->Value[0]); DPRINT((0,"ShowPageDirs(): VA = %.8X\n",pArgs->Value[0])); DPRINT((0,"ShowPageDirs(): pPGD = %.8X\n",(ULONG)pPGD)); if(pPGD && ((*pPGD)&_PAGE_PRESENT)) { // 4M page if((*pPGD)&_PAGE_4M) { PPAGEDIR pPage = (PPAGEDIR)pPGD; PutStatusText("Linear Physical Attributes"); PICE_sprintf(tempCmd,"%.8X %.8X %s %s %s (LARGE PAGE PTE @ %.8X)\n", pArgs->Value[0], (pPage->PTBase<<12)|(pArgs->Value[0]&0x7FFFFF), pPage->P?"P ":"NP", pPage->RW?"RW":"R ", pPage->US?"U":"S", (ULONG)pPGD); } else { pPTE = ADDR_TO_PTE(pArgs->Value[0]); DPRINT((0,"ShowPageDirs(): pPTE = %.8X\n",(ULONG)pPTE)); if(pPTE) { PPAGEDIR pPage = (PPAGEDIR)pPTE; DPRINT((0,"ShowPageDirs(): pPage->PTBase = %.8X\n",(ULONG)pPage->PTBase)); PutStatusText("Linear Physical Attributes"); PICE_sprintf(tempCmd,"%.8X %.8X %s %s %s (PTE @ %.8X)\n", pArgs->Value[0], (pPage->PTBase<<12)|(pArgs->Value[0]&(_PAGE_SIZE-1)), (pPage->P==1)?"P ":"NP", pPage->RW?"RW":"R ", pPage->US?"U":"S", (ULONG)pPTE); } } Print(OUTPUT_WINDOW,tempCmd); } else { PICE_sprintf(tempCmd,"page at %.8X not present.\n",pArgs->Value[0]); Print(OUTPUT_WINDOW,tempCmd); } } } return TRUE; } //************************************************************************* // ShowProcesses() // //************************************************************************* COMMAND_PROTOTYPE(ShowProcesses) { PEPROCESS my_current = IoGetCurrentProcess(); PLIST_ENTRY current_entry; PEPROCESS currentps; ENTER_FUNC(); current_entry = pPsProcessListHead->Flink; if( current_entry ){ PutStatusText("NAME TASK PID"); while( current_entry != pPsProcessListHead ){ currentps = CONTAINING_RECORD(current_entry, EPROCESS, ProcessListEntry); DPRINT((0,"currentps = %x\n",currentps)); //ei would be nice to mark current process! PICE_sprintf(tempCmd,"%-16.16s %-12x %x\n",currentps->ImageFileName, (ULONG)currentps,currentps->UniqueProcessId); Print(OUTPUT_WINDOW,tempCmd); if(WaitForKey()==FALSE) break; current_entry = current_entry->Flink; } } LEAVE_FUNC(); return TRUE; } //************************************************************************* // DisplayMemoryDword() // //************************************************************************* COMMAND_PROTOTYPE(DisplayMemoryDword) { ULONG i,j,k; static ULONG addr=0,addrorg; static USHORT segment; char temp[8]; LPSTR pSymbolName; ENTER_FUNC(); DPRINT((0,"DisplayMemoryDword()\n")); if(pArgs->Count==2) { segment=(USHORT)pArgs->Value[0]; if(!segment)segment=GLOBAL_DATA_SEGMENT; addr=pArgs->Value[1]; OldSelector = segment; OldOffset = addr; addrorg=addr; addr=GetLinearAddress(segment,addr); } else if(pArgs->Count==1) { segment=CurrentDS; addr=pArgs->Value[0]; OldOffset = addr; addrorg=addr; addr=GetLinearAddress(segment,addr); } else if(pArgs->Count==0) { addr += sizeof(ULONG)*4*4; OldOffset = addr; } if(ScanExportsByAddress(&pSymbolName,addr)) { PICE_sprintf(tempCmd," %s ",pSymbolName); SetForegroundColor(COLOR_TEXT); SetBackgroundColor(COLOR_CAPTION); PutChar(tempCmd,GLOBAL_SCREEN_WIDTH-1-PICE_strlen(tempCmd),wWindow[DATA_WINDOW].y-1); ResetColor(); } DisableScroll(DATA_WINDOW); if(DisplayMemory != DisplayMemoryDword) { Clear(DATA_WINDOW); DisplayMemory = DisplayMemoryDword; } else Home(DATA_WINDOW); for(k=0;kCount==2) { segment=(USHORT)pArgs->Value[0]; if(!segment)segment=GLOBAL_DATA_SEGMENT; addr=pArgs->Value[1]; OldSelector = segment; OldOffset = addr; addrorg=addr; addr=GetLinearAddress(segment,addr); } else if(pArgs->Count==1) { segment=CurrentDS; addr=pArgs->Value[0]; OldOffset = addr; addrorg=addr; addr=GetLinearAddress(segment,addr); } else if(pArgs->Count==0) { addr += sizeof(ULONG)*4*4; OldOffset = addr; } if(DisplayMemory != DisplayMemoryByte) { Clear(DATA_WINDOW); DisplayMemory = DisplayMemoryByte; } else Home(DATA_WINDOW); if(ScanExportsByAddress(&pSymbolName,addr)) { PICE_sprintf(tempCmd," %s ",pSymbolName); SetForegroundColor(COLOR_TEXT); SetBackgroundColor(COLOR_CAPTION); PutChar(tempCmd,GLOBAL_SCREEN_WIDTH-1-PICE_strlen(tempCmd),wWindow[DATA_WINDOW].y-1); ResetColor(); } DisableScroll(DATA_WINDOW); for(k=0;kCount==1) { segment=CurrentDS; addr=pArgs->Value[0]; OldOffset = addr; addrorg=addr; addr=GetLinearAddress(segment,addr); } else if(pArgs->Count==0) { addr += sizeof(ULONG)*4*4; OldOffset = addr; } DisableScroll(DATA_WINDOW); if(DisplayMemory != DisplayPhysMemDword) { Clear(DATA_WINDOW); DisplayMemory = DisplayPhysMemDword; } else Home(DATA_WINDOW); for(k=0;kGLOBAL_SCREEN_WIDTH-1) { tempCmd[GLOBAL_SCREEN_WIDTH-2]='\n'; tempCmd[GLOBAL_SCREEN_WIDTH-1]=0; } if( (ulLineNumberToInvert!=-1) && ((int)(ulLineNumberToInvert-ulLineNumber)>=0) && ((ulLineNumberToInvert-ulLineNumber)=0) && ((ulLineNumberToInvert-ulLineNumber)CountSwitches, pArgs->Count)); if(pArgs->CountSwitches>1) return TRUE; if(pArgs->CountSwitches==1) { if(pArgs->Switch[0] == 'f') bForceDisassembly = TRUE; } // we have args if(pArgs->Count==2) { addr=pArgs->Value[1]; segment=(USHORT)pArgs->Value[0]; addrorg=addrstart=addr; addr=GetLinearAddress(segment,addr); usOldDisasmSegment = segment; ulOldDisasmOffset = addr; } else if(pArgs->Count==1) { addr=pArgs->Value[0]; segment=CurrentCS; addrorg=addrstart=addr; addr=GetLinearAddress(segment,addr); usOldDisasmSegment = segment; ulOldDisasmOffset = addr; } else if(pArgs->Count==0) { segment = usOldDisasmSegment; addrorg=addrstart=addr; addr = GetLinearAddress(usOldDisasmSegment,ulOldDisasmOffset); } else return TRUE; DPRINT((0,"Unassemble(%0.4X:%0.8X), lastst: %x, lastend:%x\n",segment,addr,ulLastDisassStartAddress,ulLastDisassEndAddress)); // // unassemble // DisableScroll(SOURCE_WINDOW); // if we're inside last disassembly range we only need to move to highlight if(ulLastDisassStartAddress && ulLastDisassEndAddress && addr>=ulLastDisassStartAddress && addrname = %S\n",pCurrentMod->name)); mod_addr = (ULONG)pCurrentMod->BaseAddress; pCurrentSymbols = FindModuleSymbols(mod_addr); DPRINT((0,"Unassemble(): pCurrentSymbols = %x\n",(ULONG)pCurrentSymbols)); } DPRINT((0,"Unassemble(): pCurrentMod = %x, showsrc: %d\n",pCurrentMod, bShowSrc)); ulCurrentlyDisplayedLineNumber = 0; if(bShowSrc && bForceDisassembly == FALSE && (pSrc = FindSourceLineForAddress(addr,&ulLineNumber,&pSrcStart,&pSrcEnd,&pFilename)) ) { DPRINT((0,"FoundSourceLineForAddress: file: %s line: %d\n", pFilename, ulLineNumber)); PICE_strcpy(szCurrentFile,pFilename); ulCurrentlyDisplayedLineNumber = ulLineNumber; Clear(SOURCE_WINDOW); // display file name SetForegroundColor(COLOR_TEXT); SetBackgroundColor(COLOR_CAPTION); if(PICE_strlen(pFilename)(wWindow[SOURCE_WINDOW].cy/2) ) { DisplaySourceFile(pSrcStart,pSrcEnd,ulLineNumber-(wWindow[SOURCE_WINDOW].cy/2),ulLineNumber); } else { DisplaySourceFile(pSrcStart,pSrcEnd,ulLineNumber,ulLineNumber); } } else { *szCurrentFile = 0; DPRINT((0,"Couldn't find source for file\n")); Home(SOURCE_WINDOW); // for each line in the disassembly window for(i=0;i>4)]; tempCmd[j*2+1]=HexDigit[((*(PUCHAR)(addrbefore+j)&0xF))]; } else { tempCmd[j*2]='?'; tempCmd[j*2+1]='?'; } } else { tempCmd[j*2]=' '; tempCmd[j*2+1]=' '; } } } PICE_strcat(tempCmd,"\n"); if(ulWindowOffset) { LONG len = PICE_strlen(tempCmd); if(ulWindowOffset < len) PICE_memcpy(tempCmd,&tempCmd[ulWindowOffset],len-ulWindowOffset); else tempCmd[0]='\n'; } Print(SOURCE_WINDOW,tempCmd); if(addrbefore==CurrentEIP) { ResetColor(); } // if potential SW breakpoint, undo marked text if(IsSwBpAtAddress(addrbefore)) { HatchLine(wWindow[SOURCE_WINDOW].y+i); } // if breakpoint was installed before disassembly, put it back if(bSWBpAtAddr) { ReInstallSWBreakpoint(addrbefore); } } if(ulLastDisassStartAddress==0 && ulLastDisassEndAddress==0) { ulLastDisassStartAddress=addrstart; ulLastDisassEndAddress=addr; } if(!IsAddressValid(addrstart)) { ulLastDisassStartAddress=0; ulLastDisassEndAddress=0; } } EnableScroll(SOURCE_WINDOW); return TRUE; } //************************************************************************* // ShowModules() // //************************************************************************* COMMAND_PROTOTYPE(ShowModules) { PDEBUG_MODULE pMod; DPRINT((0,"ShowModules()\n")); if(BuildModuleList()) { pMod = pdebug_module_head; do { if(pMod->size) { if(pMod == pCurrentMod) { PICE_sprintf(tempCmd,"%.8X - %.8X *%-32S\n", (unsigned int)pMod->BaseAddress, (unsigned int) ((unsigned int)pMod->BaseAddress+pMod->size),pMod->name); } else { PICE_sprintf(tempCmd,"%.8X - %.8X %-32S\n", (unsigned int)pMod->BaseAddress, (unsigned int) ((unsigned int)pMod->BaseAddress+pMod->size), pMod->name); } } Print(OUTPUT_WINDOW,tempCmd); if(WaitForKey()==FALSE) break; }while((pMod = pMod->next)!=pdebug_module_tail); } return TRUE; } //************************************************************************* // DecodeVmFlags() // //************************************************************************* //ei FIX THIS!!!!!!!!!!!!!!!!!! LPSTR DecodeVmFlags(ULONG flags) { ULONG i; /* #define VM_READ 0x0001 #define VM_WRITE 0x0002 #define VM_EXEC 0x0004 #define VM_SHARED 0x0008 #define VM_MAYREAD 0x0010 #define VM_MAYWRITE 0x0020 #define VM_MAYEXEC 0x0040 #define VM_MAYSHARE 0x0080 #define VM_GROWSDOWN 0x0100 #define VM_GROWSUP 0x0200 #define VM_SHM 0x0400 #define VM_DENYWRITE 0x0800 #define VM_EXECUTABLE 0x1000 #define VM_LOCKED 0x2000 #define VM_IO 0x4000 #define VM_STACK_FLAGS 0x0177 */ static LPSTR flags_syms_on[]={"R","W","X","S","MR","MW","MX","MS","GD","GU","SHM","exe","LOCK","IO",""}; static char temp[256]; // terminate string *temp = 0; //ei fix fix fix #if 0 if(flags == VM_STACK_FLAGS) { PICE_strcpy(temp," (STACK)"); } else { for(i=0;i<15;i++) { if(flags&0x1) { PICE_strcat(temp," "); PICE_strcat(temp,flags_syms_on[i]); } flags >>= 1; } } #endif return temp; } //************************************************************************* // ShowVirtualMemory() // //************************************************************************* COMMAND_PROTOTYPE(ShowVirtualMemory) { PEPROCESS my_current = IoGetCurrentProcess(); PLIST_ENTRY current_entry; PMADDRESS_SPACE vma = NULL; MEMORY_AREA* current; char filename[64]; DPRINT((0,"ShowVirtualMemory()\n")); if( my_current ) vma = &(my_current->AddressSpace); if( !vma ) vma = my_init_mm; while( vma ) { if(pArgs->Count == 0) { PutStatusText("START END LENGTH VMA TYPE ATTR"); current_entry = vma->MAreaListHead.Flink; while (current_entry != &vma->MAreaListHead) { *filename = 0; current = CONTAINING_RECORD(current_entry, MEMORY_AREA, Entry); // find the filename if(((current->Type == MEMORY_AREA_SECTION_VIEW) ) && current->Data.SectionData.Section->FileObject) { if(IsAddressValid((ULONG)current->Data.SectionData.Section->FileObject->FileName.Buffer) ) PICE_sprintf(filename,"%.64S",current->Data.SectionData.Section->FileObject->FileName.Buffer); } PICE_sprintf(tempCmd,"%.8X %.8X %.8X %.8X %x %x %s\n", (ULONG)current->BaseAddress, (ULONG)current->BaseAddress+current->Length, current->Length, (ULONG)current, current->Type, current->Attributes,//DecodeVmFlags(current->Type, current->Attributes), filename); Print(OUTPUT_WINDOW,tempCmd); if(WaitForKey()==FALSE) break; current_entry = current_entry->Flink; } } if( vma == &(my_current->AddressSpace) ) vma = my_init_mm; // switch to kernel memory area else vma = 0; // if we already did kernel, end loop } return TRUE; } //************************************************************************* // Ver() // //************************************************************************* COMMAND_PROTOTYPE(Ver) { //ei add kernel version info??!! PICE_sprintf(tempCmd,"pICE: version %u.%u (build %u) for Reactos\n", PICE_MAJOR_VERSION, PICE_MINOR_VERSION, PICE_BUILD); Print(OUTPUT_WINDOW,tempCmd); /* PICE_sprintf(tempCmd,"pICE: loaded on %s kernel release %s\n", system_utsname.sysname, system_utsname.release); */ Print(OUTPUT_WINDOW,tempCmd); Print(OUTPUT_WINDOW,"pICE: written by Klaus P. Gerlicher and Goran Devic.\n"); Print(OUTPUT_WINDOW,"pICE: ported to Reactos by Eugene Ingerman.\n"); return TRUE; } //************************************************************************* // Hboot() // //************************************************************************* COMMAND_PROTOTYPE(Hboot) { // nudge the reset line through keyboard controller __asm__("\n\t \ movb $0xFE,%al\n\t \ outb %al,$0x64"); // never gets here return TRUE; } //************************************************************************* // SetSrcDisplay() // //************************************************************************* COMMAND_PROTOTYPE(SetSrcDisplay) { ARGS Args; if(pArgs->Count==0) { bShowSrc=bShowSrc?FALSE:TRUE; PICE_memset(&Args,0,sizeof(ARGS)); // make unassembler refresh all again ulLastDisassStartAddress=ulLastDisassEndAddress=0; Args.Count=0; Unassemble(&Args); } return TRUE; } //************************************************************************* // I3here() // //************************************************************************* COMMAND_PROTOTYPE(I3here) { if(pArgs->Count==1) { if(pArgs->Value[0]==1) { if(!bInt3Here) { bInt3Here=TRUE; Print(OUTPUT_WINDOW,"I3HERE is now ON\n"); } else Print(OUTPUT_WINDOW,"I3HERE is already ON\n"); } else if(pArgs->Value[0]==0) { if(bInt3Here) { bInt3Here=FALSE; Print(OUTPUT_WINDOW,"I3HERE is now OFF\n"); } else Print(OUTPUT_WINDOW,"I3HERE is already OFF\n"); } } else if(pArgs->Count==0) { if(bInt3Here) { Print(OUTPUT_WINDOW,"I3HERE is ON\n"); } else { Print(OUTPUT_WINDOW,"I3HERE is OFF\n"); } } // never gets here return TRUE; } COMMAND_PROTOTYPE(I1here) { if(pArgs->Count==1) { if(pArgs->Value[0]==1) { if(!bInt1Here) { bInt1Here=TRUE; Print(OUTPUT_WINDOW,"I1HERE is now ON\n"); } else Print(OUTPUT_WINDOW,"I1HERE is already ON\n"); } else if(pArgs->Value[0]==0) { if(bInt1Here) { bInt1Here=FALSE; Print(OUTPUT_WINDOW,"I1HERE is now OFF\n"); } else Print(OUTPUT_WINDOW,"I1HERE is already OFF\n"); } } else if(pArgs->Count==0) { if(bInt1Here) { Print(OUTPUT_WINDOW,"I1HERE is ON\n"); } else { Print(OUTPUT_WINDOW,"I1HERE is OFF\n"); } } // never gets here return TRUE; } COMMAND_PROTOTYPE(NextInstr) { static char tempDisasm[256]; ULONG addr,addrbefore; bNeedToFillBuffer=FALSE; if(!pArgs->Count) { addr=addrbefore=GetLinearAddress(CurrentCS,CurrentEIP); DPRINT((0,"addr before %.8X\n",addrbefore)); Disasm(&addr,tempDisasm); DPRINT((0,"addr after %.8X\n",addr)); CurrentEIP=CurrentEIP+(addr-addrbefore); // display register contents DisplayRegs(); // unassemble DPRINT((0,"new CS:EIP %04.x:%.8X\n",CurrentCS,CurrentEIP)); PICE_memset(pArgs,0,sizeof(ARGS)); // make unassembler refresh all again ulLastDisassStartAddress=ulLastDisassEndAddress=0; pArgs->Count=2; pArgs->Value[0]=(ULONG)CurrentCS; pArgs->Value[1]=CurrentEIP; Unassemble(pArgs); } bNeedToFillBuffer=TRUE; return TRUE; } COMMAND_PROTOTYPE(SetGetRegisters) { ULONG i; if(pArgs->Count==0) { // display whole set for(i=0;RegKeyWords[i].pValue!=0;i++) { switch(RegKeyWords[i].ulSize) { case 1: PICE_sprintf(tempCmd,"%s = %.8X\n",RegKeyWords[i].KeyWord,*(PUCHAR)(RegKeyWords[i].pValue)); break; case 2: PICE_sprintf(tempCmd,"%s = %.8X\n",RegKeyWords[i].KeyWord,*(PUSHORT)(RegKeyWords[i].pValue)); break; case 4: PICE_sprintf(tempCmd,"%s = %.8X\n",RegKeyWords[i].KeyWord,*(PULONG)(RegKeyWords[i].pValue)); break; } Print(OUTPUT_WINDOW,tempCmd); if(WaitForKey()==FALSE)break; } } else if(pArgs->Count==1) { // display selected register for(i=0;RegKeyWords[i].pValue!=0;i++) { if(PICE_strcmpi(pArgs->pToken[0],RegKeyWords[i].KeyWord)==0) { switch(RegKeyWords[i].ulSize) { case 1: PICE_sprintf(tempCmd,"%s = %.2X\n",RegKeyWords[i].KeyWord,*(PUCHAR)(RegKeyWords[i].pValue)); break; case 2: PICE_sprintf(tempCmd,"%s = %.4X\n",RegKeyWords[i].KeyWord,*(PUSHORT)(RegKeyWords[i].pValue)); break; case 4: PICE_sprintf(tempCmd,"%s = %.8X\n",RegKeyWords[i].KeyWord,*(PULONG)(RegKeyWords[i].pValue)); break; } Print(OUTPUT_WINDOW,tempCmd); break; } } } else if(pArgs->Count==2) { // set selected register to value for(i=0;RegKeyWords[i].pValue!=0;i++) { if(PICE_strcmpi(pArgs->pToken[0],RegKeyWords[i].KeyWord)==0) { switch(RegKeyWords[i].ulSize) { case 1: *(PUCHAR)(RegKeyWords[i].pValue)=(UCHAR)pArgs->Value[1]; break; case 2: *(PUSHORT)(RegKeyWords[i].pValue)=(USHORT)pArgs->Value[1]; break; case 4: *(PULONG)(RegKeyWords[i].pValue)=(ULONG)pArgs->Value[1]; break; } DisplayRegs(); RepaintSource(); break; } } } return TRUE; } //************************************************************************* // SetCodeDisplay() // //************************************************************************* COMMAND_PROTOTYPE(SetCodeDisplay) { ARGS Args; if(pArgs->Count==0) { bCodeOn=bCodeOn?FALSE:TRUE; PICE_memset(&Args,0,sizeof(ARGS)); Args.Count=0; // make unassembler refresh all again ulLastDisassStartAddress=ulLastDisassEndAddress=0; Unassemble(&Args); } else if(pArgs->Count==1) { bCodeOn=(pArgs->Value[0]==0)?FALSE:TRUE; PICE_memset(&Args,0,sizeof(ARGS)); Args.Count=0; // make unassembler refresh all again ulLastDisassStartAddress=ulLastDisassEndAddress=0; Unassemble(&Args); } return TRUE; } //************************************************************************* // ShowCPU() // //************************************************************************* COMMAND_PROTOTYPE(ShowCPU) { ULONG i; for(i=0;CPUInfo[i].pValue!=NULL;i++) { PICE_sprintf(tempCmd,"%s = %.8X\n",CPUInfo[i].Name,*(CPUInfo[i].pValue)); Print(OUTPUT_WINDOW,tempCmd); if(WaitForKey()==FALSE)break; } return TRUE; } //************************************************************************* // WalkStack() // //************************************************************************* COMMAND_PROTOTYPE(WalkStack) { if(!pArgs->Count) { IntelStackWalk(CurrentEIP,CurrentEBP,CurrentESP); } return TRUE; } //************************************************************************* // PokeDword() // //************************************************************************* COMMAND_PROTOTYPE(PokeDword) { ULONG ulData; // read old data ulData = ReadPhysMem(pArgs->Value[1],sizeof(ULONG)); PICE_sprintf(tempCmd,"value @ %.8X was %.8X\n",pArgs->Value[1],ulData); Print(OUTPUT_WINDOW,tempCmd); // write new data WritePhysMem(pArgs->Value[1],pArgs->Value[2],sizeof(ULONG)); // read check ulData = ReadPhysMem(pArgs->Value[1],sizeof(ULONG)); PICE_sprintf(tempCmd,"value @ %.8X = %.8X\n",pArgs->Value[1],ulData); Print(OUTPUT_WINDOW,tempCmd); return TRUE; } //************************************************************************* // PokeMemory() // //************************************************************************* COMMAND_PROTOTYPE(PokeMemory) { DPRINT((0,"PokeMemory()\n")); DPRINT((0,"PokeMemory(): value[0] = %.8X value[1] = %.8X value[3] = %.8X count = %.8X\n",pArgs->Value[0],pArgs->Value[1],pArgs->Value[2],pArgs->Count)); // must be three parameters if(pArgs->Count == 3) { switch(pArgs->Value[0]) { case 4: return PokeDword(pArgs); default: case 1: case 2: break; } } else { Print(OUTPUT_WINDOW,"you need to supply a physical address and datum to write!\n"); } return TRUE; } //************************************************************************* // PeekDword() // //************************************************************************* COMMAND_PROTOTYPE(PeekDword) { ULONG ulData; ulData = ReadPhysMem(pArgs->Value[1],sizeof(ULONG)); PICE_sprintf(tempCmd,"%.8X\n",ulData); Print(OUTPUT_WINDOW,tempCmd); return TRUE; } //************************************************************************* // PeekWord() // //************************************************************************* COMMAND_PROTOTYPE(PeekWord) { USHORT usData; usData = (USHORT)ReadPhysMem(pArgs->Value[1],sizeof(USHORT)); PICE_sprintf(tempCmd,"%.4X\n",usData); Print(OUTPUT_WINDOW,tempCmd); return TRUE; } //************************************************************************* // PeekByte() // //************************************************************************* COMMAND_PROTOTYPE(PeekByte) { UCHAR ucData; ucData = (UCHAR)ReadPhysMem(pArgs->Value[1],sizeof(UCHAR)); PICE_sprintf(tempCmd,"%.2X\n",ucData); Print(OUTPUT_WINDOW,tempCmd); return TRUE; } //************************************************************************* // PeekMemory() // //************************************************************************* COMMAND_PROTOTYPE(PeekMemory) { DPRINT((0,"PeekMemory()\n")); DPRINT((0,"PeekMemory(): value[0] = %.8X value[1] = %.8X count = %.8X\n",pArgs->Value[0],pArgs->Value[1],pArgs->Count)); if(pArgs->Count == 2) { switch(pArgs->Value[0]) { case 1: return PeekByte(pArgs); case 2: return PeekWord(pArgs); case 4: return PeekDword(pArgs); default: break; } } return TRUE; } //************************************************************************* // UnassembleAtCurrentEip() // //************************************************************************* COMMAND_PROTOTYPE(UnassembleAtCurrentEip) { PICE_memset(pArgs,0,sizeof(ARGS)); pArgs->Count = 2; pArgs->Value[0] = CurrentCS; pArgs->Value[1] = CurrentEIP; Unassemble(pArgs); return TRUE; } //************************************************************************* // SwitchTables() // //************************************************************************* COMMAND_PROTOTYPE(SwitchTables) { ULONG i; DPRINT((0,"SwitchTables()\n")); // no arguments -> display load symbol tables if(!pArgs->Count) { for(i=0;iname,(ULONG)apSymbols[i],apSymbols[i]->ulNumberOfSrcFiles); else PICE_sprintf(tempCmd," %-32S @ %.8X (%5u source files)\n",apSymbols[i]->name,(ULONG)apSymbols[i],apSymbols[i]->ulNumberOfSrcFiles); Print(OUTPUT_WINDOW,tempCmd); if(WaitForKey()==FALSE)break; } } } // 1 argument -> set new current symbols else if(pArgs->Count == 1) { PDEBUG_MODULE pTempMod; char temp[DEBUG_MODULE_NAME_LEN]; pCurrentSymbols = (PICE_SYMBOLFILE_HEADER*)pArgs->Value[0]; CopyWideToAnsi( temp, pCurrentSymbols->name ); DPRINT((0,"TableSwitchSym: pCurrentSymbols: %x, Name: %s\n", pCurrentSymbols, temp)); pTempMod = IsModuleLoaded(temp); if( pTempMod ) pCurrentMod = pTempMod; } return TRUE; } //************************************************************************* // SwitchFiles() // //************************************************************************* COMMAND_PROTOTYPE(SwitchFiles) { PICE_SYMBOLFILE_SOURCE* pSrc; ULONG i; LPSTR p; DPRINT((0,"SwitchFiles()\n")); // no arguments -> show files for current symbols if(!pArgs->Count) { if(pCurrentSymbols && pCurrentSymbols->ulNumberOfSrcFiles) { LPSTR pCurrentFile=NULL; // find out the current file name if(*szCurrentFile!=0) { if((pCurrentFile = strrchr(szCurrentFile,'/')) ) { pCurrentFile++; } else { pCurrentFile = szCurrentFile; } } pSrc = (PICE_SYMBOLFILE_SOURCE*)((ULONG)pCurrentSymbols + pCurrentSymbols->ulOffsetToSrcFiles); for(i=0;iulNumberOfSrcFiles;i++) { if(pCurrentFile) { if((p = strrchr(pSrc->filename,'/')) ) { if(PICE_strcmpi(p+1,pCurrentFile)==0) PICE_sprintf(tempCmd,"*%-32s @ %.8X\n",p+1,(ULONG)pSrc); else PICE_sprintf(tempCmd," %-32s @ %.8X\n",p+1,(ULONG)pSrc); } else { if(PICE_strcmpi(pSrc->filename,pCurrentFile)==0) PICE_sprintf(tempCmd,"*%-32s @ %.8X\n",pSrc->filename,(ULONG)pSrc); else PICE_sprintf(tempCmd," %-32s @ %.8X\n",pSrc->filename,(ULONG)pSrc); } } else { if((p = strrchr(pSrc->filename,'/')) ) { PICE_sprintf(tempCmd,"%-32s @ %.8X\n",p+1,(ULONG)pSrc); } else { PICE_sprintf(tempCmd,"%-32s @ %.8X\n",pSrc->filename,(ULONG)pSrc); } } Print(OUTPUT_WINDOW,tempCmd); if(WaitForKey()==FALSE)break; (LPSTR)pSrc += pSrc->ulOffsetToNext; } } else Print(OUTPUT_WINDOW,"No source files available!\n"); } // 1 argument -> argument is pointer PICE_SYMBOLFILE_SOURCE struct -> // set current file and show it else if(pArgs->Count == 1) { PICE_SYMBOLFILE_SOURCE* pSrc = (PICE_SYMBOLFILE_SOURCE*)pArgs->Value[0]; LPSTR pFilename = pSrc->filename; ClrLine(wWindow[SOURCE_WINDOW].y-1); if(PICE_strlen(pFilename)ulOffsetToNext, 1, -1); } return TRUE; } //************************************************************************* // ShowLocals() // //************************************************************************* COMMAND_PROTOTYPE(ShowLocals) { PLOCAL_VARIABLE p; if(pArgs->Count==0) { p = FindLocalsByAddress(GetLinearAddress(CurrentCS,CurrentEIP)); DPRINT((0,"ShowLocals: %x\n", p)); if(p) { DPRINT((0,"ShowLocals: name %s, type_name %s\n", p->name, p->type_name)); while(PICE_strlen(p->name)) { if(!p->bRegister) { PICE_sprintf(tempCmd,"[EBP%.4d / #%u] %x %s %s \n",p->offset,p->line,p->value,p->type_name,p->name); } else { PICE_sprintf(tempCmd,"[%-8s / #%u] %x %s %s #%u\n",LocalVarRegs[p->offset],p->line,p->value,p->type_name,p->name); } Print(OUTPUT_WINDOW,tempCmd); p++; } } } return TRUE; } //************************************************************************* // ShowSymbols() // //************************************************************************* COMMAND_PROTOTYPE(ShowSymbols) { PICE_SYMBOLFILE_HEADER* pSymbols; ULONG index,addr; LPSTR pSearchString,pName,pFind; // no args -> list full symbols for current module if(!pArgs->Count) { // have current module ? if(pCurrentMod) { DPRINT((0,"ShowSymbols(): full listing of symbols for %S\n",pCurrentMod->name)); addr = (ULONG)pCurrentMod->BaseAddress; if((pSymbols = FindModuleSymbols(addr)) ) { PICE_sprintf(tempCmd,"symbols for module \"%S\"\n",pCurrentMod->name); Print(OUTPUT_WINDOW,tempCmd); index = 0; while((index = ListSymbolStartingAt(pCurrentMod,pSymbols,index,tempCmd))) { Print(OUTPUT_WINDOW,tempCmd); if(WaitForKey()==FALSE)break; } } } } // partial name else if(pArgs->Count == 1) { if(pCurrentMod) { addr = (ULONG)pCurrentMod->BaseAddress; if((pSymbols = FindModuleSymbols(addr))) { pSearchString = (LPSTR)pArgs->Value[0]; PICE_sprintf(tempCmd,"symbols for module \"%S\" (searching for \"%s\")\n",pCurrentMod->name,pSearchString); Print(OUTPUT_WINDOW,tempCmd); if(pSearchString) { if(*pSearchString=='*' && pSearchString[PICE_strlen(pSearchString)-1]=='*') { pSearchString[PICE_strlen(pSearchString)-1] = 0; pSearchString++; index = 0; while((index = ListSymbolStartingAt(pCurrentMod,pSymbols,index,tempCmd))) { pName = strrchr(tempCmd,' '); pName++; pFind = strstr(pName,pSearchString); if(pFind) { Print(OUTPUT_WINDOW,tempCmd); if(WaitForKey()==FALSE)break; } } // TODO } else if(pSearchString[PICE_strlen(pSearchString)-1]=='*') { pSearchString[PICE_strlen(pSearchString)-1] = 0; index = 0; index = ListSymbolStartingAt(pCurrentMod,pSymbols,index,tempCmd); if(index) { do { pName = strrchr(tempCmd,' '); pName++; pFind = strstr(pName,pSearchString); if(pFind && (((ULONG)pName-(ULONG)pFind)==0) ) { Print(OUTPUT_WINDOW,tempCmd); if(WaitForKey()==FALSE)break; } }while((index = ListSymbolStartingAt(pCurrentMod,pSymbols,index,tempCmd))); } } } } } } return TRUE; } //************************************************************************* // EvaluateExpression() // //************************************************************************* COMMAND_PROTOTYPE(EvaluateExpression) { PICE_SYMBOLFILE_HEADER* pSymbols; ULONG addr; if(pArgs->Count == 1) { if(pCurrentMod) { addr = (ULONG)pCurrentMod->BaseAddress; if( (pSymbols = FindModuleSymbols(addr) ) ) { DPRINT((0,"EvaluateExpression: %s\n", (LPSTR)pArgs->Value[0])); Evaluate(pSymbols,(LPSTR)pArgs->Value[0]); } } } return TRUE; } //************************************************************************* // SizeCodeWindow() // //************************************************************************* COMMAND_PROTOTYPE(SizeCodeWindow) { ULONG NewHeight,TotalHeight; if(pArgs->Count == 1) { NewHeight = pArgs->Value[0]; TotalHeight = wWindow[SOURCE_WINDOW].cy + wWindow[OUTPUT_WINDOW].cy; if(NewHeight < TotalHeight) { if(wWindow[SOURCE_WINDOW].cy != NewHeight) { wWindow[SOURCE_WINDOW].cy = NewHeight; wWindow[OUTPUT_WINDOW].y = wWindow[SOURCE_WINDOW].y + wWindow[SOURCE_WINDOW].cy + 1; wWindow[OUTPUT_WINDOW].cy = TotalHeight - NewHeight; RepaintDesktop(); } } } else { PICE_sprintf(tempCmd,"code window at position %u has %u lines \n",wWindow[SOURCE_WINDOW].y,wWindow[SOURCE_WINDOW].cy); Print(OUTPUT_WINDOW,tempCmd); } return TRUE; } //************************************************************************* // SizeDataWindow() // //************************************************************************* COMMAND_PROTOTYPE(SizeDataWindow) { ULONG NewHeight,TotalHeight; if(pArgs->Count) { NewHeight = pArgs->Value[0]; TotalHeight = wWindow[DATA_WINDOW].cy + wWindow[SOURCE_WINDOW].cy; if(NewHeight < TotalHeight) { if(wWindow[DATA_WINDOW].cy != NewHeight) { wWindow[DATA_WINDOW].cy = NewHeight; wWindow[SOURCE_WINDOW].y = wWindow[DATA_WINDOW].y + wWindow[DATA_WINDOW].cy + 1; wWindow[SOURCE_WINDOW].cy = TotalHeight - NewHeight; RepaintDesktop(); } } } else { PICE_sprintf(tempCmd,"data window has %u lines \n",wWindow[DATA_WINDOW].cy); Print(OUTPUT_WINDOW,tempCmd); } return TRUE; } //************************************************************************* // ClearScreen() // //************************************************************************* COMMAND_PROTOTYPE(ClearScreen) { EmptyRingBuffer(); Clear(OUTPUT_WINDOW); CheckRingBuffer(); return TRUE; } //************************************************************************* // ShowMappings() // //************************************************************************* COMMAND_PROTOTYPE(ShowMappings) { #if 0 ULONG ulPageDir; ULONG ulPageTable; ULONG address; ULONG phys_addr; pgd_t * pPGD; pmd_t * pPMD; pte_t * pPTE; struct mm_struct* p = NULL; struct task_struct* my_current = (struct task_struct*)0xFFFFE000; DPRINT((0,"ShowMappings()\n")); if(pArgs->Count == 1) { // We're in DebuggerShell(), so we live on a different stack (ULONG)my_current &= ulRealStackPtr; // in case we have a user context we use it's mm_struct if(my_current->mm) { p = my_current->mm; } // no user context -> use kernel's context else { p = my_init_mm; } // get the requested address from arguments phys_addr = pArgs->Value[0]; DPRINT((0,"ShowMappings(): p = %X phys_addr = %X\n",(ULONG)p,phys_addr)); // for every page directory for(ulPageDir=0;ulPageDir<1024;ulPageDir++) { address = (ulPageDir<<22); // get the page directory for the address pPGD = pgd_offset(p,address); // if page dir present if(pPGD && pgd_val(*pPGD)&_PAGE_PRESENT) { DPRINT((0,"ShowMappings(): page directory present for %x\n",address)); // not large page if(!(pgd_val(*pPGD)&_PAGE_4M)) { DPRINT((0,"ShowMappings(): page directory for 4k pages\n")); for(ulPageTable=0;ulPageTable<1024;ulPageTable++) { address = (ulPageDir<<22)|(ulPageTable<<12); pPMD = pmd_offset(pPGD,address); if(pPMD) { pPTE = pte_offset(pPMD,address); if(pPTE) { if(*(PULONG)pPTE & _PAGE_PRESENT) { ULONG ulPte = *(PULONG)pPTE & 0xFFFFF000; if(ulPte == (phys_addr & 0xFFFFF000)) { PICE_sprintf(tempCmd,"%.8X\n",address+(phys_addr&0xFFF)); Print(OUTPUT_WINDOW,tempCmd); if(WaitForKey()==FALSE)return TRUE; } } } } } } // large page else { address = (ulPageDir<<22); if((pgd_val(*pPGD)&0xFFC00000) == (phys_addr & 0xFFC00000) ) { if( ((address|(phys_addr&0x7FFFFF))&~TASK_SIZE) == phys_addr) PICE_sprintf(tempCmd,"%.8X (identity map %.8X+%.8X)\n",address|(phys_addr&0x7FFFFF),TASK_SIZE,phys_addr); else PICE_sprintf(tempCmd,"%.8X\n",address|(phys_addr&0x7FFFFF)); Print(OUTPUT_WINDOW,tempCmd); if(WaitForKey()==FALSE)return TRUE; } } } } } #endif PICE_sprintf(tempCmd,"Not implemented yet!\n"); Print(OUTPUT_WINDOW,tempCmd); return TRUE; } //************************************************************************* // ShowTimers() // //************************************************************************* COMMAND_PROTOTYPE(ShowTimers) { return TRUE; } //************************************************************************* // FindPCIVendorName() // //************************************************************************* LPSTR FindPCIVendorName(USHORT vendorid) { ULONG i; for(i=0;iCountSwitches>1) return TRUE; if(pArgs->CountSwitches==1) { if(pArgs->Switch[0] == 'a') bShowAll = TRUE; } if(pArgs->Count < 3) { if(pArgs->Count > 0) { bUseBus = FALSE; bus_req = pArgs->Value[0]; } if(pArgs->Count > 1) { bUseDev = FALSE; dev_req = pArgs->Value[1]; } // save old config space selector oldCF8 = inl((PULONG)0xcf8); for(bus=0;bus<256;bus++) { for(dev=0;dev<32;dev++) { if(!((bUseDev || dev == dev_req) && (bUseBus || bus == bus_req) )) continue; pciNumber.u.AsUlong = 0; pciNumber.u.bits.dev = dev; pciNumber.u.bits.bus = bus; pciNumber.u.bits.func = 0; pciNumber.u.bits.ce = 1; outl(pciNumber.u.AsUlong,(PULONG)0xcf8); data = inl((PULONG)0xcfc); if(data != 0xFFFFFFFF) // valid device { if((pVendorName = FindPCIVendorName((USHORT)data)) ) { PICE_sprintf(tempCmd,"Bus%-8uDev%-8u === %.4X %.4X %s ====\n",bus,dev,(USHORT)data,(USHORT)(data>>16),pVendorName); } else { PICE_sprintf(tempCmd,"Bus%-8uDev%-8u === %.4X %.4X N/A ====\n",bus,dev,(USHORT)data,(USHORT)(data>>16)); } Print(OUTPUT_WINDOW,tempCmd); if(WaitForKey()==FALSE)goto CommonShowPCIExit; p = (PULONG)&pciConfig; for(reg=0;regCount == 1) { } return TRUE; } //************************************************************************* // SetKeyboardLayout() // //************************************************************************* COMMAND_PROTOTYPE(SetKeyboardLayout) { PKEYBOARD_LAYOUT layout; ENTER_FUNC(); layout = GetKeyboardLayout(); switch(pArgs->Count) { case 0: PICE_sprintf(tempCmd,"current layout = %s\n", layout->name); Print(OUTPUT_WINDOW,tempCmd); break; case 1: layout = SetKeyboardLayoutByName((LPSTR)pArgs->Value[0]); PICE_sprintf(tempCmd,"current layout = %s\n", layout->name); Print(OUTPUT_WINDOW,tempCmd); break; } LEAVE_FUNC(); return TRUE; } //************************************************************************* // ShowSysCallTable() // //************************************************************************* COMMAND_PROTOTYPE(ShowSysCallTable) { #if 0 LPSTR pName; ULONG i; ENTER_FUNC(); if(pArgs->Count == 0) { PICE_sprintf(tempCmd,"%u system calls\n",190); Print(OUTPUT_WINDOW,tempCmd); if(WaitForKey()!=FALSE) for(i=0;i<190;i++) { if((pName = FindFunctionByAddress(sys_call_table[i],NULL,NULL)) ) { PICE_sprintf(tempCmd,"%-.3u: %.8X (%s)\n",i,sys_call_table[i],pName); } else { PICE_sprintf(tempCmd,"%-.3u: %.8X (%s)\n",i,sys_call_table[i],pName); } Print(OUTPUT_WINDOW,tempCmd); if(WaitForKey()==FALSE) break; } } else if(pArgs->Count == 1) { i = pArgs->Value[0]; if(i<190) { if((pName = FindFunctionByAddress(sys_call_table[i],NULL,NULL)) ) { PICE_sprintf(tempCmd,"%-.3u: %.8X (%s)\n",i,sys_call_table[i],pName); } else { PICE_sprintf(tempCmd,"%-.3u: %.8X (%s)\n",i,sys_call_table[i],pName); } Print(OUTPUT_WINDOW,tempCmd); } } LEAVE_FUNC(); #endif PICE_sprintf(tempCmd,"Not implemented yet!\n"); Print(OUTPUT_WINDOW,tempCmd); return TRUE; } //************************************************************************* // SetAltKey() // //************************************************************************* COMMAND_PROTOTYPE(SetAltKey) { if(pArgs->Count == 1) { ucBreakKey = (UCHAR)pArgs->Value[0]; PICE_sprintf(tempCmd,"new break key is CTRL-%c\n",ucBreakKey); Print(OUTPUT_WINDOW,tempCmd); } else if(pArgs->Count == 0) { PICE_sprintf(tempCmd,"current break key is CTRL-%c\n",ucBreakKey); Print(OUTPUT_WINDOW,tempCmd); } COMMAND_RET; } //************************************************************************* // ShowContext() // //************************************************************************* COMMAND_PROTOTYPE(ShowContext) { COMMAND_RET; } //************************************************************************* // // utility functions for parsing // //************************************************************************* //************************************************************************* // FindCommand() // //************************************************************************* LPSTR FindCommand(LPSTR p) { ULONG i,j,k=0; LPSTR result=NULL; tempCmd[0]=0; for(j=0,i=0;CmdTable[i].Cmd!=NULL;i++) { if(PICE_strncmpi(CmdTable[i].Cmd,p,PICE_strlen(p)) == 0 && CmdTable[i].CommandGroup != COMMAND_GROUP_HELP_ONLY) { if(PICE_strlen(tempCmd)) PICE_strcat(tempCmd,", "); PICE_strcat(tempCmd,CmdTable[i].Cmd); j++; k=i; } } if(PICE_strlen(tempCmd)) { SetBackgroundColor(COLOR_CAPTION); SetForegroundColor(COLOR_TEXT); ClrLine(wWindow[OUTPUT_WINDOW].y+wWindow[OUTPUT_WINDOW].cy); PutChar(tempCmd,1,wWindow[OUTPUT_WINDOW].y+wWindow[OUTPUT_WINDOW].cy); if(j==1) { PICE_sprintf(tempCmd,"%s",CmdTable[k].Help); PutChar(tempCmd,40,wWindow[OUTPUT_WINDOW].y+wWindow[OUTPUT_WINDOW].cy); result=CmdTable[k].Cmd; } ResetColor(); } return result; } //************************************************************************* // CompactString() // //************************************************************************* void CompactString(LPSTR p) { ULONG i; for(i=1;i='0' && p[i]<='9') { result<<=4; result|=(ULONG)(UCHAR)(p[i]-'0'); } else if(p[i]>='A' && p[i]<='F') { result<<=4; result|=(ULONG)(UCHAR)(p[i]-'A'+10); } else if(p[i]>='a' && p[i]<='f') { result<<=4; result|=(ULONG)(UCHAR)(p[i]-'a'+10); } else return FALSE; } p+=(i+1); if(p[i]==':') { ULONG ulSelector=result; if(ulSelector>0xFFFF) return FALSE; for(i=0;i<8 && p[i]!=0 && p[i]!=' ' && p[i]!=':';i++) { if(p[i]>='0' && p[i]<='9') { result<<=4; result|=(ULONG)(UCHAR)(p[i]-'0'); } else if(p[i]>='A' && p[i]<='F') { result<<=4; result|=(ULONG)(UCHAR)(p[i]-'A'+10); } else if(p[i]>='a' && p[i]<='f') { result<<=4; result|=(ULONG)(UCHAR)(p[i]-'a'+10); } else return FALSE; } gCurrentSelector=(USHORT)ulSelector; gCurrentOffset=result; result = GetLinearAddress((USHORT)ulSelector,result); } *pValue=result; return TRUE; } //************************************************************************* // ConvertTokenToDec() // //************************************************************************* BOOLEAN ConvertTokenToDec(LPSTR p,PULONG pValue) { ULONG result=0; char c; while((c = *p)) { if(c >= '0' && c <= '9') { result *= 10; result += (ULONG)(c - '0'); } else return FALSE; p++; } *pValue = result; return TRUE; } //************************************************************************* // ConvertTokenToSymbol() // //************************************************************************* BOOLEAN ConvertTokenToSymbol(LPSTR pToken,PULONG pValue) { LPSTR pEx; char temp[64]; LPSTR p; PDEBUG_MODULE pModFound; DPRINT((0,"ConvertTokenToSymbol()\n")); PICE_strcpy(temp,pToken); p = temp; // test for module!symbol string pEx = PICE_strchr(p,'!'); if(pEx) { DPRINT((0,"ConvertTokenToSymbol(): module!symbol syntax detected\n")); // terminate module name *pEx = 0; // now we have two pointers pEx++; DPRINT((0,"ConvertTokenToSymbol(): module = %s symbol = %s\n",p,pEx)); if( pModFound=IsModuleLoaded(p) ) { if((*pValue = FindFunctionInModuleByName(pEx,pModFound))) return TRUE; } } else { if(pCurrentMod) { if((*pValue = FindFunctionInModuleByName(p,pCurrentMod))) return TRUE; } return ScanExports(p,pValue); } return FALSE; } //************************************************************************* // ConvertTokenToModuleAndName() // //************************************************************************* BOOLEAN ConvertTokenToModuleAndName(LPSTR pToken,PULONG pulModuleName,PULONG pulFunctionName) { LPSTR pEx; char temp[64]; LPSTR p; static char module_name[128]; static char function_name[128]; // test for module!symbol string PICE_strcpy(temp,pToken); p = temp; DPRINT((0,"ConvertTokenToModuleAndName(%s)\n",p)); pEx = PICE_strchr(p,'!'); if(pEx) { DPRINT((0,"ConvertTokenToModuleAndName(): module!symbol syntax detected\n")); // terminate module name *pEx = 0; // now we have two pointers pEx++; DPRINT((0,"ConvertTokenToModuleAndName(): module = %s symbol = %s\n",p,pEx)); PICE_strcpy(module_name,p); PICE_strcpy(function_name,pEx); *pulModuleName = (ULONG)module_name; *pulFunctionName = (ULONG)function_name; return TRUE; } return FALSE; } //************************************************************************* // ConvertTokenToModule() // // convert an argument module name to a pointer to the module's symbols //************************************************************************* BOOLEAN ConvertTokenToModule(LPSTR p,PULONG pValue) { ULONG i; char temp[DEBUG_MODULE_NAME_LEN]; for(i=0;iname); if(PICE_strcmpi(p,temp)==0) { *pValue = (ULONG)apSymbols[i]; return TRUE; } } } for(i=0;iname); if(PICE_strncmpi(temp,p,PICE_strlen(p))==0) { *pValue = (ULONG)apSymbols[i]; return TRUE; } } } return FALSE; } //************************************************************************* // ConvertTokenToProcess() // //************************************************************************* BOOLEAN ConvertTokenToProcess(LPSTR p,PULONG pValue) { return FALSE; } //************************************************************************* // ReplaceKeywordWithValue() // //************************************************************************* BOOLEAN ReplaceKeywordWithValue(LPSTR p,PULONG pValue,KEYWORDS* pKeyWords) { ULONG i; for(i=0;pKeyWords[i].KeyWord!=NULL;i++) { if(PICE_strcmpi(p,pKeyWords[i].KeyWord)==0) { switch(pKeyWords[i].ulSize) { case sizeof(USHORT): *pValue=(ULONG)*(PUSHORT)(pKeyWords[i].pValue); break; case sizeof(ULONG): *pValue=*(PULONG)(pKeyWords[i].pValue); break; } return TRUE; } } return FALSE; } //************************************************************************* // ConvertTokenToKeyword() // //************************************************************************* BOOLEAN ConvertTokenToKeyword(LPSTR p,PULONG pValue) { char Name[256]; ULONG count; DPRINT((0,"ConvertTokenToKeyword()\n")); count=StrLenUpToWhiteChar(p," "); PICE_strncpy(Name,p,count); Name[count]=0; if(ReplaceKeywordWithValue(Name,pValue,RegKeyWords)) { DPRINT((0,"ConvertTokenToKeyword(): success\n")); return TRUE; } return FALSE; } //************************************************************************* // ConvertTokenToSpecialKeyword() // //************************************************************************* BOOLEAN ConvertTokenToSpecialKeyword(LPSTR p,PULONG pValue) { char Name[256]; ULONG count; count=StrLenUpToWhiteChar(p," "); PICE_strncpy(Name,p,count); Name[count]=0; if(ReplaceKeywordWithValue(Name,pValue,SpecialKeyWords)) { return TRUE; } return FALSE; } //************************************************************************* // ConvertTokenToOnOff() // //************************************************************************* BOOLEAN ConvertTokenToOnOff(LPSTR p,PULONG pValue) { char Name[256]; ULONG count; count=StrLenUpToWhiteChar(p," "); PICE_strncpy(Name,p,count); Name[count]=0; if(ReplaceKeywordWithValue(Name,pValue,OnOffKeyWords)) { return TRUE; } return FALSE; } //************************************************************************* // ConvertSizeToKeyword() // //************************************************************************* BOOLEAN ConvertSizeToKeyword(LPSTR p,PULONG pValue) { ULONG count; count=StrLenUpToWhiteChar(p," "); if(count > 1) return FALSE; switch(*p) { // BYTE case 'b': case 'B': *pValue = 1; break; // WORD case 'w': case 'W': *pValue = 2; break; // DWORD case 'd': case 'D': *pValue = 4; break; // QWORD case 'q': case 'Q': *pValue = 4; break; default: return FALSE; } return TRUE; } //************************************************************************* // ConvertTokenToSrcFile() // //************************************************************************* BOOLEAN ConvertTokenToSrcFile(LPSTR p,PULONG pValue) { PICE_SYMBOLFILE_SOURCE* pSrc; LPSTR pFilename,pFilenameSrc; ULONG i; DPRINT((0,"ConvertTokenToSrcFile(%s)\n",p)); if(pCurrentSymbols && pCurrentSymbols->ulNumberOfSrcFiles) { DPRINT((0,"ConvertTokenToSrcFile(): current symbols for %S\n",pCurrentSymbols->name)); pSrc = (PICE_SYMBOLFILE_SOURCE*)((ULONG)pCurrentSymbols + pCurrentSymbols->ulOffsetToSrcFiles); for(i=0;iulNumberOfSrcFiles;i++) { pFilename = strrchr(pSrc->filename,'/'); if(!pFilename) pFilename = pSrc->filename; else pFilename++; pFilenameSrc = strrchr(p,'/'); if(!pFilenameSrc ) pFilenameSrc = p; else pFilenameSrc++; DPRINT((0,"ConvertTokenToSrcFile(): %s\n",pFilename)); if(PICE_strcmpi(pFilename,pFilenameSrc) == 0) { DPRINT((0,"ConvertTokenToSrcFile(): found %s\n",pFilename)); *pValue = (ULONG)pSrc; return TRUE; } // go to next file (LPSTR)pSrc += pSrc->ulOffsetToNext; } pSrc = (PICE_SYMBOLFILE_SOURCE*)((ULONG)pCurrentSymbols + pCurrentSymbols->ulOffsetToSrcFiles); // if not found now do a lookup for partials for(i=0;iulNumberOfSrcFiles;i++) { pFilename = strrchr(pSrc->filename,'/'); if(!pFilename) pFilename = pSrc->filename; else pFilename++; DPRINT((0,"ConvertTokenToSrcFile(): %s\n",pFilename)); if(PICE_strncmpi(pFilename,p,PICE_strlen(p)) == 0) { DPRINT((0,"ConvertTokenToSrcFile(): found %s\n",pFilename)); *pValue = (ULONG)pSrc; return TRUE; } // go to next file (LPSTR)pSrc += pSrc->ulOffsetToNext; } } return FALSE; } //************************************************************************* // ConvertTokenToLineNumber() // //************************************************************************* BOOLEAN ConvertTokenToLineNumber(LPSTR p,PULONG pValue) { ULONG ulDecimal; DPRINT((0,"ConvertTokenToLineNumber()\n")); if(*p++ == '.') { ulDecimal = ExtractNumber(p); DPRINT((0,"ConvertTokenToLineNumber(): ulDecimal = %u\n",ulDecimal)); if(ulDecimal) { DPRINT((0,"ConvertTokenToLineNumber(): current file = %s\n",szCurrentFile)); if(pCurrentMod && PICE_strlen(szCurrentFile)) { DPRINT((0,"ConvertTokenToLineNumber(): current file %S\n",pCurrentMod->name)); if(FindAddressForSourceLine(ulDecimal,szCurrentFile,pCurrentMod,pValue)) { DPRINT((0,"ConvertTokenToLineNumber(): value = %x\n",*pValue)); return TRUE; } } } } return FALSE; } //************************************************************************* // IsWhiteChar() // //************************************************************************* BOOLEAN IsWhiteChar(char c,LPSTR WhiteChars) { USHORT lenWhiteChar = PICE_strlen(WhiteChars); USHORT i; for(i=0;iFlags & COMMAND_HAS_SWITCHES) { // token starts with '-' and is 2 chars long // must be a switch if(PICE_strchr(pCurrentCommand->pszRecognizedSwitches,*(pToken+1)) ) { DPRINT((0,"is a switch!\n")); Arguments.Switch[j++]=*(pToken+1); continue; } // not a valid switch else { PICE_sprintf(tempCmd," <-- %s is not a valid switch\n",pToken); Print(OUTPUT_WINDOW,tempCmd); Print(OUTPUT_WINDOW,":"); goto CommonParseReturnPoint; } } else { PICE_sprintf(tempCmd," <-- %s can't have any switches\n",pCurrentCommand->Cmd); Print(OUTPUT_WINDOW,tempCmd); Print(OUTPUT_WINDOW,":"); goto CommonParseReturnPoint; } } if(pCurrentCommand->Flags & COMMAND_HAS_PARAMS) { if(!pCurrentCommand->ParamFlags[i]) { PICE_sprintf(tempCmd," <-- %s can't have more than %u parameters\n",pCurrentCommand->Cmd,i); Print(OUTPUT_WINDOW,tempCmd); Print(OUTPUT_WINDOW,":"); goto CommonParseReturnPoint; } DPRINT((0,"Parse(): PARAM_CAN_BE_SRCLINE\n")); if(pCurrentCommand->ParamFlags[i] & PARAM_CAN_BE_SRCLINE) { if(ConvertTokenToLineNumber(pToken,&Arguments.Value[i])) { i++; continue; } if(*pToken == '.') { PICE_sprintf(tempCmd," <-- no line number %s found\n",pToken); Print(OUTPUT_WINDOW,tempCmd); Print(OUTPUT_WINDOW,":"); goto CommonParseReturnPoint; } } DPRINT((0,"Parse(): PARAM_CAN_BE_NUMERIC\n")); if(pCurrentCommand->ParamFlags[i] & PARAM_CAN_BE_NUMERIC) { if(ConvertTokenToHex(pToken,&Arguments.Value[i])) { i++; continue; } } DPRINT((0,"Parse(): PARAM_CAN_BE_DECIMAL\n")); if(pCurrentCommand->ParamFlags[i] & PARAM_CAN_BE_DECIMAL) { if(ConvertTokenToDec(pToken,&Arguments.Value[i])) { i++; continue; } } DPRINT((0,"Parse(): PARAM_CAN_BE_REG_KEYWORD\n")); if(pCurrentCommand->ParamFlags[i] & PARAM_CAN_BE_REG_KEYWORD) { if(ConvertTokenToKeyword(pToken,&Arguments.Value[i])) { Arguments.pToken[i] = pToken; i++; continue; } } DPRINT((0,"Parse(): PARAM_CAN_BE_SYMBOLIC\n")); if(pCurrentCommand->ParamFlags[i] & PARAM_CAN_BE_SYMBOLIC) { if(ConvertTokenToSymbol(pToken,&Arguments.Value[i])) { i++; continue; } } DPRINT((0,"Parse(): PARAM_CAN_BE_VIRTUAL_SYMBOLIC\n")); if(pCurrentCommand->ParamFlags[i] & PARAM_CAN_BE_VIRTUAL_SYMBOLIC) { DPRINT((0,"might be a virtual modname!symbol syntax!\n")); if(ConvertTokenToModuleAndName(pToken,&Arguments.Value[i],&Arguments.Value[i+1])) { Arguments.bNotTranslated[i]=TRUE; Arguments.bNotTranslated[i+1]=TRUE; i+=2; continue; } } DPRINT((0,"Parse(): PARAM_CAN_BE_MODULE\n")); if(pCurrentCommand->ParamFlags[i] & PARAM_CAN_BE_MODULE) { if(ConvertTokenToModule(pToken,&Arguments.Value[i])) { i++; continue; } } DPRINT((0,"Parse(): PARAM_CAN_BE_PRNAME\n")); if(pCurrentCommand->ParamFlags[i] & PARAM_CAN_BE_PRNAME) { if(ConvertTokenToProcess(pToken,&Arguments.Value[i])) { i++; continue; } } DPRINT((0,"Parse(): PARAM_CAN_BE_SRC_FILE\n")); if(pCurrentCommand->ParamFlags[i] & PARAM_CAN_BE_SRC_FILE) { if(ConvertTokenToSrcFile(pToken,&Arguments.Value[i])) { i++; continue; } } DPRINT((0,"Parse(): PARAM_CAN_BE_ASTERISK\n")); if(pCurrentCommand->ParamFlags[i] & PARAM_CAN_BE_ASTERISK) { if(PICE_strlen(pToken)==1 && pToken[0]=='*') { Arguments.Value[i]=-1; i++; continue; } } DPRINT((0,"Parse(): PARAM_CAN_BE_LETTER\n")); if(pCurrentCommand->ParamFlags[i] & PARAM_CAN_BE_LETTER) { if(PICE_strlen(pToken)==1 && PICE_isprint(pToken[0])) { Arguments.Value[i]=(ULONG)pToken[0]; i++; continue; } } DPRINT((0,"Parse(): PARAM_CAN_BE_ONOFF\n")); if(pCurrentCommand->ParamFlags[i] & PARAM_CAN_BE_ONOFF) { if(ConvertTokenToOnOff(pToken,&Arguments.Value[i])) { i++; continue; } } DPRINT((0,"Parse(): PARAM_CAN_BE_PARTIAL_SYM_NAME\n")); if(pCurrentCommand->ParamFlags[i] & PARAM_CAN_BE_PARTIAL_SYM_NAME) { Arguments.Value[i] = (ULONG)pToken; i++; continue; } DPRINT((0,"Parse(): PARAM_CAN_BE_ANY_STRING\n")); if(pCurrentCommand->ParamFlags[i] & PARAM_CAN_BE_ANY_STRING) { Arguments.Value[i] = (ULONG)pToken; i++; continue; } DPRINT((0,"Parse(): PARAM_CAN_BE_SIZE_DESC\n")); if(pCurrentCommand->ParamFlags[i] & PARAM_CAN_BE_SIZE_DESC) { if(ConvertSizeToKeyword(pToken,&Arguments.Value[i])) { Arguments.pToken[i] = pToken; i++; continue; } } PICE_sprintf(tempCmd," <-- syntax error in parameter %u!\n",i); Print(OUTPUT_WINDOW,tempCmd); Print(OUTPUT_WINDOW,":"); goto CommonParseReturnPoint; } else { PICE_sprintf(tempCmd," <-- %s has no parameters\n",pCurrentCommand->Cmd); Print(OUTPUT_WINDOW,tempCmd); Print(OUTPUT_WINDOW,":"); goto CommonParseReturnPoint; } // next token i++; } }while(pToken && iCmd,Arguments.CountSwitches)); if(!bInvokedByFkey) { DPRINT((0,"Parse(): adding new line\n")); Print(OUTPUT_WINDOW,"\n"); } // call the command handler result=pCurrentCommand->Handler(&Arguments); if(result && !bInvokedByFkey && pCurrentCommand->Handler!=LeaveIce && pCurrentCommand->Handler!=SingleStep ) { DPRINT((0,"Parse(): adding colon\n")); Print(OUTPUT_WINDOW,":"); } } CommonParseReturnPoint: SuspendPrintRingBuffer(FALSE); PrintRingBuffer(wWindow[OUTPUT_WINDOW].cy-1); ShowStatusLine(); }