@@ -72,6 +72,8 @@ static ssize_t riscv32_reg_read(target_s *target, uint32_t c, void *data, size_t
7272static ssize_t riscv32_reg_write (target_s * target , uint32_t c , const void * data , size_t max );
7373static void riscv32_regs_read (target_s * target , void * data );
7474static void riscv32_regs_write (target_s * target , const void * data );
75+ static void riscv32_mem_read (target_s * target , void * dest , target_addr_t src , size_t len );
76+ static void riscv32_mem_write (target_s * target , target_addr_t dest , const void * src , size_t len );
7577
7678static int riscv32_breakwatch_set (target_s * target , breakwatch_s * breakwatch );
7779static int riscv32_breakwatch_clear (target_s * target , breakwatch_s * breakwatch );
@@ -548,7 +550,139 @@ static void riscv32_sysbus_mem_write(
548550 riscv32_sysbus_mem_adjusted_write (hart , address , data , remainder , native_access_width , native_access_length );
549551}
550552
551- void riscv32_mem_read (target_s * const target , void * const dest , const target_addr_t src , const size_t len )
553+ static void riscv32_abstract_progbuf_mem_read (
554+ riscv_hart_s * const hart , void * const dest , const target_addr_t src , const size_t len )
555+ {
556+ if (!(hart -> extensions & RV_ISA_EXT_COMPRESSED )) {
557+ DEBUG_ERROR ("This target does not implement the compressed ISA extension\n" );
558+ return ;
559+ }
560+
561+ /* Figure out the maximal width of access to perform, up to the bitness of the target */
562+ const uint8_t access_width = riscv_mem_access_width (hart , src , len );
563+ // const uint8_t access_length = 1U << access_width;
564+ // /* Build the access command */
565+ // const uint32_t command = RV_DM_ABST_CMD_ACCESS_MEM | RV_ABST_READ | (access_width << RV_ABST_MEM_ACCESS_SHIFT) |
566+ // (access_length < len ? RV_ABST_MEM_ADDR_POST_INC : 0U);
567+ // /* Write the address to read to arg1 */
568+ // if (!riscv_dm_write(hart->dbg_module, RV_DM_DATA1, src))
569+ // return;
570+ // uint8_t *const data = (uint8_t *)dest;
571+ // for (size_t offset = 0; offset < len; offset += access_length) {
572+ // /* Execute the read */
573+ // if (!riscv_dm_write(hart->dbg_module, RV_DM_ABST_COMMAND, command) || !riscv_command_wait_complete(hart))
574+ // return;
575+ // /* Extract back the data from arg0 */
576+ // uint32_t value = 0;
577+ // if (!riscv_dm_read(hart->dbg_module, RV_DM_DATA0, &value))
578+ // return;
579+ // riscv32_unpack_data(data + offset, value, access_width);
580+ // }
581+
582+ /* Disable auto-exec */
583+ // if (!riscv_dm_write(hart->dbg_module, RV_DM_ABST_AUTO, 0))
584+ // return;
585+
586+ /*
587+ * progbuf 0
588+ * c.lw x8,0(x11) // Pull the address from DATA1
589+ * c.lw x9,0(x8) // Read the data at that location
590+ */
591+ if (!riscv_dm_write (hart -> dbg_module , RV_DM_PROGBUF0 , 0x40044180U ))
592+ return ;
593+
594+ /*
595+ * progbuf 1
596+ * c.nop // alternately, `c.addi x8, 4` , for auto-increment (0xc1040411)
597+ * c.sw x9, 0(x10) // Write back to DATA0
598+ */
599+ if (!riscv_dm_write (hart -> dbg_module , RV_DM_PROGBUF1 , 0xc1040001U ))
600+ return ;
601+
602+ /*
603+ * progbuf 2
604+ * c.sw x8, 0(x11) // Write addy to DATA1
605+ * c.ebreak
606+ */
607+ if (!riscv_dm_write (hart -> dbg_module , RV_DM_PROGBUF2 , 0x9002c180U ))
608+ return ;
609+
610+ /* StaticUpdatePROGBUFRegs */
611+ uint32_t rr ;
612+ if (!riscv_dm_read (hart -> dbg_module , 0x12U , & rr )) {
613+ DEBUG_ERROR ("Could not get hart info\n" );
614+ return ;
615+ }
616+ DEBUG_INFO ("rr: %08" PRIx32 "\n" , rr );
617+ const uint32_t data0_offset = 0xe0000000U | (rr & 0x7ffU );
618+ if (!riscv_dm_write (hart -> dbg_module , RV_DM_DATA0 , data0_offset )) // DATA0's location in memory.
619+ return ;
620+ if (!riscv_dm_write (hart -> dbg_module , RV_DM_ABST_COMMAND , 0x0023100aU )) // Copy data to x10
621+ return ;
622+ if (!riscv_dm_write (hart -> dbg_module , RV_DM_DATA0 , data0_offset + 4U )) // DATA1's location in memory.
623+ return ;
624+ if (!riscv_dm_write (hart -> dbg_module , RV_DM_ABST_COMMAND , 0x0023100bU )) // Copy data to x11
625+ return ;
626+ // if (!riscv_dm_write(hart->dbg_module, RV_DM_DATA0, 0x40022010U)) // FLASH->CTLR
627+ // return;
628+ // if (!riscv_dm_write(hart->dbg_module, RV_DM_ABST_COMMAND, 0x0023100cU)) // Copy data to x12
629+ // return;
630+ // #define CR_PAGE_PG ((uint32_t)0x00010000)
631+ // #define CR_BUF_LOAD ((uint32_t)0x00040000)
632+ // if (!riscv_dm_write(hart->dbg_module, RV_DM_DATA0, CR_PAGE_PG | CR_BUF_LOAD))
633+ // return;
634+ // if (!riscv_dm_write(hart->dbg_module, RV_DM_ABST_COMMAND, 0x0023100dU)) // Copy data to x13
635+ // return;
636+
637+ /* Enable auto-exec */
638+ // if (!riscv_dm_write(hart->dbg_module, RV_DM_ABST_AUTO, 1U))
639+ // return;
640+
641+ if (!riscv_dm_write (hart -> dbg_module , RV_DM_DATA1 , src ))
642+ return ;
643+ if (!riscv_dm_write (hart -> dbg_module , RV_DM_ABST_COMMAND , 0x00241000U ) || !riscv_command_wait_complete (hart ))
644+ return ;
645+
646+ /* Extract back the data from arg0 */
647+ uint32_t value = 0 ;
648+ if (!riscv_dm_read (hart -> dbg_module , RV_DM_DATA0 , & value ))
649+ return ;
650+
651+ riscv32_unpack_data (dest , value , access_width );
652+ }
653+
654+ static void riscv32_abstract_progbuf_mem_write (
655+ riscv_hart_s * const hart , const target_addr_t dest , const void * const src , const size_t len )
656+ {
657+ DEBUG_TARGET ("Performing %zu byte write of %08" PRIx32 " using PROGBUF\n" , len , dest );
658+
659+ (void )hart ;
660+ (void )dest ;
661+ (void )src ;
662+ (void )len ;
663+
664+ // /* Figure out the maximal width of access to perform, up to the bitness of the target */
665+ // const uint8_t access_width = riscv_mem_access_width(hart, dest, len);
666+ // const uint8_t access_length = 1U << access_width;
667+ // /* Build the access command */
668+ // const uint32_t command = RV_DM_ABST_CMD_ACCESS_MEM | RV_ABST_WRITE | (access_width << RV_ABST_MEM_ACCESS_SHIFT) |
669+ // (access_length < len ? RV_ABST_MEM_ADDR_POST_INC : 0U);
670+ // /* Write the address to write to arg1 */
671+ // if (!riscv_dm_write(hart->dbg_module, RV_DM_DATA1, dest))
672+ // return;
673+ // const uint8_t *const data = (const uint8_t *)src;
674+ // for (size_t offset = 0; offset < len; offset += access_length) {
675+ // /* Pack the data to write into arg0 */
676+ // uint32_t value = riscv32_pack_data(data + offset, access_width);
677+ // if (!riscv_dm_write(hart->dbg_module, RV_DM_DATA0, value))
678+ // return;
679+ // /* Execute the write */
680+ // if (!riscv_dm_write(hart->dbg_module, RV_DM_ABST_COMMAND, command) || !riscv_command_wait_complete(hart))
681+ // return;
682+ // }
683+ }
684+
685+ static void riscv32_mem_read (target_s * const target , void * const dest , const target_addr_t src , const size_t len )
552686{
553687 /* If we're asked to do a 0-byte read, do nothing */
554688 if (!len ) {
@@ -559,8 +693,15 @@ void riscv32_mem_read(target_s *const target, void *const dest, const target_add
559693 riscv_hart_s * const hart = riscv_hart_struct (target );
560694 if (hart -> flags & RV_HART_FLAG_MEMORY_SYSBUS )
561695 riscv32_sysbus_mem_read (hart , dest , src , len );
562- else
696+ else if ( hart -> flags & RV_HART_FLAG_MEMORY_ABSTRACT ) {
563697 riscv32_abstract_mem_read (hart , dest , src , len );
698+ if (hart -> status == RISCV_HART_NOT_SUPP ) {
699+ DEBUG_WARN ("Abstract memory access not supported, falling back to prog buffer\n" );
700+ hart -> flags &= (uint8_t )~RV_HART_FLAG_MEMORY_ABSTRACT ;
701+ riscv32_abstract_progbuf_mem_read (hart , dest , src , len );
702+ }
703+ } else
704+ riscv32_abstract_progbuf_mem_read (hart , dest , src , len );
564705
565706#if ENABLE_DEBUG
566707 DEBUG_PROTO ("%s: @ %08" PRIx32 " len %zu:" , __func__ , src , len );
@@ -578,7 +719,7 @@ void riscv32_mem_read(target_s *const target, void *const dest, const target_add
578719#endif
579720}
580721
581- void riscv32_mem_write (target_s * const target , const target_addr_t dest , const void * const src , const size_t len )
722+ static void riscv32_mem_write (target_s * const target , const target_addr_t dest , const void * const src , const size_t len )
582723{
583724#if ENABLE_DEBUG
584725 DEBUG_PROTO ("%s: @ %" PRIx32 " len %zu:" , __func__ , dest , len );
@@ -601,8 +742,15 @@ void riscv32_mem_write(target_s *const target, const target_addr_t dest, const v
601742 riscv_hart_s * const hart = riscv_hart_struct (target );
602743 if (hart -> flags & RV_HART_FLAG_MEMORY_SYSBUS )
603744 riscv32_sysbus_mem_write (hart , dest , src , len );
604- else
745+ else if ( hart -> flags & RV_HART_FLAG_MEMORY_ABSTRACT ) {
605746 riscv32_abstract_mem_write (hart , dest , src , len );
747+ if (hart -> status == RISCV_HART_NOT_SUPP ) {
748+ DEBUG_WARN ("Abstract memory access not supported, falling back to prog buffer\n" );
749+ hart -> flags &= (uint8_t )~RV_HART_FLAG_MEMORY_ABSTRACT ;
750+ riscv32_abstract_progbuf_mem_write (hart , dest , src , len );
751+ }
752+ } else
753+ riscv32_abstract_progbuf_mem_write (hart , dest , src , len );
606754}
607755
608756/*
0 commit comments