Core: Migrate register access API from debugger into core

This commit is contained in:
Vicki Pfau 2022-05-16 15:58:50 -07:00
parent 6f09085676
commit 87738ba8f3
9 changed files with 342 additions and 220 deletions

View File

@ -135,6 +135,10 @@ struct mCore {
size_t (*listMemoryBlocks)(const struct mCore*, const struct mCoreMemoryBlock**);
void* (*getMemoryBlock)(struct mCore*, size_t id, size_t* sizeOut);
size_t (*listRegisters)(const struct mCore*, const struct mCoreRegisterInfo**);
bool (*readRegister)(const struct mCore*, const char* name, void* out);
bool (*writeRegister)(struct mCore*, const char* name, const void* in);
#ifdef USE_DEBUGGERS
bool (*supportsDebuggerType)(struct mCore*, enum mDebuggerType);
struct mDebuggerPlatform* (*debuggerPlatform)(struct mCore*);

View File

@ -286,6 +286,21 @@ struct mCoreMemoryBlock {
uint32_t segmentStart;
};
enum mCoreRegisterType {
mCORE_REGISTER_GPR = 0,
mCORE_REGISTER_FPR,
mCORE_REGISTER_FLAGS,
mCORE_REGISTER_SIMD,
};
struct mCoreRegisterInfo {
const char* name;
const char** aliases;
unsigned width;
uint32_t mask;
enum mCoreRegisterType type;
};
CXX_GUARD_END
#endif

View File

@ -118,8 +118,6 @@ struct mDebuggerPlatform {
void (*trace)(struct mDebuggerPlatform*, char* out, size_t* length);
bool (*getRegister)(struct mDebuggerPlatform*, const char* name, int32_t* value);
bool (*setRegister)(struct mDebuggerPlatform*, const char* name, int32_t value);
bool (*lookupIdentifier)(struct mDebuggerPlatform*, const char* name, int32_t* value, int* segment);
uint32_t (*getStackTraceMode)(struct mDebuggerPlatform*);

View File

@ -242,8 +242,6 @@ static bool ARMDebuggerHasBreakpoints(struct mDebuggerPlatform*);
static void ARMDebuggerTrace(struct mDebuggerPlatform*, char* out, size_t* length);
static void ARMDebuggerFormatRegisters(struct ARMRegisterFile* regs, char* out, size_t* length);
static void ARMDebuggerFrameFormatRegisters(struct mStackFrame* frame, char* out, size_t* length);
static bool ARMDebuggerGetRegister(struct mDebuggerPlatform*, const char* name, int32_t* value);
static bool ARMDebuggerSetRegister(struct mDebuggerPlatform*, const char* name, int32_t value);
static uint32_t ARMDebuggerGetStackTraceMode(struct mDebuggerPlatform*);
static void ARMDebuggerSetStackTraceMode(struct mDebuggerPlatform*, uint32_t);
static bool ARMDebuggerUpdateStackTrace(struct mDebuggerPlatform* d);
@ -261,8 +259,6 @@ struct mDebuggerPlatform* ARMDebuggerPlatformCreate(void) {
platform->checkBreakpoints = ARMDebuggerCheckBreakpoints;
platform->hasBreakpoints = ARMDebuggerHasBreakpoints;
platform->trace = ARMDebuggerTrace;
platform->getRegister = ARMDebuggerGetRegister;
platform->setRegister = ARMDebuggerSetRegister;
platform->getStackTraceMode = ARMDebuggerGetStackTraceMode;
platform->setStackTraceMode = ARMDebuggerSetStackTraceMode;
platform->updateStackTrace = ARMDebuggerUpdateStackTrace;
@ -511,82 +507,6 @@ static void ARMDebuggerFrameFormatRegisters(struct mStackFrame* frame, char* out
ARMDebuggerFormatRegisters(frame->regs, out, length);
}
bool ARMDebuggerGetRegister(struct mDebuggerPlatform* d, const char* name, int32_t* value) {
struct ARMDebugger* debugger = (struct ARMDebugger*) d;
struct ARMCore* cpu = debugger->cpu;
if (strcmp(name, "sp") == 0) {
*value = cpu->gprs[ARM_SP];
return true;
}
if (strcmp(name, "lr") == 0) {
*value = cpu->gprs[ARM_LR];
return true;
}
if (strcmp(name, "pc") == 0) {
*value = cpu->gprs[ARM_PC];
return true;
}
if (strcmp(name, "cpsr") == 0) {
*value = cpu->cpsr.packed;
return true;
}
// TODO: test if mode has SPSR
if (strcmp(name, "spsr") == 0) {
*value = cpu->spsr.packed;
return true;
}
if (name[0] == 'r') {
char* end;
uint32_t reg = strtoul(&name[1], &end, 10);
if (reg <= ARM_PC) {
*value = cpu->gprs[reg];
return true;
}
}
return false;
}
bool ARMDebuggerSetRegister(struct mDebuggerPlatform* d, const char* name, int32_t value) {
struct ARMDebugger* debugger = (struct ARMDebugger*) d;
struct ARMCore* cpu = debugger->cpu;
if (strcmp(name, "sp") == 0) {
cpu->gprs[ARM_SP] = value;
return true;
}
if (strcmp(name, "lr") == 0) {
cpu->gprs[ARM_LR] = value;
return true;
}
if (strcmp(name, "pc") == 0) {
cpu->gprs[ARM_PC] = value;
if (cpu->executionMode == MODE_ARM) {
ARMWritePC(cpu);
} else {
ThumbWritePC(cpu);
}
return true;
}
if (name[0] == 'r') {
char* end;
uint32_t reg = strtoul(&name[1], &end, 10);
if (reg > ARM_PC) {
return false;
}
cpu->gprs[reg] = value;
if (reg == ARM_PC) {
if (cpu->executionMode == MODE_ARM) {
ARMWritePC(cpu);
} else {
ThumbWritePC(cpu);
}
}
return true;
}
return false;
}
static uint32_t ARMDebuggerGetStackTraceMode(struct mDebuggerPlatform* d) {
struct ARMDebugger* debugger = (struct ARMDebugger*) d;
return debugger->stackTraceMode;

View File

@ -452,7 +452,7 @@ static void _writeRegister(struct CLIDebugger* debugger, struct CLIDebugVector*
debugger->backend->printf(debugger->backend, "%s\n", ERROR_INVALID_ARGS);
return;
}
if (!debugger->d.platform->setRegister(debugger->d.platform, dv->charValue, dv->next->intValue)) {
if (!debugger->d.core->writeRegister(debugger->d.core, dv->charValue, &dv->next->intValue)) {
debugger->backend->printf(debugger->backend, "%s\n", ERROR_INVALID_ARGS);
}
}

View File

@ -156,7 +156,7 @@ bool mDebuggerLookupIdentifier(struct mDebugger* debugger, const char* name, int
if (debugger->core->lookupIdentifier(debugger->core, name, value, segment)) {
return true;
}
if (debugger->platform && debugger->platform->getRegister(debugger->platform, name, value)) {
if (debugger->platform && debugger->core->readRegister(debugger->core, name, value)) {
return true;
}
return false;

View File

@ -60,6 +60,23 @@ static const struct mCoreMemoryBlock _GBCMemoryBlocks[] = {
{ GB_BASE_HRAM, "hram", "HRAM", "High RAM", GB_BASE_HRAM, GB_BASE_HRAM + GB_SIZE_HRAM, GB_SIZE_HRAM, mCORE_MEMORY_RW | mCORE_MEMORY_MAPPED },
};
static const struct mCoreRegisterInfo _GBRegisters[] = {
{ "b", NULL, 1, 0xFF, mCORE_REGISTER_GPR },
{ "c", NULL, 1, 0xFF, mCORE_REGISTER_GPR },
{ "d", NULL, 1, 0xFF, mCORE_REGISTER_GPR },
{ "e", NULL, 1, 0xFF, mCORE_REGISTER_GPR },
{ "h", NULL, 1, 0xFF, mCORE_REGISTER_GPR },
{ "l", NULL, 1, 0xFF, mCORE_REGISTER_GPR },
{ "a", NULL, 1, 0xFF, mCORE_REGISTER_GPR },
{ "f", NULL, 1, 0xF0, mCORE_REGISTER_GPR },
{ "bc", NULL, 2, 0xFFFF, mCORE_REGISTER_GPR },
{ "de", NULL, 2, 0xFFFF, mCORE_REGISTER_GPR },
{ "hl", NULL, 2, 0xFFFF, mCORE_REGISTER_GPR },
{ "af", NULL, 2, 0xFFF0, mCORE_REGISTER_GPR },
{ "pc", NULL, 2, 0xFFFF, mCORE_REGISTER_GPR },
{ "sp", NULL, 2, 0xFFFF, mCORE_REGISTER_GPR },
};
struct mVideoLogContext;
struct GBCore {
struct mCore d;
@ -837,6 +854,141 @@ void* _GBGetMemoryBlock(struct mCore* core, size_t id, size_t* sizeOut) {
}
}
static size_t _GBCoreListRegisters(const struct mCore* core, const struct mCoreRegisterInfo** list) {
UNUSED(core);
*list = _GBRegisters;
return sizeof(_GBRegisters) / sizeof(*_GBRegisters);
}
static bool _GBCoreReadRegister(const struct mCore* core, const char* name, void* out) {
struct SM83Core* cpu = core->cpu;
uint16_t* value16 = out;
uint8_t* value8 = out;
if (strcmp(name, "b") == 0) {
*value8 = cpu->b;
return true;
}
if (strcmp(name, "c") == 0) {
*value8 = cpu->c;
return true;
}
if (strcmp(name, "d") == 0) {
*value8 = cpu->d;
return true;
}
if (strcmp(name, "e") == 0) {
*value8 = cpu->e;
return true;
}
if (strcmp(name, "a") == 0) {
*value8 = cpu->a;
return true;
}
if (strcmp(name, "f") == 0) {
*value8 = cpu->f.packed;
return true;
}
if (strcmp(name, "h") == 0) {
*value8 = cpu->h;
return true;
}
if (strcmp(name, "l") == 0) {
*value8 = cpu->l;
return true;
}
if (strcmp(name, "bc") == 0) {
*value16 = cpu->bc;
return true;
}
if (strcmp(name, "de") == 0) {
*value16 = cpu->de;
return true;
}
if (strcmp(name, "hl") == 0) {
*value16 = cpu->hl;
return true;
}
if (strcmp(name, "af") == 0) {
*value16 = cpu->af;
return true;
}
if (strcmp(name, "pc") == 0) {
*value16 = cpu->pc;
return true;
}
if (strcmp(name, "sp") == 0) {
*value16 = cpu->sp;
return true;
}
return false;
}
static bool _GBCoreWriteRegister(struct mCore* core, const char* name, const void* in) {
struct SM83Core* cpu = core->cpu;
uint32_t value = *(uint32_t*) in;
if (strcmp(name, "b") == 0) {
cpu->b = value;
return true;
}
if (strcmp(name, "c") == 0) {
cpu->c = value;
return true;
}
if (strcmp(name, "d") == 0) {
cpu->d = value;
return true;
}
if (strcmp(name, "e") == 0) {
cpu->e = value;
return true;
}
if (strcmp(name, "h") == 0) {
cpu->h = value;
return true;
}
if (strcmp(name, "l") == 0) {
cpu->l = value;
return true;
}
if (strcmp(name, "a") == 0) {
cpu->a = value;
return true;
}
if (strcmp(name, "f") == 0) {
cpu->f.packed = value & 0xF0;
return true;
}
if (strcmp(name, "bc") == 0) {
cpu->bc = value;
return true;
}
if (strcmp(name, "de") == 0) {
cpu->de = value;
return true;
}
if (strcmp(name, "hl") == 0) {
cpu->hl = value;
return true;
}
if (strcmp(name, "af") == 0) {
cpu->af = value;
cpu->f.packed &= 0xF0;
return true;
}
if (strcmp(name, "pc") == 0) {
cpu->pc = value;
cpu->memory.setActiveRegion(cpu, cpu->pc);
return true;
}
if (strcmp(name, "sp") == 0) {
cpu->sp = value;
return true;
}
return false;
}
#ifdef USE_DEBUGGERS
static bool _GBCoreSupportsDebuggerType(struct mCore* core, enum mDebuggerType type) {
UNUSED(core);
@ -1117,6 +1269,9 @@ struct mCore* GBCoreCreate(void) {
core->rawWrite32 = _GBCoreRawWrite32;
core->listMemoryBlocks = _GBListMemoryBlocks;
core->getMemoryBlock = _GBGetMemoryBlock;
core->listRegisters = _GBCoreListRegisters;
core->readRegister = _GBCoreReadRegister;
core->writeRegister = _GBCoreWriteRegister;
#ifdef USE_DEBUGGERS
core->supportsDebuggerType = _GBCoreSupportsDebuggerType;
core->debuggerPlatform = _GBCoreDebuggerPlatform;

View File

@ -8,6 +8,7 @@
#include <mgba/core/core.h>
#include <mgba/core/log.h>
#include <mgba/internal/arm/debugger/debugger.h>
#include <mgba/internal/arm/isa-inlines.h>
#include <mgba/internal/debugger/symbols.h>
#include <mgba/internal/gba/cheats.h>
#include <mgba/internal/gba/gba.h>
@ -32,6 +33,7 @@
#include <mgba-util/memory.h>
#include <mgba-util/patch.h>
#include <mgba-util/vfs.h>
#include <errno.h>
static const struct mCoreChannelInfo _GBAVideoLayers[] = {
{ GBA_LAYER_BG0, "bg0", "Background 0", NULL },
@ -127,6 +129,32 @@ static const struct mCoreMemoryBlock _GBAMemoryBlocksEEPROM[] = {
{ REGION_CART_SRAM_MIRROR, "eeprom", "EEPROM", "EEPROM (8kiB)", 0, SIZE_CART_EEPROM, SIZE_CART_EEPROM, mCORE_MEMORY_RW },
};
static const struct mCoreRegisterInfo _GBARegisters[] = {
{ "r0", NULL, 4, 0xFFFFFFFF, mCORE_REGISTER_GPR },
{ "r1", NULL, 4, 0xFFFFFFFF, mCORE_REGISTER_GPR },
{ "r2", NULL, 4, 0xFFFFFFFF, mCORE_REGISTER_GPR },
{ "r3", NULL, 4, 0xFFFFFFFF, mCORE_REGISTER_GPR },
{ "r4", NULL, 4, 0xFFFFFFFF, mCORE_REGISTER_GPR },
{ "r5", NULL, 4, 0xFFFFFFFF, mCORE_REGISTER_GPR },
{ "r6", NULL, 4, 0xFFFFFFFF, mCORE_REGISTER_GPR },
{ "r7", NULL, 4, 0xFFFFFFFF, mCORE_REGISTER_GPR },
{ "r8", NULL, 4, 0xFFFFFFFF, mCORE_REGISTER_GPR },
{ "r9", NULL, 4, 0xFFFFFFFF, mCORE_REGISTER_GPR },
{ "r10", NULL, 4, 0xFFFFFFFF, mCORE_REGISTER_GPR },
{ "r11", NULL, 4, 0xFFFFFFFF, mCORE_REGISTER_GPR },
{ "r12", (const char*[]) { "ip", NULL }, 4, 0xFFFFFFFF, mCORE_REGISTER_GPR },
{ "sp", (const char*[]) { "r13", NULL }, 4, 0xFFFFFFFF, mCORE_REGISTER_GPR },
{ "lr", (const char*[]) { "r14", NULL }, 4, 0xFFFFFFFF, mCORE_REGISTER_GPR },
{ "pc", (const char*[]) { "r15", NULL }, 4, 0xFFFFFFFF, mCORE_REGISTER_GPR },
{ "cpsr", NULL, 4, 0xF00000FF, mCORE_REGISTER_FLAGS },
{ "spsr", NULL, 4, 0xF00000FF, mCORE_REGISTER_FLAGS },
{ "spsr_irq", NULL, 4, 0xF00000FF, mCORE_REGISTER_FLAGS },
{ "spsr_fiq", NULL, 4, 0xF00000FF, mCORE_REGISTER_FLAGS },
{ "spsr_svc", NULL, 4, 0xF00000FF, mCORE_REGISTER_FLAGS },
{ "spsr_abt", NULL, 4, 0xF00000FF, mCORE_REGISTER_FLAGS },
{ "spsr_und", NULL, 4, 0xF00000FF, mCORE_REGISTER_FLAGS },
};
struct mVideoLogContext;
#define CPU_COMPONENT_AUDIO_MIXER CPU_COMPONENT_MISC_1
@ -839,7 +867,7 @@ static void _GBACoreRawWrite32(struct mCore* core, uint32_t address, int segment
GBAPatch32(cpu, address, value, NULL);
}
size_t _GBAListMemoryBlocks(const struct mCore* core, const struct mCoreMemoryBlock** blocks) {
size_t _GBACoreListMemoryBlocks(const struct mCore* core, const struct mCoreMemoryBlock** blocks) {
const struct GBA* gba = core->board;
switch (gba->memory.savedata.type) {
case SAVEDATA_SRAM:
@ -860,7 +888,7 @@ size_t _GBAListMemoryBlocks(const struct mCore* core, const struct mCoreMemoryBl
}
}
void* _GBAGetMemoryBlock(struct mCore* core, size_t id, size_t* sizeOut) {
void* _GBACoreGetMemoryBlock(struct mCore* core, size_t id, size_t* sizeOut) {
struct GBA* gba = core->board;
switch (id) {
default:
@ -900,6 +928,137 @@ void* _GBAGetMemoryBlock(struct mCore* core, size_t id, size_t* sizeOut) {
}
}
static size_t _GBACoreListRegisters(const struct mCore* core, const struct mCoreRegisterInfo** list) {
UNUSED(core);
*list = _GBARegisters;
return sizeof(_GBARegisters) / sizeof(*_GBARegisters);
}
static bool _GBACoreReadRegister(const struct mCore* core, const char* name, void* out) {
struct ARMCore* cpu = core->cpu;
int32_t* value = out;
switch (name[0]) {
case 'r':
case 'R':
++name;
break;
case 'c':
case 'C':
if (strcmp(name, "cpsr") == 0 || strcmp(name, "CPSR") == 0) {
*value = cpu->cpsr.packed;
_ARMReadCPSR(cpu);
return true;
}
return false;
case 'i':
case 'I':
if (strcmp(name, "ip") == 0 || strcmp(name, "IP") == 0) {
*value = cpu->gprs[12];
return true;
}
return false;
case 's':
case 'S':
if (strcmp(name, "sp") == 0 || strcmp(name, "SP") == 0) {
*value = cpu->gprs[ARM_SP];
return true;
}
// TODO: SPSR
return false;
case 'l':
case 'L':
if (strcmp(name, "lr") == 0 || strcmp(name, "LR") == 0) {
*value = cpu->gprs[ARM_LR];
return true;
}
return false;
case 'p':
case 'P':
if (strcmp(name, "pc") == 0 || strcmp(name, "PC") == 0) {
*value = cpu->gprs[ARM_PC];
return true;
}
return false;
default:
return false;
}
char* parseEnd;
errno = 0;
unsigned long regId = strtoul(name, &parseEnd, 10);
if (errno || regId > 15 || *parseEnd) {
return false;
}
*value = cpu->gprs[regId];
return true;
}
static bool _GBACoreWriteRegister(struct mCore* core, const char* name, const void* in) {
struct ARMCore* cpu = core->cpu;
int32_t value = *(const int32_t*) in;
switch (name[0]) {
case 'r':
case 'R':
++name;
break;
case 'c':
case 'C':
if (strcmp(name, "cpsr") == 0) {
cpu->cpsr.packed = value & 0xF00000FF;
_ARMReadCPSR(cpu);
return true;
}
return false;
case 'i':
case 'I':
if (strcmp(name, "ip") == 0 || strcmp(name, "IP") == 0) {
cpu->gprs[12] = value;
return true;
}
return false;
case 's':
case 'S':
if (strcmp(name, "sp") == 0 || strcmp(name, "SP") == 0) {
cpu->gprs[ARM_SP] = value;
return true;
}
// TODO: SPSR
return false;
case 'l':
case 'L':
if (strcmp(name, "lr") == 0 || strcmp(name, "LR") == 0) {
cpu->gprs[ARM_LR] = value;
return true;
}
return false;
case 'p':
case 'P':
if (strcmp(name, "pc") == 0 || strcmp(name, "PC") == 0) {
name = "15";
break;
}
return false;
default:
return false;
}
char* parseEnd;
errno = 0;
unsigned long regId = strtoul(name, &parseEnd, 10);
if (errno || regId > 15 || *parseEnd) {
return false;
}
cpu->gprs[regId] = value;
if (regId == ARM_PC) {
if (cpu->cpsr.t) {
ThumbWritePC(cpu);
} else {
ARMWritePC(cpu);
}
}
return true;
}
#ifdef USE_DEBUGGERS
static bool _GBACoreSupportsDebuggerType(struct mCore* core, enum mDebuggerType type) {
UNUSED(core);
@ -1233,8 +1392,11 @@ struct mCore* GBACoreCreate(void) {
core->rawWrite8 = _GBACoreRawWrite8;
core->rawWrite16 = _GBACoreRawWrite16;
core->rawWrite32 = _GBACoreRawWrite32;
core->listMemoryBlocks = _GBAListMemoryBlocks;
core->getMemoryBlock = _GBAGetMemoryBlock;
core->listMemoryBlocks = _GBACoreListMemoryBlocks;
core->getMemoryBlock = _GBACoreGetMemoryBlock;
core->listRegisters = _GBACoreListRegisters;
core->readRegister = _GBACoreReadRegister;
core->writeRegister = _GBACoreWriteRegister;
#ifdef USE_DEBUGGERS
core->supportsDebuggerType = _GBACoreSupportsDebuggerType;
core->debuggerPlatform = _GBACoreDebuggerPlatform;

View File

@ -72,8 +72,6 @@ static void SM83DebuggerListWatchpoints(struct mDebuggerPlatform*, struct mWatch
static void SM83DebuggerCheckBreakpoints(struct mDebuggerPlatform*);
static bool SM83DebuggerHasBreakpoints(struct mDebuggerPlatform*);
static void SM83DebuggerTrace(struct mDebuggerPlatform*, char* out, size_t* length);
static bool SM83DebuggerGetRegister(struct mDebuggerPlatform*, const char* name, int32_t* value);
static bool SM83DebuggerSetRegister(struct mDebuggerPlatform*, const char* name, int32_t value);
struct mDebuggerPlatform* SM83DebuggerPlatformCreate(void) {
struct SM83Debugger* platform = malloc(sizeof(struct SM83Debugger));
@ -88,8 +86,6 @@ struct mDebuggerPlatform* SM83DebuggerPlatformCreate(void) {
platform->d.checkBreakpoints = SM83DebuggerCheckBreakpoints;
platform->d.hasBreakpoints = SM83DebuggerHasBreakpoints;
platform->d.trace = SM83DebuggerTrace;
platform->d.getRegister = SM83DebuggerGetRegister;
platform->d.setRegister = SM83DebuggerSetRegister;
platform->d.getStackTraceMode = NULL;
platform->d.setStackTraceMode = NULL;
platform->d.updateStackTrace = NULL;
@ -227,131 +223,3 @@ static void SM83DebuggerTrace(struct mDebuggerPlatform* d, char* out, size_t* le
cpu->d, cpu->e, cpu->h, cpu->l,
cpu->sp, cpu->memory.currentSegment(cpu, cpu->pc), cpu->pc, disassembly);
}
bool SM83DebuggerGetRegister(struct mDebuggerPlatform* d, const char* name, int32_t* value) {
struct SM83Debugger* debugger = (struct SM83Debugger*) d;
struct SM83Core* cpu = debugger->cpu;
if (strcmp(name, "a") == 0) {
*value = cpu->a;
return true;
}
if (strcmp(name, "b") == 0) {
*value = cpu->b;
return true;
}
if (strcmp(name, "c") == 0) {
*value = cpu->c;
return true;
}
if (strcmp(name, "d") == 0) {
*value = cpu->d;
return true;
}
if (strcmp(name, "e") == 0) {
*value = cpu->e;
return true;
}
if (strcmp(name, "h") == 0) {
*value = cpu->h;
return true;
}
if (strcmp(name, "l") == 0) {
*value = cpu->l;
return true;
}
if (strcmp(name, "bc") == 0) {
*value = cpu->bc;
return true;
}
if (strcmp(name, "de") == 0) {
*value = cpu->de;
return true;
}
if (strcmp(name, "hl") == 0) {
*value = cpu->hl;
return true;
}
if (strcmp(name, "af") == 0) {
*value = cpu->af;
return true;
}
if (strcmp(name, "pc") == 0) {
*value = cpu->pc;
return true;
}
if (strcmp(name, "sp") == 0) {
*value = cpu->sp;
return true;
}
if (strcmp(name, "f") == 0) {
*value = cpu->f.packed;
return true;
}
return false;
}
bool SM83DebuggerSetRegister(struct mDebuggerPlatform* d, const char* name, int32_t value) {
struct SM83Debugger* debugger = (struct SM83Debugger*) d;
struct SM83Core* cpu = debugger->cpu;
if (strcmp(name, "a") == 0) {
cpu->a = value;
return true;
}
if (strcmp(name, "b") == 0) {
cpu->b = value;
return true;
}
if (strcmp(name, "c") == 0) {
cpu->c = value;
return true;
}
if (strcmp(name, "d") == 0) {
cpu->d = value;
return true;
}
if (strcmp(name, "e") == 0) {
cpu->e = value;
return true;
}
if (strcmp(name, "h") == 0) {
cpu->h = value;
return true;
}
if (strcmp(name, "l") == 0) {
cpu->l = value;
return true;
}
if (strcmp(name, "bc") == 0) {
cpu->bc = value;
return true;
}
if (strcmp(name, "de") == 0) {
cpu->de = value;
return true;
}
if (strcmp(name, "hl") == 0) {
cpu->hl = value;
return true;
}
if (strcmp(name, "af") == 0) {
cpu->af = value;
cpu->f.packed &= 0xF0;
return true;
}
if (strcmp(name, "pc") == 0) {
cpu->pc = value;
cpu->memory.setActiveRegion(cpu, cpu->pc);
return true;
}
if (strcmp(name, "sp") == 0) {
cpu->sp = value;
return true;
}
if (strcmp(name, "f") == 0) {
cpu->f.packed = value & 0xF0;
return true;
}
return false;
}