mirror of
https://github.com/SourMesen/Mesen.git
synced 2025-04-02 10:52:48 -04:00
Debugger - Basic FCEUX CDL file support
This commit is contained in:
parent
c1b4859740
commit
273c000c44
20 changed files with 708 additions and 130 deletions
|
@ -463,27 +463,31 @@ class BaseMapper : public IMemoryHandler, public Snapshotable, public INotificat
|
|||
memcpy(*buffer, _chrRam, _chrSize);
|
||||
}
|
||||
|
||||
uint32_t GetChrSize()
|
||||
uint32_t GetChrSize(bool includeChrRam = true)
|
||||
{
|
||||
return _chrSize;
|
||||
if(includeChrRam || !_hasChrRam) {
|
||||
return _chrSize;
|
||||
} else {
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
|
||||
uint32_t ToAbsoluteAddress(uint16_t addr)
|
||||
int32_t ToAbsoluteAddress(uint16_t addr)
|
||||
{
|
||||
uint8_t *prgAddr = _prgPages[addr >> 8] + (addr & 0xFF);
|
||||
if(prgAddr >= _prgRom && prgAddr < _prgRom + _prgSize) {
|
||||
return (uint32_t)(prgAddr - _prgRom);
|
||||
}
|
||||
return 0;
|
||||
return -1;
|
||||
}
|
||||
|
||||
uint32_t ToAbsoluteChrAddress(uint16_t addr)
|
||||
int32_t ToAbsoluteChrAddress(uint16_t addr)
|
||||
{
|
||||
uint8_t *chrAddr = _chrPages[addr >> 8] + (addr & 0xFF);
|
||||
if(chrAddr >= _chrRam && chrAddr < _chrRam + _chrSize) {
|
||||
return (uint32_t)(chrAddr - _chrRam);
|
||||
}
|
||||
return 0;
|
||||
return -1;
|
||||
}
|
||||
|
||||
int32_t FromAbsoluteAddress(uint32_t addr)
|
||||
|
|
20
Core/CPU.h
20
Core/CPU.h
|
@ -83,24 +83,24 @@ private:
|
|||
uint8_t GetOPCode()
|
||||
{
|
||||
_state.DebugPC = _state.PC;
|
||||
uint8_t opCode = MemoryRead(_state.PC, true);
|
||||
uint8_t opCode = MemoryRead(_state.PC, MemoryOperationType::ExecOpCode);
|
||||
_state.PC++;
|
||||
return opCode;
|
||||
}
|
||||
|
||||
void DummyRead()
|
||||
{
|
||||
MemoryRead(_state.PC);
|
||||
MemoryRead(_state.PC, MemoryOperationType::ExecOperand);
|
||||
}
|
||||
|
||||
uint8_t ReadByte()
|
||||
{
|
||||
return MemoryRead(_state.PC++);
|
||||
return MemoryRead(_state.PC++, MemoryOperationType::ExecOperand);
|
||||
}
|
||||
|
||||
uint16_t ReadWord()
|
||||
{
|
||||
uint16_t value = MemoryReadWord(PC());
|
||||
uint16_t value = MemoryReadWord(_state.PC, MemoryOperationType::ExecOperand);
|
||||
_state.PC += 2;
|
||||
return value;
|
||||
}
|
||||
|
@ -145,25 +145,25 @@ private:
|
|||
IncCycleCount();
|
||||
}
|
||||
|
||||
uint8_t MemoryRead(uint16_t addr, bool forExecute = false) {
|
||||
uint8_t MemoryRead(uint16_t addr, MemoryOperationType operationType = MemoryOperationType::Read) {
|
||||
while(_dmcDmaRunning) {
|
||||
//Stall CPU until we can process a DMC read
|
||||
if((addr != 0x4016 && addr != 0x4017) || _dmcCounter == 1) {
|
||||
//While the CPU is stalled, reads are performed on the current address
|
||||
//This behavior causes the $4016/7 data corruption when a DMC is running.
|
||||
//When reading $4016/7, only the last read counts (because this only occurs to low-to-high transitions, i.e once in this case)
|
||||
_memoryManager->Read(addr, forExecute);
|
||||
_memoryManager->Read(addr);
|
||||
}
|
||||
IncCycleCount();
|
||||
}
|
||||
uint8_t value = _memoryManager->Read(addr, forExecute);
|
||||
uint8_t value = _memoryManager->Read(addr, operationType);
|
||||
IncCycleCount();
|
||||
return value;
|
||||
}
|
||||
|
||||
uint16_t MemoryReadWord(uint16_t addr) {
|
||||
uint8_t lo = MemoryRead(addr);
|
||||
uint8_t hi = MemoryRead(addr + 1);
|
||||
uint16_t MemoryReadWord(uint16_t addr, MemoryOperationType operationType = MemoryOperationType::Read) {
|
||||
uint8_t lo = MemoryRead(addr, operationType);
|
||||
uint8_t hi = MemoryRead(addr + 1, operationType);
|
||||
return lo | hi << 8;
|
||||
}
|
||||
|
||||
|
|
154
Core/CodeDataLogger.cpp
Normal file
154
Core/CodeDataLogger.cpp
Normal file
|
@ -0,0 +1,154 @@
|
|||
#pragma once
|
||||
|
||||
#include "stdafx.h"
|
||||
#include "CodeDataLogger.h"
|
||||
|
||||
CodeDataLogger::CodeDataLogger(uint32_t prgSize, uint32_t chrSize)
|
||||
{
|
||||
_prgSize = prgSize;
|
||||
_chrSize = chrSize;
|
||||
_cdlData = new uint8_t[prgSize+chrSize];
|
||||
Reset();
|
||||
}
|
||||
|
||||
CodeDataLogger::~CodeDataLogger()
|
||||
{
|
||||
delete[] _cdlData;
|
||||
}
|
||||
|
||||
void CodeDataLogger::Reset()
|
||||
{
|
||||
_codeSize = 0;
|
||||
_dataSize = 0;
|
||||
_usedChrSize = 0;
|
||||
_drawnChrSize = 0;
|
||||
_readChrSize = 0;
|
||||
memset(_cdlData, 0, _prgSize + _chrSize);
|
||||
}
|
||||
|
||||
bool CodeDataLogger::LoadCdlFile(string cdlFilepath)
|
||||
{
|
||||
ifstream cdlFile(cdlFilepath, ios::in | ios::binary);
|
||||
if(cdlFile) {
|
||||
cdlFile.seekg(0, std::ios::end);
|
||||
size_t fileSize = (size_t)cdlFile.tellg();
|
||||
cdlFile.seekg(0, std::ios::beg);
|
||||
|
||||
if(fileSize == _prgSize + _chrSize) {
|
||||
Reset();
|
||||
|
||||
cdlFile.read((char*)_cdlData, _prgSize + _chrSize);
|
||||
cdlFile.close();
|
||||
|
||||
for(int i = 0, len = _prgSize; i < len; i++) {
|
||||
if(IsCode(i)) {
|
||||
_codeSize++;
|
||||
} else if(IsData(i)) {
|
||||
_dataSize++;
|
||||
}
|
||||
}
|
||||
|
||||
for(int i = 0, len = _chrSize; i < len; i++) {
|
||||
if(IsDrawn(i) || IsRead(i)) {
|
||||
_usedChrSize++;
|
||||
if(IsDrawn(i)) {
|
||||
_drawnChrSize++;
|
||||
} else if(IsRead(i)) {
|
||||
_readChrSize++;
|
||||
}
|
||||
}
|
||||
}
|
||||
return true;
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
bool CodeDataLogger::SaveCdlFile(string cdlFilepath)
|
||||
{
|
||||
ofstream cdlFile(cdlFilepath, ios::out | ios::binary);
|
||||
if(cdlFile) {
|
||||
cdlFile.write((char*)_cdlData, _prgSize+_chrSize);
|
||||
cdlFile.close();
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
void CodeDataLogger::SetFlag(int32_t absoluteAddr, CdlPrgFlags flag)
|
||||
{
|
||||
if(absoluteAddr >= 0 && absoluteAddr < _prgSize) {
|
||||
if((_cdlData[absoluteAddr] & (uint8_t)flag) != (uint8_t)flag) {
|
||||
if(flag == CdlPrgFlags::Code) {
|
||||
if(IsData(absoluteAddr)) {
|
||||
//Remove the data flag from bytes that we are flagging as code
|
||||
_cdlData[absoluteAddr] &= ~(uint8_t)CdlPrgFlags::Data;
|
||||
_dataSize--;
|
||||
}
|
||||
_cdlData[absoluteAddr] |= (uint8_t)flag;
|
||||
_codeSize++;
|
||||
} else if(flag == CdlPrgFlags::Data) {
|
||||
if(!IsCode(absoluteAddr)) {
|
||||
_cdlData[absoluteAddr] |= (uint8_t)flag;
|
||||
_dataSize++;
|
||||
}
|
||||
} else {
|
||||
_cdlData[absoluteAddr] |= (uint8_t)flag;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void CodeDataLogger::SetFlag(int32_t chrAbsoluteAddr, CdlChrFlags flag)
|
||||
{
|
||||
if(chrAbsoluteAddr >= 0 && chrAbsoluteAddr < _chrSize) {
|
||||
if((_cdlData[_prgSize + chrAbsoluteAddr] & (uint8_t)flag) != (uint8_t)flag) {
|
||||
_usedChrSize++;
|
||||
if(flag == CdlChrFlags::Read) {
|
||||
_readChrSize++;
|
||||
} else if(flag == CdlChrFlags::Drawn) {
|
||||
_drawnChrSize++;
|
||||
}
|
||||
_cdlData[_prgSize + chrAbsoluteAddr] |= (uint8_t)flag;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
CdlRatios CodeDataLogger::GetRatios()
|
||||
{
|
||||
CdlRatios ratios;
|
||||
ratios.CodeRatio = (float)_codeSize / (float)_prgSize;
|
||||
ratios.DataRatio = (float)_dataSize / (float)_prgSize;
|
||||
ratios.PrgRatio = (float)(_codeSize + _dataSize) / (float)_prgSize;
|
||||
if(_chrSize > 0) {
|
||||
ratios.ChrRatio = (float)(_usedChrSize) / (float)_chrSize;
|
||||
ratios.ChrReadRatio = (float)(_readChrSize) / (float)_chrSize;
|
||||
ratios.ChrDrawnRatio = (float)(_drawnChrSize) / (float)_chrSize;
|
||||
} else {
|
||||
ratios.ChrRatio = -1;
|
||||
ratios.ChrReadRatio = -1;
|
||||
ratios.ChrDrawnRatio = -1;
|
||||
}
|
||||
|
||||
return ratios;
|
||||
}
|
||||
|
||||
bool CodeDataLogger::IsCode(uint32_t absoluteAddr)
|
||||
{
|
||||
return (_cdlData[absoluteAddr] & (uint8_t)CdlPrgFlags::Code) == (uint8_t)CdlPrgFlags::Code;
|
||||
}
|
||||
|
||||
bool CodeDataLogger::IsData(uint32_t absoluteAddr)
|
||||
{
|
||||
return (_cdlData[absoluteAddr] & (uint8_t)CdlPrgFlags::Data) == (uint8_t)CdlPrgFlags::Data;
|
||||
}
|
||||
|
||||
bool CodeDataLogger::IsRead(uint32_t absoluteAddr)
|
||||
{
|
||||
return (_cdlData[absoluteAddr + _prgSize] & (uint8_t)CdlChrFlags::Read) == (uint8_t)CdlChrFlags::Read;
|
||||
}
|
||||
|
||||
bool CodeDataLogger::IsDrawn(uint32_t absoluteAddr)
|
||||
{
|
||||
return (_cdlData[absoluteAddr + _prgSize] & (uint8_t)CdlChrFlags::Drawn) == (uint8_t)CdlChrFlags::Drawn;
|
||||
}
|
65
Core/CodeDataLogger.h
Normal file
65
Core/CodeDataLogger.h
Normal file
|
@ -0,0 +1,65 @@
|
|||
#pragma once
|
||||
|
||||
#include "stdafx.h"
|
||||
#include "../Utilities/SimpleLock.h"
|
||||
|
||||
enum class CdlPrgFlags
|
||||
{
|
||||
Code = 0x01,
|
||||
Data = 0x02,
|
||||
IndirectCode = 0x10,
|
||||
IndirectData = 0x20,
|
||||
PcmData = 0x40,
|
||||
};
|
||||
|
||||
enum class CdlChrFlags
|
||||
{
|
||||
Drawn = 0x01,
|
||||
Read = 0x02,
|
||||
};
|
||||
|
||||
struct CdlRatios
|
||||
{
|
||||
float CodeRatio;
|
||||
float DataRatio;
|
||||
float PrgRatio;
|
||||
|
||||
float ChrRatio;
|
||||
float ChrReadRatio;
|
||||
float ChrDrawnRatio;
|
||||
};
|
||||
|
||||
class CodeDataLogger
|
||||
{
|
||||
private:
|
||||
uint8_t *_cdlData = nullptr;
|
||||
uint32_t _prgSize = 0;
|
||||
uint32_t _chrSize = 0;
|
||||
|
||||
uint32_t _codeSize = 0;
|
||||
uint32_t _dataSize = 0;
|
||||
uint32_t _usedChrSize = 0;
|
||||
uint32_t _readChrSize = 0;
|
||||
uint32_t _drawnChrSize = 0;
|
||||
|
||||
SimpleLock _lock;
|
||||
|
||||
public:
|
||||
CodeDataLogger(uint32_t prgSize, uint32_t chrSize);
|
||||
~CodeDataLogger();
|
||||
|
||||
void Reset();
|
||||
|
||||
bool LoadCdlFile(string cdlFilepath);
|
||||
bool SaveCdlFile(string cdlFilepath);
|
||||
|
||||
void SetFlag(int32_t absoluteAddr, CdlPrgFlags flag);
|
||||
void SetFlag(int32_t chrAbsoluteAddr, CdlChrFlags flag);
|
||||
|
||||
CdlRatios GetRatios();
|
||||
|
||||
bool IsCode(uint32_t absoluteAddr);
|
||||
bool IsData(uint32_t absoluteAddr);
|
||||
bool IsRead(uint32_t absoluteAddr);
|
||||
bool IsDrawn(uint32_t absoluteAddr);
|
||||
};
|
|
@ -267,6 +267,7 @@
|
|||
<ItemGroup>
|
||||
<ClInclude Include="APU.h" />
|
||||
<ClInclude Include="BF909x.h" />
|
||||
<ClInclude Include="CodeDataLogger.h" />
|
||||
<ClInclude Include="DeltaModulationChannel.h" />
|
||||
<ClInclude Include="ApuEnvelope.h" />
|
||||
<ClInclude Include="ApuFrameCounter.h" />
|
||||
|
@ -338,6 +339,7 @@
|
|||
<ClCompile Include="ApuLengthCounter.cpp" />
|
||||
<ClCompile Include="Breakpoint.cpp" />
|
||||
<ClCompile Include="CheatManager.cpp" />
|
||||
<ClCompile Include="CodeDataLogger.cpp" />
|
||||
<ClCompile Include="Console.cpp" />
|
||||
<ClCompile Include="ControlManager.cpp" />
|
||||
<ClCompile Include="Debugger.cpp" />
|
||||
|
|
|
@ -239,6 +239,9 @@
|
|||
<ClInclude Include="HdPpu.h">
|
||||
<Filter>Header Files\HD</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="CodeDataLogger.h">
|
||||
<Filter>Debugger</Filter>
|
||||
</ClInclude>
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ClCompile Include="CPU.cpp">
|
||||
|
@ -322,5 +325,8 @@
|
|||
<ClCompile Include="DeltaModulationChannel.cpp">
|
||||
<Filter>Source Files\APU</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="CodeDataLogger.cpp">
|
||||
<Filter>Debugger</Filter>
|
||||
</ClCompile>
|
||||
</ItemGroup>
|
||||
</Project>
|
|
@ -9,11 +9,13 @@
|
|||
#include "Disassembler.h"
|
||||
#include "VideoDecoder.h"
|
||||
#include "APU.h"
|
||||
#include "CodeDataLogger.h"
|
||||
|
||||
Debugger* Debugger::Instance = nullptr;
|
||||
|
||||
Debugger::Debugger(shared_ptr<Console> console, shared_ptr<CPU> cpu, shared_ptr<PPU> ppu, shared_ptr<MemoryManager> memoryManager, shared_ptr<BaseMapper> mapper)
|
||||
{
|
||||
_romFilepath = Console::GetROMPath();
|
||||
_console = console;
|
||||
_cpu = cpu;
|
||||
_ppu = ppu;
|
||||
|
@ -23,14 +25,21 @@ Debugger::Debugger(shared_ptr<Console> console, shared_ptr<CPU> cpu, shared_ptr<
|
|||
uint8_t *prgBuffer;
|
||||
mapper->GetPrgCopy(&prgBuffer);
|
||||
_disassembler.reset(new Disassembler(memoryManager->GetInternalRAM(), prgBuffer, mapper->GetPrgSize()));
|
||||
_codeDataLogger.reset(new CodeDataLogger(mapper->GetPrgSize(), mapper->GetChrSize(false)));
|
||||
|
||||
_stepCount = -1;
|
||||
|
||||
LoadCdlFile(FolderUtilities::CombinePath(FolderUtilities::GetDebuggerFolder(), FolderUtilities::GetFilename(_romFilepath, false) + ".cdl"));
|
||||
|
||||
Debugger::Instance = this;
|
||||
}
|
||||
|
||||
Debugger::~Debugger()
|
||||
{
|
||||
SaveCdlFile(FolderUtilities::CombinePath(FolderUtilities::GetDebuggerFolder(), FolderUtilities::GetFilename(_romFilepath, false) + ".cdl"));
|
||||
|
||||
Run();
|
||||
|
||||
Console::Pause();
|
||||
Debugger::Instance = nullptr;
|
||||
Run();
|
||||
|
@ -39,6 +48,34 @@ Debugger::~Debugger()
|
|||
Console::Resume();
|
||||
}
|
||||
|
||||
bool Debugger::LoadCdlFile(string cdlFilepath)
|
||||
{
|
||||
if(_codeDataLogger->LoadCdlFile(cdlFilepath)) {
|
||||
for(int i = 0, len = _mapper->GetPrgSize(); i < len; i++) {
|
||||
if(_codeDataLogger->IsCode(i)) {
|
||||
i = _disassembler->BuildCache(i, 0xFFFF) - 1;
|
||||
}
|
||||
}
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
bool Debugger::SaveCdlFile(string cdlFilepath)
|
||||
{
|
||||
return _codeDataLogger->SaveCdlFile(cdlFilepath);
|
||||
}
|
||||
|
||||
void Debugger::ResetCdlLog()
|
||||
{
|
||||
_codeDataLogger->Reset();
|
||||
}
|
||||
|
||||
CdlRatios Debugger::GetCdlRatios()
|
||||
{
|
||||
return _codeDataLogger->GetRatios();
|
||||
}
|
||||
|
||||
void Debugger::AddBreakpoint(BreakpointType type, uint32_t address, bool isAbsoluteAddr, bool enabled)
|
||||
{
|
||||
_bpLock.Acquire();
|
||||
|
@ -104,48 +141,78 @@ shared_ptr<Breakpoint> Debugger::GetMatchingBreakpoint(BreakpointType type, uint
|
|||
return shared_ptr<Breakpoint>();
|
||||
}
|
||||
|
||||
void Debugger::PrivateCheckBreakpoint(BreakpointType type, uint32_t addr)
|
||||
void Debugger::UpdateCallstack(uint32_t addr)
|
||||
{
|
||||
if(_lastInstruction == 0x60 && !_callstackRelative.empty()) {
|
||||
//RTS
|
||||
_callstackRelative.pop_back();
|
||||
_callstackRelative.pop_back();
|
||||
_callstackAbsolute.pop_back();
|
||||
_callstackAbsolute.pop_back();
|
||||
} else if(_lastInstruction == 0x20 && _callstackRelative.size() < 1022) {
|
||||
//JSR
|
||||
uint16_t targetAddr = _memoryManager->DebugRead(addr + 1) | (_memoryManager->DebugRead(addr + 2) << 8);
|
||||
_callstackRelative.push_back(addr);
|
||||
_callstackRelative.push_back(targetAddr);
|
||||
|
||||
_callstackAbsolute.push_back(_mapper->ToAbsoluteAddress(addr));
|
||||
_callstackAbsolute.push_back(_mapper->ToAbsoluteAddress(targetAddr));
|
||||
}
|
||||
}
|
||||
|
||||
void Debugger::ProcessStepConditions(uint32_t addr)
|
||||
{
|
||||
if(_stepOut && _lastInstruction == 0x60) {
|
||||
//RTS found, set StepCount to 2 to break on the following instruction
|
||||
Step(2);
|
||||
} else if(_stepOverAddr != -1 && addr == _stepOverAddr) {
|
||||
Step(1);
|
||||
} else if(_stepCycleCount != -1 && abs(_cpu->GetCycleCount() - _stepCycleCount) < 100 && _cpu->GetCycleCount() >= _stepCycleCount) {
|
||||
Step(1);
|
||||
}
|
||||
}
|
||||
|
||||
void Debugger::BreakOnBreakpoint(MemoryOperationType type, uint32_t addr)
|
||||
{
|
||||
BreakpointType breakpointType;
|
||||
switch(type) {
|
||||
case MemoryOperationType::Read: breakpointType = BreakpointType::Read; break;
|
||||
case MemoryOperationType::Write: breakpointType = BreakpointType::Write; break;
|
||||
case MemoryOperationType::ExecOpCode:
|
||||
case MemoryOperationType::ExecOperand: breakpointType = BreakpointType::Execute; break;
|
||||
}
|
||||
|
||||
if(GetMatchingBreakpoint(breakpointType, addr)) {
|
||||
//Found a matching breakpoint, stop execution
|
||||
Step(1);
|
||||
SleepUntilResume();
|
||||
}
|
||||
}
|
||||
|
||||
void Debugger::PrivateProcessRamOperation(MemoryOperationType type, uint32_t addr)
|
||||
{
|
||||
_breakLock.Acquire();
|
||||
|
||||
//Check if a breakpoint has been hit and freeze execution if one has
|
||||
bool breakDone = false;
|
||||
if(type == BreakpointType::Execute) {
|
||||
int32_t absoluteAddr = _mapper->ToAbsoluteAddress(addr);
|
||||
if(type == MemoryOperationType::ExecOpCode) {
|
||||
_codeDataLogger->SetFlag(absoluteAddr, CdlPrgFlags::Code);
|
||||
_disassembler->BuildCache(absoluteAddr, addr);
|
||||
_lastInstruction = _memoryManager->DebugRead(addr);
|
||||
|
||||
//Update callstack
|
||||
if(_lastInstruction == 0x60 && !_callstackRelative.empty()) {
|
||||
//RTS
|
||||
_callstackRelative.pop_back();
|
||||
_callstackRelative.pop_back();
|
||||
_callstackAbsolute.pop_back();
|
||||
_callstackAbsolute.pop_back();
|
||||
} else if(_lastInstruction == 0x20 && _callstackRelative.size() < 1022) {
|
||||
//JSR
|
||||
uint16_t targetAddr = _memoryManager->DebugRead(addr + 1) | (_memoryManager->DebugRead(addr + 2) << 8);
|
||||
_callstackRelative.push_back(addr);
|
||||
_callstackRelative.push_back(targetAddr);
|
||||
UpdateCallstack(addr);
|
||||
ProcessStepConditions(addr);
|
||||
|
||||
_callstackAbsolute.push_back(_mapper->ToAbsoluteAddress(addr));
|
||||
_callstackAbsolute.push_back(_mapper->ToAbsoluteAddress(targetAddr));
|
||||
}
|
||||
|
||||
if(_stepOut && _lastInstruction == 0x60) {
|
||||
//RTS found, set StepCount to 2 to break on the following instruction
|
||||
Step(2);
|
||||
} else if(_stepOverAddr != -1 && addr == _stepOverAddr) {
|
||||
Step(1);
|
||||
} else if(_stepCycleCount != -1 && abs(_cpu->GetCycleCount() - _stepCycleCount) < 100 && _cpu->GetCycleCount() >= _stepCycleCount) {
|
||||
Step(1);
|
||||
}
|
||||
_disassembler->BuildCache(_mapper->ToAbsoluteAddress(addr), addr);
|
||||
breakDone = SleepUntilResume();
|
||||
} else if(type == MemoryOperationType::ExecOperand) {
|
||||
_codeDataLogger->SetFlag(absoluteAddr, CdlPrgFlags::Code);
|
||||
} else {
|
||||
_codeDataLogger->SetFlag(absoluteAddr, CdlPrgFlags::Data);
|
||||
}
|
||||
|
||||
if(!breakDone && GetMatchingBreakpoint(type, addr)) {
|
||||
//Found a matching breakpoint, stop execution
|
||||
Step(1);
|
||||
SleepUntilResume();
|
||||
if(!breakDone) {
|
||||
BreakOnBreakpoint(type, addr);
|
||||
}
|
||||
|
||||
_breakLock.Release();
|
||||
|
@ -173,6 +240,12 @@ bool Debugger::SleepUntilResume()
|
|||
return false;
|
||||
}
|
||||
|
||||
void Debugger::PrivateProcessVramOperation(MemoryOperationType type, uint32_t addr)
|
||||
{
|
||||
int32_t absoluteAddr = _mapper->ToAbsoluteChrAddress(addr);
|
||||
_codeDataLogger->SetFlag(absoluteAddr, type == MemoryOperationType::Read ? CdlChrFlags::Read : CdlChrFlags::Drawn);
|
||||
}
|
||||
|
||||
void Debugger::GetState(DebugState *state)
|
||||
{
|
||||
state->CPU = _cpu->GetState();
|
||||
|
@ -272,10 +345,17 @@ uint32_t Debugger::GetRelativeAddress(uint32_t addr)
|
|||
return _mapper->FromAbsoluteAddress(addr);
|
||||
}
|
||||
|
||||
void Debugger::CheckBreakpoint(BreakpointType type, uint32_t addr)
|
||||
void Debugger::ProcessRamOperation(MemoryOperationType type, uint32_t addr)
|
||||
{
|
||||
if(Debugger::Instance) {
|
||||
Debugger::Instance->PrivateCheckBreakpoint(type, addr);
|
||||
Debugger::Instance->PrivateProcessRamOperation(type, addr);
|
||||
}
|
||||
}
|
||||
|
||||
void Debugger::ProcessVramOperation(MemoryOperationType type, uint32_t addr)
|
||||
{
|
||||
if(Debugger::Instance) {
|
||||
Debugger::Instance->PrivateProcessVramOperation(type, addr);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -10,6 +10,7 @@ using std::deque;
|
|||
#include "PPU.h"
|
||||
#include "Breakpoint.h"
|
||||
#include "../Utilities/SimpleLock.h"
|
||||
#include "CodeDataLogger.h"
|
||||
|
||||
class MemoryManager;
|
||||
class Console;
|
||||
|
@ -38,6 +39,7 @@ private:
|
|||
static Debugger* Instance;
|
||||
|
||||
unique_ptr<Disassembler> _disassembler;
|
||||
unique_ptr<CodeDataLogger> _codeDataLogger;
|
||||
shared_ptr<Console> _console;
|
||||
shared_ptr<CPU> _cpu;
|
||||
shared_ptr<PPU> _ppu;
|
||||
|
@ -52,6 +54,7 @@ private:
|
|||
SimpleLock _bpLock;
|
||||
SimpleLock _breakLock;
|
||||
|
||||
string _romFilepath;
|
||||
string _outputCache;
|
||||
atomic<int32_t> _stepCount;
|
||||
atomic<int32_t> _stepCycleCount;
|
||||
|
@ -60,8 +63,12 @@ private:
|
|||
atomic<int32_t> _stepOverAddr;
|
||||
|
||||
private:
|
||||
void PrivateCheckBreakpoint(BreakpointType type, uint32_t addr);
|
||||
void PrivateProcessRamOperation(MemoryOperationType type, uint32_t addr);
|
||||
void PrivateProcessVramOperation(MemoryOperationType type, uint32_t addr);
|
||||
shared_ptr<Breakpoint> GetMatchingBreakpoint(BreakpointType type, uint32_t addr);
|
||||
void UpdateCallstack(uint32_t addr);
|
||||
void ProcessStepConditions(uint32_t addr);
|
||||
void BreakOnBreakpoint(MemoryOperationType type, uint32_t addr);
|
||||
bool SleepUntilResume();
|
||||
|
||||
public:
|
||||
|
@ -89,6 +96,11 @@ public:
|
|||
void StepOut();
|
||||
void Run();
|
||||
|
||||
bool LoadCdlFile(string cdlFilepath);
|
||||
bool SaveCdlFile(string cdlFilepath);
|
||||
CdlRatios GetCdlRatios();
|
||||
void ResetCdlLog();
|
||||
|
||||
bool IsCodeChanged();
|
||||
string GenerateOutput();
|
||||
string* GetCode();
|
||||
|
@ -96,5 +108,6 @@ public:
|
|||
uint8_t GetMemoryValue(uint32_t addr);
|
||||
uint32_t GetRelativeAddress(uint32_t addr);
|
||||
|
||||
static void CheckBreakpoint(BreakpointType type, uint32_t addr);
|
||||
static void ProcessRamOperation(MemoryOperationType type, uint32_t addr);
|
||||
static void ProcessVramOperation(MemoryOperationType type, uint32_t addr);
|
||||
};
|
|
@ -93,29 +93,30 @@ Disassembler::~Disassembler()
|
|||
}
|
||||
}
|
||||
|
||||
void Disassembler::BuildCache(uint32_t absoluteAddr, uint16_t memoryAddr)
|
||||
uint32_t Disassembler::BuildCache(uint32_t absoluteAddr, uint16_t memoryAddr)
|
||||
{
|
||||
if(memoryAddr < 0x2000) {
|
||||
memoryAddr = memoryAddr & 0x7FF;
|
||||
if(!_disassembleMemoryCache[memoryAddr]) {
|
||||
shared_ptr<DisassemblyInfo> disInfo(new DisassemblyInfo(&_internalRAM[memoryAddr]));
|
||||
_disassembleMemoryCache[memoryAddr] = disInfo;
|
||||
memoryAddr += disInfo->GetSize();
|
||||
}
|
||||
return memoryAddr;
|
||||
} else {
|
||||
while(!_disassembleCache[absoluteAddr]) {
|
||||
shared_ptr<DisassemblyInfo> disInfo(new DisassemblyInfo(&_prgROM[absoluteAddr]));
|
||||
_disassembleCache[absoluteAddr] = disInfo;
|
||||
|
||||
uint8_t opCode = _prgROM[absoluteAddr];
|
||||
|
||||
if(opCode == 0x10 || opCode == 0x20 || opCode == 0x30 || opCode == 0x40 || opCode == 0x50 || opCode == 0x60 || opCode == 0x70 || opCode == 0x90 || opCode == 0xB0 || opCode == 0xD0 || opCode == 0xF0 || opCode == 0x4C || opCode == 0x6C) {
|
||||
//Hit a jump/return instruction, can't assume that what follows is actual code, stop disassembling
|
||||
break;
|
||||
}
|
||||
|
||||
absoluteAddr += disInfo->GetSize();
|
||||
memoryAddr += disInfo->GetSize();
|
||||
}
|
||||
absoluteAddr += _disassembleCache[absoluteAddr]->GetSize();
|
||||
return absoluteAddr;
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -16,7 +16,7 @@ public:
|
|||
Disassembler(uint8_t* internalRAM, uint8_t* prgROM, uint32_t prgSize);
|
||||
~Disassembler();
|
||||
|
||||
void BuildCache(uint32_t absoluteAddr, uint16_t memoryAddr);
|
||||
uint32_t BuildCache(uint32_t absoluteAddr, uint16_t memoryAddr);
|
||||
string GetRAMCode();
|
||||
string GetCode(uint32_t startAddr, uint32_t endAddr, uint16_t &memoryAddr);
|
||||
};
|
||||
|
|
|
@ -95,9 +95,9 @@ uint8_t MemoryManager::DebugRead(uint16_t addr)
|
|||
return value;
|
||||
}
|
||||
|
||||
uint8_t MemoryManager::Read(uint16_t addr, bool forExecution)
|
||||
uint8_t MemoryManager::Read(uint16_t addr, MemoryOperationType operationType)
|
||||
{
|
||||
Debugger::CheckBreakpoint(forExecution ? BreakpointType::Execute : BreakpointType::Read, addr);
|
||||
Debugger::ProcessRamOperation(operationType, addr);
|
||||
|
||||
uint8_t value;
|
||||
if(addr <= 0x1FFF) {
|
||||
|
@ -112,7 +112,7 @@ uint8_t MemoryManager::Read(uint16_t addr, bool forExecution)
|
|||
|
||||
void MemoryManager::Write(uint16_t addr, uint8_t value)
|
||||
{
|
||||
Debugger::CheckBreakpoint(BreakpointType::Write, addr);
|
||||
Debugger::ProcessRamOperation(MemoryOperationType::Write, addr);
|
||||
|
||||
if(addr <= 0x1FFF) {
|
||||
_internalRAM[addr & 0x07FF] = value;
|
||||
|
@ -141,14 +141,16 @@ uint8_t MemoryManager::DebugReadVRAM(uint16_t addr)
|
|||
return _mapper->ReadVRAM(addr);
|
||||
}
|
||||
|
||||
uint8_t MemoryManager::ReadVRAM(uint16_t addr)
|
||||
uint8_t MemoryManager::ReadVRAM(uint16_t addr, MemoryOperationType operationType)
|
||||
{
|
||||
Debugger::ProcessVramOperation(operationType, addr);
|
||||
ProcessVramAccess(addr);
|
||||
return _mapper->ReadVRAM(addr);
|
||||
}
|
||||
|
||||
void MemoryManager::WriteVRAM(uint16_t addr, uint8_t value)
|
||||
{
|
||||
Debugger::ProcessVramOperation(MemoryOperationType::Write, addr);
|
||||
ProcessVramAccess(addr);
|
||||
_mapper->WriteVRAM(addr, value);
|
||||
}
|
||||
|
|
|
@ -6,6 +6,15 @@
|
|||
|
||||
class BaseMapper;
|
||||
|
||||
enum class MemoryOperationType
|
||||
{
|
||||
Read = 0,
|
||||
Write = 1,
|
||||
ExecOpCode = 2,
|
||||
ExecOperand = 3,
|
||||
PpuRenderingRead = 4,
|
||||
};
|
||||
|
||||
class MemoryManager: public Snapshotable
|
||||
{
|
||||
private:
|
||||
|
@ -42,11 +51,11 @@ class MemoryManager: public Snapshotable
|
|||
|
||||
uint8_t* GetInternalRAM();
|
||||
|
||||
uint8_t Read(uint16_t addr, bool forExecution = false);
|
||||
uint8_t Read(uint16_t addr, MemoryOperationType operationType = MemoryOperationType::Read);
|
||||
void Write(uint16_t addr, uint8_t value);
|
||||
|
||||
void ProcessVramAccess(uint16_t &addr);
|
||||
uint8_t ReadVRAM(uint16_t addr);
|
||||
uint8_t ReadVRAM(uint16_t addr, MemoryOperationType operationType = MemoryOperationType::PpuRenderingRead);
|
||||
void WriteVRAM(uint16_t addr, uint8_t value);
|
||||
|
||||
uint32_t ToAbsoluteChrAddress(uint16_t vramAddr);
|
||||
|
|
|
@ -81,7 +81,7 @@ uint8_t PPU::ReadRAM(uint16_t addr)
|
|||
return _spriteRAM[_state.SpriteRamAddr];
|
||||
case PPURegisters::VideoMemoryData:
|
||||
returnValue = _memoryReadBuffer;
|
||||
_memoryReadBuffer = _memoryManager->ReadVRAM(_state.VideoRamAddr);
|
||||
_memoryReadBuffer = _memoryManager->ReadVRAM(_state.VideoRamAddr, MemoryOperationType::Read);
|
||||
|
||||
if(_state.VideoRamAddr >= 0x3F00) {
|
||||
returnValue = ReadPaletteRAM(_state.VideoRamAddr);
|
||||
|
|
290
GUI.NET/Debugger/frmDebugger.Designer.cs
generated
290
GUI.NET/Debugger/frmDebugger.Designer.cs
generated
|
@ -34,20 +34,16 @@
|
|||
this.components = new System.ComponentModel.Container();
|
||||
this.splitContainer = new System.Windows.Forms.SplitContainer();
|
||||
this.tlpTop = new System.Windows.Forms.TableLayoutPanel();
|
||||
this.ctrlDebuggerCode = new Mesen.GUI.Debugger.ctrlDebuggerCode();
|
||||
this.contextMenuCode = new System.Windows.Forms.ContextMenuStrip(this.components);
|
||||
this.mnuShowNextStatement = new System.Windows.Forms.ToolStripMenuItem();
|
||||
this.mnuSetNextStatement = new System.Windows.Forms.ToolStripMenuItem();
|
||||
this.ctrlConsoleStatus = new Mesen.GUI.Debugger.ctrlConsoleStatus();
|
||||
this.ctrlDebuggerCodeSplit = new Mesen.GUI.Debugger.ctrlDebuggerCode();
|
||||
this.tableLayoutPanel10 = new System.Windows.Forms.TableLayoutPanel();
|
||||
this.grpWatch = new System.Windows.Forms.GroupBox();
|
||||
this.ctrlWatch = new Mesen.GUI.Debugger.ctrlWatch();
|
||||
this.grpBreakpoints = new System.Windows.Forms.GroupBox();
|
||||
this.ctrlBreakpoints = new Mesen.GUI.Debugger.Controls.ctrlBreakpoints();
|
||||
this.grpCallstack = new System.Windows.Forms.GroupBox();
|
||||
this.menuStrip = new System.Windows.Forms.MenuStrip();
|
||||
this.fileToolStripMenuItem = new System.Windows.Forms.ToolStripMenuItem();
|
||||
this.toolStripMenuItem3 = new System.Windows.Forms.ToolStripSeparator();
|
||||
this.mnuClose = new System.Windows.Forms.ToolStripMenuItem();
|
||||
this.mnuView = new System.Windows.Forms.ToolStripMenuItem();
|
||||
this.mnuSplitView = new System.Windows.Forms.ToolStripMenuItem();
|
||||
|
@ -73,6 +69,26 @@
|
|||
this.toolsToolStripMenuItem = new System.Windows.Forms.ToolStripMenuItem();
|
||||
this.mnuPpuViewer = new System.Windows.Forms.ToolStripMenuItem();
|
||||
this.mnuMemoryViewer = new System.Windows.Forms.ToolStripMenuItem();
|
||||
this.mnuCodeDataLogger = new System.Windows.Forms.ToolStripMenuItem();
|
||||
this.statusStrip = new System.Windows.Forms.StatusStrip();
|
||||
this.lblPrgAnalysis = new System.Windows.Forms.ToolStripStatusLabel();
|
||||
this.lblPrgAnalysisResult = new System.Windows.Forms.ToolStripStatusLabel();
|
||||
this.lblChrAnalysis = new System.Windows.Forms.ToolStripStatusLabel();
|
||||
this.lblChrAnalysisResult = new System.Windows.Forms.ToolStripStatusLabel();
|
||||
this.tmrCdlRatios = new System.Windows.Forms.Timer(this.components);
|
||||
this.mnuResetCdlLog = new System.Windows.Forms.ToolStripMenuItem();
|
||||
this.autoLoadsaveCDLFileToolStripMenuItem = new System.Windows.Forms.ToolStripMenuItem();
|
||||
this.generateROMToolStripMenuItem = new System.Windows.Forms.ToolStripMenuItem();
|
||||
this.saveStrippedDataToolStripMenuItem = new System.Windows.Forms.ToolStripMenuItem();
|
||||
this.saveUnusedDataToolStripMenuItem = new System.Windows.Forms.ToolStripMenuItem();
|
||||
this.toolStripMenuItem4 = new System.Windows.Forms.ToolStripSeparator();
|
||||
this.mnuSaveAsCdlFile = new System.Windows.Forms.ToolStripMenuItem();
|
||||
this.mnuLoadCdlFile = new System.Windows.Forms.ToolStripMenuItem();
|
||||
this.ctrlDebuggerCode = new Mesen.GUI.Debugger.ctrlDebuggerCode();
|
||||
this.ctrlConsoleStatus = new Mesen.GUI.Debugger.ctrlConsoleStatus();
|
||||
this.ctrlDebuggerCodeSplit = new Mesen.GUI.Debugger.ctrlDebuggerCode();
|
||||
this.ctrlWatch = new Mesen.GUI.Debugger.ctrlWatch();
|
||||
this.ctrlBreakpoints = new Mesen.GUI.Debugger.Controls.ctrlBreakpoints();
|
||||
this.ctrlCallstack = new Mesen.GUI.Debugger.Controls.ctrlCallstack();
|
||||
((System.ComponentModel.ISupportInitialize)(this.splitContainer)).BeginInit();
|
||||
this.splitContainer.Panel1.SuspendLayout();
|
||||
|
@ -85,6 +101,7 @@
|
|||
this.grpBreakpoints.SuspendLayout();
|
||||
this.grpCallstack.SuspendLayout();
|
||||
this.menuStrip.SuspendLayout();
|
||||
this.statusStrip.SuspendLayout();
|
||||
this.SuspendLayout();
|
||||
//
|
||||
// splitContainer
|
||||
|
@ -104,8 +121,8 @@
|
|||
//
|
||||
this.splitContainer.Panel2.Controls.Add(this.tableLayoutPanel10);
|
||||
this.splitContainer.Panel2MinSize = 50;
|
||||
this.splitContainer.Size = new System.Drawing.Size(984, 588);
|
||||
this.splitContainer.SplitterDistance = 422;
|
||||
this.splitContainer.Size = new System.Drawing.Size(984, 564);
|
||||
this.splitContainer.SplitterDistance = 412;
|
||||
this.splitContainer.TabIndex = 1;
|
||||
//
|
||||
// tlpTop
|
||||
|
@ -122,21 +139,9 @@
|
|||
this.tlpTop.Name = "tlpTop";
|
||||
this.tlpTop.RowCount = 1;
|
||||
this.tlpTop.RowStyles.Add(new System.Windows.Forms.RowStyle(System.Windows.Forms.SizeType.Percent, 100F));
|
||||
this.tlpTop.Size = new System.Drawing.Size(984, 422);
|
||||
this.tlpTop.Size = new System.Drawing.Size(984, 412);
|
||||
this.tlpTop.TabIndex = 2;
|
||||
//
|
||||
// ctrlDebuggerCode
|
||||
//
|
||||
this.ctrlDebuggerCode.Code = null;
|
||||
this.ctrlDebuggerCode.ContextMenuStrip = this.contextMenuCode;
|
||||
this.ctrlDebuggerCode.Dock = System.Windows.Forms.DockStyle.Fill;
|
||||
this.ctrlDebuggerCode.Location = new System.Drawing.Point(3, 3);
|
||||
this.ctrlDebuggerCode.Name = "ctrlDebuggerCode";
|
||||
this.ctrlDebuggerCode.Size = new System.Drawing.Size(546, 416);
|
||||
this.ctrlDebuggerCode.TabIndex = 2;
|
||||
this.ctrlDebuggerCode.OnWatchAdded += new Mesen.GUI.Debugger.ctrlDebuggerCode.WatchAddedEventHandler(this.ctrlDebuggerCode_OnWatchAdded);
|
||||
this.ctrlDebuggerCode.Enter += new System.EventHandler(this.ctrlDebuggerCode_Enter);
|
||||
//
|
||||
// contextMenuCode
|
||||
//
|
||||
this.contextMenuCode.Items.AddRange(new System.Windows.Forms.ToolStripItem[] {
|
||||
|
@ -161,27 +166,6 @@
|
|||
this.mnuSetNextStatement.Size = new System.Drawing.Size(258, 22);
|
||||
this.mnuSetNextStatement.Text = "Set Next Statement";
|
||||
//
|
||||
// ctrlConsoleStatus
|
||||
//
|
||||
this.ctrlConsoleStatus.Dock = System.Windows.Forms.DockStyle.Top;
|
||||
this.ctrlConsoleStatus.Location = new System.Drawing.Point(552, 0);
|
||||
this.ctrlConsoleStatus.Margin = new System.Windows.Forms.Padding(0);
|
||||
this.ctrlConsoleStatus.Name = "ctrlConsoleStatus";
|
||||
this.ctrlConsoleStatus.Size = new System.Drawing.Size(432, 362);
|
||||
this.ctrlConsoleStatus.TabIndex = 3;
|
||||
//
|
||||
// ctrlDebuggerCodeSplit
|
||||
//
|
||||
this.ctrlDebuggerCodeSplit.Code = null;
|
||||
this.ctrlDebuggerCodeSplit.Dock = System.Windows.Forms.DockStyle.Fill;
|
||||
this.ctrlDebuggerCodeSplit.Location = new System.Drawing.Point(555, 3);
|
||||
this.ctrlDebuggerCodeSplit.Name = "ctrlDebuggerCodeSplit";
|
||||
this.ctrlDebuggerCodeSplit.Size = new System.Drawing.Size(1, 416);
|
||||
this.ctrlDebuggerCodeSplit.TabIndex = 4;
|
||||
this.ctrlDebuggerCodeSplit.Visible = false;
|
||||
this.ctrlDebuggerCodeSplit.OnWatchAdded += new Mesen.GUI.Debugger.ctrlDebuggerCode.WatchAddedEventHandler(this.ctrlDebuggerCode_OnWatchAdded);
|
||||
this.ctrlDebuggerCodeSplit.Enter += new System.EventHandler(this.ctrlDebuggerCodeSplit_Enter);
|
||||
//
|
||||
// tableLayoutPanel10
|
||||
//
|
||||
this.tableLayoutPanel10.ColumnCount = 3;
|
||||
|
@ -196,7 +180,7 @@
|
|||
this.tableLayoutPanel10.Name = "tableLayoutPanel10";
|
||||
this.tableLayoutPanel10.RowCount = 1;
|
||||
this.tableLayoutPanel10.RowStyles.Add(new System.Windows.Forms.RowStyle(System.Windows.Forms.SizeType.Percent, 100F));
|
||||
this.tableLayoutPanel10.Size = new System.Drawing.Size(984, 162);
|
||||
this.tableLayoutPanel10.Size = new System.Drawing.Size(984, 148);
|
||||
this.tableLayoutPanel10.TabIndex = 0;
|
||||
//
|
||||
// grpWatch
|
||||
|
@ -205,46 +189,29 @@
|
|||
this.grpWatch.Dock = System.Windows.Forms.DockStyle.Fill;
|
||||
this.grpWatch.Location = new System.Drawing.Point(3, 3);
|
||||
this.grpWatch.Name = "grpWatch";
|
||||
this.grpWatch.Size = new System.Drawing.Size(322, 156);
|
||||
this.grpWatch.Size = new System.Drawing.Size(322, 142);
|
||||
this.grpWatch.TabIndex = 2;
|
||||
this.grpWatch.TabStop = false;
|
||||
this.grpWatch.Text = "Watch";
|
||||
//
|
||||
// ctrlWatch
|
||||
//
|
||||
this.ctrlWatch.Dock = System.Windows.Forms.DockStyle.Fill;
|
||||
this.ctrlWatch.Location = new System.Drawing.Point(3, 16);
|
||||
this.ctrlWatch.Name = "ctrlWatch";
|
||||
this.ctrlWatch.Size = new System.Drawing.Size(316, 137);
|
||||
this.ctrlWatch.TabIndex = 0;
|
||||
//
|
||||
// grpBreakpoints
|
||||
//
|
||||
this.grpBreakpoints.Controls.Add(this.ctrlBreakpoints);
|
||||
this.grpBreakpoints.Dock = System.Windows.Forms.DockStyle.Fill;
|
||||
this.grpBreakpoints.Location = new System.Drawing.Point(331, 3);
|
||||
this.grpBreakpoints.Name = "grpBreakpoints";
|
||||
this.grpBreakpoints.Size = new System.Drawing.Size(322, 156);
|
||||
this.grpBreakpoints.Size = new System.Drawing.Size(322, 142);
|
||||
this.grpBreakpoints.TabIndex = 3;
|
||||
this.grpBreakpoints.TabStop = false;
|
||||
this.grpBreakpoints.Text = "Breakpoints";
|
||||
//
|
||||
// ctrlBreakpoints
|
||||
//
|
||||
this.ctrlBreakpoints.Dock = System.Windows.Forms.DockStyle.Fill;
|
||||
this.ctrlBreakpoints.Location = new System.Drawing.Point(3, 16);
|
||||
this.ctrlBreakpoints.Name = "ctrlBreakpoints";
|
||||
this.ctrlBreakpoints.Size = new System.Drawing.Size(316, 137);
|
||||
this.ctrlBreakpoints.TabIndex = 0;
|
||||
this.ctrlBreakpoints.BreakpointChanged += new System.EventHandler(this.ctrlBreakpoints_BreakpointChanged);
|
||||
//
|
||||
// grpCallstack
|
||||
//
|
||||
this.grpCallstack.Controls.Add(this.ctrlCallstack);
|
||||
this.grpCallstack.Dock = System.Windows.Forms.DockStyle.Fill;
|
||||
this.grpCallstack.Location = new System.Drawing.Point(659, 3);
|
||||
this.grpCallstack.Name = "grpCallstack";
|
||||
this.grpCallstack.Size = new System.Drawing.Size(322, 156);
|
||||
this.grpCallstack.Size = new System.Drawing.Size(322, 142);
|
||||
this.grpCallstack.TabIndex = 4;
|
||||
this.grpCallstack.TabStop = false;
|
||||
this.grpCallstack.Text = "Callstack";
|
||||
|
@ -266,11 +233,17 @@
|
|||
// fileToolStripMenuItem
|
||||
//
|
||||
this.fileToolStripMenuItem.DropDownItems.AddRange(new System.Windows.Forms.ToolStripItem[] {
|
||||
this.toolStripMenuItem3,
|
||||
this.mnuClose});
|
||||
this.fileToolStripMenuItem.Name = "fileToolStripMenuItem";
|
||||
this.fileToolStripMenuItem.Size = new System.Drawing.Size(37, 20);
|
||||
this.fileToolStripMenuItem.Text = "File";
|
||||
//
|
||||
// toolStripMenuItem3
|
||||
//
|
||||
this.toolStripMenuItem3.Name = "toolStripMenuItem3";
|
||||
this.toolStripMenuItem3.Size = new System.Drawing.Size(100, 6);
|
||||
//
|
||||
// mnuClose
|
||||
//
|
||||
this.mnuClose.Name = "mnuClose";
|
||||
|
@ -463,7 +436,8 @@
|
|||
//
|
||||
this.toolsToolStripMenuItem.DropDownItems.AddRange(new System.Windows.Forms.ToolStripItem[] {
|
||||
this.mnuPpuViewer,
|
||||
this.mnuMemoryViewer});
|
||||
this.mnuMemoryViewer,
|
||||
this.mnuCodeDataLogger});
|
||||
this.toolsToolStripMenuItem.Name = "toolsToolStripMenuItem";
|
||||
this.toolsToolStripMenuItem.Size = new System.Drawing.Size(48, 20);
|
||||
this.toolsToolStripMenuItem.Text = "Tools";
|
||||
|
@ -471,23 +445,188 @@
|
|||
// mnuPpuViewer
|
||||
//
|
||||
this.mnuPpuViewer.Name = "mnuPpuViewer";
|
||||
this.mnuPpuViewer.Size = new System.Drawing.Size(157, 22);
|
||||
this.mnuPpuViewer.Size = new System.Drawing.Size(171, 22);
|
||||
this.mnuPpuViewer.Text = "PPU Viewer";
|
||||
this.mnuPpuViewer.Click += new System.EventHandler(this.mnuNametableViewer_Click);
|
||||
//
|
||||
// mnuMemoryViewer
|
||||
//
|
||||
this.mnuMemoryViewer.Name = "mnuMemoryViewer";
|
||||
this.mnuMemoryViewer.Size = new System.Drawing.Size(157, 22);
|
||||
this.mnuMemoryViewer.Size = new System.Drawing.Size(171, 22);
|
||||
this.mnuMemoryViewer.Text = "Memory Viewer";
|
||||
this.mnuMemoryViewer.Click += new System.EventHandler(this.mnuMemoryViewer_Click);
|
||||
//
|
||||
// mnuCodeDataLogger
|
||||
//
|
||||
this.mnuCodeDataLogger.DropDownItems.AddRange(new System.Windows.Forms.ToolStripItem[] {
|
||||
this.autoLoadsaveCDLFileToolStripMenuItem,
|
||||
this.toolStripMenuItem4,
|
||||
this.mnuLoadCdlFile,
|
||||
this.mnuSaveAsCdlFile,
|
||||
this.mnuResetCdlLog,
|
||||
this.generateROMToolStripMenuItem});
|
||||
this.mnuCodeDataLogger.Name = "mnuCodeDataLogger";
|
||||
this.mnuCodeDataLogger.Size = new System.Drawing.Size(171, 22);
|
||||
this.mnuCodeDataLogger.Text = "Code/Data Logger";
|
||||
//
|
||||
// statusStrip
|
||||
//
|
||||
this.statusStrip.Items.AddRange(new System.Windows.Forms.ToolStripItem[] {
|
||||
this.lblPrgAnalysis,
|
||||
this.lblPrgAnalysisResult,
|
||||
this.lblChrAnalysis,
|
||||
this.lblChrAnalysisResult});
|
||||
this.statusStrip.Location = new System.Drawing.Point(0, 588);
|
||||
this.statusStrip.Name = "statusStrip";
|
||||
this.statusStrip.Size = new System.Drawing.Size(984, 24);
|
||||
this.statusStrip.TabIndex = 3;
|
||||
this.statusStrip.Text = "statusStrip1";
|
||||
//
|
||||
// lblPrgAnalysis
|
||||
//
|
||||
this.lblPrgAnalysis.BorderStyle = System.Windows.Forms.Border3DStyle.Etched;
|
||||
this.lblPrgAnalysis.Name = "lblPrgAnalysis";
|
||||
this.lblPrgAnalysis.Size = new System.Drawing.Size(76, 19);
|
||||
this.lblPrgAnalysis.Text = "PRG analysis:";
|
||||
//
|
||||
// lblPrgAnalysisResult
|
||||
//
|
||||
this.lblPrgAnalysisResult.BorderSides = System.Windows.Forms.ToolStripStatusLabelBorderSides.Right;
|
||||
this.lblPrgAnalysisResult.BorderStyle = System.Windows.Forms.Border3DStyle.Etched;
|
||||
this.lblPrgAnalysisResult.Name = "lblPrgAnalysisResult";
|
||||
this.lblPrgAnalysisResult.Size = new System.Drawing.Size(235, 19);
|
||||
this.lblPrgAnalysisResult.Text = "xx% (Code: xx%, Data: xx%, Unknown: xx%)";
|
||||
//
|
||||
// lblChrAnalysis
|
||||
//
|
||||
this.lblChrAnalysis.Name = "lblChrAnalysis";
|
||||
this.lblChrAnalysis.Size = new System.Drawing.Size(78, 19);
|
||||
this.lblChrAnalysis.Text = "CHR analysis:";
|
||||
//
|
||||
// lblChrAnalysisResult
|
||||
//
|
||||
this.lblChrAnalysisResult.Name = "lblChrAnalysisResult";
|
||||
this.lblChrAnalysisResult.Size = new System.Drawing.Size(239, 19);
|
||||
this.lblChrAnalysisResult.Text = "xx% (Drawn: xx%, Read: xx%, Unknown: xx%)";
|
||||
//
|
||||
// tmrCdlRatios
|
||||
//
|
||||
this.tmrCdlRatios.Interval = 300;
|
||||
this.tmrCdlRatios.Tick += new System.EventHandler(this.tmrCdlRatios_Tick);
|
||||
//
|
||||
// mnuResetCdlLog
|
||||
//
|
||||
this.mnuResetCdlLog.Name = "mnuResetCdlLog";
|
||||
this.mnuResetCdlLog.Size = new System.Drawing.Size(193, 22);
|
||||
this.mnuResetCdlLog.Text = "Reset log";
|
||||
this.mnuResetCdlLog.Click += new System.EventHandler(this.mnuResetCdlLog_Click);
|
||||
//
|
||||
// autoLoadsaveCDLFileToolStripMenuItem
|
||||
//
|
||||
this.autoLoadsaveCDLFileToolStripMenuItem.Checked = true;
|
||||
this.autoLoadsaveCDLFileToolStripMenuItem.CheckState = System.Windows.Forms.CheckState.Checked;
|
||||
this.autoLoadsaveCDLFileToolStripMenuItem.Enabled = false;
|
||||
this.autoLoadsaveCDLFileToolStripMenuItem.Name = "autoLoadsaveCDLFileToolStripMenuItem";
|
||||
this.autoLoadsaveCDLFileToolStripMenuItem.Size = new System.Drawing.Size(193, 22);
|
||||
this.autoLoadsaveCDLFileToolStripMenuItem.Text = "Auto load/save log file";
|
||||
//
|
||||
// generateROMToolStripMenuItem
|
||||
//
|
||||
this.generateROMToolStripMenuItem.DropDownItems.AddRange(new System.Windows.Forms.ToolStripItem[] {
|
||||
this.saveStrippedDataToolStripMenuItem,
|
||||
this.saveUnusedDataToolStripMenuItem});
|
||||
this.generateROMToolStripMenuItem.Enabled = false;
|
||||
this.generateROMToolStripMenuItem.Name = "generateROMToolStripMenuItem";
|
||||
this.generateROMToolStripMenuItem.Size = new System.Drawing.Size(193, 22);
|
||||
this.generateROMToolStripMenuItem.Text = "Generate ROM";
|
||||
//
|
||||
// saveStrippedDataToolStripMenuItem
|
||||
//
|
||||
this.saveStrippedDataToolStripMenuItem.Name = "saveStrippedDataToolStripMenuItem";
|
||||
this.saveStrippedDataToolStripMenuItem.Size = new System.Drawing.Size(170, 22);
|
||||
this.saveStrippedDataToolStripMenuItem.Text = "Save stripped data";
|
||||
//
|
||||
// saveUnusedDataToolStripMenuItem
|
||||
//
|
||||
this.saveUnusedDataToolStripMenuItem.Name = "saveUnusedDataToolStripMenuItem";
|
||||
this.saveUnusedDataToolStripMenuItem.Size = new System.Drawing.Size(170, 22);
|
||||
this.saveUnusedDataToolStripMenuItem.Text = "Save unused data";
|
||||
//
|
||||
// toolStripMenuItem4
|
||||
//
|
||||
this.toolStripMenuItem4.Name = "toolStripMenuItem4";
|
||||
this.toolStripMenuItem4.Size = new System.Drawing.Size(190, 6);
|
||||
//
|
||||
// mnuSaveAsCdlFile
|
||||
//
|
||||
this.mnuSaveAsCdlFile.Name = "mnuSaveAsCdlFile";
|
||||
this.mnuSaveAsCdlFile.Size = new System.Drawing.Size(193, 22);
|
||||
this.mnuSaveAsCdlFile.Text = "Save as CDL file...";
|
||||
this.mnuSaveAsCdlFile.Click += new System.EventHandler(this.mnuSaveAsCdlFile_Click);
|
||||
//
|
||||
// mnuLoadCdlFile
|
||||
//
|
||||
this.mnuLoadCdlFile.Name = "mnuLoadCdlFile";
|
||||
this.mnuLoadCdlFile.Size = new System.Drawing.Size(193, 22);
|
||||
this.mnuLoadCdlFile.Text = "Load CDL file...";
|
||||
this.mnuLoadCdlFile.Click += new System.EventHandler(this.mnuLoadCdlFile_Click);
|
||||
//
|
||||
// ctrlDebuggerCode
|
||||
//
|
||||
this.ctrlDebuggerCode.Code = null;
|
||||
this.ctrlDebuggerCode.ContextMenuStrip = this.contextMenuCode;
|
||||
this.ctrlDebuggerCode.Dock = System.Windows.Forms.DockStyle.Fill;
|
||||
this.ctrlDebuggerCode.Location = new System.Drawing.Point(3, 3);
|
||||
this.ctrlDebuggerCode.Name = "ctrlDebuggerCode";
|
||||
this.ctrlDebuggerCode.Size = new System.Drawing.Size(546, 406);
|
||||
this.ctrlDebuggerCode.TabIndex = 2;
|
||||
this.ctrlDebuggerCode.OnWatchAdded += new Mesen.GUI.Debugger.ctrlDebuggerCode.WatchAddedEventHandler(this.ctrlDebuggerCode_OnWatchAdded);
|
||||
this.ctrlDebuggerCode.Enter += new System.EventHandler(this.ctrlDebuggerCode_Enter);
|
||||
//
|
||||
// ctrlConsoleStatus
|
||||
//
|
||||
this.ctrlConsoleStatus.Dock = System.Windows.Forms.DockStyle.Top;
|
||||
this.ctrlConsoleStatus.Location = new System.Drawing.Point(552, 0);
|
||||
this.ctrlConsoleStatus.Margin = new System.Windows.Forms.Padding(0);
|
||||
this.ctrlConsoleStatus.Name = "ctrlConsoleStatus";
|
||||
this.ctrlConsoleStatus.Size = new System.Drawing.Size(432, 362);
|
||||
this.ctrlConsoleStatus.TabIndex = 3;
|
||||
//
|
||||
// ctrlDebuggerCodeSplit
|
||||
//
|
||||
this.ctrlDebuggerCodeSplit.Code = null;
|
||||
this.ctrlDebuggerCodeSplit.Dock = System.Windows.Forms.DockStyle.Fill;
|
||||
this.ctrlDebuggerCodeSplit.Location = new System.Drawing.Point(555, 3);
|
||||
this.ctrlDebuggerCodeSplit.Name = "ctrlDebuggerCodeSplit";
|
||||
this.ctrlDebuggerCodeSplit.Size = new System.Drawing.Size(1, 406);
|
||||
this.ctrlDebuggerCodeSplit.TabIndex = 4;
|
||||
this.ctrlDebuggerCodeSplit.Visible = false;
|
||||
this.ctrlDebuggerCodeSplit.OnWatchAdded += new Mesen.GUI.Debugger.ctrlDebuggerCode.WatchAddedEventHandler(this.ctrlDebuggerCode_OnWatchAdded);
|
||||
this.ctrlDebuggerCodeSplit.Enter += new System.EventHandler(this.ctrlDebuggerCodeSplit_Enter);
|
||||
//
|
||||
// ctrlWatch
|
||||
//
|
||||
this.ctrlWatch.Dock = System.Windows.Forms.DockStyle.Fill;
|
||||
this.ctrlWatch.Location = new System.Drawing.Point(3, 16);
|
||||
this.ctrlWatch.Name = "ctrlWatch";
|
||||
this.ctrlWatch.Size = new System.Drawing.Size(316, 123);
|
||||
this.ctrlWatch.TabIndex = 0;
|
||||
//
|
||||
// ctrlBreakpoints
|
||||
//
|
||||
this.ctrlBreakpoints.Dock = System.Windows.Forms.DockStyle.Fill;
|
||||
this.ctrlBreakpoints.Location = new System.Drawing.Point(3, 16);
|
||||
this.ctrlBreakpoints.Name = "ctrlBreakpoints";
|
||||
this.ctrlBreakpoints.Size = new System.Drawing.Size(316, 123);
|
||||
this.ctrlBreakpoints.TabIndex = 0;
|
||||
this.ctrlBreakpoints.BreakpointChanged += new System.EventHandler(this.ctrlBreakpoints_BreakpointChanged);
|
||||
//
|
||||
// ctrlCallstack
|
||||
//
|
||||
this.ctrlCallstack.Dock = System.Windows.Forms.DockStyle.Fill;
|
||||
this.ctrlCallstack.Location = new System.Drawing.Point(3, 16);
|
||||
this.ctrlCallstack.Name = "ctrlCallstack";
|
||||
this.ctrlCallstack.Size = new System.Drawing.Size(316, 137);
|
||||
this.ctrlCallstack.Size = new System.Drawing.Size(316, 123);
|
||||
this.ctrlCallstack.TabIndex = 0;
|
||||
this.ctrlCallstack.FunctionSelected += new System.EventHandler(this.ctrlCallstack_FunctionSelected);
|
||||
//
|
||||
|
@ -498,6 +637,7 @@
|
|||
this.ClientSize = new System.Drawing.Size(984, 612);
|
||||
this.Controls.Add(this.splitContainer);
|
||||
this.Controls.Add(this.menuStrip);
|
||||
this.Controls.Add(this.statusStrip);
|
||||
this.MainMenuStrip = this.menuStrip;
|
||||
this.MinimumSize = new System.Drawing.Size(1000, 650);
|
||||
this.Name = "frmDebugger";
|
||||
|
@ -515,6 +655,8 @@
|
|||
this.grpCallstack.ResumeLayout(false);
|
||||
this.menuStrip.ResumeLayout(false);
|
||||
this.menuStrip.PerformLayout();
|
||||
this.statusStrip.ResumeLayout(false);
|
||||
this.statusStrip.PerformLayout();
|
||||
this.ResumeLayout(false);
|
||||
this.PerformLayout();
|
||||
|
||||
|
@ -564,5 +706,21 @@
|
|||
private System.Windows.Forms.ToolStripMenuItem mnuResetFontSize;
|
||||
private System.Windows.Forms.GroupBox grpCallstack;
|
||||
private Controls.ctrlCallstack ctrlCallstack;
|
||||
private System.Windows.Forms.ToolStripSeparator toolStripMenuItem3;
|
||||
private System.Windows.Forms.ToolStripMenuItem mnuCodeDataLogger;
|
||||
private System.Windows.Forms.StatusStrip statusStrip;
|
||||
private System.Windows.Forms.ToolStripStatusLabel lblPrgAnalysis;
|
||||
private System.Windows.Forms.ToolStripStatusLabel lblPrgAnalysisResult;
|
||||
private System.Windows.Forms.Timer tmrCdlRatios;
|
||||
private System.Windows.Forms.ToolStripStatusLabel lblChrAnalysis;
|
||||
private System.Windows.Forms.ToolStripStatusLabel lblChrAnalysisResult;
|
||||
private System.Windows.Forms.ToolStripMenuItem autoLoadsaveCDLFileToolStripMenuItem;
|
||||
private System.Windows.Forms.ToolStripSeparator toolStripMenuItem4;
|
||||
private System.Windows.Forms.ToolStripMenuItem mnuLoadCdlFile;
|
||||
private System.Windows.Forms.ToolStripMenuItem mnuSaveAsCdlFile;
|
||||
private System.Windows.Forms.ToolStripMenuItem mnuResetCdlLog;
|
||||
private System.Windows.Forms.ToolStripMenuItem generateROMToolStripMenuItem;
|
||||
private System.Windows.Forms.ToolStripMenuItem saveStrippedDataToolStripMenuItem;
|
||||
private System.Windows.Forms.ToolStripMenuItem saveUnusedDataToolStripMenuItem;
|
||||
}
|
||||
}
|
|
@ -40,6 +40,22 @@ namespace Mesen.GUI.Debugger
|
|||
|
||||
//Pause a few frames later to give the debugger a chance to disassemble some code
|
||||
InteropEmu.DebugStep(100000);
|
||||
|
||||
UpdateCdlRatios();
|
||||
tmrCdlRatios.Start();
|
||||
}
|
||||
|
||||
private void UpdateCdlRatios()
|
||||
{
|
||||
CdlRatios ratios = new CdlRatios();
|
||||
InteropEmu.DebugGetCdlRatios(ref ratios);
|
||||
|
||||
lblPrgAnalysisResult.Text = string.Format("{0:0.00}% (Code: {1:0.00}%, Data: {2:0.00}%, Unknown: {3:0.00}%)", ratios.PrgRatio * 100, ratios.CodeRatio * 100, ratios.DataRatio * 100, (1 - ratios.PrgRatio) * 100);
|
||||
if(ratios.ChrRatio >= 0) {
|
||||
lblChrAnalysisResult.Text = string.Format("{0:0.00}% (Drawn: {1:0.00}%, Read: {2:0.00}%, Unknown: {3:0.00}%)", ratios.ChrRatio * 100, ratios.ChrDrawnRatio * 100, ratios.ChrReadRatio * 100, (1 - ratios.ChrRatio) * 100);
|
||||
} else {
|
||||
lblChrAnalysisResult.Text = "N/A (CHR RAM)";
|
||||
}
|
||||
}
|
||||
|
||||
private void _notifListener_OnNotification(InteropEmu.NotificationEventArgs e)
|
||||
|
@ -249,5 +265,38 @@ namespace Mesen.GUI.Debugger
|
|||
{
|
||||
_lastCodeWindow.ScrollToLineNumber((int)sender);
|
||||
}
|
||||
|
||||
private void tmrCdlRatios_Tick(object sender, EventArgs e)
|
||||
{
|
||||
this.UpdateCdlRatios();
|
||||
}
|
||||
|
||||
private void mnuLoadCdlFile_Click(object sender, EventArgs e)
|
||||
{
|
||||
OpenFileDialog ofd = new OpenFileDialog();
|
||||
ofd.Filter = "CDL files (*.cdl)|*.cdl";
|
||||
if(ofd.ShowDialog() == System.Windows.Forms.DialogResult.OK) {
|
||||
if(!InteropEmu.DebugLoadCdlFile(ofd.FileName)) {
|
||||
MessageBox.Show("Could not load CDL file. The file selected file is invalid.", "Error", MessageBoxButtons.OK, MessageBoxIcon.Error);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private void mnuSaveAsCdlFile_Click(object sender, EventArgs e)
|
||||
{
|
||||
SaveFileDialog sfd = new SaveFileDialog();
|
||||
sfd.Filter = "CDL files (*.cdl)|*.cdl";
|
||||
sfd.AddExtension = true;
|
||||
if(sfd.ShowDialog() == System.Windows.Forms.DialogResult.OK) {
|
||||
if(!InteropEmu.DebugSaveCdlFile(sfd.FileName)) {
|
||||
MessageBox.Show("Error while trying to save CDL file.", "Error", MessageBoxButtons.OK, MessageBoxIcon.Error);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private void mnuResetCdlLog_Click(object sender, EventArgs e)
|
||||
{
|
||||
InteropEmu.DebugResetCdlLog();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -123,4 +123,10 @@
|
|||
<metadata name="menuStrip.TrayLocation" type="System.Drawing.Point, System.Drawing, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a">
|
||||
<value>107, 17</value>
|
||||
</metadata>
|
||||
<metadata name="statusStrip.TrayLocation" type="System.Drawing.Point, System.Drawing, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a">
|
||||
<value>713, 17</value>
|
||||
</metadata>
|
||||
<metadata name="tmrCdlRatios.TrayLocation" type="System.Drawing.Point, System.Drawing, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a">
|
||||
<value>822, 17</value>
|
||||
</metadata>
|
||||
</root>
|
|
@ -82,6 +82,11 @@ namespace Mesen.GUI
|
|||
[DllImport(DLLPath)] public static extern IntPtr DebugGetCode();
|
||||
[DllImport(DLLPath)] public static extern Byte DebugGetMemoryValue(UInt32 addr);
|
||||
[DllImport(DLLPath)] public static extern UInt32 DebugGetRelativeAddress(UInt32 addr);
|
||||
|
||||
[DllImport(DLLPath)] [return: MarshalAs(UnmanagedType.I1)] public static extern bool DebugLoadCdlFile([MarshalAs(UnmanagedType.CustomMarshaler, MarshalTypeRef=typeof(UTF8Marshaler))]string cdlFilepath);
|
||||
[DllImport(DLLPath)] [return: MarshalAs(UnmanagedType.I1)] public static extern bool DebugSaveCdlFile([MarshalAs(UnmanagedType.CustomMarshaler, MarshalTypeRef=typeof(UTF8Marshaler))]string cdlFilepath);
|
||||
[DllImport(DLLPath)] public static extern void DebugGetCdlRatios(ref CdlRatios ratios);
|
||||
[DllImport(DLLPath)] public static extern void DebugResetCdlLog();
|
||||
|
||||
[DllImport(DLLPath, EntryPoint="DebugGetMemoryState")] private static extern UInt32 DebugGetMemoryStateWrapper(DebugMemoryType type, IntPtr buffer);
|
||||
public static byte[] DebugGetMemoryState(DebugMemoryType type)
|
||||
|
@ -268,6 +273,17 @@ namespace Mesen.GUI
|
|||
}
|
||||
}
|
||||
|
||||
public struct CdlRatios
|
||||
{
|
||||
public float CodeRatio;
|
||||
public float DataRatio;
|
||||
public float PrgRatio;
|
||||
|
||||
public float ChrRatio;
|
||||
public float ChrReadRatio;
|
||||
public float ChrDrawnRatio;
|
||||
}
|
||||
|
||||
public struct DebugState
|
||||
{
|
||||
public CPUState CPU;
|
||||
|
|
|
@ -1,6 +1,7 @@
|
|||
#include "stdafx.h"
|
||||
#include "../Core/Console.h"
|
||||
#include "../Core/Debugger.h"
|
||||
#include "../Core/CodeDataLogger.h"
|
||||
|
||||
static shared_ptr<Debugger> _debugger = nullptr;
|
||||
|
||||
|
@ -15,7 +16,6 @@ extern "C"
|
|||
DllExport void __stdcall DebugRelease()
|
||||
{
|
||||
if(_debugger != nullptr) {
|
||||
_debugger->Run();
|
||||
_debugger.reset();
|
||||
}
|
||||
}
|
||||
|
@ -43,4 +43,9 @@ extern "C"
|
|||
|
||||
DllExport uint8_t __stdcall DebugGetMemoryValue(uint32_t addr) { return _debugger->GetMemoryValue(addr); }
|
||||
DllExport uint32_t __stdcall DebugGetRelativeAddress(uint32_t addr) { return _debugger->GetRelativeAddress(addr); }
|
||||
|
||||
DllExport bool __stdcall DebugLoadCdlFile(char* cdlFilepath) { return _debugger->LoadCdlFile(cdlFilepath); }
|
||||
DllExport bool __stdcall DebugSaveCdlFile(char* cdlFilepath) { return _debugger->SaveCdlFile(cdlFilepath); }
|
||||
DllExport void __stdcall DebugGetCdlRatios(CdlRatios* cdlRatios) { *cdlRatios = _debugger->GetCdlRatios(); }
|
||||
DllExport void __stdcall DebugResetCdlLog() { _debugger->ResetCdlLog(); }
|
||||
};
|
||||
|
|
|
@ -56,6 +56,13 @@ string FolderUtilities::GetHdPackFolder()
|
|||
return folder;
|
||||
}
|
||||
|
||||
string FolderUtilities::GetDebuggerFolder()
|
||||
{
|
||||
string folder = CombinePath(GetHomeFolder(), "Debugger\\");
|
||||
CreateFolder(folder);
|
||||
return folder;
|
||||
}
|
||||
|
||||
string FolderUtilities::GetSaveStateFolder()
|
||||
{
|
||||
string folder = CombinePath(GetHomeFolder(), "SaveStates\\");
|
||||
|
|
|
@ -20,6 +20,7 @@ public:
|
|||
static string GetMovieFolder();
|
||||
static string GetScreenshotFolder();
|
||||
static string GetHdPackFolder();
|
||||
static string GetDebuggerFolder();
|
||||
|
||||
static vector<string> GetFolders(string rootFolder);
|
||||
static vector<string> GetFilesInFolder(string rootFolder, string mask, bool recursive);
|
||||
|
|
Loading…
Add table
Reference in a new issue