From b2eb65b3d4068580557c979dfc1046d3d5b1b6f9 Mon Sep 17 00:00:00 2001 From: dragonmux Date: Sat, 11 Feb 2023 09:02:25 +0000 Subject: [PATCH] riscv_debug: Implemented regs_write for both rv32 and rv64 --- src/target/riscv32.c | 17 +++++++++++++++++ src/target/riscv64.c | 17 +++++++++++++++++ 2 files changed, 34 insertions(+) diff --git a/src/target/riscv32.c b/src/target/riscv32.c index da3b11eb481..08c7d0534bd 100644 --- a/src/target/riscv32.c +++ b/src/target/riscv32.c @@ -68,6 +68,7 @@ typedef struct riscv32_regs { #define RV32_MATCH_AFTER 0x00040000U static void riscv32_regs_read(target_s *target, void *data); +static void riscv32_regs_write(target_s *target, const void *data); static void riscv32_mem_read(target_s *target, void *dest, target_addr_t src, size_t len); static int riscv32_breakwatch_set(target_s *target, breakwatch_s *breakwatch); @@ -88,6 +89,7 @@ bool riscv32_probe(target_s *const target) /* Provide the length of a suitable registers structure */ target->regs_size = sizeof(riscv32_regs_s); target->regs_read = riscv32_regs_read; + target->regs_write = riscv32_regs_write; target->mem_read = riscv32_mem_read; target->breakwatch_set = riscv32_breakwatch_set; @@ -122,6 +124,21 @@ static void riscv32_regs_read(target_s *const target, void *const data) riscv_csr_read(hart, RV_DPC, ®s->pc); } +static void riscv32_regs_write(target_s *const target, const void *const data) +{ + /* Grab the hart structure and figure out how many registers need reading out */ + riscv_hart_s *const hart = riscv_hart_struct(target); + riscv32_regs_s *const regs = (riscv32_regs_s *)data; + const size_t gprs_count = hart->extensions & RV_ISA_EXT_EMBEDDED ? 16U : 32U; + /* Loop through writing out the GPRs, except for the first which is always 0 */ + for (size_t gpr = 1; gpr < gprs_count; ++gpr) { + // TODO: handle when this fails.. + riscv_csr_write(hart, RV_GPR_BASE + gpr, ®s->gprs[gpr]); + } + /* Special access to poke in the program counter that will be executed on resuming the hart */ + riscv_csr_write(hart, RV_DPC, ®s->pc); +} + /* Takes in data from abstract command arg0 and, based on the access width, unpacks it to dest */ void riscv32_unpack_data(void *const dest, const uint32_t data, const uint8_t access_width) { diff --git a/src/target/riscv64.c b/src/target/riscv64.c index 2f21551c87a..c156fa8c450 100644 --- a/src/target/riscv64.c +++ b/src/target/riscv64.c @@ -43,6 +43,7 @@ typedef struct riscv64_regs { } riscv64_regs_s; static void riscv64_regs_read(target_s *target, void *data); +static void riscv64_regs_write(target_s *target, const void *data); static void riscv64_mem_read(target_s *target, void *dest, target_addr_t src, size_t len); bool riscv64_probe(target_s *const target) @@ -52,6 +53,7 @@ bool riscv64_probe(target_s *const target) /* Provide the length of a suitable registers structure */ target->regs_size = sizeof(riscv64_regs_s); target->regs_read = riscv64_regs_read; + target->regs_write = riscv64_regs_write; target->mem_read = riscv64_mem_read; return true; @@ -72,6 +74,21 @@ static void riscv64_regs_read(target_s *const target, void *const data) riscv_csr_read(hart, RV_DPC, ®s->pc); } +static void riscv64_regs_write(target_s *const target, const void *const data) +{ + /* Grab the hart structure and figure out how many registers need reading out */ + riscv_hart_s *const hart = riscv_hart_struct(target); + riscv64_regs_s *const regs = (riscv64_regs_s *)data; + const size_t gprs_count = hart->extensions & RV_ISA_EXT_EMBEDDED ? 16U : 32U; + /* Loop through writing out the GPRs, except for the first which is always 0 */ + for (size_t gpr = 1; gpr < gprs_count; ++gpr) { + // TODO: handle when this fails.. + riscv_csr_write(hart, RV_GPR_BASE + gpr, ®s->gprs[gpr]); + } + /* Special access to poke in the program counter that will be executed on resuming the hart */ + riscv_csr_write(hart, RV_DPC, ®s->pc); +} + /* Takes in data from abstract command arg0 and, based on the access width, unpacks it to dest */ void riscv64_unpack_data( void *const dest, const uint32_t data_low, const uint32_t data_high, const uint8_t access_width)