diff options
-rw-r--r-- | engines/sci/console.cpp | 29 | ||||
-rw-r--r-- | engines/sci/debug.h | 10 | ||||
-rw-r--r-- | engines/sci/engine/scriptdebug.cpp | 22 |
3 files changed, 50 insertions, 11 deletions
diff --git a/engines/sci/console.cpp b/engines/sci/console.cpp index 6efe6849bb..eccd94e30e 100644 --- a/engines/sci/console.cpp +++ b/engines/sci/console.cpp @@ -3741,6 +3741,12 @@ bool Console::cmdBreakpointList(int argc, const char **argv) { case BREAK_BACKTRACE: bpaction = " (action: show backtrace)"; break; + case BREAK_INSPECT: + bpaction = " (action: show object)"; + break; + case BREAK_NONE: + bpaction = " (action: ignore)"; + break; default: bpaction = ""; } @@ -3802,13 +3808,7 @@ bool Console::cmdBreakpointDelete(int argc, const char **argv) { // Delete it _debugState._breakpoints.erase(bp); - // Update EngineState::_activeBreakpointTypes. - int type = 0; - for (bp = _debugState._breakpoints.begin(); bp != end; ++bp) { - type |= bp->_type; - } - - _debugState._activeBreakpointTypes = type; + _debugState.updateActiveBreakpointTypes(); return true; } @@ -3831,13 +3831,22 @@ bool Console::cmdBreakpointAction(int argc, const char **argv) { bpaction = BREAK_LOG; else if (arg == "bt") bpaction = BREAK_BACKTRACE; + else if (arg == "inspect") + bpaction = BREAK_INSPECT; + else if (arg == "none") + bpaction = BREAK_NONE; else usage = true; if (usage) { debugPrintf("Change the action for the breakpoint with the specified index.\n"); - debugPrintf("Usage: %s <breakpoint index> break|log|bt\n", argv[0]); + debugPrintf("Usage: %s <breakpoint index> break|log|bt|inspect|none\n", argv[0]); debugPrintf("<index> * will process all breakpoints\n"); + debugPrintf("Actions: break : break into debugger\n"); + debugPrintf(" log : log without breaking\n"); + debugPrintf(" bt : show backtrace without breaking\n"); + debugPrintf(" inspect: show object (only for bpx/bpr/bpw)\n"); + debugPrintf(" none : ignore breakpoint\n"); return true; } @@ -3846,6 +3855,7 @@ bool Console::cmdBreakpointAction(int argc, const char **argv) { if (strcmp(argv[1], "*") == 0) { for (; bp != end; ++bp) bp->_action = bpaction; + _debugState.updateActiveBreakpointTypes(); return true; } @@ -3862,6 +3872,9 @@ bool Console::cmdBreakpointAction(int argc, const char **argv) { } bp->_action = bpaction; + + _debugState.updateActiveBreakpointTypes(); + return true; } diff --git a/engines/sci/debug.h b/engines/sci/debug.h index 03ab594e0d..afcac19f04 100644 --- a/engines/sci/debug.h +++ b/engines/sci/debug.h @@ -47,9 +47,11 @@ enum BreakpointType { }; enum BreakpointAction { - BREAK_BREAK, // break into debugger when breakpoint is triggered - BREAK_LOG, // log the breakpoint, and don't break into debugger - BREAK_BACKTRACE // show a backtrace, and don't break into debugger + BREAK_NONE, // ignore breakpoint + BREAK_BREAK, // break into debugger when breakpoint is triggered + BREAK_LOG, // log the breakpoint, and don't break into debugger + BREAK_BACKTRACE, // show a backtrace, and don't break into debugger + BREAK_INSPECT // show object, and don't break into debugger }; struct Breakpoint { @@ -81,6 +83,8 @@ struct DebugState { StackPtr old_sp; Common::List<Breakpoint> _breakpoints; //< List of breakpoints int _activeBreakpointTypes; //< Bit mask specifying which types of breakpoints are active + + void updateActiveBreakpointTypes(); }; // Various global variables used for debugging are declared here diff --git a/engines/sci/engine/scriptdebug.cpp b/engines/sci/engine/scriptdebug.cpp index ce1d2dd1f3..277c6b034e 100644 --- a/engines/sci/engine/scriptdebug.cpp +++ b/engines/sci/engine/scriptdebug.cpp @@ -68,6 +68,16 @@ const char *opcodeNames[] = { }; #endif // REDUCE_MEMORY_USAGE +void DebugState::updateActiveBreakpointTypes() { + int type = 0; + for (Common::List<Breakpoint>::iterator bp = _breakpoints.begin(); bp != _breakpoints.end(); ++bp) { + if (bp->_action != BREAK_NONE) + type |= bp->_type; + } + + _activeBreakpointTypes = type; +} + // Disassembles one command from the heap, returns address of next command or 0 if a ret was encountered. reg_t disassemble(EngineState *s, reg32_t pos, reg_t objAddr, bool printBWTag, bool printBytecode) { SegmentObj *mobj = s->_segMan->getSegment(pos.getSegment(), SEG_TYPE_SCRIPT); @@ -688,6 +698,8 @@ bool SciEngine::checkSelectorBreakpoint(BreakpointType breakpointType, reg_t sen for (bpIter = _debugState._breakpoints.begin(); bpIter != _debugState._breakpoints.end(); ++bpIter) { if (bpIter->_type != breakpointType) continue; + if (bpIter->_action == BREAK_NONE) + continue; if (bpIter->_name == methodName || (bpIter->_name.hasSuffix("::") && methodName.hasPrefix(bpIter->_name))) { _console->debugPrintf("Break on %s (in [%04x:%04x])\n", methodName.c_str(), PRINT_REG(send_obj)); @@ -696,6 +708,8 @@ bool SciEngine::checkSelectorBreakpoint(BreakpointType breakpointType, reg_t sen _debugState.breakpointWasHit = true; } else if (bpIter->_action == BREAK_BACKTRACE) { logBacktrace(); + } else if (bpIter->_action == BREAK_INSPECT) { + printObject(send_obj); } return true; } @@ -709,6 +723,8 @@ bool SciEngine::checkExportBreakpoint(uint16 script, uint16 pubfunct) { Common::List<Breakpoint>::const_iterator bp; for (bp = _debugState._breakpoints.begin(); bp != _debugState._breakpoints.end(); ++bp) { + if (bp->_action == BREAK_NONE) + continue; if (bp->_type == BREAK_EXPORT && bp->_address == bpaddress) { _console->debugPrintf("Break on script %d, export %d\n", script, pubfunct); if (bp->_action == BREAK_BREAK) { @@ -716,6 +732,8 @@ bool SciEngine::checkExportBreakpoint(uint16 script, uint16 pubfunct) { _debugState.breakpointWasHit = true; } else if (bp->_action == BREAK_BACKTRACE) { logBacktrace(); + } else if (bp->_action == BREAK_INSPECT) { + // Ignoring this mode, to make it identical to BREAK_LOG } return true; } @@ -729,6 +747,8 @@ bool SciEngine::checkAddressBreakpoint(const reg32_t &address) { if (_debugState._activeBreakpointTypes & BREAK_ADDRESS) { Common::List<Breakpoint>::const_iterator bp; for (bp = _debugState._breakpoints.begin(); bp != _debugState._breakpoints.end(); ++bp) { + if (bp->_action == BREAK_NONE) + continue; if (bp->_type == BREAK_ADDRESS && bp->_regAddress == address) { _console->debugPrintf("Break at %04x:%04x\n", PRINT_REG(address)); if (bp->_action == BREAK_BREAK) { @@ -736,6 +756,8 @@ bool SciEngine::checkAddressBreakpoint(const reg32_t &address) { _debugState.breakpointWasHit = true; } else if (bp->_action == BREAK_BACKTRACE) { logBacktrace(); + } else if (bp->_action == BREAK_INSPECT) { + // Ignoring this mode, to make it identical to BREAK_LOG } return true; } |