diff --git a/src/debugger/CartDebug.cxx b/src/debugger/CartDebug.cxx index 6b45044ae..5b306f78c 100644 --- a/src/debugger/CartDebug.cxx +++ b/src/debugger/CartDebug.cxx @@ -169,177 +169,74 @@ string CartDebug::toString() } // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -const string& CartDebug::disassemble(int start, int lines) +bool CartDebug::disassemble(bool autocode) { - static string result= ""; - ostringstream buffer; - string cpubuf; + bool changed = false; - if(start < 0x80 || start > 0xffff) - return result; + // Test current disassembly; don't re-disassemble if it hasn't changed + // ... + changed = true; // FIXME - do { - buffer << getLabel(start, true, 4) << ": "; - - int count = disassemble(start, cpubuf); - for(int i = 0; i < count; i++) - buffer << hex << setw(2) << setfill('0') << myDebugger.peek(start++) << " " << dec; - - if(count < 3) buffer << " "; - if(count < 2) buffer << " "; - - buffer << " " << cpubuf << "\n"; - } while(--lines > 0 && start <= 0xffff); - - result = buffer.str(); - return result; -} - -// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -void CartDebug::disassemble(IntArray& addr, StringList& addrLabel, - StringList& bytes, StringList& data, - int start, int end) -{ - if(start < 0x80 || end > 0xffff) - return; - - string cpubuf, tmp; - char buf[255]; - - do { - addr.push_back(start); - addrLabel.push_back(getLabel(start, true, 4) + ":"); - - cpubuf = ""; - int count = disassemble(start, cpubuf); - - tmp = ""; - for(int i = 0; i < count; i++) - { - sprintf(buf, "%02x ", myDebugger.peek(start++)); - tmp += buf; - } - bytes.push_back(tmp); - - data.push_back(cpubuf); - } - while(start <= end); -} - -// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -void CartDebug::disassemble(DisassemblyList& list, uInt16 start, bool autocode) -{ - DiStella distella; - distella.disassemble(list, start, autocode); - - // TODO - look at list, extract address to label mappings -} - -// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -int CartDebug::disassemble(int address, string& result) -{ - ostringstream buf; - int count = 0; - int opcode = mySystem.peek(address); - - // Are we looking at a read or write operation? - // It will determine what type of label to use - bool isRead = (CartDebug::AccessModeTable[opcode] == CartDebug::Read); - - switch(CartDebug::AddressModeTable[opcode]) + if(changed) { - case CartDebug::Absolute: - buf << CartDebug::InstructionMnemonicTable[opcode] << " " - << getLabel(myDebugger.dpeek(address + 1), isRead, 4) << " ; " - << M6502::ourInstructionCycleTable[opcode]; - count = 3; - break; + myDisassembly.clear(); + myAddrToLineList.clear(); - case CartDebug::AbsoluteX: - buf << CartDebug::InstructionMnemonicTable[opcode] << " " - << getLabel(myDebugger.dpeek(address + 1), isRead, 4) << ",x ; " - << M6502::ourInstructionCycleTable[opcode]; - count = 3; - break; + // TODO - add logic to determine correct start address to use + // it will depend on the current bank and PC + uInt16 start = myDebugger.dpeek(0xfffc); - case CartDebug::AbsoluteY: - buf << CartDebug::InstructionMnemonicTable[opcode] << " " - << getLabel(myDebugger.dpeek(address + 1), isRead, 4) << ",y ; " - << M6502::ourInstructionCycleTable[opcode]; - count = 3; - break; + DiStella distella(myDisassembly, start, autocode); - case CartDebug::Immediate: - buf << CartDebug::InstructionMnemonicTable[opcode] << " #$" - << hex << setw(2) << setfill('0') << (int) mySystem.peek(address + 1) << " ; " - << dec << M6502::ourInstructionCycleTable[opcode]; - count = 2; - break; + // Parts of the disassembly will be accessed later in different ways + // We place those parts in separate maps, to speed up access + for(uInt32 i = 0; i < myDisassembly.size(); ++i) + { + const DisassemblyTag& tag = myDisassembly[i]; - case CartDebug::Implied: - buf << CartDebug::InstructionMnemonicTable[opcode] << " ; " - << M6502::ourInstructionCycleTable[opcode]; - count = 1; - break; + // Create a mapping from addresses to line numbers + if(tag.address != 0) + myAddrToLineList.insert(make_pair(tag.address, i)); - case CartDebug::Indirect: - buf << CartDebug::InstructionMnemonicTable[opcode] << " (" - << getLabel(myDebugger.dpeek(address + 1), isRead, 4) << ") ; " - << M6502::ourInstructionCycleTable[opcode]; - count = 3; - break; - - case CartDebug::IndirectX: - buf << CartDebug::InstructionMnemonicTable[opcode] << " (" - << getLabel(mySystem.peek(address + 1), isRead, 2) << ",x) ; " - << M6502::ourInstructionCycleTable[opcode]; - count = 2; - break; - - case CartDebug::IndirectY: - buf << CartDebug::InstructionMnemonicTable[opcode] << " (" - << getLabel(mySystem.peek(address + 1), isRead, 2) << "),y ; " - << M6502::ourInstructionCycleTable[opcode]; - count = 2; - break; - - case CartDebug::Relative: - buf << CartDebug::InstructionMnemonicTable[opcode] << " " - << getLabel(address + 2 + ((Int16)(Int8)mySystem.peek(address + 1)), isRead, 4) - << " ; " << M6502::ourInstructionCycleTable[opcode]; - count = 2; - break; - - case CartDebug::Zero: - buf << CartDebug::InstructionMnemonicTable[opcode] << " " - << getLabel(mySystem.peek(address + 1), isRead, 2) << " ; " - << M6502::ourInstructionCycleTable[opcode]; - count = 2; - break; - - case CartDebug::ZeroX: - buf << CartDebug::InstructionMnemonicTable[opcode] << " " - << getLabel(mySystem.peek(address + 1), isRead, 2) << ",x ; " - << M6502::ourInstructionCycleTable[opcode]; - count = 2; - break; - - case CartDebug::ZeroY: - buf << CartDebug::InstructionMnemonicTable[opcode] << " " - << getLabel(mySystem.peek(address + 1), isRead, 2) << ",y ; " - << M6502::ourInstructionCycleTable[opcode]; - count = 2; - break; - - default: - buf << "dc $" << hex << setw(2) << setfill('0') << (int) opcode << " ; " - << dec << M6502::ourInstructionCycleTable[opcode]; - count = 1; - break; + // TODO - look at list, extract address to label mappings + // we need these for label support in the UI and promptwidget + } } - result = buf.str(); - return count; + return changed; +} + +// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +int CartDebug::addressToLine(uInt16 address) const +{ + map::const_iterator iter = myAddrToLineList.find(address); + return iter != myAddrToLineList.end() ? iter->second : 0; +} + +// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +string CartDebug::disassemble(uInt16 start, uInt16 lines) const +{ + if(!(start & 0x1000)) + return "Disassembly below 0x1000 not yet supported"; + + DisassemblyList list; + DiStella distella(list, start, false); + + // Fill the string with disassembled data + start &= 0xFFF; + ostringstream buffer; + for(uInt32 i = 0; i < list.size() && lines > 0; ++i) + { + const CartDebug::DisassemblyTag& tag = list[i]; + if((tag.address & 0xfff) >= start) + { + buffer << uppercase << hex << setw(4) << setfill('0') << tag.address + << ": " << tag.disasm << " " << tag.bytes << endl; + --lines; + } + } + + return buffer.str(); } // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - @@ -677,396 +574,3 @@ int CartDebug::extractValue(char *c) const } return ret; } - -// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -const CartDebug::Equate CartDebug::ourSystemEquates[kSystemEquateSize] = { -// Standard $00-based TIA write locations: - { "VSYNC", 0x00, EQF_WRITE }, - { "VBLANK", 0x01, EQF_WRITE }, - { "WSYNC", 0x02, EQF_WRITE }, - { "RSYNC", 0x03, EQF_WRITE }, - { "NUSIZ0", 0x04, EQF_WRITE }, - { "NUSIZ1", 0x05, EQF_WRITE }, - { "COLUP0", 0x06, EQF_WRITE }, - { "COLUP1", 0x07, EQF_WRITE }, - { "COLUPF", 0x08, EQF_WRITE }, - { "COLUBK", 0x09, EQF_WRITE }, - { "CTRLPF", 0x0A, EQF_WRITE }, - { "REFP0", 0x0B, EQF_WRITE }, - { "REFP1", 0x0C, EQF_WRITE }, - { "PF0", 0x0D, EQF_WRITE }, - { "PF1", 0x0E, EQF_WRITE }, - { "PF2", 0x0F, EQF_WRITE }, - { "RESP0", 0x10, EQF_WRITE }, - { "RESP1", 0x11, EQF_WRITE }, - { "RESM0", 0x12, EQF_WRITE }, - { "RESM1", 0x13, EQF_WRITE }, - { "RESBL", 0x14, EQF_WRITE }, - { "AUDC0", 0x15, EQF_WRITE }, - { "AUDC1", 0x16, EQF_WRITE }, - { "AUDF0", 0x17, EQF_WRITE }, - { "AUDF1", 0x18, EQF_WRITE }, - { "AUDV0", 0x19, EQF_WRITE }, - { "AUDV1", 0x1A, EQF_WRITE }, - { "GRP0", 0x1B, EQF_WRITE }, - { "GRP1", 0x1C, EQF_WRITE }, - { "ENAM0", 0x1D, EQF_WRITE }, - { "ENAM1", 0x1E, EQF_WRITE }, - { "ENABL", 0x1F, EQF_WRITE }, - { "HMP0", 0x20, EQF_WRITE }, - { "HMP1", 0x21, EQF_WRITE }, - { "HMM0", 0x22, EQF_WRITE }, - { "HMM1", 0x23, EQF_WRITE }, - { "HMBL", 0x24, EQF_WRITE }, - { "VDELP0", 0x25, EQF_WRITE }, - { "VDEL01", 0x26, EQF_WRITE }, - { "VDELP1", 0x26, EQF_WRITE }, - { "VDELBL", 0x27, EQF_WRITE }, - { "RESMP0", 0x28, EQF_WRITE }, - { "RESMP1", 0x29, EQF_WRITE }, - { "HMOVE", 0x2A, EQF_WRITE }, - { "HMCLR", 0x2B, EQF_WRITE }, - { "CXCLR", 0x2C, EQF_WRITE }, - -// Mirrored $40-based TIA write locations: - { "VSYNC.40", 0x40, EQF_WRITE }, - { "VBLANK.40", 0x41, EQF_WRITE }, - { "WSYNC.40", 0x42, EQF_WRITE }, - { "RSYNC.40", 0x43, EQF_WRITE }, - { "NUSIZ0.40", 0x44, EQF_WRITE }, - { "NUSIZ1.40", 0x45, EQF_WRITE }, - { "COLUP0.40", 0x46, EQF_WRITE }, - { "COLUP1.40", 0x47, EQF_WRITE }, - { "COLUPF.40", 0x48, EQF_WRITE }, - { "COLUBK.40", 0x49, EQF_WRITE }, - { "CTRLPF.40", 0x4A, EQF_WRITE }, - { "REFP0.40", 0x4B, EQF_WRITE }, - { "REFP1.40", 0x4C, EQF_WRITE }, - { "PF0.40", 0x4D, EQF_WRITE }, - { "PF1.40", 0x4E, EQF_WRITE }, - { "PF2.40", 0x4F, EQF_WRITE }, - { "RESP0.40", 0x50, EQF_WRITE }, - { "RESP1.40", 0x51, EQF_WRITE }, - { "RESM0.40", 0x52, EQF_WRITE }, - { "RESM1.40", 0x53, EQF_WRITE }, - { "RESBL.40", 0x54, EQF_WRITE }, - { "AUDC0.40", 0x55, EQF_WRITE }, - { "AUDC1.40", 0x56, EQF_WRITE }, - { "AUDF0.40", 0x57, EQF_WRITE }, - { "AUDF1.40", 0x58, EQF_WRITE }, - { "AUDV0.40", 0x59, EQF_WRITE }, - { "AUDV1.40", 0x5A, EQF_WRITE }, - { "GRP0.40", 0x5B, EQF_WRITE }, - { "GRP1.40", 0x5C, EQF_WRITE }, - { "ENAM0.40", 0x5D, EQF_WRITE }, - { "ENAM1.40", 0x5E, EQF_WRITE }, - { "ENABL.40", 0x5F, EQF_WRITE }, - { "HMP0.40", 0x60, EQF_WRITE }, - { "HMP1.40", 0x61, EQF_WRITE }, - { "HMM0.40", 0x62, EQF_WRITE }, - { "HMM1.40", 0x63, EQF_WRITE }, - { "HMBL.40", 0x64, EQF_WRITE }, - { "VDELP0.40", 0x65, EQF_WRITE }, - { "VDEL01.40", 0x66, EQF_WRITE }, - { "VDELP1.40", 0x66, EQF_WRITE }, - { "VDELBL.40", 0x67, EQF_WRITE }, - { "RESMP0.40", 0x68, EQF_WRITE }, - { "RESMP1.40", 0x69, EQF_WRITE }, - { "HMOVE.40", 0x6A, EQF_WRITE }, - { "HMCLR.40", 0x6B, EQF_WRITE }, - { "CXCLR.40", 0x6C, EQF_WRITE }, - -// Standard $00-based TIA read locations: - { "CXM0P", 0x00, EQF_READ }, - { "CXM1P", 0x01, EQF_READ }, - { "CXP0FB", 0x02, EQF_READ }, - { "CXP1FB", 0x03, EQF_READ }, - { "CXM0FB", 0x04, EQF_READ }, - { "CXM1FB", 0x05, EQF_READ }, - { "CXBLPF", 0x06, EQF_READ }, - { "CXPPMM", 0x07, EQF_READ }, - { "INPT0", 0x08, EQF_READ }, - { "INPT1", 0x09, EQF_READ }, - { "INPT2", 0x0A, EQF_READ }, - { "INPT3", 0x0B, EQF_READ }, - { "INPT4", 0x0C, EQF_READ }, - { "INPT5", 0x0D, EQF_READ }, - -// Mirrored $10-based TIA read locations: - { "CXM0P.10", 0x10, EQF_READ }, - { "CXM1P.10", 0x11, EQF_READ }, - { "CXP0FB.10", 0x12, EQF_READ }, - { "CXP1FB.10", 0x13, EQF_READ }, - { "CXM0FB.10", 0x14, EQF_READ }, - { "CXM1FB.10", 0x15, EQF_READ }, - { "CXBLPF.10", 0x16, EQF_READ }, - { "CXPPMM.10", 0x17, EQF_READ }, - { "INPT0.10", 0x18, EQF_READ }, - { "INPT1.10", 0x19, EQF_READ }, - { "INPT2.10", 0x1A, EQF_READ }, - { "INPT3.10", 0x1B, EQF_READ }, - { "INPT4.10", 0x1C, EQF_READ }, - { "INPT5.10", 0x1D, EQF_READ }, - -// Mirrored $20-based TIA read locations: - { "CXM0P.20", 0x20, EQF_READ }, - { "CXM1P.20", 0x21, EQF_READ }, - { "CXP0FB.20", 0x22, EQF_READ }, - { "CXP1FB.20", 0x23, EQF_READ }, - { "CXM0FB.20", 0x24, EQF_READ }, - { "CXM1FB.20", 0x25, EQF_READ }, - { "CXBLPF.20", 0x26, EQF_READ }, - { "CXPPMM.20", 0x27, EQF_READ }, - { "INPT0.20", 0x28, EQF_READ }, - { "INPT1.20", 0x29, EQF_READ }, - { "INPT2.20", 0x2A, EQF_READ }, - { "INPT3.20", 0x2B, EQF_READ }, - { "INPT4.20", 0x2C, EQF_READ }, - { "INPT5.20", 0x2D, EQF_READ }, - -// Mirrored $30-based TIA read locations: - { "CXM0P.30", 0x30, EQF_READ }, - { "CXM1P.30", 0x31, EQF_READ }, - { "CXP0FB.30", 0x32, EQF_READ }, - { "CXP1FB.30", 0x33, EQF_READ }, - { "CXM0FB.30", 0x34, EQF_READ }, - { "CXM1FB.30", 0x35, EQF_READ }, - { "CXBLPF.30", 0x36, EQF_READ }, - { "CXPPMM.30", 0x37, EQF_READ }, - { "INPT0.30", 0x38, EQF_READ }, - { "INPT1.30", 0x39, EQF_READ }, - { "INPT2.30", 0x3A, EQF_READ }, - { "INPT3.30", 0x3B, EQF_READ }, - { "INPT4.30", 0x3C, EQF_READ }, - { "INPT5.30", 0x3D, EQF_READ }, - -// Standard RIOT locations (read, write, or both): - { "SWCHA", 0x280, EQF_RW }, - { "SWCHB", 0x282, EQF_RW }, - { "SWACNT", 0x281, EQF_WRITE }, - { "SWBCNT", 0x283, EQF_WRITE }, - { "INTIM", 0x284, EQF_READ }, - { "TIMINT", 0x285, EQF_READ }, - { "TIM1T", 0x294, EQF_WRITE }, - { "TIM8T", 0x295, EQF_WRITE }, - { "TIM64T", 0x296, EQF_WRITE }, - { "T1024T", 0x297, EQF_WRITE } -}; - -/////////////////////////////////////////////////////////////////// -// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -CartDebug::AddressingMode CartDebug::AddressModeTable[256] = { - Implied, IndirectX, Invalid, IndirectX, // 0x0? - Zero, Zero, Zero, Zero, - Implied, Immediate, Implied, Immediate, - Absolute, Absolute, Absolute, Absolute, - - Relative, IndirectY, Invalid, IndirectY, // 0x1? - ZeroX, ZeroX, ZeroX, ZeroX, - Implied, AbsoluteY, Implied, AbsoluteY, - AbsoluteX, AbsoluteX, AbsoluteX, AbsoluteX, - - Absolute, IndirectX, Invalid, IndirectX, // 0x2? - Zero, Zero, Zero, Zero, - Implied, Immediate, Implied, Immediate, - Absolute, Absolute, Absolute, Absolute, - - Relative, IndirectY, Invalid, IndirectY, // 0x3? - ZeroX, ZeroX, ZeroX, ZeroX, - Implied, AbsoluteY, Implied, AbsoluteY, - AbsoluteX, AbsoluteX, AbsoluteX, AbsoluteX, - - Implied, IndirectX, Invalid, IndirectX, // 0x4? - Zero, Zero, Zero, Zero, - Implied, Immediate, Implied, Immediate, - Absolute, Absolute, Absolute, Absolute, - - Relative, IndirectY, Invalid, IndirectY, // 0x5? - ZeroX, ZeroX, ZeroX, ZeroX, - Implied, AbsoluteY, Implied, AbsoluteY, - AbsoluteX, AbsoluteX, AbsoluteX, AbsoluteX, - - Implied, IndirectX, Invalid, IndirectX, // 0x6? - Zero, Zero, Zero, Zero, - Implied, Immediate, Implied, Immediate, - Indirect, Absolute, Absolute, Absolute, - - Relative, IndirectY, Invalid, IndirectY, // 0x7? - ZeroX, ZeroX, ZeroX, ZeroX, - Implied, AbsoluteY, Implied, AbsoluteY, - AbsoluteX, AbsoluteX, AbsoluteX, AbsoluteX, - - Immediate, IndirectX, Immediate, IndirectX, // 0x8? - Zero, Zero, Zero, Zero, - Implied, Immediate, Implied, Immediate, - Absolute, Absolute, Absolute, Absolute, - - Relative, IndirectY, Invalid, IndirectY, // 0x9? - ZeroX, ZeroX, ZeroY, ZeroY, - Implied, AbsoluteY, Implied, AbsoluteY, - AbsoluteX, AbsoluteX, AbsoluteY, AbsoluteY, - - Immediate, IndirectX, Immediate, IndirectX, // 0xA? - Zero, Zero, Zero, Zero, - Implied, Immediate, Implied, Immediate, - Absolute, Absolute, Absolute, Absolute, - - Relative, IndirectY, Invalid, IndirectY, // 0xB? - ZeroX, ZeroX, ZeroY, ZeroY, - Implied, AbsoluteY, Implied, AbsoluteY, - AbsoluteX, AbsoluteX, AbsoluteY, AbsoluteY, - - Immediate, IndirectX, Immediate, IndirectX, // 0xC? - Zero, Zero, Zero, Zero, - Implied, Immediate, Implied, Immediate, - Absolute, Absolute, Absolute, Absolute, - - Relative, IndirectY, Invalid, IndirectY, // 0xD? - ZeroX, ZeroX, ZeroX, ZeroX, - Implied, AbsoluteY, Implied, AbsoluteY, - AbsoluteX, AbsoluteX, AbsoluteX, AbsoluteX, - - Immediate, IndirectX, Immediate, IndirectX, // 0xE? - Zero, Zero, Zero, Zero, - Implied, Immediate, Implied, Immediate, - Absolute, Absolute, Absolute, Absolute, - - Relative, IndirectY, Invalid, IndirectY, // 0xF? - ZeroX, ZeroX, ZeroX, ZeroX, - Implied, AbsoluteY, Implied, AbsoluteY, - AbsoluteX, AbsoluteX, AbsoluteX, AbsoluteX -}; - -// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -CartDebug::AccessMode CartDebug::AccessModeTable[256] = { - None, Read, None, Write, // 0x0? - None, Read, Write, Write, - None, Read, Write, Read, - None, Read, Write, Write, - - Read, Read, None, Write, // 0x1? - None, Read, Write, Write, - None, Read, None, Write, - None, Read, Write, Write, - - Read, Read, None, Write, // 0x2? - Read, Read, Write, Write, - None, Read, Write, Read, - Read, Read, Write, Write, - - Read, Read, None, Write, // 0x3? - None, Read, Write, Write, - None, Read, None, Write, - None, Read, Write, Write, - - None, Read, None, Write, // 0x4? - None, Read, Write, Write, - None, Read, Write, Read, - Read, Read, Write, Write, - - Read, Read, None, Write, // 0x5? - None, Read, Write, Write, - None, Read, None, Write, - None, Read, Write, Write, - - None, Read, None, Write, // 0x6? - None, Read, Write, Write, - None, Read, Write, Read, - Read, Read, Write, Write, - - Read, Read, None, Write, // 0x7? - None, Read, Write, Write, - None, Read, None, Write, - None, Read, Write, Write, - - None, Write, None, Write, // 0x8? - Write, Write, Write, Write, - None, None, None, Read, - Write, Write, Write, Write, - - Read, Write, None, Write, // 0x9? - Write, Write, Write, Write, - None, Write, None, Write, - Write, Write, Write, Write, - - Read, Read, Read, Read, // 0xA? - Read, Read, Read, Read, - None, Read, None, Read, - Read, Read, Read, Read, - - Read, Read, None, Read, // 0xB? - Read, Read, Read, Read, - None, Read, None, Read, - Read, Read, Read, Read, - - Read, Read, None, Write, // 0xC? - Read, Read, Write, Write, - None, Read, None, Read, - Read, Read, Write, Write, - - Read, Read, None, Write, // 0xD? - None, Read, Write, Write, - None, Read, None, Write, - None, Read, Write, Write, - - Read, Read, None, Write, // 0xE? - Read, Read, Write, Write, - None, Read, None, Read, - Read, Read, Write, Write, - - Read, Read, None, Write, // 0xF? - None, Read, Write, Write, - None, Read, None, Write, - None, Read, Write, Write -}; - -// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -const char* CartDebug::InstructionMnemonicTable[256] = { - "BRK", "ORA", "n/a", "slo", "nop", "ORA", "ASL", "slo", // 0x0? - "PHP", "ORA", "ASLA", "anc", "nop", "ORA", "ASL", "slo", - - "BPL", "ORA", "n/a", "slo", "nop", "ORA", "ASL", "slo", // 0x1? - "CLC", "ORA", "nop", "slo", "nop", "ORA", "ASL", "slo", - - "JSR", "AND", "n/a", "rla", "BIT", "AND", "ROL", "rla", // 0x2? - "PLP", "AND", "ROLA", "anc", "BIT", "AND", "ROL", "rla", - - "BMI", "AND", "n/a", "rla", "nop", "AND", "ROL", "rla", // 0x3? - "SEC", "AND", "nop", "rla", "nop", "AND", "ROL", "rla", - - "RTI", "EOR", "n/a", "sre", "nop", "EOR", "LSR", "sre", // 0x4? - "PHA", "EOR", "LSRA", "asr", "JMP", "EOR", "LSR", "sre", - - "BVC", "EOR", "n/a", "sre", "nop", "EOR", "LSR", "sre", // 0x5? - "CLI", "EOR", "nop", "sre", "nop", "EOR", "LSR", "sre", - - "RTS", "ADC", "n/a", "rra", "nop", "ADC", "ROR", "rra", // 0x6? - "PLA", "ADC", "RORA", "arr", "JMP", "ADC", "ROR", "rra", - - "BVS", "ADC", "n/a", "rra", "nop", "ADC", "ROR", "rra", // 0x7? - "SEI", "ADC", "nop", "rra", "nop", "ADC", "ROR", "rra", - - "nop", "STA", "nop", "sax", "STY", "STA", "STX", "sax", // 0x8? - "DEY", "nop", "TXA", "ane", "STY", "STA", "STX", "sax", - - "BCC", "STA", "n/a", "sha", "STY", "STA", "STX", "sax", // 0x9? - "TYA", "STA", "TXS", "shs", "shy", "STA", "shx", "sha", - - "LDY", "LDA", "LDX", "lax", "LDY", "LDA", "LDX", "lax", // 0xA? - "TAY", "LDA", "TAX", "lxa", "LDY", "LDA", "LDX", "lax", - - "BCS", "LDA", "n/a", "lax", "LDY", "LDA", "LDX", "lax", // 0xB? - "CLV", "LDA", "TSX", "las", "LDY", "LDA", "LDX", "lax", - - "CPY", "CMP", "nop", "dcp", "CPY", "CMP", "DEC", "dcp", // 0xC? - "INY", "CMP", "DEX", "sbx", "CPY", "CMP", "DEC", "dcp", - - "BNE", "CMP", "n/a", "dcp", "nop", "CMP", "DEC", "dcp", // 0xD? - "CLD", "CMP", "nop", "dcp", "nop", "CMP", "DEC", "dcp", - - "CPX", "SBC", "nop", "isb", "CPX", "SBC", "INC", "isb", // 0xE? - "INX", "SBC", "NOP", "sbc", "CPX", "SBC", "INC", "isb", - - "BEQ", "SBC", "n/a", "isb", "nop", "SBC", "INC", "isb", // 0xF? - "SED", "SBC", "nop", "isb", "nop", "SBC", "INC", "isb" -}; diff --git a/src/debugger/CartDebug.hxx b/src/debugger/CartDebug.hxx index db4234884..27f6b1a23 100644 --- a/src/debugger/CartDebug.hxx +++ b/src/debugger/CartDebug.hxx @@ -21,6 +21,8 @@ class System; +#include + #include "bspf.hxx" #include "Array.hxx" #include "Cart.hxx" @@ -83,32 +85,44 @@ class CartDebug : public DebuggerSystem */ void addRamArea(uInt16 start, uInt16 size, uInt16 roffset, uInt16 woffset); -//////////////////////////////////////// - /** - Disassemble from the starting address the specified number of lines - and place result in a string. - */ - const string& disassemble(int start, int lines); - - /** - Disassemble from the starting address to the ending address - and place addresses, bytes and data in given arrays. - */ - void disassemble(IntArray& addr, StringList& addrLabel, - StringList& bytes, StringList& data, - int start, int end); - + // The following two methods are meant to be used together + // First, a call is made to disassemble(), which updates the disassembly + // list; it will figure out when an actual complete disassembly is + // required, and when the previous results can be used + // + // Later, successive calls to disassemblyList() simply return the + // previous results; no disassembly is done in this case /** Disassemble from the given address using the Distella disassembler Address-to-label mappings (and vice-versa) are also determined here + + @return True if disassembly changed from previous call, else false */ - void disassemble(DisassemblyList& list, uInt16 start, bool autocode); + bool disassemble(bool autocode); + + /** + Get the results from the most recent call to disassemble() + */ + const DisassemblyList& disassemblyList() const { return myDisassembly; } + + /** + Determine the line in the disassembly that corresponds to the given + address. A value of zero indicates that no such address exists. + */ + int addressToLine(uInt16 address) const; + + /** + Disassemble from the starting address the specified number of lines. + Note that automatic code determination is turned off for this method; + it will treat all address contents as instructions. + */ + string disassemble(uInt16 start, uInt16 lines) const; int getBank(); int bankCount(); string getCartType(); -//////////////////////////////////////// +//////////////////////////////////////// /** Add a label and associated address */ @@ -148,9 +162,7 @@ class CartDebug : public DebuggerSystem int countCompletions(const char *in); const string& getCompletions() const { return myCompletions; } const string& getCompletionPrefix() const { return myCompPrefix; } - - private: - int disassemble(int address, string& result); +//////////////////////////////////////// private: enum equate_t { @@ -186,6 +198,7 @@ class CartDebug : public DebuggerSystem CartState myOldState; DisassemblyList myDisassembly; + map myAddrToLineList; LabelToAddr mySystemAddresses; AddrToLabel mySystemReadLabels; // labels used in a read context @@ -200,40 +213,6 @@ class CartDebug : public DebuggerSystem string myCompPrefix; uInt16 myRWPortAddress; - - enum { kSystemEquateSize = 158 }; - static const Equate ourSystemEquates[kSystemEquateSize]; - -////////////////////////////////////////////// - /** - Enumeration of the 6502 addressing modes - */ - enum AddressingMode - { - Absolute, AbsoluteX, AbsoluteY, Immediate, Implied, - Indirect, IndirectX, IndirectY, Invalid, Relative, - Zero, ZeroX, ZeroY - }; - - /** - Enumeration of the 6502 access modes - */ - enum AccessMode - { - Read, Write, None - }; - - /// Addressing mode for each of the 256 opcodes - /// This specifies how the opcode argument is addressed - static AddressingMode AddressModeTable[256]; - - /// Access mode for each of the 256 opcodes - /// This specifies how the opcode will access its argument - static AccessMode AccessModeTable[256]; - - /// Table of instruction mnemonics - static const char* InstructionMnemonicTable[256]; -////////////////////////////////////////////// }; #endif diff --git a/src/debugger/DiStella.cxx b/src/debugger/DiStella.cxx index c071d96df..888686029 100644 --- a/src/debugger/DiStella.cxx +++ b/src/debugger/DiStella.cxx @@ -25,19 +25,9 @@ #include "DiStella.hxx" // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -DiStella::DiStella() +DiStella::DiStella(CartDebug::DisassemblyList& list, uInt16 start, + bool autocode) : labels(NULL) /* array of information about addresses-- can be from 2K-48K bytes in size */ -{ -} - -// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -DiStella::~DiStella() -{ -} - -// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -uInt32 DiStella::disassemble(CartDebug::DisassemblyList& list, uInt16 start, - bool autocode) { while(!myAddressQueue.empty()) myAddressQueue.pop(); @@ -52,7 +42,7 @@ uInt32 DiStella::disassemble(CartDebug::DisassemblyList& list, uInt16 start, if (labels == NULL) { fprintf (stderr, "Malloc failed for 'labels' variable\n"); - return 0; + return; } memset(labels,0,myAppData.length); @@ -103,8 +93,11 @@ uInt32 DiStella::disassemble(CartDebug::DisassemblyList& list, uInt16 start, disasm(list, myOffset, 3); free(labels); /* Free dynamic memory before program ends */ +} - return list.size(); +// - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - +DiStella::~DiStella() +{ } // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - @@ -139,8 +132,8 @@ void DiStella::disasm(CartDebug::DisassemblyList& list, uInt32 distart, int pass else myBuf << HEX4 << myPC+myOffset << "' '"; - myBuf << ".byte $" << HEX2 << (int)Debugger::debugger().peek(myPC|0x1000) << " ; "; - showgfx(Debugger::debugger().peek(myPC|0x1000)); + myBuf << ".byte $" << HEX2 << (int)Debugger::debugger().peek(myPC+myOffset) << " ; "; + showgfx(Debugger::debugger().peek(myPC+myOffset)); myBuf << " $" << HEX4 << myPC+myOffset; addEntry(list); } @@ -154,7 +147,7 @@ void DiStella::disasm(CartDebug::DisassemblyList& list, uInt32 distart, int pass { bytes = 1; myBuf << HEX4 << myPC+myOffset << "'L" << myPC+myOffset << "'.byte " - << "$" << HEX2 << (int)Debugger::debugger().peek(myPC|0x1000); + << "$" << HEX2 << (int)Debugger::debugger().peek(myPC+myOffset); } myPC++; @@ -167,11 +160,11 @@ void DiStella::disasm(CartDebug::DisassemblyList& list, uInt32 distart, int pass if (bytes == 17) { addEntry(list); - myBuf << " ' '.byte $" << HEX2 << (int)Debugger::debugger().peek(myPC|0x1000); + myBuf << " ' '.byte $" << HEX2 << (int)Debugger::debugger().peek(myPC+myOffset); bytes = 1; } else - myBuf << ",$" << HEX2 << (int)Debugger::debugger().peek(myPC|0x1000); + myBuf << ",$" << HEX2 << (int)Debugger::debugger().peek(myPC+myOffset); } myPC++; } @@ -185,7 +178,7 @@ void DiStella::disasm(CartDebug::DisassemblyList& list, uInt32 distart, int pass } else { - op = Debugger::debugger().peek(myPC|0x1000); + op = Debugger::debugger().peek(myPC+myOffset); /* version 2.1 bug fix */ if (pass == 2) mark(myPC+myOffset, VALID_ENTRY); @@ -254,7 +247,7 @@ void DiStella::disasm(CartDebug::DisassemblyList& list, uInt32 distart, int pass else myBuf << HEX4 << myPC+myOffset << "' '"; - op = Debugger::debugger().peek(myPC|0x1000); myPC++; + op = Debugger::debugger().peek(myPC+myOffset); myPC++; myBuf << ".byte $" << HEX2 << (int)op; addEntry(list); } @@ -321,7 +314,7 @@ void DiStella::disasm(CartDebug::DisassemblyList& list, uInt32 distart, int pass case ABSOLUTE: { - ad = Debugger::debugger().dpeek(myPC|0x1000); myPC+=2; + ad = Debugger::debugger().dpeek(myPC+myOffset); myPC+=2; labfound = mark(ad, REFERENCED); if (pass == 1) { @@ -380,7 +373,7 @@ void DiStella::disasm(CartDebug::DisassemblyList& list, uInt32 distart, int pass case ZERO_PAGE: { - d1 = Debugger::debugger().peek(myPC|0x1000); myPC++; + d1 = Debugger::debugger().peek(myPC+myOffset); myPC++; labfound = mark(d1, REFERENCED); if (pass == 3) { @@ -402,7 +395,7 @@ void DiStella::disasm(CartDebug::DisassemblyList& list, uInt32 distart, int pass case IMMEDIATE: { - d1 = Debugger::debugger().peek(myPC|0x1000); myPC++; + d1 = Debugger::debugger().peek(myPC+myOffset); myPC++; if (pass == 3) { sprintf(linebuff," #$%.2X ",d1); @@ -415,7 +408,7 @@ void DiStella::disasm(CartDebug::DisassemblyList& list, uInt32 distart, int pass case ABSOLUTE_X: { - ad = Debugger::debugger().dpeek(myPC|0x1000); myPC+=2; + ad = Debugger::debugger().dpeek(myPC+myOffset); myPC+=2; labfound = mark(ad, REFERENCED); if (pass == 3) { @@ -465,7 +458,7 @@ void DiStella::disasm(CartDebug::DisassemblyList& list, uInt32 distart, int pass case ABSOLUTE_Y: { - ad = Debugger::debugger().dpeek(myPC|0x1000); myPC+=2; + ad = Debugger::debugger().dpeek(myPC+myOffset); myPC+=2; labfound = mark(ad, REFERENCED); if (pass == 3) { @@ -514,7 +507,7 @@ void DiStella::disasm(CartDebug::DisassemblyList& list, uInt32 distart, int pass case INDIRECT_X: { - d1 = Debugger::debugger().peek(myPC|0x1000); myPC++; + d1 = Debugger::debugger().peek(myPC+myOffset); myPC++; if (pass == 3) { sprintf(linebuff," ($%.2X,X)",d1); @@ -527,7 +520,7 @@ void DiStella::disasm(CartDebug::DisassemblyList& list, uInt32 distart, int pass case INDIRECT_Y: { - d1 = Debugger::debugger().peek(myPC|0x1000); myPC++; + d1 = Debugger::debugger().peek(myPC+myOffset); myPC++; if (pass == 3) { sprintf(linebuff," ($%.2X),Y",d1); @@ -540,7 +533,7 @@ void DiStella::disasm(CartDebug::DisassemblyList& list, uInt32 distart, int pass case ZERO_PAGE_X: { - d1 = Debugger::debugger().peek(myPC|0x1000); myPC++; + d1 = Debugger::debugger().peek(myPC+myOffset); myPC++; labfound = mark(d1, REFERENCED); if (pass == 3) { @@ -562,7 +555,7 @@ void DiStella::disasm(CartDebug::DisassemblyList& list, uInt32 distart, int pass case ZERO_PAGE_Y: { - d1 = Debugger::debugger().peek(myPC|0x1000); myPC++; + d1 = Debugger::debugger().peek(myPC+myOffset); myPC++; labfound = mark(d1,REFERENCED); if (pass == 3) { @@ -584,7 +577,7 @@ void DiStella::disasm(CartDebug::DisassemblyList& list, uInt32 distart, int pass case RELATIVE: { - d1 = Debugger::debugger().peek(myPC|0x1000); myPC++; + d1 = Debugger::debugger().peek(myPC+myOffset); myPC++; ad = d1; if (d1 >= 128) ad = d1 - 256; @@ -620,7 +613,7 @@ void DiStella::disasm(CartDebug::DisassemblyList& list, uInt32 distart, int pass case ABS_INDIRECT: { - ad = Debugger::debugger().dpeek(myPC|0x1000); myPC+=2; + ad = Debugger::debugger().dpeek(myPC+myOffset); myPC+=2; labfound = mark(ad, REFERENCED); if (pass == 3) { diff --git a/src/debugger/DiStella.hxx b/src/debugger/DiStella.hxx index 4f709e904..aa8123fdb 100644 --- a/src/debugger/DiStella.hxx +++ b/src/debugger/DiStella.hxx @@ -41,10 +41,6 @@ */ class DiStella { - public: - DiStella(); - ~DiStella(); - public: /** Disassemble the current state of the System from the given start address. @@ -52,11 +48,11 @@ class DiStella @param list The results of the disassembly are placed here @param start The address at which to start disassembly @param autocode If enabled, try to determine code vs. data sections - - @return The number of lines that were disassembled */ - uInt32 disassemble(CartDebug::DisassemblyList& list, uInt16 start, - bool autocode = true); + DiStella(CartDebug::DisassemblyList& list, uInt16 start, + bool autocode = true); + + ~DiStella(); private: // Marked bits diff --git a/src/debugger/gui/RomListWidget.cxx b/src/debugger/gui/RomListWidget.cxx index fff5b8a67..811d06c9e 100644 --- a/src/debugger/gui/RomListWidget.cxx +++ b/src/debugger/gui/RomListWidget.cxx @@ -52,12 +52,15 @@ RomListWidget::~RomListWidget() } // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -void RomListWidget::setList(StringList& label, StringList& bytes, StringList& disasm, - BoolArray& state) +void RomListWidget::setList(const CartDebug::DisassemblyList& list, + const BoolArray& state) { - myLabel = label; - myDisasm = disasm; + myList = &list; + // TODO - maybe there's a better way than copying all the bytes again?? + StringList bytes; + for(uInt32 i = 0; i < list.size(); ++i) + bytes.push_back(list[i].bytes); CheckListWidget::setList(bytes, state); } @@ -85,7 +88,8 @@ void RomListWidget::drawWidget(bool hilite) { //cerr << "RomListWidget::drawWidget\n"; FBSurface& s = _boss->dialog().surface(); - int i, pos, xpos, ypos, len = _list.size(); + const CartDebug::DisassemblyList& dlist = *myList; + int i, pos, xpos, ypos, len = dlist.size(); string buffer; int deltax; @@ -126,11 +130,11 @@ void RomListWidget::drawWidget(bool hilite) } // Draw labels - s.drawString(_font, myLabel[pos], xpos, ypos, + s.drawString(_font, dlist[pos].label, xpos, ypos, myLabelWidth, kTextColor); // Draw disassembly - s.drawString(_font, myDisasm[pos], xpos + myLabelWidth, ypos, + s.drawString(_font, dlist[pos].disasm, xpos + myLabelWidth, ypos, r.left, kTextColor); // Draw editable bytes diff --git a/src/debugger/gui/RomListWidget.hxx b/src/debugger/gui/RomListWidget.hxx index b426f8dc5..076164c59 100644 --- a/src/debugger/gui/RomListWidget.hxx +++ b/src/debugger/gui/RomListWidget.hxx @@ -26,7 +26,7 @@ class CheckboxWidget; class ContextMenu; #include "CheckListWidget.hxx" - +#include "CartDebug.hxx" /** RomListWidget */ class RomListWidget : public CheckListWidget @@ -38,8 +38,7 @@ class RomListWidget : public CheckListWidget int x, int y, int w, int h); virtual ~RomListWidget(); - void setList(StringList& label, StringList& bytes, StringList& disasm, - BoolArray& state); + void setList(const CartDebug::DisassemblyList& list, const BoolArray& state); protected: void handleMouseDown(int x, int y, int button, int clickCount); @@ -56,7 +55,7 @@ class RomListWidget : public CheckListWidget int myLabelWidth; int myBytesWidth; - StringList myLabel, myDisasm; + const CartDebug::DisassemblyList* myList; }; #endif diff --git a/src/debugger/gui/RomWidget.cxx b/src/debugger/gui/RomWidget.cxx index 6a4c2b069..a2e17e213 100644 --- a/src/debugger/gui/RomWidget.cxx +++ b/src/debugger/gui/RomWidget.cxx @@ -100,9 +100,6 @@ RomWidget::RomWidget(GuiObject* boss, const GUI::Font& font, int x, int y) // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - RomWidget::~RomWidget() { - myAddrList.clear(); - myLineList.clear(); - delete mySaveRom; } @@ -166,71 +163,39 @@ void RomWidget::loadConfig() // Fill romlist the current bank of source or disassembly // Only reload full bank when necessary - if(myListIsDirty || bankChanged) + // TODO - bank changes aren't the only time that the disassembly needs to + // be redone; ROMs which dynamically change cart address space and + // have self-modifying code need to be taken into account + // As well, we don't always start from the 0xfffc; this only + // happens in the startup bank + myListIsDirty |= cart.disassemble(true); + if(myListIsDirty) { -/* - // Clear old mappings - myAddrList.clear(); - myLineList.clear(); - - StringList label, data, disasm; + const CartDebug::DisassemblyList& list = cart.disassemblyList(); BoolArray state; - // Disassemble zero-page RAM and entire bank and reset breakpoints - cart.disassemble(myAddrList, label, data, disasm, 0x80, 0xff); - cart.disassemble(myAddrList, label, data, disasm, 0xf000, 0xffff); - PackedBitArray& bp = dbg.breakpoints(); - for(unsigned int i = 0; i < data.size(); ++i) + for(uInt32 i = 0; i < list.size(); ++i) { - if(bp.isSet(myAddrList[i])) + const CartDebug::DisassemblyTag& tag = list[i]; + if(tag.address != 0 && bp.isSet(tag.address)) state.push_back(true); else state.push_back(false); } - // Create a mapping from addresses to line numbers - for(unsigned int i = 0; i < myAddrList.size(); ++i) - myLineList.insert(make_pair(myAddrList[i], i)); - - myRomList->setList(label, data, disasm, state); + myRomList->setList(list, state); // Restore the old bank, in case we inadvertently switched while reading. dbg.setBank(myCurrentBank); -*/ - CartDebug::DisassemblyList list; - cart.disassemble(list, dbg.dpeek(0xfffc), true); - - for(uInt32 i = 0; i < list.size(); ++i) - { - const CartDebug::DisassemblyTag& tag = list[i]; - printf("%.4X|%5s|%s|%s|\n", tag.address, tag.label.c_str(), tag.disasm.c_str(), tag.bytes.c_str()); - } - - myListIsDirty = false; } // Update romlist to point to current PC - // Take mirroring of PC into account, as well as zero-page RAM - int pc = dbg.cpuDebug().pc(); - if(pc & 0x1000) pc |= 0xe000; - AddrToLine::iterator iter = myLineList.find(pc); - - // if current PC not found, do an update (we're executing what - // we thought was an operand) - - // This doesn't help, and seems to actually hurt. - /* - if(iter == myLineList.end()) { - incrementalUpdate(myRomList->currentPos(), myRomList->rows()); - iter = myLineList.find(pc); - } - */ - - if(iter != myLineList.end()) - myRomList->setHighlighted(iter->second); + int pcline = cart.addressToLine(dbg.cpuDebug().pc()); + if(pcline > 0) + myRomList->setHighlighted(pcline); // Set current bank IntArray alist; @@ -249,34 +214,53 @@ void RomWidget::loadConfig() // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - void RomWidget::setBreak(int data) { + const CartDebug::DisassemblyList& list = + instance().debugger().cartDebug().disassemblyList(); + if(data >= (int)list.size()) return; + bool state = myRomList->getState(data); - instance().debugger().setBreakPoint(myAddrList[data], state); + if(list[data].address != 0) + instance().debugger().setBreakPoint(list[data].address, state); } // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - void RomWidget::setPC(int data) { - ostringstream command; - command << "pc #" << myAddrList[data]; - instance().debugger().run(command.str()); + const CartDebug::DisassemblyList& list = + instance().debugger().cartDebug().disassemblyList(); + if(data >= (int)list.size()) return; + + if(list[data].address != 0) + { + ostringstream command; + command << "pc #" << list[data].address; + instance().debugger().run(command.str()); + } } // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - void RomWidget::patchROM(int data, const string& bytes) { - ostringstream command; + const CartDebug::DisassemblyList& list = + instance().debugger().cartDebug().disassemblyList(); + if(data >= (int)list.size()) return; - // Temporarily set to base 16, since that's the format the disassembled - // byte string is in. This eliminates the need to prefix each byte with - // a '$' character - BaseFormat oldbase = instance().debugger().parser().base(); - instance().debugger().parser().setBase(kBASE_16); + if(list[data].address != 0) + { + ostringstream command; - command << "rom #" << myAddrList[data] << " " << bytes; - instance().debugger().run(command.str()); + // Temporarily set to base 16, since that's the format the disassembled + // byte string is in. This eliminates the need to prefix each byte with + // a '$' character + BaseFormat oldbase = instance().debugger().parser().base(); + instance().debugger().parser().setBase(kBASE_16); - // Restore previous base - instance().debugger().parser().setBase(oldbase); + command << "rom #" << list[data].address << " " << bytes; + instance().debugger().run(command.str()); + + // Restore previous base + instance().debugger().parser().setBase(oldbase); + } } // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - diff --git a/src/debugger/gui/RomWidget.hxx b/src/debugger/gui/RomWidget.hxx index c0880dd39..0ac17fc98 100644 --- a/src/debugger/gui/RomWidget.hxx +++ b/src/debugger/gui/RomWidget.hxx @@ -29,14 +29,10 @@ class InputTextDialog; class RomListWidget; class StringList; -#include - #include "Array.hxx" #include "Widget.hxx" #include "Command.hxx" - -typedef map AddrToLine; - +#include "CartDebug.hxx" class RomWidget : public Widget, public CommandSender { @@ -60,14 +56,7 @@ class RomWidget : public Widget, public CommandSender kRomNameEntered = 'RWrn' }; - RomListWidget* myRomList; - - /** List of addresses indexed by line number */ - IntArray myAddrList; - - /** List of line numbers indexed by address */ - AddrToLine myLineList; - + RomListWidget* myRomList; DataGridWidget* myBank; EditTextWidget* myBankCount; InputTextDialog* mySaveRom;