From a70a6cca5a29b1711dcd3dc0ee15a9ffad8f45d0 Mon Sep 17 00:00:00 2001 From: Rosalie Wanders Date: Sun, 9 Feb 2025 14:23:13 +0100 Subject: [PATCH] Implement register mirroring --- src/device/rcp/ai/ai_controller.c | 7 +++++-- src/device/rcp/ai/ai_controller.h | 2 +- src/device/rcp/mi/mi_controller.h | 2 +- src/device/rcp/pi/pi_controller.c | 8 ++++++-- src/device/rcp/pi/pi_controller.h | 2 +- src/device/rcp/rdp/rdp_core.c | 10 ++++++++-- src/device/rcp/rdp/rdp_core.h | 4 ++-- src/device/rcp/ri/ri_controller.h | 2 +- src/device/rcp/rsp/rsp_core.c | 7 ++++--- src/device/rcp/rsp/rsp_core.h | 4 ++-- src/device/rcp/si/si_controller.c | 5 ++++- src/device/rcp/si/si_controller.h | 2 +- src/device/rcp/vi/vi_controller.c | 10 ++++++++-- src/device/rcp/vi/vi_controller.h | 2 +- src/device/rdram/rdram.c | 10 +++++++++- 15 files changed, 54 insertions(+), 23 deletions(-) diff --git a/src/device/rcp/ai/ai_controller.c b/src/device/rcp/ai/ai_controller.c index bc46a5f75..c494f5c1a 100644 --- a/src/device/rcp/ai/ai_controller.c +++ b/src/device/rcp/ai/ai_controller.c @@ -180,7 +180,7 @@ void read_ai_regs(void* opaque, uint32_t address, uint32_t* value) ai->last_read = *value; } } - else + else if (reg < AI_REGS_COUNT) { *value = ai->regs[reg]; } @@ -216,7 +216,10 @@ void write_ai_regs(void* opaque, uint32_t address, uint32_t value, uint32_t mask return; } - masked_write(&ai->regs[reg], value, mask); + if (reg < AI_REGS_COUNT) + { + masked_write(&ai->regs[reg], value, mask); + } } void ai_end_of_dma_event(void* opaque) diff --git a/src/device/rcp/ai/ai_controller.h b/src/device/rcp/ai/ai_controller.h index 6b2217cfc..fcaf74f54 100644 --- a/src/device/rcp/ai/ai_controller.h +++ b/src/device/rcp/ai/ai_controller.h @@ -71,7 +71,7 @@ struct ai_controller static osal_inline uint32_t ai_reg(uint32_t address) { - return (address & 0xffff) >> 2; + return (address & 0x1f) >> 2; } void init_ai(struct ai_controller* ai, diff --git a/src/device/rcp/mi/mi_controller.h b/src/device/rcp/mi/mi_controller.h index 5098e5d89..9c0861bd5 100644 --- a/src/device/rcp/mi/mi_controller.h +++ b/src/device/rcp/mi/mi_controller.h @@ -57,7 +57,7 @@ struct mi_controller static osal_inline uint32_t mi_reg(uint32_t address) { - return (address & 0xffff) >> 2; + return (address & 0xf) >> 2; } void init_mi(struct mi_controller* mi, struct r4300_core* r4300); diff --git a/src/device/rcp/pi/pi_controller.c b/src/device/rcp/pi/pi_controller.c index 0fc36bf3d..904341ccc 100644 --- a/src/device/rcp/pi/pi_controller.c +++ b/src/device/rcp/pi/pi_controller.c @@ -153,7 +153,8 @@ void read_pi_regs(void* opaque, uint32_t address, uint32_t* value) struct pi_controller* pi = (struct pi_controller*)opaque; uint32_t reg = pi_reg(address); - *value = pi->regs[reg]; + if (reg < PI_REGS_COUNT) + *value = pi->regs[reg]; if (reg == PI_WR_LEN_REG || reg == PI_RD_LEN_REG) *value = 0x7F; @@ -209,7 +210,10 @@ void write_pi_regs(void* opaque, uint32_t address, uint32_t value, uint32_t mask return; } - masked_write(&pi->regs[reg], value, mask); + if (reg < PI_REGS_COUNT) + { + masked_write(&pi->regs[reg], value, mask); + } } void pi_end_of_dma_event(void* opaque) diff --git a/src/device/rcp/pi/pi_controller.h b/src/device/rcp/pi/pi_controller.h index 8f2dafdd7..c95d7c8ae 100644 --- a/src/device/rcp/pi/pi_controller.h +++ b/src/device/rcp/pi/pi_controller.h @@ -87,7 +87,7 @@ struct pi_controller static osal_inline uint32_t pi_reg(uint32_t address) { - return (address & 0xffff) >> 2; + return (address & 0x3f) >> 2; } diff --git a/src/device/rcp/rdp/rdp_core.c b/src/device/rcp/rdp/rdp_core.c index f091801bd..3063aa1b9 100644 --- a/src/device/rcp/rdp/rdp_core.c +++ b/src/device/rcp/rdp/rdp_core.c @@ -128,7 +128,10 @@ void read_dps_regs(void* opaque, uint32_t address, uint32_t* value) struct rdp_core* dp = (struct rdp_core*)opaque; uint32_t reg = dps_reg(address); - *value = dp->dps_regs[reg]; + if (reg < DPS_REGS_COUNT) + { + *value = dp->dps_regs[reg]; + } } void write_dps_regs(void* opaque, uint32_t address, uint32_t value, uint32_t mask) @@ -136,7 +139,10 @@ void write_dps_regs(void* opaque, uint32_t address, uint32_t value, uint32_t mas struct rdp_core* dp = (struct rdp_core*)opaque; uint32_t reg = dps_reg(address); - masked_write(&dp->dps_regs[reg], value, mask); + if (reg < DPS_REGS_COUNT) + { + masked_write(&dp->dps_regs[reg], value, mask); + } } void rdp_interrupt_event(void* opaque) diff --git a/src/device/rcp/rdp/rdp_core.h b/src/device/rcp/rdp/rdp_core.h index d679e04c5..57997a1b5 100644 --- a/src/device/rcp/rdp/rdp_core.h +++ b/src/device/rcp/rdp/rdp_core.h @@ -95,12 +95,12 @@ struct rdp_core static osal_inline uint32_t dpc_reg(uint32_t address) { - return (address & 0xffff) >> 2; + return (address & 0x1f) >> 2; } static osal_inline uint32_t dps_reg(uint32_t address) { - return (address & 0xffff) >> 2; + return (address & 0x1f) >> 2; } void init_rdp(struct rdp_core* dp, diff --git a/src/device/rcp/ri/ri_controller.h b/src/device/rcp/ri/ri_controller.h index 940fa80e5..7cf2eac91 100644 --- a/src/device/rcp/ri/ri_controller.h +++ b/src/device/rcp/ri/ri_controller.h @@ -51,7 +51,7 @@ struct ri_controller static osal_inline uint32_t ri_reg(uint32_t address) { - return (address & 0xffff) >> 2; + return (address & 0x1f) >> 2; } static osal_inline uint16_t ri_address_to_id_field(uint32_t address) diff --git a/src/device/rcp/rsp/rsp_core.c b/src/device/rcp/rsp/rsp_core.c index 550d9bb07..99767bc03 100644 --- a/src/device/rcp/rsp/rsp_core.c +++ b/src/device/rcp/rsp/rsp_core.c @@ -304,11 +304,11 @@ void read_rsp_regs2(void* opaque, uint32_t address, uint32_t* value) struct rsp_core* sp = (struct rsp_core*)opaque; uint32_t reg = rsp_reg2(address); - *value = sp->regs2[reg]; + if (reg < SP_REGS2_COUNT) + *value = sp->regs2[reg]; if (reg == SP_PC_REG) *value &= 0xffc; - } void write_rsp_regs2(void* opaque, uint32_t address, uint32_t value, uint32_t mask) @@ -319,7 +319,8 @@ void write_rsp_regs2(void* opaque, uint32_t address, uint32_t value, uint32_t ma if (reg == SP_PC_REG) mask &= 0xffc; - masked_write(&sp->regs2[reg], value, mask); + if (reg < SP_REGS2_COUNT) + masked_write(&sp->regs2[reg], value, mask); } void do_SP_Task(struct rsp_core* sp) diff --git a/src/device/rcp/rsp/rsp_core.h b/src/device/rcp/rsp/rsp_core.h index 2d067cfbc..7db69239b 100644 --- a/src/device/rcp/rsp/rsp_core.h +++ b/src/device/rcp/rsp/rsp_core.h @@ -111,12 +111,12 @@ static osal_inline uint32_t rsp_mem_address(uint32_t address) static osal_inline uint32_t rsp_reg(uint32_t address) { - return (address & 0xffff) >> 2; + return (address & 0x1f) >> 2; } static osal_inline uint32_t rsp_reg2(uint32_t address) { - return (address & 0xffff) >> 2; + return (address & 0x1f) >> 2; } void init_rsp(struct rsp_core* sp, diff --git a/src/device/rcp/si/si_controller.c b/src/device/rcp/si/si_controller.c index c35de3745..0019769b1 100644 --- a/src/device/rcp/si/si_controller.c +++ b/src/device/rcp/si/si_controller.c @@ -123,7 +123,10 @@ void read_si_regs(void* opaque, uint32_t address, uint32_t* value) struct si_controller* si = (struct si_controller*)opaque; uint32_t reg = si_reg(address); - *value = si->regs[reg]; + if (reg < SI_REGS_COUNT) + { + *value = si->regs[reg]; + } } void write_si_regs(void* opaque, uint32_t address, uint32_t value, uint32_t mask) diff --git a/src/device/rcp/si/si_controller.h b/src/device/rcp/si/si_controller.h index 01a371f1d..1b22433a6 100644 --- a/src/device/rcp/si/si_controller.h +++ b/src/device/rcp/si/si_controller.h @@ -72,7 +72,7 @@ struct si_controller static osal_inline uint32_t si_reg(uint32_t address) { - return (address & 0xffff) >> 2; + return (address & 0x1f) >> 2; } diff --git a/src/device/rcp/vi/vi_controller.c b/src/device/rcp/vi/vi_controller.c index 4cd3abb6a..b644fcd76 100644 --- a/src/device/rcp/vi/vi_controller.c +++ b/src/device/rcp/vi/vi_controller.c @@ -105,7 +105,10 @@ void read_vi_regs(void* opaque, uint32_t address, uint32_t* value) vi->regs[VI_CURRENT_REG] = (vi->regs[VI_CURRENT_REG] & (~1)) | vi->field; } - *value = vi->regs[reg]; + if (reg < VI_REGS_COUNT) + { + *value = vi->regs[reg]; + } } void write_vi_regs(void* opaque, uint32_t address, uint32_t value, uint32_t mask) @@ -151,7 +154,10 @@ void write_vi_regs(void* opaque, uint32_t address, uint32_t value, uint32_t mask return; } - masked_write(&vi->regs[reg], value, mask); + if (reg < VI_REGS_COUNT) + { + masked_write(&vi->regs[reg], value, mask); + } } void vi_vertical_interrupt_event(void* opaque) diff --git a/src/device/rcp/vi/vi_controller.h b/src/device/rcp/vi/vi_controller.h index efa575d3e..6309b00b7 100644 --- a/src/device/rcp/vi/vi_controller.h +++ b/src/device/rcp/vi/vi_controller.h @@ -64,7 +64,7 @@ struct vi_controller static osal_inline uint32_t vi_reg(uint32_t address) { - return (address & 0xffff) >> 2; + return (address & 0x3f) >> 2; } diff --git a/src/device/rdram/rdram.c b/src/device/rdram/rdram.c index 28065eaf0..d36192be4 100644 --- a/src/device/rdram/rdram.c +++ b/src/device/rdram/rdram.c @@ -173,7 +173,11 @@ void read_rdram_regs(void* opaque, uint32_t address, uint32_t* value) return; } - *value = rdram->regs[module][reg]; + if (reg < RDRAM_REGS_COUNT) { + *value = rdram->regs[module][reg]; + } else { + *value = 0; + } /* some bits are inverted when read */ if (reg == RDRAM_MODE_REG) { @@ -188,6 +192,10 @@ void write_rdram_regs(void* opaque, uint32_t address, uint32_t value, uint32_t m size_t module; size_t modules = get_modules_count(rdram); + if (reg >= RDRAM_REGS_COUNT) { + return; + } + /* HACK: Detect when current Control calibration is about to start, * so we can set corrupted rdram_dram handler */