mirror of
https://github.com/AppleWin/AppleWin.git
synced 2024-06-27 07:29:30 +00:00
.21 Added: Help for BRK
.20 Moved: BRK and BRKOP now under HELP BREAKPOINTS .19 Added: Shift-F7 will run the emulator at normal speed but with debugger breakpoints active .18 Added: Implemented BPIO -- currently is the same as BPM
This commit is contained in:
parent
56b772af43
commit
195775b703
|
@ -1,5 +1,9 @@
|
||||||
/*
|
/*
|
||||||
2.7.0.#
|
2.7.0.#
|
||||||
|
.21 Added: Help for BRK
|
||||||
|
.20 Moved: BRK and BRKOP now under HELP BREAKPOINTS
|
||||||
|
.19 Added: Shift-F7 will run the emulator at normal speed but with debugger breakpoints active!
|
||||||
|
.18 Added: Implemented BPIO -- currently is the same as BPM
|
||||||
.17 Fixed: HELP <category> wasn't displaying when category was one of: FLAGS, OUTPUT, WATCHES
|
.17 Fixed: HELP <category> wasn't displaying when category was one of: FLAGS, OUTPUT, WATCHES
|
||||||
.16 Fixed: WL was displaying number of watches
|
.16 Fixed: WL was displaying number of watches
|
||||||
.15 Fixed: Memory Dump was over-writing watches.
|
.15 Fixed: Memory Dump was over-writing watches.
|
||||||
|
|
|
@ -160,30 +160,8 @@ void RequestDebugger()
|
||||||
FrameWndProc( g_hFrameWindow, WM_KEYUP , DEBUG_TOGGLE_KEY, 0 );
|
FrameWndProc( g_hFrameWindow, WM_KEYUP , DEBUG_TOGGLE_KEY, 0 );
|
||||||
}
|
}
|
||||||
|
|
||||||
bool CheckDebugBreak( int iOpcode )
|
|
||||||
{
|
|
||||||
if (g_bDebugDelayBreakCheck)
|
|
||||||
{
|
|
||||||
g_bDebugDelayBreakCheck = false;
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Running at full speed? (debugger not running)
|
|
||||||
if ((g_nAppMode != MODE_DEBUG) && (g_nAppMode != MODE_STEPPING))
|
|
||||||
{
|
|
||||||
if (((iOpcode == 0) && IsDebugBreakOnInvalid(0)) ||
|
|
||||||
((g_iDebugOnOpcode) && (g_iDebugOnOpcode == iOpcode))) // User wants to enter debugger on opcode?
|
|
||||||
{
|
|
||||||
RequestDebugger();
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Break into debugger on invalid opcodes
|
// Break into debugger on invalid opcodes
|
||||||
#define INV if (IsDebugBreakOnInvalid(1)) { RequestDebugger(); bBreakOnInvalid = true; }
|
#define INV IsDebugBreakOnInvalid(AM_1);
|
||||||
|
|
||||||
/****************************************************************************
|
/****************************************************************************
|
||||||
*
|
*
|
||||||
|
@ -314,7 +292,7 @@ static __forceinline int Fetch(BYTE& iOpcode, ULONG uExecutedCycles)
|
||||||
? IORead[(PC>>4) & 0xFF](PC,PC,0,0,uExecutedCycles) // Fetch opcode from I/O memory, but params are still from mem[]
|
? IORead[(PC>>4) & 0xFF](PC,PC,0,0,uExecutedCycles) // Fetch opcode from I/O memory, but params are still from mem[]
|
||||||
: *(mem+PC);
|
: *(mem+PC);
|
||||||
|
|
||||||
if (CheckDebugBreak( iOpcode ))
|
if (IsDebugBreakOpcode( iOpcode ))
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
#ifdef USE_SPEECH_API
|
#ifdef USE_SPEECH_API
|
||||||
|
@ -376,7 +354,7 @@ static __forceinline void CheckInterruptSources(ULONG uExecutedCycles)
|
||||||
|
|
||||||
#include "cpu/cpu6502.h" // MOS 6502
|
#include "cpu/cpu6502.h" // MOS 6502
|
||||||
#include "cpu/cpu65C02.h" // WDC 65C02
|
#include "cpu/cpu65C02.h" // WDC 65C02
|
||||||
#include "cpu/cpu65d02.h" // Debug Cpu
|
#include "cpu/cpu65d02.h" // Debug CPU Memory Visualizer
|
||||||
|
|
||||||
//===========================================================================
|
//===========================================================================
|
||||||
|
|
||||||
|
|
|
@ -4,7 +4,7 @@ AppleWin : An Apple //e emulator for Windows
|
||||||
Copyright (C) 1994-1996, Michael O'Brien
|
Copyright (C) 1994-1996, Michael O'Brien
|
||||||
Copyright (C) 1999-2001, Oliver Schmidt
|
Copyright (C) 1999-2001, Oliver Schmidt
|
||||||
Copyright (C) 2002-2005, Tom Charlesworth
|
Copyright (C) 2002-2005, Tom Charlesworth
|
||||||
Copyright (C) 2006-2010, Tom Charlesworth, Michael Pohoreski
|
Copyright (C) 2006-2011, Tom Charlesworth, Michael Pohoreski
|
||||||
|
|
||||||
AppleWin is free software; you can redistribute it and/or modify
|
AppleWin is free software; you can redistribute it and/or modify
|
||||||
it under the terms of the GNU General Public License as published by
|
it under the terms of the GNU General Public License as published by
|
||||||
|
@ -37,7 +37,7 @@ static DWORD Cpu6502 (DWORD uTotalCycles)
|
||||||
ULONG uExecutedCycles = 0;
|
ULONG uExecutedCycles = 0;
|
||||||
BOOL bSlowerOnPagecross = 0; // Set if opcode writes to memory (eg. ASL, STA)
|
BOOL bSlowerOnPagecross = 0; // Set if opcode writes to memory (eg. ASL, STA)
|
||||||
WORD base;
|
WORD base;
|
||||||
bool bBreakOnInvalid = false;
|
g_bDebugBreakpointHit = 0;
|
||||||
|
|
||||||
do
|
do
|
||||||
{
|
{
|
||||||
|
@ -321,12 +321,16 @@ static DWORD Cpu6502 (DWORD uTotalCycles)
|
||||||
NMI(uExecutedCycles, uExtraCycles, flagc, flagn, flagv, flagz);
|
NMI(uExecutedCycles, uExtraCycles, flagc, flagn, flagv, flagz);
|
||||||
IRQ(uExecutedCycles, uExtraCycles, flagc, flagn, flagv, flagz);
|
IRQ(uExecutedCycles, uExtraCycles, flagc, flagn, flagv, flagz);
|
||||||
|
|
||||||
if (bBreakOnInvalid)
|
if ( IsDebugBreakpointHit() )
|
||||||
break;
|
break;
|
||||||
|
|
||||||
} while (uExecutedCycles < uTotalCycles);
|
} while (uExecutedCycles < uTotalCycles);
|
||||||
|
|
||||||
EF_TO_AF
|
EF_TO_AF
|
||||||
|
|
||||||
|
if( g_bDebugBreakpointHit )
|
||||||
|
if ((g_nAppMode != MODE_DEBUG) && (g_nAppMode != MODE_STEPPING)) // Running at full speed? (debugger not running)
|
||||||
|
RequestDebugger();
|
||||||
|
|
||||||
return uExecutedCycles;
|
return uExecutedCycles;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -4,7 +4,7 @@ AppleWin : An Apple //e emulator for Windows
|
||||||
Copyright (C) 1994-1996, Michael O'Brien
|
Copyright (C) 1994-1996, Michael O'Brien
|
||||||
Copyright (C) 1999-2001, Oliver Schmidt
|
Copyright (C) 1999-2001, Oliver Schmidt
|
||||||
Copyright (C) 2002-2005, Tom Charlesworth
|
Copyright (C) 2002-2005, Tom Charlesworth
|
||||||
Copyright (C) 2006-2010, Tom Charlesworth, Michael Pohoreski
|
Copyright (C) 2006-2011, Tom Charlesworth, Michael Pohoreski
|
||||||
|
|
||||||
AppleWin is free software; you can redistribute it and/or modify
|
AppleWin is free software; you can redistribute it and/or modify
|
||||||
it under the terms of the GNU General Public License as published by
|
it under the terms of the GNU General Public License as published by
|
||||||
|
@ -40,7 +40,7 @@ static DWORD Cpu65C02 (DWORD uTotalCycles)
|
||||||
ULONG uExecutedCycles = 0;
|
ULONG uExecutedCycles = 0;
|
||||||
BOOL bSlowerOnPagecross = 0; // Set if opcode writes to memory (eg. ASL, STA)
|
BOOL bSlowerOnPagecross = 0; // Set if opcode writes to memory (eg. ASL, STA)
|
||||||
WORD base;
|
WORD base;
|
||||||
bool bBreakOnInvalid = false;
|
g_bDebugBreakpointHit = 0;
|
||||||
|
|
||||||
do
|
do
|
||||||
{
|
{
|
||||||
|
@ -55,283 +55,287 @@ static DWORD Cpu65C02 (DWORD uTotalCycles)
|
||||||
else
|
else
|
||||||
#endif
|
#endif
|
||||||
{
|
{
|
||||||
if (!Fetch(iOpcode, uExecutedCycles))
|
if (!Fetch(iOpcode, uExecutedCycles))
|
||||||
break;
|
break;
|
||||||
|
|
||||||
switch (iOpcode)
|
switch (iOpcode)
|
||||||
{
|
{
|
||||||
#define $ INV // INV = Invalid -> Debugger Break
|
#define $ INV // INV = Invalid -> Debugger Break
|
||||||
case 0x00: BRK CYC(7) break;
|
case 0x00: BRK CYC(7) break;
|
||||||
case 0x01: idx ORA CYC(6) break;
|
case 0x01: idx ORA CYC(6) break;
|
||||||
case 0x02: $ IMM NOP CYC(2) break;
|
case 0x02: $ IMM NOP CYC(2) break;
|
||||||
case 0x03: $ NOP CYC(2) break;
|
case 0x03: $ NOP CYC(2) break;
|
||||||
case 0x04: ZPG TSB CYC(5) break;
|
case 0x04: ZPG TSB CYC(5) break;
|
||||||
case 0x05: ZPG ORA CYC(3) break;
|
case 0x05: ZPG ORA CYC(3) break;
|
||||||
case 0x06: ZPG ASLc CYC(5) break;
|
case 0x06: ZPG ASLc CYC(5) break;
|
||||||
case 0x07: $ NOP CYC(2) break;
|
case 0x07: $ NOP CYC(2) break;
|
||||||
case 0x08: PHP CYC(3) break;
|
case 0x08: PHP CYC(3) break;
|
||||||
case 0x09: IMM ORA CYC(2) break;
|
case 0x09: IMM ORA CYC(2) break;
|
||||||
case 0x0A: asl CYC(2) break;
|
case 0x0A: asl CYC(2) break;
|
||||||
case 0x0B: $ NOP CYC(2) break;
|
case 0x0B: $ NOP CYC(2) break;
|
||||||
case 0x0C: ABS TSB CYC(6) break;
|
case 0x0C: ABS TSB CYC(6) break;
|
||||||
case 0x0D: ABS ORA CYC(4) break;
|
case 0x0D: ABS ORA CYC(4) break;
|
||||||
case 0x0E: ABS ASLc CYC(6) break;
|
case 0x0E: ABS ASLc CYC(6) break;
|
||||||
case 0x0F: $ NOP CYC(2) break;
|
case 0x0F: $ NOP CYC(2) break;
|
||||||
case 0x10: REL BPL CYC(2) break;
|
case 0x10: REL BPL CYC(2) break;
|
||||||
case 0x11: idy ORA CYC(5) break;
|
case 0x11: idy ORA CYC(5) break;
|
||||||
case 0x12: izp ORA CYC(5) break;
|
case 0x12: izp ORA CYC(5) break;
|
||||||
case 0x13: $ NOP CYC(2) break;
|
case 0x13: $ NOP CYC(2) break;
|
||||||
case 0x14: ZPG TRB CYC(5) break;
|
case 0x14: ZPG TRB CYC(5) break;
|
||||||
case 0x15: zpx ORA CYC(4) break;
|
case 0x15: zpx ORA CYC(4) break;
|
||||||
case 0x16: zpx ASLc CYC(6) break;
|
case 0x16: zpx ASLc CYC(6) break;
|
||||||
case 0x17: $ NOP CYC(2) break;
|
case 0x17: $ NOP CYC(2) break;
|
||||||
case 0x18: CLC CYC(2) break;
|
case 0x18: CLC CYC(2) break;
|
||||||
case 0x19: aby ORA CYC(4) break;
|
case 0x19: aby ORA CYC(4) break;
|
||||||
case 0x1A: INA CYC(2) break;
|
case 0x1A: INA CYC(2) break;
|
||||||
case 0x1B: $ NOP CYC(2) break;
|
case 0x1B: $ NOP CYC(2) break;
|
||||||
case 0x1C: ABS TRB CYC(6) break;
|
case 0x1C: ABS TRB CYC(6) break;
|
||||||
case 0x1D: abx ORA CYC(4) break;
|
case 0x1D: abx ORA CYC(4) break;
|
||||||
case 0x1E: abx ASLc CYC(6) break;
|
case 0x1E: abx ASLc CYC(6) break;
|
||||||
case 0x1F: $ NOP CYC(2) break;
|
case 0x1F: $ NOP CYC(2) break;
|
||||||
case 0x20: ABS JSR CYC(6) break;
|
case 0x20: ABS JSR CYC(6) break;
|
||||||
case 0x21: idx AND CYC(6) break;
|
case 0x21: idx AND CYC(6) break;
|
||||||
case 0x22: $ IMM NOP CYC(2) break;
|
case 0x22: $ IMM NOP CYC(2) break;
|
||||||
case 0x23: $ NOP CYC(2) break;
|
case 0x23: $ NOP CYC(2) break;
|
||||||
case 0x24: ZPG BIT CYC(3) break;
|
case 0x24: ZPG BIT CYC(3) break;
|
||||||
case 0x25: ZPG AND CYC(3) break;
|
case 0x25: ZPG AND CYC(3) break;
|
||||||
case 0x26: ZPG ROLc CYC(5) break;
|
case 0x26: ZPG ROLc CYC(5) break;
|
||||||
case 0x27: $ NOP CYC(2) break;
|
case 0x27: $ NOP CYC(2) break;
|
||||||
case 0x28: PLP CYC(4) break;
|
case 0x28: PLP CYC(4) break;
|
||||||
case 0x29: IMM AND CYC(2) break;
|
case 0x29: IMM AND CYC(2) break;
|
||||||
case 0x2A: rol CYC(2) break;
|
case 0x2A: rol CYC(2) break;
|
||||||
case 0x2B: $ NOP CYC(2) break;
|
case 0x2B: $ NOP CYC(2) break;
|
||||||
case 0x2C: ABS BIT CYC(4) break;
|
case 0x2C: ABS BIT CYC(4) break;
|
||||||
case 0x2D: ABS AND CYC(2) break;
|
case 0x2D: ABS AND CYC(2) break;
|
||||||
case 0x2E: ABS ROLc CYC(6) break;
|
case 0x2E: ABS ROLc CYC(6) break;
|
||||||
case 0x2F: $ NOP CYC(2) break;
|
case 0x2F: $ NOP CYC(2) break;
|
||||||
case 0x30: REL BMI CYC(2) break;
|
case 0x30: REL BMI CYC(2) break;
|
||||||
case 0x31: idy AND CYC(5) break;
|
case 0x31: idy AND CYC(5) break;
|
||||||
case 0x32: izp AND CYC(5) break;
|
case 0x32: izp AND CYC(5) break;
|
||||||
case 0x33: $ NOP CYC(2) break;
|
case 0x33: $ NOP CYC(2) break;
|
||||||
case 0x34: zpx BIT CYC(4) break;
|
case 0x34: zpx BIT CYC(4) break;
|
||||||
case 0x35: zpx AND CYC(4) break;
|
case 0x35: zpx AND CYC(4) break;
|
||||||
case 0x36: zpx ROLc CYC(6) break;
|
case 0x36: zpx ROLc CYC(6) break;
|
||||||
case 0x37: $ NOP CYC(2) break;
|
case 0x37: $ NOP CYC(2) break;
|
||||||
case 0x38: SEC CYC(2) break;
|
case 0x38: SEC CYC(2) break;
|
||||||
case 0x39: aby AND CYC(4) break;
|
case 0x39: aby AND CYC(4) break;
|
||||||
case 0x3A: DEA CYC(2) break;
|
case 0x3A: DEA CYC(2) break;
|
||||||
case 0x3B: $ NOP CYC(2) break;
|
case 0x3B: $ NOP CYC(2) break;
|
||||||
case 0x3C: abx BIT CYC(4) break;
|
case 0x3C: abx BIT CYC(4) break;
|
||||||
case 0x3D: abx AND CYC(4) break;
|
case 0x3D: abx AND CYC(4) break;
|
||||||
case 0x3E: abx ROLc CYC(6) break;
|
case 0x3E: abx ROLc CYC(6) break;
|
||||||
case 0x3F: $ NOP CYC(2) break;
|
case 0x3F: $ NOP CYC(2) break;
|
||||||
case 0x40: RTI CYC(6) DoIrqProfiling(uExecutedCycles); break;
|
case 0x40: RTI CYC(6) DoIrqProfiling(uExecutedCycles); break;
|
||||||
case 0x41: idx EOR CYC(6) break;
|
case 0x41: idx EOR CYC(6) break;
|
||||||
case 0x42: $ IMM NOP CYC(2) break;
|
case 0x42: $ IMM NOP CYC(2) break;
|
||||||
case 0x43: $ NOP CYC(2) break;
|
case 0x43: $ NOP CYC(2) break;
|
||||||
case 0x44: $ ZPG NOP CYC(3) break;
|
case 0x44: $ ZPG NOP CYC(3) break;
|
||||||
case 0x45: ZPG EOR CYC(3) break;
|
case 0x45: ZPG EOR CYC(3) break;
|
||||||
case 0x46: ZPG LSRc CYC(5) break;
|
case 0x46: ZPG LSRc CYC(5) break;
|
||||||
case 0x47: $ NOP CYC(2) break;
|
case 0x47: $ NOP CYC(2) break;
|
||||||
case 0x48: PHA CYC(3) break;
|
case 0x48: PHA CYC(3) break;
|
||||||
case 0x49: IMM EOR CYC(2) break;
|
case 0x49: IMM EOR CYC(2) break;
|
||||||
case 0x4A: lsr CYC(2) break;
|
case 0x4A: lsr CYC(2) break;
|
||||||
case 0x4B: $ NOP CYC(2) break;
|
case 0x4B: $ NOP CYC(2) break;
|
||||||
case 0x4C: ABS JMP CYC(3) break;
|
case 0x4C: ABS JMP CYC(3) break;
|
||||||
case 0x4D: ABS EOR CYC(4) break;
|
case 0x4D: ABS EOR CYC(4) break;
|
||||||
case 0x4E: ABS LSRc CYC(6) break;
|
case 0x4E: ABS LSRc CYC(6) break;
|
||||||
case 0x4F: $ NOP CYC(2) break;
|
case 0x4F: $ NOP CYC(2) break;
|
||||||
case 0x50: REL BVC CYC(2) break;
|
case 0x50: REL BVC CYC(2) break;
|
||||||
case 0x51: idy EOR CYC(5) break;
|
case 0x51: idy EOR CYC(5) break;
|
||||||
case 0x52: izp EOR CYC(5) break;
|
case 0x52: izp EOR CYC(5) break;
|
||||||
case 0x53: $ NOP CYC(2) break;
|
case 0x53: $ NOP CYC(2) break;
|
||||||
case 0x54: $ zpx NOP CYC(4) break;
|
case 0x54: $ zpx NOP CYC(4) break;
|
||||||
case 0x55: zpx EOR CYC(4) break;
|
case 0x55: zpx EOR CYC(4) break;
|
||||||
case 0x56: zpx LSRc CYC(6) break;
|
case 0x56: zpx LSRc CYC(6) break;
|
||||||
case 0x57: $ NOP CYC(2) break;
|
case 0x57: $ NOP CYC(2) break;
|
||||||
case 0x58: CLI CYC(2) break;
|
case 0x58: CLI CYC(2) break;
|
||||||
case 0x59: aby EOR CYC(4) break;
|
case 0x59: aby EOR CYC(4) break;
|
||||||
case 0x5A: PHY CYC(3) break;
|
case 0x5A: PHY CYC(3) break;
|
||||||
case 0x5B: $ NOP CYC(2) break;
|
case 0x5B: $ NOP CYC(2) break;
|
||||||
case 0x5C: $ abx NOP CYC(8) break;
|
case 0x5C: $ abx NOP CYC(8) break;
|
||||||
case 0x5D: abx EOR CYC(4) break;
|
case 0x5D: abx EOR CYC(4) break;
|
||||||
case 0x5E: abx LSRc CYC(6) break;
|
case 0x5E: abx LSRc CYC(6) break;
|
||||||
case 0x5F: $ NOP CYC(2) break;
|
case 0x5F: $ NOP CYC(2) break;
|
||||||
case 0x60: RTS CYC(6) break;
|
case 0x60: RTS CYC(6) break;
|
||||||
case 0x61: idx ADCc CYC(6) break;
|
case 0x61: idx ADCc CYC(6) break;
|
||||||
case 0x62: $ IMM NOP CYC(2) break;
|
case 0x62: $ IMM NOP CYC(2) break;
|
||||||
case 0x63: $ NOP CYC(2) break;
|
case 0x63: $ NOP CYC(2) break;
|
||||||
case 0x64: ZPG STZ CYC(3) break;
|
case 0x64: ZPG STZ CYC(3) break;
|
||||||
case 0x65: ZPG ADCc CYC(3) break;
|
case 0x65: ZPG ADCc CYC(3) break;
|
||||||
case 0x66: ZPG RORc CYC(5) break;
|
case 0x66: ZPG RORc CYC(5) break;
|
||||||
case 0x67: $ NOP CYC(2) break;
|
case 0x67: $ NOP CYC(2) break;
|
||||||
case 0x68: PLA CYC(4) break;
|
case 0x68: PLA CYC(4) break;
|
||||||
case 0x69: IMM ADCc CYC(2) break;
|
case 0x69: IMM ADCc CYC(2) break;
|
||||||
case 0x6A: ror CYC(2) break;
|
case 0x6A: ror CYC(2) break;
|
||||||
case 0x6B: $ NOP CYC(2) break;
|
case 0x6B: $ NOP CYC(2) break;
|
||||||
case 0x6C: IABSCMOS JMP CYC(6) break;
|
case 0x6C: IABSCMOS JMP CYC(6) break;
|
||||||
case 0x6D: ABS ADCc CYC(4) break;
|
case 0x6D: ABS ADCc CYC(4) break;
|
||||||
case 0x6E: ABS RORc CYC(6) break;
|
case 0x6E: ABS RORc CYC(6) break;
|
||||||
case 0x6F: $ NOP CYC(2) break;
|
case 0x6F: $ NOP CYC(2) break;
|
||||||
case 0x70: REL BVS CYC(2) break;
|
case 0x70: REL BVS CYC(2) break;
|
||||||
case 0x71: idy ADCc CYC(5) break;
|
case 0x71: idy ADCc CYC(5) break;
|
||||||
case 0x72: izp ADCc CYC(5) break;
|
case 0x72: izp ADCc CYC(5) break;
|
||||||
case 0x73: $ NOP CYC(2) break;
|
case 0x73: $ NOP CYC(2) break;
|
||||||
case 0x74: zpx STZ CYC(4) break;
|
case 0x74: zpx STZ CYC(4) break;
|
||||||
case 0x75: zpx ADCc CYC(4) break;
|
case 0x75: zpx ADCc CYC(4) break;
|
||||||
case 0x76: zpx RORc CYC(6) break;
|
case 0x76: zpx RORc CYC(6) break;
|
||||||
case 0x77: $ NOP CYC(2) break;
|
case 0x77: $ NOP CYC(2) break;
|
||||||
case 0x78: SEI CYC(2) break;
|
case 0x78: SEI CYC(2) break;
|
||||||
case 0x79: aby ADCc CYC(4) break;
|
case 0x79: aby ADCc CYC(4) break;
|
||||||
case 0x7A: PLY CYC(4) break;
|
case 0x7A: PLY CYC(4) break;
|
||||||
case 0x7B: $ NOP CYC(2) break;
|
case 0x7B: $ NOP CYC(2) break;
|
||||||
case 0x7C: IABSX JMP CYC(6) break; //
|
case 0x7C: IABSX JMP CYC(6) break; //
|
||||||
case 0x7D: abx ADCc CYC(4) break;
|
case 0x7D: abx ADCc CYC(4) break;
|
||||||
case 0x7E: abx RORc CYC(6) break;
|
case 0x7E: abx RORc CYC(6) break;
|
||||||
case 0x7F: $ NOP CYC(2) break;
|
case 0x7F: $ NOP CYC(2) break;
|
||||||
case 0x80: REL BRA CYC(2) break;
|
case 0x80: REL BRA CYC(2) break;
|
||||||
case 0x81: idx STA CYC(6) break;
|
case 0x81: idx STA CYC(6) break;
|
||||||
case 0x82: $ IMM NOP CYC(2) break;
|
case 0x82: $ IMM NOP CYC(2) break;
|
||||||
case 0x83: $ NOP CYC(2) break;
|
case 0x83: $ NOP CYC(2) break;
|
||||||
case 0x84: ZPG STY CYC(3) break;
|
case 0x84: ZPG STY CYC(3) break;
|
||||||
case 0x85: ZPG STA CYC(3) break;
|
case 0x85: ZPG STA CYC(3) break;
|
||||||
case 0x86: ZPG STX CYC(3) break;
|
case 0x86: ZPG STX CYC(3) break;
|
||||||
case 0x87: $ NOP CYC(2) break;
|
case 0x87: $ NOP CYC(2) break;
|
||||||
case 0x88: DEY CYC(2) break;
|
case 0x88: DEY CYC(2) break;
|
||||||
case 0x89: IMM BITI CYC(2) break;
|
case 0x89: IMM BITI CYC(2) break;
|
||||||
case 0x8A: TXA CYC(2) break;
|
case 0x8A: TXA CYC(2) break;
|
||||||
case 0x8B: $ NOP CYC(2) break;
|
case 0x8B: $ NOP CYC(2) break;
|
||||||
case 0x8C: ABS STY CYC(4) break;
|
case 0x8C: ABS STY CYC(4) break;
|
||||||
case 0x8D: ABS STA CYC(4) break;
|
case 0x8D: ABS STA CYC(4) break;
|
||||||
case 0x8E: ABS STX CYC(4) break;
|
case 0x8E: ABS STX CYC(4) break;
|
||||||
case 0x8F: $ NOP CYC(2) break;
|
case 0x8F: $ NOP CYC(2) break;
|
||||||
case 0x90: REL BCC CYC(2) break;
|
case 0x90: REL BCC CYC(2) break;
|
||||||
case 0x91: idy STA CYC(6) break;
|
case 0x91: idy STA CYC(6) break;
|
||||||
case 0x92: izp STA CYC(5) break;
|
case 0x92: izp STA CYC(5) break;
|
||||||
case 0x93: $ NOP CYC(2) break;
|
case 0x93: $ NOP CYC(2) break;
|
||||||
case 0x94: zpx STY CYC(4) break;
|
case 0x94: zpx STY CYC(4) break;
|
||||||
case 0x95: zpx STA CYC(4) break;
|
case 0x95: zpx STA CYC(4) break;
|
||||||
case 0x96: zpy STX CYC(4) break;
|
case 0x96: zpy STX CYC(4) break;
|
||||||
case 0x97: $ NOP CYC(2) break;
|
case 0x97: $ NOP CYC(2) break;
|
||||||
case 0x98: TYA CYC(2) break;
|
case 0x98: TYA CYC(2) break;
|
||||||
case 0x99: aby STA CYC(5) break;
|
case 0x99: aby STA CYC(5) break;
|
||||||
case 0x9A: TXS CYC(2) break;
|
case 0x9A: TXS CYC(2) break;
|
||||||
case 0x9B: $ NOP CYC(2) break;
|
case 0x9B: $ NOP CYC(2) break;
|
||||||
case 0x9C: ABS STZ CYC(4) break;
|
case 0x9C: ABS STZ CYC(4) break;
|
||||||
case 0x9D: abx STA CYC(5) break;
|
case 0x9D: abx STA CYC(5) break;
|
||||||
case 0x9E: abx STZ CYC(5) break;
|
case 0x9E: abx STZ CYC(5) break;
|
||||||
case 0x9F: $ NOP CYC(2) break;
|
case 0x9F: $ NOP CYC(2) break;
|
||||||
case 0xA0: IMM LDY CYC(2) break;
|
case 0xA0: IMM LDY CYC(2) break;
|
||||||
case 0xA1: idx LDA CYC(6) break;
|
case 0xA1: idx LDA CYC(6) break;
|
||||||
case 0xA2: IMM LDX CYC(2) break;
|
case 0xA2: IMM LDX CYC(2) break;
|
||||||
case 0xA3: $ NOP CYC(2) break;
|
case 0xA3: $ NOP CYC(2) break;
|
||||||
case 0xA4: ZPG LDY CYC(3) break;
|
case 0xA4: ZPG LDY CYC(3) break;
|
||||||
case 0xA5: ZPG LDA CYC(3) break;
|
case 0xA5: ZPG LDA CYC(3) break;
|
||||||
case 0xA6: ZPG LDX CYC(3) break;
|
case 0xA6: ZPG LDX CYC(3) break;
|
||||||
case 0xA7: $ NOP CYC(2) break;
|
case 0xA7: $ NOP CYC(2) break;
|
||||||
case 0xA8: TAY CYC(2) break;
|
case 0xA8: TAY CYC(2) break;
|
||||||
case 0xA9: IMM LDA CYC(2) break;
|
case 0xA9: IMM LDA CYC(2) break;
|
||||||
case 0xAA: TAX CYC(2) break;
|
case 0xAA: TAX CYC(2) break;
|
||||||
case 0xAB: $ NOP CYC(2) break;
|
case 0xAB: $ NOP CYC(2) break;
|
||||||
case 0xAC: ABS LDY CYC(4) break;
|
case 0xAC: ABS LDY CYC(4) break;
|
||||||
case 0xAD: ABS LDA CYC(4) break;
|
case 0xAD: ABS LDA CYC(4) break;
|
||||||
case 0xAE: ABS LDX CYC(4) break;
|
case 0xAE: ABS LDX CYC(4) break;
|
||||||
case 0xAF: $ NOP CYC(2) break;
|
case 0xAF: $ NOP CYC(2) break;
|
||||||
case 0xB0: REL BCS CYC(2) break;
|
case 0xB0: REL BCS CYC(2) break;
|
||||||
case 0xB1: idy LDA CYC(5) break;
|
case 0xB1: idy LDA CYC(5) break;
|
||||||
case 0xB2: izp LDA CYC(5) break;
|
case 0xB2: izp LDA CYC(5) break;
|
||||||
case 0xB3: $ NOP CYC(2) break;
|
case 0xB3: $ NOP CYC(2) break;
|
||||||
case 0xB4: zpx LDY CYC(4) break;
|
case 0xB4: zpx LDY CYC(4) break;
|
||||||
case 0xB5: zpx LDA CYC(4) break;
|
case 0xB5: zpx LDA CYC(4) break;
|
||||||
case 0xB6: zpy LDX CYC(4) break;
|
case 0xB6: zpy LDX CYC(4) break;
|
||||||
case 0xB7: $ NOP CYC(2) break;
|
case 0xB7: $ NOP CYC(2) break;
|
||||||
case 0xB8: CLV CYC(2) break;
|
case 0xB8: CLV CYC(2) break;
|
||||||
case 0xB9: aby LDA CYC(4) break;
|
case 0xB9: aby LDA CYC(4) break;
|
||||||
case 0xBA: TSX CYC(2) break;
|
case 0xBA: TSX CYC(2) break;
|
||||||
case 0xBB: $ NOP CYC(2) break;
|
case 0xBB: $ NOP CYC(2) break;
|
||||||
case 0xBC: abx LDY CYC(4) break;
|
case 0xBC: abx LDY CYC(4) break;
|
||||||
case 0xBD: abx LDA CYC(4) break;
|
case 0xBD: abx LDA CYC(4) break;
|
||||||
case 0xBE: aby LDX CYC(4) break;
|
case 0xBE: aby LDX CYC(4) break;
|
||||||
case 0xBF: $ NOP CYC(2) break;
|
case 0xBF: $ NOP CYC(2) break;
|
||||||
case 0xC0: IMM CPY CYC(2) break;
|
case 0xC0: IMM CPY CYC(2) break;
|
||||||
case 0xC1: idx CMP CYC(6) break;
|
case 0xC1: idx CMP CYC(6) break;
|
||||||
case 0xC2: $ IMM NOP CYC(2) break;
|
case 0xC2: $ IMM NOP CYC(2) break;
|
||||||
case 0xC3: $ NOP CYC(2) break;
|
case 0xC3: $ NOP CYC(2) break;
|
||||||
case 0xC4: ZPG CPY CYC(3) break;
|
case 0xC4: ZPG CPY CYC(3) break;
|
||||||
case 0xC5: ZPG CMP CYC(3) break;
|
case 0xC5: ZPG CMP CYC(3) break;
|
||||||
case 0xC6: ZPG DECc CYC(5) break;
|
case 0xC6: ZPG DECc CYC(5) break;
|
||||||
case 0xC7: $ NOP CYC(2) break;
|
case 0xC7: $ NOP CYC(2) break;
|
||||||
case 0xC8: INY CYC(2) break;
|
case 0xC8: INY CYC(2) break;
|
||||||
case 0xC9: IMM CMP CYC(2) break;
|
case 0xC9: IMM CMP CYC(2) break;
|
||||||
case 0xCA: DEX CYC(2) break;
|
case 0xCA: DEX CYC(2) break;
|
||||||
case 0xCB: $ NOP CYC(2) break;
|
case 0xCB: $ NOP CYC(2) break;
|
||||||
case 0xCC: ABS CPY CYC(4) break;
|
case 0xCC: ABS CPY CYC(4) break;
|
||||||
case 0xCD: ABS CMP CYC(4) break;
|
case 0xCD: ABS CMP CYC(4) break;
|
||||||
case 0xCE: ABS DECc CYC(5) break;
|
case 0xCE: ABS DECc CYC(5) break;
|
||||||
case 0xCF: $ NOP CYC(2) break;
|
case 0xCF: $ NOP CYC(2) break;
|
||||||
case 0xD0: REL BNE CYC(2) break;
|
case 0xD0: REL BNE CYC(2) break;
|
||||||
case 0xD1: idy CMP CYC(5) break;
|
case 0xD1: idy CMP CYC(5) break;
|
||||||
case 0xD2: izp CMP CYC(5) break;
|
case 0xD2: izp CMP CYC(5) break;
|
||||||
case 0xD3: $ NOP CYC(2) break;
|
case 0xD3: $ NOP CYC(2) break;
|
||||||
case 0xD4: $ zpx NOP CYC(4) break;
|
case 0xD4: $ zpx NOP CYC(4) break;
|
||||||
case 0xD5: zpx CMP CYC(4) break;
|
case 0xD5: zpx CMP CYC(4) break;
|
||||||
case 0xD6: zpx DECc CYC(6) break;
|
case 0xD6: zpx DECc CYC(6) break;
|
||||||
case 0xD7: $ NOP CYC(2) break;
|
case 0xD7: $ NOP CYC(2) break;
|
||||||
case 0xD8: CLD CYC(2) break;
|
case 0xD8: CLD CYC(2) break;
|
||||||
case 0xD9: aby CMP CYC(4) break;
|
case 0xD9: aby CMP CYC(4) break;
|
||||||
case 0xDA: PHX CYC(3) break;
|
case 0xDA: PHX CYC(3) break;
|
||||||
case 0xDB: $ NOP CYC(2) break;
|
case 0xDB: $ NOP CYC(2) break;
|
||||||
case 0xDC: $ abx NOP CYC(4) break;
|
case 0xDC: $ abx NOP CYC(4) break;
|
||||||
case 0xDD: abx CMP CYC(4) break;
|
case 0xDD: abx CMP CYC(4) break;
|
||||||
case 0xDE: abx DECc CYC(6) break;
|
case 0xDE: abx DECc CYC(6) break;
|
||||||
case 0xDF: $ NOP CYC(2) break;
|
case 0xDF: $ NOP CYC(2) break;
|
||||||
case 0xE0: IMM CPX CYC(2) break;
|
case 0xE0: IMM CPX CYC(2) break;
|
||||||
case 0xE1: idx SBCc CYC(6) break;
|
case 0xE1: idx SBCc CYC(6) break;
|
||||||
case 0xE2: $ IMM NOP CYC(2) break;
|
case 0xE2: $ IMM NOP CYC(2) break;
|
||||||
case 0xE3: $ NOP CYC(2) break;
|
case 0xE3: $ NOP CYC(2) break;
|
||||||
case 0xE4: ZPG CPX CYC(3) break;
|
case 0xE4: ZPG CPX CYC(3) break;
|
||||||
case 0xE5: ZPG SBCc CYC(3) break;
|
case 0xE5: ZPG SBCc CYC(3) break;
|
||||||
case 0xE6: ZPG INCc CYC(5) break;
|
case 0xE6: ZPG INCc CYC(5) break;
|
||||||
case 0xE7: $ NOP CYC(2) break;
|
case 0xE7: $ NOP CYC(2) break;
|
||||||
case 0xE8: INX CYC(2) break;
|
case 0xE8: INX CYC(2) break;
|
||||||
case 0xE9: IMM SBCc CYC(2) break;
|
case 0xE9: IMM SBCc CYC(2) break;
|
||||||
case 0xEA: NOP CYC(2) break;
|
case 0xEA: NOP CYC(2) break;
|
||||||
case 0xEB: $ NOP CYC(2) break;
|
case 0xEB: $ NOP CYC(2) break;
|
||||||
case 0xEC: ABS CPX CYC(4) break;
|
case 0xEC: ABS CPX CYC(4) break;
|
||||||
case 0xED: ABS SBCc CYC(4) break;
|
case 0xED: ABS SBCc CYC(4) break;
|
||||||
case 0xEE: ABS INCc CYC(6) break;
|
case 0xEE: ABS INCc CYC(6) break;
|
||||||
case 0xEF: $ NOP CYC(2) break;
|
case 0xEF: $ NOP CYC(2) break;
|
||||||
case 0xF0: REL BEQ CYC(2) break;
|
case 0xF0: REL BEQ CYC(2) break;
|
||||||
case 0xF1: idy SBCc CYC(5) break;
|
case 0xF1: idy SBCc CYC(5) break;
|
||||||
case 0xF2: izp SBCc CYC(5) break;
|
case 0xF2: izp SBCc CYC(5) break;
|
||||||
case 0xF3: $ NOP CYC(2) break;
|
case 0xF3: $ NOP CYC(2) break;
|
||||||
case 0xF4: $ zpx NOP CYC(4) break;
|
case 0xF4: $ zpx NOP CYC(4) break;
|
||||||
case 0xF5: zpx SBCc CYC(4) break;
|
case 0xF5: zpx SBCc CYC(4) break;
|
||||||
case 0xF6: zpx INCc CYC(6) break;
|
case 0xF6: zpx INCc CYC(6) break;
|
||||||
case 0xF7: $ NOP CYC(2) break;
|
case 0xF7: $ NOP CYC(2) break;
|
||||||
case 0xF8: SED CYC(2) break;
|
case 0xF8: SED CYC(2) break;
|
||||||
case 0xF9: aby SBCc CYC(4) break;
|
case 0xF9: aby SBCc CYC(4) break;
|
||||||
case 0xFA: PLX CYC(4) break;
|
case 0xFA: PLX CYC(4) break;
|
||||||
case 0xFB: $ NOP CYC(2) break;
|
case 0xFB: $ NOP CYC(2) break;
|
||||||
case 0xFC: $ abx NOP CYC(4) break;
|
case 0xFC: $ abx NOP CYC(4) break;
|
||||||
case 0xFD: abx SBCc CYC(4) break;
|
case 0xFD: abx SBCc CYC(4) break;
|
||||||
case 0xFE: abx INCc CYC(6) break;
|
case 0xFE: abx INCc CYC(6) break;
|
||||||
case 0xFF: $ NOP CYC(2) break;
|
case 0xFF: $ NOP CYC(2) break;
|
||||||
}
|
}
|
||||||
#undef $
|
#undef $
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
CheckInterruptSources(uExecutedCycles);
|
CheckInterruptSources(uExecutedCycles);
|
||||||
NMI(uExecutedCycles, uExtraCycles, flagc, flagn, flagv, flagz);
|
NMI(uExecutedCycles, uExtraCycles, flagc, flagn, flagv, flagz);
|
||||||
IRQ(uExecutedCycles, uExtraCycles, flagc, flagn, flagv, flagz);
|
IRQ(uExecutedCycles, uExtraCycles, flagc, flagn, flagv, flagz);
|
||||||
|
|
||||||
if (bBreakOnInvalid)
|
if( IsDebugBreakpointHit() )
|
||||||
break;
|
break;
|
||||||
|
|
||||||
} while (uExecutedCycles < uTotalCycles);
|
} while (uExecutedCycles < uTotalCycles);
|
||||||
|
|
||||||
EF_TO_AF
|
EF_TO_AF // Emulator Flags to Apple Flags
|
||||||
|
|
||||||
|
if( g_bDebugBreakpointHit )
|
||||||
|
if ((g_nAppMode != MODE_DEBUG) && (g_nAppMode != MODE_STEPPING)) // Running at full speed? (debugger not running)
|
||||||
|
RequestDebugger();
|
||||||
|
|
||||||
return uExecutedCycles;
|
return uExecutedCycles;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -1,7 +1,7 @@
|
||||||
/*
|
/*
|
||||||
AppleWin : An Apple //e emulator for Windows
|
AppleWin : An Apple //e emulator for Windows
|
||||||
|
|
||||||
Copyright (C) 2010, Tom Charlesworth, Michael Pohoreski
|
Copyright (C) 2010-2011, Tom Charlesworth, Michael Pohoreski
|
||||||
|
|
||||||
AppleWin is free software; you can redistribute it and/or modify
|
AppleWin is free software; you can redistribute it and/or modify
|
||||||
it under the terms of the GNU General Public License as published by
|
it under the terms of the GNU General Public License as published by
|
||||||
|
@ -84,6 +84,9 @@ inline u8 ReadByte( u16 addr, int uExecutedCycles )
|
||||||
// Based on Modified 65C02
|
// Based on Modified 65C02
|
||||||
static DWORD Cpu65D02 (DWORD uTotalCycles)
|
static DWORD Cpu65D02 (DWORD uTotalCycles)
|
||||||
{
|
{
|
||||||
|
// Optimisation:
|
||||||
|
// . Copy the global /regs/ vars to stack-based local vars
|
||||||
|
// (Oliver Schmidt says this gives a performance gain, see email - The real deal: "1.10.5")
|
||||||
WORD addr;
|
WORD addr;
|
||||||
BOOL flagc; // must always be 0 or 1, no other values allowed
|
BOOL flagc; // must always be 0 or 1, no other values allowed
|
||||||
BOOL flagn; // must always be 0 or 0x80.
|
BOOL flagn; // must always be 0 or 0x80.
|
||||||
|
@ -96,13 +99,21 @@ static DWORD Cpu65D02 (DWORD uTotalCycles)
|
||||||
ULONG uExecutedCycles = 0;
|
ULONG uExecutedCycles = 0;
|
||||||
BOOL bSlowerOnPagecross = 0; // Set if opcode writes to memory (eg. ASL, STA)
|
BOOL bSlowerOnPagecross = 0; // Set if opcode writes to memory (eg. ASL, STA)
|
||||||
WORD base;
|
WORD base;
|
||||||
bool bBreakOnInvalid = false;
|
g_bDebugBreakpointHit = 0;
|
||||||
|
|
||||||
do
|
do
|
||||||
{
|
{
|
||||||
UINT uExtraCycles = 0;
|
UINT uExtraCycles = 0;
|
||||||
BYTE iOpcode;
|
BYTE iOpcode;
|
||||||
|
|
||||||
|
#ifdef SUPPORT_CPM
|
||||||
|
if (g_ActiveCPU == CPU_Z80)
|
||||||
|
{
|
||||||
|
const UINT uZ80Cycles = z80_mainloop(uTotalCycles, uExecutedCycles); CYC(uZ80Cycles)
|
||||||
|
}
|
||||||
|
else
|
||||||
|
#endif
|
||||||
|
|
||||||
if (!Fetch(iOpcode, uExecutedCycles))
|
if (!Fetch(iOpcode, uExecutedCycles))
|
||||||
break;
|
break;
|
||||||
|
|
||||||
|
@ -643,10 +654,16 @@ static DWORD Cpu65D02 (DWORD uTotalCycles)
|
||||||
NMI(uExecutedCycles, uExtraCycles, flagc, flagn, flagv, flagz);
|
NMI(uExecutedCycles, uExtraCycles, flagc, flagn, flagv, flagz);
|
||||||
IRQ(uExecutedCycles, uExtraCycles, flagc, flagn, flagv, flagz);
|
IRQ(uExecutedCycles, uExtraCycles, flagc, flagn, flagv, flagz);
|
||||||
|
|
||||||
if (bBreakOnInvalid)
|
if( IsDebugBreakpointHit() )
|
||||||
break;
|
break;
|
||||||
|
|
||||||
} while (uExecutedCycles < uTotalCycles);
|
} while (uExecutedCycles < uTotalCycles);
|
||||||
|
|
||||||
EF_TO_AF
|
EF_TO_AF // Emulator Flags to Apple Flags
|
||||||
|
|
||||||
|
if( g_bDebugBreakpointHit )
|
||||||
|
if ((g_nAppMode != MODE_DEBUG) && (g_nAppMode != MODE_STEPPING)) // // Running at full speed? (debugger not running)
|
||||||
|
RequestDebugger();
|
||||||
|
|
||||||
return uExecutedCycles;
|
return uExecutedCycles;
|
||||||
}
|
}
|
||||||
|
|
|
@ -31,9 +31,9 @@ enum AppMode_e
|
||||||
{
|
{
|
||||||
MODE_LOGO = 0
|
MODE_LOGO = 0
|
||||||
, MODE_PAUSED
|
, MODE_PAUSED
|
||||||
, MODE_RUNNING
|
, MODE_RUNNING // 6502 is running at normal speed (Debugger breakpoints may or may not be active)
|
||||||
, MODE_DEBUG
|
, MODE_DEBUG // 6502 is paused
|
||||||
, MODE_STEPPING
|
, MODE_STEPPING // 6502 is running at full speed (Debugger breakpoints always active)
|
||||||
};
|
};
|
||||||
|
|
||||||
#define SPEED_MIN 0
|
#define SPEED_MIN 0
|
||||||
|
|
|
@ -36,7 +36,7 @@ Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||||
#define ALLOW_INPUT_LOWERCASE 1
|
#define ALLOW_INPUT_LOWERCASE 1
|
||||||
|
|
||||||
// See /docs/Debugger_Changelog.txt for full details
|
// See /docs/Debugger_Changelog.txt for full details
|
||||||
const int DEBUGGER_VERSION = MAKE_VERSION(2,7,0,17);
|
const int DEBUGGER_VERSION = MAKE_VERSION(2,7,0,21);
|
||||||
|
|
||||||
|
|
||||||
// Public _________________________________________________________________________________________
|
// Public _________________________________________________________________________________________
|
||||||
|
@ -51,10 +51,18 @@ Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||||
|
|
||||||
// Breakpoints ________________________________________________________________
|
// Breakpoints ________________________________________________________________
|
||||||
|
|
||||||
// Full-Speed debugging
|
|
||||||
int g_nDebugOnBreakInvalid = 0;
|
// MODE_RUNNING // Normal Speed Breakpoints: Shift-F7 exit debugger, keep breakpoints active, enter run state at NORMAL speed
|
||||||
int g_iDebugOnOpcode = 0;
|
bool g_bDebugNormalSpeedBreakpoints = 0;
|
||||||
bool g_bDebugDelayBreakCheck = false;
|
|
||||||
|
// MODE_STEPPING // Full Speed Breakpoints
|
||||||
|
|
||||||
|
// Any Speed Breakpoints
|
||||||
|
int g_nDebugBreakOnInvalid = 0; // Bit Flags of Invalid Opcode to break on: // iOpcodeType = AM_IMPLIED (BRK), AM_1, AM_2, AM_3
|
||||||
|
int g_iDebugBreakOnOpcode = 0;
|
||||||
|
|
||||||
|
bool g_bDebugBreakDelayCheck = false; // If exiting the debugger, allow at least one instruction to execute so we don't trigger on the same invalid opcode
|
||||||
|
int g_bDebugBreakpointHit = 0; // See: BreakpointHit_t
|
||||||
|
|
||||||
int g_nBreakpoints = 0;
|
int g_nBreakpoints = 0;
|
||||||
Breakpoint_t g_aBreakpoints[ MAX_BREAKPOINTS ];
|
Breakpoint_t g_aBreakpoints[ MAX_BREAKPOINTS ];
|
||||||
|
@ -318,8 +326,6 @@ Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||||
void _BWZ_ListAll ( const Breakpoint_t * aBreakWatchZero, const int nMax );
|
void _BWZ_ListAll ( const Breakpoint_t * aBreakWatchZero, const int nMax );
|
||||||
|
|
||||||
// bool CheckBreakpoint (WORD address, BOOL memory);
|
// bool CheckBreakpoint (WORD address, BOOL memory);
|
||||||
bool CheckBreakpointsIO ();
|
|
||||||
bool CheckBreakpointsReg ();
|
|
||||||
bool _CmdBreakpointAddReg ( Breakpoint_t *pBP, BreakpointSource_t iSrc, BreakpointOperator_t iCmp, WORD nAddress, int nLen, bool bIsTempBreakpoint );
|
bool _CmdBreakpointAddReg ( Breakpoint_t *pBP, BreakpointSource_t iSrc, BreakpointOperator_t iCmp, WORD nAddress, int nLen, bool bIsTempBreakpoint );
|
||||||
int _CmdBreakpointAddCommonArg ( int iArg, int nArg, BreakpointSource_t iSrc, BreakpointOperator_t iCmp, bool bIsTempBreakpoint=false );
|
int _CmdBreakpointAddCommonArg ( int iArg, int nArg, BreakpointSource_t iSrc, BreakpointOperator_t iCmp, bool bIsTempBreakpoint=false );
|
||||||
void _BWZ_Clear( Breakpoint_t * aBreakWatchZero, int iSlot );
|
void _BWZ_Clear( Breakpoint_t * aBreakWatchZero, int iSlot );
|
||||||
|
@ -707,7 +713,7 @@ Update_t CmdBenchmarkStop (int nArgs)
|
||||||
{
|
{
|
||||||
g_bBenchmarking = false;
|
g_bBenchmarking = false;
|
||||||
DebugEnd();
|
DebugEnd();
|
||||||
g_nAppMode = MODE_RUNNING;
|
|
||||||
FrameRefreshStatus(DRAW_TITLE);
|
FrameRefreshStatus(DRAW_TITLE);
|
||||||
VideoRedrawScreen();
|
VideoRedrawScreen();
|
||||||
DWORD currtime = GetTickCount();
|
DWORD currtime = GetTickCount();
|
||||||
|
@ -807,13 +813,19 @@ _Help:
|
||||||
//===========================================================================
|
//===========================================================================
|
||||||
Update_t CmdBreakInvalid (int nArgs) // Breakpoint IFF Full-speed!
|
Update_t CmdBreakInvalid (int nArgs) // Breakpoint IFF Full-speed!
|
||||||
{
|
{
|
||||||
if ((nArgs > 2) || (nArgs == 0))
|
if (nArgs > 2) // || (nArgs == 0))
|
||||||
goto _Help;
|
goto _Help;
|
||||||
|
|
||||||
int iType = 0; // default to BRK
|
int iType = AM_IMPLIED; // default to BRK
|
||||||
int nActive = 0;
|
int nActive = 0;
|
||||||
|
|
||||||
// if (nArgs == 2)
|
if (nArgs == 0)
|
||||||
|
{
|
||||||
|
nArgs = 1;
|
||||||
|
g_aArgs[ 1 ].nValue = AM_IMPLIED;
|
||||||
|
g_aArgs[ 1 ].sArg[0] = 0;
|
||||||
|
}
|
||||||
|
|
||||||
iType = g_aArgs[ 1 ].nValue;
|
iType = g_aArgs[ 1 ].nValue;
|
||||||
|
|
||||||
// Cases:
|
// Cases:
|
||||||
|
@ -847,10 +859,10 @@ Update_t CmdBreakInvalid (int nArgs) // Breakpoint IFF Full-speed!
|
||||||
{
|
{
|
||||||
if (! nFound) // bValidParam) // case 1a or 1c
|
if (! nFound) // bValidParam) // case 1a or 1c
|
||||||
{
|
{
|
||||||
if ((iType < 0) || (iType > AM_3))
|
if ((iType < AM_IMPLIED) || (iType > AM_3))
|
||||||
goto _Help;
|
goto _Help;
|
||||||
|
|
||||||
if (IsDebugBreakOnInvalid( iType ))
|
if ( IsDebugBreakOnInvalid( iType ) )
|
||||||
iParam = PARAM_ON;
|
iParam = PARAM_ON;
|
||||||
else
|
else
|
||||||
iParam = PARAM_OFF;
|
iParam = PARAM_OFF;
|
||||||
|
@ -910,31 +922,31 @@ Update_t CmdBreakOpcode (int nArgs) // Breakpoint IFF Full-speed!
|
||||||
if (nArgs == 1)
|
if (nArgs == 1)
|
||||||
{
|
{
|
||||||
int iOpcode = g_aArgs[ 1] .nValue;
|
int iOpcode = g_aArgs[ 1] .nValue;
|
||||||
g_iDebugOnOpcode = iOpcode & 0xFF;
|
g_iDebugBreakOnOpcode = iOpcode & 0xFF;
|
||||||
|
|
||||||
_tcscpy( sAction, TEXT("Setting") );
|
_tcscpy( sAction, TEXT("Setting") );
|
||||||
|
|
||||||
if (iOpcode >= NUM_OPCODES)
|
if (iOpcode >= NUM_OPCODES)
|
||||||
{
|
{
|
||||||
wsprintf( sText, TEXT("Warning: clamping opcode: %02X"), g_iDebugOnOpcode );
|
wsprintf( sText, TEXT("Warning: clamping opcode: %02X"), g_iDebugBreakOnOpcode );
|
||||||
ConsoleBufferPush( sText );
|
ConsoleBufferPush( sText );
|
||||||
return ConsoleUpdate();
|
return ConsoleUpdate();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (g_iDebugOnOpcode == 0)
|
if (g_iDebugBreakOnOpcode == 0)
|
||||||
// Show what the current break opcode is
|
// Show what the current break opcode is
|
||||||
wsprintf( sText, TEXT("%s full speed Break on Opcode: None")
|
wsprintf( sText, TEXT("%s full speed Break on Opcode: None")
|
||||||
, sAction
|
, sAction
|
||||||
, g_iDebugOnOpcode
|
, g_iDebugBreakOnOpcode
|
||||||
, g_aOpcodes65C02[ g_iDebugOnOpcode ].sMnemonic
|
, g_aOpcodes65C02[ g_iDebugBreakOnOpcode ].sMnemonic
|
||||||
);
|
);
|
||||||
else
|
else
|
||||||
// Show what the current break opcode is
|
// Show what the current break opcode is
|
||||||
wsprintf( sText, TEXT("%s full speed Break on Opcode: %02X %s")
|
wsprintf( sText, TEXT("%s full speed Break on Opcode: %02X %s")
|
||||||
, sAction
|
, sAction
|
||||||
, g_iDebugOnOpcode
|
, g_iDebugBreakOnOpcode
|
||||||
, g_aOpcodes65C02[ g_iDebugOnOpcode ].sMnemonic
|
, g_aOpcodes65C02[ g_iDebugBreakOnOpcode ].sMnemonic
|
||||||
);
|
);
|
||||||
|
|
||||||
ConsoleBufferPush( sText );
|
ConsoleBufferPush( sText );
|
||||||
|
@ -1031,7 +1043,7 @@ bool _CheckBreakpointValue( Breakpoint_t *pBP, int nVal )
|
||||||
|
|
||||||
|
|
||||||
//===========================================================================
|
//===========================================================================
|
||||||
bool CheckBreakpointsIO ()
|
int CheckBreakpointsIO ()
|
||||||
{
|
{
|
||||||
const int NUM_TARGETS = 2;
|
const int NUM_TARGETS = 2;
|
||||||
|
|
||||||
|
@ -1041,7 +1053,7 @@ bool CheckBreakpointsIO ()
|
||||||
NO_6502_TARGET
|
NO_6502_TARGET
|
||||||
};
|
};
|
||||||
int nBytes;
|
int nBytes;
|
||||||
bool bStatus = false;
|
bool bBreakpointHit = 0;
|
||||||
|
|
||||||
int iTarget;
|
int iTarget;
|
||||||
int nAddress;
|
int nAddress;
|
||||||
|
@ -1064,7 +1076,7 @@ bool CheckBreakpointsIO ()
|
||||||
{
|
{
|
||||||
if (_CheckBreakpointValue( pBP, nAddress ))
|
if (_CheckBreakpointValue( pBP, nAddress ))
|
||||||
{
|
{
|
||||||
return true;
|
return BP_HIT_MEM;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -1072,14 +1084,14 @@ bool CheckBreakpointsIO ()
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
return bStatus;
|
return bBreakpointHit;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Returns true if a register breakpoint is triggered
|
// Returns true if a register breakpoint is triggered
|
||||||
//===========================================================================
|
//===========================================================================
|
||||||
bool CheckBreakpointsReg ()
|
int CheckBreakpointsReg ()
|
||||||
{
|
{
|
||||||
bool bStatus = false;
|
int bBreakpointHit = 0;
|
||||||
|
|
||||||
for (int iBreakpoint = 0; iBreakpoint < MAX_BREAKPOINTS; iBreakpoint++)
|
for (int iBreakpoint = 0; iBreakpoint < MAX_BREAKPOINTS; iBreakpoint++)
|
||||||
{
|
{
|
||||||
|
@ -1091,29 +1103,30 @@ bool CheckBreakpointsReg ()
|
||||||
switch (pBP->eSource)
|
switch (pBP->eSource)
|
||||||
{
|
{
|
||||||
case BP_SRC_REG_PC:
|
case BP_SRC_REG_PC:
|
||||||
bStatus = _CheckBreakpointValue( pBP, regs.pc );
|
bBreakpointHit = _CheckBreakpointValue( pBP, regs.pc );
|
||||||
break;
|
break;
|
||||||
case BP_SRC_REG_A:
|
case BP_SRC_REG_A:
|
||||||
bStatus = _CheckBreakpointValue( pBP, regs.a );
|
bBreakpointHit = _CheckBreakpointValue( pBP, regs.a );
|
||||||
break;
|
break;
|
||||||
case BP_SRC_REG_X:
|
case BP_SRC_REG_X:
|
||||||
bStatus = _CheckBreakpointValue( pBP, regs.x );
|
bBreakpointHit = _CheckBreakpointValue( pBP, regs.x );
|
||||||
break;
|
break;
|
||||||
case BP_SRC_REG_Y:
|
case BP_SRC_REG_Y:
|
||||||
bStatus = _CheckBreakpointValue( pBP, regs.y );
|
bBreakpointHit = _CheckBreakpointValue( pBP, regs.y );
|
||||||
break;
|
break;
|
||||||
case BP_SRC_REG_P:
|
case BP_SRC_REG_P:
|
||||||
bStatus = _CheckBreakpointValue( pBP, regs.ps );
|
bBreakpointHit = _CheckBreakpointValue( pBP, regs.ps );
|
||||||
break;
|
break;
|
||||||
case BP_SRC_REG_S:
|
case BP_SRC_REG_S:
|
||||||
bStatus = _CheckBreakpointValue( pBP, regs.sp );
|
bBreakpointHit = _CheckBreakpointValue( pBP, regs.sp );
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (bStatus)
|
if (bBreakpointHit)
|
||||||
{
|
{
|
||||||
|
bBreakpointHit = BP_HIT_REG;
|
||||||
if (pBP->bTemp)
|
if (pBP->bTemp)
|
||||||
_BWZ_Clear(pBP, iBreakpoint);
|
_BWZ_Clear(pBP, iBreakpoint);
|
||||||
|
|
||||||
|
@ -1121,7 +1134,7 @@ bool CheckBreakpointsReg ()
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return bStatus;
|
return bBreakpointHit;
|
||||||
}
|
}
|
||||||
|
|
||||||
void ClearTempBreakpoints ()
|
void ClearTempBreakpoints ()
|
||||||
|
@ -1234,7 +1247,7 @@ Update_t CmdBreakpointAddReg (int nArgs)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if ((! bHaveSrc) && (! bHaveCmp))
|
if ((! bHaveSrc) && (! bHaveCmp)) // Inverted/Convoluted logic: didn't find BOTH this pass, so we must have already found them.
|
||||||
{
|
{
|
||||||
int dArgs = _CmdBreakpointAddCommonArg( iArg, nArgs, iSrc, iCmp );
|
int dArgs = _CmdBreakpointAddCommonArg( iArg, nArgs, iSrc, iCmp );
|
||||||
if (!dArgs)
|
if (!dArgs)
|
||||||
|
@ -1389,7 +1402,8 @@ Update_t CmdBreakpointAddPC (int nArgs)
|
||||||
//===========================================================================
|
//===========================================================================
|
||||||
Update_t CmdBreakpointAddIO (int nArgs)
|
Update_t CmdBreakpointAddIO (int nArgs)
|
||||||
{
|
{
|
||||||
return UPDATE_CONSOLE_DISPLAY;
|
return CmdBreakpointAddMem( nArgs );
|
||||||
|
// return UPDATE_BREAKPOINTS | UPDATE_CONSOLE_DISPLAY;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@ -7168,13 +7182,13 @@ void DebugContinueStepping ()
|
||||||
{
|
{
|
||||||
if ((regs.pc >= g_nDebugSkipStart) && (regs.pc < (g_nDebugSkipStart + g_nDebugSkipLen)))
|
if ((regs.pc >= g_nDebugSkipStart) && (regs.pc < (g_nDebugSkipStart + g_nDebugSkipLen)))
|
||||||
{
|
{
|
||||||
// Enter turbo debugger g_nAppMode -- UI not updated, etc.
|
// Enter turbo debugger mode -- UI not updated, etc.
|
||||||
g_nDebugSteps = -1;
|
g_nDebugSteps = -1;
|
||||||
g_nAppMode = MODE_STEPPING;
|
g_nAppMode = MODE_STEPPING;
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
// Enter normal debugger g_nAppMode -- UI updated every instruction, etc.
|
// Enter normal debugger mode -- UI updated every instruction, etc.
|
||||||
g_nDebugSteps = 1;
|
g_nDebugSteps = 1;
|
||||||
g_nAppMode = MODE_STEPPING;
|
g_nAppMode = MODE_STEPPING;
|
||||||
}
|
}
|
||||||
|
@ -7188,12 +7202,9 @@ void DebugContinueStepping ()
|
||||||
|
|
||||||
InternalSingleStep();
|
InternalSingleStep();
|
||||||
|
|
||||||
bool bBreak = CheckBreakpointsIO();
|
_IsDebugBreakpointHit(); // Updates g_bDebugBreakpointHit
|
||||||
|
|
||||||
if (CheckBreakpointsReg())
|
if ((regs.pc == g_nDebugStepUntil) || g_bDebugBreakpointHit)
|
||||||
bBreak = true;
|
|
||||||
|
|
||||||
if ((regs.pc == g_nDebugStepUntil) || bBreak)
|
|
||||||
g_nDebugSteps = 0;
|
g_nDebugSteps = 0;
|
||||||
else if (g_nDebugSteps > 0)
|
else if (g_nDebugSteps > 0)
|
||||||
g_nDebugSteps--;
|
g_nDebugSteps--;
|
||||||
|
@ -7203,7 +7214,7 @@ void DebugContinueStepping ()
|
||||||
{
|
{
|
||||||
if (!((++nStepsTaken) & 0xFFFF))
|
if (!((++nStepsTaken) & 0xFFFF))
|
||||||
{
|
{
|
||||||
if (nStepsTaken == 0x10000)
|
if (nStepsTaken == 0x10000) // HACK_MAGIC_NUM
|
||||||
VideoRedrawScreen();
|
VideoRedrawScreen();
|
||||||
else
|
else
|
||||||
VideoRefreshScreen();
|
VideoRefreshScreen();
|
||||||
|
@ -7215,32 +7226,11 @@ void DebugContinueStepping ()
|
||||||
FrameRefreshStatus(DRAW_TITLE);
|
FrameRefreshStatus(DRAW_TITLE);
|
||||||
// BUG: PageUp, Trace - doesn't center cursor
|
// BUG: PageUp, Trace - doesn't center cursor
|
||||||
|
|
||||||
// if ((g_nDebugStepStart < regs.pc) && (g_nDebugStepStart+3 >= regs.pc))
|
g_nDisasmCurAddress = regs.pc;
|
||||||
// Still within current disasm "window"?
|
|
||||||
/*
|
|
||||||
if ((regs.pc >= g_nDisasmTopAddress) && (regs.pc <= g_nDisasmBotAddress))
|
|
||||||
{
|
|
||||||
int eMode = g_aOpcodes[*(mem+g_nDisasmCurAddress)].addrmode;
|
|
||||||
int nBytes = g_aOpmodes[ eMode ]._nBytes;
|
|
||||||
g_nDisasmCurAddress += nBytes;
|
|
||||||
// g_nDisasmTopAddress += nBytes;
|
|
||||||
// g_nDisasmBotAddress += nBytes;
|
|
||||||
}
|
|
||||||
else
|
|
||||||
*/
|
|
||||||
{
|
|
||||||
g_nDisasmCurAddress = regs.pc;
|
|
||||||
}
|
|
||||||
|
|
||||||
DisasmCalcTopBotAddress();
|
DisasmCalcTopBotAddress();
|
||||||
|
|
||||||
// g_nDisasmCurAddress += g_aOpmodes[g_aOpcodes[*(mem+g_nDisasmCurAddress)].addrmode]._nBytes;
|
|
||||||
// DisasmCalcTopBotAddress();
|
|
||||||
|
|
||||||
Update_t bUpdate = UPDATE_ALL;
|
Update_t bUpdate = UPDATE_ALL;
|
||||||
// if (nStepsTaken >= 0x10000) // HACK_MAGIC_NUM
|
|
||||||
// bUpdate = UPDATE_ALL;
|
|
||||||
|
|
||||||
UpdateDisplay( bUpdate ); // nStepsTaken >= 0x10000);
|
UpdateDisplay( bUpdate ); // nStepsTaken >= 0x10000);
|
||||||
nStepsTaken = 0;
|
nStepsTaken = 0;
|
||||||
}
|
}
|
||||||
|
@ -7297,6 +7287,8 @@ void DebugEnd ()
|
||||||
}
|
}
|
||||||
|
|
||||||
g_vMemorySearchResults.erase( g_vMemorySearchResults.begin(), g_vMemorySearchResults.end() );
|
g_vMemorySearchResults.erase( g_vMemorySearchResults.begin(), g_vMemorySearchResults.end() );
|
||||||
|
|
||||||
|
g_nAppMode = MODE_RUNNING;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
|
@ -30,16 +30,33 @@ using namespace std;
|
||||||
// extern vector<int> g_aBookmarks;
|
// extern vector<int> g_aBookmarks;
|
||||||
|
|
||||||
// Breakpoints
|
// Breakpoints
|
||||||
|
enum BreakpointHit_t
|
||||||
|
{
|
||||||
|
BP_HIT_NONE = 0
|
||||||
|
,BP_HIT_INVALID = (1 << 0)
|
||||||
|
,BP_HIT_OPCODE = (1 << 1)
|
||||||
|
,BP_HIT_REG = (1 << 2)
|
||||||
|
,BP_HIT_MEM = (1 << 3)
|
||||||
|
};
|
||||||
|
|
||||||
extern int g_nBreakpoints;
|
extern int g_nBreakpoints;
|
||||||
extern Breakpoint_t g_aBreakpoints[ MAX_BREAKPOINTS ];
|
extern Breakpoint_t g_aBreakpoints[ MAX_BREAKPOINTS ];
|
||||||
|
|
||||||
extern const char *g_aBreakpointSource [ NUM_BREAKPOINT_SOURCES ];
|
extern const char *g_aBreakpointSource [ NUM_BREAKPOINT_SOURCES ];
|
||||||
extern const TCHAR *g_aBreakpointSymbols[ NUM_BREAKPOINT_OPERATORS ];
|
extern const TCHAR *g_aBreakpointSymbols[ NUM_BREAKPOINT_OPERATORS ];
|
||||||
|
|
||||||
// Full-Speed debugging
|
// MODE_RUNNING // Normal Speed Breakpoints
|
||||||
extern int g_nDebugOnBreakInvalid;
|
extern bool g_bDebugNormalSpeedBreakpoints;
|
||||||
extern int g_iDebugOnOpcode ;
|
|
||||||
extern bool g_bDebugDelayBreakCheck;
|
// MODE_STEPPING // Full Speed Breakpoints
|
||||||
|
|
||||||
|
// Any Speed Breakpoints
|
||||||
|
extern int g_nDebugBreakOnInvalid ;
|
||||||
|
extern int g_iDebugBreakOnOpcode ;
|
||||||
|
|
||||||
|
// Breakpoint Status
|
||||||
|
extern bool g_bDebugBreakDelayCheck;
|
||||||
|
extern int g_bDebugBreakpointHit ;
|
||||||
|
|
||||||
// Commands
|
// Commands
|
||||||
void VerifyDebuggerCommandTable();
|
void VerifyDebuggerCommandTable();
|
||||||
|
@ -133,24 +150,70 @@ using namespace std;
|
||||||
bool Bookmark_Find( const WORD nAddress );
|
bool Bookmark_Find( const WORD nAddress );
|
||||||
|
|
||||||
// Breakpoints
|
// Breakpoints
|
||||||
|
int CheckBreakpointsIO ();
|
||||||
|
int CheckBreakpointsReg ();
|
||||||
|
|
||||||
bool GetBreakpointInfo ( WORD nOffset, bool & bBreakpointActive_, bool & bBreakpointEnable_ );
|
bool GetBreakpointInfo ( WORD nOffset, bool & bBreakpointActive_, bool & bBreakpointEnable_ );
|
||||||
|
|
||||||
// 0 = Brk, 1 = Invalid1, .. 3 = Invalid 3
|
inline int _IsDebugBreakpointHit()
|
||||||
inline bool IsDebugBreakOnInvalid( int iOpcodeType )
|
|
||||||
{
|
{
|
||||||
bool bActive = (g_nDebugOnBreakInvalid >> iOpcodeType) & 1;
|
g_bDebugBreakpointHit |= CheckBreakpointsIO() || CheckBreakpointsReg();
|
||||||
return bActive;
|
return g_bDebugBreakpointHit;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
inline int _IsDebugBreakOnOpcode( int iOpcode )
|
||||||
|
{
|
||||||
|
if (g_iDebugBreakOnOpcode == iOpcode)
|
||||||
|
g_bDebugBreakpointHit |= BP_HIT_OPCODE;
|
||||||
|
return g_bDebugBreakpointHit;
|
||||||
|
}
|
||||||
|
|
||||||
|
// iOpcodeType = AM_IMPLIED (BRK), AM_1, AM_2, AM_3
|
||||||
|
inline int IsDebugBreakOnInvalid( int iOpcodeType )
|
||||||
|
{
|
||||||
|
g_bDebugBreakpointHit |= ((g_nDebugBreakOnInvalid >> iOpcodeType) & 1) ? BP_HIT_INVALID : 0;
|
||||||
|
return g_bDebugBreakpointHit;
|
||||||
|
}
|
||||||
|
|
||||||
|
// iOpcodeType = AM_IMPLIED (BRK), AM_1, AM_2, AM_3
|
||||||
inline void SetDebugBreakOnInvalid( int iOpcodeType, int nValue )
|
inline void SetDebugBreakOnInvalid( int iOpcodeType, int nValue )
|
||||||
{
|
{
|
||||||
if (iOpcodeType <= AM_3)
|
if (iOpcodeType <= AM_3)
|
||||||
{
|
{
|
||||||
g_nDebugOnBreakInvalid &= ~ ( 1 << iOpcodeType);
|
g_nDebugBreakOnInvalid &= ~ ( 1 << iOpcodeType);
|
||||||
g_nDebugOnBreakInvalid |= ((nValue & 1) << iOpcodeType);
|
g_nDebugBreakOnInvalid |= ((nValue & 1) << iOpcodeType);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
//
|
||||||
|
// CPU checks the Debugger breakpoints
|
||||||
|
// a) at opcode fetch
|
||||||
|
// b) after opcode execution
|
||||||
|
//
|
||||||
|
inline int IsDebugBreakOpcode( int iOpcode )
|
||||||
|
{
|
||||||
|
if (g_bDebugBreakDelayCheck)
|
||||||
|
{
|
||||||
|
g_bDebugBreakDelayCheck = false;
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (! iOpcode )
|
||||||
|
IsDebugBreakOnInvalid( AM_IMPLIED );
|
||||||
|
|
||||||
|
if (g_iDebugBreakOnOpcode ) // User wants to enter debugger on specific opcode?
|
||||||
|
_IsDebugBreakOnOpcode(iOpcode);
|
||||||
|
|
||||||
|
return g_bDebugBreakpointHit;
|
||||||
|
}
|
||||||
|
//
|
||||||
|
inline int IsDebugBreakpointHit()
|
||||||
|
{
|
||||||
|
if ( !g_bDebugNormalSpeedBreakpoints )
|
||||||
|
return false;
|
||||||
|
return _IsDebugBreakpointHit();
|
||||||
|
}
|
||||||
|
|
||||||
// Source Level Debugging
|
// Source Level Debugging
|
||||||
int FindSourceLine( WORD nAddress );
|
int FindSourceLine( WORD nAddress );
|
||||||
const char* FormatAddress( WORD nAddress, int nBytes );
|
const char* FormatAddress( WORD nAddress, int nBytes );
|
||||||
|
|
|
@ -40,8 +40,6 @@ Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||||
// CPU (Main)
|
// CPU (Main)
|
||||||
{TEXT(".") , CmdCursorJumpPC , CMD_CURSOR_JUMP_PC , "Locate the cursor in the disasm window" }, // centered
|
{TEXT(".") , CmdCursorJumpPC , CMD_CURSOR_JUMP_PC , "Locate the cursor in the disasm window" }, // centered
|
||||||
{TEXT("=") , CmdCursorSetPC , CMD_CURSOR_SET_PC , "Sets the PC to the current instruction" },
|
{TEXT("=") , CmdCursorSetPC , CMD_CURSOR_SET_PC , "Sets the PC to the current instruction" },
|
||||||
{TEXT("BRK") , CmdBreakInvalid , CMD_BREAK_INVALID , "Enter debugger on BRK or INVALID" },
|
|
||||||
{TEXT("BRKOP") , CmdBreakOpcode , CMD_BREAK_OPCODE , "Enter debugger on opcode" },
|
|
||||||
{TEXT("G") , CmdGo , CMD_GO , "Run [until PC = address]" },
|
{TEXT("G") , CmdGo , CMD_GO , "Run [until PC = address]" },
|
||||||
{TEXT("IN") , CmdIn , CMD_IN , "Input byte from IO $C0xx" },
|
{TEXT("IN") , CmdIn , CMD_IN , "Input byte from IO $C0xx" },
|
||||||
{TEXT("KEY") , CmdKey , CMD_INPUT_KEY , "Feed key into emulator" },
|
{TEXT("KEY") , CmdKey , CMD_INPUT_KEY , "Feed key into emulator" },
|
||||||
|
@ -73,6 +71,8 @@ Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||||
// {TEXT("BMLOAD") , CmdBookmarkLoad , CMD_BOOKMARK_LOAD , "Load bookmarks" },
|
// {TEXT("BMLOAD") , CmdBookmarkLoad , CMD_BOOKMARK_LOAD , "Load bookmarks" },
|
||||||
{TEXT("BMSAVE") , CmdBookmarkSave , CMD_BOOKMARK_SAVE , "Save bookmarks" },
|
{TEXT("BMSAVE") , CmdBookmarkSave , CMD_BOOKMARK_SAVE , "Save bookmarks" },
|
||||||
// Breakpoints
|
// Breakpoints
|
||||||
|
{TEXT("BRK") , CmdBreakInvalid , CMD_BREAK_INVALID , "Enter debugger on BRK or INVALID" },
|
||||||
|
{TEXT("BRKOP") , CmdBreakOpcode , CMD_BREAK_OPCODE , "Enter debugger on opcode" },
|
||||||
{TEXT("BP") , CmdBreakpoint , CMD_BREAKPOINT , "Alias for BPR (Breakpoint Register Add)" },
|
{TEXT("BP") , CmdBreakpoint , CMD_BREAKPOINT , "Alias for BPR (Breakpoint Register Add)" },
|
||||||
{TEXT("BPA") , CmdBreakpointAddSmart, CMD_BREAKPOINT_ADD_SMART , "Add (smart) breakpoint" },
|
{TEXT("BPA") , CmdBreakpointAddSmart, CMD_BREAKPOINT_ADD_SMART , "Add (smart) breakpoint" },
|
||||||
// {TEXT("BPP") , CmdBreakpointAddFlag , CMD_BREAKPOINT_ADD_FLAG , "Add breakpoint on flags" },
|
// {TEXT("BPP") , CmdBreakpointAddFlag , CMD_BREAKPOINT_ADD_FLAG , "Add breakpoint on flags" },
|
||||||
|
|
|
@ -512,7 +512,7 @@ Update_t CmdHelpSpecific (int nArgs)
|
||||||
switch( iParam )
|
switch( iParam )
|
||||||
{
|
{
|
||||||
case PARAM_CAT_BOOKMARKS : iCmdBegin = CMD_BOOKMARK ; iCmdEnd = CMD_BOOKMARK_SAVE ; break;
|
case PARAM_CAT_BOOKMARKS : iCmdBegin = CMD_BOOKMARK ; iCmdEnd = CMD_BOOKMARK_SAVE ; break;
|
||||||
case PARAM_CAT_BREAKPOINTS: iCmdBegin = CMD_BREAKPOINT ; iCmdEnd = CMD_BREAKPOINT_SAVE ; break;
|
case PARAM_CAT_BREAKPOINTS: iCmdBegin = CMD_BREAK_INVALID ; iCmdEnd = CMD_BREAKPOINT_SAVE ; break;
|
||||||
case PARAM_CAT_CONFIG : iCmdBegin = CMD_BENCHMARK ; iCmdEnd = CMD_CONFIG_SAVE ; break;
|
case PARAM_CAT_CONFIG : iCmdBegin = CMD_BENCHMARK ; iCmdEnd = CMD_CONFIG_SAVE ; break;
|
||||||
case PARAM_CAT_CPU : iCmdBegin = CMD_ASSEMBLE ; iCmdEnd = CMD_UNASSEMBLE ; break;
|
case PARAM_CAT_CPU : iCmdBegin = CMD_ASSEMBLE ; iCmdEnd = CMD_UNASSEMBLE ; break;
|
||||||
case PARAM_CAT_FLAGS :
|
case PARAM_CAT_FLAGS :
|
||||||
|
@ -895,6 +895,24 @@ Update_t CmdHelpSpecific (int nArgs)
|
||||||
case CMD_BOOKMARK_SAVE:
|
case CMD_BOOKMARK_SAVE:
|
||||||
break;
|
break;
|
||||||
// Breakpoints
|
// Breakpoints
|
||||||
|
case CMD_BREAK_INVALID:
|
||||||
|
sprintf( sTemp, TEXT(" Usage: [%s%s | %s%s] | [ # | # %s%s | # %s%s ]")
|
||||||
|
, CHC_COMMAND
|
||||||
|
, g_aParameters[ PARAM_ON ].m_sName
|
||||||
|
, CHC_COMMAND
|
||||||
|
, g_aParameters[ PARAM_OFF ].m_sName
|
||||||
|
, CHC_COMMAND
|
||||||
|
, g_aParameters[ PARAM_ON ].m_sName
|
||||||
|
, CHC_COMMAND
|
||||||
|
, g_aParameters[ PARAM_OFF ].m_sName
|
||||||
|
);
|
||||||
|
Colorize( sText, sTemp );
|
||||||
|
ConsolePrint( sText );
|
||||||
|
sprintf( sTemp, TEXT("Where: # is 0=BRK, 1=Invalid Opcode_1, 2=Invalid Opcode_2, 3=Invalid Opcode_3"));
|
||||||
|
Colorize( sText, sTemp );
|
||||||
|
ConsolePrint( sText );
|
||||||
|
break;
|
||||||
|
// case CMD_BREAK_OPCODE:
|
||||||
case CMD_BREAKPOINT:
|
case CMD_BREAKPOINT:
|
||||||
sprintf( sTemp, TEXT(" Usage: [%s%s | %s%s | %s%s]")
|
sprintf( sTemp, TEXT(" Usage: [%s%s | %s%s | %s%s]")
|
||||||
, CHC_COMMAND
|
, CHC_COMMAND
|
||||||
|
|
|
@ -280,8 +280,6 @@
|
||||||
// CPU
|
// CPU
|
||||||
, CMD_CURSOR_JUMP_PC // Shift
|
, CMD_CURSOR_JUMP_PC // Shift
|
||||||
, CMD_CURSOR_SET_PC // Ctrl
|
, CMD_CURSOR_SET_PC // Ctrl
|
||||||
, CMD_BREAK_INVALID
|
|
||||||
, CMD_BREAK_OPCODE
|
|
||||||
, CMD_GO
|
, CMD_GO
|
||||||
, CMD_IN
|
, CMD_IN
|
||||||
, CMD_INPUT_KEY
|
, CMD_INPUT_KEY
|
||||||
|
@ -313,6 +311,8 @@
|
||||||
, CMD_BOOKMARK_GOTO
|
, CMD_BOOKMARK_GOTO
|
||||||
, CMD_BOOKMARK_SAVE
|
, CMD_BOOKMARK_SAVE
|
||||||
// Breakpoints
|
// Breakpoints
|
||||||
|
, CMD_BREAK_INVALID
|
||||||
|
, CMD_BREAK_OPCODE
|
||||||
, CMD_BREAKPOINT
|
, CMD_BREAKPOINT
|
||||||
, CMD_BREAKPOINT_ADD_SMART // smart breakpoint
|
, CMD_BREAKPOINT_ADD_SMART // smart breakpoint
|
||||||
, CMD_BREAKPOINT_ADD_REG // break on: PC == Address (fetch/execute)
|
, CMD_BREAKPOINT_ADD_REG // break on: PC == Address (fetch/execute)
|
||||||
|
|
|
@ -972,7 +972,7 @@ LRESULT CALLBACK FrameWndProc (
|
||||||
}
|
}
|
||||||
else if (g_nAppMode == MODE_DEBUG)
|
else if (g_nAppMode == MODE_DEBUG)
|
||||||
{
|
{
|
||||||
DebuggerProcessKey(wparam);
|
DebuggerProcessKey(wparam); // Debugger already active, re-direct key to debugger
|
||||||
}
|
}
|
||||||
|
|
||||||
if (wparam == VK_F10)
|
if (wparam == VK_F10)
|
||||||
|
@ -1468,19 +1468,13 @@ void ProcessButtonClick (int button)
|
||||||
ResetMachineState();
|
ResetMachineState();
|
||||||
g_nAppMode = MODE_RUNNING;
|
g_nAppMode = MODE_RUNNING;
|
||||||
}
|
}
|
||||||
if ((g_nAppMode == MODE_DEBUG) || (g_nAppMode == MODE_STEPPING))
|
if ((g_nAppMode == MODE_DEBUG) || (g_nAppMode == MODE_STEPPING)) // exit debugger
|
||||||
{
|
{
|
||||||
// If any breakpoints active,
|
// If any breakpoints active and ! we are not running at normal speed
|
||||||
if (g_nBreakpoints)
|
if (g_nBreakpoints && !g_bDebugNormalSpeedBreakpoints)
|
||||||
{
|
CmdGo( 0 ); // 6502 runs at full speed, switch to MODE_STEPPNIG
|
||||||
// switch to MODE_STEPPING
|
|
||||||
CmdGo( 0 );
|
|
||||||
}
|
|
||||||
else
|
else
|
||||||
{
|
DebugEnd(); // 6502 runs at normal speed, switch to MODE_RUNNING
|
||||||
DebugEnd();
|
|
||||||
g_nAppMode = MODE_RUNNING;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
DrawStatusArea((HDC)0,DRAW_TITLE);
|
DrawStatusArea((HDC)0,DRAW_TITLE);
|
||||||
VideoRedrawScreen();
|
VideoRedrawScreen();
|
||||||
|
@ -1510,10 +1504,7 @@ void ProcessButtonClick (int button)
|
||||||
{
|
{
|
||||||
ResetMachineState();
|
ResetMachineState();
|
||||||
}
|
}
|
||||||
|
// Allow F7 to enter debugger even though emulator isn't "running"
|
||||||
// bug/feature: allow F7 to enter debugger even though emulator isn't "running"
|
|
||||||
//else
|
|
||||||
|
|
||||||
if (g_nAppMode == MODE_STEPPING)
|
if (g_nAppMode == MODE_STEPPING)
|
||||||
{
|
{
|
||||||
DebuggerInputConsoleChar( DEBUG_EXIT_KEY );
|
DebuggerInputConsoleChar( DEBUG_EXIT_KEY );
|
||||||
|
@ -1521,8 +1512,13 @@ void ProcessButtonClick (int button)
|
||||||
else
|
else
|
||||||
if (g_nAppMode == MODE_DEBUG)
|
if (g_nAppMode == MODE_DEBUG)
|
||||||
{
|
{
|
||||||
g_bDebugDelayBreakCheck = true;
|
if (KeybGetShiftStatus())
|
||||||
ProcessButtonClick(BTN_RUN);
|
g_bDebugNormalSpeedBreakpoints = true; // MODE_RUNNING // Normal Speed Breakpoints: Shift-F7 exit debugger, keep breakpoints active, enter run state at NORMAL speed
|
||||||
|
else
|
||||||
|
g_bDebugNormalSpeedBreakpoints = false; // MODE_STEPPING // Full Speed Breakpoints
|
||||||
|
|
||||||
|
g_bDebugBreakDelayCheck = true;
|
||||||
|
ProcessButtonClick(BTN_RUN); // Exit debugger, switch to MODE_RUNNING or MODE_STEPPING
|
||||||
|
|
||||||
// TODO: DD Full-Screen Palette
|
// TODO: DD Full-Screen Palette
|
||||||
// exiting debugger using wrong palette, but this makes problem worse...
|
// exiting debugger using wrong palette, but this makes problem worse...
|
||||||
|
|
Loading…
Reference in New Issue
Block a user